🏠 back to Observable

d3.drag() in d3@6

This notebook https://observablehq.com/d/2271d8c7295e1891 is a clone of this blo.ck https://bl.ocks.org/mbostock/519d494035dd642e19eee4e242570114 updated to run in d3@6.
But the dragging behavior doesn’t quite work in the same as in d3@5. The circle jumps when
the drag starts.

Am not sure what the right way is to handle dragging when using scales to convert between data space and the SVG canvas. In particular when we use a scale to invert the y-coordinate of the SVG canvas it is unclear how to get the circles to drag correctly.

drag.subject also expects (event, d) as arguments

1 Like

Here’s a working example:

Thank you for the suggestions and the example code.

One thing I’m not sure I fully understand is what d3.drag.subject() really is doing in this revised version of the example:

When I use d.x and d.y to set the position of the circle, I need to set the subject() as shown in the code. When I don’t set the subject(), the dragging causes the circle to jump to the d.x, d.y coordinates but in the pixel space. That is event.x = d.x, event.y = d.y and then dragging causes event.x and event.y to update starting from that data space location. When I add in the subject() then event.x and event.y are properly set to the pixel space location of the circle. I think I understand that, though I’m unclear on why it is a good default to set event.x = d.x, event.y = d.y when the subject isn’t specified.

Interestingly when I use d.xPos, d.yPos to set the position of the circle, I don’t need to set the subject and the drag operates as I would expect. So it seems like there is something special about the x,y fields of the datum (in fact the documentation of d3.drag().subject() seems to talk about this), but I couldn’t figure out from the documentation exactly what might be doing on.