javascript - D3、嵌套追加和数据流

标签 javascript d3.js

我终于在学习 D3 的过程中,偶然发现了一个我无法找到答案的问题。我不确定我的问题是因为我没有按照图书馆的惯用方式思考,还是因为我目前不知道的程序。我还应该提一下,我在 6 月份才开始做与网络相关的事情,所以我对 javascript 还很陌生。

假设我们正在构建一个工具,为用户提供带有相应图像的食物列表。让我们添加额外的约束,即每个列表项都需要用唯一的 ID 标记,以便它可以链接到另一个 View 。我解决这个问题的第一直觉是创建一个列表 <div>每个都有自己的 ID,其中每个 div有自己的<p><img> .生成的 HTML 看起来像:

<div id="chocolate">
  <p>Chocolate Cookie</p>
  <img src="chocolate.jpg" />
</div>
<div id="sugar">
  <p>Sugar Cookie</p>
  <img src="sugar.jpg" />
</div>

此工具的数据位于 JSON 数组中,其中单个 JSON 如下所示:

{ "label": "sugar", "text": "Sugar Cookie", "img": "sugar.jpg" }

有没有办法一次性生成 HTML?从添加 div 的基本情况开始,代码可能类似于:

d3.select(containerId).selectAll('div')                                                          
   .data(food)
   .enter().append('div')
   .attr('id', function(d) { return d.label; });

现在,添加一个 <div> 怎么样?用<p>在里面?我最初的想法是做类似的事情:

d3.select(containerId).selectAll('div')                                                          
   .data(food)
   .enter().append('div')
   .attr('id', function(d) { return d.label; })
       .append('p').text('somethingHere');

但是,我看到了两个问题:(1) 你如何从 div 中获取数据?元素,以及 (2) 如何在一个声明链中将多个子元素附加到同一个父元素?我想不出一种方法来完成第三步,我将在 img 上附加.

我在另一篇文章中发现了嵌套选择,它指向 http://bost.ocks.org/mike/nest/ .但是嵌套选择,因此将追加分成三个 block ,是否适合/惯用这种情况?或者实际上是否有一种结构良好的方法可以在一个声明链中形成这种结构?似乎有一种方法可以在 https://github.com/mbostock/d3/wiki/Selections 中提到子选择,但我对语言不够熟悉,无法检验该假设。

从概念层面来看,这三个对象( divpimg )更像是一个组而不是单独的实体,如果代码也能反射(reflect)这一点就好了。

最佳答案

您不能在一个链接命令中添加多个子元素。您需要将父选择保存在变量中。这应该做你想做的:

var data = [{ "label": "chocolate", "text": "Chocolate Cookie", "img": "chocolate.jpg" },
        { "label": "sugar", "text": "Sugar Cookie", "img": "sugar.jpg" }];

var diventer = d3.select("body").selectAll("div")
    .data(data)
  .enter().append("div")
    .attr("id", function(d) { return d.label; });

diventer.append("p")
    .text(function(d) { return d.text; });

diventer.append("img")
    .attr("src", function(d) { return d.img; });​

参见工作 fiddle :http://jsfiddle.net/UNjuP/

您想知道像 pimg 这样的子元素如何访问绑定(bind)到其父元素的数据。附加新元素时,数据会自动从父元素继承。这意味着 p 和 img 元素将与父 div 绑定(bind)相同的数据。

这种数据传播对于append 方法来说并不是唯一的。它发生在以下 selection 方法中:append , insert , 和 select .

例如,对于selection.append:

selection.append(name)

Appends a new element with the specified name as the last child of each element in the current selection. Returns a new selection containing the appended elements. Each new element inherits the data of the current elements, if any, in the same manner as select for subselections. The name must be specified as a constant, though in the future we might allow appending of existing elements or a function to generate the name dynamically.

如果有什么不清楚的地方,请随时询问细节。


编辑

您可以添加多个子元素,而无需使用 selection.each 方法将选择存储在变量中。然后,您还可以直接从父级访问数据:

var data = [{ "label": "chocolate", "text": "Chocolate Cookie", "img": "chocolate.jpg" },
        { "label": "sugar", "text": "Sugar Cookie", "img": "sugar.jpg" }];

d3.select("body").selectAll("div")
    .data(data)
  .enter().append("div")
    .attr("id", function(d) { return d.label; })
    .each(function(d) {
        d3.select(this).append("p")
          .text(d.text);
        d3.select(this).append("img")
          .attr("src", d.img);
    });

关于javascript - D3、嵌套追加和数据流,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13203897/

相关文章:

javascript - HTML 元素的属性列表

javascript - 如何将 D3 sunburst 序列分区更新到 v4?

javascript - 为什么我的 D3 热图上的颜色分布不同?

javascript - 分离节点并避免 d3.js 中树形图中的重叠

javascript - 获取所有刻度值 (NVD3)

javascript - 内联 CSS 样式未渲染 [以前为 : Component is not rendering its elements - react]

javascript - 为什么es6 Set原型(prototype)有values方法?

javascript - 使用JQuery修改某个ID的HTML元素

javascript - Zurb Foundation 6 jQuery 错误

javascript - npm install 后我收到错误 : Prototype Pollution in set-value