D3.js Auto-actualización automática a través de SETInterval con JQUERY GET (JSON, XML, texto, lo que sea)
Pregunta
¿Puede alguien ayudar con cómo usar un jQuery obtener (JSON, TXT, XML, lo que sea) y setinterval (D3.js) para que pueda actualizar mi gráfico de barras D3 cada n segundos? ¿O alguien sabe de un ejemplo que usa un que utiliza para actualizar los datos a través de SetInterval en D3 SVGs? He leído este tutorial todo el día, pero sin hacer clic con cómo hacerloIncorpora JSON en lugar de caminar al azar. Muchas gracias de antemano ...
Mi intento fallido:
<!DOCTYPE html>
<html>
<head>
<meta http-equiv="content-type" content="text/html;charset=utf-8">
<title> Testing a d3.js Walking Bar Chart via jQuery getText and d3.js setInterval </title>
<script type="text/javascript" src="http://localhost:8080/dev_tests/d3/d3.js"></script>
<script type="text/javascript" src="http://localhost:8080/dev_tests/latest.jquery/jquery-latest.js"></script>
</head>
<body>
<div class="body">
<div class="content">
<style type='text/css'>
.chart {
margin-left: 42px;
}
.chart rect {
fill: steelblue;
stroke: white;
}
</style>
<script type='text/javascript'>
var t = 1297110663,
v = 70,
data = d3.range(33).map(next1);
function next1() {
$.get('http://localhost:8080/dev_tests/data/file.txt', function(data1) {
$('.result').text(data1);
alert(data1);
return {time: ++t, value: v = data1 };
});
}
var w = 20,
h = 80;
var x = d3.scale.linear()
.domain([0, 1])
.range([0, w]);
var y = d3.scale.linear()
.domain([0, 100])
.rangeRound([0, h]);
</script>
<p>Et voila!</p>
<script type='text/javascript'>
var chart3 = d3.select(".content").append("svg")
.attr("class", "chart")
.attr("width", w * data.length - 1)
.attr("height", h);
chart3.append("line")
.attr("x1", 0)
.attr("x2", w * data.length)
.attr("y1", h - .5)
.attr("y2", h - .5)
.style("stroke", "#000");
redraw3();
function redraw3() {
var rect = chart3.selectAll("rect")
.data(data, function(d) { return d.time; });
rect.enter().insert("rect", "line")
.attr("x", function(d, i) { return x(i + 1) - .5; })
.attr("y", function(d) { return h - y(d.value) - .5; })
.attr("width", w)
.attr("height", function(d) { return y(d.value); })
.transition()
.duration(1000)
.attr("x", function(d, i) { return x(i) - .5; });
rect.transition()
.duration(1000)
.attr("x", function(d, i) { return x(i) - .5; });
rect.exit().transition()
.duration(1000)
.attr("x", function(d, i) { return x(i - 1) - .5; })
.remove();
}
setInterval(function() {
data.shift();
data.push(data);
redraw3();
}, 3500);
</script>
</div>
</div>
</body>
</html>
Solución
- Crea tu matriz de datos
- Cargar nuevos datos de forma asíncrona
- Al cargar datos,
next1()
lo en la matriz de datos - redibuje su gráfico
Puede simular esto sin una llamada JSON haciendo esto:
var data = [], t = 0; var interval = setInterval(function() { var value = Math.random() * 100; data.push({time: ++t, value: value}); redraw(); }, 1000);
y cuando obtiene ese funcionamiento, cambie a esto:
var data = [], t = 0; var interval = setInterval(function() { $.getJSON("path/to/data.json", function(datum) { data.push({time: ++t, value: datum}); redraw(); }); }, 1000);
Un problema con esto, sin embargo, es que si alguna de las solicitudes de JSON demora más de un segundo, podría terminar con la carga de datos fuera del pedido.Por lo que es mejor usar
push()
y hacer cola a la siguiente carga solo después de que haya terminado con el anterior:var data = [], t = 0, timeout; function loadNext() { $.getJSON("path/to/data.json", function(datum) { data.push({time: ++t, value: datum}); redraw(); timeout = setTimeout(loadNext, 1000); }); } loadNext();
¿Tiene sentido?