This commit is contained in:
lb 2023-10-25 17:02:43 +08:00
parent e153d7e077
commit 5ba186b0c6
7 changed files with 7997 additions and 8776 deletions

View File

@ -12,8 +12,8 @@ ENV = 'development'
VUE_APP_TITLE = 产线监控系统 VUE_APP_TITLE = 产线监控系统
# 芋道管理系统/开发环境 # 芋道管理系统/开发环境
# VUE_APP_BASE_API = 'http://192.168.1.8:48082' VUE_APP_BASE_API = 'http://192.168.1.8:48082'
VUE_APP_BASE_API = 'http://192.168.0.33:48082' # VUE_APP_BASE_API = 'http://192.168.0.33:48082'
# 路由懒加载 # 路由懒加载
VUE_CLI_BABEL_TRANSPILE_MODULES = true VUE_CLI_BABEL_TRANSPILE_MODULES = true

View File

@ -71,6 +71,7 @@
"screenfull": "5.0.2", "screenfull": "5.0.2",
"sortablejs": "1.10.2", "sortablejs": "1.10.2",
"throttle-debounce": "2.1.0", "throttle-debounce": "2.1.0",
"uuid": "^9.0.1",
"video.js": "^8.5.2", "video.js": "^8.5.2",
"vue": "2.7.14", "vue": "2.7.14",
"vue-count-to": "1.0.13", "vue-count-to": "1.0.13",

View File

@ -9,48 +9,30 @@
<section class="process-bom"> <section class="process-bom">
<SearchBar :formConfigs="searchBarFormConfig" ref="search-bar" /> <SearchBar :formConfigs="searchBarFormConfig" ref="search-bar" />
<div <div class="btns" style="
class="btns"
style="
text-align: right; text-align: right;
position: absolute; position: absolute;
top: 20px; top: 20px;
right: 20px; right: 20px;
display: flex; display: flex;
"> ">
<el-button type="primary" plain class="btn-create" icon="el-icon-plus"> <el-button type="primary" plain :disabled="currentDet == null" class="btn-create" icon="el-icon-plus">
分配设备 分配设备
</el-button> </el-button>
<el-input <el-input icon="el-icon-search" placeholder="搜索" v-model="searchText" style="margin-left: 20px">
icon="el-icon-search"
placeholder="搜索"
style="margin-left: 20px">
<i slot="prefix" class="el-input__icon el-icon-search"></i> <i slot="prefix" class="el-input__icon el-icon-search"></i>
</el-input> </el-input>
</div> </div>
<!-- 列表 --> <!-- 列表 -->
<base-table <base-table :table-props="tableProps" :page="queryParams.pageNo" :limit="queryParams.pageSize" :table-data="list"
:table-props="tableProps"
:page="queryParams.pageNo"
:limit="queryParams.pageSize"
:table-data="list"
@emitFun="handleEmitFun"> @emitFun="handleEmitFun">
<method-btn <method-btn v-if="tableBtn.length" slot="handleBtn" label="操作" :width="120" :method-list="tableBtn"
v-if="tableBtn.length"
slot="handleBtn"
label="操作"
:width="120"
:method-list="tableBtn"
@clickBtn="handleTableBtnClick" /> @clickBtn="handleTableBtnClick" />
</base-table> </base-table>
<!-- 分页组件 --> <!-- 分页组件 -->
<pagination <pagination v-show="total > 0" :total="total" :page.sync="queryParams.pageNo" :limit.sync="queryParams.pageSize"
v-show="total > 0"
:total="total"
:page.sync="queryParams.pageNo"
:limit.sync="queryParams.pageSize"
@pagination="getList" /> @pagination="getList" />
</section> </section>
</template> </template>
@ -59,7 +41,12 @@
export default { export default {
name: 'ProcessBom', name: 'ProcessBom',
components: {}, components: {},
props: {}, props: {
currentDet: {
type: Object,
default: null
}
},
data() { data() {
return { return {
searchBarFormConfig: [{ label: '工序下设备' }], searchBarFormConfig: [{ label: '工序下设备' }],
@ -82,13 +69,60 @@ export default {
pageNo: 1, pageNo: 1,
pageSize: 10, pageSize: 10,
}, },
searchText: ''
}; };
}, },
computed: {}, watch: {
currentDet: {
handler(val) {
if (val != null) {
this.getList(val);
} else {
this.clearList();
}
},
immediate: true,
deep: true
}
},
methods: { methods: {
handleEmitFun() { }, handleEmitFun() { },
handleTableBtnClick() { }, handleTableBtnClick() { },
getList() {}, put(payload) {
return this.http(this.updateUrl, 'put', payload);
},
post(payload) {
return this.http(this.addUrl, 'post', payload);
},
recv(payload) {
return this.http(this.pageUrl, 'get', payload);
},
info(payload) {
return this.http(this.infoUrl, 'get', payload);
},
http(url, method, payload) {
return this.$axios({
url,
method,
params: method === 'get' ? payload : null,
data: method !== 'get' ? payload : null,
})
},
getList({ detId, detName, detDesc, flowId, sectionName } = {}) {
console.log('get list')
},
getList() {
this.list = [
{ name: '1', code: 'bomg-1', remark: 'Tochter' },
{ name: '2', code: 'bomg-2', remark: 'Bruder' },
{ name: '3', code: 'bomg-3', remark: 'Kalt' },
]
},
clearList() {
this.list = [];
}
}, },
}; };
</script> </script>

View File

@ -22,14 +22,14 @@
<el-button type="primary" plain class="btn-create" icon="el-icon-plus" @click="handleAdd"> <el-button type="primary" plain class="btn-create" icon="el-icon-plus" @click="handleAdd">
新建工序 新建工序
</el-button> </el-button>
<el-button class="btn-serialize" @click="handleToJson">序列化</el-button> <!-- <el-button class="btn-serialize" @click="handleToJson">序列化</el-button>
<el-button class="btn-antiserialize" @click="handleLoadJson"> <el-button class="btn-antiserialize" @click="handleLoadJson">
反序列化 反序列化
</el-button> </el-button> -->
<el-button class="btn-edit" @click="handleEdit">编辑</el-button> <el-button class="btn-edit" :disabled="currentDet == null" @click="handleEdit">编辑</el-button>
<el-button type="error" class="btn-delete" @click="handleDelete"> <!-- <el-button type="danger" plain :disabled="currentDet == null" class="btn-delete" @click="handleDelete">
删除 删除
</el-button> </el-button> -->
</div> </div>
<div class="process-graph__panel" ref="panel"></div> <div class="process-graph__panel" ref="panel"></div>
@ -101,31 +101,30 @@ export default {
updateUrl: '/extend/process-flow-view/update', updateUrl: '/extend/process-flow-view/update',
addUrl: '/extend/process-flow-view/create', addUrl: '/extend/process-flow-view/create',
// pageUrl: '/extend/process-flow-det/get', // pageUrl: '/extend/process-flow-det/get',
infoUrl: '/extend/process-flow-view/get', infoUrl: '/extend/process-flow-view/getByFlowId',
layout: { layout: {
id: null, id: null,
flowId: null, flowId: null,
content: '', content: '',
createTime: null createTime: null
}, },
currentDet: null,
}; };
}, },
watch: { watch: {
'form.sectionId': { 'form.sectionId': {
handler(id) { handler(id) {
// const { form } = this;
// const { sectionId } = form;
// if (sectionId) {
// const { label } = this.$refs['form'].getSelectItem(
// 'sectionId',
// sectionId
// );
// form.workshopName = label;
// }
}, },
immediate: false, immediate: false,
}, },
currentDet: {
handler(val) {
this.$emit('det-selected', val)
},
deep: true,
immediate: true
}
}, },
activated() { activated() {
this.loadLayout().then(json => { this.loadLayout().then(json => {
@ -303,8 +302,16 @@ export default {
// }, // },
// }); // });
}, },
deactivated() {
this.graph.dispose();
this.$nextTick(() => {
this.resetLayout();
this.graph = null;
})
},
computed: {}, computed: {},
methods: { methods: {
initGraph(json) { initGraph(json) {
const graph = new Graph({ const graph = new Graph({
container: this.$refs.panel, container: this.$refs.panel,
@ -312,11 +319,96 @@ export default {
size: 10, size: 10,
visible: true, visible: true,
}, },
history: true history: true,
selecting: {
className: 'my-select'
},
connecting: {
snap: true,
allowBlank: false,
allowLoop: false,
allowNode: false,
allowPort: true,
allowEdge: false,
},
scroller: {
enabled: true,
pannable: true,
cursor: 'grab'
},
mousewheel: {
enabled: true,
modifiers: ['ctrl', 'meta']
}
}); });
graph.fromJSON(json)
graph.fromJSON(json)
this.graph = graph; this.graph = graph;
this.$nextTick(() => {
this.registerGraphEvents();
})
},
registerGraphEvents() {
const reset = () => {
const nodes = this.graph.getNodes();
const edges = this.graph.getEdges();
this.currentDet = null;
nodes.forEach(node => {
node.attr('container/stroke', '#ccc');
});
edges.forEach(edge => {
edge.attr('line/stroke', '#ccc')
})
}
this.graph.on('node:click', ({ e, x, y, node, view }) => {
reset();
node.attr('container/stroke', '#0b58ff');
const { detId, detName, detDesc, processId, sectionName } = node.attrs;
this.currentDet = {}
this.$set(this.currentDet, 'detId', detId.text)
this.$set(this.currentDet, 'detName', detName.text)
this.$set(this.currentDet, 'detDesc', detDesc.text)
this.$set(this.currentDet, 'flowId', processId.text)
this.$set(this.currentDet, 'sectionName', sectionName.text)
});
this.graph.on('edge:click', ({ e, x, y, edge, view }) => {
// console.log('edge clicked!', edge)
reset();
edge.attr('line/stroke', '#0b58ff')
});
this.graph.on('blank:click', ({ e, x, y }) => {
reset();
});
this.graph.on('node:mouseenter', ({ node }) => {
node.addTools({
name: 'button-remove',
args: {
x: '100%',
y: 0,
offset: { x: 0, y: 0 },
onClick: ({ e, cell, view }) => {
this.$confirm(
'确定删除这个工序吗?',
'提示',
{
confirmButtonText: '确定',
cancelButtonText: '取消',
type: 'warning'
}
).then(() => {
view.cell.remove()
}).catch(err => {
return;
})
}
}
})
});
this.graph.on('node:mouseleave', ({ node }) => {
node.removeTools();
})
}, },
resetLayout() { resetLayout() {
@ -356,6 +448,7 @@ export default {
async handleUpdateLayout() { async handleUpdateLayout() {
this.layout.content = JSON.stringify(this.graph.toJSON()); this.layout.content = JSON.stringify(this.graph.toJSON());
let code, data; let code, data;
console.table([this.layout, this.$route.params.id])
// //
if (this.layout.id) { if (this.layout.id) {
({ code, data } = await this.put(this.layout)); ({ code, data } = await this.put(this.layout));
@ -501,4 +594,8 @@ export default {
.x6-widget-selection-selected { .x6-widget-selection-selected {
border: 1px solid red; border: 1px solid red;
} }
.my-select {
border: 1px solid red;
}
</style> </style>

View File

@ -1,11 +1,27 @@
import { Node, ObjectExt } from '@antv/x6'; import { Node, ObjectExt, Shape } from '@antv/x6';
import { IdToName } from '@/utils' import { IdToName } from '@/utils'
import cache from '@/utils/cache' import cache from '@/utils/cache'
import axios from '@/utils/request' import axios from '@/utils/request'
import { v4 } from 'uuid'
Shape.Edge.config({
attrs: {
line: {
stroke: '#ccc',
strokeWidth: 1,
targetMarker: {
name: 'block',
width: 1,
height: 1
},
},
}
})
export default class ProcessNode extends Node { } export default class ProcessNode extends Node { }
ProcessNode.config({ ProcessNode.config({
width: 240, width: 200,
height: 100, height: 100,
markup: [ markup: [
{ {
@ -68,6 +84,39 @@ ProcessNode.config({
}, },
}, },
], ],
attrs: {
line: {
fill: 'red'
}
},
ports: {
groups: {
in: {
position: 'left',
attrs: {
circle: {
r: 2,
magnet: true,
stroke: '#0b58ff',
strokeWidth: 1,
fill: '#0b58ff'
}
}
},
out: {
position: 'right',
attrs: {
circle: {
r: 2,
magnet: true,
stroke: '#0b58ff',
strokeWidth: 1,
fill: '#0b58ff'
}
}
}
}
},
propHooks(metadata) { propHooks(metadata) {
const { detId, detName, detDesc, sectionName, processId, ...others } = metadata; const { detId, detName, detDesc, sectionName, processId, ...others } = metadata;
// debugger; // debugger;
@ -94,7 +143,6 @@ async function getSectionFrom(sectionId) {
} }
} }
); );
debugger;
return IdToName(sectionId, sectionList); return IdToName(sectionId, sectionList);
} }
@ -109,7 +157,11 @@ export async function createProcessNode({ flowId, id, name, sectionId, remark })
detDesc: remark, // 工序说明 detDesc: remark, // 工序说明
processId: flowId, // 工艺ID processId: flowId, // 工艺ID
detId: id, // 工序ID detId: id, // 工序ID
tools: [{ name: 'button-remove' }], tools: [],
ports: [
{ id: v4(), group: 'in' },
{ id: v4(), group: 'out' },
]
}; };
} }

View File

@ -8,8 +8,8 @@
<template> <template>
<div class="app-container process-flow-view"> <div class="app-container process-flow-view">
<ProcessInfo /> <ProcessInfo />
<ProcessDetail style="margin-top: 16px" /> <ProcessDetail style="margin-top: 16px" @det-selected="handleDetSelected" />
<ProcessBomList style="margin-top: 16px" /> <ProcessBomList style="margin-top: 16px" :current-det="currentDet" />
</div> </div>
</template> </template>
@ -25,6 +25,7 @@ export default {
data() { data() {
return { return {
flowId: null, flowId: null,
currentDet: null
}; };
}, },
provide() { provide() {
@ -40,7 +41,14 @@ export default {
this.flowId = this.$route.params.id; this.flowId = this.$route.params.id;
}, },
computed: {}, computed: {},
methods: {}, methods: {
handleDetSelected(det) {
if (det != null) {
this.currentDet = { ...det }
}
else this.currentDet = null;
}
},
}; };
</script> </script>

16469
yarn.lock

File diff suppressed because it is too large Load Diff