import React, { Component } from 'react'; import { connect } from 'dva'; import moment from 'moment'; import _ from 'lodash'; import { Form, Input, Timeline, Row, Button, Checkbox, Icon, Table, InputNumber, TimePicker, Modal, message, Tabs, Drawer } from 'antd'; import './ThiftManagement.less'; import { taskComShiftDelete, //班次管理-班次删除并删除班次的考勤时间安排 taskComShiftPage, //获取班次分页查询 taskComShiftGet, //根据id获取班次 taskComShiftInsert, //添加班次 taskComShiftUpdate //编辑班次 } from '../../services/api'; const FormItem = Form.Item; const { confirm } = Modal; const format = 'HH:mm'; const formItemLayout = { labelCol: { xs: { span: 24 }, sm: { span: 7 } }, wrapperCol: { xs: { span: 24 }, sm: { span: 12 }, md: { span: 10 } } }; const initFormData = { canEdit: true, shiftType: '', //班次类型 effectRule: '', //生效规则 shiftId: '', //班次ID shiftName: '', //班次名称 commutTimes: 1, //每天上下班次数 absentLow: 0, //旷工时间下限 absentSwitch: '0', //旷工校验开关 clockWorkLimit: 0, //上下班打卡时限 clockLimitSwitch: '0', //上下班打卡时限开关 permitLateUp: 0, //允许迟到时间上限 permitLateSwitch: '0', //允许迟到校验开关 shiftRuleList: [ { startWorkTime: moment(`08:00`, format), endWorkTime: moment(`11:00`, format), isStartNextDay: '0', isEndNextDay: '0' } ] }; const { TabPane } = Tabs; @connect(state => ({ profile: state.profile })) @Form.create() export default class NewShift extends Component { constructor(props) { super(props); this.state = { open3: false, //新增班次 visible: false, //添加地点 shiftType: this.props.location.pathname.slice(-1), //1 考勤班次 2 任务班次 taskComShiftPage: [], formData: { ...initFormData }, pagenav: { pageNumber: 1, pageSize: 10, showQuickJumper: true, showSizeChanger: true, showTotal: total => `总共 ${total} 条`, onShowSizeChange: (pageNumber, pageSize) => { const pagenav = Object.assign({}, this.state.pagenav); pagenav.pageNumber = pageNumber; pagenav.pageSize = pageSize; this.setState({ pagenav }); setTimeout(() => { this.taskComShiftPage(); }); }, onChange: (page, pageSize) => { const pagenav = Object.assign({}, this.state.pagenav); pagenav.pageNumber = page; pagenav.pageSize = pageSize; this.setState({ pagenav }); setTimeout(() => { this.taskComShiftPage(); }); }, total: 0 }, totalTime: 0 }; } componentDidMount() { this.taskComShiftPage(); } componentWillReceiveProps(props) { if(props.modalVisble && this.state.shiftType != '2') { this.setState({ shiftType: '2' }); } } //班次管理-班次删除并删除班次的考勤时间安排 taskComShiftDelete = (shiftId, shiftType) => { taskComShiftDelete({ shiftId, shiftType }) .then(data => { this.taskComShiftPage(); }) }; //添加班次 taskComShiftInsert = obj => { taskComShiftInsert(obj) .then(data => { this.setState({ open3: false }); this.taskComShiftPage(); this.props.onClose && this.props.onClose(); this.props.onUpdateShiftPage && this.props.onUpdateShiftPage(); }) }; //编辑班次 taskComShiftUpdate = obj => { taskComShiftUpdate(obj) .then(data => { this.setState({ open3: false }); this.taskComShiftPage(); this.props.onClose && this.props.onClose(); this.props.onUpdateShiftPage && this.props.onUpdateShiftPage(); }) }; //根据id获取班次 taskComShiftGet = shiftId => { taskComShiftGet({ shiftId }) .then(response => { const { data } = response; const formData = {}; const { shiftType, //班次类型 effectRule, //生效规则 shiftName, //班次名称 commutTimes, //每天上下班次数 absentLow, //旷工时间下限 absentSwitch, //旷工校验开关 clockWorkLimit, //上下班打卡时限 clockLimitSwitch, //上下班打卡时限开关 permitLateUp, //允许迟到时间上限 permitLateSwitch, //允许迟到校验开关 shiftRuleList, canEdit, shiftMessage } = data; if (!canEdit) { let tip = shiftMessage.split('\n'); tip = tip.map( (item, index) => index === 0 ? ( {item} ) : (

{item}

) ); message.error(tip); } const newshiftRuleList = shiftRuleList.map(val => { val['startWorkTime'] = moment(val['startWorkTime'], format); val['endWorkTime'] = moment(val['endWorkTime'], format); return val; }); const { setFieldsValue } = this.props.form; formData['shiftType'] = shiftType; formData['effectRule'] = effectRule; formData['shiftId'] = shiftId; formData['shiftName'] = shiftName; formData['commutTimes'] = commutTimes; formData['absentLow'] = absentLow; formData['absentSwitch'] = absentSwitch; formData['clockWorkLimit'] = clockWorkLimit; formData['clockLimitSwitch'] = clockLimitSwitch; formData['permitLateUp'] = permitLateUp; formData['permitLateSwitch'] = permitLateSwitch; formData['shiftRuleList'] = newshiftRuleList; formData['canEdit'] = canEdit; formData['shiftMessage'] = shiftMessage; this.setState({ formData }); setFieldsValue({ shiftName, commutTimes: shiftRuleList.length }); }) .catch(err => { console.log(err, '根据id获取班次-err'); }); }; //获取班次分页查询 taskComShiftPage = () => { const { shiftType } = this.state; const { pageSize, pageNumber } = this.state.pagenav; taskComShiftPage({ pageSize, pageNumber, shiftType }) .then(response => { console.log(response, 'taskComShiftPage-获取班次分页查询-response'); const pagenav = Object.assign({}, this.state.pagenav); let { data } = response.data; pagenav.total = response.data.total; data = data.map((val, i) => { val.key = i; return val; }); if (data.length > 0) { this.setState({ taskComShiftPage: data, pagenav }); } else { this.setState({}); } }) .catch(err => { console.log(err, 'taskComShiftPage-获取班次分页查询-err'); }); }; /******************************相关事件******************************/ //表单提交 handleSubmit = () => { this.props.form.validateFields((err, values) => { const { shiftType, formData } = this.state; const { shiftId, shiftName, absentLow, absentSwitch, clockWorkLimit, clockLimitSwitch, permitLateUp, permitLateSwitch, shiftRuleList, shiftMessage, canEdit } = formData; if (!canEdit) { message.error(shiftMessage); return; } //时间改变-------------------------------------- const len = shiftRuleList.length; let ret = false; shiftRuleList.forEach((val1, i) => { const preStart = shiftRuleList[i]['startWorkTime'].hour() * 60 + shiftRuleList[i]['startWorkTime'].minute(); const preEnd = shiftRuleList[i]['endWorkTime'].hour() * 60 + shiftRuleList[i]['endWorkTime'].minute(); //设置为次日 注:只能是最后一轮的下班时间才能是次日 if (i === len - 1 && preStart > preEnd) { //总时间不能大于24小时要求最后一轮的结束时间不能大作第一轮的开始时间 const times = this.computeTime(); if (!times.length) { return null; } const allminute = times.reduce((a, b) => a + b); const tatalHour = allminute / 60; if (tatalHour > 24) { message.error('总时间需控制在24小时内,请重新选择。'); ret = true; } else { shiftRuleList[i]['isEndNextDay'] = '1'; } } //设置为当日 if (i === len - 1 && preStart < preEnd) { shiftRuleList[i]['isEndNextDay'] = '0'; } if (len === 1 && preStart === preEnd) { message.error('上下班时间不能一样'); ret = true; } //处理大于两个班次的 if (len === 1 || i >= len - 1) { return true; } const nextStart = shiftRuleList[i + 1]['startWorkTime'].hour() * 60 + shiftRuleList[i + 1]['startWorkTime'].minute(); //如果不是最后一轮开始时间不能大于结束时间 if (preStart >= preEnd) { message.error('只有最后一轮才能选择次日的时间,请重新选择。'); ret = true; } //前一轮的下班时间要小于后一轮的上班时间 if (preEnd >= nextStart && i < len - 2) { message.error('上一班次的下班时间要小于下一班次的上班时间'); ret = true; } //设置班次每轮的上班时间时,除了现有的判断条件外,需要在选择时间时,判断并筛选小时的显示:下一轮的上班时间小时,需大于等于上一轮的上班时间小时。即:第一轮为9:00上班,第二轮只能选择9及之后的小时数。 if((preStart > nextStart&&preStart < preEnd)||(preStart > nextStart&&(preEnd < nextStart || i >= len - 2))){//根据之前其他人开发的上述条件筛选,防止多次提示message message.error('下一轮的上班时间小时,需大于等于上一轮的上班时间小时。'); ret = true; } // 总时长不能大于24小时 const startTime = shiftRuleList[0]['startWorkTime'].hour() * 60 + shiftRuleList[0]['startWorkTime'].minute(); const endTime = shiftRuleList[shiftRuleList.length - 1]['endWorkTime'].hour() * 60 + shiftRuleList[shiftRuleList.length - 1]['endWorkTime'].minute(); if (startTime <= endTime && shiftRuleList[shiftRuleList.length - 1]['isEndNextDay'] === '1') { message.error('总时长需要小于24小时!'); ret = true; } }); if (ret) { return; } //附加设置-------------------------------------------------------- const times = this.computeTime(); const totalTimes = this.computeTotalTime().reduce((a, b) => a + b); if (totalTimes / 60 > 24) { return false; } const minTime = Math.min.apply(null, times); if ( (!_.isInteger(absentLow) && absentSwitch) || (!_.isInteger(clockWorkLimit) && clockLimitSwitch) || (!_.isInteger(permitLateUp) && permitLateSwitch) ) { message.error('允许迟到、分钟只能是正整数'); return; } if ( absentLow <= permitLateUp && absentSwitch === '1' && permitLateSwitch === '1' ) { message.error('允许旷工时间需大于允许迟到时间,请重新输入'); return; } if ( clockWorkLimit >= minTime || absentLow >= minTime || permitLateUp >= minTime ) { message.error( '打卡时限、旷工、迟到时间不得超过每轮班次的间隔时间,请重新输入' ); return; } //转换时间格式 const newshiftRuleList = shiftRuleList.map(val => { const obj = {}; obj['isStartNextDay'] = val['isStartNextDay']; obj['isEndNextDay'] = val['isEndNextDay']; const endhour = val['endWorkTime'].hour(); const starthour = val['startWorkTime'].hour(); const ends = val['endWorkTime']['_i'].split(':'); const starts = val['startWorkTime']['_i'].split(':'); obj['endWorkTime'] = endhour < 10 ? `0${endhour}:${val['endWorkTime']['_i'].split(':')[1]}` : `${ends[0]}:${ends[1]}`; obj['startWorkTime'] = starthour < 10 ? `0${starthour}:${val['startWorkTime']['_i'].split(':')[1]}` : `${starts[0]}:${starts[1]}`; return obj; }); const obj = { shiftId, shiftType, shiftName, commutTimes: shiftRuleList.length, absentLow, absentSwitch, clockWorkLimit, clockLimitSwitch, permitLateUp, permitLateSwitch, shiftRuleJson: JSON.stringify(newshiftRuleList) }; if (!err) { if (shiftId) { //编缉 confirm({ title: '选择班次生效时间', content: '若选择“立即生效”,今天相关的内勤组记录会重新核算', okText: '立即生效', onOk: () => { obj.effectRule = '1'; this.taskComShiftUpdate(obj); }, cancelText: '明日生效', onCancel: () => { obj.effectRule = '2'; this.taskComShiftUpdate(obj); } }); } else { //编缉更新 this.taskComShiftInsert(obj); } } }); }; //迟到单选框 lateCheckChange = (filed, filed1, e) => { console.log(filed, filed1, e.target.checked, ' e.target.checked'); const { formData } = this.state; if (!e.target.checked) { formData[filed1] = 0; } formData[filed] = e.target.checked ? '1' : '0'; this.setState({ formData }); }; //附加设置 inputChange = (file, val) => { const { formData } = this.state; formData[file] = val; this.setState({ formData }); }; /******************************render******************************/ renderTable = () => { //table 编辑 const tableEditor = record => { const { formData } = this.state; formData['shiftId'] = record.shiftId; this.setState({ open3: true, formData }); this.taskComShiftGet(record.shiftId); }; const columns = [ { title: '班次名称', dataIndex: 'shiftName', key: '1', width: 200 }, { title: '班次类型', key: '2', dataIndex: 'shiftType', render: (text, record) => { return (
{record.shiftType === '1' && '考勤班次'} {record.shiftType === '2' && '任务班次'}
); }, width: 100 }, { title: '考勤时间安排', dataIndex: 'shiftRuleTime', key: '3', render: (text, record) => { return (
); } }, { title: '操作', dataIndex: 'd', key: '4', width: 150, render: (text, record) => { return (
编辑 { confirm({ content: (
删除的班次不可恢复!确认删除" {record.shiftName} "
), okText: '删除', onOk: () => { this.taskComShiftDelete(record.shiftId, record.shiftType); }, cancelText: '取消', onCancel() { console.log('Cancel'); } }); }} > 删除
); } } ]; return ( ); }; computeTime = () => { const { formData } = this.state; const { shiftRuleList } = formData; const times = []; shiftRuleList.forEach(val => { const { endWorkTime, startWorkTime } = val; const sartHour = startWorkTime.hour(); const endHour = endWorkTime.hour(); const startMinute = startWorkTime.minute(); const endMinute = endWorkTime.minute(); if ( sartHour < endHour || (sartHour === endHour && startMinute < endMinute) ) { times.push((endHour - sartHour) * 60 + endMinute - startMinute); } else { times.push((24 - sartHour + endHour) * 60 + endMinute - startMinute); } }); return times; }; computeTotalTime = () => { const { formData } = this.state; const { shiftRuleList } = formData; const totalTimes = []; for (let i = 0; i < shiftRuleList.length; i++) { const { endWorkTime, startWorkTime } = shiftRuleList[i]; const sartHour = startWorkTime.hour(); const endHour = endWorkTime.hour(); const startMinute = startWorkTime.minute(); const endMinute = endWorkTime.minute(); if ( sartHour < endHour || (sartHour === endHour && startMinute < endMinute) ) { totalTimes.push((endHour - sartHour) * 60 + endMinute - startMinute); } else { totalTimes.push( (24 - sartHour + endHour) * 60 + endMinute - startMinute ); } if (i < shiftRuleList.length - 1) { totalTimes.push( (shiftRuleList[i + 1].startWorkTime.hour() - endHour) * 60 + shiftRuleList[i + 1].startWorkTime.minute() - endMinute ); } } return totalTimes; }; //选择时间的时候 timeChange = (time, i, file) => { const { formData } = this.state; const shiftRuleList = formData.shiftRuleList.map(val => { const obj = {}; obj.startWorkTime = val.startWorkTime; obj.endWorkTime = val.endWorkTime; obj.isStartNextDay = val.isStartNextDay; obj.isEndNextDay = val.isEndNextDay; return obj; }); shiftRuleList[i][file] = moment(time, format); formData['shiftRuleList'] = shiftRuleList; this.setState({ formData }); //设置为次日 注:只能是最后一轮的下班时间才能是次日 const len = shiftRuleList.length; const start = shiftRuleList[i]['startWorkTime'].hour() * 60 + shiftRuleList[i]['startWorkTime'].minute(); const end = shiftRuleList[i]['endWorkTime'].hour() * 60 + shiftRuleList[i]['endWorkTime'].minute(); //设置为次日1 if (i === len - 1 && start > end) { shiftRuleList[i]['isEndNextDay'] = '1'; } //设置为当日0 if (i === len - 1 && start < end) { shiftRuleList[i]['isEndNextDay'] = '0'; } let totalTime = 0; if (shiftRuleList[shiftRuleList.length - 1]['isEndNextDay'] === '0') { totalTime = shiftRuleList[shiftRuleList.length - 1].endWorkTime.hour() - shiftRuleList[0].startWorkTime.hour() + (shiftRuleList[shiftRuleList.length - 1].endWorkTime.minute() - shiftRuleList[0].startWorkTime.minute()) / 60; } else { totalTime = shiftRuleList[shiftRuleList.length - 1].endWorkTime.hour() + 24 - shiftRuleList[0].startWorkTime.hour() + (shiftRuleList[shiftRuleList.length - 1].endWorkTime.minute() - shiftRuleList[0].startWorkTime.minute()) / 60; } this.setState({ totalTime }); }; render() { const { getFieldDecorator } = this.props.form; const formData = { ...this.state.formData }; const { shiftId, shiftName, //班次名称 commutTimes, //每天上下班次数 // absentLow, //旷工时间下限 // absentSwitch, //旷工校验开关 // clockWorkLimit, //严重迟到时间下限 // clockLimitSwitch, //严重迟到校验开关 permitLateUp, //允许迟到时间上限 permitLateSwitch //允许迟到校验开关 } = this.state.formData; const { shiftRuleList } = this.state.formData; if(!this.props.modalVisble) { return (
{/*
*/} {this.renderTable()} {/* 选择班次--新增班次 */} { this.setState({ open3: false }); }} zIndex={11} className="CreateThiftManagement" >
{getFieldDecorator('shiftName', { rules: [ { required: true, message: '请输入' }, { max: 15, message: '限制15个字' } ], initialValue: shiftName || null })( { formData['shiftName'] = e.target.value; this.setState({ formData }); }} /> )} {getFieldDecorator('commutTimes', { rules: [{ required: true, message: '请输入' }], initialValue: commutTimes || null })( { let val = num; const { setFieldsValue } = this.props.form; const shiftArr = []; if (val > 5) { val = 5; } if (val <= 0 || val === '') { val = 1; window.setTimeout(() => setFieldsValue({ commutTimes: 1 }) ); } if (!_.isInteger(val)) { val = 1; } for (let i = 0; i < val; i++) { const startWorkTime = 8 + (i * 4 - 1); let endWorkTime = startWorkTime + 3; if (endWorkTime > 24) { endWorkTime -= 24; shiftArr.push({ isEndNextDay: '1', isStartNextDay: '0', startWorkTime: moment( `${startWorkTime}:00`, format ), endWorkTime: moment( `${endWorkTime}:00`, format ) }); } else { shiftArr.push({ isEndNextDay: '0', isStartNextDay: '0', startWorkTime: moment( `${startWorkTime}:00`, format ), endWorkTime: moment( `${endWorkTime}:00`, format ) }); } } const newformData = { ...formData }; newformData.commutTimes = val; newformData.shiftRuleList = shiftArr; this.setState({ formData: newformData }); }} max={5} min={1} step={1} addonAfter="次" /> )} {shiftRuleList.map((val, i) => { return (
第{i + 1} 轮班次:
test
test
{ this.timeChange(time, i, 'startWorkTime'); }} className="task-TimePicker" format={format} /> { this.timeChange(time, i, 'endWorkTime'); }} className="task-TimePicker" format={format} /> {shiftRuleList[i]['isEndNextDay'] === '1' ? ( 次日 ) : null}
); })} {(() => { const times = this.computeTime(); if (!times.length) { return null; } const allminute = times.reduce((a, b) => a + b); const hour = parseInt(allminute / 60, 10); const minute = allminute % 60; if (allminute / 60 > 24) { return (
总时长不得大于24小时
); } else { return (
合计工作时长 {hour} 小时 {minute} 分钟
); } })()}
{ this.lateCheckChange( 'permitLateSwitch', 'permitLateUp', val ); }} name="permitLateSwitch" > 允许迟到 { this.inputChange('permitLateUp', val); }} /> 分钟 {/* { this.lateCheckChange( 'absentSwitch', 'absentLow', val ); }} name="absentSwitch" > 迟到超过 { this.inputChange('absentLow', val); }} /> 分钟 (视为旷工) */} {/* { this.lateCheckChange( 'clockLimitSwitch', 'clockWorkLimit', val ); }} name="clockLimitSwitch" > 打卡时限 { if (val === '' || val < 0) { val = 0; } this.inputChange('clockWorkLimit', val); }} /> 分钟 (上班前和下班后的打卡时间限制,超过视为漏打卡) */}
{ this.setState({ visible: false }); }} onCancel={() => { this.setState({ visible: false }); }} wrapClassName="thiftModal" > 若选择“立即生效”,今天相关的任务记录会重新核算!
); }else { return ( { this.props.onClose && this.props.onClose(); }} style={this.props.style} // zIndex={11} className="CreateThiftManagement" >
{getFieldDecorator('shiftName', { rules: [ { required: true, message: '请输入' }, { max: 15, message: '限制15个字' } ], initialValue: shiftName || null })( { formData['shiftName'] = e.target.value; this.setState({ formData }); }} /> )} {getFieldDecorator('commutTimes', { rules: [{ required: true, message: '请输入' }], initialValue: commutTimes || null })( { let val = num; const { setFieldsValue } = this.props.form; const shiftArr = []; if (val > 5) { val = 5; } if (val <= 0 || val === '') { val = 1; window.setTimeout(() => setFieldsValue({ commutTimes: 1 }) ); } if (!_.isInteger(val)) { val = 1; } for (let i = 0; i < val; i++) { const startWorkTime = 8 + (i * 4 - 1); let endWorkTime = startWorkTime + 3; if (endWorkTime > 24) { endWorkTime -= 24; shiftArr.push({ isEndNextDay: '1', isStartNextDay: '0', startWorkTime: moment( `${startWorkTime}:00`, format ), endWorkTime: moment( `${endWorkTime}:00`, format ) }); } else { shiftArr.push({ isEndNextDay: '0', isStartNextDay: '0', startWorkTime: moment( `${startWorkTime}:00`, format ), endWorkTime: moment( `${endWorkTime}:00`, format ) }); } } const newformData = { ...formData }; newformData.commutTimes = val; newformData.shiftRuleList = shiftArr; this.setState({ formData: newformData }); }} max={5} min={1} step={1} addonAfter="次" /> )} {shiftRuleList.map((val, i) => { return (
第{i + 1} 轮班次:
test
test
{ this.timeChange(time, i, 'startWorkTime'); }} className="task-TimePicker" format={format} /> { this.timeChange(time, i, 'endWorkTime'); }} className="task-TimePicker" format={format} /> {shiftRuleList[i]['isEndNextDay'] === '1' ? ( 次日 ) : null}
); })} {(() => { const times = this.computeTime(); if (!times.length) { return null; } const allminute = times.reduce((a, b) => a + b); const hour = parseInt(allminute / 60, 10); const minute = allminute % 60; if (allminute / 60 > 24) { return (
总时长不得大于24小时
); } else { return (
合计工作时长 {hour} 小时 {minute} 分钟
); } })()}
{ this.lateCheckChange( 'permitLateSwitch', 'permitLateUp', val ); }} name="permitLateSwitch" > 允许迟到 { this.inputChange('permitLateUp', val); }} /> 分钟
) } } }