首页 > 解决方案 > Highcharts日期不起作用

问题描述

我正在为一个项目学习一些 Highcharts,这是我第一次尝试使用我的数据集(VAST 挑战 2017 MC1)进行时间线演示并从行更改为列时遇到一个奇怪的问题。在你问之前,我已经检查了我在 StackOverflow 上可以找到的所有内容。

关键是日期已正确发送到图表并使用正确的 js 时间戳["1430441008000", 50];我提供给系列的完整对象结构是: {type: "column", name: "4 axle+ truck", data: ["1430441008000", 50].

列显示正确,唯一的问题是所有内容的日期为 1970 年 1 月 1 日。完整的代码在片段中,您会在问题的末尾找到一段 CSV 用于测试目的。

let rawData;
let dataArray = [];
const labels = {"1": "2 axle car", "2": "2 axle truck", "3": "3 axle truck",
    "4": "4 axle+ truck", "5": "2 axle bus", "6": "3 axle bus", "2P": "park patrol"};

$(document).ready(function(){
    d3.csv("/csv/data.csv", function(error, d){
        if (error) throw error;
        rawData=d;


        piechart(pieChartHelper());
        timeLine(timeLineHelper());
    });
});


function piechart(pieData){
    Highcharts.chart('container', {
        chart: {
            plotBackgroundColor: null,
            plotBorderWidth: null,
            plotShadow: false,
            type: 'pie'
        },
        title: {
            text: 'Vehicle Types'
        },
        tooltip: {
            pointFormat: '{series.name}: <b>{point.percentage:.1f}%</b>'
        },
        plotOptions: {
            pie: {
                allowPointSelect: true,
                cursor: 'pointer',
                dataLabels: {
                    enabled: true,
                    format: '<b>{point.name}</b>: {point.percentage:.1f} %',
                    style: {
                        color: (Highcharts.theme && Highcharts.theme.contrastTextColor) || 'black'
                    }
                }
            }
        },
        series: [{
            name: "Results",
            colorByPoint: true,
            data:pieData
        }]
    });
}

function pieChartHelper() {
    let pieData;
    let pieData2 = [];

    for (let i = 0; i < rawData.length; i++) {

        dataArray.push({
            name: labels[rawData[i]["car-type"]],
            y: rawData[i]["car-type"]!=="2P" ? Number(rawData[i]["car-type"]) : '8'
        });
    }

    pieData = d3.nest()
        .key(function(d){return d.name;})
        .rollup(function(d){
            return Math.round(d3.sum(d, function(g){return g.y;}));
        }).entries(dataArray);

    for (let i = 0; i < pieData.length; i++) {
        pieData2.push({
            name: pieData[i].key,
            y: pieData[i].values
        })
    }
    return pieData2;
}

function toTimestamp(strDate){
    let A = _.toInteger(strDate.slice(0,4));
    let M = _.toInteger(strDate.slice(5,7))-1;
    let D = _.toInteger(strDate.slice(8,10));
    let H = _.toInteger(strDate.slice(11,13));
    let m = _.toInteger(strDate.slice(14,16));
    let s = _.toInteger(strDate.slice(17,19));

    return Date.UTC(A,M,D,H,m,s);

}

function timeLine(data){

    Highcharts.chart('container2', {
        chart: {
            zoomType: 'x'
        },
        tooltip: {
            formatter: function() {
                var date = new Date(this.x);
                var year = date.getFullYear();
                return year + '<br/>' + '<span style="color:'+this.series.color+'">'+ this.series.name +'</span>: '+ this.y;
            },
        },
        title: {
            text: 'USD to EUR exchange rate over time'
        },
        subtitle: {
            text: document.ontouchstart === undefined ?
                'Click and drag in the plot area to zoom in' : 'Pinch the chart to zoom in'
        },
        xAxis: {
            type: 'datetime',
            dateTimeLabelFormats:{
                millisecond: '%H:%M:%S.%L',
                second: '%H:%M:%S',
                minute: '%H:%M',
                hour: '%H:%M',
                day: '%e. %b',
                week: '%e. %b',
                month: '%b \'%y',
                year: '%Y'
            }
        },
        yAxis: {
            title: {
                text: 'Exchange rate'
            }
        },
        legend: {
            enabled: false
        },
        plotOptions: {
            area: {
                fillColor: {
                    linearGradient: {
                        x1: 0,
                        y1: 0,
                        x2: 0,
                        y2: 1
                    },
                    stops: [
                        [0, Highcharts.getOptions().colors[0]],
                        [1, Highcharts.Color(Highcharts.getOptions().colors[0]).setOpacity(0).get('rgba')]
                    ]
                },
                marker: {
                    radius: 2
                },
                lineWidth: 1,
                states: {
                    hover: {
                        lineWidth: 1
                    }
                },
                threshold: null
            }
        },

        series: data
    });
}

function timeLineHelper(){
    let timeArray = [];
    let timeArray2 = [];
    console.log(rawData[0]["Timestamp"]);
    console.log(toTimestamp(rawData[0]["Timestamp"]));
    for (let i = 0; i < rawData.length; i++) {

        timeArray.push({
            name: labels[rawData[i]["car-type"]],
            data: {
                key: rawData[i]["Timestamp"].slice(0,10),
                value: 1
            }
        });
    }
    console.log("time array: "+ timeArray[0].data.key );

    timeArray = d3.nest()
        .key(function(d) { return d.name; })
        .key(function(d) { return d.data.key; })
        .rollup(function(v) { return d3.sum(v, function(d) { return (d.data.value); }); })
        .entries(timeArray);

    for (let i = 0; i < timeArray.length; i++) {
        timeArray2.push({
            type: 'column',
            name: timeArray[i].key,
            data: [
                _.toString(toTimestamp(rawData[i]["Timestamp"])),
                timeArray[i].values[0].values]
        });
    }
    console.log(timeArray2);
    return timeArray2;

}
<!DOCTYPE html>
<html lang="en">
<head>
    <title>Progetto VA</title>
    <meta http-equiv="x-ua-compatible" content="ie=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />

    <link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0/css/bootstrap.min.css">
    <link rel="stylesheet" href="https://fonts.googleapis.com/css?family=Raleway:400,800">
    <link rel='stylesheet' href="https://maxcdn.bootstrapcdn.com/font-awesome/4.7.0/css/font-awesome.min.css">

</head>

<body>
<h1>IT WORKS!</h1>
<div id="container"></div>
<div id="container2"></div>

<script src="/js/jquery.min.js"></script>
<script src="/js/tether.min.js"></script>
<script src="/js/d3.min.js"></script>
<script src="/js/hc/highcharts.js"></script>
<script src="/js/va.js"></script>
<script src="/js/bootstrap.min.js"></script>
<script src="/js/lodash.js"></script>


</body>
</html>

CSV:

Timestamp,car-id,car-type,gate-name
2015-05-01 00:43:28,20154301124328-262,4,entrance3
2015-05-01 01:03:48,20154301124328-262,4,general-gate1
2015-05-01 01:06:24,20154301124328-262,4,ranger-stop2
2015-05-01 01:09:25,20154301124328-262,4,ranger-stop0
2015-05-01 01:12:36,20154301124328-262,4,general-gate2
2015-05-01 01:24:02,20154301124328-262,4,general-gate5
2015-05-01 01:31:41,20153101013141-937,1,entrance3
2015-05-01 01:33:57,20154301124328-262,4,entrance4
2015-05-01 01:53:34,20153101013141-937,1,general-gate1
2015-05-01 01:56:20,20153101013141-937,1,ranger-stop2
2015-05-01 01:59:36,20153101013141-937,1,ranger-stop0
2015-05-01 02:03:01,20153101013141-937,1,general-gate2
2015-05-01 02:15:17,20153101013141-937,1,general-gate5
2015-05-01 02:25:58,20153101013141-937,1,entrance4
2015-05-01 02:52:12,20155201025212-846,4,entrance1
2015-05-01 02:53:12,20155301025312-741,4,entrance3
2015-05-01 03:01:46,20150101030146-497,3,entrance4
2015-05-01 03:05:45,20155201025212-846,4,general-gate7
2015-05-01 03:13:05,20155201025212-846,4,general-gate4
2015-05-01 03:16:55,20155301025312-741,4,general-gate1
2015-05-01 03:19:56,20155301025312-741,4,ranger-stop2
2015-05-01 03:21:55,20150101030146-497,3,entrance2
2015-05-01 03:23:26,20155301025312-741,4,ranger-stop0
2015-05-01 03:24:45,20155201025212-846,4,general-gate1

标签: javascriptdatetimehighcharts

解决方案


我认为这是列格式的问题。现在,为每个值创建一个单独的系列(就像饼系列一样)。我认为您只想创建一个具有多个点的系列。启用列的图例以确认我在说什么。

这部分是错误的:

for (let i = 0; i < timeArray.length; i++) {
    timeArray2.push({
        type: 'column',
        name: timeArray[i].key,
        data: [
            _.toString(toTimestamp(rawData[i]["Timestamp"])),
            timeArray[i].values[0].values]
    });
}

应该更像这样:

timeArray2 = [{
    data: [],
    name: 'My series name',
    type: 'column'
}];
for (let i = 0; i < timeArray.length; i++) {
    timeArray2[0].data.push([
        _.toString(toTimestamp(rawData[i]["Timestamp"])),
        timeArray[i].values[0].values
    ]);
}

当然,这是@Mike Zavarello 所说的补充:更改stringnumberx 值。


推荐阅读