Newer
Older
indexation / public / js / force-directed-graph.js
@kieffer kieffer on 1 Mar 2017 4 KB v1
"use strict";

(function() {
  var loc = window.location.pathname,
    dir = loc.substring(0, loc.lastIndexOf('/'));

  var svg = d3.select("svg"),
    width = +svg.attr("width"),
    height = +svg.attr("height");

  var color = d3.scaleOrdinal(d3.schemeCategory20);

  var simulation = d3.forceSimulation()
    .force("link", d3.forceLink().id(function(d) {
      return d.id;
    }))
    .force("charge", d3.forceManyBody())
    .force("center", d3.forceCenter(width / 2, height / 2));


  d3.json(dir + "data/out/corpus/graph.json", function(error, graph) {
    if (error) throw error;

    // var numCommunities = 128;

    // graph.nodes.forEach(function(node) {
    //   node.communities = [];
    //   node.communityBuffer = [];
    //   for (var community = 0; community < numCommunities; community++) {
    //     // Initialize with a small Exponential variate
    //     node.communities[community] = 0.01 * -Math.log(Math.random());
    //     node.communityBuffer[community] = 0.0;
    //   }
    // });

    // var communitySums = [];

    // for (var iteration = 0; iteration < 20; iteration++) {
    //   for (var community = 0; community < numCommunities; community++) {
    //     communitySums[community] = 0.0;
    //   }

    //   // Estimate community memberships for each edge
    //   graph.links.forEach(function(edge) {
    //     var sourceCommunities = graph.nodes[edge.source].communities;
    //     var targetCommunities = graph.nodes[edge.target].communities;
    //     var distribution = [];

    //     // Multiply the two community membership vectors
    //     for (var community = 0; community < numCommunities; community++) {
    //       distribution[community] = sourceCommunities[community] * targetCommunities[community];
    //     }

    //     // Normalize and add to the gradient
    //     var normalizer = edge.value / d3.sum(distribution);
    //     for (var community = 0; community < numCommunities; community++) {
    //       distribution[community] *= normalizer;
    //       communitySums[community] += distribution[community];
    //       graph.nodes[edge.source].communityBuffer[community] += distribution[community];
    //       graph.nodes[edge.target].communityBuffer[community] += distribution[community];
    //     }
    //   });

    //   // We need to divide each node value by the square root of the community sum.
    //   var communityNormalizers = []
    //   for (var community = 0; community < numCommunities; community++) {
    //     communityNormalizers[community] = 1.0 / Math.sqrt(communitySums[community]);
    //   }

    //   // Update parameters and clear the buffer.
    //   graph.nodes.forEach(function(node) {
    //     for (var community = 0; community < numCommunities; community++) {
    //       node.communities[community] = node.communityBuffer[community] * communityNormalizers[community];
    //       node.communityBuffer[community] = 0.0;
    //     }
    //     node.community = 0;
    //     for (var community = 0; community < numCommunities; community++) {
    //       node.community = (node.communities[node.community] < node.communities[community]) ? community : node.community;
    //     }
    //   });
    // }

    var link = svg.append("g")
      .attr("class", "links")
      .selectAll("line")
      .data(graph.links)
      .enter().append("line")
      .attr("stroke-width", function(d) {
        return d.value;
      })

    var node = svg.append("g")
      .attr("class", "nodes")
      .selectAll("circle")
      .data(graph.nodes)
      .enter().append("circle")
      .attr("r", function(d) {
        return 5;
        // return 10 * d.specificity;
      })
      .attr("fill", function(d) {
        return color(d.group);
      })
      .call(d3.drag()
        .on("start", dragstarted)
        .on("drag", dragged)
        .on("end", dragended));

    node.append("title")
      .text(function(d) {
        return d.istex + '\n' + d.value;
      });

    link.append("title")
      .text(function(d) {
        return d.value;
      });

    simulation
      .nodes(graph.nodes)
      .on("tick", ticked);

    simulation.force("link")
      .links(graph.links);

    function ticked() {
      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;
        });

      node
        .attr("cx", function(d) {
          return d.x;
        })
        .attr("cy", function(d) {
          return d.y;
        });
    }
  });

  function dragstarted(d) {
    if (!d3.event.active) simulation.alphaTarget(0.3).restart();
    d.fx = d.x;
    d.fy = d.y;
  }

  function dragged(d) {
    d.fx = d3.event.x;
    d.fy = d3.event.y;
  }

  function dragended(d) {
    if (!d3.event.active) simulation.alphaTarget(0);
    d.fx = null;
    d.fy = null;
  }

})();