css - D3 map 不以页面为中心?

标签 css d3.js

我在网页上将我的 D3 map 居中时遇到困难。 map 位于 map 类和 div 中,但 CSS 似乎不会使其居中。

我对 SVG 所在的类“.map”应用的任何边距似乎也不起作用。我不确定为什么我无法将任何 CSS 应用于 map ,但也许我应该在实际的 D3 代码中做一些事情?不确定。谢谢!

这是我的代码:

<!DOCTYPE html>
<html>

<head>
  <script src="https://d3js.org/d3.v4.min.js"></script>
  <script src='https://cdnjs.cloudflare.com/ajax/libs/d3-tip/0.7.1/d3-tip.js'></script>
  <meta charset='utf-8'>
  <meta name="viewport" content='width=device-width, initial-scale=1.0'>
  <title></title>
  <style>
    .d3-tip {
      line-height: 1;
      font-weight: bold;
      padding: 10px;
      background: rgba(0, 0, 0, 0.8);
      color: #fff;
      border-radius: 10px;
    }

    .active {
      fill: rgba(149, 165, 166, 0.8);
    }

    body {
      background: rgba(32, 32, 32, 1);
      color: rgba(255, 255, 255, 0.8);
    }

    h1 {
      font-family: Impact, Charcoal, sans-serif;
      text-align: center;
    }

    h2 {
      font-family: Impact, Charcoal, sans-serif;
      text-align: center;
    }

    p {
      font-family: "Arial Black", Gadget, sans-serif;
      text-align: center;
    }

    #box {
      border: 10px solid black;
      margin: auto;
      padding: 10px;
      width: 75%;
      border-radius: 10px;
    }

    .map {
      margin-left: auto;
      margin-right: auto;
    }
  </style>
  <script>
    function draw(geo_data) {

      var margin = 0,
        width = 2000 - margin,
        height = 700 - margin;

      var centered;

      var svg = d3.select('#map')
        .append('svg')
        .attr('width', width + margin)
        .attr('height', height + margin)
        .append('g')
        .attr('class', 'map');

      var formatComma = d3.format(",")

      var projection = d3.geoAlbersUsa();

      var path = d3.geoPath().projection(projection);

      var map = svg.selectAll('path')
        .data(geo_data.features)
        .enter()
        .append('path')
        .attr('d', path)
        .attr('fill', 'rgba(105, 105, 105, 1)')
        .attr('stroke', 'rgba(0, 0, 0, 1)')
        .attr('stroke-width', 0.5)
        .on('mouseover', function(d) {
          d3.select(this).attr('fill', 'rgba(108, 122, 137, 0.5)')
        })
        .on('mouseout', function() {
          if (d3.select(this).classed('clicked')) {
            console.log('is clicked')
            d3.select(this).attr('fill', 'rgba(105, 105, 105, 1)')
          } else {
            console.log('is not clicked')
            d3.select(this).attr('fill', 'rgba(105, 105, 105, 1)')
          }
        })
        // Calls click-to-zoom function defined below.
        .on('click', clicked);

      var tip = d3.tip()
        .attr('class', 'd3-tip')
        .offset([-10, 0])
        .html(function(d) {
          return "<p><font size='4rem'>" + d.city + ", " + d.state + "</p></font>" + "<p><font size='3rem'><strong>Guns Manufactured: </strong>" + formatComma(d.guns) + "</p>" +
            "<p><strong>Top Manufacturer:</strong> " + d.manufacturer +
            "</p></font>";
        })

      svg.call(tip);

      // Click-to-zoom function adapted from Mike Bostock's code: https://bl.ocks.org/mbostock/2206590

      function clicked(d) {

        d3.select(this).attr('fill', 'rgba(108, 122, 137, 0.5)');
        if (d3.select(this).classed('clicked')) {
          d3.select(this).attr('clicked', false);
        } else {
          d3.select(this).attr('clicked', true);
        }

        var x, y, k;

        if (d && centered !== d) {
          var centroid = path.centroid(d);
          x = centroid[0];
          y = centroid[1];
          k = 4;
          centered = d;
        } else {
          x = width / 2;
          y = height / 2;
          k = 1;
          centered = null;
        }

        map.selectAll('path')
          .classed('active', centered && function(d) {
            return d === centered;
          });

        map.transition()
          .duration(1000)
          .attr('transform', 'translate(' + width / 2 + ',' + height / 2 + ')scale(' + k + ')translate(' + -x + ',' + -y + ')')
          .style('stroke-width', 1 / k + 'px');

        // Transitions circles upon zoom.

        svg.selectAll('circle')
          .transition()
          .duration(1000)
          .attr('transform', 'translate(' + width / 2 + ',' + height / 2 + ')scale(' + k + ')translate(' + -x + ',' + -y + ')')
          .style('stroke-width', 1 / k + 'px');
      }

      d3.csv('https://raw.githubusercontent.com/dieterholger/US-Gun-Manufacturing-Interactive/master/top100cities.csv', function(error, data) {

        // Converts strings in csv to integers so they can be used.

        data.forEach(function(d) {
          return d.guns = +d.guns;
        })

        // This returns the max number of guns.

        var guns = data.map(function(d) {
          return d.guns;
        });

        var guns_extent = d3.extent(data, function(d) {
          return d.guns;
        });

        var radius = d3.scaleSqrt()
          .domain(guns_extent)
          .range([2, 40]);

        svg.append('g')
          .attr('class', 'bubble')
          .selectAll('circle')
          .data(data)
          .enter()
          .append('circle')
          .attr('cx', function(d) {
            return projection([d.lon, d.lat])[0];
          })
          .attr('cy', function(d) {
            return projection([d.lon, d.lat])[1];
          })
          .attr('r', function(d) {
            return radius(d.guns);
          })
          .attr('fill', 'rgba(248, 148, 6, 0.5)')
          .attr('stroke', 'black')
          .on('mouseover', function(d) {
            tip.show(d);
            return d3.select(this).attr('fill', 'rgba(248, 148, 6, 0.9)');
          })
          .on('mouseout', function(d) {
            tip.hide(d);
            return d3.select(this).attr('fill', 'rgba(248, 148, 6, 0.5)');
          })


      });
    };
  </script>
</head>

<body>

  <div id='box'>
  </div>
  <div id='map'>
    <h2>Hover your mouse to see data on the cities and click a state to zoom in.</h2>
  </div>
  <div id='box'>
  </div>
  <script>
    d3.json('https://raw.githubusercontent.com/dieterholger/US-Gun-Manufacturing-Interactive/master/us_states.json', draw);
  </script>
</body>

最佳答案

将 map 包含在另一个 div 中,其宽度与其上方的框相同 (75%)。您可能希望将 div 样式移动到 CSS 类,如果它按您想要的方式工作的话。

<div style="display:block; margin-left:auto; margin-right:auto; width:75%">
    <div id="map">
    ...
    </div>
</div>

更新

我刚刚发现了真正的问题。您对 ma​​pcss 定义是针对类的,而不是针对 id 的。并且......如果你想使用自动边距,你需要定义一个宽度。

更改您的 css 以匹配以下内容:

#map {
  width: 75%;
  margin-left: auto;
  margin-right: auto;
} 

关于css - D3 map 不以页面为中心?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49278757/

相关文章:

d3.js。带酒吧的旋转地球仪

javascript - 如何将图像附加到特定位置的另一个元素上?

javascript - 使用与使用 JavaScript 的任何其他元素相同的样式设置 textarea 内容的样式?

html - 行内 block 元素扩展下面的空间

javascript - 如何反转 d3 色带 d3-scale-chromatic d3.interpolateViridis

javascript - Svg 如何像 float 一样左右定位元素?

javascript - D3JS - 以恒定速度沿 svg 路径制作圆圈

css - 将可折叠按钮对齐到导航栏的右侧

javascript - 在 jQuery 中滑动 3D 旋转木马

javascript - D3.js 强制布局突出显示,无需单击或悬停