g6/packages/site/examples/net/layoutMechanism/demo/customBigraph.js
2023-02-02 10:31:36 +08:00

250 lines
5.1 KiB
JavaScript

import G6 from '@antv/g6';
const data = {
nodes: [
{
id: '0',
label: 'A',
cluster: 'part1',
},
{
id: '1',
label: 'B',
cluster: 'part1',
},
{
id: '2',
label: 'C',
cluster: 'part1',
},
{
id: '3',
label: 'D',
cluster: 'part1',
},
{
id: '4',
label: 'E',
cluster: 'part1',
},
{
id: '5',
label: 'F',
cluster: 'part1',
},
{
id: '6',
label: 'a',
cluster: 'part2',
},
{
id: '7',
label: 'b',
cluster: 'part2',
},
{
id: '8',
label: 'c',
cluster: 'part2',
},
{
id: '9',
label: 'd',
cluster: 'part2',
},
],
edges: [
{
source: '0',
target: '6',
},
{
source: '0',
target: '7',
},
{
source: '0',
target: '9',
},
{
source: '1',
target: '6',
},
{
source: '1',
target: '9',
},
{
source: '1',
target: '7',
},
{
source: '2',
target: '8',
},
{
source: '2',
target: '9',
},
{
source: '2',
target: '6',
},
{
source: '3',
target: '8',
},
{
source: '4',
target: '6',
},
{
source: '4',
target: '7',
},
{
source: '5',
target: '9',
},
],
};
G6.registerLayout('bigraph-layout', {
execute() {
const self = this;
const center = self.center || [0, 0];
const biSep = self.biSep || 100;
const nodeSep = self.nodeSep || 20;
const nodeSize = self.nodeSize || 20;
const direction = self.direction || 'horizontal';
let part1Pos = 0;
let part2Pos = 0;
if (direction === 'horizontal') {
part1Pos = center[0] - biSep / 2;
part2Pos = center[0] + biSep / 2;
}
const { nodes, edges } = self;
const part1Nodes = [];
const part2Nodes = [];
const part1NodeMap = new Map();
const part2NodeMap = new Map();
// separate the nodes and init the positions
nodes.forEach(function (node, i) {
if (node.cluster === 'part1') {
part1Nodes.push(node);
part1NodeMap.set(node.id, i);
} else {
part2Nodes.push(node);
part2NodeMap.set(node.id, i);
}
});
// order the part1 node
part1Nodes.forEach(function (p1n) {
let index = 0;
let adjCount = 0;
edges.forEach(function (edge) {
const sourceId = edge.source;
const targetId = edge.target;
if (sourceId === p1n.id) {
index += part2NodeMap.get(targetId);
adjCount += 1;
} else if (targetId === p1n.id) {
index += part2NodeMap.get(sourceId);
adjCount += 1;
}
});
index /= adjCount;
p1n.index = index;
});
part1Nodes.sort(function (a, b) {
return a.index - b.index;
});
part2Nodes.forEach(function (p2n) {
let index = 0;
let adjCount = 0;
edges.forEach(function (edge) {
const sourceId = edge.source;
const targetId = edge.target;
if (sourceId === p2n.id) {
index += part1NodeMap.get(targetId);
adjCount += 1;
} else if (targetId === p2n.id) {
index += part1NodeMap.get(sourceId);
adjCount += 1;
}
});
index /= adjCount;
p2n.index = index;
});
part2Nodes.sort(function (a, b) {
return a.index - b.index;
});
// place the nodes
const hLength = part1Nodes.length > part2Nodes.length ? part1Nodes.length : part2Nodes.length;
const height = hLength * (nodeSep + nodeSize);
let begin = center[1] - height / 2;
if (direction === 'vertical') {
begin = center[0] - height / 2;
}
part1Nodes.forEach(function (p1n, i) {
if (direction === 'horizontal') {
p1n.x = part1Pos;
p1n.y = begin + i * (nodeSep + nodeSize);
} else {
p1n.x = begin + i * (nodeSep + nodeSize);
p1n.y = part1Pos;
}
});
part2Nodes.forEach(function (p2n, i) {
if (direction === 'horizontal') {
p2n.x = part2Pos;
p2n.y = begin + i * (nodeSep + nodeSize);
} else {
p2n.x = begin + i * (nodeSep + nodeSize);
p2n.y = part2Pos;
}
});
},
});
const container = document.getElementById('container');
const width = container.scrollWidth;
const height = container.scrollHeight || 500;
const graph = new G6.Graph({
container: 'container',
width,
height,
layout: {
type: 'bigraph-layout',
biSep: 300,
nodeSep: 20,
nodeSize: 20,
},
animate: true,
defaultNode: {
size: 20,
style: {
fill: '#C6E5FF',
stroke: '#5B8FF9',
},
},
defaultEdge: {
size: 1,
color: '#e2e2e2',
},
modes: {
default: ['drag-canvas'],
},
});
graph.data(data);
graph.render();
if (typeof window !== 'undefined')
window.onresize = () => {
if (!graph || graph.get('destroyed')) return;
if (!container || !container.scrollWidth || !container.scrollHeight) return;
graph.changeSize(container.scrollWidth, container.scrollHeight);
};