I'm working on a bar chart using d3.js, the bar shoud be able correspond to a new json data.
var m = [30, 5, 5, 5],
w = 375 - m[1] - m[3],
h = 260 - m[0] - m[2];
var format = d3.format(",.0f");
var wdthnew = d3.scale.linear().range([0, w]),
wdth = d3.scale.linear().range([0, w]).domain([0, 25000]),
hght = d3.scale.ordinal().rangeRoundBands([0, h], .1);
var svg = d3.select("body").append("svg")
.attr("width", w + m[1] + m[3])
.attr("height", h + m[0] + m[2])
.append("g")
.attr("transform", "translate(" + m[3] + "," + m[0] + ")");
d3.json("barchartjson.php", function(data) {
data.sort(function(a, b) { return b.value - a.value; });
hght.domain(data.map(function(d) { return d.orientation; }));
var bar = svg.selectAll("g.bar")
.data(data)
.enter().append("g")
.attr("class", "bar")
.attr("transform", function(d) { return "translate(0," + hght(d.orientation) + ")"; });
bar.append("rect")
.attr("id", "activebar")
.attr("width", 0)
.attr("height", hght.rangeBand())
.transition()
.delay(100)
.duration(1000)
.attr("width", function(d) { return wdth(d.value); });
});
function makebar(date1, date2) {
var barchartjson = "barchartjson.php?df="+date1+"&dl="+date2;
d3.json(barchartjson , function(datanew) {
datanew.sort(function(a, b) { return b.jumlah - a.jumlah; });
wdthnew.domain([0, d3.sum(datanew, function(d) { return d.value; })]);
console.log("SUM datanew: "+ d3.sum(datanew, function(d) { return d.value; }));
console.log("Array datanew: ");
console.log(datanew);
var updatebar = svg.selectAll("#activebar");
updatebar.transition().duration(1000)
.attr("width", function(a) { console.log("update width: wdthnew("+a.value+") = "+wdthnew(a.value));
return wdthnew(a.value); });
});
}
Here is the json from barchartjson.php used at the first time:
[{"orientation":"negatif","value":"15964"},{"orientation":"netral","value":"2788"},{"orientation":"positif","value":"9701"}]
The bar is showing properly for the first time. The problem is when makebar() is called, updating the bar width with the new json data. Each bar width is updated, but in some case they are out of range. Here is the output from console.log :
SUM datanew: 2520
Array datanew:
[Object
value: "1411"
orientation: "negatif"
__proto__: Object
,
Object
value: "846"
orientation: "positif"
__proto__: Object
,
Object
value: "263"
orientation: "netral"
__proto__: Object
]
update width: wdthnew(15964) = 2312.246031746032
update width: wdthnew(9701) = 1405.1051587301588
update width: wdthnew(2788) = 403.81746031746036
a new json successfully called , but the log showing that wdthnew is keep scaling the old json.
updatebar.transition().duration(1000)
.attr("width", function(a) { console.log("update width: wdthnew("+a.value+") = "+wdthnew(a.value));
return wdthnew(a.value); });
resulting:
update width: wdthnew(15964) = 2312.246031746032
despite 15694 is from the old json, the wdthnew(d.value) is actually return a value from wdthnew(1411) wich is 2312 and it is out of range..
Can someone help me solve this problem? Or point out where I'm doing wrong? I'm new to d3.js and javascript. I'm sorry for the bad grammar. English is not my native language.
jsFiddle here: /
I'm working on a bar chart using d3.js, the bar shoud be able correspond to a new json data.
var m = [30, 5, 5, 5],
w = 375 - m[1] - m[3],
h = 260 - m[0] - m[2];
var format = d3.format(",.0f");
var wdthnew = d3.scale.linear().range([0, w]),
wdth = d3.scale.linear().range([0, w]).domain([0, 25000]),
hght = d3.scale.ordinal().rangeRoundBands([0, h], .1);
var svg = d3.select("body").append("svg")
.attr("width", w + m[1] + m[3])
.attr("height", h + m[0] + m[2])
.append("g")
.attr("transform", "translate(" + m[3] + "," + m[0] + ")");
d3.json("barchartjson.php", function(data) {
data.sort(function(a, b) { return b.value - a.value; });
hght.domain(data.map(function(d) { return d.orientation; }));
var bar = svg.selectAll("g.bar")
.data(data)
.enter().append("g")
.attr("class", "bar")
.attr("transform", function(d) { return "translate(0," + hght(d.orientation) + ")"; });
bar.append("rect")
.attr("id", "activebar")
.attr("width", 0)
.attr("height", hght.rangeBand())
.transition()
.delay(100)
.duration(1000)
.attr("width", function(d) { return wdth(d.value); });
});
function makebar(date1, date2) {
var barchartjson = "barchartjson.php?df="+date1+"&dl="+date2;
d3.json(barchartjson , function(datanew) {
datanew.sort(function(a, b) { return b.jumlah - a.jumlah; });
wdthnew.domain([0, d3.sum(datanew, function(d) { return d.value; })]);
console.log("SUM datanew: "+ d3.sum(datanew, function(d) { return d.value; }));
console.log("Array datanew: ");
console.log(datanew);
var updatebar = svg.selectAll("#activebar");
updatebar.transition().duration(1000)
.attr("width", function(a) { console.log("update width: wdthnew("+a.value+") = "+wdthnew(a.value));
return wdthnew(a.value); });
});
}
Here is the json from barchartjson.php used at the first time:
[{"orientation":"negatif","value":"15964"},{"orientation":"netral","value":"2788"},{"orientation":"positif","value":"9701"}]
The bar is showing properly for the first time. The problem is when makebar() is called, updating the bar width with the new json data. Each bar width is updated, but in some case they are out of range. Here is the output from console.log :
SUM datanew: 2520
Array datanew:
[Object
value: "1411"
orientation: "negatif"
__proto__: Object
,
Object
value: "846"
orientation: "positif"
__proto__: Object
,
Object
value: "263"
orientation: "netral"
__proto__: Object
]
update width: wdthnew(15964) = 2312.246031746032
update width: wdthnew(9701) = 1405.1051587301588
update width: wdthnew(2788) = 403.81746031746036
a new json successfully called , but the log showing that wdthnew is keep scaling the old json.
updatebar.transition().duration(1000)
.attr("width", function(a) { console.log("update width: wdthnew("+a.value+") = "+wdthnew(a.value));
return wdthnew(a.value); });
resulting:
update width: wdthnew(15964) = 2312.246031746032
despite 15694 is from the old json, the wdthnew(d.value) is actually return a value from wdthnew(1411) wich is 2312 and it is out of range..
Can someone help me solve this problem? Or point out where I'm doing wrong? I'm new to d3.js and javascript. I'm sorry for the bad grammar. English is not my native language.
jsFiddle here: http://jsfiddle/saido/5mREA/
Share Improve this question edited May 3, 2012 at 19:38 ZachB 15.5k5 gold badges66 silver badges93 bronze badges asked Apr 25, 2012 at 11:24 FrendhiFrendhi 791 silver badge7 bronze badges2 Answers
Reset to default 3Turns out the problem was in function makebar():
at this line I supposed to attach the new data:
var updatebar = svg.selectAll("#activebar").data(datanew);
Now the console.log showing and calculating the proper values.
I'm sorry I'm not sure how to explain the technical issue in much more detail.
Perhaps create a buffer array/object that will store the data prior to using it... Then create an update interval that won't update before new data arrives.
Update: Here's an example
var data = [{x: 1, y: 3},
{x: 2, y: 4},
{x: 3, y: 5},
...
];
var iningData = [];
/* ining data gets .pushed(...) in every 1 or
2 seconds, depending on network traffic */
var updateDelay = 3000;
setInterval(function() {
for (var index = 0; index < data.length; index++) {
seriesData.shift();
seriesData.push(iningData.shift());
redrawGraph();
}
}, updateDelay);
发布者:admin,转转请注明出处:http://www.yc00.com/questions/1745587676a4634641.html
评论列表(0条)