簡體   English   中英

如何在力有向圖中繪制線/邊?

[英]how to draw lines/edges in a force directed graph?

我正在嘗試使用 d3.js 為數據集實現強制有向圖。我的代碼輸出節點,作為頁面頂部的小點,而邊緣無法繪制。如果鏈接被排除在模擬之外,節點將被正確繪制,任何關於我可能做錯的地方的提示都會有所幫助!

代碼筆鏈接

數據集:

{ nodes": [
        { "country": "East Timor", "code": "tl" },
        { "country": "Canada", "code": "ca" },
        { "country": "Turkmenistan", "code": "tm" },
        { "country": "United States of America", "code": "us" },
        { "country": "Lithuania", "code": "lt" },
        { "country": "Cambodia", "code": "kh" },
        { "country": "Ethiopia", "code": "et" },
        { "country": "Swaziland", "code": "sz" },
        ],
"links": [
        { "target": 66, "source": 0 },
        { "target": 3, "source": 1 },
        { "target": 100, "source": 2 },
        { "target": 40, "source": 2 },
        { "target": 125, "source": 2 },
        { "target": 147, "source": 2 },
        { "target": 159, "source": 3 },
        { "target": 18, "source": 3 },
        }


let request = new XMLHttpRequest();
request.addEventListener("load", loaded);

function loaded() {
  const data = JSON.parse(request.responseText);

  var nodes = data.nodes;
  var links = data.links;

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


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

  // creates lines in graph,
  var link = svg
  .append("g")
  .attr("class", "links")
  .selectAll("line")
  .data(links)
  .enter()
  .append("line");


  var node = svg
  .append("g")
  .attr("class", "nodes")
  .selectAll("circle")
  //pass node data
  .data(nodes)

  .enter()
  .append("circle")
  .attr("r", 5)

  .attr("fill", "red")

  .call(
    d3
    .drag()
    .on("start", dragstarted)
    .on("drag", dragged)
    .on("end", dragended)
  );

  simulation
  // pass nodes,on tick call function ticked
    .nodes(nodes)
    .on("tick", ticked);
  // pass links
  simulation.force("link").links(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;
  }
}
request.open(
  "GET",
  "https://www.cs.mun.ca/~h65ped/Public/country%20data%20for%20force%20directed%20graph/countries.json",
  true
);
request.send(null);

看看你的links數組:

"links": [
    { "target": 66, "source": 0 },
    { "target": 3, "source": 1 },
    { "target": 100, "source": 2 },
    //etc..

如您所見,對於目標和來源都沒有國家作為價值。 鏈接改為使用節點的索引

因此,這...

.force("link", d3.forceLink().id(function(d) {
    return d.country;
}));

... 是錯的。 只需刪除id

.force("link", d3.forceLink());

這是更新的 Codepen: https ://codepen.io/anon/pen/NwKvbg ? editors = 0010

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM