make zoom using nvd3 - angularjs

I need make zoom in graphic. I am using angular js and nvd3.
this is a part of my Code, html and angular module:
var app = angular.module('DL', ['nvd3']);
app.controller('daCtrl', function($scope) {
$scope.graphic = [{key: "a", values: [[243434, 1],[363352, 2],...]}, [[243434, 1],[363352, 2],...]},... ];
$scope.options = {
chart: {
type: "lineChart",
height: 450,
margin : {
top: 20,
right: 20,
bottom: 60,
left: 65
},
x: function(d){ return d[0]; },
y: function(d){ return d[1]/100; },
average: function(d) { return d.mean/100; },
color: d3.scale.category10().range(),
transitionDuration: 300,
useInteractiveGuideline: true,
clipVoronoi: false,
xAxis: {
axisLabel: 'Date',
tickFormat: function(d) {
return d3.time.format('%m/%d/%y')(new Date(d));
}
},
yAxis: {
axisLabel: 'Measure',
tickFormat: function(d){
return d3.format('.02f')(d);
},
axisLabelDistance: 20,
showMaxMin: true,
staggerLabels: true
}
}
};
});
<link rel="stylesheet" type="text/css" href="../bower_components/nvd3/nv.d3.css">
<script src="../bower_components/d3/d3.js"></script>
<script src="../bower_components/nvd3/nv.d3.js"></script>
<script src="../bower_components/angular-nvd3/dist/angular-nvd3.js"></script>
<nvd3 options="options" data="graphic"></nvd3>
The graphic is ok, but I need make zoom over the graphic.
I've seen that D3 is possible, but not if you can with equally nvd3

Try to use a lineWithFocusChart instead of lineChart and then add this options to your chart:
x2Axis: {
tickFormat: function (d) {
return d3.time.format('%m/%d/%y')(new Date(d));
}
},
y2Axis: {
tickFormat: function(d){
return d3.format('.02f')(d);
}
}

I know that I am two years late to the party but zooming in angularjs is totally a thing, just add something like:
zoom: {
enabled: true,
scaleExtent: [1, 10000],
useFixedDomain: false,
useNiceScale: false,
horizontalOff: false,
verticalOff: true,
unzoomEventType: "dblclick.zoom"
}
To your chart options

I changed nvd3 to dygraph using Dygraphs angularjs Directive (https://twittstrap.com/dygraphs-angularjs-directive/)
Now (the same example of website)
HTML:
<head>
<script src="bower_components/jquery/dist/jquery.min.js"></script>
<script src="bower_components/dygraphs/dygraph-combined.js"></script>
<script src="bower_components/angular/angular.min.js"></script>
<script src="bower_components/angular-sanitize/angular-sanitize.js"></script>
<script src="bower_components/moment/moment.js"></script>
<script src="bower_components/bootstrap/dist/js/bootstrap.min.js"></script>
<script src="bower_components/angular-dygraphs/src/angular-dygraphs.js"></script>
<!--<link rel="stylesheet" type="text/css" href="bower_components/angular-dygraphs/demo/demo.css"/>-->
<link rel="stylesheet" href="bower_components/bootstrap/dist/css/bootstrap.min.css">
</head>
<body ng-app="demoApp">
<div ng-controller="DemoCtrl">
<ng-dygraphs data="graph.data" options="graph.options" legend="graph.legend"></ng-dygraphs>
<div>
</body>
js:
var example = angular.module('demoApp', [
"angular-dygraphs"
]);
demoApp.controller('DemoCtrl', function ($scope) {
$scope.graph = {
data: [
],
options: {
labels: ["x", "A", "B"]
},
legend: {
series: {
A: {
label: "Series A"
},
B: {
label: "Series B",
format: 3
}
}
}
};
var base_time = Date.parse("2008/07/01");
var num = 24 * 0.25 * 365;
for (var i = 0; i < num; i++) {
$scope.graph.data.push([ new Date(base_time + i * 3600 * 1000),
i + 50 * (i % 60), // line
i * (num - i) * 4.0 / num // parabola
]);
}
});

Related

Showing datetime in x axis of shield ui chart

I am trying to show a chart with datetime x axis, i tried different formats for the date time field and none of them works(chart is not displayed) unless i send as year only for example:2019.
Below is the code i am using.
I appreciate any help on this please.
Regards
Nader
<!DOCTYPE html>
<html>
<head>
<meta charset=utf-8 />
<title>JS Bin</title>
<link rel="stylesheet" type="text/css" href="//www.shieldui.com/shared/components/latest/chart/css/shield-chart.min.css" />
<script type="text/javascript" src="//www.shieldui.com/shared/components/latest/chart/js/jquery-1.9.1.min.js"></script>
<script type="text/javascript" src="//www.shieldui.com/shared/components/latest/chart/js/shield-chart.all.min.js"></script>
</head>
<body>
<div id="chart"></div>
</body>
</html>
//Fill datasource
var industryPrices = [
{ x: '2009-11-09 00:00:00.000', y: 0.103 },
{ x: '2009-11-09 00:00:00.000', y: 0.105 },
{ x: '2009-11-09 00:00:00.000', y: 0.112 },
{ x: '2009-11-09 00:00:00.000', y: 0.111 }
];
//Initialize the shield chart
$("#chart").shieldChart({
theme: "light",
exportOptions: {
image: false,
print: false
},
primaryHeader: {
text: "Results chart"
},
chartLegend: {
align: 'right',
verticalAlign: 'top',
renderDirection: 'vertical'
},
seriesSettings: {
line: {
enablePointSelection: true,
pointMark: {
activeSettings: {
pointSelectedState: {
drawWidth: 4,
drawRadius: 4
}
}
}
}
},
axisX: {
axisType: 'datetime',
},
axisY: {
title: {
text: "Results"
}
},
//Set data source for chart
dataSeries: [{
seriesType: 'line',
collectionAlias: "Results",
data: industryPrices
}]
});

Highstock highcharts stacked column jQuery.getJSON array not working

I have developed a very simple column chart from a json three dimensional array:
0: timestamp in millliseconds
1:given recognition
2:received recognition
[[1490288274653,7,175],[1490374674653,1,1],[1490806674653,1,1],[1490979474653,3,3],[1491065874653,4,4],[1491411474653,6,0],[1491497874653,2,0],[1491584274653,18,0],[1491843474653,8,0],[1491929874653,1,0],[1492621074653,25,0],[1492707474653,12,0],[1492793874653,2,0],[1501174674653,2,0],[1503593874653,2,2],[1510765074653,1,0],[1510851474653,1,1],[1510937874653,5,0],[1511197074653,7,3],[1511369874653,7,2],[1511542674653,1,0],[1511801874653,7,3],[1511974674653,1,0],[1512493074653,1,1],[1512665874653,2,2],[1512752274653,9,4],[1513184274653,2,2],[1513270674653,2,2],[1513616274653,3,0],[1513789074653,4,2],[1514912274653,1,0],[1515430674653,1,0]]
The array displays timestamp on the xAxis and given recognition on the y axis.
How do I create a stacked column with "received recognition" stacked on "given recognition" on the yAxis?
I have searched google for hours and I can't find an example that uses same json array like mine, without strings as catagories.
I assume I will have to customise series or plotOptions and identify the data columns via the number data[1], data[2]?
How will I achieve a similar column like this CSV column:
http://marialaustsen.com/columncsv.html
HTML:
<!doctype html>
<html>
<head>
<meta charset="UTF-8">
<title>myGraph</title>
<!--
<link href="http://ajax.googleapis.com/ajax/libs/jqueryui/1.8/themes/base/jquery-ui.css" type="text/css" rel="stylesheet" />
-->
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.2.1/jquery.min.js"></script>
<link href="https://code.jquery.com/ui/1.12.0/themes/smoothness/jquery-ui.css" type="text/css" rel="stylesheet" />
<script src="https://code.jquery.com/ui/1.12.0/jquery-ui.js" integrity="sha256-0YPKAwZP7Mp3ALMRVB2i8GXeEndvCq3eSl/WsAl1Ryk=" crossorigin="anonymous"></script>
<!-- <script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jqueryui/1.8.21/jquery-ui.min.js"></script>-->
<!-- Highcharts is already included in Highstock, so it is not necessary to load both. The highstock.js file is included in the package. -->
<script src="http://code.highcharts.com/stock/highstock.js"></script>
<!-- But the separate files can't run in the same page along with each other or with highcharts.js. So if stock or maps are required in the same page as each other or with basic Highcharts, they can be loaded as modules: -->
<script src="http://code.highcharts.com/modules/exporting.js"></script>
</head>
<body>
<div id="container" style="height: 400px; width: 100%"></div>
<script>
$(function() {
console.log($);
$.getJSON('http://localhost:3000/recognition', function(data) {
// Create the chart
window.chart = new Highcharts.StockChart({
chart: {
type: 'column',
renderTo: 'container'
},
legend: {
enabled: true,
},
tooltip: {
pointFormat: '<span style="color:{point.color}">\u25CF </span> <b>{point.series.name}: <b>{point.y}</b> ({point.percentage:.1f}%)<br/>',
valueSuffix: ' k',
shared: true,
},
series: [{
name: 'Brands',
data: data
}],
rangeSelector: {
selected: 1,
inputDateFormat: '%Y-%m-%d',
floating: true,
y: -75,
verticalAlign: 'bottom'
},
title: {
text: 'Team members received and sent recognition'
},
navigator: {
margin: 50
},
xAxis: {
type: 'datetime',
title: {
text: 'DATES'
}
},
yAxis: {
title: {
text: 'BRANDS'
}
},
plotOptions: {
column: {
stacking: 'normal'
}
},
}, function(chart) {
// apply the date pickers
setTimeout(function() {
$('input.highcharts-range-selector', $('#' + chart.options.chart.renderTo)).datepicker()
}, 0)
});
});
// Set the datepicker's date format
$.datepicker.setDefaults({
dateFormat: 'yy-mm-dd',
onSelect: function(dateText) {
chart.xAxis[0].setExtremes($('input.highcharts-range-selector:eq(0)').datepicker("getDate").getTime(), $('input.highcharts-range-selector:eq(1)').datepicker("getDate").getTime());
//this.onchange();
this.onblur();
}
});
});
</script>
</body>
</html>
You need to prepare your data - split it into 2 separate series:
series: (function() {
var series = [{
name: 'received recognition',
data: []
}, {
name: 'given recognition',
data: []
}];
data.forEach(function(p) {
series[0].data.push([p[0], p[1]]);
series[1].data.push([p[0], p[2]]);
});
return series;
})()
Live demo: http://jsfiddle.net/kkulig/88sr9ofn/

updating high chart on real time in angular js after a particular time

I want to update high chart on real time in angular js after a particular time span and it should get reflects on html without user interaction in angular JS.
Below are code for Controller,Directive and HTML. I am using rest web service to fetch the data from back end.
Controller :
function dashboardController($scope, $http) {
this.$scope = $scope;
$scope.init=function(){
_refreshPageData();
function _refreshPageData() {
$http({
method : 'GET',
url : 'http://localhost:8080/SpringWebApp/rest/employee/monthlydata'
}).then(function successCallback(response) {
$scope.data = response.data;
var data = $scope.data;
var a = [];
parseInt($scope.data[0].data);
angular.forEach(data, function(data, key) {
a.push(parseInt(data.data));
});
console.log($scope.data);
$scope.chartConfig = {
xAxis: {
categories: ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun',
'Jul', 'Aug', 'Sep', 'Oct', 'Nov', 'Dec']
},
title: {
text: 'USD to EUR exchange rate from 2006 through 2008'
}, subtitle: {
text: document.ontouchstart === undefined ?
'Click and drag in the plot area to zoom in' :
'Pinch the chart to zoom in'
},
yAxis: { title: { text: 'Temperature (Celsius)' } },
tooltip: { valueSuffix: ' celsius' },
legend: { align: 'center', verticalAlign: 'bottom', borderWidth: 0 },
plotOptions: {
area: {
fillColor: {
linearGradient: { x1: 200, y1: 220, x2: 220, y2: 2221},
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: [{
type:'area',
data :a
}]
};
}, function errorCallback(response) {
console.log(response.statusText);
});
}
}
}
Directive :
var chartDirective = function () {
return {
restrict: 'E',
replace: true,
template: '<div></div>',
scope: {
config: '='
},
link: function (scope, element, attrs) {
var chart;
var process = function () {
var defaultOptions = {
chart: { renderTo: element[0] },
};
var config = angular.extend(defaultOptions, scope.config);
chart = new Highcharts.Chart(config);
};
process();
scope.$watch("config.series", function (loading) {
process();
});
scope.$watch("config.loading", function (loading) {
if (!chart) {
return;
}
if (loading) {
chart.showLoading();
} else {
chart.hideLoading();
}
});
}
};
};
Html :
<!DOCTYPE html>
<html lang="en">
<head>
<script data-require="angular.js#*" data-semver="1.2.5" src="http://code.angularjs.org/1.2.5/angular.js"></script>
<script data-require="jquery#*" data-semver="2.0.3" src="http://code.jquery.com/jquery-2.0.3.min.js"></script>
<script data-require="highcharts#*" data-semver="2.3.5" src="//cdnjs.cloudflare.com/ajax/libs/highcharts/2.3.5/highcharts.js"></script>
<script src="chartDirective.js"></script>
<script src="dashboardController.js"></script>
<script src="app.js"></script>
<meta charset="utf-8">
</head>
<body ng-app="app">
<div ng-controller="dashboardController">
<div ng-init="init()"></div>
<chart config="chartConfig"></chart>
</div>
</body>
</html>
You can make a request based on the interval using $interval
$interval(function() {
YourApi.response.then,
series.addPoint([whatever);
}, 1000);

nvd3 AngularJS date format issue - non-epoch

I am using nvd3 chart in AngularJS. I am getting the data like series of [{"09/01/2015", 5},...]. i.e. [{mm/dd/yyyy, decimal}]. After checking NVD3 tutorial looks like date needs to be in epoch format, which is not possible for my case. I dont see any reference for that. How can make a line chart with Y axis some decimal values and X axis month-year or complete date without converting to epoch format.
Any reference or tutorial also would be a great help. Thanks in advance...
My Code:
var appCntrl = angular.module("AppCntrl",['nvd3']);
appCntrl.controller("QPBDController", function($scope){
$scope.score = {
"data":[7.97,8.93,6.53,4.87,4.98,4.56],
"term":["09/01/2015","10/01/2015","11/01/2015","12/01/2015","01/01/2016","02/01/2016"]
};
$scope.options = {
chart: {
type: 'lineChart',
height: 450,
margin : {
top: 20,
right: 20,
bottom: 40,
left: 55
},
x: function(d){ return d.x; },
y: function(d){ return d.y; },
useInteractiveGuideline: true,
dispatch: {
stateChange: function(e){ console.log("stateChange"); },
changeState: function(e){ console.log("changeState"); },
tooltipShow: function(e){ console.log("tooltipShow"); },
tooltipHide: function(e){ console.log("tooltipHide"); }
},
xAxis: {
tickFormat: function(d) {return d3.time.format("%b %d, %Y")(d);}
},
yAxis: {
axisLabel: 'Voltage (v)',
tickFormat: function(d){
return d3.format('.02f')(d);
},
axisLabelDistance: -10
},
callback: function(chart){
console.log("!!! lineChart callback !!!");
}
},
title: {
enable: true,
text: 'Title for Line Chart'
},
subtitle: {
enable: true,
text: 'Subtitle for simple line chart.',
css: {
'text-align': 'center',
'margin': '10px 13px 0px 7px'
}
},
caption: {
enable: true,
html: '<b>Figure 1.</b> .',
css: {
'text-align': 'justify',
'margin': '10px 13px 0px 7px'
}
}
};
$scope.data = sinAndCos();
var str = ["s"];
/*Random Data Generator */
function sinAndCos() {
var sin = [],sin2 = [],
cos = [];
//Data is represented as an array of {x,y} pairs.
for (var i = 0; i < $scope.score.term.length; i++) {
sin.push({x: $scope.score.term[i], y: $scope.score.data[i]});
sin2.push({x: $scope.score.term[i], y: $scope.score.data[i]});
cos.push({x: $scope.score.term[i], y: $scope.score.data[i]});
}
console.log(sin);
//Line chart data should be sent as an array of series objects.
return [
{
values: sin, //values - represents the array of {x,y} data points
key: 'Sine Wave', //key - the name of the series.
color: '#ff7f0e', //color - optional: choose your own line color.
strokeWidth: 2,
classed: 'dashed'
},
{
values: cos,
key: 'Cosine Wave',
color: '#2ca02c'
},
{
values: sin2,
key: 'Another sine wave',
color: '#7777ff',
area: true //area - set to true if you want this line to turn into a filled area chart.
}
];
};
});
index.html:
<link href="node_modules/bootstrap/dist/css/bootstrap.min.css" rel="stylesheet">
<link href="css/app.css" rel="stylesheet">
<script src="node_modules/angular/angular.min.js"></script>
<script src="node_modules/angular-ui-router/release/angular-ui-router.min.js"></script>
<script src="node_modules/d3/d3.min.js"></script>
<script src="node_modules/nvd3/build/nv.d3.min.js"></script>
<script src="node_modules/angular-nvd3/dist/angular-nvd3.min.js"></script>
<link href="node_modules/nvd3/build/nv.d3.min.css" rel="stylesheet">
<script src="bizkpi.js"></script>
<script src="js/controllers.js"></script>
<nvd3 options="options" data="data"></nvd3>
The above code shows an error in console like below and nothing comes up in GUI
TypeError: n.getMonth is not a function
at Yn.A.b (d3.min.js:1)
at t (d3.min.js:1)
at SVGTextElement.$scope.options.chart.xAxis.tickFormat (controllers.js:29)
at SVGTextElement.arguments.length.each.function.n.textContent (d3.min.js:3)
at d3.min.js:3
at Y (d3.min.js:1)
at Array.Co.each (d3.min.js:3)
at Array.Co.text (d3.min.js:3)
at SVGGElement.<anonymous> (d3.min.js:5)
you will have to format the date as follows:
vm.chart.options.chart.xAxis.tickFormat = function(d) {return d3.time.format("%b %d, %Y")(d);};
in your options.chart you should have :
lines: {
xScale: d3.time.scale(),
},
I think you should set the ticks and tickValues as well for example..
vm.chart.options.chart.xAxis.ticks = d3.time.monday;
vm.chart.options.chart.xAxis.tickValues = function(d) {return d3.time.monday.range(from, to, 2);};
};

To pass dynamic json array to Highcharts Pie Chart

I passed json encoded string(eg. $TEXT2 consisting ["chrome","15","firefox","20"]) from xcode to an array(eg. arr) in javascript.Now I want to pass this array containing json string dynamically to Highcharts Pie. The HTML code is
<!DOCTYPE HTML>
<html>
<head>
<meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=20, user-scalable=no;" />
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<title>Pie chart</title>
<!-- 1. Add these JavaScript inclusions in the head of your page -->
<script type="text/javascript" src="jquery-1.6.2.js"></script>
<script type="text/javascript" src="highcharts.js"></script>
<script type="text/javascript" src="jquery.form.js"></script>
<!-- 2. Add the JavaScript to initialize the chart on document ready -->
<script type="text/javascript">
var chart;
var arr = $TEXT2;
$(document).ready(function(){
chart = new Highcharts.Chart({
chart: {
renderTo: 'container',
plotBackgroundColor: null,
plotBorderWidth: null,
plotShadow: false
},
title: {
text: 'Interactive Pie'
},
tooltip: {
formatter: function() {
return '<b>'+ this.point.name +'</b>: '+ this.y +' %';
}
},
plotOptions: {
pie: {
allowPointSelect: true,
cursor: 'pointer',
dataLabels: {
enabled: false
},
showInLegend: true
}
},
series: [{
type: 'pie',
name: 'Browser share',
data: []
}]
});
});
</script>
<body>
<br>
<!-- 3. Add the container -->
<div id="container" style="width: 300px; height: 350px; margin: 0 auto"></div>
<!-- 2. Add the JavaScript to initialize the chart on document ready -->
</body>
</html>
I am trying to use getjson method although m unaware of its usage.
Since i want to pass my array i.e arr to data[] in Highcharts,I am doing:
$.getJSON("arr", function(json) {
chart.series = json;
var chart = new Highcharts.Chart(chart);
});
Can anyone help me on dis.
Thanks in advance.
I would wrap the JSON call in the document.ready function and then wrap the plot call in the getJSON's success callback:
$(document).ready(function() {
$.getJSON("arr", function(json) {
chart = new Highcharts.Chart({
chart: {
renderTo: 'container',
plotBackgroundColor: null,
plotBorderWidth: null,
plotShadow: false
},
title: {
text: 'Interactive Pie'
},
tooltip: {
formatter: function() {
return '<b>'+ this.point.name +'</b>: '+ this.y +' %';
}
},
plotOptions: {
pie: {
allowPointSelect: true,
cursor: 'pointer',
dataLabels: {
enabled: false
},
showInLegend: true
},
series: [{
type: 'pie',
name: 'Browser share',
data: json
}]
});
});
});
Of course for this to work, you should modify your backend code to return a properly formatted array of arrays that HighCharts expects:
[["chrome",15],["firefox",20]]
You could "fix" your returned array in the JS, but it would be better to do it in the JSON backend call.
<script type="text/javascript">
jQuery(document).ready(function () {
alert('call pie');
var data1 = $("#dataidd").val();
alert('pie data' + data1);
/*--------Pie Chart---------*/
$('#PieChartDiv').highcharts({
chart: {
plotBackgroundColor: null,
plotBorderWidth: null,
plotShadow: false
},
title: {
text: 'Comparision and Analysis Report'
},
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: [{
type: 'pie',
name: 'Issue Details',
// data: jQuery.parseJSON(data1)
data: JSON.parse(data1)
}]
});
});
</script>
Simply do :
Create array with Jquery as bellow :
$.each(data['values'], function(i, val) {
x_values_sub['name'] = i
x_values_sub['y'] = val
x_values.push(x_values_sub);
x_values_sub = {};
});
// Then call this array with HighCharts as data
series: [{
type: 'pie',
name: null,
data: x_values
}]
// Tested and it works with simple javascript object :
Object Part1Name: 25 Part2Name: 75__proto__: Object
You can bind chart with JSON data, directly. You just need to set the json property names as highchart standard. 'Y' for value and 'name' for label.
Your JSON should be as like follow:
[ { name: "Chrome", y: 25 }, { name: "Firefox", y: 20 } ]

Resources