分层布局中的节点可以使用某些功能进行排序吗?
Can nodes in a hierarchichal layout be ordered with some function?
给定一个有向图,其中一个值与每个节点相关联,我们如何使用 vis.js 来显示根据该值排序的节点?例如,相同深度的所有节点从左到右从“最有价值”到“最不有价值”显示
在下面的示例中,节点 5 到 8 是节点 4 的子节点,并且按照 edges
的索引而不是 [=15= 的索引顺序从左到右添加] 每个节点。
所以我们可以重新排列 edges
以在 nodes
:
中对 from
节点的 value
进行降序排序
function rank(edges) {
// get a copy of edges
let edges2 = edges.map(function(edge) {return Object.assign({}, edge);});
// sort edges by node value
edges2.sort(function(a, b) {
let nodeA = nodes.find(function(n) {return n.id == a.from});
let nodeB = nodes.find(function(n) {return n.id == b.from});
return nodeB.value - nodeA.value;
});
return edges2;
}
未排序和按此函数排序的工作示例:
const nodes = [
{id: 1, level: 0, value: 1, label: "1"},
{id: 2, level: 1, value: 1, label: "2"},
{id: 3, level: 1, value: 2, label: "3"},
{id: 4, level: 2, value: 1, label: "4"},
{id: 5, level: 3, value: 1, label: "5"},
{id: 6, level: 3, value: 2, label: "6"},
{id: 7, level: 3, value: 3, label: "7"},
{id: 8, level: 3, value: 4, label: "8"}
];
const edges = [
{from: 2, to: 1},
{from: 3, to: 1},
{from: 4, to: 3},
{from: 5, to: 4},
{from: 6, to: 4},
{from: 7, to: 4},
{from: 8, to: 4}
];
const options = {
nodes: {
shape: "dot"
},
edges: {
smooth: {
type: "cubicBezier",
forceDirection: "vertical",
roundness: 0.4
}
},
layout: {
hierarchical: {
direction: "UD",
},
},
physics: false
}
// unranked
const data1 = {
nodes: nodes,
edges: edges
}
const container1 = document.getElementById("network1");
const network1 = new vis.Network(container1, data1, options);
// ranked
const data2 = {
nodes: nodes,
edges: rank(edges)
}
function rank(edges) {
// get a copy of edges
let edges2 = edges.map(function(edge) {return Object.assign({}, edge);});
// sort edges by node value
edges2.sort(function(a, b) {
let nodeA = nodes.find(function(n) {return n.id == a.from});
let nodeB = nodes.find(function(n) {return n.id == b.from});
return nodeB.value - nodeA.value;
});
return edges2;
}
const container2 = document.getElementById("network2");
const network2 = new vis.Network(container2, data2, options);
#wrapper {
display: flex;
}
#network1 {
flex: 0 0 50%;
height: 180px;
border: 1px solid #000;
}
#network2 {
flex: 1;
height: 180px;
border: 1px solid #000;
}
<script type="text/javascript" src="https://unpkg.com/vis-network@9.0.4/dist/vis-network.min.js"></script>
<div id="wrapper">
<div id="network1"></div>
<div id="network2"></div>
</div>
给定一个有向图,其中一个值与每个节点相关联,我们如何使用 vis.js 来显示根据该值排序的节点?例如,相同深度的所有节点从左到右从“最有价值”到“最不有价值”显示
在下面的示例中,节点 5 到 8 是节点 4 的子节点,并且按照 edges
的索引而不是 [=15= 的索引顺序从左到右添加] 每个节点。
所以我们可以重新排列 edges
以在 nodes
:
from
节点的 value
进行降序排序
function rank(edges) {
// get a copy of edges
let edges2 = edges.map(function(edge) {return Object.assign({}, edge);});
// sort edges by node value
edges2.sort(function(a, b) {
let nodeA = nodes.find(function(n) {return n.id == a.from});
let nodeB = nodes.find(function(n) {return n.id == b.from});
return nodeB.value - nodeA.value;
});
return edges2;
}
未排序和按此函数排序的工作示例:
const nodes = [
{id: 1, level: 0, value: 1, label: "1"},
{id: 2, level: 1, value: 1, label: "2"},
{id: 3, level: 1, value: 2, label: "3"},
{id: 4, level: 2, value: 1, label: "4"},
{id: 5, level: 3, value: 1, label: "5"},
{id: 6, level: 3, value: 2, label: "6"},
{id: 7, level: 3, value: 3, label: "7"},
{id: 8, level: 3, value: 4, label: "8"}
];
const edges = [
{from: 2, to: 1},
{from: 3, to: 1},
{from: 4, to: 3},
{from: 5, to: 4},
{from: 6, to: 4},
{from: 7, to: 4},
{from: 8, to: 4}
];
const options = {
nodes: {
shape: "dot"
},
edges: {
smooth: {
type: "cubicBezier",
forceDirection: "vertical",
roundness: 0.4
}
},
layout: {
hierarchical: {
direction: "UD",
},
},
physics: false
}
// unranked
const data1 = {
nodes: nodes,
edges: edges
}
const container1 = document.getElementById("network1");
const network1 = new vis.Network(container1, data1, options);
// ranked
const data2 = {
nodes: nodes,
edges: rank(edges)
}
function rank(edges) {
// get a copy of edges
let edges2 = edges.map(function(edge) {return Object.assign({}, edge);});
// sort edges by node value
edges2.sort(function(a, b) {
let nodeA = nodes.find(function(n) {return n.id == a.from});
let nodeB = nodes.find(function(n) {return n.id == b.from});
return nodeB.value - nodeA.value;
});
return edges2;
}
const container2 = document.getElementById("network2");
const network2 = new vis.Network(container2, data2, options);
#wrapper {
display: flex;
}
#network1 {
flex: 0 0 50%;
height: 180px;
border: 1px solid #000;
}
#network2 {
flex: 1;
height: 180px;
border: 1px solid #000;
}
<script type="text/javascript" src="https://unpkg.com/vis-network@9.0.4/dist/vis-network.min.js"></script>
<div id="wrapper">
<div id="network1"></div>
<div id="network2"></div>
</div>