<script setup lang="ts">
import type { Station, StationAlarms, StationDevices } from '@/apis';
import { usePermission } from '@/composables';
import { DEVICE_TYPE_LITERALS, PERMISSION_TYPE_LITERALS } from '@/enums';
import axios from 'axios';
import dayjs from 'dayjs';
import { isFunction } from 'es-toolkit';
import { MoreHorizontalIcon, MoreVerticalIcon } from 'lucide-vue-next';
import { NButton, NCard, NCheckbox, NDropdown, NFlex, NIcon, NTag, NTooltip, useThemeVars, type DropdownOption } from 'naive-ui';
import { computed, toRefs } from 'vue';

const themeVars = useThemeVars();

const props = defineProps<{
  station: Station;
  devices: StationDevices;
  alarms: StationAlarms;
  selectable?: boolean;
}>();

const selected = defineModel<boolean>('selected', { default: false });

const emit = defineEmits<{
  clickDetail: [type: 'device' | 'alarm', station: Station];
  clickConfig: [station: Station];
}>();

const { hasPermission } = usePermission();

const { station, devices, alarms, selectable } = toRefs(props);

const onlineDeviceCount = computed(() => {
  return Object.values(DEVICE_TYPE_LITERALS).reduce((count, deviceType) => {
    const onlineDevices = devices.value[deviceType].filter((device) => device.deviceStatus === '10');
    return count + onlineDevices.length;
  }, 0);
});
const offlineDeviceCount = computed(() => {
  return Object.values(DEVICE_TYPE_LITERALS).reduce((count, deviceType) => {
    const offlineDevices = devices.value[deviceType].filter((device) => device.deviceStatus === '20');
    return count + offlineDevices.length;
  }, 0);
});
const deviceCount = computed(() => {
  return Object.values(DEVICE_TYPE_LITERALS).reduce((count, deviceType) => {
    return count + devices.value[deviceType].length;
  }, 0);
});

const alarmCount = computed(() => {
  return alarms.value.unclassified.length;
});

const openVideoPlatform = async () => {
  try {
    const response = await axios.get<Record<string, string>>(`/minio/ndm/ndm-vimps.json?_t=${dayjs().unix()}`);
    const url = response.data[station.value.code];
    if (!url) {
      window.$message.warning(`未找到车站编码 ${station.value.code} 对应的视频平台URL`);
      return;
    }
    window.open(url, '_blank');
  } catch (error) {
    console.error('获取视频平台URL失败:', error);
    window.$message.error('获取视频平台URL失败');
  }
};

const openDeviceConfigModal = () => {
  if (!station.value.online) {
    window.$message.error('当前车站离线，无法查看');
    return;
  }
  emit('clickConfig', station.value);
};

const dropdownOptions = computed<DropdownOption[]>(() => [
  {
    label: '视频平台',
    key: 'video-platform',
    onSelect: openVideoPlatform,
  },
  {
    label: '设备配置',
    key: 'device-config',
    show: hasPermission(station.value.code, PERMISSION_TYPE_LITERALS.OPERATION),
    onSelect: openDeviceConfigModal,
  },
]);

const onSelectDropdownOption = (key: string, option: DropdownOption) => {
  const onSelect = option['onSelect'];
  if (isFunction(onSelect)) {
    onSelect();
  }
};
</script>

<template>
  <NCard bordered hoverable size="medium" :header-style="{ padding: `6px` }" :content-style="{ padding: `0px 6px 6px 6px` }">
    <template #header>
      <template v-if="station.ip">
        <NTooltip trigger="click">
          <template #trigger>
            <span style="font-size: smaller">{{ station.name }}</span>
          </template>
          <span>{{ station.ip }}</span>
        </NTooltip>
      </template>
      <template v-else>
        <span style="font-size: smaller">{{ station.name }}</span>
      </template>
    </template>
    <template #header-extra>
      <NFlex align="center" :size="4">
        <NCheckbox v-if="selectable" v-model:checked="selected" :disabled="!station.online" />
        <NTag :type="station.online ? 'success' : 'error'" size="small">
          {{ station.online ? '在线' : '离线' }}
        </NTag>
        <NDropdown trigger="click" :options="dropdownOptions" @select="onSelectDropdownOption">
          <NButton quaternary size="tiny" :focusable="false">
            <template #icon>
              <NIcon :component="MoreVerticalIcon" />
            </template>
          </NButton>
        </NDropdown>
      </NFlex>
    </template>
    <template #default>
      <NFlex vertical :size="6" :style="{ opacity: station.online ? '1' : '0.5' }">
        <NFlex vertical :size="4">
          <NFlex justify="flex-end" align="center" :size="2">
            <span>{{ deviceCount }} 台设备</span>
            <NButton quaternary size="tiny" :focusable="false" @click="() => emit('clickDetail', 'device', station)">
              <template #icon>
                <NIcon :component="MoreHorizontalIcon" />
              </template>
            </NButton>
          </NFlex>

          <NFlex justify="flex-end" align="center" :size="2">
            <div>
              <span :style="{ color: onlineDeviceCount > 0 ? themeVars.successColor : '' }">在线 {{ onlineDeviceCount }} 台</span>
              <span> · </span>
              <span :style="{ color: offlineDeviceCount > 0 ? themeVars.errorColor : '' }">离线 {{ offlineDeviceCount }} 台</span>
            </div>
            <!-- 占位按钮，对齐布局 -->
            <NButton quaternary size="tiny" :focusable="false" style="visibility: hidden">
              <template #icon>
                <NIcon :component="MoreHorizontalIcon" />
              </template>
            </NButton>
          </NFlex>
        </NFlex>

        <NFlex justify="flex-end" align="center" :size="2">
          <span :style="{ color: alarmCount > 0 ? themeVars.warningColor : '' }">今日 {{ alarmCount }} 条告警</span>
          <NButton quaternary size="tiny" :focusable="false" @click="() => emit('clickDetail', 'alarm', station)">
            <template #icon>
              <NIcon :component="MoreHorizontalIcon" />
            </template>
          </NButton>
        </NFlex>
      </NFlex>
    </template>
  </NCard>
</template>

<style scoped lang="scss"></style>
