Как перетащить группу svg с помощью поведения d3.js drag?
Я использую D3js drag. Единственный элемент - это перетащить отлично. но я хочу перетащить группу элементов. Как это можно сделать. Вот что находится на моей ссылка Js Fiddle:
function onDragDrop(dragHandler, dropHandler) {
var drag = d3.behavior.drag();
drag.on("drag", dragHandler)
.on("dragend", dropHandler);
return drag;
}
var g = d3.select("body").select("svg").append("g")
.data([{ x: 50, y: 50 }]);
g.append("rect")
.attr("width", 40)
.attr("height", 40)
.attr("stroke", "red")
.attr("fill","transparent")
.attr("x", function (d) { return d.x; })
.attr("y", function (d) { return d.y; })
.call(onDragDrop(dragmove, dropHandler));
g.append("text")
.text("Any Text")
.attr("x", function (d) { return d.x; })
.attr("y", function (d) { return d.y; })
.call(onDragDrop(dragmove, dropHandler));
function dropHandler(d) {
// alert('dropped');
}
function dragmove(d) {
d3.select(this)
.attr("x", d.x = d3.event.x)
.attr("y", d.y = d3.event.y);
}
Я хочу перетащить одновременно прямоугольник и текст. Вот что я пытался, но не повезло. Я думаю, что я пропустил что-то простое.
Ответы
Ответ 1
Во-первых, элемент <g> не нуждается в атрибутах x
и y
(как в: они просто игнорируются). Вместо этого вы можете использовать transform="translate(x,y)"
.
Во-вторых, вам нужно будет проверить, что элемент, который вы получаете в обработчике dragmove, фактически является элементом <g> , а не дочерним элементом. Это связано с тем, что элементы <g> не имеют фактической области попадания. Их дети, хотя, и события мыши сначала идут к детям, а затем приходят к родителям. Вы можете проверить evt.target
и evt.currentTarget
, чтобы увидеть это в действии. target
- это элемент, который был первоначально избит, currentTarget
- это цель события, которая в данный момент обрабатывает событие (например, элемент <g> , если событие разбухает).
Ответ 2
Для d3 v4:
var drag_this = d3.drag().subject(this)
.on('start',function (d) {
if (d.x1){
d.x1 = d3.event.x - d.xt;
d.y1 = d3.event.y - d.yt;
}else{
d.x1 = d3.event.x;
d.y1 = d3.event.y;
}
})
.on('drag',function(d){
d3.select(this)
.attr("transform", "translate(" + (d3.event.x - d.x1) + "," + (d3.event.y - d.y1) + ")");
d.xt = d3.event.x - d.x1;
d.yt = d3.event.y - d.y1;
});
my_group.call(drag_this);
Это предполагает, что у вас есть данные, привязанные к группе.