【问题标题】:Creating and appending detached elements with d3.create使用 d3.create 创建和附加分离的元素
【发布时间】:2018-04-24 10:23:36
【问题描述】:

假设我创建了一个像这样的简单图形:

<!doctype html>
<html lang="en">

<head>
  <script src="https://d3js.org/d3.v5.min.js"></script>
</head>

<body>
  <svg></svg>
  <script>
    const svg = d3.select('svg');
    const g = svg.append('g');

    g.append('g')
      .selectAll('g')
      .data([5, 10, 20, 40])
      .enter()
      .append('rect')
      .attr('fill', 'green')
      .attr('x', d => d)
      .attr('y', d => d)
      .attr('height', d => d)
      .attr('width', d => d);
  </script>
</body>

</html>

但是,我想创建一个分离的&lt;g&gt;,而不是仅仅附加到它,然后可以随意附加它(例如,它可以从函数返回)。

在 d3 V5 中,有一个 d3.create() 函数可以创建一个分离的元素。

<!doctype html>
<html lang="en">

<head>
  <script src="https://d3js.org/d3.v5.min.js"></script>
</head>

<body>
  <svg></svg>
  <script>
    const svg = d3.select('svg');
    const g = svg.append('g');

    const detachedG = d3.create('g');
    detachedG.selectAll('g')
      .data([5, 10, 20, 40])
      .enter()
      .append('rect')
      .attr('fill', 'green')
      .attr('x', d => d)
      .attr('y', d => d)
      .attr('height', d => d)
      .attr('width', d => d);

    g.append(() => detachedG.node());
  </script>
</body>

</html>

但它不会出现在浏览器中,即使 DOM 看起来一样。

任何想法如何解决这个问题?

【问题讨论】:

    标签: javascript d3.js svg


    【解决方案1】:

    只需命名它:

    const detachedG = d3.create('svg:g');
    

    这是更改后的代码:

    <!doctype html>
    <html lang="en">
        <head><script src="https://d3js.org/d3.v5.min.js"></script></head>
        <body>
            <svg></svg>
            <script>
                const svg = d3.select('svg');
                const g = svg.append('g');
    
                const detachedG = d3.create('svg:g');
                detachedG.selectAll('g')
                    .data([5,10,20,40])
                    .enter()
                    .append('rect')
                    .attr('fill', 'green')
                    .attr('x', d => d)
                    .attr('y', d => d)
                    .attr('height', d => d)
                    .attr('width', d => d);
    
                g.append(() => detachedG.node());
            </script>
        </body>
    </html>

    说明

    当使用append() 方法附加 SVG 元素时,98.47% 的 D3 程序员不使用命名空间(来源:Fakedata Inc.)。因此,而不是:

    selection.append("svg:rect")
    

    我们通常只是这样做:

    selection.append("rect") 
    

    那么,这里为什么需要命名空间?

    在内部,d3.create 使用 d3.creator 使用 document.documentElement 调用它:

    export default function(name) {
        return select(creator(name).call(document.documentElement));
    }
    

    这会更改 thisd3.creator 方法。当我们使用 append(内部使用 d3.creator)创建 SVG 元素时,我们通常不使用命名空间,因为:

    如果没有指定命名空间,命名空间将继承自父元素。

    但是,由于将document.documentElement 用作this,因此在这种情况下命名空间变得必要。

    【讨论】:

    • 你会使用什么命名空间来创建一个未附加的 div ? d3.create("div:div") 会好吗?谢谢
    • @user2728841 在这种情况下不需要命名空间,因为 div 是一个 HTML 元素。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2014-03-10
    • 1970-01-01
    • 1970-01-01
    • 2017-10-04
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多