scr-web/src/components/Topology/index.vue

173 lines
4.1 KiB
Vue
Raw Blame History

This file contains ambiguous Unicode characters!

This file contains ambiguous Unicode characters that may be confused with others in your current locale. If your use case is intentional and legitimate, you can safely ignore this warning. Use the Escape button to highlight these characters.

<template>
<div id="mountNode" style="height: 100%; width: 100%"></div>
</template>
<script>
import G6 from '@antv/g6';
import registerDefault from './registerDefault';
export default {
props: {
defaultEdgeType: {
type: String
},
defaultNodeType: {
type: String,
default: 'circle'
},
// 拓扑的配置
options: {
type: Object,
default: function() {
return {};
}
},
data: {
type: Object,
default: function() {
return {};
}
},
layout: {
type: Object
}
},
data() {
return {
graph: null,
currentLayout: ''
};
},
created() {
registerDefault(G6, this.defaultNodeType, this.defaultEdgeType);
},
mounted() {
this.initGraph();
window.addEventListener('resize', this.changeSize);
},
beforeUnmount() {
window.removeEventListener('resize', this.changeSize);
},
watch: {
data() {
if (this.graph) {
this.graph.changeData(this.data);
}
}
},
methods: {
initGraph() {
const target = document.getElementById('mountNode');
// const minimap = new G6.Minimap(this.minimapConfig);
// 实例化 grid 插件
const options = {
// plugins: [grid], // 将 minimap 实例配置到图上
modes: {
default: [
'drag-canvas',
'zoom-canvas',
'drag-node',
'drag-combo'
// {
// type: 'tooltip', // 提示框
// formatText:
// this.tipFormat ||
// function(model) {
// // 提示框文本内容
// const text = [];
// text.push(`<div>${model.label}</div>`);
// return text.join('');
// },
// offset: 60
// }
] // 允许拖拽画布、放缩画布、拖拽节点
},
// fitCenter: true,
container: 'mountNode', // String | HTMLElement必须在 Step 1 中创建的容器 id 或容器本身
width: target.offsetWidth, // Number必须图的宽度
height: target.offsetHeight, // Number必须图的高度
defaultNode: {
type: 'image',
size: [60],
color: '#ffffff',
style: {
fill: '#9EC9FF',
lineWidth: 1
},
labelCfg: {
style: {
fill: '#ffffff',
fontSize: 12
},
position: 'bottom'
}
},
defaultEdge: {
type: 'circle-running',
style: {
stroke: '#7ECEF4',
lineWidth: 2
}
},
groupByTypes: false,
defaultCombo: {
type: 'rect',
padding: [40, 40, 40, 40],
style: {
fill: '#112A51',
stroke: '#112A51',
radius: 4
},
labelCfg: {
refY: 20,
refX: 20,
position: 'top',
style: {
fill: '#ffffff',
fontSize: 15
}
}
},
layout: this.layout
};
const graph = new G6.Graph(options);
this.graph = graph;
graph.read(this.data);
this.bindEvent();
},
save () {
const data = this.graph.save();
return data;
},
itemClick(evt, type) {
const { clientX, clientY, item } = evt;
const params = {
x: clientX, y: clientY, item: item.getModel()
}
this.$emit(type, params)
},
bindEvent() {
this.graph.on('node:click', evt => {
this.itemClick(evt, 'nodeClick')
});
this.graph.on('edge:click', evt => {
this.itemClick(evt, 'edgeClick')
});
this.graph.on('canvas:click', evt => {
this.$emit('canvasClick')
});
},
changeSize() {
setTimeout(() => {
const target = document.getElementById('mountNode');
const width = target.offsetWidth;
const height = target.offsetHeight;
this.graph.changeSize(width, height);
}, 1000);
}
}
};
</script>
<style lang="scss">
</style>