<script lang="ts" setup>
import { computed, reactive, ref, watch } from 'vue';

import { Page } from '@vben/common-ui';
import { useAccessStore } from '@vben/stores';

import {
  getResidentCpConfig,
  saveResidentCpConfig,
} from '#/api/legacy/resident-activity';
import { getAllowedSysOrigins } from '#/views/system/shared';

import {
  Button,
  Card,
  Input,
  InputNumber,
  Modal,
  Select,
  Space,
  Spin,
  Table,
  Tag,
  message,
} from 'antdv-next';

defineOptions({ name: 'ResidentCpConfigPage' });

interface CpLevelConfig {
  cabinConfigId?: null | string;
  level: number;
  levelName: string;
  requiredIntimacyValue: number;
}

type RelationType = 'BROTHER' | 'CP' | 'SISTERS';

const CP_LEVEL_COUNT = 6;
const CP_MIN_LEVEL = 0;

const relationTypeOptions: Array<{ label: string; value: RelationType }> = [
  { label: 'CP', value: 'CP' },
  { label: 'Brother', value: 'BROTHER' },
  { label: 'Sisters', value: 'SISTERS' },
];

function defaultLevel(level: number): CpLevelConfig {
  return {
    cabinConfigId: null,
    level,
    levelName: `CP ${level}级`,
    requiredIntimacyValue: 0,
  };
}

function defaultLevels() {
  return Array.from({ length: CP_LEVEL_COUNT }, (_, index) =>
    defaultLevel(index + CP_MIN_LEVEL),
  );
}

function defaultDismissConsumeGolds(): Record<RelationType, number> {
  return {
    BROTHER: 0,
    CP: 0,
    SISTERS: 0,
  };
}

const accessStore = useAccessStore();
const sysOriginOptions = computed(() => {
  const options = getAllowedSysOrigins(accessStore.accessCodes || []);
  return options.length > 0 ? options : getAllowedSysOrigins([]);
});

const loading = ref(false);
const saving = ref(false);

const columns = [
  { dataIndex: 'level', key: 'level', title: '等级', width: 100 },
  { dataIndex: 'levelName', key: 'levelName', title: '等级文案', width: 260 },
  {
    dataIndex: 'requiredIntimacyValue',
    key: 'requiredIntimacyValue',
    title: '所需亲密值',
    width: 220,
  },
];

const form = reactive({
  configured: false,
  dismissConsumeGolds: defaultDismissConsumeGolds(),
  sysOrigin: '',
  levels: defaultLevels(),
});

function normalizeLevels(levels: Array<Record<string, any>> | undefined) {
  const levelMap = new Map<number, Record<string, any>>();
  for (const item of levels || []) {
    const level = Number(item.level ?? CP_MIN_LEVEL);
    if (level >= CP_MIN_LEVEL && level < CP_LEVEL_COUNT) {
      levelMap.set(level, item);
    }
  }
  return defaultLevels().map((fallback) => {
    const item = levelMap.get(fallback.level);
    if (!item) {
      return fallback;
    }
    return {
      cabinConfigId: item.cabinConfigId ? String(item.cabinConfigId) : null,
      level: fallback.level,
      levelName: String(item.levelName || fallback.levelName),
      requiredIntimacyValue: Number(item.requiredIntimacyValue || 0),
    };
  });
}

function applyConfig(result: Record<string, any> | null | undefined) {
  const value = result ?? {};
  const dismissConsumeGolds = value.dismissConsumeGolds || {};
  form.configured = Boolean(value.configured);
  form.sysOrigin = String(
    value.sysOrigin || form.sysOrigin || sysOriginOptions.value[0]?.value || '',
  );
  form.dismissConsumeGolds = {
    BROTHER: Number(dismissConsumeGolds.BROTHER || 0),
    CP: Number(dismissConsumeGolds.CP || 0),
    SISTERS: Number(dismissConsumeGolds.SISTERS || 0),
  };
  form.levels = normalizeLevels(value.levels);
}

async function loadConfig() {
  if (!form.sysOrigin) {
    return;
  }
  loading.value = true;
  try {
    const result = await getResidentCpConfig(form.sysOrigin);
    applyConfig(result);
  } finally {
    loading.value = false;
  }
}

function validateLevels() {
  for (const item of relationTypeOptions) {
    const gold = Number(form.dismissConsumeGolds[item.value] || 0);
    if (gold < 0) {
      message.error(`${item.label} 解绑金币不能小于 0`);
      return false;
    }
  }
  let previous = -1;
  for (const item of form.levels) {
    const requiredValue = Number(item.requiredIntimacyValue || 0);
    if (requiredValue < 0) {
      message.error('所需亲密值不能小于 0');
      return false;
    }
    if (requiredValue < previous) {
      message.error('所需亲密值需要按等级递增');
      return false;
    }
    previous = requiredValue;
  }
  return true;
}

function buildDismissConsumeGolds() {
  const result = defaultDismissConsumeGolds();
  for (const item of relationTypeOptions) {
    result[item.value] = Number(form.dismissConsumeGolds[item.value] || 0);
  }
  return result;
}

async function submitForm() {
  if (!validateLevels()) {
    return;
  }
  saving.value = true;
  try {
    await saveResidentCpConfig({
      sysOrigin: form.sysOrigin,
      dismissConsumeGolds: buildDismissConsumeGolds(),
      levels: form.levels.map((item) => ({
        cabinConfigId: item.cabinConfigId || null,
        level: item.level,
        levelName: String(item.levelName || `CP ${item.level}级`).trim(),
        requiredIntimacyValue: Number(item.requiredIntimacyValue || 0),
      })),
    });
    message.success('保存成功');
    await loadConfig();
  } finally {
    saving.value = false;
  }
}

function handleSave() {
  Modal.confirm({
    async onOk() {
      await submitForm();
    },
    title: '确认保存 CP 配置？',
    content: '保存后 Flutter 端 CP 权益配置接口会读取新的等级亲密值和解绑金币。',
  });
}

watch(
  sysOriginOptions,
  (options) => {
    if (!form.sysOrigin) {
      form.sysOrigin = String(options[0]?.value || '');
    }
  },
  { immediate: true },
);

watch(
  () => form.sysOrigin,
  (value) => {
    if (value) {
      void loadConfig();
    }
  },
  { immediate: true },
);
</script>

<template>
  <Page auto-content-height>
    <Spin :spinning="loading">
      <Card :bordered="false" title="CP 配置">
        <Space class="toolbar" wrap>
          <Select
            v-model:value="form.sysOrigin"
            :options="sysOriginOptions"
            option-filter-prop="label"
            option-label-prop="label"
            placeholder="请选择系统"
            show-search
            style="width: 180px"
          />
          <Tag :color="form.configured ? 'success' : 'processing'">
            {{ form.configured ? '已配置' : '未配置' }}
          </Tag>
          <Button :loading="saving" type="primary" @click="handleSave">
            保存
          </Button>
        </Space>

        <div class="section-title">解绑金币配置</div>
        <Space class="gold-fields" wrap>
          <div
            v-for="item in relationTypeOptions"
            :key="item.value"
            class="gold-field"
          >
            <div class="field-label">{{ item.label }}</div>
            <InputNumber
              v-model:value="form.dismissConsumeGolds[item.value]"
              :min="0"
              :precision="0"
              style="width: 180px"
            />
          </div>
        </Space>

        <Table
          :columns="columns"
          :data-source="form.levels"
          :pagination="false"
          row-key="level"
        >
          <template #bodyCell="{ column, record }">
            <template v-if="column.key === 'level'">
              第 {{ record.level }} 级
            </template>
            <template v-else-if="column.key === 'levelName'">
              <Input
                v-model:value="record.levelName"
                :maxlength="30"
                placeholder="请输入等级文案"
              />
            </template>
            <template v-else-if="column.key === 'requiredIntimacyValue'">
              <InputNumber
                v-model:value="record.requiredIntimacyValue"
                :min="0"
                :precision="0"
                style="width: 180px"
              />
            </template>
          </template>
        </Table>
      </Card>
    </Spin>
  </Page>
</template>

<style scoped>
.toolbar {
  margin-bottom: 16px;
}

.section-title {
  margin: 8px 0 12px;
  font-weight: 600;
}

.gold-fields {
  margin-bottom: 20px;
}

.field-label {
  margin-bottom: 6px;
  color: rgb(80 80 80);
}
</style>
