Keep line in SVG always connecting two objects

4

I have two circle objects, which I can move with the mouse. I wanted a line between the two circles, which always moves if one, the line is always glued.

The code I have to move the objects:

var dragged = null; //L'élément en cours de drag

function start_drag(objet,event)
{
  dragged = objet;

  if( event.preventDefault ) event.preventDefault();
}

function drag_onmousemove(event)  //Lorsque la souris se déplace
{
  if( dragged ) 
  {
    x = event.clientX;
    y = event.clientY;
    elementHeight = dragged.clientHeight; //hauteur du obj
    elementWidth = dragged.clientWidth;
    dragged.style.position = 'absolute';
    dragged.style.left = x - elementWidth/2 + 'px'; //divise longueur par 2 pour le milieu
    dragged.style.top = y - elementHeight/2 + 'px';


  }
}

function drag_onmouseup(event)  
{
  dragged = null; 

}

function addEvent(obj,event,fct)
{
  if( obj.attachEvent)
    obj.attachEvent('on' + event,fct);
  else
    obj.addEventListener(event,fct,true);
}

addEvent(document,'mousemove',drag_onmousemove);
addEvent(document,'mouseup',drag_onmouseup);	
<div id="divcircle" onmousedown="start_drag(document.getElementById('divcircle'), event);" style="position:absolute; height:50px; width:50px;"> 
  <svg id="svg">
    <circle cx="50" cy="50" r="5" stroke="black" stroke-width="3" fill="green" />
  </svg>	
</div>
<div id="divcircle2" onmousedown="start_drag(document.getElementById('divcircle2'), event);" style="position:absolute; height:50px; width:50px;"> 
  <svg id="svg">
    <circle cx="40" cy="40" r="5" stroke="black" stroke-width="3" fill="green" />
  </svg>	
</div>
    
asked by anonymous 17.11.2014 / 17:05

1 answer

8

Considering the syntax of the line:

<line x1="20" y1="100" x2="200" y2="220" stroke="black" stroke-width="2"/>

What you need to do is to animate the desired property. In your case, you have to make one of the pairs, or x1 and y1 , or x2 and y2 have the same value as the moved circle.


Practical example of use:

I took the drag'n'drop technique found this link , which is more stable than yours, and adapted by adding the part that links the elements:

var selectedElement = 0;
var selectedLine = 0;
var selectedLineX = 0;
var currentX = 0;
var currentY = 0;
var currentMatrix = 0;

function selectElement(evt,lin,linx) {
  selectedElement = evt.target;
  selectedLine = document.getElementById( lin );
  selectedLineX = linx;
  currentX = evt.clientX;
  currentY = evt.clientY;
  currentMatrix = selectedElement.getAttributeNS(null, "transform").slice(7,-1).split(' ');
  for(var i=0; i<currentMatrix.length; i++) {
    currentMatrix[i] = parseFloat(currentMatrix[i]);
  }
  selectedElement.parentNode.setAttributeNS(null, "onmousemove", "moveElement(evt)");
  selectedElement.setAttributeNS(null, "onmouseup", "deselectElement(evt)");
}


function moveElement(evt){
  dx = evt.clientX - currentX;
  dy = evt.clientY - currentY;
  currentMatrix[4] += dx;
  currentMatrix[5] += dy;
  newMatrix = "matrix(" + currentMatrix.join(' ') + ")";
  selectedElement.setAttributeNS(null, "transform", newMatrix);
  currentX = evt.clientX;
  currentY = evt.clientY;
  if ( selectedLineX == 1 ) {
    selectedLine.x1.baseVal.value = selectedElement.cx.baseVal.value + currentMatrix[4];
    selectedLine.y1.baseVal.value = selectedElement.cy.baseVal.value + currentMatrix[5];
  } else {
    selectedLine.x2.baseVal.value = selectedElement.cx.baseVal.value + currentMatrix[4];
    selectedLine.y2.baseVal.value = selectedElement.cy.baseVal.value + currentMatrix[5];
  }
}

function deselectElement(evt){
  if(selectedElement != 0){
    selectedElement.parentNode.removeAttributeNS(null, "onmousemove");
    selectedElement.removeAttributeNS(null, "onmouseup");
    selectedElement = 0;
  }
}
body,html,#dd,#svg1{padding:0;margin:0;width:100%;height:100%}
circle {cursor:move}
<div id="dd">
  <svg id="svg1">
    <line id="l1-2" x1="80" y1="80" x2="40" y2="40" stroke="black" stroke-width="2"/>
    <circle
       cx="80" cy="80" r="5" stroke="black" stroke-width="3" fill="green"
       transform="matrix(1 0 0 1 0 0)" onmousedown="selectElement(evt,'l1-2',1);"
    />
    <circle
       cx="40" cy="40" r="5" stroke="black" stroke-width="3" fill="green"
       transform="matrix(1 0 0 1 0 0)" onmousedown="selectElement(evt,'l1-2',2);"
    />
    <line id="l3-4" x1="80" y1="40" x2="40" y2="80" stroke="black" stroke-width="2"/>
    <circle
       cx="80" cy="40" r="5" stroke="black" stroke-width="3" fill="red"
       transform="matrix(1 0 0 1 0 0)" onmousedown="selectElement(evt,'l3-4',1);"
    />
    <circle
       cx="40" cy="80" r="5" stroke="black" stroke-width="3" fill="red"
       transform="matrix(1 0 0 1 0 0)" onmousedown="selectElement(evt,'l3-4',2);"
    />
  </svg>	
</div>

The parameters of the function: selectElement(evt, 'ID DA LINHA', ponta_desejada_1_ou_2 );

    
17.11.2014 / 17:12