【问题标题】:Transition between paths with different number of data points具有不同数据点数量的路径之间的转换
【发布时间】:2016-03-30 16:01:48
【问题描述】:

我正在尝试使用 d3 在具有不同数量数据点的两条线之间创建动画。

我参考了 Mike Bostock 的帖子:https://bl.ocks.org/mbostock/3916621,其中包含用于“M0...”格式描述的两条路径的 pathTween 方法。

我试图绘制的数据是原始数据点。 例如:

var line = d3.svg.line().interpolate("monotone")
  .x(function(d){ return d.x; })
  .y(function(d){ return d.y; });

low_res = [
    {x: 0     , y: 4  },
    {x: 5     , y: 14 },
    {x: 10  , y: 11 },
    {x: 85  , y: 14 },
    {x: 90  , y: 11 },
    {x: 95  , y: 7  },
    {x: 100 , y: 4  },
  ];
  var high_res = [[
    {x: 0     , y: 4  },
    {x: 1     , y: 12 },
    {x: 2     , y: 11 },
    {x: 3     , y: 11 },
    {x: 4     , y: 14 },
    {x: 5     , y: 14 },
    {x: 6     , y: 12 },
    {x: 7     , y: 4  },
    {x: 8     , y: 3  },
    {x: 9     , y: 1  },
    {x: 10  , y: 11 },
    {x: 11  , y: 11 },
    {x: 12  , y: 1  },
    {x: 13  , y: 13 },
    {x: 14  , y: 1  },
    {x: 15  , y: 5  },
    {x: 16  , y: 13 },
    {x: 17  , y: 10 },
    ]]
  var lines = svg.selectAll(".line").data(high_res)
          .enter()
          .append("path")
          .attr("class","line")
          .attr("d", line)
          .style("stroke", "blue");

这适用于显示高分辨率图。 Mike Bostock 的例子如下:

  var d0 = "M0,0c100,0 0,100 100,100c100,0 0,-100 100,-100",
          d1 = "M0,0c100,0 0,100 100,100c100,0 0,-100 100,-100c100,0 0,100 100,100";
    svg.append("path")
            .attr("transform", "translate(180,150)scale(2,2)")
            .attr("d", d0)
            .call(transition, d0, d1);

    function transition(path, d0, d1) {
        path.transition()
                .duration(2000)
                .attrTween("d", pathTween(d1, 4))
                .each("end", function() { d3.select(this).call(transition, d1, d0); });
    }

    function pathTween(d1, precision) {
        return function() {
            var path0 = this,
                    path1 = path0.cloneNode(),
                    n0 = path0.getTotalLength(),
                    n1 = (path1.setAttribute("d", d1), path1).getTotalLength();

            // Uniform sampling of distance based on specified precision.
            var distances = [0], i = 0, dt = precision / Math.max(n0, n1);
            while ((i += dt) < 1) distances.push(i);
            distances.push(1);

            // Compute point-interpolators at each distance.
            var points = distances.map(function(t) {
                var p0 = path0.getPointAtLength(t * n0),
                        p1 = path1.getPointAtLength(t * n1);
                return d3.interpolate([p0.x, p0.y], [p1.x, p1.y]);
            });

            return function(t) {
                return t < 1 ? "M" + points.map(function(p) { return p(t); }).join("L") : d1;
            };
        };
    }

我正在努力弄清楚如何从我的一组原始数据中创建一个本机路径对象,例如第二个示例中的 d0、d1,这些原始数据可以传递给转换函数,即:

.call(transition, d0, d1);

非常感谢您的任何建议。

【问题讨论】:

    标签: animation d3.js


    【解决方案1】:

    您的问题似乎可以归结为:

    如何为我的数据点生成路径?

    这实际上是 line 函数正在做的事情。很简单:

    var low_res = [
        {x: 0   , y: 4  },
        {x: 5   , y: 14 },
        {x: 10  , y: 11 },
        {x: 85  , y: 14 },
        {x: 90  , y: 11 },
        {x: 95  , y: 7  },
        {x: 100 , y: 4  },
      ],
      high_res = [
        {x: 0     , y: 4  },
        {x: 1     , y: 12 },
        {x: 2     , y: 11 },
        {x: 3     , y: 11 },
        {x: 4     , y: 14 },
        {x: 5     , y: 14 },
        {x: 6     , y: 12 },
        {x: 7     , y: 4  },
        {x: 8     , y: 3  },
        {x: 9     , y: 1  },
        {x: 10  , y: 11 },
        {x: 11  , y: 11 },
        {x: 12  , y: 1  },
        {x: 13  , y: 13 },
        {x: 14  , y: 1  },
        {x: 15  , y: 5  },
        {x: 16  , y: 13 },
        {x: 17  , y: 10 },
      ];
        
    var line = d3.svg.line().interpolate("monotone")
      .x(function(d){ return d.x; })
      .y(function(d){ return d.y; });
        
    var d0 = line(low_res),
        d1 = line(high_res);
        
    console.log(d0);
    console.log(d1);
    &lt;script src="https://cdnjs.cloudflare.com/ajax/libs/d3/3.4.11/d3.min.js"&gt;&lt;/script&gt;

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2018-03-21
      • 1970-01-01
      • 1970-01-01
      • 2012-07-20
      • 2019-07-24
      • 2013-08-16
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多