0

I am using the force layout example here

I need to add labels to the nodes. All examples I have seen use something like this:

node.append("text")
  .attr("dx", 12)
  .attr("dy", ".35em")
  .text(function(d) { return d.name });

But this works when there is a function being called on local data such as:

d3.json("graph.json", function(error, json) {

But in my example the data is all client side and thus does not require d3.json to pass over it. How can I add labels to each node in this scenario? Below is the code I am using:

<body>
<script src="//d3js.org/d3.v3.min.js"></script>
<script>

// set a width and height for our SVG
var width = 1000,
height = 800;

// setup links
var links = [
{ source: 'Baratheon', target:'Lannister' },
{ source: 'Baratheon', target:'Stark' },
{ source: 'Lannister', target:'Stark' },
{ source: 'Stark', target:'Bolton' },
];

// create empty nodes array
var nodes = {};

// compute nodes from links data
links.forEach(function(link) {
    link.source = nodes[link.source] ||
        (nodes[link.source] = {name: link.source});
    link.target = nodes[link.target] ||
        (nodes[link.target] = {name: link.target});
});


// add a SVG to the body for our viz
var svg=d3.select('body').append('svg')
    .attr('width', width)
    .attr('height', height);

// use the force
var force = d3.layout.force()
    .size([width, height])
    .nodes(d3.values(nodes))
    .links(links)
    .on("tick", tick)
    .linkDistance(300)
    .start();

// add links
var link = svg.selectAll('.link')
    .data(links)
    .enter().append('line')
    .attr('class', 'link');

// add nodes
var node = svg.selectAll('.node')
    .data(force.nodes())
    .enter().append('circle')
    .attr('class', 'node')
    .attr('r', width * 0.01);


// what to do
function tick(e) {

    node.attr('cx', function(d) { return d.x; })
        .attr('cy', function(d) { return d.y; })
        .call(force.drag);

    link.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>
Cybernetic
  • 12,628
  • 16
  • 93
  • 132

1 Answers1

0

The example of labeling you cited works because each node is bound to an object by the .data() method. Each one of these objects has a name property that contains the label for the node.

In your code, you already have this set up! Your nodes are bound to the force.nodes() array of objects, whose children all have name properties. All you have to do is call node.text(function(d) { return d.name }).

By default, these labels will not be visible. See this question for ideas on how to display node labels.