<template>
  <view class="formBox">
    <view :class="['input_list', { 'scan_page': scanPage }]">
      <block v-for="(item, index) in localFormConfigList" :key="index">
        <!-- **********************switch开关 -->
        <view
          :class="['input_item', 'input_item_fir', !scanPage && 'border_bottom', item.className]"
          v-if="item.type == 'switch' && item.isShow == '1' && isInclude(currentType, item.store.type)"
        >
          <view class="input_tit">{{ item.label }}</view>
          <switch
            class="public_switch"
            :checked="item.defValue == 'true' && isInclude(currentType, item.store.type)"
            @change="switchChange($event, item.vModel)"
          />
        </view>
        <!-- ******************************input框 -->
        <view
          :class="['input_item', !scanPage && 'border_bottom', item.className]"
          v-if="item.type == 'text' && item.isShow == '1' && isInclude(currentType, item.store.type)"
        >
          <view class="input_tit">{{ item.label }}</view>
          <view class="input_con">
            <input
              class="input"
              @blur="setVal($event, item.vModel)"
              :value="item.defValue"
              placeholder-class="placeholder"
              :placeholder="item.placeholder"
            />
            <!-- 获取验证码 -->
            <block v-if="item.vModel == 'provingCode'">
              <view
                :class="['code_con_txt', disabledBtn ? '' : 'colorCustom']"
                @click="getCode"
                v-if="seconds <= 0"
              >获取验证码</view>
              <view class="code_con_txt colorCustom" v-else>{{ seconds }}秒后重新获取</view>
            </block>
            <!-- 获取手机号 -->
            <block v-if="(item.vModel == 'certNum' || item.vModel == 'guardianCertNum') && showPhotoImg">
              <view class="code_con_txt" @click="photoBtnClick">
                <image class="photo_btn" :src="iconUrl.photograph"></image>
              </view>
            </block>
          </view>
        </view>
        <!-- ****************************单选框 -->
        <view
          :class="['input_item', !scanPage && 'border_bottom', item.className]"
          v-if="item.type == 'radio' && item.isShow == '1' && isInclude(currentType, item.store.type)"
        >
          <view class="input_tit">{{ item.label }}</view>
          <view class="input_con">
            <view class="radio_list">
              <view
                :class="['radio_item', item.defValue == optIndex ? 'backgroundCustom' : '']"
                v-for="(cell, optIndex) in item.options"
                :key="optIndex"
                @click="radioClick(item.vModel, optIndex)"
              >{{ cell.label }}</view>
            </view>
          </view>
        </view>
        <!-- ********************************日期框 -->
        <view
          :class="['input_item', !scanPage && 'border_bottom', item.className]"
          v-if="item.type == 'datePicker' && item.isShow == '1' && isInclude(currentType, item.store.type)"
        >
          <view class="input_tit">{{ item.label }}</view>
          <picker
            mode="date"
            @change="setVal($event, item.vModel)"
            :end="today"
            :value="item.defValue"
          >
            <view class="input_con">
              <input class="input" disabled :value="item.defValue" />
              <image class="public_right_img" :src="iconUrl.icon_right"></image>
            </view>
          </picker>
        </view>
        <!-- ****************************下拉框 -->
        <view
          :class="['input_item', !scanPage && 'border_bottom', item.className]"
          v-if="item.type == 'select' && item.isShow == '1' && isInclude(currentType, item.store.type)"
        >
          <view class="input_tit">{{ item.label }}</view>
          <picker
            @change="pickerChange($event, item.vModel)"
            :value="item.defValue"
            :range="item.options"
            range-key="label"
            :disabled="item.isDisabled"
          >
            <view class="input_con">
              <input
                :class="['input', item.isDisabled && 'inputDisabled']"
                disabled
                :value="item.options[item.defValue] ? item.options[item.defValue].label : ''"
              />
              <image class="public_right_img" :src="iconUrl.icon_right"></image>
            </view>
          </picker>
        </view>
        <!-- ****************************省市区 -->
        <view
          :class="['input_item', !scanPage && 'border_bottom', item.className]"
          v-if="item.type == 'region' && item.isShow == '1' && isInclude(currentType, item.store.type)"
        >
          <view class="input_tit">{{ item.label }}</view>
          <picker
            @change="regionChange($event, item.vModel)"
            mode="region"
            :value="item.defValue"
          >
            <view class="input_con">
              <view class="input">{{ item.defValue || '请选择' + item.label }}</view>
              <image class="public_right_img" :src="iconUrl.icon_right"></image>
            </view>
          </picker>
        </view>
        <!--   ***************************** 提示  -->
        <view
          class="tip"
          v-if="item.type == 'tip' && isInclude(currentType, item.store.type)"
        >{{ item.label }}</view>
      </block>
    </view>

    <view class="public_btn backgroundCustom_F08" @click="toSelect">{{ btnName }}</view>
    <view
      class="public_btn addHealthCard colorCustom"
      @click="toRelation"
      v-if="showRelation"
    >已有健康卡，一键快速关联</view>

    <canvas
      canvas-id="pressCanvas"
      class="press-canvas"
      :style="{ width: windowWidth + 'px', height: windowWidth + 'px' }"
    ></canvas>
  </view>
</template>

<script lang="ts" setup>
import { ref, reactive, watch, onMounted } from 'vue';
import { uploadZxFileUrl, idCardVerification, sendVerificationCode_V3 } from '@/pagesPersonal/service';
import { common,imgCompress } from '@/utils';
import icon from '@/utils/icon';
import store from '@/store';

const props = defineProps({
  /**form表单列表 */
  formConfigList: {
    type: Array,
    default: () => []
  },
  /**当前方式  default 默认(身份识别)  children新生儿(监护人身份证) */
  currentType: {
    type: String,
    default: ''
  },
  /**
   * 按钮名称
   */
  btnName: {
    type: String,
    default: '下一步'
  },
  /**
   * 是否在健康卡身份证识别页面
   * 此页面需要修改form样式
   */
  scanPage: {
    type: Boolean,
    default: false
  },
  /**
   * 证件号码input后面是否展示照相机图片
   */
  showPhotoImg: {
    type: Boolean,
    default: true
  },
  /**
   * 是否展示 关联健康卡按钮
   */
  showRelation: {
    type: Boolean,
    default: false
  }
});

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

const iconUrl = ref(icon)
const mobile = ref(''); //获取验证码时用到的手机号
const pcId = ref(''); //验证码pcId,
const seconds = ref(0); //获取验证码剩余时间
const disabledBtn = ref(true); //获取验证码按钮是否禁用
const windowWidth = ref(0);
const today = ref('');
const localFormConfigList = ref<any[]>([]);
const currentType = ref('');
let timer: any = null;

onMounted(() => {
  const sysInfo = uni.getSystemInfoSync();
  windowWidth.value = sysInfo.windowWidth;
});

watch(
  () => props.formConfigList,
  (newVal) => {
    if (!common.isEmpty(newVal)) {
      let cType = props.currentType;
      let fList = JSON.parse(JSON.stringify(newVal)); // Deep copy to avoid mutating prop
      fList.map((item: any) => {
        item.store = common.isJSON(item.store) ? JSON.parse(item.store) : item.store;
        item.options = common.isJSON(item.options) ? JSON.parse(item.options) : item.options;
        /**日期初始化 */
        if (item.type == 'datePicker') {
          item.defValue = common.newDay();
        }
      });
      if (!cType) {
        if (fList.filter((item: any) => item.vModel == 'children' && item.defValue == 'true').length > 0) {
          /**如果新生儿已开启 */
          cType = 'children';
        } else {
          cType = 'default';
        }
      }
      fList.sort((a: any, b: any) => {
        if (a.store.index && b.store.index) {
          return Number(a.store.index) - Number(b.store.index);
        } else {
          return 1;
        }
      });
      fList = setFormConfigList(fList);
      
      today.value = common.newDay();
      localFormConfigList.value = fList;
      currentType.value = cType;
    }
  },
  { immediate: true, deep: true }
);

// WXS helper replacement
const isInclude = (str: string, strs: string | string[]) => {
  if (strs && strs.indexOf(str) != -1) {
    return true;
  } else {
    return false;
  }
};

/**
 * 读取身份证按钮点击
 */
const photoBtnClick = async () => {
  let resp = await chooseImage();
  if (!common.isEmpty(resp)) {
    let data = await upLoad(resp);
    if (!common.isEmpty(data)) {
      let queryData = {
        filePath: data.url.replace(/\\/g, '/'),
        type: 1 //1身份证 2户口本
      };
      let { resData } = await idCardVerification(queryData);
      if (resData.RespCode == 10000 && resData.Data) {
        let idCardInfo = resData.Data;
        let fList = localFormConfigList.value;
        let cType = currentType.value;
        fList.map((item) => {
          if (cType == 'children') {
            /**如果是新生儿  给监护人证件信息赋值 */
            if (item.vModel == 'guardianName') {
              item.defValue = idCardInfo[0].Names;
            } else if (item.vModel == 'guardianCertNum') {
              item.defValue = idCardInfo[0].IdCards;
            }
          } else {
            /**否则给当前就诊人证件信息赋值 */
            if (item.vModel == 'memberName') {
              item.defValue = idCardInfo[0].Names;
            } else if (item.vModel == 'certNum') {
              item.defValue = idCardInfo[0].IdCards;
            }
          }
        });
        localFormConfigList.value = fList;
      }
    }
  }
};

/**选取照片 */
const chooseImage = () => {
  return new Promise((resolve) => {
    uni.chooseImage({
      count: 1,
      sourceType: ['album', 'camera'],
      /**album:从相册选图 camera:使用相机 */
      success: (res) => {
        resolve(res);
      }
    });
  });
};

/**
 * 上传图片
 */
const upLoad = (resp: any) => {
  uni.showLoading({
    mask: true
  });
  return new Promise<any>((resolve) => {
    imgCompress.getLessLimitSizeImage(
      'pressCanvas',
      resp.tempFilePaths[0],
      1,
      windowWidth.value,
      (path: string) => {
        uni.uploadFile({
          url: uploadZxFileUrl,
          filePath: path,
          name: 'newsFile',
          formData: {
            user: 'test'
          },
          header: {
            token: store.state.token
          },
          success(res) {
            uni.hideLoading();
            let data = JSON.parse(res.data);
            if (data.RespCode == '10000') {
              resolve(data);
            } else {
              common.showModal('图片上传失败');
              resolve(false);
            }
          }
        });
      }
    );
  });
};

/**
 * 点击获取验证码
 */
const getCode = async () => {
  if (disabledBtn.value) {
    return;
  }
  let queryData = {
    mobile: mobile.value
  };
  let { resData } = await sendVerificationCode_V3(queryData);

  if (resData.RespCode == 10000 && resData.Data) {
    pcId.value = resData.Data[0].pcId;
    common.showModal('发送成功！');
    startCountDown();
  }
};

const startCountDown = () => {
  if (timer) clearInterval(timer);
  seconds.value = 60;
  disabledBtn.value = true;
  timer = setInterval(() => {
    seconds.value--;
    if (seconds.value <= 0) {
      clearInterval(timer);
      seconds.value = 0;
      disabledBtn.value = false;
    }
  }, 1000);
};

/**
 * 滑块开关
 */
const switchChange = async (e: any, key: string) => {
  let value = e.detail.value;
  let cType = currentType.value;
  let fList = localFormConfigList.value;
  fList.map((item) => {
    if (item.vModel == key) {
      item.defValue = value ? 'true' : 'false';
    }
  });
  if (value && key == 'children') {
    cType = key;
  } else if (key == 'children') {
    /**关闭新生儿 */
    cType = 'default';
  }
  /**开启新生儿时  显示性别和出生日期  关闭时隐藏*/
  fList.map((cell) => {
    if (cell.vModel == 'sex' || cell.vModel == 'birthDate') {
      if (key == 'children') {
        /**判断当前证件类型是否为身份证  如果是身份证  不显示性别和出生日期 */
        let certType = fList.filter((item) => item.vModel == 'certType')[0];
        cell.isShow = value
          ? '1'
          : certType.options[certType.defValue].value == '01'
          ? '0'
          : '1';
      }
    }
  });
  fList = setFormConfigList(fList);
  currentType.value = cType;
  localFormConfigList.value = fList;
};

/**
 * 选择证件类型
 */
const pickerChange = (e: any, key: string) => {
  let value = e.detail.value;
  let fList = localFormConfigList.value;
  let cType = currentType.value;
  fList.map((item) => {
    if (item.vModel == key) {
      item.defValue = value;
      if (item.vModel == 'certType' && cType != 'children') {
        fList.map((cell) => {
          /**如果选择的不是身份证  显示性别和出生日期(新生儿页面不隐藏) */
          if (cell.vModel == 'sex' || cell.vModel == 'birthDate') {
            cell.isShow = item.options[value].value != '01' ? '1' : '0';
          }
          /**如果选择的不是身份证  禁用验证方式选择 */
          if (cell.vModel == 'checkType') {
            cell.isDisabled = item.options[value].value != '01' ? true : false;
            cell.defValue = 0;
          }
          /**如果选择的不是身份证  显示手机号和验证码*/
          if (cell.vModel == 'userMobile' || cell.vModel == 'provingCode') {
            cell.isShow = 1;
          }
        });
      }
      /**选择验证方式 */
      if (item.vModel == 'checkType') {
        fList.map((cell) => {
          /**如果选择的不是手机号验证  隐藏手机号和验证码  1手机号验证  2人脸*/
          if (cell.vModel == 'userMobile' || cell.vModel == 'provingCode') {
            cell.isShow = item.options[value].value == '1' ? '1' : '0';
          }
        });
      }
    }
  });
  localFormConfigList.value = fList;
};

/**
 * 省市区选择器
 */
const regionChange = (e: any, key: string) => {
  let value = e.detail.value;
  let fList = localFormConfigList.value;
  fList.map((item) => {
    if (item.vModel == key) {
      item.defValue = value;
    }
  });
  localFormConfigList.value = fList;
};

/**
 * 输入框赋值
 */
const setVal = (e: any, key: string) => {
  let fList = localFormConfigList.value;
  let value = e.detail.value;
  fList.map((item) => {
    if (item.vModel == key) {
      item.defValue = value;
      /**输入手机号时 判断发送验证码按钮显隐 */
      if (item.vModel == 'userMobile') {
        let reg = new RegExp(item.regularExpressions);
        let disabled = true;
        if (reg.test(item.defValue)) {
          disabled = false;
        }
        disabledBtn.value = disabled;
        mobile.value = item.defValue;
      }
      /**输入身份证号时  转换大写*/
      if (item.vModel == 'certNum' || item.vModel == 'guardianCertNum') {
        item.defValue = item.defValue.toUpperCase();
      }
    }
  });
  localFormConfigList.value = fList;
};

/**
 * 单选框点击
 */
const radioClick = (key: string, index: number) => {
  let fList = localFormConfigList.value;
  fList.map((item) => {
    if (item.vModel == key) {
      item.defValue = index;
    }
  });
  localFormConfigList.value = fList;
};

/**
 * 点击下一步
 */
const toSelect = async () => {
  await common.sleep();
  emit('toSelect', {
    formConfigList: localFormConfigList.value,
    currentType: currentType.value,
    pcId: pcId.value
  });
};

/**
 * 点击关联健康卡
 */
const toRelation = () => {
  /**点击关联健康卡 给父组件一个relation为true判断 */
  emit('toSelect', {
    relation: true
  });
};

// 设置圆角
const setFormConfigList = (fList: any[]) => {
  fList.forEach((item, index) => {
    item.className = '';
    if (item.type == 'tip' && item.isShow == '1') {
      for (let i = 1; i < index; i++) {
        if (fList[index - i].isShow == '1') {
          fList[index - i].className = 'toBoderRadio';
          break;
        }
      }
    }
  });
  return fList;
};
</script>

<style lang="scss" scoped>
.formBox {
  padding: 0 30upx;
}

.input_list {
  display: inline-block;
  width: 100%;
  overflow: hidden;
  border-radius: 24upx;
}

.input_item {
  height: 110upx;
  display: flex;
  align-items: center;
  position: relative;
  margin-bottom: -4upx;
  background: #fff;
  padding: 0 30upx;
}
.public_right_img {
  right: 30upx;
}
.input_con {
  width: 460upx;
  display: flex;
  align-items: center;
  justify-content: space-between;
}

.input_tit {
  font-size: 30upx;
  color: rgba(85, 85, 85, 1);
  width: 230upx;
  flex-shrink: 0;
}

.radio_list {
  width: 100%;
  display: flex;
  align-items: center;
}

.radio_item {
  padding: 6upx 48upx;
  font-family: PingFangSC-Medium, PingFang SC;
  font-weight: 500;
  color: #fff;
  background-color: #ccc;
  border-radius: 64upx;
  line-height: 44upx;
  margin-right: 24upx;
}

.input {
  padding: 20upx 0;
}

.public_btn {
  margin: 60upx 30upx;
}

.code_con .input {
  width: 300upx;
}

.code_con_txt {
  font-size: 28upx;
  white-space: nowrap;
  padding: 20upx 0 20upx 20upx;
  color: #999;
}

.input_item_fir {
  justify-content: space-between;
}

.tip {
  font-size: 30upx;
  font-family: Source Han Sans CN;
  font-weight: 500;
  color: rgba(1, 1, 1, 1);
  padding: 20upx 0;
  background-color: #f1f1f6;
  position: relative;
}
.tip + .input_item {
  border-radius: 24upx 24upx 0 0;
}

.tip:before,
.tip:after {
  content: '';
  display: block;
  width: 30upx;
  height: 100%;
  background-color: #f1f1f6;
  top: 0;
  position: absolute;
}

.tip:before {
  left: -30upx;
}

.tip:after {
  right: -30upx;
}

.btnBox {
  width: 150upx;
}

.btnBox button {
  display: flex;
  align-items: center;
  justify-content: center;
  background-color: transparent;
}

.disabledBtn {
  opacity: 0.5;
}

.photo_btn {
  width: 40upx;
  height: 36upx;
}

.press-canvas {
  position: absolute;
  top: -2000upx;
  background-color: gray;
}

.inputDisabled {
  color: #999;
}
.scan_page .input_item {
  height: 80upx;
  line-height: 24upx;
}

.addHealthCard {
  border: 1px solid;
  font-family: PingFangSC-Regular, PingFang SC;
  font-weight: 400;
  margin-top: -10upx;
}
.toBoderRadio {
  border-radius: 0 0 30upx 30upx;
}
</style>
