Excel文件里记录着POI点信息(包含经纬度),这些记录也可以分类别保存在不同的sheet里。下面介绍如何根据sheet名称,自动把Excel里的点位信息在地图上分组点标记展示,地图展示选用高德地图API。
后台开发使用Python Web框架 Tornado,代码如下:
代码语言:python代码运行次数:0复制import pandas as pd
from tornado.options import define,options
import tornado.ioloop
import tornado.web
import os
define('port',default=8000,help='run on the given port',type=int)
class cross_originAllowed_Handler(tornado.web.RequestHandler):
def initialize(self):
self.set_header('Access-Control-Allow-Origin','*')
self.set_header('Access-Control-Allow-Methods','POST,GET')
self.set_header('Access-Control-Max-Age',1000)
self.set_header('Access-Control-Allow-Headers','*')
class ApiHandler(cross_originAllowed_Handler):
def get(self):
excel=pd.ExcelFile('db.xlsx')
result={}
for sheet_name in excel.sheet_names:
df=pd.read_excel(excel,sheet_name)
result[sheet_name]=json.loads(df.to_json(orient='records'))
self.write(result)
return
class mapHandler(tornado.web.RequestHandler):
def get(self):
self.render('index.html')
def make_app():
return tornado.web.Application(
[
(r"/api.json", ApiHandler),
(r"/", mapHandler),
],
static_path=os.path.join(os.path.curdir,'static'),
template_path=os.path.join(os.path.curdir,'template'),
debug=True)
if __name__ == "__main__":
app = make_app()
options.parse_command_line()
app.listen(options.port)
tornado.ioloop.IOLoop.current().start()
地图展示页面使用高德地图JavaScript API,代码如下:
代码语言:html复制<html>
<head>
<meta name="viewport" content="initial-scale=1.0, user-scalable=no">
<script type="text/javascript" src="https://underscorejs.net/js/jquery-1.11.0.min.js"></script>
<script type="text/javascript" src="https://underscorejs.net/js/underscore.js"></script>
<script type="text/javascript" src="https://webapi.amap.com/maps?v=2.0&key=yourkey"></script>
<script type="text/template" id="toggleTemplate">
<% _.each(layers,(points,name)=> { %>
<div class="radio-group"><a class="radio-button radio-button-checked" data-layer="<%=name%>" onclick="javascript:void(0);"><span class="radio-button-inner"><%=name%></span></a> </div>
<% }) %>
<div class="radio-group"><a title="点击切换名称显示" id="toggleLabel" data-label="name" class="radio-button" onclick="javascript:void(0);"><span class="radio-button-inner" >名称</span> </a><a title="点击切换地图风格" id="toggleStyle" class="radio-button" onclick="javascript:void(0);" data-style='normal'><span class="radio-button-inner">标准</span> </a> </div>
</script>
<script type="text/template" id="infoTemplate">
<% _.each(row,(value,col)=> { %>
<%=col %>:<%=value %><br>
<% }) %>
</script>
<style>
body.darkblue .amap-marker-label{
background:#000001;
color:white;
border:1px solid white;
}
body.normal .amap-marker-label{
background:white;
color:black;
border: 1px solid black;
}
#container {width:100%; height: 100%; }
#mapgroup .radio-button-wrapper {
width: 80px;
padding: 0 !important;
text-align: center;
border: 0 !important;
background: rgba(0, 0, 0, .6) !important;
color: #fff !important;
border-radius: 0 !important;
}
.mapgroup {
position: fixed;
right: 0;
top: 23%;
z-index: 999;
width: 80px;
}
.radio-group {
width: 80px;
display: grid;
cursor: pointer;
}
.white .radio-button,
.radio-button {
background-color: white;
color: #000;
user-select: none;
line-height: 40px;
text-align: center;
text-decoration: none;
border: 1px solid black;
border-radius: 10px;
caret-color: transparent;
}
.dark .radio-button {
background-color: black;
color: #fff;
line-height: 40px;
text-align: center;
text-decoration: none;
border: 1px solid white;
border-radius: 10px;
caret-color: transparent;
}
.radio-button-checked,
.white .radio-button-checked,
.dark .radio-button-checked {
background-color: #337ab7;
color: #fff;
caret-color: transparent;
}
</style>
</head>
<body>
<div id="container"></div>
<div id="mapgroup" class="mapgroup" contenteditable="false">
</div>
</body>
<script type="text/javascript" >
var map = new AMap.Map('container',{
zoom: 12,
center: [113.667116,34.776845]
});
var infoTemplate=_.template($('#infoTemplate').html());
var infoWindow = new AMap.InfoWindow({
});
var toggleTemplate=_.template($('#toggleTemplate').html());
$.get('../api.json',function(data){
layers= _.mapObject(data,(table,name)=>{
var markers=_.map(table,row=>{
console.log(row);
var lng=row["经度"];
var lat=row["纬度"];
console.log(lng,lat);
var marker = new AMap.Marker({
position: new AMap.LngLat(parseFloat(lng), parseFloat(lat)),
title: row['名称'],
icon: `../static/imgs/${name}.png`,
});
var row0=_.omit(row,['经度','纬度','名称']);
marker.content = infoTemplate({row:row0});
marker.on('click', markerClick);
return marker;
})
map.add(markers);
return markers;
})
function markerClick(e) {
infoWindow.setContent(e.target.content);
infoWindow.open(map, e.target.getPosition());
}
$('#mapgroup').html(toggleTemplate({layers:data}));
map.setFitView();
})
$('#mapgroup').delegate('#toggleStyle','click',function () {
var labelType= $(this).data('style');
if (labelType == 'normal') {
var styleName = "amap://styles/darkblue" ;
$(this).data('style','darkblue').addClass('radio-button-checked').find('span').text('暗夜');
$('body').removeClass('normal').addClass('darkblue');
}
else {
var styleName = "amap://styles/normal" ;
$(this).data('style','normal').removeClass('radio-button-checked').find('span').text('标准');
$('body').removeClass('darkblue').addClass('normal');
}
map.setMapStyle(styleName);
})
$('#mapgroup').delegate('#toggleLabel','click',function () {
var labelType = $(this).data('label');
if (labelType == 'none') {
$(this).data('label', 'name');
$(this).removeClass('radio-button-checked');
_.each(layers,(markers,name)=>{
_.each(markers,marker=>{
marker.setLabel({
offset: new AMap.Pixel(0, 0),
content:'',
direction: 'top'
});
})
})
}
else if(labelType == 'name') {
$(this).data('label', 'none');
$(this).addClass('radio-button-checked');
_.each(layers,(markers,name)=>{
_.each(markers,marker=>{
marker.setLabel({
offset: new AMap.Pixel(0, 0),
content: marker.getTitle(),
direction: 'top'
});
})
})
}
});
$('#mapgroup').delegate('.radio-group [data-layer]','click',function () {
var name=$(this).data('layer');
if($(this).hasClass('radio-button-checked')){
$(this).removeClass('radio-button-checked');
_.each(layers[name],marker=>{
marker.hide();
})
}
else{
$(this).addClass('radio-button-checked');
_.each(layers[name],marker=>{
marker.show();
})
}
})
</script>
</html>