D3.JS - Rotate a pie chart on mouse down event

有些话、适合烂在心里 提交于 2019-12-02 14:35:18

Pretty easy with d3:

var svg = d3.select("body").append("svg")
  .attr("width", width)
  .attr("height", height)
  .append("g")
  .attr("transform", "translate(" + width / 2 + "," + height / 2 + ")");

var g = svg.selectAll(".arc")
    .data(pie(data))
    .enter().append("g")
    .attr("class", "arc");

g.append("path")
    .attr("d", arc)
    .style("fill", function(d) {
      return color(d.data.age);
    });

var curAngle = 0;
var interval = null;

svg.on("mousedown", function(d) {
    interval = setInterval(goRotate,10);
});

svg.on("mouseup", function(d){
    clearInterval(interval);
})

function goRotate() {
    curAngle += 1;
    svg.attr("transform", "translate(" + width / 2 + "," + height / 2 + ") rotate(" + curAngle + "," + 0 + "," + 0 + ")");
  }

Working example.

I did a similar thing with a compass instead of pie chart. You mainly need three methods - each bound to a different mouse event.

Bind this to the mousedown event on your compass circle:

function beginCompassRotate(el) {

    var rect = compassCircle[0][0].getBBox(); //compassCircle would be your piechart d3 object
    compassMoving = true;
    compassCenter = {
        x: (rect.width / 2),
        y: (rect.height / 2)
    }
}

Bind this to the mouse move on your canvas or whatever is holding your pie chart - you can bind it to the circle (your pie chart) but it makes the movement a little glitchy. Binding it to the circle's container keeps it smooth.

function rotateCompass() {
    if (compassMoving) {
        var mouse = d3.mouse(svg[0][0]);

        var p2 = {
            x: mouse[0],
            y: mouse[1]
        };

        var newAngle = getAngle(compassCenter, p2) + 90;
        //again this v is your pie chart instead of compass
        compass.attr("transform", "translate(90,90) rotate(" + newAngle + "," + 0 + "," + 0 + ")");
    }
}

Finally bind this to the mouseup on your canvas - again you can bind it to the circle but this way you can end the rotation without the mouse over the circle. If it is on the circle you will keep rotating the circle until you have a mouse up event over the circle.

function endCompassRotate(el) {
    compassMoving = false;
}

Here is a jsfiddle showing it working: http://jsfiddle.net/4oy2ggdt/

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!