flx:提交新施工日志模块 修复bug

This commit is contained in:
Rain_ 2025-07-30 17:19:46 +08:00
parent 9407bcbf24
commit 0d5ad3f4bd
12 changed files with 1961 additions and 31 deletions

Binary file not shown.

After

Width:  |  Height:  |  Size: 886 B

View File

@ -1,7 +1,7 @@
/**
* api接口统一管理 施工日志
*/
import {post,get} from '../http'
import { post, get } from '../http'
export const addBuildersDiaryApi = data => post('xmgl/projectBuildLog/add', data); //新增 施工日志
export const editBuildersDiaryApi = data => post('xmgl/projectBuildLog/edit', data); // 编辑 施工日志
@ -10,3 +10,16 @@ export const deleteBuildersDiaryApi = data => post('xmgl/projectBuildLog/delete'
//施工列表
export const getListDataApi = data => post('xmgl/projectBuildLog/list', data); //获取 施工日志 列表
// 全部施工日志
// 分页列表查询ocr施工日志信息
export const getOcrBuildLogPageApi = data => get('xmgl/ocrBuildLog/page', data);
// 列表查询ocr施工日志信息
export const getOcrBuildLogListApi = data => get('xmgl/ocrBuildLog/list', data);
// 添加ocr施工日志信息
export const addOcrBuildLogApi = data => post('xmgl/ocrBuildLog/add', data);
// 编辑ocr施工日志信息
export const editOcrBuildLogApi = data => post('xmgl/ocrBuildLog/edit', data);
// 删除ocr施工日志信息
export const deleteOcrBuildLogApi = data => post('xmgl/ocrBuildLog/delete', data);
// 统计某月每天的ocr施工日志
export const getOcrBuildLogCountOcrBuildLogForMonthApi = data => post('xmgl/ocrBuildLog/countOcrBuildLogForMonth', data);

View File

@ -206,6 +206,7 @@ if (process.env.NODE_ENV == "development") {
// axios.defaults.baseURL = "https://zm.zhgdyun.com:11111";
// // axios.defaults.baseURL = "http://121.37.106.37:9809";
// axios.defaults.baseURL = "http://139.9.66.234:20628";
// axios.defaults.baseURL = "http://jxj.zhgdyun.com:9500";
} else if (process.env.NODE_ENV == "debug") {
axios.defaults.baseURL = "https://www.ceshi.com";

View File

@ -1984,6 +1984,12 @@ const routes2 = [{
component: () =>
import ("@/views/projectFront/buildersDiary/diaryList.vue"),
},
{
path: "/project/buildersDiary/buildersDiaryAll",
name: "施工日志_全部施工日志",
component: () =>
import ("@/views/projectFront/buildersDiary/buildersDiaryAll.vue"),
},
{
path: "/project/qualitySpringback/buildManage",
name: "质量回弹_楼栋管理",

View File

@ -102,6 +102,7 @@ export default new Vuex.Store({
// // WORKFLOWURL: 'http://47.93.215.234:19098/#/workspace/forms',//鞍钢测试平台工作流地址(弃用)
// WORKFLOWURL: 'http://42.180.188.17:19998/#/workspace/forms', //鞍钢平台工作流地址
// WORKFLOWURL: "http://42.180.188.17:19098/#/workspace/forms", //鞍钢测试平台工作流地址
PREVIEWURL: "http://219.147.96.221:8012/onlinePreview",
// UPLOADURL: 'http://192.168.34.221:8111/upload/image', //演示平台 雄本地
// FILEURL: 'http://192.168.34.221:8111/image/', //演示平台 雄本地

View File

@ -28,7 +28,9 @@ import {
selectAllProjectInfoList,
getRangeAddrByUserIdCompanyBigScreenApi,
} from "@/assets/js/api/companyBigScreen.js";
import {
getSystemUserBySnApi
} from "@/assets/js/api/account.js";
//
const mapObj = ref(null);
const projectSn = ref("");
@ -92,6 +94,7 @@ const addMarker = (maskPolygon) => {
console.log("点击了坐标点", data);
marker.value = marker;
mapObj.value.setCenter([e.lnglat.getLng(), e.lnglat.getLat()]);
getSystemUserBySn(data.projectSn);
});
}
});
@ -149,7 +152,8 @@ const getRangeAddrByUserIdCompanyBigScreen = () => {
}
return prev;
}, []);
loadMapScript().then(() => {
loadMapScript()
.then(() => {
showProvinceMask(resultList);
})
.catch((err) => {
@ -159,6 +163,24 @@ const getRangeAddrByUserIdCompanyBigScreen = () => {
}
});
};
const getSystemUserBySn = (projectSn) => {
let data = {
sn: projectSn,
queryType:"projectLevel"
};
getSystemUserBySnApi(data).then((res) => {
if (res.code == 200) {
if(res.result && res.result.length > 0) {
const result = res.result[0];
let userId = result.userId;
window.open(`${window.location.protocol}//${window.location.host}/bigscreen/#/large?userId=${userId}&sn=$${projectSn}`, '_blank')
} else {
ElMessage.error("没有权限!");
return;
}
}
});
};
//
onMounted(() => {

View File

@ -50,7 +50,7 @@
<div>低风险0</div>
</div> -->
</div>
<div class="box5">
<div class="box5" v-if="isDrawingMode">
<div class="header_title">操作</div>
<el-radio-group
@change="onToolChange"
@ -211,7 +211,9 @@
<script>
import { fabric } from "fabric";
import "./index.scss";
fabric.Object.prototype.set({
hasRotatingPoint: false, //
});
const TOOLS = [
{ name: "铅笔", type: "pencil", icon: "icon-pan_icon" },
{ name: "实线", type: "line", icon: "icon-xian" },
@ -242,6 +244,10 @@ export default {
placement: { type: String, default: "left" },
configJson: { type: String, default: () => "" },
zonePlaceInfoId: { type: String, default: () => "" },
isDrawingMode: {
type: Boolean,
default: true,
},
},
data() {
return {
@ -276,7 +282,7 @@ export default {
// http://192.168.34.133:8081/img/datacentre_icon2.d1e40835.png
drawer: true,
riskColorInfo: {
radio1: "rect",
radio1: "move",
position: "",
fontSize: "",
@ -492,7 +498,8 @@ export default {
},
initCanvas() {
this.boardObj = new fabric.Canvas(this.$refs.myCanvas, {
isDrawingMode: true,
isDrawingMode: this.isDrawingMode,
// isDrawingMode: true,
selectable: true,
selection: true,
devicePixelRatio: true,
@ -533,7 +540,7 @@ export default {
}
);
}
this.changeTool("rect");
this.changeTool("move");
},
//
updateFillAndStrokeEcho() {
@ -967,6 +974,15 @@ export default {
return this.boardObj;
},
},
computed: {
newWatch() {
const { configJson, zonePlaceInfoId } = this;
return {
configJson,
zonePlaceInfoId,
};
},
},
watch: {
strokeColor(newVal) {
if (this.boardObj) this.boardObj.freeDrawingBrush.color = newVal;
@ -974,10 +990,35 @@ export default {
strokeWidth(newVal) {
if (this.boardObj) this.boardObj.freeDrawingBrush.width = newVal;
},
zonePlaceInfoId(newVal) {
if (newVal) {
newWatch: {
handler(newVal) {
console.log(2222222, newVal)
this.removeEvent();
if (this.boardObj) {
this.boardObj.dispose();
this.boardObj = null;
}
this.initCanvas();
this.initEvent();
},
deep: true,
},
isDrawingMode(newVal) {
console.log(2222222222222, newVal);
if (this.boardObj) {
this.riskColorInfo.radio1 = "move";
this.boardObj.isDrawingMode = newVal;
if (!newVal) {
this.removeEvent();
if (this.boardObj) {
this.boardObj.dispose();
this.boardObj = null;
}
this.initCanvas();
this.initEvent();
} else {
this.changeTool("move");
}
}
},
},
@ -1327,8 +1368,9 @@ export default {
.board-box {
// position: relative;
background: white;
width: 567px;
// width: 567px;
height: calc(100% - 68px - 68px);
width: 375px;
position: absolute;
top: 50%;
left: 50%;

View File

@ -99,6 +99,10 @@
>
<div>{{ item.zoneName }}</div>
<div>
<img
@click="isDrawingModeClick()"
src="@/assets/images/icon-paint.png"
/>
<img
@click="dealAdd(5, item)"
src="@/assets/images/icon-edit.png"
@ -112,8 +116,8 @@
</ul>
</div>
<div class="content-box1">
<div class="content-box1-top">
<el-button size="medium" icon="el-icon-circle-close"> </el-button>
<div class="content-box1-top" v-if="isDrawingMode">
<el-button size="medium" @click="clearFabric" icon="el-icon-circle-close"> </el-button>
<el-button
@click="saveFabric"
type="primary"
@ -125,6 +129,7 @@
<MyPictode
class="mypictode"
ref="canvasfabric"
:isDrawingMode="isDrawingMode"
:canvasWidth="width"
:canvasHeight="height"
:zonePlaceInfoId="zonePlaceInfo.id"
@ -289,7 +294,7 @@ import {
} from "@/assets/js/api/equipmentCenter/cameraList";
// import MyFabric from "./components/myfabric.vue";
import MyPictode from "./components/myPictode.vue";
import { isJSON } from '@/util/nowDate';
import { isJSON } from "@/util/nowDate";
export default {
components: {
// MyFabric,
@ -392,6 +397,7 @@ export default {
id: "",
configJson: "",
},
isDrawingMode:false,
};
},
created() {
@ -401,12 +407,18 @@ export default {
},
mounted() {},
methods: {
isDrawingModeClick(){
this.isDrawingMode = true;
},
clearFabric(){
this.isDrawingMode = false;
},
saveFabric() {
const boardObjRef = this.$refs.canvasfabric.boardObjRef();
// JSON
// JSON
const configJson = boardObjRef.toJSON();
// JSON 便
console.log('画布内容转换后的 JSON 数据:', configJson);
console.log("画布内容转换后的 JSON 数据:", configJson);
let params = {
...this.zonePlaceInfo,
configJson: JSON.stringify(configJson),
@ -415,6 +427,7 @@ export default {
if (result.success) {
this.$message.success(result.message);
this.refreshOcrZonePlace();
this.isDrawingMode = false;
}
});
},
@ -445,7 +458,10 @@ export default {
this.ocrZonePlaceList = res.result.records;
this.ocrZonePlaceInfo.total = res.result.total;
if (!this.zonePlaceInfo.id && this.ocrZonePlaceList.length > 0) {
this.selectZonePlace(this.ocrZonePlaceList[0])
this.selectZonePlace(this.ocrZonePlaceList[0]);
} else {
const find = this.ocrZonePlaceList.find(item => item.id === this.zonePlaceInfo.id)
if(find) this.selectZonePlace(find);
}
}
});

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,327 @@
<template>
<div class="calendar">
<!-- <div class="calendar-header">
<button @click="prevMonth">&lt;</button>
<h2>{{ currentYear }} {{ currentMonth + 1 }} </h2>
<button @click="nextMonth">&gt;</button>
</div> -->
<div class="calendar-weekdays">
<span v-for="day in weekdays" :key="day">{{ day }}</span>
</div>
<div class="calendar-days">
<div
v-for="day in daysInMonth"
:key="day.date"
class="calendar-day"
@click="selectDate(day.date)"
:class="day.id || day.num ? 'calendar-day2' : 'calendar-day1'"
>
<div class="calendar-day_header">
<div
class="calendar-text"
:class="{
'other-month': day.isOtherMonth,
'current-day': day.isCurrentDay || day.id || day.num,
}"
>
{{ day.day }}
</div>
<div
class="calendar-box1"
:class="day.id || day.num ? 'bg-color88' : 'bg-colord0'"
>
{{ day.id || day.num ? "已填写" : "未填写" }}
</div>
</div>
<div class="calendar-day_box1" v-if="defaultType == 2 && dateTimeUp(day.date)" @click="addView(day)">
<i class="el-icon-edit"></i>
去填写
</div>
<div class="calendar-day_box2" :class="{'box2-center': defaultType == 2}" @click="examineCalendarView(day)">
<div class="view-box1" v-if="defaultType == 1">共有{{day.num}}条记录</div>
<div class="view-box">
<i class="el-icon-view"></i>
查看详情
</div>
</div>
</div>
</div>
</div>
</template>
<script>
import dayjs from "dayjs";
export default {
name: "CalendarView",
props: {
defaultMonth: { type: String, default: () => dayjs().format("YYYY-MM") },
ocrBuildLogAllList: { type: Array, default: () => [] },
type: { type: Number, default: () => 1 },
},
data() {
return {
currentDate: this.defaultMonth,
weekdays: ["日", "一", "二", "三", "四", "五", "六"],
dataList: [],
defaultType: 1,
};
},
computed: {
dateTimeUp() {
return (dateTime) => {
return dayjs(dateTime).isBefore(dayjs());
};
},
currentYear() {
return dayjs(this.currentDate).year();
},
currentMonth() {
return dayjs(this.currentDate).month();
},
daysInMonth() {
console.log(22222222222, this.currentDate);
const currentDayjs = dayjs(this.currentDate);
const startOfMonth = currentDayjs.startOf("month");
const endOfMonth = currentDayjs.endOf("month");
const startDay = startOfMonth.day();
const endDay = endOfMonth.day();
//
const prevMonthDays = [];
for (let i = startDay - 1; i >= 0; i--) {
const date = startOfMonth.subtract(startDay - i, "day");
// console.log(date.date(),date.format('YYYY-MM-DD'));
prevMonthDays.unshift({
day: date.date(),
date: date.format("YYYY-MM-DD"),
isOtherMonth: true,
isCurrentDay: false,
});
}
//
const currentMonthDays = [];
for (let i = 0; i < endOfMonth.date(); i++) {
const date = startOfMonth.add(i, "day");
currentMonthDays.push({
day: date.date(),
date: date.format("YYYY-MM-DD"),
isOtherMonth: false,
isCurrentDay: date.isSame(dayjs(), "day"),
});
}
//
const nextMonthDays = [];
for (let i = 1; i <= 6 - endDay; i++) {
const date = endOfMonth.add(i, "day");
nextMonthDays.push({
day: date.date(),
date: date.format("YYYY-MM-DD"),
isOtherMonth: true,
isCurrentDay: false,
});
}
const resultList = [
...prevMonthDays,
...currentMonthDays,
...nextMonthDays,
];
return resultList.map((item) => {
const find = this.dataList.find((ele) => dayjs(ele.date).format("YYYY-MM-DD") == item.date);
if (find) {
return {
...item,
...find,
};
}
return {
...item,
};
});
},
},
methods: {
prevMonth() {
this.currentDate = this.currentDate.subtract(1, "month");
},
nextMonth() {
this.currentDate = this.currentDate.add(1, "month");
},
currentDay() {
this.currentDate = dayjs(this.defaultMonth).format("YYYY-MM");
},
selectDate(date) {
this.$emit("date-selected", date);
},
addView(row) {
this.$emit("addView", row);
},
examineCalendarView(row) {
this.$emit("examineCalendarView", row);
},
},
watch: {
defaultMonth: {
// immediate: true,
handler(newVal) {
console.log(1111111, newVal);
this.currentDay();
},
},
type: {
handler(newVal) {
this.defaultType = newVal;
},
deep: true,
immediate: true,
},
ocrBuildLogAllList: {
handler(newVal) {
this.dataList = newVal;
},
deep: true,
immediate: true,
},
},
};
</script>
<style lang="less" scoped>
.calendar {
width: 100%;
border: 1px solid #ebebeb;
}
.calendar-header {
display: flex;
justify-content: space-between;
align-items: center;
margin-bottom: 10px;
}
.calendar-weekdays {
display: flex;
justify-content: space-around;
// margin-bottom: 10px;
background: #fafafa;
> span {
flex: 1;
height: 55px;
font-size: 16px;
color: #4d4d4d;
border: 1px solid #ebebeb;
display: flex;
align-items: center;
justify-content: center;
}
}
.calendar-days {
display: grid;
grid-template-columns: repeat(7, 1fr);
gap: 0px;
height: 620px;
grid-auto-rows: auto;
}
.calendar-day2:hover .calendar-day_box2 {
display: flex;
}
.calendar-day1:hover .calendar-day_box1 {
display: flex;
}
.calendar-day:hover {
background-color: #f2f8ff;
}
.calendar-day {
cursor: pointer;
// height: 122px;
border: 1px solid #ebebeb;
position: relative;
.calendar-day_box2 {
width: calc(100% - 40px);
height: 50%;
font-size: 14px;
background-color: #e6f1fe;
position: absolute;
left: 50%;
bottom: 0;
transform: translateX(-50%);
// display: flex;
align-items: center;
justify-content: space-between;
padding: 0 20px;
display: none;
.view-box1 {
color: #1A1A1A;
}
.view-box {
display: flex;
align-items: center;
justify-content: center;
color: #4181fe;
i {
margin-right: 5px;
font-size: 15px;
}
}
}
.box2-center {
justify-content: center;
}
.calendar-day_box1 {
width: calc(84px - 20px);
padding: 8px 10px;
background: #4181fe;
border-radius: 3px;
display: flex;
align-items: center;
justify-content: center;
font-size: 14px;
color: #ffffff;
position: absolute;
left: 50%;
top: 50%;
transform: translate(-50%, -50%);
display: none;
i {
margin-right: 5px;
font-size: 16px;
}
}
.calendar-day_header {
display: flex;
align-items: center;
justify-content: space-between;
padding: 5px 10px 5px 5px;
.calendar-box1 {
padding: 2px 6px;
border-radius: 132px;
font-size: 14px;
color: #ffffff;
}
.bg-color88 {
background-color: #88cf65;
}
.bg-colord0 {
background-color: #d00000;
}
.calendar-text {
font-size: 14px;
color: #4d4d4d;
width: 36px;
padding: 10px 0;
text-align: center;
}
.other-month {
color: #b3b3b3;
}
.current-day {
background-color: #4181fe;
color: white;
border-radius: 50%;
}
}
}
</style>

View File

@ -0,0 +1,175 @@
<template>
<div class="ledger">
<el-table
height="calc(100% - 64px)"
max-height="calc(100% - 64px)"
class="tables"
:data="dataList"
>
<el-table-column
type="selection"
width="55"
align="center"
></el-table-column>
<el-table-column
prop="date"
align="center"
label="日志日期"
show-overflow-tooltip
></el-table-column>
<el-table-column
v-if="type == 1"
prop="uploaderName"
align="center"
label="上传人"
show-overflow-tooltip
></el-table-column>
<el-table-column
prop="weatherJson"
align="center"
label="天气"
show-overflow-tooltip
>
<template slot-scope="scope">
<span v-if="scope.row.weatherJson">
风力{{ scope.row.weatherJson.win_speed }}&nbsp; 气温{{
scope.row.weatherJson.tem_day
}}&nbsp; 天气{{ scope.row.weatherJson.wea }}
</span>
</template>
</el-table-column>
<!-- <el-table-column
prop="weatherJson"
align="center"
label="岗位"
show-overflow-tooltip
></el-table-column> -->
<el-table-column
prop="constructionAreaNames"
align="center"
label="施工区域"
show-overflow-tooltip
></el-table-column>
<el-table-column
prop="attendance"
align="center"
label="出勤情况"
show-overflow-tooltip
></el-table-column>
<el-table-column
prop="constructionTask"
align="center"
label="施工任务"
show-overflow-tooltip
></el-table-column>
<el-table-column
prop="constructionUnitNames"
align="center"
label="施工单位"
show-overflow-tooltip
></el-table-column>
<el-table-column
prop="constructionWorkerNames"
align="center"
label="施工人员"
show-overflow-tooltip
></el-table-column>
<el-table-column label="操作" width="240" align="center">
<template slot-scope="scope">
<div class="tableBtns">
<div @click="examineView(scope.row)" class="operationText">
<i class="el-icon-view"></i>
<span>查看</span>
</div>
<div @click="editView(scope.row)" class="operationText">
<img
src="@/assets/images/icon-edit.png"
width="15px"
height="15px"
/>
<span>{{ $t("message.deviceManage.edit") }}</span>
</div>
<div @click="deleteView(scope.row)" class="operationText">
<img
src="@/assets/images/icon-delete.png"
width="15px"
height="15px"
/>
<span>{{ $t("message.deviceManage.delete") }}</span>
</div>
</div>
</template>
</el-table-column>
</el-table>
<pagination
:total="Number(pageInfo.total)"
:page.sync="pageInfo.pageNo"
:limit.sync="pageInfo.pageSize"
@pagination="getList"
layout="total, prev, pager, next, jumper"
/>
</div>
</template>
<script>
export default {
name: "LedgerView",
props: {
type: { type: Number, default: () => 1 },
ocrBuildLogList: { type: Array, default: () => [] },
pageInfo: {
type: Object,
default: () => ({
pageNo: 1,
pageSize: 10,
total: 0,
}),
},
},
data() {
return {
dataList: [],
};
},
computed: {},
methods: {
getList() {},
examineView(row) {
this.$emit("examineView", row);
},
editView(row) {
this.$emit("editView", row);
},
deleteView(row) {
this.$emit("deleteView", row);
},
},
watch: {
ocrBuildLogList: {
handler(newVal) {
this.dataList = newVal;
},
deep: true,
immediate: true,
},
},
};
</script>
<style lang="less" scoped>
.el-icon-view {
color: #5181f6;
font-size: 15px;
margin-right: 5px;
}
.ledger {
height: 100%;
}
.tables {
min-height: initial;
}
/deep/ .pagination-container {
padding: 16px;
}
</style>

View File

@ -355,7 +355,7 @@
</el-steps>
<el-form
v-if="stepActive == 0"
ref="workTicketForm"
ref="workTicketFormRef"
:model="workTicketForm"
:rules="workTicketRules"
label-width="130px"
@ -634,7 +634,7 @@
</div>
<div>
<i class="el-icon-warning-outline"></i>
<div>点击立即开始则会下发指令到作业监控设备开启设备录像</div>
<div>点击立即开始将会下发工单任务至执法记录仪设备中施工员需要到设备的工单任务中点击开始执行工单任务进行录音录像拍照</div>
</div>
</div>
</div>
@ -660,7 +660,7 @@
icon="el-icon-circle-check"
@click="onNextStep"
size="medium"
>确定
>{{ workTicketType == 1 ? "确定" : stepActive == 1 || workTicketBindCamera == 0 ? "确定" : "下一步" }}</el-button }}
</el-button>
</div>
<div class="dialog-footer" v-else>
@ -868,7 +868,7 @@
<div
@click="onStateShow(3, workTicketDetail.id)"
class="bg-3e"
v-if="workTicketDetail.status == 2"
v-if="workTicketDetail.status == 3"
>
继续作业
</div>
@ -1705,11 +1705,9 @@ export default {
this.$message.success(res.message);
this.initWorkTicketClose();
this.getWorkTicketList();
if (operateStatus == 1) {
this.onExamineClick({
id: this.workTicketId,
});
}
this.onExamineClick({
id: this.workTicketId,
});
}
});
},
@ -1726,9 +1724,10 @@ export default {
initWorkTicketForm() {
this.stepActive = 0;
this.workTicketId = "";
this.selectList = [];
this.workTicketForm = {
typeId: "",
workTicketNumber: "",
workTicketNumber: `GZP${Date.now()}`,
constructionAreas:
this.queryBindRegionList.length > 0
? this.queryBindRegionList.map((item) => item.id)
@ -1800,7 +1799,7 @@ export default {
this.workTicketDialog = true;
this.$nextTick(() => {
this.$refs["workTicketForm"].clearValidate();
this.$refs["workTicketFormRef"].clearValidate();
});
},
//
@ -1809,12 +1808,16 @@ export default {
},
//
async onNextStep() {
console.log(this.stepActive, this.workTicketType);
if (this.workTicketType == 1) {
const valid = await this.$refs["workTicketFormRef"].validate();
if (!valid) return this.$message.warning("请填写必填项!");
this.addWorkTicket(2);
return;
}
if (this.stepActive == 0) {
const valid = await this.$refs["workTicketForm"].validate();
console.log("我进来了");
const valid = await this.$refs["workTicketFormRef"].validate();
if (!valid) return this.$message.warning("请填写必填项!");
if (this.workTicketBindCamera == 0) {
this.submit();
@ -2115,7 +2118,7 @@ export default {
width: 400px;
}
.customConfirm1 .el-message-box__message::after {
content: "点击立即开始作业后,需要到执法记录仪上手动结束工单,结束后录像将会自动上传到平台,可在历史回放中查看";
content: "点击立即开始后,将会下发工单任务至执法记录仪设备中,施工员需要到设备的工单任务中点击开始执行工单任务进行录音、录像、拍照。";
color: #ffa026;
font-size: 12px;
display: inline-block;