Skip to content

Instantly share code, notes, and snippets.

@karibot
Created Mar 30, 2019
Embed
What would you like to do?
D3 practice - Collapsible Force Layout
<html>
<head>
<meta charset="utf-8">
<title>D3 practice</title>
<meta name="viewport" content="width=device-width, initial-scale 1.0">
</head>
<body class="site-container">
<div class="site-content">
</div>
<script type="text/javascript" src="//ajax.googleapis.com/ajax/libs/jquery/1.12.4/jquery.min.js"></script>
<script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/d3/4.2.2/d3.min.js"></script>
<script type="text/javascript" src="links.js"></script>
<script>
$(document).ready(function() {
//Width and height
var w = 500;
var h = 300;
//const serverData is now imported from HTML at line 13 // links.js attached to this gist
let [nodes, edges] = serverData.reduce( (memo, item) => {
const [nodes, links] = memo;
const [source, target] = item;
let sourceIndex = nodes.indexOf(source);
let targetIndex = nodes.indexOf(target);
if (sourceIndex === -1) { nodes.push(source); sourceIndex = nodes.length-1; }
if (targetIndex === -1) { nodes.push(target); targetIndex = nodes.length-1; }
links.push({source: sourceIndex, target: targetIndex});
return memo;
}, [[], []]);
nodes = nodes.reduce( (memo, item) => {
memo.push({name: item});
return memo;
}, []);
console.log(nodes,edges);
//Original data
var dataset = {
nodes,
edges
};
//Initialize a default force layout, using the nodes and edges in dataset
var force = d3.forceSimulation()
.force('link', d3.forceLink())
.force("collide",d3.forceCollide(20).iterations(16) )
.force("charge", d3.forceManyBody(10))
.force("x", d3.forceX(w / 2))
.force("y", d3.forceY(h / 2))
.on("tick", tick);
var colors = d3.scaleOrdinal(d3.schemeCategory10);
//Create SVG element
var svg = d3.select("body")
.append("svg")
.attr("width", w)
.attr("height", h);
start();
function start() {
var nodeElements = svg.selectAll(".node")
.data(dataset.nodes, function(d){return d.id}).enter().append('g').attr('class', 'node');
var linkElements = svg.selectAll(".link")
.data(dataset.edges);
nodeElements
.append("circle")
.attr("r", 10)
.style("fill", function(d, i) {
return colors(0);
});
nodeElements.append('text')
.attr('font-size', 6)
.attr('text-anchor', 'middle')
.text(d => d.name);
linkElements.enter()
.insert("line", ".node")
.attr("class", "link")
.style("stroke", "#ccc")
.style("stroke-width", 1);
nodeElements.exit().remove();
linkElements.exit().remove();
force.nodes(dataset.nodes)
force.force("link").links(dataset.edges)
force.restart();
}
function tick() {
var nodeElements = svg.selectAll(".node");
var linkElements = svg.selectAll(".link");
// nodeElements.attr("cx", function(d,i) {return d.x; })
// .attr("cy", function(d) { return d.y; })
nodeElements.attr('transform', d => `translate(${d.x}, ${d.y})`)
linkElements.attr("x1", function(d) { return d.source.x; })
.attr("y1", function(d) { return d.source.y; })
.attr("x2", function(d) { return d.target.x; })
.attr("y2", function(d) { return d.target.y; });
}
});
</script>
</body>
</html>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment