<template>
  <a-modal
    :open="open"
    title="新建多维表格文件"
    :confirm-loading="loading"
    @ok="handleOk"
    @cancel="handleCancel"
  >
    <a-form
      ref="formRef"
      :model="formState"
      :rules="rules"
      layout="vertical"
    >
      <a-form-item label="图标" name="icon">
        <a-select
          v-model:value="formState.icon"
          :options="iconSelectOptions"
          :show-search="false"
        >
          <template #option="{ value: optValue }">
            <span class="file-create-modal__option">
              <component
                :is="resolveBitableIcon(optValue)"
                class="file-create-modal__option-icon"
              />
              <span>{{ labelForKey(optValue) }}</span>
            </span>
          </template>
          <template #label="{ value: labelValue }">
            <span class="file-create-modal__selected">
              <component
                :is="resolveBitableIcon(labelValue)"
                class="file-create-modal__selected-icon"
              />
              <span>{{ labelForKey(labelValue) }}</span>
            </span>
          </template>
        </a-select>
      </a-form-item>
      <a-form-item label="文件名" name="name">
        <a-input
          v-model:value="formState.name"
          placeholder="请输入文件名"
          :maxlength="100"
        />
      </a-form-item>
      <a-form-item label="描述" name="description">
        <a-textarea
          v-model:value="formState.description"
          placeholder="可选，文件用途描述"
          :rows="2"
          :maxlength="500"
        />
      </a-form-item>
    </a-form>
  </a-modal>
</template>

<script setup lang="ts">
import { ref, reactive, computed, watch } from 'vue'
import type { FormInstance } from 'ant-design-vue'
import { useBitableStore } from '@/stores/bitable'
import {
  BITABLE_ICON_OPTIONS,
  DEFAULT_BITABLE_ICON,
  resolveBitableIcon,
  type BitableIconKey,
} from './bitableIcons'

const props = defineProps<{
  open: boolean
}>()

const emit = defineEmits<{
  (e: 'success', fileId: string): void
  (e: 'cancel'): void
}>()

const store = useBitableStore()
const formRef = ref<FormInstance | null>(null)
const loading = ref(false)

/** a-select options: value = icon key, label rendered through #option template. */
const iconSelectOptions = computed(() =>
  BITABLE_ICON_OPTIONS.map((o) => ({ value: o.value, label: o.label })),
)

function labelForKey(key: string): string {
  return BITABLE_ICON_OPTIONS.find((o) => o.value === key)?.label ?? key
}

const formState = reactive({
  name: '',
  icon: DEFAULT_BITABLE_ICON as BitableIconKey,
  description: '',
})

const rules = {
  name: [
    { required: true, message: '请输入文件名', trigger: 'blur' },
    { min: 1, max: 100, message: '文件名长度 1-100', trigger: 'blur' },
  ],
}

watch(
  () => props.open,
  (val) => {
    if (val) {
      formState.name = ''
      formState.icon = DEFAULT_BITABLE_ICON
      formState.description = ''
    }
  },
)

async function handleOk(): Promise<void> {
  try {
    await formRef.value?.validate()
  } catch {
    return
  }

  loading.value = true
  try {
    const file = await store.createFile(
      formState.name.trim(),
      formState.icon,
      formState.description.trim(),
    )
    if (file) emit('success', file.id)
  } finally {
    loading.value = false
  }
}

function handleCancel(): void {
  emit('cancel')
}
</script>

<style scoped>
.file-create-modal__option,
.file-create-modal__selected {
  display: inline-flex;
  align-items: center;
  gap: 8px;
}

.file-create-modal__option-icon,
.file-create-modal__selected-icon {
  font-size: 16px;
  color: var(--color-primary, #1a1a1a);
}
</style>
