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

import { useRequest } from '@/hooks/request';
import { t } from '@/i18n';
import {
  addBatchMonitorPointAlarm,
  getMonitorPointAlarm,
  getMonitorPointInfo,
  updateBatchMonitorPointAlarm,
  updateLimits,
} from '@/api';

import type { FormInstance, Rule } from 'ant-design-vue/es/form';
import type { LimitForm, MonitoringPointData, WarningItem } from '@/types';

const emit = defineEmits(['setClick']);

interface Props {
  monitoringId?: number;
  monitoringData: MonitoringPointData[];
}

const { handleRequest } = useRequest();

const props = defineProps<Props>();
const limitOpen = ref<boolean>(false);
const warningOpen = ref<boolean>(false);
const warningShow = ref<boolean>(false);
const formRef = ref<FormInstance>();
const limitForm = ref<LimitForm>({
  id: undefined,
  regionId: undefined,
  tempUpper: undefined,
  tempLower: undefined,
  tempPreset: undefined,
  humidityUpper: undefined,
  humidityLower: undefined,
  humidityPreset: undefined,
  batch: false,
  batchPointIds: '',
  batchIds: [],
});
const warningList = ref<WarningItem[]>([
  {
    pointId: props.monitoringId,
    enabled: false,
    type: 1,
    val: undefined,
    duration: undefined,
  },
  {
    pointId: props.monitoringId,
    enabled: false,
    type: 2,
    val: undefined,
    duration: undefined,
  },
]);

const rules: Record<string, Rule[]> = {
  id: [{ required: true, message: t('common.cannotEmpty'), trigger: 'change' }],
  tempUpper: [{ required: true, message: t('common.cannotEmpty'), trigger: 'change' }],
  tempLower: [{ required: true, message: t('common.cannotEmpty'), trigger: 'change' }],
  tempPreset: [{ required: true, message: t('common.cannotEmpty'), trigger: 'change' }],
  humidityUpper: [{ required: true, message: t('common.cannotEmpty'), trigger: 'change' }],
  humidityLower: [{ required: true, message: t('common.cannotEmpty'), trigger: 'change' }],
  humidityPreset: [{ required: true, message: t('common.cannotEmpty'), trigger: 'change' }],
  batchIds: [{ required: true, message: t('common.cannotEmpty'), trigger: 'change' }],
};

const addLimit = () => {
  limitOpen.value = true;
  limitForm.value.batch = false;
};

const addWarning = () => {
  getMonitorPointList();
  warningOpen.value = true;
};

const getMonitorPointList = () => {
  handleRequest(async () => {
    if (props.monitoringId) {
      const data = await getMonitorPointAlarm(props.monitoringId);
      if (data.length) {
        warningShow.value = true;
        data.forEach((item, i) => {
          const { id, pointId, enabled, type, val, duration } = item;
          Object.assign(warningList.value[i], {
            id,
            pointId,
            enabled,
            type,
            val,
            duration,
          });
        });
      } else {
        warningShow.value = false;
        warningList.value = [
          {
            pointId: props.monitoringId,
            enabled: false,
            type: 1,
            val: undefined,
            duration: undefined,
          },
          {
            pointId: props.monitoringId,
            enabled: false,
            type: 2,
            val: undefined,
            duration: undefined,
          },
        ];
      }
    }
  });
};

const getLimit = () => {
  formRef.value
    ?.validate()
    .then(() => {
      handleRequest(async () => {
        if (limitForm.value.batch) {
          if (limitForm.value.batchIds) {
            limitForm.value.batchPointIds = limitForm.value.batchIds.join();
          }
        }
        const {
          id,
          regionId,
          tempUpper,
          tempLower,
          tempPreset,
          humidityUpper,
          humidityLower,
          humidityPreset,
          batch,
          batchPointIds,
        } = limitForm.value;
        await updateLimits({
          id,
          regionId,
          tempUpper,
          tempLower,
          tempPreset,
          humidityUpper,
          humidityLower,
          humidityPreset,
          batch,
          batchPointIds,
        });
        getMonitorPoint();
        limitOpen.value = false;
        emit('setClick');
      });
    })
    .catch(() => {});
};

const getMonitorPoint = () => {
  handleRequest(async () => {
    if (props.monitoringId) {
      const { humidityLower, humidityPreset, humidityUpper, tempLower, tempPreset, tempUpper, id, regionId } =
        await getMonitorPointInfo(props.monitoringId);

      Object.assign(limitForm.value, {
        humidityLower,
        humidityPreset,
        humidityUpper,
        tempLower,
        tempPreset,
        tempUpper,
        id,
        regionId,
      });
    }
  });
};

const getWarning = () => {
  handleRequest(async () => {
    if (warningShow.value) {
      await updateBatchMonitorPointAlarm(warningList.value);
    } else {
      await addBatchMonitorPointAlarm(warningList.value);
    }
  });

  warningOpen.value = false;
};

const addBatch = () => {
  limitForm.value.batchIds = [];
  limitForm.value.id = undefined;
};

watch(
  () => props.monitoringId,
  (count) => {
    if (count) {
      getMonitorPoint();
      getMonitorPointList();
    }
  },
);

onMounted(() => {
  getMonitorPoint();
});
</script>

<template>
  <div>
    <div>
      <AButton type="text" class="icon-button icon-style" @click="addLimit">
        <SvgIcon name="setting" />
        {{ $t('envMonitor.setTemperatureHumidityLimits') }}
      </AButton>
      <AButton type="text" class="icon-button icon-style" @click="addWarning">
        <SvgIcon name="setting" />
        {{ $t('envMonitor.setTemperaturHumidityAlerts') }}
      </AButton>
    </div>

    <AModal
      v-model:open="limitOpen"
      :title="$t('envMonitor.setTemperatureHumidityLimits')"
      :footer="null"
      width="704px"
      :mask-closable="false"
      :keyboard="false"
    >
      <AForm ref="formRef" :model="limitForm" layout="vertical" :rules="rules">
        <AFormItem v-if="limitForm.batch" :label="$t('envMonitor.selectMonitoringPointNameCheck')" name="batchIds">
          <ASelect
            class="select-width"
            v-model:value="limitForm.batchIds"
            mode="multiple"
            :options="monitoringData"
            :field-names="{ label: 'name', value: 'id' }"
            :placeholder="$t('common.plzSelect')"
            :max-tag-count="limitForm.batchIds?.length === 1 ? 1 : 0"
            allow-clear
          >
            <template #maxTagPlaceholder="omittedValues">
              <span>+ {{ omittedValues.length }} ...</span>
            </template>
          </ASelect>
        </AFormItem>
        <AFormItem v-else :label="$t('envMonitor.selectMonitoringPointNameCheck')" name="id">
          <ASelect
            class="select-width"
            v-model:value="limitForm.id"
            :options="monitoringData"
            :field-names="{ label: 'name', value: 'id' }"
            :placeholder="$t('common.plzSelect')"
          />
        </AFormItem>

        <AFlex justify="space-between">
          <AFormItem :label="$t('envMonitor.indoorTemperatureSettingValue')" name="tempPreset">
            <AInputNumber
              :placeholder="$t('common.pleaseEnter')"
              class="select-width"
              v-model:value="limitForm.tempPreset"
              :min="0"
              :max="200"
            />
          </AFormItem>
          <AFormItem :label="$t('envMonitor.upperLimitValueIndoorTemperature')" name="tempUpper">
            <AInputNumber
              :placeholder="$t('common.pleaseEnter')"
              class="select-width"
              v-model:value="limitForm.tempUpper"
              :min="0"
              :max="200"
            />
          </AFormItem>
          <AFormItem :label="$t('envMonitor.lowerLimitValueIndoorTemperature')" name="tempLower">
            <AInputNumber
              :placeholder="$t('common.pleaseEnter')"
              class="select-width"
              v-model:value="limitForm.tempLower"
              :min="0"
              :max="200"
            />
          </AFormItem>
        </AFlex>
        <AFlex justify="space-between">
          <AFormItem :label="$t('envMonitor.indoorHumiditySettingValue')" name="humidityPreset">
            <AInputNumber
              :placeholder="$t('common.pleaseEnter')"
              class="select-width"
              v-model:value="limitForm.humidityPreset"
              :min="0"
              :max="200"
            />
          </AFormItem>
          <AFormItem :label="$t('envMonitor.upperLimitValueIndoorHumidity')" name="humidityUpper">
            <AInputNumber
              :placeholder="$t('common.pleaseEnter')"
              class="select-width"
              v-model:value="limitForm.humidityUpper"
              :min="0"
              :max="200"
            />
          </AFormItem>
          <AFormItem :label="$t('envMonitor.minimumIndoorHumidityLevel')" name="humidityLower">
            <AInputNumber
              :placeholder="$t('common.pleaseEnter')"
              class="select-width"
              v-model:value="limitForm.humidityLower"
              :min="0"
              :max="200"
            />
          </AFormItem>
        </AFlex>
        <ACheckbox v-model:checked="limitForm.batch" @click="addBatch">{{ $t('common.batchSetting') }}</ACheckbox>
      </AForm>
      <AFlex justify="flex-end" class="limit-top">
        <AButton class="limit-button default-button" @click="limitOpen = false">{{ $t('common.cancel') }}</AButton>
        <AButton type="primary" @click="getLimit">{{ $t('common.confirm') }}</AButton>
      </AFlex>
    </AModal>

    <AModal v-model:open="warningOpen" :footer="null" width="704px" :mask-closable="false" :keyboard="false">
      <template #title>
        <div class="warning-title">{{ $t('envMonitor.setTemperaturHumidityAlerts') }}</div>
      </template>

      <div v-for="item in warningList" :key="item.id" class="warning-div warning-color">
        <ACheckbox v-model:checked="item.enabled" class="warning-color">{{
          item.type === 1 ? $t('envMonitor.enableTemperatureAlertSystem') : $t('envMonitor.enableHumidityAlert')
        }}</ACheckbox>
        <AFlex align="center" class="warning-flex">
          <div>
            {{
              item.type === 1
                ? $t('envMonitor.indoorTemperatureGreaterThan')
                : $t('envMonitor.outdoorHumidityGreaterThan')
            }}
          </div>

          <AInputNumber
            :placeholder="$t('common.pleaseEnter')"
            class="input-width"
            v-model:value="item.val"
            :min="1"
            :max="9999"
          />
          <div>{{ item.type === 1 ? '℃' : '%' }}</div>
          <div>{{ $t('envMonitor.durationGreaterThan') }}</div>
          <AInputNumber
            :placeholder="$t('common.pleaseEnter')"
            class="input-width"
            v-model:value="item.duration"
            :min="1"
            :max="9999"
          />
          <div>{{ $t('envMonitor.minTrigger') }}</div>
        </AFlex>
      </div>

      <AFlex justify="flex-end" class="limit-top">
        <AButton class="default-button limit-button" @click="warningOpen = false">{{ $t('common.cancel') }}</AButton>
        <AButton type="primary" @click="getWarning">{{ $t('common.confirm') }}</AButton>
      </AFlex>
    </AModal>
  </div>
</template>

<style lang="scss" scoped>
.input-width {
  width: 120px;
  margin: 0 12px;
}

.warning-flex {
  margin: 16px 0 32px;
}

.warning-color {
  font-size: 14px;
  font-style: normal;
  font-weight: 400;
  line-height: 22px;
  color: rgb(0 0 0 / 65%);
  text-align: left;
}

.warning-div {
  padding-top: 8px;
}

.warning-title {
  margin-bottom: 16px;
}

.limit-button {
  margin: 0 16px;
}

.limit-top {
  margin-top: 24px;
}

.icon-style {
  color: var(--antd-color-primary);
}

.select-width {
  width: 192px;
}
</style>
