chart.jsx 2,62 ko
Newer Older
import React, { useEffect, useRef } from 'react';
import * as d3 from 'd3';

const BarChart = ({ data }) => {
    const d3Chart = useRef();

    const drawChart = () => {
        const colorScale = d3.scaleOrdinal(d3.schemeCategory10);
        const margin = { top: 50, right: 40, bottom: 70, left: 60 };
        const barWidth = 40;
        const maxWidth = window.innerWidth - margin.left - margin.right;
        let chartWidth = data.length * barWidth;

        if (chartWidth > maxWidth) {
            chartWidth = maxWidth;
        }

        const height = 500 - margin.top - margin.bottom;

        d3.select(d3Chart.current).select("svg").remove();

        const svg = d3.select(d3Chart.current)
            .append("svg")
            .attr("width", chartWidth + margin.left + margin.right)
            .attr("height", height + margin.top + margin.bottom)
            .append("g")
            .attr("transform", `translate(${margin.left}, ${margin.top})`);

        const x = d3.scaleBand()
            .range([0, chartWidth])
            .padding(0.1);
        const y = d3.scaleLinear()
            .range([height, 0]);

        x.domain(data.map(d => d.date));
        y.domain([0, d3.max(data, d => d.occurrences)]);

        svg.selectAll(".bar")
            .data(data)
            .enter().append("rect")
            .attr("class", "bar")
            .attr("fill", d => colorScale(d.date))
            .attr("width", x.bandwidth())
            .attr("x", d => x(d.date))
            .attr("y", d => y(d.occurrences))
            .attr("height", d => height - y(d.occurrences));

        // Axe X
        svg.append("g")
            .attr("transform", `translate(0, ${height})`)
            .call(d3.axisBottom(x))
            .selectAll("text")
            .attr("transform", "rotate(-45)")
            .style("text-anchor", "end");

        // Axe Y
        svg.append("g")
            .call(d3.axisLeft(y));

        // Titre Axe X
        svg.append("text")
            .attr("x", chartWidth / 2)
            .attr("y", height + margin.bottom - 20)
            .style("text-anchor", "middle")
            .text("Date");

        // Titre Axe Y
        svg.append("text")
            .attr("transform", "rotate(-90)")
            .attr("y", 0)
            .attr("x", 0 - (height / 2))
            .attr("dy", "-1em")
            .style("text-anchor", "middle")
            .text("Nombre de ventes");
    };

    useEffect(() => {
        if (data && data.length > 0) {
            drawChart();
        }
    }, [data]);

    return (
        <div style={{ overflowX: 'auto' }}>
            <div ref={d3Chart}></div>
        </div>
    );
};

export default BarChart;