/**
 * designStore.js — LiteDesign 可视化编辑器状态管理
 *
 * 职责：
 *  - 组件列表（增删改排）
 *  - 当前选中组件
 *  - 撤销/重做历史栈
 *  - 模板元信息
 *  - 编辑模式（添加/选中/移动）
 */

import { defineStore } from 'pinia'
import { ref, computed, shallowRef } from 'vue'
import { COMPONENT_REGISTRY } from '../views/design/utils/componentRegistry.js'

const MAX_HISTORY = 50

export const useDesignStore = defineStore('design', () => {
  /* ========== 状态 ========== */
  const templateId = ref(null)
  const templateName = ref('未命名模板')
  const terminal = ref('h5')            // h5 | pc | miniapp
  const themeName = ref('经典红')

  const components = ref([])             // 组件列表 [{ id, type, props }]
  const selectedId = ref(null)           // 当前选中组件ID
  const editingMode = ref('select')      // select | add | move

  // 撤销/重做历史栈
  const undoStack = ref([])              // 存储 components 快照
  const redoStack = ref([])

  // UI 状态
  const previewDevice = ref('mobile')    // mobile | tablet | desktop
  const isSaving = ref(false)
  const isPublishing = ref(false)
  const showLayerPanel = ref(true)
  const widgetSearch = ref('')

  /* ========== 计算属性 ========== */
  const selectedComponent = computed(() => {
    if (!selectedId.value) return null
    return components.value.find(c => c.id === selectedId.value) || null
  })

  const selectedSchema = computed(() => {
    if (!selectedComponent.value) return null
    return COMPONENT_REGISTRY[selectedComponent.value.type] || null
  })

  const componentCount = computed(() => components.value.length)

  const canUndo = computed(() => undoStack.value.length > 0)
  const canRedo = computed(() => redoStack.value.length > 0)

  const previewWidth = computed(() => {
    const widths = { mobile: 375, tablet: 768, desktop: 1200 }
    return widths[previewDevice.value] || 375
  })

  /* ========== 历史栈操作 ========== */
  function takeSnapshot() {
    undoStack.value.push(JSON.stringify(components.value))
    if (undoStack.value.length > MAX_HISTORY) {
      undoStack.value.shift()
    }
    // 新操作清除 redo 栈
    redoStack.value = []
  }

  function undo() {
    if (!canUndo.value) return
    redoStack.value.push(JSON.stringify(components.value))
    const prev = undoStack.value.pop()
    components.value = JSON.parse(prev)
    // 尝试维持选中状态
    if (selectedId.value && !components.value.find(c => c.id === selectedId.value)) {
      selectedId.value = null
    }
  }

  function redo() {
    if (!canRedo.value) return
    undoStack.value.push(JSON.stringify(components.value))
    const next = redoStack.value.pop()
    components.value = JSON.parse(next)
    if (selectedId.value && !components.value.find(c => c.id === selectedId.value)) {
      selectedId.value = null
    }
  }

  /* ========== 组件 CRUD ========== */
  let _idCounter = Date.now()

  function _genId() {
    return 'comp_' + (_idCounter++).toString(36)
  }

  function addComponent(type, index) {
    takeSnapshot()
    const schema = COMPONENT_REGISTRY[type]
    if (!schema) return null

    const newComp = {
      id: _genId(),
      type,
      props: JSON.parse(JSON.stringify(schema.defaultProps))
    }

    if (index !== undefined && index >= 0 && index <= components.value.length) {
      components.value.splice(index, 0, newComp)
    } else {
      components.value.push(newComp)
    }

    selectedId.value = newComp.id
    return newComp
  }

  function removeComponent(id) {
    const idx = components.value.findIndex(c => c.id === id)
    if (idx === -1) return
    takeSnapshot()
    components.value.splice(idx, 1)
    if (selectedId.value === id) {
      selectedId.value = components.value.length > 0
        ? components.value[Math.min(idx, components.value.length - 1)].id
        : null
    }
  }

  function moveComponent(fromIdx, toIdx) {
    if (fromIdx === toIdx) return
    takeSnapshot()
    const [moved] = components.value.splice(fromIdx, 1)
    components.value.splice(toIdx, 0, moved)
  }

  function updateComponentProps(id, patch) {
    const comp = components.value.find(c => c.id === id)
    if (!comp) return
    // 深度合并
    comp.props = deepMerge(comp.props, patch)
  }

  function selectComponent(id) {
    selectedId.value = id
  }

  function clearSelection() {
    selectedId.value = null
  }

  /* ========== 批量/排序 ========== */
  function setComponents(newList) {
    takeSnapshot()
    components.value = newList
    selectedId.value = null
  }

  function sortComponents(orderedIds) {
    const sorted = orderedIds
      .map(id => components.value.find(c => c.id === id))
      .filter(Boolean)
    if (sorted.length !== components.value.length) return
    takeSnapshot()
    components.value = sorted
  }

  /* ========== 模板 ========== */
  function loadTemplate(data) {
    components.value = (data.components || []).map(c => ({
      id: c.id || _genId(),
      type: c.type,
      props: JSON.parse(JSON.stringify(
        (COMPONENT_REGISTRY[c.type]?.defaultProps || {})
      ))
    }))
    // 合并已有 props
    ;(data.components || []).forEach((src, i) => {
      if (src.props && components.value[i]) {
        components.value[i].props = deepMerge(components.value[i].props, src.props)
      }
    })
    templateId.value = data.id || null
    templateName.value = data.name || '未命名模板'
    terminal.value = data.terminal || 'h5'
    themeName.value = data.themeName || '经典红'
    selectedId.value = null
    undoStack.value = []
    redoStack.value = []
  }

  function getTemplateData() {
    return {
      id: templateId.value,
      name: templateName.value,
      terminal: terminal.value,
      themeName: themeName.value,
      components: components.value.map(c => ({
        id: c.id,
        type: c.type,
        props: JSON.parse(JSON.stringify(c.props))
      }))
    }
  }

  function getRenderData() {
    return {
      themeName: themeName.value,
      components: components.value.map(c => ({
        type: c.type,
        props: JSON.parse(JSON.stringify(c.props))
      }))
    }
  }

  /* ========== 辅助 ========== */
  function deepMerge(target, source) {
    const result = { ...target }
    for (const key of Object.keys(source)) {
      if (source[key] && typeof source[key] === 'object' && !Array.isArray(source[key])) {
        result[key] = deepMerge(result[key] || {}, source[key])
      } else {
        result[key] = source[key]
      }
    }
    return result
  }

  function reset() {
    components.value = []
    selectedId.value = null
    undoStack.value = []
    redoStack.value = []
    templateId.value = null
    templateName.value = '未命名模板'
    isSaving.value = false
    isPublishing.value = false
  }

  return {
    // state
    templateId, templateName, terminal, themeName,
    components, selectedId, editingMode,
    undoStack, redoStack,
    previewDevice, isSaving, isPublishing, showLayerPanel, widgetSearch,
    // computed
    selectedComponent, selectedSchema, componentCount, canUndo, canRedo, previewWidth,
    // actions
    undo, redo,
    addComponent, removeComponent, moveComponent,
    updateComponentProps, selectComponent, clearSelection,
    setComponents, sortComponents,
    loadTemplate, getTemplateData, getRenderData,
    reset
  }
})
