【问题标题】:how to update d3 chart when receiving new DATA接收新数据时如何更新d3图表
【发布时间】:2020-11-24 16:22:20
【问题描述】:

如何使用新数据更新 d3 图表: 我正在实现 ngOnchanges 三个功能:

        this.removeSvg(this.data);
        this.createSvg();
        this.drawBars(this.data);

在哪里 createSvg() :

private createSvg(): void {
    this.svg = d3.select("figure#histogram")
        .append("svg")
        .attr("width", '100%')
        .attr("height", '100%')
        .append("g")
        .attr("transform", "translate(" + this.margin + "," + this.margin + ")");
}

和 removeSvg() :

       this.svg = d3.select("figure#histogram")
       .exit().remove()
       d3.select("#histogram").select("svg").remove();

和drawBars(数据:任何[]):

private drawBars(data: any[]): void {
    // Create the X-axis band scale
    const x = d3.scaleBand()
        .range([this.axisMin, 340])
        .domain(data.map(d => d.xAxis))
        .padding(0);

    // Create the Y-axis band scale
    const y = d3.scaleLinear()
        .domain([0, this.axisMax])
        .range([this.height, 0])
        .nice();


    // Create and fill the bars
    this.svg.selectAll("bars")
        .data(data)
        .enter()
        .append("rect")
        .attr("x", d => x(d.xAxis))
        .attr("y", d => y(d.yAxis))
        .attr("width", x.bandwidth())
        .attr("height", (d) => this.height - y(d.yAxis))
        .attr("fill", "rgb(13, 185, 240)");
}

但它不会刷新图表,即使确定数据正在刷新(因此对于第一个图表,我们继续将所有其他图表视为相同的数据) 有什么帮助吗?也许删除或退出在这里是错误的!

【问题讨论】:

    标签: javascript angular typescript d3.js charts


    【解决方案1】:

    解决了!

    对于任何面临此问题的人,我建议他使用以下解决方案: 保持一切原样,但确保在每次更改时刷新数据,然后清空所有元素的 svg:

    his.svg.selectAll("*").remove()
    

    ,然后用新数据再次绘制图表。

    【讨论】:

      【解决方案2】:
      this.svg.selectAll("bars")
              .data(data, d => d)
              .join(
                  enter => enter
                      .append("rect")
                      .attr("x", d => x(d.xAxis))
                      .attr("y", d => y(d.yAxis))
                      .attr("width", x.bandwidth())
                      .attr("height", (d) => this.height - y(d.yAxis))
                      .attr("fill", "rgb(13, 185, 240)"),
                  update => update.call(update => update
                      .transition(t)
                      .attr("x", d => x(d.xAxis))
                      .attr("y", d => y(d.yAxis))
                      .attr("height", (d) => this.height - y(d.yAxis))),
                  exit => exit.call(exit => exit
                      .transition(t)
                      .attr("x", 0)
                      .attr("y", 0)
                      .attr("height", 0)
                      .remove()))
      

      这对更新数据时的转换没有帮助。

      【讨论】:

        【解决方案3】:

        在 D3 中,可以通过选择来操作 DOM。在您的drawBars() 函数中,您使用enter 选择来描述新数据会发生什么。 要描述发生变化的数据会发生什么,请使用update 选择;对于留下的数据,使用exit 选择。要跟踪更新的数据,您需要在 data() 调用上使用一个键函数来唯一标识每个元素。

        See this tutorial 以获得更深入的概述。

        在您的drawBars() 函数中:

        private drawBars(data: any[]): void {
            // ...
            let t = svg.transition().duration(500);
            
            this.svg.selectAll("bars")
                .data(data, d => d)
                .join(
                enter => enter
                    .append("rect")
                    .attr("x", d => x(d.xAxis))
                    .attr("y", d => y(d.yAxis))
                    .attr("width", x.bandwidth())
                    .attr("height", (d) => this.height - y(d.yAxis))
                    .attr("fill", "rgb(13, 185, 240)"),
                update => update.call(update => update.transition(t)
                    .attr("x", d => x(d.xAxis))
                    .attr("y", d => y(d.yAxis))
                    .attr("height", (d) => this.height - y(d.yAxis))),
                exit => exit.call(exit => exit.transition(t)
                    .attr("x", 0)
                    .attr("y", 0)
                    .attr("height", 0)
                    .remove()))
        }
        

        【讨论】:

        • 感谢@Hugo Elhaj-Lahsen 的回复,但没有成功!它不断将以前的图表栏附加到新图表栏的顶部
        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2012-01-22
        • 2016-03-09
        • 2018-08-03
        • 1970-01-01
        • 1970-01-01
        • 2016-03-13
        相关资源
        最近更新 更多