Skip to content

Commit a0545b8

Browse files
committed
Leaflet部分:增加自定义范围打印输出.绘制矩形,输出矩形范围内地图,支持增加图框、标题、左右下角说明文字
1 parent 9ae5c82 commit a0545b8

File tree

11 files changed

+1353
-224
lines changed

11 files changed

+1353
-224
lines changed

config/config-leaflet.js

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -187,7 +187,16 @@ var config = {
187187
icon: "boundarycanvas.png",
188188
update: "最后更新时间:2018-11-2",
189189
person: "基础平台/产品中心-龚跃健"
190-
}
190+
},
191+
{
192+
name: "自定义范围打印输出",
193+
file: "customprint",
194+
diffcult: "1",
195+
detail: "绘制矩形,输出矩形范围内地图,支持增加图框、标题、左右下角说明文字",
196+
icon: "customprint.png",
197+
update: "最后更新时间:2018-12-18",
198+
person: "基础平台/产品中心-龚跃健"
199+
}
191200
]
192201
},
193202
{
Lines changed: 241 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,241 @@
1+
<!DOCTYPE html>
2+
<html xmlns="http://www.w3.org/1999/xhtml">
3+
<head>
4+
<meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
5+
<title>导出成图片</title>
6+
<script include="filesaver,draw,domtoimage"
7+
src="../../libs/zondyclient/include-leaflet-local.js"></script>
8+
<style>
9+
body {
10+
height: 700px;
11+
}
12+
</style>
13+
<script type="text/javascript">
14+
//定义地图
15+
var map;
16+
var extent = {};//地图范围
17+
var scale;//比例尺
18+
var extent_km = 111.319490793274;
19+
/**初始化地图显示
20+
*/
21+
function init() {
22+
//地图容器
23+
map = L.map('leaf_map', {
24+
//参考坐标系
25+
crs: L.CRS.EPSG3857,
26+
//显示中心
27+
center: [40, 116.3],
28+
//最小显示等级
29+
minZoom: 0,
30+
//最大显示等级
31+
maxZoom: 16,
32+
//当前显示等级
33+
zoom: 12
34+
});
35+
//加载瓦片图层数据(OSM)
36+
var tiles = L.tileLayer('http://{s}.tile.osm.org/{z}/{x}/{y}.png', {
37+
//只显示一个图层,不平铺显示
38+
noWrap: true
39+
}).addTo(map);
40+
41+
//添加绘制图层
42+
var drawnItems = new L.FeatureGroup();
43+
map.addLayer(drawnItems);
44+
//添加绘制控件
45+
var drawControl = new L.Control.Draw({
46+
draw: {
47+
//绘制线
48+
polyline: false,
49+
//绘制多边形
50+
polygon: false,
51+
//绘制矩形
52+
rectangle: true,
53+
//绘制圆
54+
circle: false,
55+
//绘制标注
56+
marker: false,
57+
//绘制圆形标注
58+
circlemarker: false
59+
}
60+
});
61+
//添加绘制控件
62+
map.addControl(drawControl);
63+
//绘制事件
64+
map.on(L.Draw.Event.CREATED, function (e) {
65+
66+
var bounds = e.layer._bounds;
67+
//地图边框,已放入绘制接口(dom-to-image)中绘制
68+
// var Rectangle = L.rectangle(bounds, {
69+
// color: '#000',
70+
// weight: 1,
71+
// fillColor: 'rgba(255, 255, 255, 0)'
72+
// }).addTo(map);
73+
// Rectangle.name = "MapFrame";
74+
extent.xmin = bounds._southWest.lng;
75+
extent.ymin = bounds._southWest.lat;
76+
extent.xmax = bounds._northEast.lng;
77+
extent.ymax = bounds._northEast.lat;
78+
79+
getRecommendScale();
80+
81+
var a1 = map.options.crs.latLngToPoint(L.latLng(bounds._northEast.lat, bounds._southWest.lng), map.getZoom());//左上
82+
var a4 = map.options.crs.latLngToPoint(L.latLng(bounds._southWest.lat, bounds._northEast.lng), map.getZoom());//右下
83+
var mapBounds = map.getBounds();
84+
var mapLeftTopPoint = map.options.crs.latLngToPoint(L.latLng(mapBounds._northEast.lat, mapBounds._southWest.lng), map.getZoom());
85+
var startPointX = mapLeftTopPoint.x - a1.x - 7;
86+
var startPointY = mapLeftTopPoint.y - a1.y - 7;
87+
var mapParams = {};
88+
mapParams.width = parseInt(a4.x - mapLeftTopPoint.x + 9);
89+
mapParams.height = parseInt(a4.y - mapLeftTopPoint.y + 10);
90+
mapParams.startPointX = startPointX;
91+
mapParams.startPointY = startPointY;
92+
93+
var layExtent = layoutSetting();
94+
var laya1 = map.options.crs.latLngToPoint(L.latLng(layExtent.ymax, layExtent.xmin), map.getZoom());//左上
95+
var laya4 = map.options.crs.latLngToPoint(L.latLng(layExtent.ymin, layExtent.xmax), map.getZoom());//右下
96+
var laystartPointX = mapLeftTopPoint.x - laya1.x - 9;
97+
var laystartPointY = mapLeftTopPoint.y - laya1.y - 9;
98+
99+
var layParams = {};
100+
layParams.width = parseInt(laya4.x - mapLeftTopPoint.x + 7);//输出地图版面宽
101+
layParams.height = parseInt(laya4.y - mapLeftTopPoint.y + 8);//输出地图版面高
102+
layParams.startPointX = laystartPointX;//输出地图版面的x像素坐标
103+
layParams.startPointY = laystartPointY;//输出地图版面的y像素坐标
104+
105+
//以下参数都是在有layParams的前提下,位置已设置为固定
106+
var mapFrameStyleParams = {};
107+
mapFrameStyleParams.strokeStyle = "black"; //图像的边框线颜色
108+
mapFrameStyleParams.lineWidth = 2;
109+
110+
var titleParams = {};
111+
titleParams.font = '30px 微软雅黑';
112+
titleParams.textAlign = 'center';
113+
titleParams.textBaseline = 'bottom';
114+
titleParams.text = '地图标题';
115+
116+
var leftTextParams = {};
117+
leftTextParams.font = '15px 微软雅黑';
118+
leftTextParams.textAlign = 'left';
119+
leftTextParams.textBaseline = 'top';
120+
leftTextParams.text = '左下角文字';
121+
122+
var rightTextParams = {};
123+
rightTextParams.font = '15px 微软雅黑';
124+
rightTextParams.textAlign = 'right';
125+
rightTextParams.textBaseline = 'top';
126+
rightTextParams.text = '右下角文字';
127+
128+
//width和height为必须参数,其他参数为可选参数(扩展参数)
129+
domtoimage.toPng(map.getContainer(), {
130+
width: mapParams.width,//输出地图内容的宽
131+
height: mapParams.height,//输出地图内容的高
132+
startPointX: mapParams.startPointX,//输出地图内容左上角x像素坐标
133+
startPointY: mapParams.startPointY,//输出地图内容左上角y像素坐标
134+
layParams: layParams,//输出版面参数
135+
mapFrameStyleParams: mapFrameStyleParams,//图框参数
136+
titleParams: titleParams,//标题参数
137+
leftTextParams: leftTextParams,//左下角文字参数
138+
rightTextParams: rightTextParams//右下角文字参数
139+
}).then(function (dataUrl) {
140+
var blob = _dataURItoBlob(dataUrl);
141+
saveAs(blob, 'map.png');
142+
});
143+
});
144+
}
145+
146+
/**
147+
* 将获取的图片路径转成blob
148+
* @param dataURI
149+
* @returns {*}
150+
* @private
151+
*/
152+
function _dataURItoBlob(dataURI) {
153+
var byteString = atob(dataURI.split(',')[1]);
154+
var mimeString = dataURI.split(',')[0].split(':')[1].split(';')[0];
155+
var ab = new ArrayBuffer(byteString.length);
156+
var dw = new DataView(ab);
157+
for (var i = 0; i < byteString.length; i++) {
158+
dw.setUint8(i, byteString.charCodeAt(i));
159+
}
160+
return new Blob([ab], {type: mimeString});
161+
}
162+
163+
/**
164+
* 获取建议的比例尺,比例尺也可以自己设置
165+
*/
166+
function getRecommendScale() {
167+
var x_min = extent.xmin;
168+
var y_min = extent.ymin;
169+
var x_max = extent.xmax;
170+
var y_max = extent.ymax;
171+
var map_width = (x_max - x_min) * extent_km * 1000 * 1000;
172+
var map_height = (y_max - y_min) * extent_km * 1000 * 1000;
173+
//纸张宽度,默认为横版A4大小
174+
var paper_width = 297;
175+
//纸张高度,默认为横版A4大小
176+
var paper_height = 210;
177+
var r_scale = (map_width / paper_width) > (map_height / paper_height) ? Math.ceil(map_width / paper_width) : Math.ceil(map_height / paper_height);
178+
var log10 = r_scale.toString().length - 1;
179+
var pow10 = Math.pow(10, log10);
180+
scale = Math.ceil(r_scale / pow10) * pow10;//直接使用推荐的比例尺
181+
}
182+
183+
/**
184+
* 获取输出版面坐标范围,默认以横版A4大小输出
185+
* @returns {{}}
186+
*/
187+
function layoutSetting() {
188+
var x_min = extent.xmin;
189+
var y_min = extent.ymin;
190+
var x_max = extent.xmax;
191+
var y_max = extent.ymax;
192+
//地图实际宽度
193+
var map_width = (x_max - x_min) * extent_km * 1000 * 1000;
194+
//地图实际高度
195+
var map_height = (y_max - y_min) * extent_km * 1000 * 1000;
196+
//纸张宽度,默认为横版A4大小
197+
var paper_width = 297;
198+
//纸张高度,默认为横版A4大小
199+
var paper_height = 210;
200+
//根据比例尺调整后的地图宽度(mm)
201+
var scale_map_width = Math.round(map_width / scale);
202+
//根据比例尺调整后的地图高度(mm)
203+
var scale_map_height = Math.round(map_height / scale);
204+
//纸张与地图的宽度差值
205+
var differ_width_val = (paper_width - scale_map_width) / 2;
206+
//纸张与地图的高度差值
207+
var differ_height_val = (paper_height - scale_map_height) / 2;
208+
var differ_x_extent = differ_width_val * scale / 1000 / 1000 / this.extent_km;
209+
var differ_y_extent = differ_height_val * scale / 1000 / 1000 / this.extent_km;
210+
//版面的左上角x坐标
211+
var layout_l_x = x_min - differ_x_extent;
212+
//版面的左上角y坐标
213+
var layout_l_y = y_max + differ_y_extent;
214+
//版面的右下角x坐标
215+
var layout_r_x = x_max + differ_x_extent;
216+
//版面的右下角y坐标
217+
var layout_r_y = y_min - differ_y_extent;
218+
219+
//输出版面范围
220+
// var bounds = [[layout_l_y, layout_l_x], [layout_r_y, layout_r_x]];
221+
// var Rectangle = L.rectangle(bounds, {
222+
// color: '#ffcc33',
223+
// weight: 2,
224+
// fillColor: 'rgba(255, 255, 255, 0)'
225+
// });
226+
// Rectangle.name = "layoutSetting";
227+
// Rectangle.addTo(map);
228+
var layExtent = {};
229+
layExtent.xmin = layout_l_x;
230+
layExtent.ymin = layout_r_y;
231+
layExtent.xmax = layout_r_x;
232+
layExtent.ymax = layout_l_y;
233+
return layExtent;
234+
}
235+
</script>
236+
</head>
237+
<body onload="init()">
238+
<div id="leaf_map" style="width: 100%; height: 95%;position: absolute">
239+
</div>
240+
</body>
241+
</html>
Lines changed: 52 additions & 39 deletions
Original file line numberDiff line numberDiff line change
@@ -1,52 +1,65 @@
11
<!DOCTYPE html>
22
<html xmlns="http://www.w3.org/1999/xhtml">
3+
34
<head>
4-
<meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
5+
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
56
<title>Draw</title>
67
<script include="Draw" src="../../libs/zondyclient/include-leaflet-local.js"></script>
78
<style>
8-
#map{height:600px}
9+
#map {
10+
height: 600px
11+
}
912
</style>
1013
</head>
14+
1115
<body>
12-
<div id="map"></div>
13-
<script>
14-
var osmUrl = 'http://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png',
15-
osmAttrib = '&copy; <a href="http://openstreetmap.org/copyright">OpenStreetMap</a> contributors',
16-
osm = L.tileLayer('https://api.tiles.mapbox.com/v4/{id}/{z}/{x}/{y}.png?access_token=' +
17-
'sk.eyJ1IjoiY2hlbmdkYWRhIiwiYSI6ImNqZDFjaGo0ZjFzcnoyeG54enoxdnNuZHUifQ.hTWXXBUQ0wdGeuDF3GWeUw', {
18-
attribution: '<a href="#">Mapbox</a>',
19-
maxZoom: 18,
20-
id: 'mapbox.streets',
21-
}),
22-
map = new L.Map('map', { center: new L.LatLng(30.58791323870018, 114.3474077911377), zoom: 10 }),
23-
drawnItems = L.featureGroup().addTo(map);
24-
L.control.layers({
25-
'osm': osm.addTo(map),
26-
"google": L.tileLayer('http://www.google.cn/maps/vt?lyrs=s@189&gl=cn&x={x}&y={y}&z={z}', {
27-
attribution: 'google'
28-
})
29-
}, { 'drawlayer': drawnItems }, { position: 'topleft', collapsed: false }).addTo(map);
30-
map.addControl(new L.Control.Draw({
31-
edit: {
32-
featureGroup: drawnItems,
33-
poly: {
34-
allowIntersection: false
16+
<div id="map"></div>
17+
<script>
18+
var osmUrl = 'http://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png',
19+
osmAttrib = '&copy; <a href="http://openstreetmap.org/copyright">OpenStreetMap</a> contributors',
20+
osm = L.tileLayer('https://api.tiles.mapbox.com/v4/{id}/{z}/{x}/{y}.png?access_token=' +
21+
'sk.eyJ1IjoiY2hlbmdkYWRhIiwiYSI6ImNqZDFjaGo0ZjFzcnoyeG54enoxdnNuZHUifQ.hTWXXBUQ0wdGeuDF3GWeUw', {
22+
attribution: '<a href="#">Mapbox</a>',
23+
maxZoom: 18,
24+
id: 'mapbox.streets',
25+
}),
26+
map = new L.Map('map', {
27+
center: new L.LatLng(30.58791323870018, 114.3474077911377),
28+
zoom: 10
29+
}),
30+
drawnItems = L.featureGroup().addTo(map);
31+
L.control.layers({
32+
'osm': osm.addTo(map),
33+
"google": L.tileLayer('http://www.google.cn/maps/vt?lyrs=s@189&gl=cn&x={x}&y={y}&z={z}', {
34+
attribution: 'google'
35+
})
36+
}, {
37+
'drawlayer': drawnItems
38+
}, {
39+
position: 'topleft',
40+
collapsed: false
41+
}).addTo(map);
42+
map.addControl(new L.Control.Draw({
43+
edit: {
44+
featureGroup: drawnItems,
45+
poly: {
46+
allowIntersection: false
47+
}
48+
},
49+
draw: {
50+
polygon: {
51+
allowIntersection: false,
52+
showArea: true
53+
}
3554
}
36-
},
37-
draw: {
38-
polygon: {
39-
allowIntersection: false,
40-
showArea: true
41-
}
42-
}
43-
}));
55+
}));
4456

45-
map.on(L.Draw.Event.CREATED, function (event) {
46-
var layer = event.layer;
57+
map.on(L.Draw.Event.CREATED, function (event) {
58+
var layer = event.layer;
4759

48-
drawnItems.addLayer(layer);
49-
});
50-
</script>
60+
drawnItems.addLayer(layer);
61+
});
62+
</script>
5163
</body>
52-
</html>
64+
65+
</html>
319 KB
Loading
Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
### 自定义范围打印输出
2+
> `说明:`只要map.getContainer()里有的图层都支持,包括标注、绘制的图层等。
3+
> 图框、标题、左下角文字、右下角文字必须在有输出版面参数的前提下,才能添加
4+
5+
```javascript
6+
//关键代码:
7+
//width和height为必须参数,其他参数为可选参数(扩展参数)
8+
domtoimage.toPng(map.getContainer(), {
9+
width: mapParams.width,//输出地图内容的宽
10+
height: mapParams.height,//输出地图内容的高
11+
startPointX: mapParams.startPointX,//输出地图内容左上角x像素坐标
12+
startPointY: mapParams.startPointY,//输出地图内容左上角y像素坐标
13+
layParams: layParams,//输出版面参数
14+
mapFrameStyleParams: mapFrameStyleParams,//图框参数
15+
titleParams: titleParams,//标题参数
16+
leftTextParams: leftTextParams,//左下角文字参数
17+
rightTextParams: rightTextParams//右下角文字参数
18+
}).then(function (dataUrl) {
19+
var blob = _dataURItoBlob(dataUrl);
20+
saveAs(blob, 'map.png');
21+
});
22+
```
15 KB
Binary file not shown.

0 commit comments

Comments
 (0)
pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy