How to get quantize values - d3.js

is there a way to get the start and end values of the quantizes of an quantize scale.
The range is defined by 5 colors ans the domain by d3.min and d3.max function on my data from an json file.
I need them for my legend of an choropleth map.
Thank you for helping.
Carsten
Thats my code
var quantizecolors = ["#d7191c","#fdae61","#ffffbf", "#a6d96a","#1a9641"];
var colorEnerg = d3.scale.quantize().range(quantizecolors);
colorEnerg.domain([
d3.min(collection.features, function(d){return d.properties.EB/d.properties.BEVZ;}),
d3.max(collection.features, function(d){return d.properties.EB/d.properties.BEVZ;})
]);

I assume that you're asking about the minimum and maximum domain values. Apart from saving them when you're setting them, you can also call colorEnerg.domain() without any values, which will return the array [min, max].
You can get the position of the breaks by computing the number and position of intervals:
var dom = colorEnerg.domain(),
l = (dom[1] - dom[0])/colorEnerg.range().length,
breaks = d3.range(0, colorEnerg.range().length).map(function(i) { return i * l; });

Related

No data in area chart

I have an area chart I am using from http://bl.ocks.org/mbostock/3883195 with a simple modification of using json data.
The json is returned without issue, and no other errors present themselves, however, no chart is displayed.
The x and y axes are displayed, but no chart.
jsfiddle.net/oqc19yff/
Any pointers welcome.
Kev
This is incorrect:
x.domain(d3.extent(data, function(d) { return d.event_time; }));
Reason:
Because x is an ordinal scale.
Instead it should have been:
//declare a variable array
var k = [];
data.forEach(function(d) {
d.event_time = d.event_time;
d.total = +d.total;
k.push(d.event_time);//in that array store all the event_time
});
Now set that array as domain of x.
x.domain(k);
working code here

How to find max value from a 2D matrix using D3.js

I have data of the following format
var data=[[5,2,3,6],[10,22,10,5],[2,3,4,5],[50,30,20,13]];
That means its a M*N array actually. How can i use d3.max from this array. I need the get the single value i.e. 50. I was trying with
var max=d3.max(data,function(d){return d});
But it's not working. Can anyone help me?
Thanks in advance
Your code will try to find the maximum of four arrays. What you actually need is another call to d3.max within the other call:
var max = d3.max(data, function (d) {
return d3.max(d);
});

For NVD3 lineChart Remove Missing Values (to be able to interpolate)

I am using NVD3 to visualise data on economic inequality. The chart for the US is here: http://www.chartbookofeconomicinequality.com/inequality-by-country/USA/
These are two lineCharts on top of each other. The problem I have is that there are quite a lot of missing values and this causes two problems:
If I would not make sure that the missing values are not visualised the line Chart would connect all shown values with the missing values. Therefore I used the following to not have the missing values included in the line chart:
chart = nv.models.lineChart()
.x(function(d) { return d[0] })
.y(function(d) { return d[1]== 0 ? null : d[1]; })
But still if you hover over the x-axis you see that the missing values are shown in the tooltip on mouseover. Can I get rid of them altogether? Possibly using remove in NVD3?
The second problem is directly related to that. Now the line only connects values of the same series when there is no missing values in between. That means there are many gaps in the lines. Is it possible to connect the dots of one series even if there are missing values in between?
Thank you for your help!
As Lars showed, getting the graph to look the way you want is just a matter of removing the missing values from your data arrays.
However, you wouldn't normally want to do that by hand, deleting all the rows with missing values. You need to use an array filter function to remove the missing values from your data arrays.
Once you have the complete data array as an array of series objects, each with an array of values, this code should work:
//to remove the missing values, so that the graph
//will just connect the valid points,
//filter each data array:
data.forEach(function(series) {
series.values = series.values.filter(
function(d){return d.y||(d.y === 0);}
);
//the filter function returns true if the
//data has a valid y value
//(either a "true" value or the number zero,
// but not null or NaN)
});
Updated fiddle here: http://jsfiddle.net/xammamax/8Kk8v/
Of course, when you are constructing the data array from a csv where each series is a separate column, you can do the filtering at the same time as you create the array:
var chartdata = [];//initialize as empty array
d3.csv("top_1_L-shaped.csv", function(error, csv) {
if (error)
return console.log("there was an error loading the csv: " + error);
var columndata = ["Germany", "Switzerland", "Portugal",
"Japan", "Italy", "Spain", "France",
"Finland", "Sweden", "Denmark", "Netherlands"];
for (var i = 0; i < columndata.length; i++) {
chartdata[i].key = columndata[i];
chartdata[i].values = csv.map(function(d) {
return [+d["year"], +d[ columndata[i] ] ];
})
.filter(function(d){
return d[1]||(d[1] === 0);
});
//the filter is applied to the mapped array,
//and the results are assigned to the values array.
}
});

d3 retrieve and add to current selection's attribute value

I'm trying to get the values for an element's translation.
For example, if I select the x axis:
d3.select('.x.axis').attr("transform")
then I get
"translate(0,112)"
How do I get the 0 and the 112 without parsing a regexp?
I'm trying to do it so that I can add to the value. In pseudocode:
d3.selectAll('.x.axis').attr('transform', 'translate('
.attr('transform').match(/(\d+)(\.\d+)?/g)[0] // <-- clearly won't work
+ additional_value
+ ', 0)');
D3 provides the transform() function for exactly this purpose:
var t = d3.transform(d3.select('.x.axis').attr("transform")),
x = t.translate[0],
y = t.translate[1];
if you would like to use selectAll you could try something like this:
// move ticks to the center of the x-axis
var transform;
d3.selectAll('.tick').attr('transform', function(){
transform = d3.transform(d3.select(this).attr("transform"));
return "translate("+transform.translate[0]+", -3)";
});

Is it possible to create pie charts with object consistency?

the pie chart update example on the bl.ocks site doesn't update the elements 'in place':
http://bl.ocks.org/j0hnsmith/5591116
function change() {
clearTimeout(timeout);
path = path.data(pie(dataset[this.value])); // update the data
// set the start and end angles to Math.PI * 2 so we can transition
// anticlockwise to the actual values later
path.enter().append("path")
.attr("fill", function (d, i) {
return color(i);
})
.attr("d", arc(enterAntiClockwise))
.each(function (d) {
this._current = {
data: d.data,
value: d.value,
startAngle: enterAntiClockwise.startAngle,
endAngle: enterAntiClockwise.endAngle
};
}); // store the initial values
path.exit()
.transition()
.duration(750)
.attrTween('d', arcTweenOut)
.remove() // now remove the exiting arcs
path.transition().duration(750).attrTween("d", arcTween); // redraw the arcs
}
Instead, it just treats the new array of value as brand new data and resizes the chart accordingly.
I've created a fiddle demonstrating the issue very simply:
http://jsfiddle.net/u9GBq/23/
If you press 'add', it add a random int to the array: this works as intended.
If you press 'remove', the only element getting transitioned out is always the last element to have entered the pie. In short, it behaves like a LIFO stack.
The expected behaviour is for the relevant pie arc to get transitioned out instead.
Is it possible to apply object consistency to pies? I've also tried adding a key function (not demonstrated on the fiddle) but that just breaks (oddly enough it works fine with my stacked graphs).
Thank you.
The easiest solution to this problem is to set missing values to zero, rather than removing them entirely, as in Part III of the Pie Chart Update series of examples. Then you get object constancy for free: you have the same number of elements, in the same order, across updates.
Alternatively, if you want a data join as in Part IV, you have to tell D3 where the entering arcs should enter from, and where the exiting arcs should exit to. A reasonable strategy is to find the closest neighboring arc from the opposite data: for a given entering arc, find the closest neighboring arc in the old data (pre-transition); likewise for a given exiting arc, find the closest neighboring arc in the new data (post-transition).
To continue the example, say you’re showing sales of apples in different regions, and want to switch to show oranges. You could use the following key function to maintain object constancy:
function key(d) {
return d.data.region;
}
(This assumes you’re using d3.layout.pie, which wraps your original data and exposes it as d.data.)
Now say when you transition to oranges, you have the following old data and new data:
var data0 = path.data(), // retrieve the old data
data1 = pie(region.values); // compute the new data
For each entering arc at index i (where d is data1[i]), you can step sequentially through preceding data in data1, and see if you can find a match in data0:
var m = data0.length;
while (--i >= 0) {
var k = key(data1[i]);
for (var j = 0; j < m; ++j) {
if (key(data0[j]) === k) return data0[j]; // a match!
}
}
If you find a match, your entering arcs can start from the matching arc’s end angle. If you don’t find a preceding match, you can then look for a following matching arc instead. If there are no matches, then there’s no overlap between the two datasets, so you might enter the arcs from angle 0°, or do a crossfade. You can likewise apply this technique to exiting arcs.
Putting it all together, here’s Part V:
Ok, found the solution.
The trick was to pass the key this way:
path = path.data(pie(dataset), function (d) {return d.data}); // this is good
as opposed to not passing it, or passing it the wrong way:
path = path.data(pie(dataset, function (d) {return d.data})); // this is bad
And here's an updated fiddle with a working transition on the right arc! :)
http://jsfiddle.net/StephanTual/PA7WD/1/

Resources