make routers on map clickable
This commit is contained in:
parent
1eb95158ae
commit
3d2db185e3
|
@ -0,0 +1,33 @@
|
|||
#!/usr/bin/python
|
||||
|
||||
from flask import Flask, render_template, request, make_response
|
||||
from pymongo import MongoClient
|
||||
from bson.json_util import dumps as bson2json
|
||||
|
||||
app = Flask(__name__)
|
||||
client = MongoClient()
|
||||
db = client.freifunk
|
||||
|
||||
tileurls = {
|
||||
"links": "http://home.heidler.eu:8000",
|
||||
"routers": "http://home.heidler.eu:8001",
|
||||
}
|
||||
|
||||
@app.route('/')
|
||||
def index():
|
||||
return render_template("map.html", tileurls=tileurls)
|
||||
|
||||
@app.route('/api/get_nearest_router')
|
||||
def get_nearest_router():
|
||||
res_router = db.routers.find_one({"position": {"$near": {
|
||||
"$geometry": {
|
||||
"type": "Point",
|
||||
"coordinates": [float(request.args.get("lng")), float(request.args.get("lat"))]
|
||||
},
|
||||
}}})
|
||||
r = make_response(bson2json(res_router))
|
||||
r.mimetype = 'application/json'
|
||||
return r
|
||||
|
||||
if __name__ == '__main__':
|
||||
app.run(host='0.0.0.0', debug=False)
|
|
@ -1,59 +0,0 @@
|
|||
<!DOCTYPE html>
|
||||
<html>
|
||||
<head>
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=no">
|
||||
<link rel="stylesheet" href="http://cdnjs.cloudflare.com/ajax/libs/leaflet/0.7.3/leaflet.css" />
|
||||
<script src="http://cdnjs.cloudflare.com/ajax/libs/leaflet/0.7.3/leaflet.js"></script>
|
||||
<style type="text/css">
|
||||
body {
|
||||
padding: 0;
|
||||
margin: 0;
|
||||
}
|
||||
html, body, #map {
|
||||
height: 100%;
|
||||
}
|
||||
#map {
|
||||
cursor: default;
|
||||
}
|
||||
.leaflet-dragging #map {
|
||||
cursor: grabbing;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<div id="map"></div>
|
||||
|
||||
<script type="text/javascript">
|
||||
var map = L.map('map').setView([49.46200, 11.1030], 17);
|
||||
L.tileLayer('https://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png', {
|
||||
attribution: 'Map data © <a href="https://openstreetmap.org">OpenStreetMap</a> contributors, <a href="https://creativecommons.org/licenses/by-sa/2.0/">CC-BY-SA</a>',
|
||||
maxNativeZoom: 19,
|
||||
maxZoom: 22
|
||||
}).addTo(map);
|
||||
var links = new L.TileLayer('http://localhost:8000/{z}/{x}/{y}.png', {maxNativeZoom: 22, maxZoom: 22, attribution: "", maximumAge: 1000*3600*24*10}).addTo(map);
|
||||
var routers = new L.TileLayer('http://localhost:8001/{z}/{x}/{y}.png', {maxNativeZoom: 22, maxZoom: 22, attribution: "", maximumAge: 1000*3600*24*10}).addTo(map);
|
||||
layersControl = new L.Control.Layers({}, {"links": links, "routers": routers});
|
||||
map.addControl(layersControl);
|
||||
//var marker = L.marker([49.47502, 10.99253]).addTo(map);
|
||||
|
||||
map.on('click', function(e) {
|
||||
console.log(e.latlng);
|
||||
console.log(map.getZoom());
|
||||
// height = width of world in px
|
||||
size_of_world_in_px = map.options.crs.scale(map.getZoom());
|
||||
deg_lng_per_pix = 360 / size_of_world_in_px;
|
||||
deg_lat_per_pix = 180 / size_of_world_in_px;
|
||||
/*
|
||||
db.routers.create_index([("location", "2dsphere")])
|
||||
49,11
|
||||
50,12
|
||||
-> difference 1,1
|
||||
-> in pix at zoom level 0 1.4,0.7
|
||||
-> pythagoras -> distance in px
|
||||
*/
|
||||
});
|
||||
|
||||
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
|
@ -0,0 +1,135 @@
|
|||
<!DOCTYPE html>
|
||||
<html>
|
||||
<head>
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=no">
|
||||
<link rel="stylesheet" href="http://cdnjs.cloudflare.com/ajax/libs/leaflet/0.7.3/leaflet.css" />
|
||||
<script src="http://cdnjs.cloudflare.com/ajax/libs/leaflet/0.7.3/leaflet.js"></script>
|
||||
<style type="text/css">
|
||||
body {
|
||||
padding: 0;
|
||||
margin: 0;
|
||||
}
|
||||
html, body, #map {
|
||||
height: 100%;
|
||||
}
|
||||
#map {
|
||||
cursor: default;
|
||||
}
|
||||
.leaflet-dragging #map {
|
||||
cursor: grabbing;
|
||||
}
|
||||
.popup-headline {
|
||||
font-size: 150%;
|
||||
}
|
||||
.popup-headline.with-neighbours {
|
||||
border-bottom: 1px solid lightgray;
|
||||
}
|
||||
.leaflet-popup-content td {
|
||||
padding: 0 3px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<div id="map"></div>
|
||||
|
||||
<script type="text/javascript">
|
||||
var map = L.map('map').setView([49.46200, 11.1030], 17);
|
||||
L.tileLayer('https://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png', {
|
||||
attribution: 'Map data © <a href="https://openstreetmap.org">OpenStreetMap</a> contributors, <a href="https://creativecommons.org/licenses/by-sa/2.0/">CC-BY-SA</a>',
|
||||
maxNativeZoom: 19,
|
||||
maxZoom: 22
|
||||
}).addTo(map);
|
||||
var links = new L.TileLayer('{{ tileurls.links }}/{z}/{x}/{y}.png', {maxNativeZoom: 22, maxZoom: 22, attribution: "", maximumAge: 1000*3600*24*10}).addTo(map);
|
||||
var routers = new L.TileLayer('{{ tileurls.routers }}/{z}/{x}/{y}.png', {maxNativeZoom: 22, maxZoom: 22, attribution: "", maximumAge: 1000*3600*24*10}).addTo(map);
|
||||
layersControl = new L.Control.Layers({}, {"links": links, "routers": routers});
|
||||
map.addControl(layersControl);
|
||||
//var marker = L.marker([49.47502, 10.99253]).addTo(map);
|
||||
|
||||
var router_pointer_radius = 7.5; // actually 7 but let's add some rounding tolerance
|
||||
|
||||
var popup;
|
||||
|
||||
map.on('click', function(pos) {
|
||||
// height = width of world in px
|
||||
var size_of_world_in_px = map.options.crs.scale(map.getZoom());
|
||||
|
||||
var px_per_deg_lng = size_of_world_in_px / 360;
|
||||
var px_per_deg_lat = size_of_world_in_px / 180;
|
||||
|
||||
ajax_get_request("{{ url_for('get_nearest_router') }}?lng=" + pos.latlng.lng + "&lat=" + pos.latlng.lat, function(router) {
|
||||
// decide if router is close enough
|
||||
var lng_delta = Math.abs(pos.latlng.lng - router.position.coordinates[0])
|
||||
var lat_delta = Math.abs(pos.latlng.lat - router.position.coordinates[1])
|
||||
|
||||
// convert degree distances into px distances on the map
|
||||
var x_delta_px = lng_delta * px_per_deg_lng;
|
||||
var y_delta_px = lat_delta * px_per_deg_lat;
|
||||
|
||||
// use pythagoras to calculate distance
|
||||
var px_distance = Math.sqrt(x_delta_px*x_delta_px + y_delta_px*y_delta_px);
|
||||
|
||||
console.debug("Distance to closest router ("+router.hostname+"): " + px_distance+"px");
|
||||
|
||||
// check if mouse click was on the router icon
|
||||
if (px_distance <= router_pointer_radius) {
|
||||
console.log("Click on '"+router.hostname+"' detected.");
|
||||
console.log(router);
|
||||
//FIXME: Flask internal url_for
|
||||
var has_neighbours = 'neighbours' in router && router.neighbours.length > 0;
|
||||
var popup_html = "";
|
||||
if (has_neighbours) {
|
||||
popup_html += "<div class=\"popup-headline with-neighbours\">";
|
||||
}
|
||||
else {
|
||||
popup_html += "<div class=\"popup-headline\">";
|
||||
}
|
||||
popup_html += "<b>Router <a href=\"https://netmon.freifunk-franken.de/router.php?router_id="+router.netmon_id+"\">"+router.hostname+"</a></b>";
|
||||
popup_html += "</div>"
|
||||
if (has_neighbours) {
|
||||
popup_html += "<table>";
|
||||
popup_html += "<tr>";
|
||||
popup_html += "<th>Hostname</th>";
|
||||
popup_html += "<th>MAC-Address</th>";
|
||||
popup_html += "<th>Quality</th>";
|
||||
popup_html += "<th>Outgoing Interface</th>";
|
||||
popup_html += "</tr>";
|
||||
for (neighbour of router.neighbours) {
|
||||
var tr_color = "#04ff0a";
|
||||
if (neighbour.quality < 105) { tr_color = "#ff1e1e"; }
|
||||
else if (neighbour.quality < 130) { tr_color = "#ff4949"; }
|
||||
else if (neighbour.quality < 155) { tr_color = "#ff6a6a"; }
|
||||
else if (neighbour.quality < 180) { tr_color = "#ffac53"; }
|
||||
else if (neighbour.quality < 205) { tr_color = "#ffeb79"; }
|
||||
else if (neighbour.quality < 230) { tr_color = "#79ff7c"; }
|
||||
popup_html += "<tr style=\"background-color: "+tr_color+";\">";
|
||||
//FIXME: Link to each neighbour
|
||||
popup_html += "<td>"+neighbour.hostname+"</td>";
|
||||
popup_html += "<td>"+neighbour.mac+"</td>";
|
||||
popup_html += "<td>"+neighbour.quality+"</td>";
|
||||
popup_html += "<td>"+neighbour.net_if+"</td>";
|
||||
popup_html += "</tr>";
|
||||
}
|
||||
popup_html += "</table>";
|
||||
}
|
||||
popup = L.popup({offset: new L.Point(1, 1), maxWidth: 500})
|
||||
.setLatLng([router.position.coordinates[1], router.position.coordinates[0]])
|
||||
.setContent(popup_html)
|
||||
.openOn(map);
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
function ajax_get_request(url, callback_fkt) {
|
||||
var xmlhttp = new XMLHttpRequest();
|
||||
xmlhttp.onreadystatechange = function() {
|
||||
if (xmlhttp.readyState == 4 && xmlhttp.status == 200) {
|
||||
var response_data = JSON.parse(xmlhttp.responseText);
|
||||
callback_fkt(response_data);
|
||||
}
|
||||
}
|
||||
xmlhttp.open("GET", url, true);
|
||||
xmlhttp.send();
|
||||
}
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
Loading…
Reference in New Issue