2

Here is an SVG Text with an anchor:

<svg xmlns="http://www.w3.org/2000/svg" version="1.1" style="width:200px;height:200px;">
  <text x="50" y="30" fill="red" text-anchor="start">I love SVG</text>
</svg>

Now if I write a drag function:

var dragMove = function (d,i) {
    //d3.select(this).attr("text-anchor", "null"); Does not work
    d3.select(this).attr("x", d3.event.x)
                .attr("y", d3.event.y);
};

var dragEnd = function (d,i) {
    //d3.select(this).attr("text-anchor", "start"); Does not work
};

var drag = d3.behavior.drag()
                .on("drag", dragMove)
                .on("dragend", dragEnd);

d3.select("svg")
    .select("text")
    .call(drag);

It jumps after you drag it depending to its anchor position. Is there a solution to this?

I tried setting the anchor-text to null and then re-set it again but that does not work. I do not want the user experience of dragging to change at all. Not even when the dragging finishes.

Any idea?

Here is the JSFiddle: http://jsfiddle.net/sewVr/

FidEliO
  • 875
  • 3
  • 14
  • 24
  • I don't think it's possible with d3 but you could use jQuery. Check out the offsetX and offsetY properties – 0xcaff Oct 08 '13 at 14:16
  • http://www.html5rocks.com/en/tutorials/dnd/basics/ You could try to use native drag and drop api's – 0xcaff Oct 08 '13 at 14:18

2 Answers2

3

Use d3.event.dx and d3.event.dy to get the relative drag position change and apply it in your dragMove() function.

Demo here: http://jsfiddle.net/sewVr/1/

Paul LeBeau
  • 97,474
  • 9
  • 154
  • 181
  • This is more general approach than my answer. – musically_ut Oct 08 '13 at 15:07
  • This does not work when there is a viewbox attribute enabled. Is there a way of working it out?! – FidEliO Oct 08 '13 at 15:20
  • That makes it a bit trickier. It should be possible, but you would need to scale dx and dy using the matrix you get back from getCTM() (an SVG DOM function). See http://www.w3.org/TR/SVG/types.html#InterfaceSVGLocatable . d3 might also have built-in function to help with that, but I am not familiar enough with d3 to give a definitive answer. – Paul LeBeau Oct 08 '13 at 16:20
  • Otherwise, if you can, make sure width and height are the same as the width and height of your viewBox. So that the scaling is 1:1. – Paul LeBeau Oct 08 '13 at 16:24
  • BigBadaboom, please check musically_ut's approach below, because it actually works out of the box for SVG with viewBox attribute enabled. – FidEliO Oct 09 '13 at 08:20
0

You can do it by saving how much were the x and y offset between the place where the mouse click happened and the origin of the text element. Like here: http://jsfiddle.net/twKD9/

musically_ut
  • 34,028
  • 8
  • 94
  • 106