Utilisation d'OpenStreetMap pour visualiser des données
#coding:latin-1 import sys sys.path.append("../../../../program/python/pyensae/src") # ligne inutile from pyensae import download_data import pandas download_data("td9_data.zip", website = 'xd') file1 = "td9_full.txt" tbl = pandas.read_csv (file1, sep = "\t") from pandas.tools.plotting import scatter_plot gr = tbl.groupby(['lng','lat'], as_index = False).agg(lambda x: len(x)) # voir http://dev.openlayers.org/docs/files/OpenLayers/Marker-js.html pour changer le marker html = """ <html><body> <div id="mapdiv"></div> <script src="http://www.openlayers.org/api/OpenLayers.js"></script> <script> map = new OpenLayers.Map("mapdiv"); map.addLayer(new OpenLayers.Layer.OSM()); var proj = new OpenLayers.Projection("EPSG:4326"); var zoom=13; var markers = new OpenLayers.Layer.Markers( "Markers" ); map.addLayer(markers); __VELIB__ map.setCenter (lonLat0, zoom); </script> </body></html> """ position =""" var lonLat{0} = new OpenLayers.LonLat( {1} ,{2} ).transform(proj, map.getProjectionObject() ); markers.addMarker(new OpenLayers.Marker(lonLat{0})); """ lines = [ ] for i,row in enumerate(gr.values) : y = lat = row[1] x = lng = row[0] line = position.format(i,x,y) lines.append(line) text = "\n".join( lines ) html = html.replace("__VELIB__", text) with open("velib.html", "w") as f : f.write(html)
Les stations Vélib dans les zones de travail
#coding:latin-1 import sys sys.path.append("../../../../program/python/pyensae/src") # ligne inutile from pyensae import download_data import pandas download_data("td9_data.zip", website = 'xd') file1 = "td9_full.txt" tbl = pandas.read_csv (file1, sep = "\t") from pandas.tools.plotting import scatter_plot gr = tbl.groupby(['lng','lat'], as_index = False).agg(lambda x: len(x)) # voir http://dev.openlayers.org/docs/files/OpenLayers/Marker-js.html pour changer le marker html = """ <html><body> <div id="mapdiv"></div> <script src="http://www.openlayers.org/api/OpenLayers.js"></script> <script> map = new OpenLayers.Map("mapdiv"); map.addLayer(new OpenLayers.Layer.OSM()); var proj = new OpenLayers.Projection("EPSG:4326"); var zoom=13; var markers = new OpenLayers.Layer.Markers( "Markers" ); map.addLayer(markers); __VELIB__ map.setCenter (lonLat0, zoom); </script> </body></html> """ position =""" var lonLat{0} = new OpenLayers.LonLat( {1} ,{2} ).transform(proj, map.getProjectionObject() ); markers.addMarker(new OpenLayers.Marker(lonLat{0})); """ lines = [ ] for i,row in enumerate(gr.values) : y = lat = row[1] x = lng = row[0] line = position.format(i,x,y) lines.append(line) text = "\n".join( lines ) html = html.replace("__VELIB__", text) with open("velib.html", "w") as f : f.write(html)
Le réseau L-World
<!DOCTYPE html> <meta charset="utf-8"> <script src="http://d3js.org/d3.v2.js?2.9.1"></script> <script src="td9_graph_lworld.js"></script> <style> .link { fill: none; stroke: #666; stroke-width: 1.5px; } .node circle { fill: #ccc; stroke: #fff; stroke-width: 1.5px; } text { font: 10px sans-serif; pointer-events: none; } </style> <body> <script> var nodes = {}; // Compute the distinct nodes from the links. links.forEach(function(link) { link.source = nodes[link.source] || (nodes[link.source] = {name: link.source}); link.target = nodes[link.target] || (nodes[link.target] = {name: link.target}); }); var width = 960, height = 500; var force = d3.layout.force() .nodes(d3.values(nodes)) .links(links) .size([width, height]) .linkDistance(60) .charge(-300) .on("tick", tick) .start(); var svg = d3.select("body").append("svg") .attr("width", width) .attr("height", height); var link = svg.selectAll(".link") .data(force.links()) .enter().append("line") .attr("class", "link"); var node = svg.selectAll(".node") .data(force.nodes()) .enter().append("g") .attr("class", "node") .call(force.drag); node.append("circle") .attr("r", 8); node.append("text") .attr("x", 12) .attr("dy", ".35em") .text(function(d) { return d.name; }); function tick() { link .attr("x1", function(d) { return d.source.x; }) .attr("y1", function(d) { return d.source.y; }) .attr("x2", function(d) { return d.target.x; }) .attr("y2", function(d) { return d.target.y; }); node .attr("transform", function(d) { return "translate(" + d.x + "," + d.y + ")"; }); } </script>
Le réseau L-World avec des événements
<!DOCTYPE html> <meta charset="utf-8"> <script src="http://d3js.org/d3.v2.js?2.9.1"></script> <script src="td9_graph_lworld.js"></script> <style> .link { fill: none; stroke: #666; stroke-width: 1.5px; } .node circle { fill: #ccc; stroke: #fff; stroke-width: 1.5px; } text { font: 10px sans-serif; pointer-events: none; } </style> <body> <script> var nodes = {}; // Compute the distinct nodes from the links. links.forEach(function(link) { link.source = nodes[link.source] || (nodes[link.source] = {name: link.source}); link.target = nodes[link.target] || (nodes[link.target] = {name: link.target}); }); var width = 960, height = 800; var force = d3.layout.force() .nodes(d3.values(nodes)) .links(links) .size([width, height]) .linkDistance(30) .charge(-300) .on("tick", tick) .start(); var svg = d3.select("body").append("svg") .attr("width", width) .attr("height", height); var link = svg.selectAll(".link") .data(force.links()) .enter().append("line") .attr("class", "link"); var node = svg.selectAll(".node") .data(force.nodes()) .enter().append("g") .attr("class", "node") .on("mouseover", mouseover) // on ajoute deux événements: la souris passe au-dessus d'un noeud .on("mouseout", mouseout) // la sortie sort de la zone du noeud .call(force.drag); // pour qu'on puisse tirer les noeuds node.append("circle") .attr("r", 8); node.append("text") .attr("x", 12) .attr("dy", ".35em") .text(function(d) { return d.name; }) .style("font-size", "10px") ; function tick() { link .attr("x1", function(d) { return d.source.x; }) .attr("y1", function(d) { return d.source.y; }) .attr("x2", function(d) { return d.target.x; }) .attr("y2", function(d) { return d.target.y; }); node .attr("transform", function(d) { return "translate(" + d.x + "," + d.y + ")"; }); } // la fonction suivante définit ce qui doit se passe au cas où le curseur passe au-dessus d'un noeud function mouseover() { d3.select(this) .select("text") .style("font-size", "30px") .text(function(d,i){return "** " + d.name + " **" ;}); d3.select(this) .style("fill", "red") .select("circle").transition() .duration(750) .attr("r", 16) .style("fill", "yellow"); } // la fonction suivante définit ce qui doit se passe au cas où le curseur sort de la zone du noeud function mouseout() { d3.select(this) .select("text") .style("font-size", "10px") .text(function(d,i){return d.name ;}); d3.select(this) .style("fill", "grey") .select("circle").transition() .duration(350) .attr("r", 8) .style("fill", "grey"); } </script>
Le fichier HTML contenant le code javascript.
<!DOCTYPE html> <!-- http://jsfiddle.net/KSAbK/1/ --> <!-- https://leanpub.com/D3-Tips-and-Tricks/read --> <meta charset="utf-8"> <style> body { font: 10px sans-serif; } .plot { fill: rgba(250, 250, 255, 0.6); } .grid .tick { stroke: lightgrey; opacity: 0.7; } .grid path { stroke-width: 0; } .axis path, .axis line { fill: none; stroke: #000; shape-rendering: crispEdges; } .x.axis path { display: none; } .line { fill: none; stroke: steelblue; stroke-width: 1.5px; } </style> <body> <script src="http://d3js.org/d3.v3.js"></script> <script src="td9_by_hours_data.js"></script> <!-- the data, contains the variable data used by the following script, it looks like the following --> <!-- data = [ {'velo': 12817.0, 'last_update': '10/9/13 11:35', 'minute': 35.0, 'heure': 11.0, 'place': 25202.0, 'name': '10/9/13 11:35', 'roulant': 225.0, 'somme': 38019.0} ,{'velo': 12744.0, 'last_update': '10/9/13 11:40', 'minute': 40.0, 'heure': 11.0, 'place': 25273.0, 'name': '10/9/13 11:40', 'roulant': 227.0, 'somme': 38017.0} ... ] ; --> <script> // defines the graph area (usually the same for for every graph) margin = { top: 20, right: 20, bottom: 20, left: 45 }; width = 800 - margin.left - margin.right; height = 500 - margin.top - margin.bottom; // defines the range of each axis var x = d3.time.scale() .domain(d3.extent(data, function (d) { return d.last_update; })) .range([0, width]); var y = d3.scale.linear() .domain(d3.extent(data, function (d) { return d.velo; })) .range([height, 0]); // graph type, also defines the columns to be used (last_update and velo in this case) var line = d3.svg.line() .x(function (d) { return x(d.last_update); }) .y(function (d) { return y(d.velo); }); // defines the function to call when zooming var zoom = d3.behavior.zoom() .x(x) //.y(y) .on("zoom", zoomed); // creates a svg section in the body section svg = d3.select('body') .append("svg") .attr('width', width + margin.left + margin.right) .attr('height', height + margin.top + margin.bottom) .append("g") .attr("transform", "translate(" + margin.left + "," + margin.top + ")") .call(zoom); svg.append("rect") .attr("width", width) .attr("height", height) .attr("class", "plot"); // two functions uses for the zoom var make_x_axis = function () { return d3.svg.axis() .scale(x) .orient("bottom") .ticks(5); }; var make_y_axis = function () { return d3.svg.axis() .scale(y) .orient("left") .ticks(10); }; // defines the axis var xAxis = d3.svg.axis() .scale(x) .orient("bottom") .ticks(10); svg.append("g") .attr("class", "x axis") .attr("transform", "translate(0, " + height + ")") .call(xAxis); var yAxis = d3.svg.axis() .scale(y) .orient("left") .ticks(10); svg.append("g") .attr("class", "y axis") .call(yAxis); svg.append("g") .attr("class", "x grid") .attr("transform", "translate(0," + height + ")") .call(make_x_axis() .tickSize(-height, 0, 0) .tickFormat("")); svg.append("g") .attr("class", "y grid") .call(make_y_axis() .tickSize(-width, 0, 0) .tickFormat("")); // objects for the zooming var clip = svg.append("clipPath") .attr("id", "clip") .append("rect") .attr("x", 0) .attr("y", 0) .attr("width", width) .attr("height", height); var chartBody = svg.append("g") .attr("clip-path", "url(#clip)"); chartBody.append("path") .datum(data) .attr("class", "line") .attr("d", line); // zooming functions function zoomed() { //console.log(d3.event.translate); // display information in the logging console of the browser (using developping tools) //console.log(d3.event.scale); svg.select(".x.axis").call(xAxis); svg.select(".y.axis").call(yAxis); svg.select(".x.grid") .call(make_x_axis() .tickSize(-height, 0, 0) .tickFormat("")); svg.select(".y.grid") .call(make_y_axis() .tickSize(-width, 0, 0) .tickFormat("")); svg.select(".line") .attr("class", "line") .attr("d", line); } </script> </body> </html>
données incluses dans un script javascript
data = [ {'velo': 12817.0, 'last_update': '10/9/13 11:35', 'minute': 35.0, 'heure': 11.0, 'place': 25202.0, 'name': '10/9/13 11:35', 'roulant': 225.0, 'somme': 38019.0} ,{'velo': 12744.0, 'last_update': '10/9/13 11:40', 'minute': 40.0, 'heure': 11.0, 'place': 25273.0, 'name': '10/9/13 11:40', 'roulant': 227.0, 'somme': 38017.0} ,{'velo': 12674.0, 'last_update': '10/9/13 11:45', 'minute': 45.0, 'heure': 11.0, 'place': 25349.0, 'name': '10/9/13 11:45', 'roulant': 221.0, 'somme': 38023.0} ,{'velo': 12646.0, 'last_update': '10/9/13 11:50', 'minute': 50.0, 'heure': 11.0, 'place': 25380.0, 'name': '10/9/13 11:50', 'roulant': 218.0, 'somme': 38026.0} ,{'velo': 12568.0, 'last_update': '10/9/13 11:55', 'minute': 55.0, 'heure': 11.0, 'place': 25457.0, 'name': '10/9/13 11:55', 'roulant': 219.0, 'somme': 38025.0} // ... ] ; var parseDate = d3.time.format("%d/%m/%Y %H:%M").parse; for (var i = 0; i < data.length; i++) { element = data[i] ; element['last_update'] = parseDate(element['last_update']) ; }