d3地图遇到的问题

来源:互联网 发布:河南省考行测成绩算法 编辑:程序博客网 时间:2024/05/17 03:26

同事最近遇到一个问题,就是用d3画出地图,然后在地图上画散点图,画完之后经过缩放,发现散点也跟着放大缩小,这样很难看,她希望能跟eharts一样能地图变大,散点不变,或者看似对于地图变小,于是我就开动,研究了一下这个问题,下面贴出问题解决代码:

<!DOCTYPE html><html lang="en"><head>    <meta charset="UTF-8">    <title>d3地图</title>    <style type="text/css">        .province{            stroke: black;            stroke-width:1px;        }        .overlay{            fill:none;            pointer-events: all;        }    </style></head><body>    <script type="text/javascript" src = "http://d3js.org/d3.v3.min.js"></script>    <script type="text/javascript">        var width = 1000;        var height = 800;        var svg = d3.select("body")                    .append("svg")                    .attr("width",width)                    .attr("height",height);        //定义投影函数        var projection = d3.geo.mercator()                            .center([107,31])                            .scale(600)                            .translate([width/2,height/2]);        //使用投影定义函数定义地理路径生成器        var path = d3.geo.path()                        .projection(projection);        var color = d3.scale.category20();        //以北京的经纬度作为投影的参数,得到北京的像素坐标        var peking = [116.3,39.9];        var proPeking = projection(peking);        var initTran = projection.translate();        var initScale = projection.scale();        //用上面得到的像素坐标绘制一个圆,该圆就正好位于北京的位置        d3.json("d3Province/china.json",function(error,toporoot){            if(error)                return console.error(error);            console.log(toporoot);            var zoom = d3.behavior.zoom()                        .scaleExtent([1,10])                        .on("zoom",function(d){                            d3.select("g").attr("transform","translate(" + d3.event.translate + ")" + "scale(" + d3.event.scale + ")");                            d3.select("circle").attr("r",8/d3.event.scale);                        })            ////////////////////////////////            var groups = svg.append("g").call(zoom)            var countries = groups.selectAll("path")                .data(toporoot.features)                .enter()                .append("path")                .attr("class","province")                .attr("d",path)                .style("fill",function(d,i){                    return color(i);                })                .call(zoom)            var circle = groups.append("circle")                    .attr("class","point")                    .attr("cx",proPeking[0])                    .attr("cy",proPeking[1])                    .attr("r",8)                    .attr("fill","yellow")        })    </script></body></html>

这里用北京的经纬度,经过定义的投影函数,转换成画布上的图标,然后用缩放用于缩放地图,解决办法就是这一行代码

d3.select("circle").attr("r",8/d3.event.scale);

当地图跟着缩放的时候,散点跟着相反的以相同的比例缩放,也就是说地图变大,散点圆的半径变小,地图缩小,散点圆的半径变大,这就是解决办法,下面贴出效果图

这里写图片描述

这里写图片描述

上下两个图对比非常明显