| | |
| | | <el-option v-for="item in shifts_list" |
| | | :key="item.value" |
| | | :label="item.label" |
| | | :value="item.value" /> |
| | | :value="item.value" |
| | | :disabled=" |
| | | operationType === 'add' && |
| | | (String(item.label || '').includes('假') || |
| | | String(item.label || '').includes('休')) |
| | | " /> |
| | | </el-select> |
| | | </el-form-item> |
| | | <el-form-item label="打卡范围(m)" |
| | | prop="radius"> |
| | | prop="radius" |
| | | v-show="!hideClockFields"> |
| | | <el-input-number v-model="form.radius" |
| | | :min="10" |
| | | :max="1000" |
| | |
| | | </el-form-item> |
| | | <!-- 高德地图选择 --> |
| | | <el-form-item label="打卡位置" |
| | | prop="longitude"> |
| | | prop="longitude" |
| | | v-show="!hideClockFields"> |
| | | <div class="map-container"> |
| | | <div class="map-header" |
| | | style="margin-bottom: 10px"> |
| | |
| | | </div> |
| | | </el-form-item> |
| | | <el-form-item label="地点名称" |
| | | prop="locationName"> |
| | | prop="locationName" |
| | | v-show="!hideClockFields"> |
| | | <el-input v-model="form.locationName" |
| | | :disabled="operationType === 'view'" |
| | | placeholder="请输入地点名称" /> |
| | | </el-form-item> |
| | | <!-- 上下班时间 --> |
| | | <el-form-item label="上班时间" |
| | | prop="startAt"> |
| | | prop="startAt" |
| | | v-show="!hideClockFields"> |
| | | <el-time-picker v-model="form.startAt" |
| | | format="HH:mm" |
| | | value-format="HH:mm" |
| | |
| | | :disabled="operationType === 'view'" /> |
| | | </el-form-item> |
| | | <el-form-item label="下班时间" |
| | | prop="endAt"> |
| | | prop="endAt" |
| | | v-show="!hideClockFields"> |
| | | <el-time-picker v-model="form.endAt" |
| | | format="HH:mm" |
| | | value-format="HH:mm" |
| | |
| | | </el-form> |
| | | <template #footer> |
| | | <span class="dialog-footer"> |
| | | <el-button type="primary" @click="submitForm" v-if="operationType !== 'view'">确定</el-button> |
| | | <el-button type="primary" |
| | | @click="submitForm" |
| | | v-if="operationType !== 'view'">确定</el-button> |
| | | <el-button @click="dialogVisible = false">取消</el-button> |
| | | </span> |
| | | </template> |
| | |
| | | // 获取班次字典值 |
| | | const { shifts_list } = useDict("shifts_list"); |
| | | |
| | | const selectedShiftLabel = computed(() => { |
| | | const item = shifts_list.value?.find( |
| | | s => String(s.value) === String(form.shift) |
| | | ); |
| | | return item?.label || ""; |
| | | }); |
| | | |
| | | const hideClockFields = computed(() => { |
| | | if (props.operationType === "view") return false; |
| | | return ( |
| | | selectedShiftLabel.value.includes("假") || |
| | | selectedShiftLabel.value.includes("休") |
| | | ); |
| | | }); |
| | | |
| | | // 表单数据 |
| | | const formRef = ref(); |
| | | const form = reactive({ |
| | |
| | | }); |
| | | |
| | | // 表单验证规则 |
| | | const rules = { |
| | | sysDeptId: [{ required: true, message: "请选择部门", trigger: "change" }], |
| | | locationName: [ |
| | | { required: true, message: "请输入地点名称", trigger: "blur" }, |
| | | ], |
| | | longitude: [{ required: true, message: "请选择打卡位置", trigger: "blur" }], |
| | | latitude: [{ required: true, message: "请选择打卡位置", trigger: "blur" }], |
| | | shift: [{ required: true, message: "请选择班次", trigger: "change" }], |
| | | radius: [{ required: true, message: "请输入打卡范围", trigger: "blur" }], |
| | | startAt: [{ required: true, message: "请选择上班时间", trigger: "change" }], |
| | | endAt: [ |
| | | { required: true, message: "请选择下班时间", trigger: "change" }, |
| | | { |
| | | validator: (rule, value, callback) => { |
| | | // 如果是夜班,不限制时间顺序 |
| | | if (form.shift && ['夜班', '夜'].includes(form.shift)) { |
| | | callback(); |
| | | return; |
| | | } |
| | | if (form.startAt && value) { |
| | | const startParts = form.startAt.split(":"); |
| | | const endParts = value.split(":"); |
| | | const startTime = |
| | | parseInt(startParts[0]) * 60 + parseInt(startParts[1]); |
| | | const endTime = parseInt(endParts[0]) * 60 + parseInt(endParts[1]); |
| | | if (endTime <= startTime) { |
| | | callback(new Error("下班时间不能早于上班时间")); |
| | | const rules = computed(() => { |
| | | const base = { |
| | | sysDeptId: [{ required: true, message: "请选择部门", trigger: "change" }], |
| | | shift: [{ required: true, message: "请选择班次", trigger: "change" }], |
| | | }; |
| | | |
| | | if (hideClockFields.value) { |
| | | return base; |
| | | } |
| | | |
| | | return { |
| | | ...base, |
| | | locationName: [ |
| | | { required: true, message: "请输入地点名称", trigger: "blur" }, |
| | | ], |
| | | longitude: [{ required: true, message: "请选择打卡位置", trigger: "blur" }], |
| | | latitude: [{ required: true, message: "请选择打卡位置", trigger: "blur" }], |
| | | radius: [{ required: true, message: "请输入打卡范围", trigger: "blur" }], |
| | | startAt: [{ required: true, message: "请选择上班时间", trigger: "change" }], |
| | | endAt: [ |
| | | { required: true, message: "请选择下班时间", trigger: "change" }, |
| | | { |
| | | validator: (rule, value, callback) => { |
| | | if (form.shift && ["夜班", "夜"].includes(form.shift)) { |
| | | callback(); |
| | | return; |
| | | } |
| | | if (form.startAt && value) { |
| | | const startParts = form.startAt.split(":"); |
| | | const endParts = value.split(":"); |
| | | const startTime = |
| | | parseInt(startParts[0]) * 60 + parseInt(startParts[1]); |
| | | const endTime = parseInt(endParts[0]) * 60 + parseInt(endParts[1]); |
| | | if (endTime <= startTime) { |
| | | callback(new Error("下班时间不能早于上班时间")); |
| | | } else { |
| | | callback(); |
| | | } |
| | | } else { |
| | | callback(); |
| | | } |
| | | } else { |
| | | callback(); |
| | | } |
| | | }, |
| | | trigger: "change", |
| | | }, |
| | | trigger: "change", |
| | | }, |
| | | ], |
| | | }; |
| | | ], |
| | | }; |
| | | }); |
| | | |
| | | // 部门选项 |
| | | const deptOptions = ref([]); |
| | |
| | | watch( |
| | | () => form.radius, |
| | | newValue => { |
| | | if (circle) { |
| | | circle.setRadius(newValue); |
| | | if (circle && newValue != null && newValue !== "") { |
| | | circle.setRadius(Number(newValue)); |
| | | } |
| | | } |
| | | ); |
| | |
| | | () => { |
| | | if (formRef.value && form.endAt) { |
| | | formRef.value.validateField("endAt"); |
| | | } |
| | | } |
| | | ); |
| | | |
| | | watch( |
| | | () => hideClockFields.value, |
| | | val => { |
| | | if (!val) return; |
| | | form.radius = null; |
| | | form.longitude = ""; |
| | | form.latitude = ""; |
| | | form.locationName = ""; |
| | | form.startAt = ""; |
| | | form.endAt = ""; |
| | | if (formRef.value) { |
| | | formRef.value.clearValidate([ |
| | | "radius", |
| | | "longitude", |
| | | "latitude", |
| | | "locationName", |
| | | "startAt", |
| | | "endAt", |
| | | ]); |
| | | } |
| | | } |
| | | ); |
| | |
| | | |
| | | // 初始化地图 |
| | | setTimeout(() => { |
| | | initMap(); |
| | | if (!hideClockFields.value) { |
| | | initMap(); |
| | | } |
| | | }, 100); |
| | | } |
| | | } |
| | |
| | | .mt8 { |
| | | margin-top: 8px; |
| | | } |
| | | </style> |
| | | </style> |