2017-09-20 1 views
2

Ich habe versucht, die Menge der Animation in einem D3-Projekt, an dem ich arbeite, zu reduzieren.Minimieren/Begrenzen Animation Funktion in d3 Bibliothek

Bis jetzt habe ich versucht, verschiedene integrierte Funktionen zu verwenden, um die Kraft der Animation zu hemmen. Zum Beispiel alpha(.1) gravity(1) charge(-1000) obwohl einige dieser Funktionen keinen großen Unterschied zu machen scheinen.

Endergebnis: Ich möchte versuchen, den riesigen Bounce zu Beginn der Animation zu beseitigen. Ist das möglich?

Hier ist meine volle js Funktion:

// return data for relationships between database tables 
returnTableRelationshipData = function(){ 

    data = { 
     "nodes":[ 
      { 
      "platform":"Source DB", 
      "description":"RELATIONSHIPS BETWEEN BUSINESS REFERENCES", 
      "ingested":"No", 
      "tableId":"RELAC_REFER", 
      "level1":"DAEG", 
      "level2":"url", 
      "nodeId":0 
      }, 
      { 
      "platform":"Source DB", 
      // see jsfiddle for full data 
     ] 
    }; 

    //find the node index 
    function find(f){ 
     var i = -1 
     data.nodes.forEach(function(node, index){ 
      if(node.nodeId == f) 
       i = index; 
     }); 
     return i; 
    } 

    //set the source and target index 
    data.links.forEach(function(d){ 
     d.source = find(d.source); 
     d.target = find(d.target); 
    }) 
    // used to store the number of links between two nodes. 
    var mLinkNum = {}; 

    // sort links first 
    sortLinks();         

    // set up linkIndex and linkNumer, because it may possible multiple links share the same source and target node 
    setLinkIndexAndNum(); 

    // check that we don't have empty or null values 
    checkDataNotEmpty(); 

    var w = 600, 
     h = 500; 

    var force = d3.layout.force() 
     .nodes(data.nodes) 
     .links(data.links) 
     .alpha(.1) 
     .gravity(1) 
     //.distance(150) 
     .charge(-1000) 
     .size([w, h]) 
     .start(); 

    var svg = d3.select(".graphContainer").append("svg:svg") 
     .attr("width", w) 
     .attr("height", h); 

    var path = svg.append("svg:g") 
     .selectAll("path") 
     .data(force.links()) 
     .enter().append("line") 
     .attr("class", "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; 
     }); 

    var node_drag = d3.behavior.drag() 
     .on("dragstart", dragstart) 
     .on("drag", dragmove) 
     .on("dragend", dragend); 

    var circle = svg.append("svg:g") 
     .selectAll("circle") 
     .data(force.nodes()) 
     .enter().append("svg:circle") 
     .attr("r", 6) 
     .call(node_drag); 

    var text = svg.append("svg:g")         
     .selectAll("g") 
     .data(force.nodes()) 
     .enter().append("svg:g"); 

    text.append("svg:text") 
     .text(function(d){ return d.description; }); 

    /*circle.on("mousedown", function(d) { d.fixed = true; });*/ 

    force.on("tick", tick); 

    function tick() { 

     path.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; 
     }); 

     circle.attr("transform", function(d){ 
      return "translate(" + d.x + "," + d.y + ")"; 
     }); 

     text.attr("transform", function(d){ 
      return "translate(" + d.x + "," + d.y + ")"; 
     }); 
    } 

    function dragstart(d, i) { 
     force.stop(); // stops the force auto positioning before you start dragging 
    } 

    function dragmove(d, i) { 
     d.px += d3.event.dx; 
     d.py += d3.event.dy; 
     d.x += d3.event.dx; 
     d.y += d3.event.dy; 
     tick(); 
    } 

    function dragend(d, i) { 
     //nodes.fixed = true; // fix all nodes after single drag 
     d.fixed = true; // of course set the node to fixed so the force doesn't include the node in its auto positioning stuff 
     tick(); 
     force.resume(); 
    } 

    // sort the links by source, then target 
    function sortLinks(){ 
     if(data.links != null){       
      data.links.sort(function(a,b){ 
       if(a.source > b.source){ 
        return 1; 
       }else if(a.source < b.source){ 
        return -1; 
       }else{ 
        if(a.target > b.target){ 
         return 1; 
        }if(a.target < b.target){ 
         return -1; 
        }else{ 
         return 0; 
        } 
       } 
      }); 
     } 
    } 

    //any links with duplicate source and target get an incremented 'linknum' 
    function setLinkIndexAndNum(){        
     for(var i = 0; i < data.links.length; i++){ 
      if(i != 0 && 
       data.links[i].source == data.links[i-1].source && 
       data.links[i].target == data.links[i-1].target){ 
       data.links[i].linkindex = data.links[i-1].linkindex + 1; 
      }else{ 
       data.links[i].linkindex = 1; 
      }// save the total number of links between two nodes 
      if(mLinkNum[data.links[i].target + "," + data.links[i].source] !== undefined){ 
       mLinkNum[data.links[i].target + "," + data.links[i].source] = data.links[i].linkindex; 
      }else{ 
       mLinkNum[data.links[i].source + "," + data.links[i].target] = data.links[i].linkindex; 
      } 
     } 
    } 

    function checkDataNotEmpty(){ 
     data.links.forEach(function(link, index, list) { 
      if (typeof link.source === 'undefined') { 
       console.log('undefined link', data.nodes[link.source]); 
      } 
      if (typeof link.target === 'undefined') { 
       console.log('undefined source', data.nodes[link.target]); 
      } 
     }); 
    } 
} 

returnTableRelationshipData(); 

Link zu jsfiddle

Ich habe versucht, meinen ursprünglichen Code mit dem SO Frage here und jsbin here

ich es geschafft, verknüpft zu verschmelzen die posten unminified Bibliothek zu Pastebin und verknüpfen Sie es dann mit der jsfiddle, als Referenz hier ist die vollständige js-Bibliothek: Unminified d3 Library v3

Es sieht aus, als ob die Animation Funktionalität

var d3_ease_default = function() { return d3_identity; };

ich eine Menge dieser Funktionen Auskommen haben versucht, um die Linie 5807 beginnt, und die Animation erscheint unverändert zu laufen.

Ich weiß, das ist nicht die beste Frage, aber wenn jemand Erfahrung davon hat, würde ich es sehr zu schätzen wissen.

Außerdem bin ich glücklich, feste Knoten zu verwenden, aber ich denke, dass sie nur behoben werden können, nachdem die Kraftanimation abgeschlossen wurde.

Antwort

3

Einer der Gründe dieser großen Bounce ist, dass alle Knoten starten die Simulation an der gleichen Position.

Versuchen Sie, sie zu verbreiten:

data.nodes.forEach(function(node){ 
    node.x = 200 + Math.random()*200; 
    node.y = 150 + Math.random()*200; 
} 

Hier sind die magischen Zahlen 200 und 150 sind einfach w/2 und h/2 minus 100. Hier

ist die aktualisierte Geige: https://jsfiddle.net/nd8e5m9s/

+0

Oh, das sieht viel besser aus. Vielen Dank. – lharby

1

Sie die d3.layout auf dragend zwingen, dass es bis zu einem gewissen Punkt der Koordinaten zwingen und machen es abprallen, entfernen Sie, warum nicht, dass

function dragend(d, i) { 
    //nodes.fixed = true; // fix all nodes after single drag 
    d.fixed = true; // of course set the node to fixed so the force doesn't include the node in its auto positioning stuff 
    tick(); 
    //force.resume(); 
} 
+0

Danke. Das scheint die Knoten zu fixieren, sobald sie animiert sind. Ich möchte trotzdem den enormen Bounce zu Beginn der Animation reduzieren. – lharby

+0

Nur teilen .... ich denke, d3.layout.force, um es Bounce und animierte Größe Pfad zwischen Link und Knoten zu machen, wenn Sie nicht animieren wollen vielleicht können Sie d3.forceSimulation() und d3.forceLink, aber dafür case rought Lösung ist das Element zu verstecken, bevor voll geladen, oder schwer (aber immer noch) verwendet d3.interpolate aber IDK, wie es an Ihrem Fall anhängen – KEKUATAN