本篇簡單介紹一下使用D3.js繪制地圖,並更具經緯度在地圖打點。最后根據點生成voronoi圖及其三角網。
下載地圖geoJson文件
去網上下載要繪制地圖的geoJson文件。
使用d3.json()
加載地圖文件,這里為了方便加載我把geoJson文件放在了js文件里。
繪制地圖
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title></title>
</head>
<body>
<div id="test-svg">
</div>
</body>
<script src="https://d3js.org/d3.v5.js"></script>
<script type="text/javascript" src="js/china.js"></script>
<script>
window.onload = function() {
var width = 1900,
height = 800;
var svg = d3.select("#test-svg")
.append('svg')
.attr('width', width + 'px')
.attr('height', height + 'px');
/*
* 創建一個地理投影
* .center 設置投影中心位置
* .scale 設置縮放系數
*
*/
var projection = d3.geoMercator()
.center([463, 36])
.scale(850)
.translate([width / 2, height / 2]);
// 創建路徑生成器path
var path = d3.geoPath().projection(projection);
// 獲取GeoJSON數據:這里我放在了js中方便加載
var features = china.features;
// 設置顏色值
var ss2 = d3.schemeSet2;
var sp2 = d3.schemePastel2;
/*
* 渲染地圖
*
* mouseover 鼠標移入變色
*
*/
svg.append('g')
.attr('class', 'map')
.selectAll('.china')
.data(features)
.join('path')
.attr('class', 'china')
.attr("fill", function(d, i) {
return ss2[i % 3]
})
.attr('d', path)
.on("mouseover", function(d, i) {
d3.select(this)
.attr("fill", sp2[i % 3]);
})
.on("mouseout", function(d, i) {
d3.select(this)
.attr("fill", ss2[i % 3]);
});
}
</script>
</html>
- 繪制效果
- 附:d3顏色方案API d3-scale-chromatic
地圖打點
a) 首先去取一些點
http://geojson.io 在網站上找到我國疆土,標注幾個城市,在右邊獲取到經緯度。
b) 把點坐標放到我們的json中
var points = china.points.features;
var coo = function(d){
// 獲取經緯度
var lngLat = d.geometry.coordinates;
// 轉為映射在地圖上的坐標
var coo = projection(lngLat);
return coo;
}
svg.selectAll('circle')
.data(points)
.join('circle')
.attr("class", "point")
.attr("cx", function(d){
return coo(d)[0];
})
.attr("cy", function(d){
return coo(d)[1];
})
.attr("fill", "#ff9")
.attr("r", 4);
添加Voronoi圖
Voronoi圖 又稱沃羅諾伊圖、泰森多邊形,繪制的過程是將點都連起來構成許多三角形,然后利用中垂線找到三角形外心,再將所有外心連接即可。在幾何、晶體學、建築學、地理學、氣象學、信息系統等許多領域有廣泛的應用。
// 獲取所有點的經緯度
var _points = points.map(function(d){
return coo(d);
});
// 創建voronoi
var voronoi = d3.voronoi().extent([
[0, 0],
[width, height]
]);
var polygons = voronoi(_points);
function polygon(d) {
return "M" + d.join("L") + "Z";
}
svg.append('g')
.attr('class', 'map')
.selectAll('.country')
.data(voronoi.polygons(_points))
.join('path')
.attr("fill", "none")
.attr("stroke", "#ff9")
.attr('class', 'voronoi')
.attr('d', polygon);
繪制Voronoi圖的三角網
- 得到的三角網數據如下,這里將它們從
source
到target
依次連成線
svg.append('g')
.selectAll('line')
.data(voronoi.links(_points))
.join('line')
.attr("stroke", "#ff9")
.attr('stroke-dasharray', 10)
.attr('class', 'line')
.attr('x1', function(d) {
return d.source[0];
})
.attr('y1', function(d) {
return d.source[1];
})
.attr('x2', function(d) {
return d.target[0]
})
.attr('y2', function(d) {
return d.target[1]
});