提交 ad5749fe authored 作者: lidongxu's avatar lidongxu

refactor(promotion/plan): 计划任务中上下班时间设置改为时分,秒固定为0

同上
上级 c55177fb
......@@ -17,4 +17,13 @@ export function createExamine(data) {
method: 'post',
data: data
})
}
// 获取稽核任务列表
export function getExamineList() {
return request({
baseURL: VITE_APP_PROMOTION,
url: `/exa/query/page`,
method: 'post',
})
}
\ No newline at end of file
......@@ -19,7 +19,6 @@
accept="image/*"
v-model="form.storePicture"
:after-read="storePictureRead"
:capture="['camera', 'album']"
preview-size="120"
@delete="deleteStorePicture">
</van-uploader>
......
<template>
<div class="app-container">
<div class="container">
<!-- 查询表单 -->
<el-form :model="queryParams"
inline
label-width="68px">
<el-form-item label="活动日期"
prop="date">
<el-date-picker v-model="queryParams.date"
type="daterange"
clearable
range-separator="至"
start-placeholder="开始日期"
end-placeholder="结束日期"
:shortcuts="pickerOptions"
@change="getTaskList" />
</el-form-item>
<el-form-item label="任务执行"
prop="taskStatus">
<el-radio-group v-model="queryParams.taskStatus"
@change="getTaskList">
<el-radio-button v-for="item in taskStatusList"
:key="item.value"
:label="item.label"
:value="item.value" />
</el-radio-group>
</el-form-item>
<!-- 省市 -->
<el-row>
<el-form-item label="区域查询"
prop="region">
<el-radio-group v-model="queryParams.region"
@change="regionChange">
<el-radio-button label="全国"
value="全国" />
<el-radio-button label="省"
value="省" />
<el-radio-button label="省-市"
value="省-市" />
</el-radio-group>
</el-form-item>
<el-form-item label="省份"
prop="province"
v-show="queryParams.region !== '全国'">
<el-select v-model="queryParams.provinceId"
placeholder="请选择省"
@change="getProCity">
<el-option v-for="item in provinceList"
:key="item.value"
:label="item.label"
:value="item.value" />
</el-select>
</el-form-item>
<el-form-item label="城市"
prop="city"
v-show="queryParams.region === '省-市'">
<el-select v-model="queryParams.cityId"
placeholder="请选择市">
<el-option v-for="item in cityList"
:key="item.value"
:label="item.label"
:value="item.value" />
</el-select>
</el-form-item>
</el-row>
<el-row>
<el-form-item label="战区"
prop="zone">
<el-select v-model="queryParams.zoneId"
placeholder="请选择战区"
clearable
:disabled="cityManagerPrivilege"
@change="getTaskList">
<el-option v-for="item in zoneList"
:key="item.value"
:label="item.label"
:value="item.value" />
</el-select>
</el-form-item>
<el-form-item label="负责人"
prop="manager">
<el-select v-model="queryParams.managerId"
placeholder="请选择负责人"
:disabled="cityManagerPrivilege"
clearable
@change="getTaskList">
<el-option v-for="item in managerList"
:key="item.value"
:label="item.label"
:value="item.value" />
</el-select>
</el-form-item>
<el-form-item label="门店"
prop="store">
<el-input v-model="queryParams.storeName"
clearable
@input="getTaskList"
placeholder="请输入门店名称" />
</el-form-item>
</el-row>
</el-form>
<!-- 数据表格 -->
<el-table :data="tableList"
:cell-style="{ 'word-wrap': 'break-word', 'white-space': 'normal' }"
border
style="width: 100%"
show-overflow-tooltip>
<el-table-column v-for="item in columns"
:key="item.label"
:prop="item.prop"
:label="item.label"
:width="item.width"
:formatter="formatter"
:fixed="item.fixed" />
<el-table-column label="操作"
width="200"
fixed="right">
<template #default="scope">
<el-button type="primary"
@click="lookPhoto(scope.row)"
text>
查看照片
</el-button>
<el-button type="danger"
@click="deleteView(scope.row)"
text>
删除
</el-button>
</template>
</el-table-column>
</el-table>
<!-- 分页 -->
<pagination :total="total"
v-model:page="queryParams.page"
v-model:limit="queryParams.pageSize"
@pagination="getTaskList" />
<!-- 照片查看弹窗 -->
<el-dialog :title="photoLookInfoObj.storeName"
v-model="photoDialogVisible"
width="60%">
<p>活动记录 ID :{{ photoLookInfoObj.id }}</p>
<p>活动时间 :{{ photoLookInfoObj.createDate }}</p>
<el-card v-for="obj in photoDialogList" shadow="never">
<template #header>{{ obj.title }}</template>
<div class="content">
<el-result :title="item.time"
:sub-title="item.title"
v-for="item in obj.list">
<template #icon>
<el-image :src="item.photoUrl"
:preview-src-list="[...obj.list.map(o => o.photoUrl)]" />
</template>
</el-result>
</div>
</el-card>
</el-dialog>
</div>
</div>
</template>
<script setup>
import { reactive } from 'vue'
import { useDatePickerOptions } from '@/hooks'
import { getWarZoneListAPI, getChargeListAPI, getTaskListAPI, getProCityAPI, deletePromotionSystemAPI, getPromotionSystemAPI, getPromotionActivityAPI, getExamineList } from '@/api'
import { parseTime } from '@/utils'
import store from '@/store'
import { ElMessage, ElMessageBox } from 'element-plus';
const { recentPickerOptions: pickerOptions, last7Date, todayDate } = useDatePickerOptions(0)
const queryParams = reactive({
taskStatus: '全部',
region: '全国',
provinceId: undefined,
cityId: undefined,
zoneId: undefined,
managerId: undefined,
storeName: undefined,
page: 1,
pageSize: 10,
date: []
})
const photoDialogVisible = ref(false)
const photoDialogList = ref([])
const photoLookInfoObj = ref({})
const total = ref(0)
// 城市经理状态为 true
const cityManagerPrivilege = computed(() => {
return store.state?.value?.user?.userInfo?.privilegeId == 1
})
// 任务状态
const taskStatusList = ref([
{
label: '是',
value: '是'
},
{
label: '否',
value: '否'
},
{
label: '全部',
value: '全部'
}
])
// 区域查询
const provinceList = ref([])
const cityList = ref([])
const getProCity = async () => {
const { data } = await getProCityAPI(queryParams)
if (queryParams.provinceId) {
queryParams.cityId = undefined
cityList.value = data.map(item => ({
label: item.name,
value: item.num
}))
} else {
provinceList.value = data.map(item => ({
label: item.name,
value: item.num
}))
}
getTaskList()
}
getProCity()
// 战区列表
const zoneList = ref([])
const getZoneList = async () => {
const { data } = await getWarZoneListAPI()
zoneList.value = data.map(item => {
return {
label: item.orgName,
value: item.qcId
}
})
}
getZoneList()
// 负责人列表
const managerList = ref([])
const getManagerList = async () => {
const { data } = await getChargeListAPI()
managerList.value = data.map(item => {
return {
label: item.name,
value: item.id,
employeeNo: item.employeeNo,
deptQcName: item.deptQcName,
deptQcId: item.deptQcId
}
})
}
getManagerList()
// 任务列表
const tableList = ref([])
const columns = ref([
{
label: '稽核标识',
prop: 'id',
width: 90,
},
{
label: '稽核人',
prop: 'temporaryName',
width: 90,
},
{
label: '稽核人工号',
prop: 'createDate',
width: 120,
},
{
label: 'CP 活动 ID',
prop: 'week',
width: 120
},
{
label: '是否执行',
prop: 'province',
width: 100
},
{
label: '战区',
prop: 'city',
width: 100
},
{
label: '城市经理',
prop: 'dealerName',
width: 120
},
{
label: '城市',
prop: 'storeName',
width: 120
},
{
label: '活动日期',
prop: 'activityPattern',
width: 150
},
{
label: '系统名称',
prop: 'approveStatus',
width: 150
},
{
label: '门店',
prop: 'clockDto.clockInTime',
width: 150
},
{
label: '经销商',
prop: 'clockDto.noonClockOutTime', // 拼接地址 noonClockOutAddress, 经纬度 noonClockOutCoordinates
width: 300
},
{
label: '活动模式',
prop: 'clockDto.noonClockInTime', // 拼接地址 noonClockInAddress, 经纬度 noonClockInCoordinates
width: 300
},
{
label: '稽核日期',
prop: 'clockDto.clockOutTime', // 拼接地址 clockOutAddress, 经纬度 clockOutCoordinates
width: 300
},
{
label: '门头照',
prop: 'deptQcOrgName',
width: 150
},
{
label: '促销员人数',
prop: 'manageName',
width: 120
},
{
label: '地堆',
prop: 'manageName',
width: 120
},
{
label: '促销员是否在岗',
prop: 'manageName',
width: 120
},
{
label: '话术',
prop: 'manageName',
width: 120
},
{
label: '物料',
prop: 'manageName',
width: 120
},
{
label: '着装',
prop: 'manageName',
width: 120
},
{
label: '工作取证照片',
prop: 'manageName',
width: 120
},
{
label: '特陈照',
prop: 'manageName',
width: 120
},
{
label: '主货架照',
prop: 'manageName',
width: 120
},
{
label: 'POS 金额',
prop: 'manageName',
width: 120
},
{
label: 'POS 照片',
prop: 'manageName',
width: 120
},
{
label: '创建人',
prop: 'manageName',
width: 120
},
{
label: '创建时间',
prop: 'manageName',
width: 120
},
{
label: '修改人',
prop: 'manageName',
width: 120
},
{
label: '修改时间',
prop: 'manageName',
width: 120
}
])
// 删除任务列表
const deleteView = async (row) => {
await ElMessageBox.confirm('确认删除吗?', '提示', {
confirmButtonText: '确定',
cancelButtonText: '取消',
type: 'warning'
})
await deletePromotionSystemAPI(row.id)
// 提示删除成功
getTaskList()
ElMessage.success('删除成功')
}
// 获取稽核任务列表
const getTaskList = async () => {
const { data } = await getExamineList(queryParams)
console.log(data)
}
getTaskList()
const formatter = (row, columns, value) => {
// 判断有值再转换
if (columns.property === 'clockDto.clockInTime' && value) {
return parseTime(value, '{h}:{i}') + '\n' + row['clockDto']['clockInAddress']
} else if (columns.property === 'clockDto.noonClockOutTime' && value) {
return parseTime(value, '{h}:{i}') + '\n' + row['clockDto']['noonClockOutAddress']
} else if (columns.property === 'clockDto.noonClockInTime' && value) {
return parseTime(value, '{h}:{i}') + '\n' + row['clockDto']['noonClockInAddress']
} else if (columns.property === 'clockDto.clockOutTime' && value) {
return parseTime(value, '{h}:{i}') + '\n' + row['clockDto']['clockOutAddress']
} else if (columns.property === 'week') {
return parseTime(row['createDate'], '周{a}')
} else if (columns.property === 'approveStatus' && value) {
const obj = {
SUBMITTED: '未审批',
APPROVED: '已审批'
}
return obj[value]
}
return value
}
// 区域查询切换
const regionChange = (val) => {
if (val === '全国') {
queryParams.provinceId = undefined
queryParams.cityId = undefined
} else if (val === '省') {
queryParams.cityId = undefined
} else if (val === '省-市') {
cityList.value = []
getProCity()
}
getTaskList()
}
// 查看照片
const lookPhoto = async (row) => {
photoDialogVisible.value = true
photoLookInfoObj.value = row
const result = await getPromotionActivityAPI(row.id)
const { tgcjPhotoInfos: tgcjPhotoInfosList, tghdPhotoInfos: tghdPhotoInfosList, tgscPhotoInfos: tgscPhotoInfosList } = result.data
if (tgscPhotoInfosList) {
var tgscPhotoInfos = [...tgscPhotoInfosList?.map(item => ({
time: parseTime(item.createTime, '{h}:{i}'),
photoUrl: item.photoUrl
}))]
}
if (tghdPhotoInfosList) {
var tghdPhotoInfos = [...tghdPhotoInfosList?.map(item => ({
time: parseTime(item.createTime, '{h}:{i}'),
photoUrl: item.photoUrl
}))]
}
if (tgcjPhotoInfosList) {
var tgcjPhotoInfos = [...tgcjPhotoInfosList?.map(item => ({
time: parseTime(item.createTime, '{h}:{i}'),
photoUrl: item.photoUrl
}))]
}
const res = await getPromotionSystemAPI(row.clockDto.id)
// 判断上班卡,午休下班卡,午休上班卡,下班卡是否有值,有则添加到数组中
// 数组是二维数组,第一到三是推广数据,第四个是打卡数据
const { clockInTime, noonClockOutTime, noonClockInTime, clockOutTime } = res.data
const clockList = []
if (clockInTime) {
clockList.push({
time: parseTime(clockInTime, '{h}:{i}'),
title: '上班卡',
photoUrl: res.data.clockInPhoto
})
}
if (noonClockOutTime) {
clockList.push({
time: parseTime(noonClockOutTime, '{h}:{i}'),
title: '午休下班卡',
photoUrl: res.data.noonClockOutPhoto
})
}
if (noonClockInTime) {
clockList.push({
time: parseTime(noonClockInTime, '{h}:{i}'),
title: '午休上班卡',
photoUrl: res.data.noonClockInPhoto
})
}
if (clockOutTime) {
clockList.push({
time: parseTime(clockOutTime, '{h}:{i}'),
title: '下班卡',
photoUrl: res.data.clockOutPhoto
})
}
// 组装数据
photoDialogList.value = [{
title: '推广试吃照片',
list: tgscPhotoInfos
}, {
title: '推广互动照片',
list: tghdPhotoInfos
}, {
title: '推广成交照片',
list: tgcjPhotoInfos
}, {
title: '考勤打卡照片',
list: clockList
}]
}
const currentChange = (page) => {
queryParams.page = page
getTaskList()
}
</script>
<style scoped
lang="scss">
::v-deep(.el-form-item) {
width: 350px !important;
}
.el-card{
margin-top: 20px;
}
/* 单元格支持 \n 换行 */
.container .el-table ::v-deep(.cell) {
white-space: pre-line;
/* 强制显示 2 行,超出的省略号 */
/* overflow: hidden;
text-overflow: ellipsis;
display: -webkit-box;
-webkit-line-clamp: 1;
-webkit-box-orient: vertical; */
}
::v-deep(.el-overlay) {
.el-card__body {
.content {
/* display: flex; */
overflow-y: hidden;
overflow-x: scroll;
white-space: nowrap;
/* 阻止内容换行 */
&::-webkit-scrollbar-track {
background: transparent;
/* 滚动条轨道背景透明 */
}
.el-result {
width: 250px;
height: 350px;
display: inline-block;
.el-result__icon {
width: 100%;
height: 100%;
}
.el-image {
width: 100%;
height: 100%;
}
}
}
}
}
</style>
\ No newline at end of file
......@@ -349,24 +349,24 @@
<el-col :span="12">
<!-- 上班打卡时间 -->
<el-form-item label="上班打卡时间"
prop="clockInTime">
<el-time-picker v-model="addOrEditPlanForm.clockInTime"
prop="inTime">
<el-time-picker v-model="addOrEditPlanForm.inTime"
placeholder="选择时间"
format="HH:mm"
value-format="YYYY-MM-DDTHH:mm:ss"
value-format="HH:mm:ss"
style="width: 95%" />
</el-form-item>
</el-col>
<el-col :span="12">
<!-- 下班打卡时间 -->
<el-form-item label="下班打卡时间"
prop="clockOutTime">
<el-time-picker v-model="addOrEditPlanForm.clockOutTime"
prop="outTime">
<el-time-picker v-model="addOrEditPlanForm.outTime"
placeholder="选择时间"
format="HH:mm"
value-format="YYYY-MM-DDTHH:mm:ss"
value-format="HH:mm:ss"
style="width: 95%"
:disabled="!addOrEditPlanForm.clockInTime"
:disabled="!addOrEditPlanForm.inTime"
:disabled-hours="disabledHours"
:disabled-minutes="disabledMinutes"
:disabled-seconds="disabledSeconds" />
......@@ -1003,14 +1003,14 @@ const addOrEditPlanFormRules = reactive({
trigger: 'blur'
}
],
clockInTime: [
inTime: [
{
required: true,
message: '请选择上班打卡时间',
trigger: 'blur'
}
],
clockOutTime: [
outTime: [
{
required: true,
message: '请选择下班打卡时间',
......@@ -1082,21 +1082,21 @@ const makeRange = (start, end) => {
}
const disabledHours = (h) => {
// 根据上班时间选择的结果,禁用小时
const date = new Date(addOrEditPlanForm.value.clockInTime)
const date = new Date(addOrEditPlanForm.value.nTime)
return makeRange(0, date.getHours() - 1);
}
const disabledMinutes = (h, m) => {
// 如果小时大于上班打卡时间小时,则不限制分钟
const inDate = new Date(addOrEditPlanForm.value.clockInTime)
const inDate = new Date(addOrEditPlanForm.value.inTime)
if (h > inDate.getHours()) {
return makeRange(0, -1);
} else {
const date = new Date(addOrEditPlanForm.value.clockInTime)
const date = new Date(addOrEditPlanForm.value.inTime)
return makeRange(0, date.getMinutes() - 1);
}
}
const disabledSeconds = (h, m, s) => {
const date = new Date(addOrEditPlanForm.value.clockInTime)
const date = new Date(addOrEditPlanForm.value.inTime)
return makeRange(0, date.getSeconds() - 1);
}
......@@ -1112,22 +1112,13 @@ const handleAddOrEditPlan = async () => {
addOrEditPlanForm.value.operNo = userStore().getEmployeeNo
addOrEditPlanForm.value.operName = store.state.value.user.userInfo.nickName
addOrEditPlanForm.value.operId = store.state.value.user.userInfo.userId
// 上班打卡和下班打卡时间前面要和 date 创建任务的年月日一致
const nowDate = new Date(addOrEditPlanForm.value.date)
const clockInTime = new Date(addOrEditPlanForm.value.clockInTime)
clockInTime.setFullYear(nowDate.getFullYear())
clockInTime.setMonth(nowDate.getMonth())
clockInTime.setDate(nowDate.getDate())
// 下班打卡时间
const clockOutTime = new Date(addOrEditPlanForm.value.clockOutTime)
clockOutTime.setFullYear(nowDate.getFullYear())
clockOutTime.setMonth(nowDate.getMonth())
clockOutTime.setDate(nowDate.getDate())
console.log(addOrEditPlanForm.value)
const dataObj = {
...addOrEditPlanForm.value,
clockInTime,
clockOutTime
// 格式是 xx:xx:xx,替换最后一对 xx 为 00
inTime: addOrEditPlanForm.value.inTime.replace(/:\d{2}$/, ':00'),
outTime: addOrEditPlanForm.value.outTime.replace(/:\d{2}$/, ':00')
}
if (dataObj.id) {
// 根据归属人 employeeId 查询它的 id 和名字
......
Markdown 格式
0%
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论