tegola簡介
Tegola是一個矢量切片服務器,提供Mapbox Vector Tiles,支持PostGIS和GeoPackage數據提供程序。用戶文檔可以在tegola.io找到
tegola特徵
- 原生幾何處理(簡化,裁剪,製作有效,交集,包含,縮放,翻譯)
- 符合Mapbox Vector Tile v2規範。
- 具有自動生成樣式的嵌入式查看器,可實現快速數據可視化
- 支持PostGIS和GeoPackage數據提供程序。可擴展的設計,以支持其他數- 據提供商。
- 支持多個緩存後端:file,s3,redis,azure blob store。
- 通過單個切片(ZXY),緯度/經度邊界和ZXY切片列表緩存種子和失效。
- 並行化的瓷磚服務和幾何處理。
- 支持Web Mercator(3857)和WGS84(4326)預測。
- 支持AWS Lambda。
導入osm數據
可以參考我前面的博文,使用最新編譯的osm2pgsql不用處理default.style中的註釋了,直接使用就可以了,我是用的是北京的數據,格式是pbf的。
最新版下載:https://ci.appveyor.com/project/openstreetmap/osm2pgsql
配置tegola的config.toml
參考官方配置說明,osm2pgsql導入數據的空間參考標識符 (SRID) 是3857不是經緯度的4326。
我的配置如下:
[webserver]
port = ":8080"
# register data providers
[[providers]]
name = "beijing" # provider name is referenced from map layers
type = "postgis" # the type of data provider. currently only supports postgis
host = "localhost" # postgis database host
port = 5432 # postgis database port
database = "beijing" # postgis database name
user = "postgres" # postgis database user
password = "123456" # postgis database password
srid = 3857 # The default srid for this provider. If not provided it will be WebMercator (3857)
[[providers.layers]]
name = "point"
tablename = "planet_osm_point"
geometry_fieldname = "way"
id_fieldname = "osm_id"
fields = [ "name" ]
#sql = "SELECT name,ST_AsBinary(way) AS way,name,osm_id FROM planet_osm_point WHERE way && !BBOX!"
[[providers.layers]]
name = "road"
geometry_fieldname = "way"
id_fieldname = "osm_id"
sql = "SELECT ST_AsBinary(way) AS way,name,osm_id FROM planet_osm_line WHERE way && !BBOX!"
[[maps]]
name = "beijing"
[[maps.layers]]
provider_layer = "beijing.point"
min_zoom = 13
max_zoom = 20
[[maps.layers]]
provider_layer = "beijing.road"
min_zoom = 10
max_zoom = 20
我這裏只配置了兩個圖層,一個點(point),13-20層顯示,一個線(road),10-20層顯示。
啓動tegola
在tegola所在目錄打開cmd,輸入 tegola serve 即可啓動
2019-04-18 09:04:18 [INFO] root.go:56: Loading config file: config.toml
2019-04-18 09:04:18 [INFO] config.go:173: loading local config (config.toml)
2019-04-18 09:04:19 [INFO] server.go:81: starting tegola server on port :8080
輸入tegola -h可以獲取幫助
編寫前端顯示html
<!DOCTYPE html>
<html>
<meta charset="UTF-8" />
<head>
<title>Tegola Sample</title>
<link rel="stylesheet" href="ol.css" type="text/css" />
<script src="ol.js"></script>
<style>
#map {
width: 1200px;
height: 700px;
}
</style>
</head>
<body>
<div id="map" class="map"></div>
<div id="name" style="font-size: 24px;"></div>
<script type="text/javascript">
var defaultStyle = new ol.style.Style({
fill: new ol.style.Fill({
color: [234, 231, 221, 1]
}),
stroke: new ol.style.Stroke({
color: [182, 177, 162, 1],
width: 1
})
});
var waterStyle = new ol.style.Style({
fill: new ol.style.Fill({
color: [28, 121, 181, 1]
}),
stroke: new ol.style.Stroke({
color: [27, 107, 159, 1],
width: 1
})
});
var streetStyle = new ol.style.Style({
fill: new ol.style.Fill({
color: [111, 44, 173, 1]
}),
stroke: new ol.style.Stroke({
color: [93, 32, 150, 1],
width: 1
})
});
var textStyle = new ol.style.Text({
font: "normal 14px 微軟雅黑", //字體與大小
fill: new ol.style.Fill({
//文字填充色
color: "#000"
}),
text: "text",
stroke: new ol.style.Stroke({
//文字邊界寬度與顏色
color: "#fff",
width: 3
})
});
var initStyle = new ol.style.Style({
fill: new ol.style.Fill({
color: "rgba(255, 255, 255, 0.2)"
}),
stroke: new ol.style.Stroke({
color: "red",
width: 2
}),
image: new ol.style.Circle({
radius: 8,
stroke: new ol.style.Stroke({
color: "red",
width: 2
})
})
});
var xStyle = new ol.style.Style({
image: new ol.style.RegularShape({
fill: new ol.style.Fill({
color: "red"
}),
stroke: new ol.style.Stroke({
color: "red",
width: 2
}),
points: 3,
radius: 8,
radius2: 0,
angle: Math.PI / 3 + Math.PI
})
});
function styleFunction(feature, resolution) {
if (
feature.get("type") == "water" ||
feature.get("layer") == "lakes" ||
feature.get("layer") == "water_lines"
) {
return [waterStyle];
}
if (feature.get("layer") == "point") {
return [xStyle, initStyle];
}
if (feature.get("layer") == "road") {
return [streetStyle];
}
if (
feature.get("layer") == "country_polygons" ||
feature.get("layer") == "landuse_areas"
) {
return null; // return null for no style to be applied
}
return [defaultStyle];
}
var map = new ol.Map({
target: "map",
layers: [
new ol.layer.VectorTile({
source: new ol.source.VectorTile({
format: new ol.format.MVT(),
url: "http://127.0.0.1:8080/maps/beijing/{z}/{x}/{y}.mvt"
}),
style: styleFunction
})
],
view: new ol.View({
center: ol.proj.fromLonLat([116.41, 39.82]), //coordinates the map will center on initially
zoom: 14,
minZoom: 0,
maxZoom: 20
})
});
var scaleLineControl = new ol.control.ScaleLine({
// 設置比例尺單位爲degrees、imperial、us、nautical或metric(度量單位)
units: "metric"
});
map.addControl(scaleLineControl);
</script>
</body>
</html>