D3.js:使用origin()函数按组中包含的元素拖动组中的所有内容(' g')

时间:2015-05-08 20:27:28

标签: javascript d3.js draggable

我不确定发生了什么,但我设置了2个非常简单的例子来展示我的要求。

这两个例子都有一个''包含' rect'和'文字'。

在第一个例子中,我正在设置拖动''本身,也就是说,如果你在该组中的任何地方进行了拖拽并拖动,它将围绕视点拖动整个事物(' rect'和#39;文本')。 http://jsfiddle.net/wup4d0nx/

var chart = d3.select("body").append("svg")
   .attr("height", 500)
   .attr("width", 500)
   .style("background", "lightgrey");

var group = chart.selectAll("g")
    .data(["Hello"])
    .enter()
    .append("g")
    .attr("id", function (d) { return d;});

var rect = group.append("rect")
    .attr("stroke", "red")
    .attr("fill", "blue")
    .attr("width", 200)
    .attr("height", 200)
    .attr("x", 10)
    .attr("y", 10);

var label = group.append("text")
    .attr("x", 40)
    .attr("y", 40)
    .attr("font-size", "22px")
    .attr("text-anchor", "start")
    .text(function (d) { return d;});

// Set up dragging for the entire group
var dragMove = function (d) {
    var x = d3.event.x;
    var y = d3.event.y;
    d3.select(this).attr("transform", "translate(" + x + "," + y + ")");
};


var drag = d3.behavior.drag()
    .origin(function (data) {
        var element = d3.select("#" + data);
        return {
            x: d3.transform(element.attr("transform")).translate[0],
            y: d3.transform(element.attr("transform")).translate[1]
        };
    })
    .on("drag", dragMove);

group.call(drag);

在第二个例子中,它不起作用并且是我感兴趣的内容,我想只需要用户可以抓取的内容来拖动整个组。

我尝试了很多次尝试。有些人根本不工作,有些工作但闪烁就像我在这里提供的例子: http://jsfiddle.net/9xeo7ehf/

var chart = d3.select("body").append("svg")
    .attr("height", 500)
    .attr("width", 500)
    .style("background", "lightgrey");

var group = chart.selectAll("g")
    .data(["Hello"])
    .enter()
    .append("g")
    .attr("id", function (d) { return d;});

var rect = group.append("rect")
    .attr("stroke", "red")
    .attr("fill", "blue")
    .attr("width", 200)
    .attr("height", 200)
    .attr("x", 10)
    .attr("y", 10);

var label = group.append("text")
    .attr("x", 40)
    .attr("y", 40)
    .attr("font-size", "22px")
    .attr("text-anchor", "start")
    .text(function (d) { return d;});

// Set up dragging for the entire group USING THE LABEL ONLY TO DRAG
var dragMove = function (d) {
    var x = d3.event.x;
    var y = d3.event.y;
    d3.select(this.parentNode).attr("transform", "translate(" + x + "," + y + ")");
};


var drag = d3.behavior.drag()
    .origin(function (data) {
        var element = d3.select("#" + data);
        return {
            x: d3.transform(element.attr("transform")).translate[0],
            y: d3.transform(element.attr("transform")).translate[1]
        };
    })
    .on("drag", dragMove);

label.call(drag);

这是怎么回事,它闪烁,我做错了什么?

非常感谢任何帮助!

谢谢!

2 个答案:

答案 0 :(得分:0)

我不确定它为什么会闪烁(因为我对D3不太熟悉),但让它停止的一种方法是使用D3的源事件:

// 50 is the offset x/y position you set for your text
var x = d3.event.sourceEvent.pageX - 50;
var y = d3.event.sourceEvent.pageY - 50;

编辑:虽然上面的代码有效,但它会使框最初“跳转”到文本的坐标。更好的解决方法是采取你的第一个例子,只过滤我们在文本上没有执行的事件元件。尝试将以下内容放在dragMove方法的顶部:

if(d3.event.sourceEvent.target.nodeName !== 'text') {
    return;
}

答案 1 :(得分:0)

在on-drag功能中尝试d3.event.sourceEvent.stopPropagation();