用户输入JSON地图上的Project

时间:2017-01-01 21:04:52

标签: javascript json d3.js

我有以下可用的D3.js项目:

http://bl.ocks.org/diggetybo/raw/e75dcb649ae3b26e2312a63434fc970c/

纬度和经度输入位于地图下方。

它应该获取用户输入的纬度和经度数,并在给定坐标处“投射”svg圆圈。问题是我要么____不是函数错误,或者dev工具根本没有抛出任何错误,但是圈子从未被投射过。

这是一个简短的文件,有人可以解释为什么它不像我想的那样工作吗?

1 个答案:

答案 0 :(得分:2)

您的更新功能没有任何意义。

  1. 它接受两个输入,但你只能用一个输入。
  2. .selectAll("circle").enter()无效d3语法。
  3. 您需要同时使用纬度和经度调用projection,然后传递0,这将导致它返回null,因为它在投影之外。
  4. 解决了所有这些问题之后,你仍然会离开,因为你已经按照边距移动了路径,最好将它们放在由边距移动的g中。
  5. 所有这一切,简单的重写将是:

    var lat = d3.select("#latValue").on("input", function() {
        update();
    }).node();
    
    var long = d3.select("#lonValue").on("input", function() {
        update();
    }).node();
    
    function update() {
    
      // lat/long to pixel
      var coors = projection([long.value, lat.value]);
    
      // if outside projection don't add circle
      if (coors === null) return;
    
      // add circle
        container
            .append("circle")
            .attr("cx", coors[0])
            .attr("cy", coors[1])
            .attr("r", Math.sqrt(5) * 4)
            .style("fill", "black")
            .style("opacity", 0.85);
    }
    

    运行代码:

    <!DOCTYPE html>
    <html lang="en">
    <head>
    <meta charset="utf-8">
    <script src="http://d3js.org/d3.v3.min.js"></script>
    <style type="text/css">
    
    /* On mouse hover, lighten state color */
    path:hover {
    	fill-opacity: .7;
    }
    </style>
    </head>
    <body>
    <script type="text/javascript">
    
    //Width and height of map
    var width = 960;
    var height = 500;
    var margins = { left: 0, top: 100, right: 0, bottom: 0 };
    // D3 Projection
    var projection = d3.geo.albersUsa()
    				   .translate([width/2, height/2])    // translate to center of screen
    				   .scale([1000]);          // scale things down so see entire US
    
    // Define path generator
    var path = d3.geo.path()               // path generator that will convert GeoJSON to SVG paths
    		  	 .projection(projection);  // tell path generator to use albersUsa projection
    
    // Define linear scale for output
    var color = d3.scale.linear()
    			  .range(["#c3e2ff","#15198e"]);
    
    //Create SVG element and append map to the SVG
    var svg = d3.select("body")
    			.append("svg")
    			.attr("width", width)
    			.attr("height", height+margins.top);
    
    svg.append('text')
      .text('Coordinate Query')
      .attr('font-size','24px')
      .attr('transform', 'translate(' + 30 + ',' +70 + ')')
      .attr('font-family','Calibri');
    
    svg.append('text')
      .text('Data as of 12/2016')
      .attr('font-size','12px')
      .attr('transform', 'translate(' + 35 + ',' +100 + ')')
      .attr('font-family','Calibri');
    // Load in my states data!
    color.domain([0,100]); // setting the range of the input data
    // Load GeoJSON data and merge with states data
    d3.json("https://jsonblob.com/api/573228c3-d068-11e6-b16a-b501dc8d2b08", function(json) {
    
    //var coordinates = d3.mouse(this);
    // Bind the data to the SVG and create one path per GeoJSON feature
    var container = svg.append("g")
    	.attr('transform', 'translate(' + margins.left + ',' + margins.top + ')');
    
    container.selectAll("path")
    	.data(json.features)
    	.enter()
    	.append("path")
    	.attr("d", path)  
    	.style("stroke", "#fff")
      .style("stroke-linejoin","round")
    	.style("stroke-width", "1.5")
    	.style("fill", 'steelblue');
    
    
    // Modified Legend Code from Mike Bostock: http://bl.ocks.org/mbostock/3888852
    var lat = d3.select("#latValue").on("input", function() {
    	update();
    }).node();
    
    var long = d3.select("#lonValue").on("input", function() {
    	update();
    }).node();
    
    function update() {
      
      // lat/long to pixel
      var coors = projection([long.value, lat.value]);
      
      // if outside projection don't add circle
      if (coors === null) return;
      
      // add circle
    	container
    		.append("circle")
    		.attr("cx", coors[0])
    		.attr("cy", coors[1])
    		.attr("r", Math.sqrt(5) * 4)
    		.style("fill", "black")
    		.style("opacity", 0.85);
    
    }
      
    });
    </script>
    <p>
    	<label 	for="latValue"
    					style="display: inline-block;width:240px;text-align:right;font-size:18px;font-family:Play">
    					Lattitude:<span id="latValue-value"></span>
    	</label>
    	<input type="number"min="-360"max="360"step="1"value="0" id="latValue">
    	<label 	for="lonValue"
    					style="display: inline-block;width:240px;text-align:right;font-size:18px;font-family:Play">
    					Longitude:<span id="lonValue-value"></span>
    	</label>
    	<input type="number"min="-360"max="360"step="1"value="0" id="lonValue">
    </p>
    </body>
    </html>