简体   繁体   中英

D3 - x domain not working

I have a plunker here - https://plnkr.co/edit/JSB4FD1yOe6Xvii6FiRn?p=preview

Its a stacked bar chart in an Angular 4 component

I'm having problems with the x domain to create the x axis

At the moment the bars are taking up the width of the whole chart.

private drawChart(data:any){
    this.layersBar = this.layersBarArea.selectAll('.layer')
        .data(data)
        .enter()
        .append('g')
        .classed('layer', true)
        .style('fill', (d:any,i:any)=>{
            return this.colors[i]
        });

    this.x.domain(data.map((d:any)=>{
        //return d.date;
    }));

    this.y.domain([0, +d3.max(this.stackedSeries, function(d:any){
        return d3.max(d, (d:any)=>{
            return d[1]
        })
    })]);

    this.layersBar.selectAll('rect')
        .data((d:any)=>{
            return d;
        })
        .enter()
        .append('rect')
        .attr('y', (d:any)=>{
            return this.y(d[1])
        })
        .attr('x', (d:any, i:any)=>{
            return this.x.date
        })

        .attr('width', this.x.bandwidth())
        .attr('height', (d:any, i:any)=>{
            return this.y(d[0]) - this.y(d[1]);
        })
}

It's a mystery to me the fact that you're asking why the x domain is not working. You can clearly see that you're not returning anything here:

this.x.domain(data.map((d:any)=>{
    //return d.date;
}));

Which makes the x domain undefined .

You have to return d.date . But, on top of that, you have to change the data: data is the stacked data. Instead of that, you want to use this.data :

this.x.domain(this.data.map((d:any)=>{
    return d.date
}));

Finally, you're setting the x position wrong. It should be:

.attr('x', (d:any, i:any)=>{
    return this.x(d.data.date)
})

Here is the updated plunker: https://plnkr.co/edit/Itz5wTydyGcohKSlSsX0?p=preview

PS: Your button doesn't work.

The issue is in this code block.

this.layersBar.selectAll('rect')
        .data((d:any)=>{
            return d;
        })
        .enter()
        .append('rect')
        .attr('y', (d:any)=>{
            return this.y(d[1])
        })
        .attr('x', (d:any, i:any)=>{
            return this.x.date
        })

        .attr('width', this.x.bandwidth())
        .attr('height', (d:any, i:any)=>{
            return this.y(d[0]) - this.y(d[1]);
        })

Where you have .attr('width', this.x.bandwidth()) this determines how wide the bars should be. Since I don't know how wide you want them to be you just need to change this.x.bandwith() to something that works for you.

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