<template>
  <div class="page-builder-blocks">
    <Draggable
      v-model="blocksWritable"
      item-key="id"
      handle=".drag-handle"
      :animation="220"
      ghost-class="block-ghost"
      chosen-class="block-chosen"
      drag-class="block-dragging"
      class="blocks-drag-list"
    >
      <template #item="{ element: block, index: idx }">
        <div class="block-card">
          <div class="block-head">
            <span class="block-head-left">
              <span class="drag-handle" title="按住拖拽排序">
                <el-icon><Rank /></el-icon>
              </span>
              <span class="block-type">{{ typeLabel(block.type) }}</span>
            </span>
            <div class="block-actions">
              <el-button link type="danger" @click="remove(idx)">删除</el-button>
            </div>
          </div>

      <template v-if="block.type === 'heading'">
        <el-form label-width="88px" size="small">
          <el-form-item label="标题文字">
            <el-input v-model="block.props.text" placeholder="标题" />
          </el-form-item>
          <el-form-item label="级别 (1-6)">
            <el-input-number v-model="block.props.level" :min="1" :max="6" />
          </el-form-item>
          <PageBuilderAnimFields v-model="block.animation" />
        </el-form>
      </template>

      <template v-else-if="block.type === 'text'">
        <el-form label-width="88px" size="small">
          <el-form-item label="HTML 模式">
            <el-switch v-model="block.props.html" />
          </el-form-item>
          <el-form-item label="内容">
            <el-input v-model="block.props.text" type="textarea" :rows="4" placeholder="纯文本或 HTML" />
          </el-form-item>
          <PageBuilderAnimFields v-model="block.animation" />
        </el-form>
      </template>

      <template v-else-if="block.type === 'link_list'">
        <div class="link-items">
          <div v-for="(it, j) in block.props.items" :key="j" class="link-row">
            <el-input v-model="it.label" placeholder="显示文字" style="width: 110px" />
            <el-input v-model="it.url" placeholder="链接" style="flex: 1; min-width: 120px" />
            <el-select v-model="it.target" style="width: 95px">
              <el-option label="当前页" value="_self" />
              <el-option label="新窗口" value="_blank" />
            </el-select>
            <el-button type="primary" link @click="openPicker(it)">选择</el-button>
            <el-button link type="danger" @click="block.props.items.splice(j, 1)">删</el-button>
          </div>
          <el-button link type="primary" @click="block.props.items.push({ label: '', url: '', target: '_self' })">
            + 添加链接
          </el-button>
        </div>
        <el-form label-width="88px" size="small" style="margin-top: 8px">
          <PageBuilderAnimFields v-model="block.animation" />
        </el-form>
      </template>

      <template v-else-if="block.type === 'button'">
        <el-form label-width="88px" size="small">
          <el-form-item label="按钮文字">
            <el-input v-model="block.props.text" />
          </el-form-item>
          <el-form-item label="链接">
            <div class="url-row">
              <el-input v-model="block.props.url" placeholder="#" />
              <el-button type="primary" @click="openPicker(block.props, 'url')">选择链接</el-button>
            </div>
          </el-form-item>
          <el-form-item label="样式">
            <el-radio-group v-model="block.props.variant">
              <el-radio-button label="primary">主色</el-radio-button>
              <el-radio-button label="ghost">线框</el-radio-button>
            </el-radio-group>
          </el-form-item>
          <PageBuilderAnimFields v-model="block.animation" />
        </el-form>
      </template>

      <template v-else-if="block.type === 'html'">
        <el-input v-model="block.props.html" type="textarea" :rows="6" placeholder="HTML 片段" />
        <el-form label-width="88px" size="small" style="margin-top: 8px">
          <PageBuilderAnimFields v-model="block.animation" />
        </el-form>
      </template>

      <template v-else-if="block.type === 'spacer'">
        <el-form label-width="88px" size="small">
          <el-form-item label="高度(px)">
            <el-input-number v-model="block.props.height" :min="0" :max="500" />
          </el-form-item>
        </el-form>
      </template>

      <template v-else-if="block.type === 'divider'">
        <span class="muted">分割线</span>
      </template>

      <template v-else-if="block.type === 'section'">
        <el-form label-width="88px" size="small">
          <el-form-item label="内边距">
            <el-input v-model="block.props.padding" placeholder="24px 16px" />
          </el-form-item>
          <el-form-item label="最大宽度">
            <el-input v-model="block.props.maxWidth" placeholder="960px" />
          </el-form-item>
          <el-form-item label="背景色">
            <el-input v-model="block.props.background" placeholder="transparent" />
          </el-form-item>
        </el-form>
        <div class="nested-label">区块内模块（可继续嵌套）</div>
        <PageBuilderBlocks
          :blocks="block.children || []"
          :site-id="siteId"
          @update:blocks="(v) => patchSectionChildren(idx, v)"
        />
      </template>

      <template v-else>
        <span class="muted">未知类型 {{ block.type }}</span>
      </template>
        </div>
      </template>
    </Draggable>

    <div class="add-bar">
      <el-dropdown trigger="click" @command="addBlock">
        <el-button type="primary">
          + 添加模块 <el-icon class="el-icon--right"><ArrowDown /></el-icon>
        </el-button>
        <template #dropdown>
          <el-dropdown-menu>
            <el-dropdown-item command="heading">标题</el-dropdown-item>
            <el-dropdown-item command="text">段落文字</el-dropdown-item>
            <el-dropdown-item command="link_list">链接组</el-dropdown-item>
            <el-dropdown-item command="button">按钮</el-dropdown-item>
            <el-dropdown-item command="html">HTML</el-dropdown-item>
            <el-dropdown-item command="spacer">留白</el-dropdown-item>
            <el-dropdown-item command="divider">分割线</el-dropdown-item>
            <el-dropdown-item command="section">区块（嵌套）</el-dropdown-item>
          </el-dropdown-menu>
        </template>
      </el-dropdown>
    </div>

    <LinkPickerDialog v-model="pickerVisible" :site-id="siteId" @select="onPicked" />
  </div>
</template>

<script setup>
import { computed, ref } from 'vue'
import { ArrowDown, Rank } from '@element-plus/icons-vue'
import Draggable from 'vuedraggable'
import LinkPickerDialog from './LinkPickerDialog.vue'
import PageBuilderAnimFields from './PageBuilderAnimFields.vue'

defineOptions({ name: 'PageBuilderBlocks' })

const props = defineProps({
  blocks: { type: Array, default: () => [] },
  siteId: { type: String, default: '' }
})
const emit = defineEmits(['update:blocks'])

const blocksWritable = computed({
  get() {
    return props.blocks
  },
  set(val) {
    emit('update:blocks', val)
  }
})

function typeLabel(t) {
  const m = {
    heading: '标题',
    text: '段落',
    link_list: '链接组',
    button: '按钮',
    html: 'HTML',
    spacer: '留白',
    divider: '分割线',
    section: '区块'
  }
  return m[t] || t
}

function newId() {
  return 'b-' + Date.now() + '-' + Math.random().toString(36).slice(2, 8)
}

function addBlock(cmd) {
  const list = [...props.blocks]
  const b = {
    id: newId(),
    type: cmd,
    props: {},
    animation: { enter: 'fadeIn', delay_ms: 0, duration_ms: 600 }
  }
  switch (cmd) {
    case 'heading':
      b.props = { text: '新标题', level: 2 }
      break
    case 'text':
      b.props = { text: '段落内容', html: false }
      break
    case 'link_list':
      b.props = { items: [{ label: '链接', url: '/', target: '_self' }] }
      break
    case 'button':
      b.props = { text: '按钮', url: '#', variant: 'primary' }
      break
    case 'html':
      b.props = { html: '<p>内容</p>' }
      break
    case 'spacer':
      b.props = { height: 24 }
      break
    case 'divider':
      b.props = {}
      break
    case 'section':
      b.props = { padding: '24px 0', maxWidth: '960px', background: 'transparent' }
      b.children = []
      break
    default:
      b.props = {}
  }
  list.push(b)
  emit('update:blocks', list)
}

function remove(idx) {
  const list = [...props.blocks]
  list.splice(idx, 1)
  emit('update:blocks', list)
}

const pickerVisible = ref(false)
const pickTarget = ref(null)

function openPicker(target, key) {
  if (key === 'url') pickTarget.value = { obj: target, key: 'url' }
  else pickTarget.value = { item: target }
  pickerVisible.value = true
}

function onPicked(url) {
  const t = pickTarget.value
  if (t?.item) t.item.url = url
  if (t?.obj && t?.key) t.obj[t.key] = url
  pickTarget.value = null
}

function patchSectionChildren(idx, children) {
  const list = props.blocks.map((b, i) => (i === idx ? { ...b, children: [...children] } : b))
  emit('update:blocks', list)
}
</script>

<style scoped>
.page-builder-blocks {
  border: 1px solid #ebeef5;
  border-radius: 8px;
  padding: 12px;
  background: #fafafa;
  max-height: 62vh;
  overflow-y: auto;
}
.block-card {
  background: #fff;
  border: 1px solid #dcdfe6;
  border-radius: 8px;
  padding: 12px;
  margin-bottom: 12px;
}
.block-head {
  display: flex;
  justify-content: space-between;
  align-items: center;
  margin-bottom: 10px;
  padding-bottom: 8px;
  border-bottom: 1px solid #ebeef5;
}
.block-type {
  font-weight: 600;
  color: #409eff;
}
.link-items {
  display: flex;
  flex-direction: column;
  gap: 8px;
}
.link-row {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 8px;
}
.url-row {
  display: flex;
  gap: 8px;
  width: 100%;
  align-items: center;
}
.url-row .el-input {
  flex: 1;
}
.nested-label {
  font-size: 13px;
  color: #606266;
  margin: 8px 0;
}
.add-bar {
  margin-top: 8px;
}
.muted {
  color: #909399;
  font-size: 13px;
}
.blocks-drag-list {
  min-height: 4px;
}
.block-head-left {
  display: inline-flex;
  align-items: center;
  gap: 4px;
}
.drag-handle {
  cursor: grab;
  display: inline-flex;
  align-items: center;
  padding: 4px 6px;
  margin-right: 4px;
  color: #909399;
  border-radius: 4px;
  user-select: none;
  touch-action: none;
}
.drag-handle:hover {
  color: #409eff;
  background: #ecf5ff;
}
.drag-handle:active {
  cursor: grabbing;
}
:deep(.block-ghost) {
  opacity: 0.55;
  background: #ecf5ff !important;
  border: 1px dashed #409eff !important;
}
:deep(.block-chosen) {
  box-shadow: 0 2px 12px rgba(64, 158, 255, 0.25);
}
:deep(.block-dragging) {
  opacity: 0.95;
}
</style>
