<script setup>
import { computed, onBeforeUnmount, onMounted, ref, watch } from 'vue'
import hotkeys from 'hotkeys-js'
import { ElMessage, ElMessageBox } from 'element-plus'
import { storeToRefs } from 'pinia'

import GlobalSearchModal from '@/components/search/GlobalSearchModal.vue'
import LinkEditorDialog from '@/components/links/LinkEditorDialog.vue'
import LinkViewDialog from '@/components/links/LinkViewDialog.vue'
import ImportExportDialog from '@/components/links/ImportExportDialog.vue'
import BrowserBookmarkImportDialog from '@/components/links/BrowserBookmarkImportDialog.vue'
import SettingsDrawer from '@/components/settings/SettingsDrawer.vue'

import { useLinksStore } from '@/stores/links'
import { useSettingsStore } from '@/stores/settings'
import { useTheme } from '@/composables/useTheme'

const linksStore = useLinksStore()
const settingsStore = useSettingsStore()

// 初始化主题
const { initTheme } = useTheme()

const { links, recentLinks, isLoading, isReady } = storeToRefs(linksStore)
const { searchShortcut } = storeToRefs(settingsStore)

const searchVisible = ref(false)
const editorVisible = ref(false)
const viewVisible = ref(false)
const importVisible = ref(false)
const browserBookmarkImportVisible = ref(false)
const settingsVisible = ref(false)
const editorMode = ref('create')
const activeLink = ref({})

const totalCount = computed(() => links.value.length)
const listLoading = computed(() => !isReady.value && isLoading.value)

async function prepareStores() {
  await Promise.all([linksStore.ensureLoaded(), settingsStore.ensureLoaded()])
}

function openSearch() {
  searchVisible.value = true
}

function openCreate() {
  editorMode.value = 'create'
  activeLink.value = {}
  editorVisible.value = true
}

function openImport() {
  importVisible.value = true
}

function openBrowserBookmarkImport() {
  browserBookmarkImportVisible.value = true
}

function openForEdit(link) {
  editorMode.value = 'edit'
  activeLink.value = link
  editorVisible.value = true
}

function openForView(link) {
  activeLink.value = link
  viewVisible.value = true
}

function openSettings() {
  settingsVisible.value = true
}

async function handleLinkSubmission(payload) {
  try {
    if (editorMode.value === 'edit' && activeLink.value?.id) {
      await linksStore.updateLink(activeLink.value.id, payload)
      ElMessage.success('书签已更新')
    } else {
      await linksStore.addLink(payload)
      ElMessage.success('书签已添加')
    }
  } catch (error) {
    console.error(error)
    ElMessage.error(error.message ?? '保存书签失败')
  }
}

async function handleOpenLink(link) {
  if (!link?.url) return
  window.open(link.url, '_blank', 'noopener,noreferrer')
  await linksStore.recordVisit(link.id)
}

async function handleDelete(link) {
  try {
    await ElMessageBox.confirm(`确定要将「${link.title}」从书签中移除吗？`, '删除书签', {
      confirmButtonText: '删除',
      cancelButtonText: '取消',
      type: 'warning',
    })
    await linksStore.removeLink(link.id)
    ElMessage.success('书签已删除')
  } catch (error) {
    if (error === 'cancel' || error === 'close') {
      return
    }
    console.error(error)
    ElMessage.error('删除动作已取消或失败')
  }
}

function normalizeShortcut(shortcut) {
  if (!shortcut) return ''
  return shortcut.replace(/\s+/g, '').toLowerCase()
}

function bindSearchHotkey(shortcut) {
  const normalized = normalizeShortcut(shortcut)
  if (!normalized) return
  hotkeys.unbind(normalized)
  hotkeys(normalized, (event) => {
    event.preventDefault()
    openSearch()
  })
}

onMounted(async () => {
  await prepareStores()
  // 主题会在 useTheme 的 onMounted 中自动初始化
  bindSearchHotkey(searchShortcut.value ?? 'ctrl+k')
  hotkeys('esc', () => {
    searchVisible.value = false
  })
})

watch(searchShortcut, (next, prev) => {
  const previous = normalizeShortcut(prev)
  const nextNormalized = normalizeShortcut(next)
  if (previous) {
    hotkeys.unbind(previous)
  }
  bindSearchHotkey(nextNormalized)
})

onBeforeUnmount(() => {
  hotkeys.unbind(normalizeShortcut(searchShortcut.value ?? 'ctrl+k'))
  hotkeys.unbind('esc')
})
</script>

<template>
  <RouterView v-slot="{ Component }">
    <component
      :is="Component"
      v-if="Component"
      :links="links"
      :recent-links="recentLinks"
      :total-count="totalCount"
      :list-loading="listLoading"
      :shortcut-label="searchShortcut"
      @open-search="openSearch"
      @create-link="openCreate"
      @import-data="openImport"
      @import-browser-bookmarks="openBrowserBookmarkImport"
      @open-settings="openSettings"
      @open-link="handleOpenLink"
      @edit-link="openForEdit"
      @delete-link="handleDelete"
      @view-link="openForView"
    />
  </RouterView>

  <GlobalSearchModal
    v-model="searchVisible"
    :search-shortcut="searchShortcut"
    @select="handleOpenLink"
    @create="openCreate"
  />

  <LinkEditorDialog v-model="editorVisible" :mode="editorMode" :link="activeLink" @submit="handleLinkSubmission" />

  <LinkViewDialog
    v-model="viewVisible"
    :link="activeLink"
    @edit="openForEdit"
    @open="handleOpenLink"
    @delete="handleDelete"
  />

  <ImportExportDialog v-model="importVisible" />

  <BrowserBookmarkImportDialog v-model="browserBookmarkImportVisible" />

  <SettingsDrawer v-model="settingsVisible" />
</template>
