<template>
  <a-spin :spinning="spinning">
    <a-form
      ref="baseFormRef"
      :model="baseFormState"
      :rules="rules"
      :label-col="{ style: { width: '100px' } }"
      :wrapper-col="{ style: { width: '330px' } }"
    >
      <a-form-item label="设备名称" name="deviceName">
        <a-input
          v-model:value.trim="baseFormState.deviceName"
          placeholder="请输入设备名称"
          :maxlength="10"
          show-count
          :style="inputStyle"
        />
      </a-form-item>
      <a-form-item label="安装方式" name="installWay">
        <a-select
          v-model:value="baseFormState.installWay"
          placeholder="请选择安装方式"
          :style="inputStyle"
        >
          <a-select-option value="Wall">墙装</a-select-option>
          <a-select-option value="Ceiling">顶装</a-select-option>
        </a-select>
      </a-form-item>
      <a-form-item label="安装位置" name="installPosition">
        <a-select
          v-model:value="baseFormState.installPosition"
          placeholder="请选择安装位置"
          :style="inputStyle"
        >
          <a-select-option value="Toilet">卫生间</a-select-option>
          <a-select-option value="Bedroom">卧室</a-select-option>
          <a-select-option value="LivingRoom">客厅</a-select-option>
          <a-select-option value="Restaurant">餐厅</a-select-option>
        </a-select>
      </a-form-item>

      <a-form-item label="X范围" class="outSideInput">
        <div class="rangeInput">
          <a-form-item name="xRangeStart">
            <a-input
              v-model:value.trim="baseFormState.xRangeStart"
              name="xRangeStart"
              :style="rangeInputStyle"
              placeholder="请输入"
            >
              <template #suffix>
                <a-tooltip>
                  <template #title>
                    <div>范围：-200 - 200 cm</div>
                  </template>
                  <info-circle-outlined style="color: rgba(0, 0, 0, 0.45)" />
                </a-tooltip>
              </template>
            </a-input>
          </a-form-item>

          <span class="line"> — </span>
          <a-form-item name="xRangeEnd">
            <a-input
              v-model:value.trim="baseFormState.xRangeEnd"
              name="xRangeEnd"
              :style="rangeInputStyle"
              placeholder="请输入"
            >
              <template #suffix>
                <a-tooltip>
                  <template #title>
                    <div>范围：-200 - 200 cm</div>
                  </template>
                  <info-circle-outlined style="color: rgba(0, 0, 0, 0.45)" />
                </a-tooltip>
              </template>
            </a-input>
          </a-form-item>
        </div>
      </a-form-item>
      <a-form-item label="Y范围" class="outSideInput">
        <div class="rangeInput">
          <a-form-item name="yRangeStart">
            <a-input
              v-model:value.trim="baseFormState.yRangeStart"
              name="yRangeStart"
              :style="rangeInputStyle"
              placeholder="请输入"
            >
              <template #suffix>
                <a-tooltip>
                  <template #title>
                    <div>范围：-250 - 250 cm</div>
                  </template>
                  <info-circle-outlined style="color: rgba(0, 0, 0, 0.45)" />
                </a-tooltip>
              </template>
            </a-input>
          </a-form-item>

          <span class="line"> — </span>
          <a-form-item name="yRangeEnd">
            <a-input
              v-model:value.trim="baseFormState.yRangeEnd"
              name="yRangeEnd"
              :style="rangeInputStyle"
              placeholder="请输入"
            >
              <template #suffix>
                <a-tooltip>
                  <template #title>
                    <div>范围：-250 - 250 cm</div>
                  </template>
                  <info-circle-outlined style="color: rgba(0, 0, 0, 0.45)" />
                </a-tooltip>
              </template>
            </a-input>
          </a-form-item>
        </div>
      </a-form-item>
      <a-form-item label="Z范围" class="outSideInput">
        <div class="rangeInput">
          <a-form-item name="zRangeStart">
            <a-input
              v-model:value.trim="baseFormState.zRangeStart"
              name="zRangeStart"
              :style="rangeInputStyle"
              placeholder="请输入"
            >
              <template #suffix>
                <a-tooltip>
                  <template #title>
                    <div>范围：0 - 50 cm</div>
                  </template>
                  <info-circle-outlined style="color: rgba(0, 0, 0, 0.45)" />
                </a-tooltip>
              </template>
            </a-input>
          </a-form-item>

          <span class="line"> — </span>
          <a-form-item name="zRangeEnd">
            <a-input
              v-model:value.trim="baseFormState.zRangeEnd"
              name="zRangeEnd"
              :style="rangeInputStyle"
              placeholder="请输入"
            >
              <template #suffix>
                <a-tooltip>
                  <template #title>
                    <div>范围：200 - 300 cm</div>
                  </template>
                  <info-circle-outlined style="color: rgba(0, 0, 0, 0.45)" />
                </a-tooltip>
              </template>
            </a-input>
          </a-form-item>
        </div>
      </a-form-item>

      <a-form-item label="安装高度" name="installHeight">
        <a-input
          v-model:value.trim="baseFormState.installHeight"
          placeholder="请输入安装高度"
          :style="inputStyle"
        >
          <template #suffix>
            <a-tooltip>
              <template #title>
                <div>范围：250 - 370 cm</div>
              </template>
              <info-circle-outlined style="color: rgba(0, 0, 0, 0.45)" />
            </a-tooltip>
          </template>
        </a-input>
      </a-form-item>
      <a-form-item label="正北向夹角" name="northAngle">
        <a-select ref="select" v-model:value="baseFormState.northAngle" :style="inputStyle">
          <a-select-option :value="0">0度</a-select-option>
          <a-select-option :value="90">90度</a-select-option>
          <a-select-option :value="180">180度</a-select-option>
          <a-select-option :value="270">270度</a-select-option>
        </a-select>
      </a-form-item>

      <a-form-item label="归属租户" name="tenantId">
        <a-select
          v-model:value="baseFormState.tenantId"
          placeholder="请选择归属租户"
          :options="tenantOptions"
          :style="inputStyle"
        >
        </a-select>
      </a-form-item>
      <a-form-item label="跌倒确认时间" name="fallingConfirm">
        <a-input
          v-model:value.trim="baseFormState.fallingConfirm"
          placeholder="请输入跌倒确认时间"
          :style="inputStyle"
        >
          <template #suffix>
            <a-tooltip>
              <template #title>
                <div>默认: 53秒</div>
              </template>
              <info-circle-outlined style="color: rgba(0, 0, 0, 0.45)" />
            </a-tooltip>
          </template>
        </a-input>
      </a-form-item>

      <div class="footer" :style="{ marginLeft: '100px' }">
        <a-space>
          <a-button type="primary" :loading="saveBaseLoading" @click="saveBaseConfig"
            >保存配置</a-button
          >
        </a-space>
      </div>
    </a-form>
  </a-spin>
</template>

<script setup lang="ts">
import { ref, reactive, defineOptions } from 'vue'
import { message, type FormInstance } from 'ant-design-vue'
import { InfoCircleOutlined } from '@ant-design/icons-vue'
import type { Rule } from 'ant-design-vue/es/form'
import * as deviceApi from '@/api/device'
import * as tenantAPI from '@/api/tenant'
import type { TenantItem } from '@/api/tenant/types'
import { useUserStore } from '@/stores/user'

defineOptions({
  name: 'deviceBaseConfig',
})

type Props = {
  devId: string // 设备id 查询使用
  clientId: string // 设备id 更新使用
}
const emit = defineEmits<{
  (e: 'success', value: void): void
}>()
const props = withDefaults(defineProps<Props>(), {
  devId: '',
  clientId: '',
})

const userStore = useUserStore()
// 基础配置表单
interface BaseFormState {
  deviceName: string // 设备名称
  installWay: InstallWay // 安装方式
  installPosition: InstallPosition // 安装位置
  xRangeStart: ID // x范围
  xRangeEnd: ID // x范围
  yRangeStart: ID // y范围
  yRangeEnd: ID // y范围
  zRangeStart: ID // z范围
  zRangeEnd: ID // z范围
  installHeight: ID // 安装高度
  northAngle: NorthAngle // 正北向夹角
  tenantId: ID // 租户id
  fallingConfirm: ID // 跌倒确认
}

const spinning = ref(false)
const baseFormState = reactive<BaseFormState>({
  deviceName: '',
  installWay: 'Wall',
  installPosition: 'Toilet',
  xRangeStart: '',
  xRangeEnd: '',
  yRangeStart: '',
  yRangeEnd: '',
  zRangeStart: '',
  zRangeEnd: '',
  installHeight: '',
  northAngle: 0,
  tenantId: null,
  fallingConfirm: 53,
})

// 范围输入框尺寸
const rangeInputStyle = {
  width: '150px',
}
// 普通输入框尺寸
const inputStyle = {
  width: '330px',
}

const baseFormRef = ref<FormInstance>()
const saveBaseLoading = ref(false)
// 保存基础配置
const saveBaseConfig = async () => {
  baseFormRef.value
    ?.validate()
    .then(async () => {
      saveBaseLoading.value = true
      console.log('saveBaseConfig 校验通过', baseFormState, props)
      try {
        await deviceApi.updateDevice({
          clientId: props.clientId,
          userId: userStore?.userInfo?.userId,
          devName: baseFormState.deviceName,
          mountPlain: baseFormState.installWay,
          installPosition: baseFormState.installPosition,
          xxStart: baseFormState.xRangeStart,
          xxEnd: baseFormState.xRangeEnd,
          yyStart: baseFormState.yRangeStart,
          yyEnd: baseFormState.yRangeEnd,
          zzStart: baseFormState.zRangeStart,
          zzEnd: baseFormState.zRangeEnd,
          height: baseFormState.installHeight,
          northAngle: baseFormState.northAngle,
          tenantId: baseFormState?.tenantId,
          fallingConfirm: Number(baseFormState?.fallingConfirm),
        })
        saveBaseLoading.value = false
        message.success('保存成功')
        emit('success')
      } catch (error) {
        console.error('saveBaseConfig 保存失败', error)
        saveBaseLoading.value = false
      }
    })
    .catch((err) => {
      console.error('saveBaseConfig 校验失败', err)
      saveBaseLoading.value = false
    })
}

// 校验输入的范围大小
const createRangeValidator = (min: number, max: number) => async (_rule: Rule, value: string) => {
  if (!value) {
    return Promise.reject(new Error('不能为空'))
  }

  if (!/^-?\d+(\.\d+)?$/.test(value)) {
    return Promise.reject(new Error('必须为数字'))
  }

  const num = parseFloat(value)
  if (num < min || num > max) {
    return Promise.reject(new Error(`范围：${min} ~ ${max}`))
  }

  return Promise.resolve()
}

// 校验起始值和结束值的大小关系
const validateRangeOrder = (startField: string, endField: string) => {
  return async () => {
    const startVal = parseFloat(baseFormState[startField as keyof BaseFormState] as string)
    const endVal = parseFloat(baseFormState[endField as keyof BaseFormState] as string)

    if (startVal >= endVal) {
      return Promise.reject(new Error('结束值须大于起始值'))
    }
    return Promise.resolve()
  }
}

// 统一校验规则
const rules: Record<string, Rule[]> = {
  xRangeStart: [
    {
      required: true,
      validator: createRangeValidator(-200, 200),
      trigger: ['change', 'blur'],
    },
  ],
  xRangeEnd: [
    {
      validator: createRangeValidator(-200, 200),
      trigger: ['change', 'blur'],
    },
    {
      validator: validateRangeOrder('xRangeStart', 'xRangeEnd'),
      trigger: ['change', 'blur'],
    },
  ],
  yRangeStart: [
    {
      validator: createRangeValidator(-250, 250),
      trigger: ['change', 'blur'],
    },
  ],
  yRangeEnd: [
    {
      validator: createRangeValidator(-250, 250),
      trigger: ['change', 'blur'],
    },
    {
      validator: validateRangeOrder('yRangeStart', 'yRangeEnd'),
      trigger: ['change', 'blur'],
    },
  ],
  zRangeStart: [
    {
      validator: createRangeValidator(0, 50),
      trigger: ['change', 'blur'],
    },
  ],
  zRangeEnd: [
    {
      validator: createRangeValidator(200, 300),
      trigger: ['change', 'blur'],
    },
  ],
}

const tenantOptions = ref<{ label: string; value: string }[]>([])
// 获取租户下拉列表
const fetchTenantList = async () => {
  try {
    const res = await tenantAPI.queryTenant({
      pageNo: 1,
      pageSize: 10000,
    })
    const { rows } = res.data
    tenantOptions.value = rows.map((item: TenantItem) => ({
      label: item.tenantName,
      value: item?.tenantId as string,
    }))
  } catch (err) {
    console.log('❌ 获取数据失败', err)
  }
}
fetchTenantList()

// 获取设备回显数据
const fetchDeviceBaseInfo = async () => {
  console.log('fetchDeviceDetail', props)
  if (!props.devId) {
    message.error('设备ID不能为空')
    return
  }
  try {
    spinning.value = true
    const res = await deviceApi.getDeviceDetailByDevId({
      devId: props.devId,
    })
    console.log('✅获取到设备详情', res)
    baseFormState.deviceName = res.data.devName
    baseFormState.installWay = res.data.mountPlain
    baseFormState.installPosition = res.data.installPosition
    baseFormState.xRangeStart = res.data.xxStart
    baseFormState.xRangeEnd = res.data.xxEnd
    baseFormState.yRangeStart = res.data.yyStart
    baseFormState.yRangeEnd = res.data.yyEnd
    baseFormState.zRangeStart = res.data.zzStart
    baseFormState.zRangeEnd = res.data.zzEnd
    baseFormState.installHeight = res.data.height
    baseFormState.northAngle = res.data.northAngle
    baseFormState.tenantId = res.data.tenantId
    baseFormState.fallingConfirm = res.data.fallingConfirm
  } catch (error) {
    console.error('❌获取设备详情失败', error)
  }
  spinning.value = false
}
fetchDeviceBaseInfo()
</script>

<style scoped lang="less">
// 取消嵌套的a-form-item的margin-bottom
:deep(.outSideInput.ant-form-item) {
  margin-bottom: 0;
}

.rangeInput {
  display: flex;
  align-items: baseline;
  gap: 8px;
}
</style>
