d3 v4 + react + ES6:如何以编程方式创建轴?

时间:2016-07-14 18:06:33

标签: d3.js reactjs ecmascript-6

我试图在当前版本4中绕过d3。具体来说:我试图为react和es6中的简单折线图创建x轴。

我已经看过Mike Bostock的例子以及他是如何做到的:

svg.append("g")
.attr("class", "axis axis--x")
.attr("transform", "translate(0," + height + ")")
.call(d3.axisBottom(x));

但这既不是反应也不是ES6。

在另一个网站上,我看到了以下变体:

renderAxis() {
  var node  = this.refs.axis;
  var axis = d3.svg.axis().orient(this.props.orient).ticks(5).scale(this.props.scale);
  d3.select(node).call(axis);
}

render() {
  return <g className="axis" ref="axis" transform={this.props.translate}></g>
}

这是反应和ES6,但不是版本4中的d3。

我可以尝试将版本3代码应用到d3的第4版但是:d3.select非常困扰我。当我使用react(或者其他一些库,比如d3)时,我不想进行DOM调用。应该使用React以最有效的方式呈现到DOM中,而不是让我获得DOM节点。

所以,我的问题是: 创建一个简单的x轴的反应方式是什么?或者,如果还没有这样的答案:采用Mike Bostock引用代码的反应方式是什么?

3 个答案:

答案 0 :(得分:3)

如果您正在使用React,那么您几乎可以控制DOM如何工作到React,因为它的内部工作原理。 React会将您的组件呈现在虚拟DOM树中,然后在插入根组件和前者时,找出页面中DOM树之间的差异。它将应用两棵树之间的差异,以便页面中的树看起来像虚拟树。

混合d3和React需要一些技巧。您使用d3(节点或属性)的所有元素都不应归React所有。否则会发生奇怪的事情。假设transform节点的g.axis属性由d3设置,这意味着您不在React中渲染它。你让你的d3逻辑拥有它的独家所有权。

现在进入下一步。如果您想使用其他工具来描述DOM节点,那么您必须将该逻辑放在componentWillMount and componentDidUpdate中。基本上,您只在React的g方法中呈现render()元素,然后在这两个React生命周期句柄中,您可以更改g元素的属性以及内部的内容。

我会指向你post that goes a bit more in detail about the hows,但我也想给我两分钱。根据我对这两者的看法和经验,最好只使用d3作为辅助函数(通用数学函数)。让渲染逻辑(DOM组合)完全在React中完成,即使出现了代码重复。维护代码是一致的,并且没有两种不同的方法来混合在一起,这样更容易。

TL; DR;将属性或节点所有权赋予React或d3以使它们一起工作;或者我的建议,在React中创建自己的轴组件,输出与d3相同的DOM元素(如果需要其他功能或样式,则输出不同),不要使用d3进行渲染。

希望我帮助过。

答案 1 :(得分:1)

经过几年尝试在React中找出d3的方法,这是我团队和我发现做轴的最好方法:

const Axis = props => {
    const axisRef = axis => {
        axis && props.axisCreator(select(axis));
    };

    return <g className={props.className} ref={axisRef} />;
};

注释

答案 2 :(得分:0)

直接使用React而不是d3的select API渲染轴的代码实际上并不那么复杂。 react-d3-axis提供了一个非常简单的~100 loc实现。使用这种方法,您可以使用d3进行数据转换和比例插值之类的操作,并使用React进行渲染。