Multiline Highchart based on Dates - javascript

I want to create a multiline highchart which takes 24hrs in x axis and for each date plot one line.
[{
"date": "2017-05-01T02:50:26",
"value": 764.88
},
{
"date": "2017-05-02T12:29:07",
"value": 978.66
},
{
"date": "2017-05-04T08:30:20",
"value": 522.61
},
{
"date": "2017-05-04T12:29:34",
"value": 762.7
},
{
"date": "2017-05-02T11:09:56",
"value": 809.96
},
{
"date": "2017-05-03T03:32:35",
"value": 736.94
},
{
"date": "2017-05-04T12:56:53",
"value": 339.68
}
]
Here we have 4 unique dates i.e
2017-05-01 , 2017-05-02 , 2017-05-03 , 2017-05-04
and we want four lines of each date. But the x axis has to be hour:minute and y axis is value. I created a fiddle.

To change the way xAxis labels display, you can use Highcharts.dateFormat() function inside xAxis.labels.formatter. Take a look at the example posted below.
API Reference:
http://api.highcharts.com/highcharts/xAxis.labels.formatter
http://api.highcharts.com/highcharts/Highcharts.dateFormat
Example:
http://jsfiddle.net/x41vev1p/

Related

Moment JS ("Must to show days in next week")

I'm working on a weather service and I need to write a code for showing the weather forecast for next week. From the server, I only have a "time" entity with "value" of next Monday like "2020-04-06T00:00:00.000+02:00".
{
"message": "Show me the weather for next week",
"entities": [
{
"value": "weather",
"text": "weather",
"entity": "radio_tag"
},
{
"value": "play_next",
"text": "next",
"entity": "media_control"
},
{
"value": "next",
"text": "next",
"entity": "next"
},
{
"value": {
"values": [
{
"value": "2020-04-06T00:00:00.000+02:00",
"grain": "week",
"type": "value"
}
],
"value": "2020-04-06T00:00:00.000+02:00",
"grain": "week",
"type": "value"
},
"entity": "time"
},
{
"value": "weather_condition",
"entity": "sub_intent"
}
],
"intent": "weather_condition",
"user_id": "5258",
"language_id": "56",
"driver": "gigaaa",
"abort": "0",
"extras": {
"coordinates": {
"lat": "44.4150804",
"lng": "19.1290729"
}
},
"conversation_messages_count": "1"
}
For example, if today is Tuesday, I must show Monday and Tuesday for next week, if today is Saturday (04.04), I must show every day from Monday (06.04) to Saturday(11.04) for next week. I am a beginner and I must use Moment JS for this.
I tried this condition if (this.conversation.payload.grain === 'week' && moment().startOf('isoWeek').isSame(this.conversation.payload.forecastTime))
but the second part of condition is not correct.
We take the current date and check if we aren't in the same isoweek as the data in order to filter out data rows from the current week. We then take the current date and add a week so we can check that <1 week has passed.
Theoretically, as long as the timezone of the user and the returned data are the same, it should be what you need.
var valueFromData = this.conversation.payload.value;
var dateFromData = moment(valueFromData).startOf('day');
var oneWeek = moment().add(7,'d').startOf('day');
if(moment().startOf('isoweek').isBefore(dateFromData)
&& dateFromData.isBefore(oneWeek))

How to sort array of objects

I need your help to understand how to sort array of objects with another array inside each of object. I have response from api with array bunch of objects like below:
[
{
"name": "[C US Equity] CITIGROUP INC",
"stats": [
{
"label": "DTD",
"value": null
},
{
"label": "MTD",
"value": null
},
{
"label": "YTD",
"value": 0.0536530913792681
},
{
"label": 2016,
"value": 0.18102519526139493
},
{
"label": 2015,
"value": -0.012946569977188238
},
{
"label": 2014,
"value": null
}
]
}...
]
I should be sort it by value of label "YTD" exclude of null value. Any help are welcome
You can use array#sort method
var oldArray = [{
"name": "[C US Equity] CITIGROUP INC",
"stats": [{
"label": "DTD",
"value": null
},
{
"label": "MTD",
"value": null
},
{
"label": "YTD",
"value": 0.0536530913792681
},
{
"label": 2016,
"value": 0.18102519526139493
},
{
"label": 2015,
"value": -0.012946569977188238
},
{
"label": 2014,
"value": null
}
]
}];
oldArray[0].stats.sort(function(a, b) {
return a.label - b.label;
})
console.log(oldArray)
You can use collection sort method provided by lodash. https://lodash.com/docs/4.17.4#sortBy
var users = [{
"name": "[C US Equity] CITIGROUP INC",
"stats": [
{
"label": "DTD",
"value": null
},
{
"label": "MTD",
"value": null
},
{
"label": "YTD",
"value": 0.0536530913792681
},
{
"label": null,
"value": 0.18102519526139493
},
{
"label": "2015",
"value": -0.012946569977188238
},
{
"label": "dtd",
"value": null
}
]
}]
console.log(_.sortBy(users[0].stats, [function(o) { if(o.label){return  o.label.toUpperCase();} }]));
This takes case of null values too.
I think this post may help you.
Take a look of it, it teaches you about how compare works.
All you need to do is to put that JSON thing into an object array,
then compare the value of YTD(make two for-loops, result [i] .stats [j] .label === 'YTD') to make the array to re-order it.
A comparison function is work like below(extracted from the above link)
function CompareNumbers( v1, v2 ) {
if ( v1 < v2 ) return -1; // v1 goes nearer to the top
if ( v1 > v2 ) return 1; // v1 goes nearer to the bottom
return 0; // both are the same
}
when it return -1(or sometimes false), the former one will be pushed to the front of your array, meanwhile 1 or true will push the former one to the back. And 0 (means not true or false, or you can handle the exception by yourself, push back or forward) will happen nothing.
But becare if your array exist two 'YTD' labelled value, if it happens it will make two value to appear in the same data.
This may help you in sorting the data while you cannot directly get a sorted data from your db server.
Oh, forgot to say, the compare function can compare the whole object.(of course you need to extract something like this ---> object[index].['Something your needed']), not only numbers.

Swimlane ngx-charts in Angular2 - Different styles on a single line chart

I have a single line chart, with dates on the X axis. After a certain date,
I would like the line to be a different color. Is this possible using ngx-charts?
Let us assume the date after which you want to change the color as T.
Now you can divide the series into 2 parts
The from start date to T
From T to end date.
And now you can plot the graph using different color for different series
The following data will generate the desired graph.
var data = [
{
"name": "Current",
"series": [
{
"value": 5599,
"name": "2016-09-20T01:04:28.176Z"
},
{
"value": 6247,
"name": "2016-09-20T12:51:24.713Z"
},
{
"value": 4283,
"name": "2016-09-18T15:42:04.800Z"
},
{
"value": 2643,
"name": "2016-09-13T20:10:53.904Z"
},
{
"value": 4105,
"name": "2016-09-18T06:15:10.845Z"
},
{
"name": "2016-09-18T13:08:42.085Z",
"value": 4401
},
{
"name": "2016-09-20T01:04:28.176Z",
"value": 3443
}
]
},
{
"name": "Future",
"series": [
{
"value": 3443,
"name": "2016-09-20T01:04:28.176Z"
},
{
"value": 2604,
"name": "2016-09-20T12:51:24.713Z"
},
{
"value": 2158,
"name": "2016-09-18T15:42:04.800Z"
},
{
"value": 5519,
"name": "2016-09-13T20:10:53.904Z"
},
{
"value": 4532,
"name": "2016-09-18T06:15:10.845Z"
},
{
"name": "2016-09-18T13:08:42.085Z",
"value": 2474
}
]
}
]

How to generate a Control Chart using D3.js?

I need a solution to represent the below data in D3.js
Ideally the chart should look similar to the example below.
Based on the following dataset I need to generate a Control Chart for the Javascript application am currently working on. I know D3.js has a lot of chart types but couldn't find which best fits the data. Some sample code would be great.
Dataset in Json format
{
"results": [
{
"individualValues":
{
"usl": 57.84,
"nom": 47.7,
"lsl": 37.56,
"readings": [
{
"date": "2017-01-01T00:00:00.000Z",
"value": 46.09
},
{
"date": "2017-01-01T01:00:00.000Z",
"value": 49.12
},
{
"date": "2017-01-01T02:00:00.000Z",
"value": 51.67
},
{
"date": "2017-01-01T02:00:00.000Z",
"value": 45.67
}]
}
},
{
"movingRangeValues":
{
"usl": 12.46,
"nom": 3.81,
"lsl": 0,
"readings": [
{
"date": "2017-01-01T00:00:00.000Z",
"value": 3.09
},
{
"date": "2017-01-01T01:00:00.000Z",
"value": 1.12
},
{
"date": "2017-01-01T02:00:00.000Z",
"value": 7.67
},
{
"date": "2017-01-01T02:00:00.000Z",
"value": 1.67
}]
}
}]
}
Expected result should look like this: .

d3js roll up a nested JSON array and sum up a total value

I have this JSON
[{
"month": "september",
"detail": [{
"date": "01-09",
"value": 5
}, {
"date": "02-09",
"value": 5
}, {
"date": "03-09",
"value": 5
}, {
"date": "04-09",
"value": 5
}, {
"date": "05-09",
"value": 5
}, {
"date": "06-09",
"value": 5
}, {
"date": "07-09",
"value": 0
}]
},
{
"month": "october",
"detail": [{
"date": "01-10",
"value": 10
}, {
"date": "02-10",
"value": 5
}, {
"date": "03-10",
"value": 5
}, {
"date": "04-10",
"value": 5
}, {
"date": "05-10",
"value": 5
}, {
"date": "07-10",
"value": 10
}]
}
I want to roll up the all the "value" in the object "detail" for each specific month using d3nest. If you count all the values for each specific months it would result in: september-value: 30 & october-value: 40.
I've tried nesting it but I can't get it right to sum up the values for each month. see my code.
d3.json('runningdata.json', function (error, data) {
console.log(data);
var Total = d3.nest()
.key(function(d) { return d.month; })
.rollup(function(value) { return d3.sum(value, function(v) { return v.detail.value; }); })
.entries(data);
console.log(JSON.stringify(Total));
});
All of this above would result in:
[{"key":"september","values":0},{"key":"october","values":0}]
You can notice the "key" are working right, they have the month as value. but the "Values" field result in 0. what i am trying to achieve needs to be:
[{"key":"september","values":30},{"key":"october","values":40}]
But when i try this:
.rollup(function(value) { return d3.sum(value, function(v) { return v.detail[0].value; }); })
instead of:
.rollup(function(value) { return d3.sum(value, function(v) { return v.detail.value; }); })
it shows me the values of the first object in the arrays.
[{"key":"september","values":5},{"key":"october","values":10}]
What am i doing wrong? I have been reading about d3 nesting.
Any help is welcome.
Note:
Im trying achieve this to make a graph which presents the total of each months and when you click on the specific month it will view the details of its month in days.
You have to update your d3.sum function like so:
d3.sum(value[0].detail, function(v) {
return v.value;
});
So your whole code would be:
var Total = d3.nest()
.key(function(d) {
return d.month;
})
.rollup(function(value) {
return d3.sum(value[0].detail, function(v) {
return v.value;
});
})
.entries(data);
You can just use basic javascript .reduce() function to do the trick. This will roll up your array of object structure into a single object with the months as the property name and the sum of the values as the value. The advantage to doing it this way is that if you want to get, say, the total for the month of September, you can simply say combined.september, rather than having to iterate through an array, searching for the object with the key property equal to "september" and then extracting the value. However, if you need to keep your original structure, see the slightly modified version at the bottom of my answer.
var data = [{
"month": "september",
"detail": [{
"date": "01-09",
"value": 5
}, {
"date": "02-09",
"value": 5
}, {
"date": "03-09",
"value": 5
}, {
"date": "04-09",
"value": 5
}, {
"date": "05-09",
"value": 5
}, {
"date": "06-09",
"value": 5
}, {
"date": "07-09",
"value": 0
}]
},
{
"month": "october",
"detail": [{
"date": "01-10",
"value": 10
}, {
"date": "02-10",
"value": 5
}, {
"date": "03-10",
"value": 5
}, {
"date": "04-10",
"value": 5
}, {
"date": "05-10",
"value": 5
}, {
"date": "07-10",
"value": 10
}]
}];
var combined = data.reduce(function (total, current){
total[current.month] = current.detail.reduce(function(tot, curr) {
return tot + curr.value;
}, 0);
return total;
}, {});
console.log(combined);
Edit -- if you need to keep your original {"key": "..", "values", ".."} structure
You can use .map() rather than .reduce() like so:
var combined = data.map(function (elem){
var total = elem.detail.reduce(function(total, current) {
return total + current.value;
}, 0);
return {key: elem.month, values: total};
});
console.log(combined);
// output:
// [ { key: 'september', value: 30 },
// { key: 'october', value: 40 } ]

Categories

Resources