Merge branch 'feature/v6.0/6.0.2' into prod
19 files modified
3 files added
| New file |
| | |
| | | import request from '@/axios'; |
| | | // 算法列表 |
| | | export const getAlgorithmManageList = (params) => { |
| | | return request({ |
| | | url: `/drone-device-core/ai/page`, |
| | | method: 'get', |
| | | params: params, |
| | | }) |
| | | }; |
| | | |
| | | export const algorithmManageEdit = data => { |
| | | return request({ |
| | | url: '/drone-device-core/ai/edit', |
| | | method: 'put', |
| | | data: data, |
| | | }); |
| | | }; |
| New file |
| | |
| | | <template> |
| | | <el-dialog class="ztzf-dialog-mange" append-to-body v-model="props.isShowView" :title="props.title" |
| | | :width="props.width" :close-on-click-modal="false" :destroy-on-close="true" @close="cancel"> |
| | | <slot name="default" /> |
| | | <template #footer v-if="props.addEditView !== 'view'"> |
| | | <div class="dialog-footer"> |
| | | <el-button v-if="props.addEditView === 'add'" type="primary" @click="submit" :icon="CirclePlus">保存</el-button> |
| | | <el-button v-else type="primary" @click="submit" :icon="CircleCheck">确认</el-button> |
| | | <el-button @click="cancel" :icon="CircleClose">取消</el-button> |
| | | </div> |
| | | </template> |
| | | </el-dialog> |
| | | </template> |
| | | <script setup> |
| | | import { ElMessage } from 'element-plus' |
| | | import { Delete, Search, CircleCheck, CircleClose, CirclePlus } from '@element-plus/icons-vue' |
| | | import { defineEmits } from 'vue'; |
| | | |
| | | const emit = defineEmits(['cancel', 'confirm']); |
| | | |
| | | const props = defineProps({ |
| | | width: { |
| | | type: String, |
| | | default: '800' |
| | | }, |
| | | isShowView: { |
| | | type: Boolean, |
| | | default: false |
| | | }, |
| | | addEditView: { |
| | | type: String, |
| | | default: 'add' |
| | | }, |
| | | title:{ |
| | | type: String, |
| | | default: '' |
| | | } |
| | | }) |
| | | |
| | | function submit() { |
| | | emit('submit') |
| | | } |
| | | function cancel() { |
| | | emit('cancel') |
| | | } |
| | | </script> |
| | | <style scoped lang="scss"> |
| | | </style> |
| | |
| | | <el-dropdown class="avue-tags__menu"> |
| | | <el-button type="primary" style="background: #409eff;border-color: #409eff"> |
| | | {{ $t('tagsView.menu') }} |
| | | <i class="el-icon-arrow-down el-icon--right"></i> |
| | | <!-- <i class="el-icon-arrow-down el-icon--right"></i> --> |
| | | </el-button> |
| | | <template #dropdown> |
| | | <el-dropdown-menu> |
| | |
| | | @import './variables.scss'; |
| | | @import './base.scss'; |
| | | @import './tool.scss'; |
| | | @import './element-ui.scss'; |
| | | a { |
| | | text-decoration: none; |
| | | color: #333; |
| | |
| | | } |
| | | } |
| | | } |
| | | } |
| | | //======以下针对表格功能 增删查改样式和弹窗========= |
| | | .ztzf-dialog-mange { |
| | | .el-dialog__body { |
| | | padding: 2rem 2rem 4rem; |
| | | flex: 1; |
| | | overflow: scroll; |
| | | border-top: 0.1rem solid #f0f0f0; |
| | | } |
| | | .el-dialog__footer { |
| | | z-index: 2; |
| | | display: block; |
| | | padding: 1rem 1.6rem; |
| | | box-sizing: border-box; |
| | | border-top: 0.1rem solid #f0f0f0; |
| | | width: 100%; |
| | | position: absolute; |
| | | left: 0; |
| | | bottom: 0; |
| | | background-color: #fff; |
| | | text-align: right; |
| | | } |
| | | } |
| | | .ztzf-search-mange { |
| | | height: 40px; |
| | | .search-contain { |
| | | display: flex;justify-content: space-between; |
| | | } |
| | | } |
| | | .ztzf-form-mange { |
| | | .el-form-item { |
| | | width: 300px; |
| | | :deep(.el-form-item__label) { |
| | | width: 120px; |
| | | } |
| | | } |
| | | } |
| | | |
| | | .ztzf-table-mange { |
| | | th.el-table__cell { |
| | | color: rgba(0, 0, 0, .85); |
| | | background-color: #fafafa; |
| | | } |
| | | } |
| | | |
| | | .table-view-mange { |
| | | width: 100%; |
| | | border-top: 0.1rem solid #ebeef5; |
| | | border-left: 0.1rem solid #ebeef5; |
| | | margin-left: 0; |
| | | margin-right: 0; |
| | | .el-col { |
| | | padding-left: 0; |
| | | padding-right: 0; |
| | | margin-bottom: 0; |
| | | height: 32px; |
| | | line-height: 32px; |
| | | border-right: 0.1rem solid #ebeef5; |
| | | text-align: center; |
| | | align-items: center; |
| | | .el-input__wrapper { |
| | | box-shadow: none !important; |
| | | border-bottom: 0.1rem solid #ebeef5; |
| | | } |
| | | } |
| | | .label { |
| | | color: #909399; |
| | | box-sizing: border-box; |
| | | background: #fafafa; |
| | | } |
| | | } |
| New file |
| | |
| | | <template> |
| | | <div class="algorithmMange"> |
| | | <div class="ztzf-search-mange"> |
| | | <el-form :model="params" inline> |
| | | <div class="search-contain"> |
| | | <div> |
| | | <el-form-item label="算法名称:"> |
| | | <el-input v-model="params.algName" placeholder="请输入算法名称" clearable /> |
| | | </el-form-item> |
| | | <el-form-item label="算法类型:"> |
| | | <el-select class="ztzf-select" :teleported="false" v-model="params.algTypeCode" placeholder="请选择算法类型" clearable> |
| | | <el-option v-for="item in sfTypes" :key="item.id" :label="item.dictValue" :value="item.dictKey" ></el-option> |
| | | </el-select> |
| | | </el-form-item> |
| | | </div> |
| | | <div class="btns"> |
| | | <el-button type="primary" @click="getList" :icon="Search">搜索</el-button> |
| | | <el-button @click="cancelSearch" :icon="Delete">清空</el-button> |
| | | </div> |
| | | </div> |
| | | </el-form> |
| | | </div> |
| | | <div class="mange-table"> |
| | | <el-table border :data="tableList" class="ztzf-table-mange"> |
| | | <el-table-column label="序号" type="index" width="60"></el-table-column> |
| | | <el-table-column prop="model_name" label="算法名称" align="center" show-overflow-tooltip></el-table-column> |
| | | <el-table-column prop="alg_type" label="算法类型" align="center"></el-table-column> |
| | | <el-table-column prop="qua_rate" label="最低准确率" align="center"> |
| | | <template #header> |
| | | <el-tooltip placement="bottom" effect="light" content="AI识别率高于最低准确率时会生成待审核状态的事件"> |
| | | <el-icon><QuestionFilled /></el-icon> |
| | | </el-tooltip> |
| | | <span>最低准确率</span> |
| | | </template> |
| | | </el-table-column> |
| | | <el-table-column prop="pass_rate" label="最高准确率" align="center"> |
| | | <template #header> |
| | | <el-tooltip placement="bottom" effect="light" content="AI识别率高于最高准确率时会生成待处理状态的事件"> |
| | | <el-icon><QuestionFilled /></el-icon> |
| | | </el-tooltip> |
| | | <span>最高准确率</span> |
| | | </template> |
| | | </el-table-column> |
| | | <el-table-column prop="event_type" label="事件生成类型" show-overflow-tooltip align="center"> |
| | | <template #default="scope"> |
| | | {{ scope.row.event_type == 0 ? '常规类' : '紧急类' }} |
| | | </template> |
| | | </el-table-column> |
| | | <el-table-column prop="remark" label="算法描述" show-overflow-tooltip /> |
| | | <el-table-column label="操作" width="180" align="center"> |
| | | <template #default="scope"> |
| | | <el-button icon="el-icon-view" type="text" @click="handleDetail(scope.row)">查看</el-button> |
| | | <el-button icon="el-icon-edit" type="text" @click="handleEdit(scope.row)">编辑</el-button> |
| | | </template> |
| | | </el-table-column> |
| | | </el-table> |
| | | </div> |
| | | <div class="pagination"> |
| | | <el-pagination class="ztzf-pagination" popper-class="custom-pagination-dropdown" background |
| | | :page-sizes="[10, 20, 30, 40, 50, 100]" :size="params.size" v-model:current-page="params.current" |
| | | v-model:page-size="params.size" layout="total, sizes, prev, pager, next, jumper" :total="total" |
| | | @size-change="handleSizeChange" @current-change="handleCurrentChange" /> |
| | | </div> |
| | | </div> |
| | | <commonDialog :isShowView="isShowViewTest" width="1000" title="查看" addEditView="view" @cancel="isShowViewTest = false"> |
| | | <template #default> |
| | | <el-row :gutter="0" class="table-view-mange"> |
| | | <el-col :span="6" class="label">算法名称</el-col> |
| | | <el-col :span="6">{{ rowView.model_name }}</el-col> |
| | | <el-col :span="6" class="label">算法类型</el-col> |
| | | <el-col :span="6">{{ rowView.alg_type }}</el-col> |
| | | </el-row> |
| | | <el-row :gutter="0" class="table-view-mange"> |
| | | <el-col :span="6" class="label">最低准确率</el-col> |
| | | <el-col :span="6">{{ rowView.qua_rate }}</el-col> |
| | | <el-col :span="6" class="label">最高准确率</el-col> |
| | | <el-col :span="6">{{ rowView.pass_rate }}</el-col> |
| | | </el-row> |
| | | <el-row :gutter="0" class="table-view-mange"> |
| | | <el-col :span="6" class="label">事件生成类型</el-col> |
| | | <el-col :span="6">{{ rowView.event_type == 0 ? '常规类' : '紧急类' }}</el-col> |
| | | <el-col :span="6" class="label"></el-col> |
| | | <el-col :span="6"></el-col> |
| | | </el-row> |
| | | <el-row :gutter="0" class="table-view-mange"> |
| | | <el-col :span="6" class="label">算法描述</el-col> |
| | | <el-col :span="18"> |
| | | <el-input v-model="rowView.remark"></el-input> |
| | | </el-col> |
| | | </el-row> |
| | | </template> |
| | | </commonDialog> |
| | | <commonDialog :isShowView="isShowEditView" title="编辑" addEditView="edit" @submit="submit(ruleFormRef)" @cancel="isShowEditView = false"> |
| | | <template #default> |
| | | <el-form class="ztzf-form-mange" ref="ruleFormRef" :model="editParams" :rules="rules" inline> |
| | | <el-form-item label="算法名称"> |
| | | <el-input v-model="editParams.model_name" disabled /> |
| | | </el-form-item> |
| | | <el-form-item label="算法类型"> |
| | | <el-select class="ztzf-select" :teleported="false" v-model="editParams.alg_type" disabled> |
| | | <el-option v-for="item in sfTypes" :key="item.id" :label="item.dictValue" :value="item.dictKey" ></el-option> |
| | | </el-select> |
| | | </el-form-item> |
| | | <el-form-item label="最低准确率" prop="qua_rate"> |
| | | <el-input v-model="editParams.qua_rate" placeholder="请输入最低准确率" required clearable /> |
| | | </el-form-item> |
| | | <el-form-item label="最高准确率" prop="pass_rate"> |
| | | <el-input v-model="editParams.pass_rate" placeholder="请输入最高准确率" clearable /> |
| | | </el-form-item> |
| | | <el-form-item label="事件生成类型" prop="event_type"> |
| | | <el-select class="ztzf-select" v-model="editParams.event_type" placeholder="请选择" clearable> |
| | | <el-option label="常规类" value="0"></el-option> |
| | | <el-option label="紧急类" value="1"></el-option> |
| | | </el-select> |
| | | </el-form-item> |
| | | <el-form-item label="算法描述"> |
| | | <el-input v-model="editParams.remark" placeholder="请输入算法描述" clearable /> |
| | | </el-form-item> |
| | | </el-form> |
| | | </template> |
| | | </commonDialog> |
| | | </template> |
| | | <script setup> |
| | | import { getAlgorithmManageList, algorithmManageEdit } from '@/api/algorithmMange/algorithmMange'; |
| | | import { getDictionaryByCode } from '@/api/system/dictbiz'; |
| | | import commonDialog from '@/components/commonDialog.vue' |
| | | import { ElMessage } from 'element-plus'; |
| | | import { Delete, Search } from '@element-plus/icons-vue' |
| | | |
| | | const total = ref(0) |
| | | const params = ref({ |
| | | current: 1, |
| | | size: 10, |
| | | algName: '', |
| | | algTypeCode: '', |
| | | }); |
| | | |
| | | let tableList = ref([]) |
| | | |
| | | let isShowViewTest = ref(false) |
| | | |
| | | let rowView = ref({}) |
| | | |
| | | let isShowEditView = ref(false) |
| | | |
| | | let sfTypes = ref([]) |
| | | const ruleFormRef = ref() |
| | | let editParams = ref({ |
| | | model_name: '', |
| | | alg_type: '', |
| | | qua_rate: '', |
| | | pass_rate: '', |
| | | event_type: '', |
| | | remark: '' |
| | | }) |
| | | const rules = reactive({ |
| | | qua_rate: [ |
| | | { required: true, message: '请输入最低准确率', trigger: 'blur' }, |
| | | { |
| | | validator: (rule, value, callback) => { |
| | | if (!/^\d+(\.\d+)?$/.test(value)) { |
| | | callback(new Error('请输入有效的数字(整数或小数)')); |
| | | } else if (parseFloat(value) < 0.1) { |
| | | callback(new Error('最低准确率不能小于0.1')); |
| | | } else if (parseFloat(value) >= parseFloat(editParams.value.pass_rate)) { |
| | | callback(new Error('最低准确率必须小于最高准确率')); |
| | | } else { |
| | | callback(); |
| | | } |
| | | }, |
| | | trigger: 'blur' |
| | | } |
| | | ], |
| | | pass_rate: [ |
| | | { required: true, message: '请输入最低准确率', trigger: 'blur' }, |
| | | { |
| | | validator: (rule, value, callback) => { |
| | | if (!/^\d+(\.\d+)?$/.test(value)) { |
| | | callback(new Error('请输入有效的数字(整数或小数)')); |
| | | } else if (parseFloat(value) > 1) { |
| | | callback(new Error('最高准确率不能大于1')); |
| | | } else { |
| | | callback(); |
| | | } |
| | | }, |
| | | trigger: 'blur' |
| | | } |
| | | ], |
| | | event_type: [ |
| | | { |
| | | required: true, |
| | | message: '请选择事件生成类型', |
| | | trigger: 'change', |
| | | }, |
| | | ], |
| | | }) |
| | | |
| | | function cancelSearch() { |
| | | params.value = { |
| | | algName: '', |
| | | algTypeCode: '', |
| | | } |
| | | params.value.current = 1 |
| | | getList() |
| | | } |
| | | |
| | | function getList() { |
| | | getAlgorithmManageList(params.value).then(res => { |
| | | tableList.value = res.data.data.records || [] |
| | | total.value = res.data.data.total || 0 |
| | | }) |
| | | } |
| | | function getSFType() { |
| | | getDictionaryByCode('WORK_ORDER_TYPE').then(res => { |
| | | sfTypes.value = res.data.data.WORK_ORDER_TYPE || [] |
| | | }); |
| | | } |
| | | function handleDetail(row) { |
| | | isShowViewTest.value = true |
| | | rowView.value = row |
| | | } |
| | | function handleEdit(row) { |
| | | isShowEditView.value = true |
| | | editParams.value = { ...row } |
| | | } |
| | | |
| | | function handleSizeChange(val) { |
| | | params.value.size = val |
| | | getList() |
| | | } |
| | | |
| | | function handleCurrentChange(val) { |
| | | params.value.current = val |
| | | getList() |
| | | } |
| | | |
| | | async function submit(formValidate) { |
| | | if (!formValidate) return |
| | | await formValidate.validate((valid, fields) => { |
| | | if (valid) { |
| | | algorithmManageEdit(editParams.value).then(res => { |
| | | ElMessage.success('保存成功') |
| | | isShowEditView.value = false |
| | | getList() |
| | | }) |
| | | } |
| | | }) |
| | | } |
| | | |
| | | onMounted(() => { |
| | | getList() |
| | | getSFType() |
| | | }) |
| | | </script> |
| | | |
| | | <style lang="scss" scoped> |
| | | .algorithmMange { |
| | | height: 0; |
| | | flex: 1; |
| | | margin: 0 10px 10px 10px; |
| | | background-color: #ffffff; |
| | | padding: 10px 20px; |
| | | border-radius: 5px; |
| | | display: flex; |
| | | flex-direction: column; |
| | | .search-box { |
| | | height: 40px; |
| | | .btns { |
| | | display: flex; |
| | | justify-content: end; |
| | | } |
| | | } |
| | | |
| | | :deep(.el-input) { |
| | | .el-input__wrapper { |
| | | width: 200px; |
| | | } |
| | | } |
| | | |
| | | // 表格 |
| | | .mange-table { |
| | | height: 0; |
| | | flex: 1; |
| | | margin-top: 18px; |
| | | overflow: auto; |
| | | } |
| | | :deep(.el-pagination) { |
| | | display: flex; |
| | | justify-content: right; |
| | | } |
| | | |
| | | :deep(.el-pagination button) { |
| | | background: center center no-repeat none !important; |
| | | color: #8eb8ea !important; |
| | | } |
| | | :deep(.ztzf-select){ |
| | | .el-select__selection { |
| | | width: 200px; |
| | | } |
| | | } |
| | | } |
| | | </style> |
| | |
| | | <template> |
| | | <el-dialog modal-class="mapDialog" v-model="isShow" width="80%"> |
| | | <el-dialog modal-class="mapDialog" v-model="isShow" width="80%" class="ztzf-dialog-mange"> |
| | | <template #header="{ titleId, titleClass }"> |
| | | <div class="my-header"> |
| | | <h4 :id="titleId" :class="titleClass">定位</h4> |
| | |
| | | |
| | | <style scoped lang="scss"> |
| | | .mapBox { |
| | | margin-top: 10px; |
| | | z-index: 2; |
| | | height: 650px; |
| | | width: 98%; |
| | |
| | | <!-- 查看弹框 --> |
| | | <el-dialog |
| | | v-model="dialogVisible" |
| | | class="ztzf-dialog-mange" |
| | | width="60%" |
| | | append-to-body |
| | | @close="dialogClose" |
| | |
| | | <!-- 视频预览 --> |
| | | <el-dialog |
| | | :title="currentVideoTitle" |
| | | class="ztzf-dialog-mange" |
| | | modal-class="videoDialog" |
| | | append-to-body |
| | | width="54%" |
| | |
| | | @click.stop="copyInfo(scope.row, scope.index)" v-if="userInfo.role_name.includes('admin')">复制 |
| | | </el-button> |
| | | </template> |
| | | </avue-crud> |
| | | </avue-crud>F |
| | | </basic-container> |
| | | </template> |
| | | |
| | |
| | | }, |
| | | }, |
| | | { |
| | | label: '创建时间', |
| | | prop: 'create_time', |
| | | addDisplay: false, |
| | | editDisplay: false, |
| | | overHidden: true, |
| | | type: 'date', |
| | | labelWidth: 130, |
| | | width: 160, |
| | | format: 'YYYY-MM-DD HH:mm:ss', |
| | | |
| | | }, |
| | | { |
| | | label: '设备描述', // '工作空间描述', |
| | | prop: 'workspace_desc', |
| | | type: 'textarea', |
| | |
| | | ], |
| | | }, |
| | | |
| | | { |
| | | label: '创建时间', |
| | | prop: 'create_time', |
| | | addDisplay: false, |
| | | editDisplay: false, |
| | | overHidden: true, |
| | | type: 'date', |
| | | labelWidth: 130, |
| | | width: 160, |
| | | format: 'YYYY-MM-DD HH:mm:ss', |
| | | |
| | | }, |
| | | |
| | | |
| | | |
| | | ], |
| | |
| | | width: 200, |
| | | type: 'daterange', |
| | | format: 'YYYY-MM-DD', |
| | | valueFormat: 'YYYY-MM-DD HH:mm:ss', |
| | | valueFormat: 'YYYY-MM-DD', |
| | | startPlaceholder: '保险开始日期', |
| | | endPlaceholder: '保险结束日期', |
| | | align: 'center', |
| | | rules: [ |
| | | { |
| | | required: false, |
| | |
| | | trigger: 'blur', |
| | | }, |
| | | ], |
| | | formatter: (row, value) => { |
| | | return value[0]? `${this.$dayjs(value[0]).format('YYYY-MM-DD')}~${this.$dayjs(value[1]).format('YYYY-MM-DD')}` : '/'; |
| | | }, |
| | | }, |
| | | // { |
| | | // label: '保险有效期', |
| | |
| | | editDisplay: false, //编辑显示 |
| | | // editDisabled: true, |
| | | addDisplay: false, |
| | | editDisplay: false, |
| | | viewDisplay: false, |
| | | // rules: [ |
| | | // { |
| | |
| | | area_code: await this.getFullAreaCode(data.area_code), |
| | | area_name: this.form.area_name, |
| | | cnmode_code: this.getDockModeText(this.form.mode_code), |
| | | // domain: data.domain === 0 ? '无人机' : data.domain === 3 ? '机巢' : '未知', |
| | | domainTxt: data.domain === 0 ? '无人机' : data.domain === 3 ? '机巢' : '未知', |
| | | cnstatus: this.form.status === false ? '离线' : '在线', |
| | | duration_of_insurance: [data?.insure_start_time || '', data?.insure_expired_time || ''], |
| | |
| | | watch( |
| | | () => Store.getters.deviceState, |
| | | value => { |
| | | console.log(value, '测试') |
| | | // console.log('设备状态变化', value.deviceInfo[props.deviceInfo.child_sn]) |
| | | if (props.sn && (value.currentSn === props.deviceInfo.child_sn || value.currentSn === props.deviceInfo.device_sn)) { |
| | | debugStatus.value = value.dockInfo[props.deviceInfo.device_sn]?.basic_osd?.mode_code === EDockModeCode.Remote_Debugging |
| | |
| | | </el-button> |
| | | </template> |
| | | </avue-crud> |
| | | <el-dialog title="固件上传" append-to-body v-model="firmwareUploadBox" width="40%" height="60%"> |
| | | <el-dialog title="固件上传" class="ztzf-dialog-mange" append-to-body v-model="firmwareUploadBox" width="40%" height="60%"> |
| | | <el-form |
| | | ref="form" |
| | | class="ztzf-form-mange" |
| | | :model="importForm" |
| | | v-loading="loadingForm" |
| | | label-width="80px" |
| | | style="width: 80%; margin-left: 10%" |
| | | :rules="rules" |
| | | > |
| | |
| | | <el-form-item label="说明" label-width="80px" prop="release_note"> |
| | | <el-input type="textarea" v-model="importForm.release_note" clearable></el-input> |
| | | </el-form-item> |
| | | <el-form-item> |
| | | <el-button type="primary" @click="onConfirm">确定</el-button> |
| | | <el-button @click="onCancel">取消</el-button> |
| | | </el-form-item> |
| | | </el-form> |
| | | <template #footer> |
| | | <div class="dialog-footer"> |
| | | <el-button type="primary" @click="onConfirm">确定</el-button> |
| | | <el-button @click="onCancel">取消</el-button> |
| | | </div> |
| | | </template> |
| | | </el-dialog> |
| | | </basic-container> |
| | | </template> |
| | |
| | | type: 'category', |
| | | // data: ['1月', '2月', '3月', '4月', '5月', '6月'], |
| | | axisLine: { |
| | | show: false, // 隐藏轴线 |
| | | }, |
| | | axisLine: { |
| | | show: false, // 隐藏轴线 |
| | | show: true, // 隐藏轴线 |
| | | }, |
| | | axisLabel: { |
| | | color: '#5B5B5D', |
| | |
| | | type: 'category', |
| | | data: ['1'], |
| | | axisLine: { |
| | | show: false, // 隐藏轴线 |
| | | show: true, // 隐藏轴线 |
| | | }, |
| | | axisTick: { |
| | | show: true, |
| | | length: 2, |
| | | lineStyle: { |
| | | color: '#363636', |
| | | }, |
| | | }, |
| | | // axisTick: { |
| | | // show: true, |
| | | // length: 2, |
| | | // lineStyle: { |
| | | // color: 'red', |
| | | // }, |
| | | // }, |
| | | axisLabel: { |
| | | color: '#363636', |
| | | margin: 8, |
| | |
| | | </avue-crud> |
| | | |
| | | <!-- 新增弹窗 --> |
| | | <el-dialog title="新增 License" v-model="addDialogVisible" width="70%" :close-on-click-modal="false" |
| | | <el-dialog class="ztzf-dialog-mange" title="新增 License" v-model="addDialogVisible" width="70%" :close-on-click-modal="false" |
| | | @close="resetForm"> |
| | | <el-form :model="newLicense" ref="licenseForm" label-width="120px"> |
| | | <el-form-item label="机构ID" prop="licenseId"> |
| | |
| | | <el-form-item label="机构名称" prop="licenseName" required> |
| | | <el-input v-model="newLicense.licenseName" /> |
| | | </el-form-item> |
| | | <el-form-item label="是否验证过期时间类型" prop="licenseType" required> |
| | | <el-form-item label="过期时间类型" prop="licenseType" required> |
| | | <el-select v-model="newLicense.licenseType" placeholder="请选择"> |
| | | <el-option label="不验证过期时间" :value="1" /> |
| | | <el-option label="验证过期时间" :value="2" /> |
| | |
| | | <el-button type="primary" text icon="el-icon-edit" @click="uploadPatch(scope.row, 'edit')" |
| | | >编辑 |
| | | </el-button> |
| | | <el-button type="primary" text icon="el-icon-delete" @click="rowDel(scope.row)" |
| | | <el-button :disabled="scope.row.patches_type_desc==='综合类'" type="primary" text icon="el-icon-delete" @click="rowDel(scope.row)" |
| | | >删除 |
| | | </el-button> |
| | | </template> |
| | |
| | | <template #category="{ row }"> |
| | | <el-tag>{{ row.categoryName }}</el-tag> |
| | | </template> |
| | | <template #menu="{ row }"> |
| | | <el-button |
| | | :disabled="row.patches_type === '综合类'" |
| | | type="primary" |
| | | text |
| | | icon="el-icon-delete" |
| | | @click="rowDel(row)" |
| | | > |
| | | 删除 |
| | | </el-button> |
| | | </template> |
| | | </avue-crud> |
| | | </basic-container> |
| | | </template> |
| | |
| | | selection: true, |
| | | grid: false, |
| | | menuWidth: 180, |
| | | labelWidth: 100, |
| | | dialogWidth: 880, |
| | | labelWidth: 90, |
| | | dialogWidth: 600, |
| | | dialogClickModal: false, |
| | | height: 'auto', |
| | | calcHeight: 20, |
| | |
| | | gridBtn: false, |
| | | searchShowBtn: false, |
| | | columnBtn: false, |
| | | delBtn: false, |
| | | column: [ |
| | | { |
| | | label: '类型名称', |
| | | prop: 'patches_type', |
| | | search: true, |
| | | searchSpan: 4, |
| | | span: 24, |
| | | rules: [{ required: true, message: '请输入类型名称', trigger: 'blur' }], |
| | | }, |
| | | { |
| | |
| | | </el-row> |
| | | <!-- 表单模块 --> |
| | | <el-dialog |
| | | class="ztzf-dialog-mange" |
| | | :title="title" |
| | | v-model="box" |
| | | width="50%" |
| | |
| | | |
| | | <!-- 新建工单对话框 --> |
| | | <el-dialog |
| | | class="ztzf-dialog-mange" |
| | | v-model="dialogVisible" |
| | | title="新建工单" |
| | | width="70%" |
| | |
| | | </el-col> |
| | | </el-row> |
| | | |
| | | <el-row> |
| | | <div class="add-box-btns"> |
| | | <el-button type="danger" @click="submitForm(1)">发起</el-button> |
| | | <el-button type="primary" @click="submitForm(0)">存草稿</el-button> |
| | | <el-button @click="dialogVisible = false">取消</el-button> |
| | | </div> |
| | | </el-row> |
| | | <!-- <el-row>--> |
| | | <!-- <div class="add-box-btns">--> |
| | | <!-- <el-button type="danger" @click="submitForm(1)">发起</el-button>--> |
| | | <!-- <el-button type="primary" @click="submitForm(0)">存草稿</el-button>--> |
| | | <!-- <el-button @click="dialogVisible = false">取消</el-button>--> |
| | | <!-- </div>--> |
| | | <!-- </el-row>--> |
| | | </el-form> |
| | | <template #footer> |
| | | <div class="dialog-footer"> |
| | | <el-button type="danger" @click="submitForm(1)">发起</el-button> |
| | | <el-button type="primary" @click="submitForm(0)">存草稿</el-button> |
| | | <el-button @click="dialogVisible = false">取消</el-button> |
| | | </div> |
| | | </template> |
| | | </el-dialog> |
| | | |
| | | <!-- 工单详情对话框 --> |
| | | <el-dialog |
| | | class="ztzf-dialog-mange" |
| | | align-center |
| | | v-model="detailVisible" |
| | | :title="detailTitle" |
| | |
| | | <map-container v-if="detailVisible" ref="MapContainer"></map-container> |
| | | </el-col> |
| | | </el-row> |
| | | |
| | | <el-row> |
| | | <div class="add-box-btns"> |
| | | <el-button |
| | | type="danger" |
| | | v-if="form.status == 0 || (form.status == 2 && userInfo.user_id == form.create_user)" |
| | | @click="submitForm(1)" |
| | | >发布</el-button |
| | | > |
| | | <el-button |
| | | type="primary" |
| | | v-if="form.status == 0 || (form.status == 2 && userInfo.user_id == form.create_user)" |
| | | @click="submitForm(0)" |
| | | >保存</el-button |
| | | > |
| | | <!-- <el-button type="primary" v-if="form.status == 0 || userInfo.user_id == form.create_user" |
| | | @click="submitForm(0)">保存</el-button> --> |
| | | |
| | | <el-button |
| | | type="primary" |
| | | v-if="form.status == 1 && hasPaddingBtnPermission()" |
| | | @click="orderLogPass(form.id)" |
| | | >通过</el-button |
| | | > |
| | | <el-button |
| | | type="danger" |
| | | v-if="form.status == 1 && hasRejectionBtnPermission()" |
| | | @click="orderLogReject(form.id)" |
| | | >驳回</el-button |
| | | > |
| | | </div> |
| | | </el-row> |
| | | </el-form> |
| | | <template #footer> |
| | | <div class="dialog-footer"> |
| | | <el-button |
| | | type="danger" |
| | | v-if="form.status == 0 || (form.status == 2 && userInfo.user_id == form.create_user)" |
| | | @click="submitForm(1)" |
| | | >发布</el-button |
| | | > |
| | | <el-button |
| | | type="primary" |
| | | v-if="form.status == 0 || (form.status == 2 && userInfo.user_id == form.create_user)" |
| | | @click="submitForm(0)" |
| | | >保存</el-button |
| | | > |
| | | <!-- <el-button type="primary" v-if="form.status == 0 || userInfo.user_id == form.create_user" |
| | | @click="submitForm(0)">保存</el-button> --> |
| | | |
| | | <el-button |
| | | type="primary" |
| | | v-if="form.status == 1 && hasPaddingBtnPermission()" |
| | | @click="orderLogPass(form.id)" |
| | | >通过</el-button |
| | | > |
| | | <el-button |
| | | type="danger" |
| | | v-if="form.status == 1 && hasRejectionBtnPermission()" |
| | | @click="orderLogReject(form.id)" |
| | | >驳回</el-button |
| | | > |
| | | </div> |
| | | </template> |
| | | </el-dialog> |
| | | |
| | | <!-- 工单详情 --> |
| | | <el-dialog |
| | | class="ztzf-dialog-mange" |
| | | align-center |
| | | v-model="detailVisibleCopy" |
| | | title="工单详情" |
| | |
| | | </el-col> |
| | | </el-row> |
| | | |
| | | <el-row> |
| | | <div class="add-box-btns"> |
| | | <el-button |
| | | type="danger" |
| | | v-if="form.status == 0 || (form.status == 2 && userInfo.user_id == form.create_user)" |
| | | @click="submitForm(1)" |
| | | >发布</el-button |
| | | > |
| | | <!-- <el-button type="primary" v-if="form.status == 0 || userInfo.user_id == form.create_user" |
| | | @click="submitForm(0)">保存</el-button> --> |
| | | |
| | | <el-button |
| | | type="primary" |
| | | v-if="form.status == 1 && hasPaddingBtnPermission()" |
| | | @click="orderLogPass(form.id)" |
| | | >通过</el-button |
| | | > |
| | | <el-button |
| | | type="danger" |
| | | v-if="form.status == 1 && hasRejectionBtnPermission()" |
| | | @click="orderLogReject(form.id)" |
| | | >驳回</el-button |
| | | > |
| | | <el-button @click="detailVisibleCopy = false">取消</el-button> |
| | | </div> |
| | | </el-row> |
| | | </el-form> |
| | | <template #footer> |
| | | <div class="dialog-footer"> |
| | | <el-button |
| | | type="danger" |
| | | v-if="form.status == 0 || (form.status == 2 && userInfo.user_id == form.create_user)" |
| | | @click="submitForm(1)" |
| | | >发布</el-button |
| | | > |
| | | <!-- <el-button type="primary" v-if="form.status == 0 || userInfo.user_id == form.create_user" |
| | | @click="submitForm(0)">保存</el-button> --> |
| | | |
| | | <el-button |
| | | type="primary" |
| | | v-if="form.status == 1 && hasPaddingBtnPermission()" |
| | | @click="orderLogPass(form.id)" |
| | | >通过</el-button |
| | | > |
| | | <el-button |
| | | type="danger" |
| | | v-if="form.status == 1 && hasRejectionBtnPermission()" |
| | | @click="orderLogReject(form.id)" |
| | | >驳回</el-button |
| | | > |
| | | <el-button @click="detailVisibleCopy = false">取消</el-button> |
| | | </div> |
| | | </template> |
| | | </el-dialog> |
| | | </basic-container> |
| | | </template> |
| | |
| | | </div> |
| | | </el-form> |
| | | <template #footer> |
| | | <div class="dialog-footer"> |
| | | <div class="dialog-footer-new"> |
| | | <el-button type="danger" :loading="submitLoading" @click="submitForm">发布</el-button> |
| | | <el-button type="infoprimary" plain :loading="draftLoading" @click="saveDraft" |
| | | >存草稿</el-button |
| | |
| | | </div> |
| | | |
| | | <!-- 操作按钮 --> |
| | | <div class="dialog-footer1"> |
| | | <div class="dialog-footer1-new"> |
| | | <div class="leftBtn" :class="currentIndex === 0 ? 'disableds' : ''" @click="leftClick"> |
| | | 上一页 |
| | | </div> |
| | |
| | | title="批量审核" |
| | | width="1100" |
| | | append-to-body |
| | | class="ztzf-dialog-mange" |
| | | custom-class="review-dialog" |
| | | @close="cancleBatchReject" |
| | | > |
| | |
| | | title="工单复核" |
| | | width="30%" |
| | | append-to-body |
| | | custom-class="re-check-dialog" |
| | | class="ztzf-dialog-mange" |
| | | @close="reCheckDialog = false" |
| | | > |
| | | <div class="dialog-footer"> |
| | |
| | | |
| | | this.loadAMapScripts(); |
| | | this.fetchDropdownData(); |
| | | // console.log('permission.tickets_processing_btn', this.permission.tickets_processing_btn); |
| | | // console.log('permission', this.permission.tickets_tab_pending); |
| | | |
| | | }, |
| | | |
| | | mounted() { |
| | |
| | | } |
| | | |
| | | let curQueryParams = {}; |
| | | |
| | | let isTabProcessed = false; |
| | | if (href.indexOf('?') != -1 && href.split('?').length > 0) { |
| | | curQueryParams = href |
| | | .split('?')[1] |
| | |
| | | return pre; |
| | | }, {}); |
| | | |
| | | const { orderNumber = undefined, day = undefined } = curQueryParams; |
| | | const { orderNumber = undefined, day = undefined, tab = undefined } = curQueryParams; |
| | | |
| | | // 日历传值 |
| | | if (day) { |
| | |
| | | find && (find.query = {}); |
| | | }); |
| | | } |
| | | if (tab) { |
| | | const isTabValid = this.filteredTabs.some(t => t.name === tab); |
| | | if (isTabValid) { |
| | | this.activeTab = tab; |
| | | this.handleTabChangeAfterJump(); |
| | | isTabProcessed = true; |
| | | const find = this.$store.state.tags.bsTagList.find(i => i.path === '/tickets/ticket'); |
| | | find && (find.query = {}); |
| | | } |
| | | } |
| | | } |
| | | |
| | | this.fetchTabCounts(); // 新增:初始化时获取 tab 数据 |
| | |
| | | // 修改这里:使用 types 数组查找对应的 label |
| | | value: |
| | | this.types.find(t => t.value === this.currentDetail.type)?.label || |
| | | this.currentDetail.type || |
| | | '/', |
| | | this.currentDetail.type |
| | | }, |
| | | { label: '关联任务', value: this.currentDetail.job_name || '/' }, |
| | | { label: '任务发起人', value: this.currentDetail.creator }, |
| | |
| | | label: '关联算法', |
| | | value: |
| | | this.algorithms.find(t => t.value === this.currentDetail.aiType)?.label || |
| | | this.currentDetail.aiType || |
| | | '/', |
| | | this.currentDetail.aiType |
| | | }, |
| | | { label: '发起单位', value: this.currentDetail.department }, |
| | | { label: '发起任务时间', value: this.currentDetail.startTime }, |
| | |
| | | }, |
| | | |
| | | handleSFNodeClick(data) { |
| | | console.log(data.dictKey, '666666666'); |
| | | this.filters.type = ''; |
| | | this.filters.algorithm = ''; |
| | | this.filters.type = data.dictKey; |
| | |
| | | |
| | | handleTabChange(tab) { |
| | | this.activeTab = tab.props?.name || tab.name; |
| | | |
| | | const isReview = this.findObject(this.option.column, 'isReview'); |
| | | // 根据条件切换显隐 |
| | | isReview.hide = !['all', 'completed', 'myTickets'].includes(this.activeTab); |
| | |
| | | this.fetchTableData(); |
| | | this.fetchTabCounts(); // 切换 tab 时重新获取数据 |
| | | }, |
| | | |
| | | //新增 跳转后触发的Tab切换 |
| | | handleTabChangeAfterJump() { |
| | | const isReview = this.findObject(this.option.column, 'isReview'); |
| | | isReview.hide = !['all', 'completed', 'myTickets'].includes(this.activeTab); |
| | | this.handleReset(); |
| | | this.page.currentPage = 1; |
| | | this.fetchTableData(); |
| | | this.fetchTabCounts(); |
| | | }, |
| | | handleSearch() { |
| | | this.page.currentPage = 1; |
| | | this.fetchTableData(); |
| | |
| | | <style lang="scss"> |
| | | .custom-dialog { |
| | | max-height: 96vh; |
| | | .el-dialog__body { |
| | | |
| | | border-top: 0.1rem solid #f0f0f0; |
| | | } |
| | | } |
| | | .custom-qrcode-popover { |
| | | min-width: 160px !important; |
| | |
| | | width: 100%; |
| | | } |
| | | } |
| | | |
| | | .dialog-footer { |
| | | text-align: center; |
| | | :deep(.el-dialog__body) { |
| | | border-top: 0.1rem solid #f0f0f0; |
| | | } |
| | | .dialog-footer-new { |
| | | text-align: right; |
| | | padding-top: 16px; |
| | | border-top: 1px solid #ebeef5; |
| | | |
| | |
| | | } |
| | | } |
| | | } |
| | | .dialog-footer1 { |
| | | .dialog-footer1-new { |
| | | position: sticky; |
| | | bottom: 28px; |
| | | left: 0; |
| | |
| | | :deep(.el-dialog__body) { |
| | | padding: 0; |
| | | background-color: #f5f7fa; |
| | | border-top: 0.1rem solid #f0f0f0; |
| | | } |
| | | } |
| | | |
| | |
| | | :deep(.el-dialog__body) { |
| | | padding: 0; |
| | | background-color: #f5f7fa; |
| | | border-top: 0.1rem solid #f0f0f0; |
| | | } |
| | | } |
| | | |
| | |
| | | </div> |
| | | |
| | | <div class="action-area"> |
| | | <!-- <img :src="st7" alt="" /> --> |
| | | <!-- <span class="todo-date">{{ item.date?.slice(0, 10).replace(/-/g, '.') }}</span> --> |
| | | <span class="todo-date">{{ item.name }}</span> |
| | | <!-- <span class="todo-date">{{ item.name }}</span> --> |
| | | <el-tooltip effect="dark" :content="item.name" placement="top"> |
| | | <span class="todo-date">{{item.name}}</span> |
| | | </el-tooltip> |
| | | </div> |
| | | </div> |
| | | </div> |
| | |
| | | .action-area { |
| | | display: flex; |
| | | align-items: center; |
| | | margin-right: 42px; |
| | | margin-right: 22px; |
| | | |
| | | img { |
| | | width: 15px; |
| | |
| | | |
| | | .todo-date { |
| | | font-weight: 400; |
| | | font-size: 14px; |
| | | color: #343434; |
| | | margin-left: 2px; |
| | | font-size: 14px; |
| | | color: #343434; |
| | | margin-left: 2px; |
| | | white-space: nowrap; |
| | | overflow: hidden; |
| | | text-overflow: ellipsis; |
| | | max-width: 200px; |
| | | display: inline-block; |
| | | } |
| | | } |
| | | } |
| | |
| | | :key="index" |
| | | @click="timeClick(item, index)" |
| | | > |
| | | {{ timeListStr[index] }} |
| | | {{ timeListStr[index] }} |
| | | </div> |
| | | </div> |
| | | </div> |
| | |
| | | <div class="card-group"> |
| | | <div class="main-card"> |
| | | <div class="status-grid"> |
| | | <div class="status-item" v-for="(item, index) in eventTypeList" :key="index"> |
| | | <div class="status-item" v-for="(item, index) in eventTypeList" :key="index" @click="jumpEventDetails(item,index)"> |
| | | <div class="statusCon"> |
| | | <div class="status-label">{{ item.name }}</div> |
| | | <div class="status-value">{{ item.value }}<span>个</span></div> |
| | |
| | | import overviewImg3 from '@/assets/images/workbench/tc3.svg'; |
| | | import overviewImg4 from '@/assets/images/workbench/tc4.svg'; |
| | | import overviewImg5 from '@/assets/images/workbench/tc5.svg'; |
| | | import { useRouter } from 'vue-router' |
| | | const router = useRouter() |
| | | let checked = ref('CURRENT_YEAR'); |
| | | let timeListStr = ['本周', '本月', '本年']; |
| | | let timeListEnum = ['CURRENT_WEEK', 'CURRENT_MONTH', 'CURRENT_YEAR']; |
| | |
| | | }); |
| | | const dateSelect = ref('CURRENT_YEAR'); |
| | | const eventTypeList = ref([ |
| | | { name: '待审核', value: 0, img: overviewImg2, color: '#FF472F', status: '2', rate: 0 }, |
| | | { name: '待处理', value: 0, img: overviewImg3, color: '#FF7411', status: '0', rate: 0 }, |
| | | { name: '处理中', value: 0, img: overviewImg4, color: '#FFC300', status: '3', rate: 0 }, |
| | | { name: '已完成', value: 0, img: overviewImg5, color: '#0291A1', status: '4', rate: 0 }, |
| | | { name: '待审核', value: 0, img: overviewImg2, color: '#FF472F', status: '2', rate: 0 ,tagging:'pending' }, |
| | | { name: '待处理', value: 0, img: overviewImg3, color: '#FF7411', status: '0', rate: 0 ,tagging:'processing' }, |
| | | { name: '处理中', value: 0, img: overviewImg4, color: '#FFC300', status: '3', rate: 0 ,tagging:'inProgress'}, |
| | | { name: '已完成', value: 0, img: overviewImg5, color: '#0291A1', status: '4', rate: 0 ,tagging:'completed'}, |
| | | ]); |
| | | // 工单统计 |
| | | const getTypeData = () => { |
| | |
| | | dateSelect.value = item; |
| | | getTypeData(); |
| | | }; |
| | | // 跳转事件工单 |
| | | const jumpEventDetails = (item,index)=>{ |
| | | // console.log('tiaozhuan',item); |
| | | router.replace({ |
| | | path: `/tickets/ticket`, |
| | | query: { tab: item.tagging } |
| | | }); |
| | | } |
| | | // 图表 |
| | | const echartsRef = ref(null); |
| | | let { chart } = useEchartsResize(echartsRef); |
| | |
| | | width: 144px; |
| | | background: #f6f8fe; |
| | | border-radius: 8px 8px 8px 8px; |
| | | |
| | | cursor: pointer; |
| | | img { |
| | | width: 26px; |
| | | height: 26px; |