2013-07-19 2 views
2

프로젝트에서 나는 노드 추가 버튼을 클릭 할 때 동적으로 cicrles를 추가하고이 원을 화살표로 연결하려고합니다. 그러나 서클을 연결하면 서클의 라벨이 서클과 함께 움직이지 않습니다. 코드는 다음과 같습니다.d3.js 노드와 레이블을 함께 이동

JS 바이올린 링크 :

는이 문제를 어떻게 해결할 수 http://jsfiddle.net/pinargocebe/kEhes/3/? 사전에

감사합니다 ..

<!DOCTYPE composition PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" 
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> 
<ui:composition xmlns="http://www.w3.org/1999/xhtml" 
xmlns:s="http://jboss.com/products/seam/taglib" 
xmlns:ui="http://java.sun.com/jsf/facelets" 
xmlns:f="http://java.sun.com/jsf/core" 
xmlns:h="http://java.sun.com/jsf/html" 
xmlns:a4j="http://richfaces.org/a4j" 
xmlns:rich="http://richfaces.org/rich" template="layout/template.xhtml"> 
<ui:define name="body"> 
    <a4j:commandButton value="Add Node" onclick="mousedown();"> 
    </a4j:commandButton> 
    <div id="activationGraphDiv" style="width: 960px; height: 500px"> 
    </div> 
    <rich:popupPanel id="addnode" width="100" height="100"> 
     <h:form> 
      <h:outputLabel value="http://add.mode.deneme#relation" /> 
      <a4j:commandButton value="OK" 
       onclick="#{rich:component('addnode')}.hide()"> 
</a4j:commandButton> 
     </h:form> 
    </rich:popupPanel> 
    <style type="text/css"> 
rect { 
fill: none; 
pointer-events: all; 
} 

.node { 
fill: white; 
stroke: pink; 
stroke-width: 2; 
color: black; 
} 

.cursor { 
fill: none; 
pointer-events: none; 
} 

.link { 
stroke: #999; 
} 

path,line { 
stroke: silver; 
stroke-width: 2; 
fill: none; 
} 
</style> 
    <script src="jquery.pack.js"></script> 
    <script type="text/javascript"> 

var width = 960, 
    height = 500; 

var sourceNode,targetNode; 

var fill = d3.scale.category20(); 

var force = d3.layout.force() 
    .size([width, height]) 
    .gravity(.05) 
.charge(-450) 
.linkDistance(200) 
    .on("tick", tick); 

var svg = d3.select("#activationGraphDiv").append("svg") 
.attr("width", width) 
.attr("height", height) 
.on("mousemove", mousemove); 

svg.append("rect") 
.attr("width", width) 
.attr("height", height); 

// Draw Lines 
var container = $('#activationGraphDiv'); 

var line = d3.svg.line() 
      .x(function(d) { return d[0]; }) 
      .y(function(d) { return d[1]; }) 
      .interpolate('linear'); 
svg 
.append('svg:path') 
.style('stroke-width', 1) 
.style('stroke', 'silver') 
.style('fill', 'rgba(120, 220, 54, 0.2)'); 

var lineData = []; 

var redrawLine = function() { 
var svgLines = svg.selectAll('path.my-lines') 
        .data(lineData) 
        .remove(); 
svgLines.enter() 
     .append('path') 
     .attr('d', line(lineData)) 
     .attr('class', 'my-lines'); 

svgLines.exit() 
     .remove(); 
}; 

var mouseIsDown = false; 
container.on('mousemove', function(e) { 
    if (mouseIsDown &amp;&amp; sourceNode!=null) { 
     lineData[1] = [e.offsetX, e.offsetY]; 
     redrawLine();  
    }}) 
    .on('mouseup',function(){ 
     sourceNode=null; 
     targetNode=null; 
     mouseIsDown=false; 
     svg.selectAll('path.my-lines') 
      .data(lineData) 
      .remove(); 
    }); 


var nodes = force.nodes(), 
links = force.links(), 
node=svg.selectAll(".node"), 
link = svg.selectAll(".link"), 
text=svg.selectAll(".nodetext"); 

var cursor = svg.append("circle") 
.attr("r", 0) 
.attr("class", "cursor"); 

restart(); 

function mousemove() { 
    cursor.attr("transform", "translate(" + d3.mouse(this) + ")"); 
} 

var i=0; 

function mousedown() { 
//x coordinate of node.. 
var x=document.getElementById("activationGraphDiv").offsetLeft; 

//y coordinate of node.. 
var y=document.getElementById("activationGraphDiv").offsetTop; 
var node = {x:x, y: y, name: i}, 
    n = nodes.push(node); 
    i++; 
    console.log("node name: "+node.name); 
    restart(); 
    sourceNode=null 
    targetNode=null; 
    mouseIsDown=false; 
} 

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

text.attr("x", function(d) {return d.x; }) 
.attr("y", function(d) { return d.y; }); 
} 
svg.append("svg:defs").selectAll("marker") 
.data(["arrow"]) 
.enter().append("svg:marker") 
.attr("id", String) 
.attr("viewBox", "0 -5 10 10") 
.attr("refX", 10) 
.attr("refY", 0) 
.attr("markerWidth", 10) 
.attr("markerHeight", 10) 
.attr("orient", "auto") 
.append("svg:path") 
.attr("d", "M0,-5L10,0L0,5"); 

function restart() { 
    node = node.data(nodes); 

node.enter().insert("circle") 
    .attr("class", "node") 
    .attr("id",function(d){return d.name;}) 
    .attr("r", 15); 

//Insert text to node.. 
text=svg.selectAll(".nodetext") 
    .data(nodes) 
    .enter() 
    .append("text") 
    .attr("class","nodetext") 
    .text(function(d){return d.name;}) 
    .attr("dx", 13) 
    .attr("dy", ".35em"); 

    d3.selectAll(".node").on("mousedown",function(d){ 
    if(sourceNode==null){ 
     mouseIsDown = true; 
     lineData[0] = [d3.mouse(this)[0], d3.mouse(this)[1]]; 
     redrawLine(); 
     sourceNode=d.index; 
     console.log("Source node: "+d.name); 
    } 
}) 
    .on("mouseup",function(d){ 
    if(targetNode==null &amp;&amp; sourceNode!=null &amp;&amp; mouseIsDown){ 
     targetNode=d.index; 
     links.push({source: sourceNode, target: targetNode}); 
     lineData[1] = [d3.mouse(this)[0], d3.mouse(this)[1]]; 
     redrawLine(); 
     console.log("Target node: "+d.name); 
     sourceNode=null; 
     targetNode=null; 
     mouseIsDown = false; 
     svg.selectAll('path.my-lines') 
      .data(lineData) 
      .remove(); 
     restart(); 
    } 
    }); 

link = link.data(links); 

link.enter().insert("line") 
     .attr("class", "link"); 
link.attr("marker-end", "url(#arrow)"); 
force.start(); 
} 
</script> 
</ui:define> 
</ui:composition> 
+0

이 PLZ UR 코드에 대한 jsfiddle을 만들 수 있습니다 – iJade

+0

깜빡 죄송합니다 이. JSFiddle 링크입니다. http://jsfiddle.net/pinargocebe/kEhes/3/ –

답변

2

정식 솔루션 그룹으로 텍스트와 동그라미를 넣어하는 것입니다. force.tick() 텍스트와 노드를 개별적으로 이동하는 대신 그룹을 변환하기 만하면됩니다.

그래서이 : 여기

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

체크 아웃 예 :

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

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

이되다

http://bl.ocks.org/mbostock/950642