I'm trying to create a link between two desired nodes manually (with the help of mouse pointer). For that i'm selecting both nodes from mouse one by one. A link (path) is creating from the first selected Node. This Link will be following the mouse pointer. And if i click on any other node, A link will be created between that and first node.
But there is an issue with the link(path). It is not actually following the mouse pointer if the SVG is transformed (translated and scaled).
Pic 1: Path is started from the clicked node position and following the mouse pointer. Here SVG is not Transformed (zoom not applied).
Pic 2: Path is started from the clicked node position but not properly following the mouse pointer. Here SVG is Transformed (zoom applied here).
Below is the sample code in which one SVG is created inside another SVG. This is the requirement of my project for later purpose.
I have tried alot but not understanding where is the issue. Here is my code : JSFiddle
var dnodes = [];
var dlinks = [];
var default_link_color = "#bbb";
var link_default_width = 2;
var min_zoom = 0.1;
var max_zoom = 7;
function initdiagram(el) {
var im = this;
var w = $(el).innerWidth();
var h = $(el).innerHeight();
var connector = d3.svg.line().interpolate("linear");
var zoom = d3.behavior.zoom().scaleExtent([min_zoom, max_zoom]);
var selectedNode1 = null;
var selectedNode2 = null;
var mainsvg = d3.select(el).append("svg")
.attr("class","mainsvg")
.attr("width", w)
.attr("height", h)
.on("mousemove", function(){
if(selectedNode1 !== null)
{
var cm = d3.mouse(this);
templink.attr("d",function(){
return connector([[selectedNode1.x , selectedNode1.y ], [ cm[0] , cm[1]]]);
});
}
if((selectedNode1 !== null) && (selectedNode2 !== null))
{
templink.attr("d",null);
}
});
var svg = mainsvg.append("svg")
.attr("class","svg")
.attr("viewBox", "0 0 " + w + " " + h)
.attr("preserveAspectRatio", "xMidYMid");
var g = svg.append("g")
.attr('width', w)
.attr('height', h);
zoom.on("zoom", function() {
g.attr("transform", "translate(" + d3.event.translate + ")scale(" + d3.event.scale + ")");
});
mainsvg.call(zoom).on("dblclick.zoom", null); //Disabling zoom on double click
function findNode(id) {
for (var i in dnodes) {
if (dnodes[i]["id"] === id) return dnodes[i];
}
}
this.addNode = function(id) {
var newNode = findNode(id);
if (newNode == undefined) {
dnodes.push({
"id": id,
fixed:false
});
}
}
this.addLink = function(sourceId, targetId) {
var sourceNode = findNode(sourceId);
var targetNode = findNode(targetId);
if ((sourceNode !== undefined) && (targetNode !== undefined)) {
dlinks.push({
"source": sourceNode,
"target": targetNode
});
}
}
var force = self.force = d3.layout.force()
.linkDistance(160)
.charge(-2000)
.on("tick",tick)
.size([w, h]);
var nodes = force.nodes(dnodes);
var links = force.links(dlinks);
this.forcestart = function(){
force.start();
}
function tick() {
node.attr("transform", function(d) {return "translate(" + d.x + "," + d.y + ")";});
link.attr('d', function(d) { var path='M '+d.source.x+' '+d.source.y+' L '+ d.target.x +' '+d.target.y; return path});
}
this.forceupdate = function(){
update(dnodes, dlinks);
}
var node = null;
var link = null;
var templink = null;
function update(dnodes, dlinks) {
g.selectAll(".link").remove();
g.selectAll(".node").remove();
g.selectAll(".templink").remove();
link = g.selectAll(".link")
.attr("class", "link")
.data(dlinks)
.enter()
.append('path')
.attr('d', function(d) {return 'M '+d.source.x+' '+d.source.y+' L '+ d.target.x +' '+d.target.y;})
.attr("class","edgepath")
.attr('id', function(d,i) {return 'edgepath'+i;})
.style("stroke",default_link_color)
.style("stroke-width",link_default_width)
.style("pointer-events", "none");
templink = g.append("path")
.attr("class","templink")
.attr("d",null)
.style("stroke","green")
.style("stroke-width",link_default_width+1)
.style("stroke-dasharray","5, 5")
.style("fill","none");
node = g.selectAll(".node")
.data(dnodes)
.enter().append("g")
.attr("class", "node");
node.append("rect")
.attr("width", 20)
.attr("height", 20)
.attr("x", -10)
.attr("y", -10)
.style("fill", "blue");
node.on("mouseup", function(d) {
if(selectedNode1 == null)
{
selectedNode1 = d;
}
});
}
return this;
}
var di = new initdiagram("#graph");
di.addNode("i0");
di.addNode("i1");
di.addNode("i2");
di.addLink("i0", "i1");
di.addLink("i1", "i2");
di.forceupdate();
di.forcestart();
text {
font-family: sans-serif;
pointer-events: none;
}
html,body { width:100%; height:100%; margin:none; padding:none; }
#graph { width:100%;height:100%; margin:auto; }
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/3.4.10/d3.min.js"></script>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
<div id="graph"></div>