Procházet zdrojové kódy

所在城市和户籍地

lifanagju_citu před 7 měsíci
rodič
revize
071dd703b0

+ 34 - 20
src/components/CtForm/index.vue

@@ -63,6 +63,7 @@
                 v-if="item.type === 'cascade'"
                 v-model="item.value"
                 :item="item"
+                ref="cascadeRef"
                 @change="handleChange(item)"
               ></cascadeUI>
               <datePickerUI
@@ -141,7 +142,6 @@ import { ref } from 'vue'
 const emit = defineEmits(['change', 'inputUpdateAutocomplete'])// 定义一个或多个自定义事件
 const props = defineProps({items: Object})
 const valid = ref(false)
-const isValid = ref(true)
 const formRef = ref()
 
 const handleChange = (item) => {
@@ -155,27 +155,41 @@ const handleChange = (item) => {
   emit('change', false)
 }
 
-const validateTime = () => {
-  isValid.value = true
-  props.items.options.forEach((e) => {
-    if (e.type !== 'date' || e.hide || !e.rules) return
-    const rules = e.rules[0]
-    const check = rules(e.value)
-    if (typeof check === 'string') {
-      isValid.value = false
-      e.option.error = true
-      e.option.errorMsg = check
-    } else {
-      e.option.error = false
-      e.option.errorMsg = null
-    }
-  })
+// const isValid = ref(true)
+// const validateTime = () => {
+//   isValid.value = true
+//   props.items.options.forEach((e) => {
+//     if (e.type !== 'date' || e.hide || !e.rules) return
+//     const rules = e.rules[0]
+//     const check = rules(e.value)
+//     if (typeof check === 'string') {
+//       isValid.value = false
+//       e.option.error = true
+//       e.option.errorMsg = check
+//     } else {
+//       e.option.error = false
+//       e.option.errorMsg = null
+//     }
+//   })
+// }
+
+const cascadeRef = ref()
+const validateCascade = () => {
+  let cascadeValid = true
+  if (cascadeRef.value && Array.isArray(cascadeRef.value) && cascadeRef.value?.length) {
+    cascadeRef.value.forEach(ref => {
+      const txt = ref?.handleBlur()
+      if (txt) cascadeValid = false
+    })
+  }
+  return cascadeValid
 }
   
-const validate = () => {
-  const form = formRef.value.validate()
-  const time = validateTime()
-  return form && time
+const validate = async () => {
+  const form = await formRef.value.validate()
+  // const time = validateTime()
+  const cascade = validateCascade()
+  return form && cascade
 }
 defineExpose({
   validate,

+ 16 - 9
src/components/FormUI/cascade/index.vue

@@ -1,9 +1,10 @@
 <!-- 级联选择器 -->
 <template>
   <div class="d-flex" style="width: 100%;">
-    <div style="line-height: 40px;">
-      <span class="ml-3" style="color: #777;">{{ item?.label }}</span>
-      <span v-if="prop.required" class="mr-1" style="color: var(--v-error-base);"> *</span>
+    <div class="mr-2" style="line-height: 40px;">
+      <span style="color: #777;">{{ item?.label }}</span>
+      <span v-if="prop.required" style="color: var(--v-error-base);"> *</span>
+      <!-- <span style="color: #777;"> :</span> -->
     </div>
     <div style="flex: 1;">
       <el-cascader
@@ -19,7 +20,7 @@
         @blur="handleBlur"
         @change="handleChange"
       ></el-cascader>
-      <div v-if="requiredTxt" class="requiredTxt">{{ requiredTxt }}</div>
+      <div :style="{'display': requiredTxt? 'block' : 'inline-block'}" class="requiredTxt">{{ requiredTxt }}</div>
     </div>
   </div>
 </template>
@@ -42,7 +43,8 @@ const prop = {
   required: item.required || false,
   size: item.size || 'large',
   multiple: item.multiple || false,
-  checkStrictly: item.checkStrictly || false,
+  emitPath: item.emitPath || false, // 在选中节点改变时,是否返回由该节点所在的各级菜单的值所组成的数组,若设置 false,则只返回该节点的值
+  checkStrictly: item.checkStrictly || false, // 是否严格的遵守父子节点不互相关联
 }
 
 const value = ref()
@@ -56,22 +58,27 @@ watch(
 )
 
 const handleChange = (val) => {
-  value.value = item.multiple ? val : Array.isArray(val) && val?.length ? val[0] : null
-  if (prop.required && value.value !== '' && value.value !== null && value.value !== undefined) requiredTxt.value = ''
-
+  value.value = val
+  handleBlur()
   emit('update:modelValue', value.value)
   emit('change', value.value)
 }
 
 const requiredTxt = ref('')
 const handleBlur = () => {
-  if (prop.required && (value.value === '' || value.value === null || value.value === undefined)) requiredTxt.value = '请输入' + item?.label
+  if (prop.required && (value.value === '' || value.value === null || value.value === undefined)) requiredTxt.value = '请选择' + item?.label
   else requiredTxt.value = ''
+  return requiredTxt.value
 }
 
 const getPlaceholder = () => {
   return prop.required ? item?.label + ' *' : item?.label
 }
+
+defineExpose({
+  handleBlur
+})
+
 </script>
 <style lang="scss" scoped>
 .requiredTxt {

+ 1 - 1
src/utils/areaDeal.js

@@ -1,7 +1,7 @@
 import { getDict } from '@/hooks/web/useDictionaries'
 
 // 根据市获取省份 
-export const cityToProvince = async (cityId, query, parentList = []) => {
+export const cityToProvince = async (cityId, query, parentList = []) => { // cityToProvince(workAreaId, {}, province.items || [])
   if (!cityId) return cityId
   query = { pid: true, cityList: true, ...query }
   const obj = {}

+ 14 - 95
src/views/recruit/personal/PersonalCenter/resume/online/components/basicInfo.vue

@@ -115,7 +115,6 @@
 import CtForm from '@/components/CtForm'
 import Snackbar from '@/plugins/snackbar'
 import { getDict } from '@/hooks/web/useDictionaries'
-import { cityToProvince } from '@/utils/areaDeal'
 import { getTimeStamp, timesTampChange } from '@/utils/date'
 import { updatePersonAvatar, saveResumeBasicInfo } from '@/api/recruit/personal/resume'
 import { useUserStore } from '@/store/user'
@@ -330,60 +329,30 @@ const items = ref({
       items: []
     },
     {
-      type: 'autocomplete',
-      key: 'workAreaProvinceId',
-      value: null,
-      label: '所在城市:省',
-      outlined: true,
-      itemText: 'name',
-      itemValue: 'id',
-      returnSelect: true,
-      noParam: true,
-      col: 6,
-      flexStyle: 'mr-3',
-      items: [],
-      change: null
-    },
-    {
-      type: 'autocomplete',
+      type: 'cascade',
       key: 'areaId',
       value: null,
-      label: '所在城市:市',
-      outlined: true,
-      itemText: 'name',
-      itemValue: 'id',
-      col: 6,
-      items: [],
-      change: null
-    },
-    {
-      type: 'autocomplete',
-      key: 'regProvinceId',
-      value: null,
-      label: '户籍地:省',
-      outlined: true,
-      clearable: true,
+      default: null,
+      label: '所在城市',
       itemText: 'name',
       itemValue: 'id',
-      returnSelect: true,
-      noParam: true,
+      required: true,
+      clearable: false,
       col: 6,
-      flexStyle: 'mr-3',
       items: [],
-      change: null
     },
     {
-      type: 'autocomplete',
+      type: 'cascade',
       key: 'regId',
       value: null,
-      label: '户籍地:市',
-      outlined: true,
-      clearable: true,
+      default: null,
+      label: '户籍地',
       itemText: 'name',
       itemValue: 'id',
+      required: false,
+      clearable: true,
       col: 6,
       items: [],
-      change: null
     },
     {
       type: 'datePicker',
@@ -402,9 +371,7 @@ const handleSave = async () => {
   const { valid } = await CtFormRef.value.formRef.validate()
   if (!valid) return
   const obj = {}
-  let clearRegProvinceId = false
   items.value.options.forEach(e => {
-    if (e.key === 'regId' && !obj[e.key]) clearRegProvinceId = true
     if (e.type === 'datepicker') obj[e.key] = getTimeStamp(e.value)
     else obj[e.key] = e.value
   })
@@ -415,8 +382,6 @@ const handleSave = async () => {
   await userStore.getUserBaseInfos(baseInfo.value.userId || null)
   getBasicInfo()
 
-  // 清除户籍地:省
-  if (clearRegProvinceId) items.value.options.forEach(e => { if (e.key === 'regProvinceId') e.value = null })
 }
 
 // 获取字典内容
@@ -427,26 +392,6 @@ const getDictData = async (dictTypeName) => {
     item.items = data
   }
 }
-const timeCount = {}
-const deal = async (id, cityKey, provinceKey) => {
-  if (!id && id !== 0) return
-  // 省份回显
-  const province = items.value.options.find(pv => pv.key === provinceKey)
-  if (!province?.items.length) { // 字典数据未获取
-    timeCount[provinceKey] = 0
-    setTimeout(() => {
-      timeCount[provinceKey]++
-      if (timeCount[provinceKey] < 6) deal(id, cityKey, provinceKey)
-    }, 2000)
-    return
-  }
-  if (province) {
-    const dealReturnObj = await cityToProvince(id, {}, province.items || [])
-    const city = items.value.options.find(pv => pv.key === cityKey)
-    if (city) city.items = dealReturnObj.cityList || []
-    province.value = dealReturnObj.pid || ''
-  }
-}
 
 items.value.options.forEach((e, index) => {
   if ((index + 2) % 2 === 0) e.flexStyle = 'mr-3'
@@ -455,45 +400,19 @@ items.value.options.forEach((e, index) => {
   if (infoExist && baseInfo.value[e.key]) e.value = baseInfo.value[e.key]
   // 日期相关
   if (e.type === 'datepicker') e.value = timesTampChange(e.value, 'Y-M-D')
-  // 所在城市回显
-  if (infoExist && e.key === 'areaId' && baseInfo.value[e.key]) {
-    const id = baseInfo.value[e.key]
-    deal(id, e.key, 'workAreaProvinceId')
-  }
-  if (infoExist && e.key === 'regId' && baseInfo.value[e.key]) {
-    const id = baseInfo.value[e.key]
-    deal(id, e.key, 'regProvinceId')
-  }
   if (e.value === undefined || e.value === null || e.value === '') completeStatus = false
 })
 // 完成度展示
   
-const provinceChange = (value, val, obj) => {
-  console.log(obj, 'area')
-  let cityKey
-  if (val?.key === 'workAreaProvinceId') cityKey = 'areaId'
-  if (val?.key === 'regProvinceId') cityKey = 'regId'
-  if (!cityKey) return
-  const item = items.value.options.find(e => e.key === cityKey)
-  if (!item) return
-  item.items = obj?.children || []
-  item.value = null
-}
 getDict('areaTreeData', null, 'areaTreeData').then(({ data }) => {
   data = data?.length && data || []
   if (!data?.length) return console.error('areaTreeData获取失败!')
   const chinaTreeData = data
   if (!chinaTreeData?.length) return console.error('chinaTreeData获取失败!')
-  const workAreaProvince = items.value.options.find(e => e.key === 'workAreaProvinceId')
-  const regAreaProvince = items.value.options.find(e => e.key === 'regProvinceId')
-  if (workAreaProvince?.items) {
-    workAreaProvince.items = chinaTreeData
-    workAreaProvince.change = provinceChange
-  }
-  if (regAreaProvince?.items) {
-    regAreaProvince.items = chinaTreeData
-    regAreaProvince.change = provinceChange
-  }
+  const workAreaProvince = items.value.options.find(e => e.key === 'areaId')
+  const regAreaProvince = items.value.options.find(e => e.key === 'regId')
+  if (workAreaProvince?.items) workAreaProvince.items = chinaTreeData
+  if (regAreaProvince?.items) regAreaProvince.items = chinaTreeData
 })
 </script>
 

+ 3 - 1
src/views/recruit/personal/PersonalCenter/resume/online/components/vocationalSkills.vue

@@ -101,7 +101,9 @@ getData()
 
 // 保存 职业技能
 const handleSave = async () => {
-  const { valid } = await formPageRef.value.formRef.validate()
+  // console.log(1, 'console', formPageRef.value.formRef)
+  const { valid } = await formPageRef.value.validate()
+  console.log(222, valid)
   if (!valid) return
   const obj = {}
   formItems.value.options.forEach(e => {