D3 / React / moment.js-日期刻度对齐

时间:2019-07-18 15:52:46

标签: reactjs d3.js momentjs

我正在使用React,D3和moment.js来构建可重复使用的折线图组件,该组件可以随时间跟踪值。

我很难使刻度线对齐正确。我目前正在使用动量并将所有内容转换为时间戳,并依赖于线性刻度,但我对其他可能有效的解决方案持开放态度!

另一个问题是x轴上的刻度线重复了一个日期,而省略了另一个。我的假设是,这一切都与之相关。

我有以下数据集:

            let time = [
                {"id": 1, "date": "06/14/2019", "total": 1},
                {"id": 2, "date": "06/15/2019", "total": 4},
                {"id": 3, "date": "06/16/2019", "total": 8},
                {"id": 4, "date": "06/17/2019", "total": 4}
            ];

这是我相关的React组件代码:

import * as d3 from 'd3';
import moment from 'moment';

const LineChart = props => {
    const margin = 20;
    const h = props.height - 2 * margin;
    const w = props.width - 2 * margin;
    const yFormat = d3.format(".2");

    const data = props.data;

    const x = d3.scaleLinear()
        .domain(d3.extent(data, d => moment(d.date, 'MM/DD/YYYY').format('X')))
        .range([margin, w]);

    // debug
    // console.log(moment("06/14/2019", 'MM/DD/YYYY').format('X'));
    // console.log(moment("06/16/2019", 'MM/DD/YYYY').format('X'));    
    // console.log(x(moment("06/14/2019", 'MM/DD/YYYY').format('X')));
    // console.log(x(moment("06/16/2019", 'MM/DD/YYYY').format('X')));

    const y = d3.scaleLinear()
        .domain([0, d3.max(data, d => d.total)])
        .range([h, margin]);

    const line = d3.line()
        .x(d => x(moment(d.date, 'MM/DD/YYYY').format('X')))
        .y(d => y(d.total));

    const xTicks = x.ticks(props.data.length).map(d => (
        x(d) >= margin && x(d) <= w ?
            <g transform={`translate(${x(d)},${h + margin})`} key={x(d)}>
                <text>{moment(d*1000).format('YYYY/MM/DD')}</text>
                <line x1='0' x2='0' y1='0' y2='5' transform="translate(0,-20)"/>
            </g>
        : null
    ));

我的渲染功能:

    return (
        <svg width={props.width} height={props.height}>
            <line className="axis" x1={margin} x2={w} y1={h} y2={h} />
            <line className="axis" x1={margin} x2={margin} y1={margin} y2={h} />
            <path className="line" d={line(data)} ref={ref} />
            <g className="axis-labels">
                {xTicks}
            </g>
            <g className="axis-labels">
                {yTicks}
            </g>
        </svg>
    );
};

这给我留下了如下折线图:

enter image description here

0 个答案:

没有答案