【问题标题】:Getting expected attribute value in D3 transition在 D3 转换中获取预期的属性值
【发布时间】:2016-08-18 09:35:12
【问题描述】:

例如我有一个过渡:

var sel = container.selectAll('div')
    .transition()
    .duration(1000)
    .attr('transform', 'translate(100,500)');

在某些时候我需要知道某些元素的位置,例如

setTimeout(() => {
    var value = d3.select('div#target')
        .expectedAttr('transform');
    assertEqual(value, 'translate(100,500)');
}, 500);

D3 中是否有这样的内置功能?否则我将不得不在 d3.transition().attr() 方法上编写自己的包装器来存储传递给它的值。

编辑

我发现 D3 在元素上创建了 __transition__ 字段,该字段似乎包含有关转换的信息,但我看不到在那里找到目标属性值的方法。

【问题讨论】:

  • 预期值是什么意思:过渡仍在运行时的特定时刻的值或过渡到的目标值?
  • @altocumulus 对,我需要知道一个属性的值,当过渡结束时该元素将具有。也许它存储在某个字段中,例如用于数据绑定的__data__ 字段。

标签: javascript d3.js


【解决方案1】:

起初我认为这是不可能的,因为目标值似乎无法被闭包隐藏。不过,通过一个小技巧,可以检索到这个值。

您必须记住,在调用transition.attr() 时,D3 将执行以下操作:

对于每个选定的元素,为具有指定名称的属性创建一个attribute tween 到指定的目标值。

这个自动创建的补间可以通过调用transition.attrTween(attrName)来访问。

当这个补间被 D3 调用时,它将返回一个interpolator。这反过来可以访问在创建插值器时关闭的目标值。当进一步阅读文档时,真正的技巧变得显而易见:

然后为过渡的每一帧调用返回的插值器,按顺序通过缓动时间t,通常在 [0, 1] 范围内。

知道 t 的最终值(在转换结束时)将是 1,您可以使用该值调用先前获得的插值器,这将产生转换的目标值。

var targetValue = transition 
  .attrTween("x2")            // Get the tween for the desired attribute
  .call(line.node())          // Call the tween to get the interpolator
  (1);                        // Call the interpolator with 1 to get the target value

以下示例通过打印已运行转换的目标值来说明这一点。

var line = d3.select("line");
line
  .transition()
  .duration(2000)
  .attr("x2", 100);
  
setTimeout(function() {
  var transition = d3.active(line.node())  // Get the active transition on the line
  var targetValue = transition 
    .attrTween("x2")                       // Get the tween for the desired attribute
    .call(line.node())                     // Call the tween to get the interpolator
    (1);                                   // Call the interpolator with 1 to get the target value
  console.log(targetValue);                // 100
}, 1000);
<script src="https://d3js.org/d3.v4.js"></script>

<svg><line x2="0" y2="100" stroke="black"></line></svg>

同样适用于样式转换,您可以使用 transition.styleTween() 获取补间。

【讨论】:

【解决方案2】:

今天遇到这个问题,发现altocumulus' answer 很有帮助。但是,我发现(至少对于当前的d3-transition@2.0.0)如果当前值已经处于目标值,.calling attrTween 将返回 null 而不是插值器.

我的解决方案最终看起来像这样:

const attrTargetValue = (selection, attr) => {
  const interpolator = selection
    .attrTween(attr)
    .call(selection.node());
  return interpolator === null
    ? selection.selection().attr(attr)
    : interpolator(1);
}

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2018-09-23
    • 1970-01-01
    • 2015-01-10
    • 1970-01-01
    • 2013-08-31
    • 2023-04-11
    • 1970-01-01
    相关资源
    最近更新 更多