
~~~
<html>
<head>
<meta charset="utf-8">
<title>中國地圖</title>
</head>
<style type="text/css">
*{
margin: 0;
padding: 0;
}
.link {
stroke: #ccc;
stroke-width: 0.5;
}
</style>
<body>
<script src="js/d3.min.js" type="text/javascript" charset="utf-8"></script>
<script src="js/jquery-1.11.3.min.js" type="text/javascript" charset="utf-8"></script>
<script type="text/javascript">
var width = 2000;
var height = 1000;
var svg = d3.select("body").append("svg")
.attr("width", width)
.attr("height", height)
.append("g")
.attr("transform", "translate(0,0)");
/*定義投影*/
var projection1 = d3.geo.mercator() //麥克托投影法
.center([107, 31]) //地圖的經緯度(將制定的經緯度設定為地圖的中心)
.scale(850) //地圖放大比例
.translate([width/2, height/2]); //位移
/*傳入投影,并計算路徑*/
var path = d3.geo.path()
.projection(projection1); //將三維地圖投影到二維坐標上。為了避免混淆,特意將projection改成projection1
var force = d3.layout.force().size([900, 900]); //size設定容器的中心
var color = d3.scale.category20();
d3.json("json/chinamap.json", function(error, root) {
if (error)
return console.error(error);
/*定義兩個數組存儲節點和邊*/
var nodes = [];
var links = [];
root.features.forEach(function(d, i) {
var centroid = path.centroid(d); //計算出數據的中點
centroid.x = centroid[0]; //數組0元素中存著中點的橫坐標
centroid.y = centroid[1]; //數組1元素中存著中點的縱坐標
centroid.feature = d; //把數據存到feature中
nodes.push(centroid); //將節點推進組數
});
var triangles = d3.geom.voronoi().triangles(nodes); //將節點進行三角剖分,將結果保存在triangles中
triangles.forEach(function(d,i){ //用循環,將每個三角的三個點兩兩相連,推進邊數組中
links.push( edge( d[0] , d[1] ) ); //edge函數在后面
links.push( edge( d[1] , d[2] ) );
links.push( edge( d[2] , d[0] ) );
});
force.gravity(0) //從中心產生的重力
.charge(0) //吸引力和排斥力
.nodes(nodes) //綁定節點
.links(links) //綁定連線
.linkDistance(function(d){ return d.distance; }) //設置連線的距離
.start(); //產生作用
var node = svg.selectAll("g")
.data(nodes)
.enter().append("g")
.attr("transform", function(d) { return "translate(" + -d.x + "," + -d.y + ")"; })
.call(force.drag) //不寫這句不能拖動
.append("path")
.attr("stroke","#000")
.attr("stroke-width",1)
.attr("fill", function(d,i){ //為地圖填充顏色
return color(i);
})
.attr("d", function(d){
return path(d.feature);
} );
var link = svg.selectAll("line") //添加連線
.data(links)
.enter()
.append("line")
.attr("class","link")
.attr("x1",function(d) { return d.source.x; } )
.attr("y1",function(d) { return d.source.y; } )
.attr("x2",function(d) { return d.target.x; } )
.attr("y2",function(d) { return d.target.y; } );
force.on("tick", function() { //及時設定force的源頭和末尾
link.attr("x1", function(d) { return d.source.x; })
.attr("y1", function(d) { return d.source.y; })
.attr("x2", function(d) { return d.target.x; })
.attr("y2", function(d) { return d.target.y; });
node.attr("transform", function(d) { //也就是nodes的數據一直在變,及時將位移改變
return "translate(" + d.x + "," + d.y + ")";
});
});
});
/*edge函數,返回源頭和目標以及距離*/
function edge(a, b) {
var dx = a[0] - b[0], dy = a[1] - b[1];
return {
source: a,
target: b,
distance: Math.sqrt(dx * dx + dy * dy)
};
}
</script>
</body>
</html>
~~~
- 前言
- 【d3.js教程01】d3入門
- 【d3.js教程02】d3入門
- 【d3.js教程03】動態初探索
- 【d3.js教程04】互動第一步
- 【d3.js教程05】簡單的圖標之弧形
- 【d3.js教程06】force 力導向圖
- 【d3.js教程07】弦圖
- 【d3.js教程08】集群圖cluster
- 【d3.js教程09】包圖pack
- 【d3.js教程10】氣泡圖bubble chart
- 【d3.js教程11】氣泡圖指定顏色
- 【d3.js教程12】地圖
- 【d3.js教程13】氣泡圖一維與多維展示以及數據處理
- 【d3.js教程14】可拖動的地圖詳解
- 【d3.js教程15】如何從excel等表格生成csv數據