admin-vben5/apps/web-antd/src/views/property/attendanceManagement/attendanceGroupSettings/attendance-group-detail.vue
dev_ljl 84cade81df
Some checks are pending
Gitea Actions Demo / Explore-Gitea-Actions (push) Waiting to run
fix:巡检计划编辑、保养计划编辑
2025-07-29 15:26:41 +08:00

245 lines
7.5 KiB
Vue
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

<script setup lang="ts">
import { ref, shallowRef } from 'vue';
import { useVbenModal } from '@vben/common-ui';
import {
Button,
Checkbox,
Descriptions,
DescriptionsItem,
Table,
} from 'ant-design-vue';
import dayjs from 'dayjs';
import duration from 'dayjs/plugin/duration';
import relativeTime from 'dayjs/plugin/relativeTime';
import { renderDict } from '#/utils/render';
import { groupInfo } from '#/api/property/attendanceManagement/attendanceGroupSettings';
import type { GroupVO } from '#/api/property/attendanceManagement/attendanceGroupSettings/model';
import {
infoCycleColumns,
infoClockingColumns,
infoNoClockingColumns,
infoWeekdayColumns,
} from '#/views/property/attendanceManagement/attendanceGroupSettings/data';
import holidayCalendar from './holiday-calendar.vue';
dayjs.extend(duration);
dayjs.extend(relativeTime);
const [BasicModal, modalApi] = useVbenModal({
onOpenChange: handleOpenChange,
onClosed() {
groupDetail.value = null;
},
});
const groupDetail = shallowRef<null | GroupVO>(null);
const weekdayData = ref<any[]>([]);
const cycleData = ref<any[]>([]);
const unCheckInData = ref<any[]>([]);
const checkInData = ref<any[]>([]);
async function handleOpenChange(open: boolean) {
if (!open) {
return null;
}
modalApi.modalLoading(true);
const {id,attendanceType} = modalApi.getData() as { id?: number | string,attendanceType?:string };
const res = await groupInfo(id as string,attendanceType as string);
groupDetail.value=res;
if(res.attendanceType==0){
unCheckInData.value=res.clockDateList.filter(item=>item.mustNoCheck==0)
checkInData.value=res.clockDateList.filter(item=>item.mustNoCheck==1)
weekdayData.value=res.weekList
weekdayData.value.forEach(item => {
if(item.shiftId){
const shift = res.attendanceList.find(i => item.shiftId == i.id);
let str = ''
if (shift.isRest) {
str = `${shift.name}${shift.startTime}~${shift.restStartTime} ${shift.restEndTime}~${shift.endTime}`;
} else {
str = `${shift.name}${shift.startTime}~${shift.endTime}`;
}
item.shiftValue=str
}
})
groupDetail.value.isAutomatic=true
}else {
cycleData.value=[];
}
modalApi.modalLoading(false);
}
const [HolidayCalendar, holidayApi] = useVbenModal({
connectedComponent: holidayCalendar,
});
/**
* 查看法定节假日日历
*/
async function showHoliday() {
holidayApi.open();
}
</script>
<template>
<BasicModal
:footer="false"
:fullscreen-button="false"
title="考勤组信息"
class="w-[70%]"
>
<div v-if="groupDetail" class="des-container">
<Descriptions size="small" :column="1" :labelStyle="{ width: '100px' }">
<DescriptionsItem label="考勤组名称">
{{ groupDetail.groupName }}
</DescriptionsItem>
<DescriptionsItem label="考勤类型">
<component
:is="renderDict(groupDetail.attendanceType, 'wy_kqlx')"
/>
</DescriptionsItem>
<DescriptionsItem label="状态">
<component :is="renderDict(groupDetail.status, 'wy_state')" />
</DescriptionsItem>
<DescriptionsItem
label="工作日设置"
v-if="groupDetail.attendanceType == 0"
>
<div class="item-font" style="width: 100%">
<Table
style="width: 90%"
bordered
:columns="infoWeekdayColumns"
:data-source="weekdayData"
size="small"
:pagination="false"
>
<template #bodyCell="{ column, record }">
<template v-if="column.dataIndex === 'dayOfWeek'">
<component :is="renderDict(record.dayOfWeek,'wy_kqgzr')"></component>
</template>
<template v-if="column.dataIndex === 'shiftId'">
<span v-if="record.shiftId">{{record.shiftValue }}</span>
<span v-else>休息</span>
</template>
</template>
</Table>
<Checkbox
class="item-padding-top"
v-model:checked="groupDetail.isAutomatic"
>
法定节假日自动排休
</Checkbox>
<Button type="link" @click="showHoliday">查看法定节假日日历</Button>
<p class="item-padding-top item-font-weight">特殊日期:</p>
<p class="item-padding">无需打卡日期:</p>
<Table
style="width: 75%"
bordered
:columns="infoNoClockingColumns"
:data-source="unCheckInData"
size="small"
:pagination="false"
>
<template #bodyCell="{ column, record }">
<template v-if="column.dataIndex === 'dateTime'">
<span v-if="record.dateType == 0">{{
dayjs(record.startDate).format('YYYY-MM-DD')
}}</span>
<span v-else>{{
dayjs(record.startDate).format('YYYY-MM-DD')
+ '~' + dayjs(record.endDate).format('YYYY-MM-DD')
}}</span>
</template>
</template>
</Table>
<p class="item-padding">必须打卡日期:</p>
<Table
style="width: 75%"
bordered
:columns="infoClockingColumns"
:data-source="checkInData"
size="small"
:pagination="false"
>
<template #bodyCell="{ column, record }">
<template v-if="column.dataIndex === 'dateTime'">
<span v-if="record.dateType == 0">{{
dayjs(record.startDate).format('YYYY-MM-DD')
}}</span>
<span v-else>{{
dayjs(record.startDate).format('YYYY-MM-DD')
+ '~' + dayjs(record.endDate).format('YYYY-MM-DD')
}}</span>
</template>
</template>
</Table>
</div>
</DescriptionsItem>
<DescriptionsItem
label="排班周期"
v-if="groupDetail.attendanceType == 1"
>
<p class="item-font">
周期天数
<span class="item-font-weight item-font-color">{{
cycleData.length
}}</span>
</p>
<Table
style="width: 80%; margin-top: 5px"
bordered
:columns="infoCycleColumns"
:data-source="cycleData"
size="small"
:pagination="false"
>
<template #bodyCell="{ column, record, index }">
<template v-if="column.dataIndex === 'day'">
<span>{{ '第' + (index + 1) + '天' }}</span>
</template>
<template v-if="column.dataIndex === 'shiftId'">
{{record.shiftId}}
</template>
</template>
</Table>
</DescriptionsItem>
</Descriptions>
<HolidayCalendar></HolidayCalendar>
</div>
</BasicModal>
</template>
<style lang="scss" scoped>
.des-container {
.item-font {
font-size: 0.875rem;
}
.item-font-weight {
font-weight: 500;
}
.item-font-color {
color: red;
}
.item-padding-top {
padding-top: 1.1rem;
}
.item-padding {
padding: 1.1rem 0 0.5rem 0;
}
:deep(
.ant-descriptions
.ant-descriptions-item-container
.ant-descriptions-item-content
) {
display: block;
}
}
</style>