简体   繁体   中英

Sunburst D3 text issue

I'm using this model : http://www.jasondavies.com/coffee-wheel/ :

在此处输入图片说明

I made a sunburst that works pretty well, except when I zoom in or out, sometimes it changes the current node.

When I look at my tooltip, I can see that the "zone" doesn't refer to the correct element and it sends me to this wrong element. I don't know where that could come from.

在此处输入图片说明

name should be "LDG", but there is a small zone in which there is a reference to another element.

loadSunburstTree: function() {
        var width = 960,
        height = width,
        radius = Math.min(width, height) / 2,
        padding = 5,
        duration = 1000;

        var x = d3.scale.linear().range([0, 2 * Math.PI]);

        var y = d3.scale.sqrt().range([0, radius]);

        var color = d3.scale.category20c();

        var path = null;
        var arc = null;
        var text = null;

        $.ajax({
            url: $("#path").val() + ".json",
            method: "GET",
            success: function(result) {

                var data = {
                         "name": "home",
                         "level" : "root",
                         "children": []
                    };

                [...] // filling the variable data here (data are correct),

                var svg = d3.select("#graph").append("svg")
                    .attr("width", width)
                    .attr("height", height + 50)
                    .datum(data)
                    .append("g")
                    .attr("transform", "translate(" + width / 2 + "," + (height / 2 + 10) + ")");

                var partition = d3.layout.partition()
                    .value(function(d) { return d.size; });

                arc = d3.svg.arc()
                    .startAngle(function(d) { return Math.max(0, Math.min(2 * Math.PI, x(d.x))); })
                    .endAngle(function(d) { return Math.max(0, Math.min(2 * Math.PI, x(d.x + d.dx))); })
                    .innerRadius(function(d) { return Math.max(0, y(d.y)); })
                    .outerRadius(function(d) { return Math.max(0, y(d.y + d.dy)); });

                path = svg.selectAll("path")
                    .data(partition.nodes)
                    .enter().append("path")
                    .attr("d", arc)
                    .style("fill", function(d) { return color((d.children ? d : d.parent).name); })
                    .on("click", click);

                text = svg.selectAll("text").data(partition.nodes);
                text.enter().append("text")
                      .style("full-opacity", 1)
                      .style("fill", function(d) {
                        return brightness(d3.rgb(colour(d))) < 125 ? "#eee" : "#000";
                      })
                      .attr("text-anchor", function(d) {
                        return x(d.x + d.dx / 2) > Math.PI ? "end" : "start";
                      })
                      .attr("dy", ".2em")
                      .attr("transform", function(d) {
                        var angle = x(d.x + d.dx / 2) * 180 / Math.PI - 90,
                            rotate = angle;
                        return "rotate(" + rotate + ")translate(" + (y(d.y) + padding) + ")rotate(" + (angle > 90 ? -180 : 0) + ")";
                      })
                        .text(function(d) {
                            if( d.dx < .01){
                                  d3.select(this).style("display","none");
                              }
                              return d.depth ? d.name : "";
                        })
                      .on("click", click);
            }
        });

        function click(d) {
            path.transition()
            .duration(duration)
            .attrTween("d", arcTween(d));

            text.transition()
            .duration(duration)
            .attrTween("transform", function(d) {
              return function() {
                var angle = x(d.x + d.dx / 2) * 180 / Math.PI - 90;
                    var  rotate = angle;                    
                return "rotate(" + rotate + ")translate(" + (y(d.y) + padding) + ")rotate(" + (angle > 90 ? -180 : 0) + ")";
                                };
                        })
            .attrTween("text-anchor", function(d) {
                return function() {
                return x(d.x + d.dx / 2) > Math.PI ? "end" : "start";
                                };
                        })
            .style("fill-opacity", function(e) { return isParentOf(d, e) ? 1 : 1e-6; })
            .each("end", function(e) {  
                d3.select(this).style("display","");
                var st = e;
                    if (st.dx / d.dx < 0.01) {
                        d3.select(this).style("display","none");
                    } else {
                        d3.select(this).style("display","");
                    }
            });
        }

        d3.select(self.frameElement).style("height", height + "px");

        // Interpolate the scales!
        function arcTween(d) {
          var xd = d3.interpolate(x.domain(), [d.x, d.x + d.dx]),
              yd = d3.interpolate(y.domain(), [d.y, 1]),
              yr = d3.interpolate(y.range(), [d.y ? 20 : 0, radius]);
          return function(d, i) {
            return i
                ? function(t) { return arc(d); }
                : function(t) { x.domain(xd(t)); y.domain(yd(t)).range(yr(t)); return arc(d); };
          };
        }

        function isParentOf(p, c) {
              if (p === c) return true;
              if (p.children) {
                return p.children.some(function(d) {
                  return isParentOf(d, c);
                });
              }
              return false;
            }

        function colour(d) {
              if (d.children) {
                // There is a maximum of two children!
                var colours = d.children.map(colour),
                    a = d3.hsl(colours[0]),
                    b = d3.hsl(colours[1]);
                // L*a*b* might be better here...
                return d3.hsl((a.h + b.h) / 2, a.s * 1.2, a.l / 1.2);
              }
              return d.colour || "#fff";
            }

        function brightness(rgb) {
              return rgb.r * .299 + rgb.g * .587 + rgb.b * .114;
            }
    }
};

PS : Looks like the demo also have this problem, it's just harder to notice because there is no tooltip.

PPS : The clickable element is the text ! (in most of the case) The texts only have an opacity = 0 and are still on the view. That what makes the problem. They must not be correctly hidden. Still working on it.

That solved the problem. Texts tooltips are no longer visible nor clickable : Just edit the text code of the function click(d) like follow :

        function click(d) {
            path.transition()
            .duration(duration)
            .attrTween("d", arcTween(d));

            text.transition()
            .duration(duration)
            .attrTween("transform", function(d) {
                return function() {
                    var angle = x(d.x + d.dx / 2) * 180 / Math.PI - 90;
                    var  rotate = angle;                    
                    return "rotate(" + rotate + ")translate(" + (y(d.y) + padding) + ")rotate(" + (angle > 90 ? -180 : 0) + ")";
                };
            })
            .attrTween("text-anchor", function(d) {
                return function() {
                    return x(d.x + d.dx / 2) > Math.PI ? "end" : "start";
                };
            })
//modified from here
            .style("fill-opacity", function(e) {
                if (isParentOf(d, e)) {
                    return 1;
                } else {
                    return 0;
                }
            })
            .each("end", function(e) {
                if (e.dx / d.dx < 0.01 || $(this).css("fill-opacity") == 0) {
                    d3.select(this).style("display","none");
                } else {
                    d3.select(this).style("display","");
                }
            });
//to here
        }

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM