【译】Learn D3 入门文档:Joins

2024-06-01 03:18
文章标签 文档 入门 learn d3 joins

本文主要是介绍【译】Learn D3 入门文档:Joins,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

引子

继 Learn D3: Animation 第七篇,只是英文翻译,可修改代码的部分用静态图片替代了,想要实时交互请阅读原文。

  • 原文:Learn D3: Joins

  • 版本:Published Mar 24, 2020

  • Origin

  • My GitHub

正文

如果你熟悉此教程中的 D3 ,你可能会惊讶于 D3 选择器被提及的如此之少。

那是因为你可能不需要它们!

D3 选择器适用一个特殊的定位:快速,动态图表的增量更新。如果你关注的是静态图表,或者每帧都可以从头开始重新绘制的图表,那么你可能更喜欢不同的抽象。另一方面,如果你想要动画过渡或从现代浏览器中榨取最佳性能,选择器适合你。

(即使你决定不使用选择器,请记住 D3 还有大量其它有用的可视化工具。比例尺、形状、插值器、颜色、地图投影和许多其它功能可用于 Canvas、WebGL 或其它 DOM 抽象,如 Observable 的 HTML 标记模板文字、React 或 Svelte 。D3 还可以使用统计、分组和聚合、时间序列和解析的方法,协助数据清理和分析。)

本质上,D3 选择器指定的是转换而不是表示。你可以指定将当前状态转换为所需状态所做的更改(插入、更新和删除),而不是表示图表(DOM)的所需状态。这有时很乏味,但允许你设置过渡动画,并最小化对 DOM 的更改,从而提高性能。

让我们看看如何做。

假设我们想显示字母表中的字母。虽然不是很直观,但我们将保持简单,以专注于技术(有关实际的示例,请参见 D3 图库 的动画和交互部分。)

92-1

这个图表是静态的,因为它是在每次单元运行时从头开始创建的,这使得 D3 代码在本质上等同于 HTML 文本。

92-2

那么,何必要用选择器呢?对,对于静态图表,没有什么理由这样做。

但假设你想更新此图表以响应不断变化的数据。并且你不想从头开始重新绘制,希望应用最小的更新集来反映新数据。你希望重用现有元素,添加需要的元素,删除不需要的元素。只需将上述代码移动到一个在数据更改时调用的方法中,你就可以获得高性能的增量更新!😲

92-3

让我们把代码分析一下。

text 是一组文本元素,最初为空,其父元素是 SVG 元素。这个父项决定了输入的文本元素稍后将附加到何处。

通过调用 selection.data ,text 被绑定到一个新的数据数组 letters 。这将计算 text 选择集的三个子集:enter 选择集表示在新数据中,去除已存在元素与新数据的交集之后,剩下的数据;update 选择集表示新数据与已存在元素的交集;exit 选择集表示在已存在元素中,去除已存在元素与新数据的交集之后,剩下的元素。

作为图示如下:

92-4

(这些选择集隐藏在代码中:selection.data 返回 update 选择集,从中可以调用 selection.enter 或 selection.exit 访问其它选择集。)

我们可以手动处理这三种情况,但 selection.join 本就能方便的处理。enter 选择集添加进来;exit 选择集被移除;最后, updateenter 选择集被合并、排序并返回。然后,我们可以为这些加入或更新元素分配属性和文本。

我们观察到只要字母和文本元素之间的关联保持不变,就不需要在更新元素时重新分配某些属性和文本内容,这样就可以更高效。要保留此关联,selection.data 需要一个键函数;为了对 enterupdateexit 的精确操作,selection.join 需要相应的函数。如果 update 比 enter 和 exit 更常见,这将大大提高性能!

92-5

与前面一样,selection.join 返回合并的 enter 和 update 选择集,因此我们可以共享应用于两者的代码,例如设置 x 属性。

传递给 selection.data 的键函数用于计算每个新数据和已选元素数据的(字符串)键,确定哪个数据绑定到哪个元素:如果元素和数据具有相同的键,则该数据绑定到元素,并且元素被放入 update 选择集。字母是很好的键,因此标识函数(d => d)在这里是合适的。

(如果未指定键函数,则数据由索引绑定:第一个数据绑定到第一个元素,依此类推。作为练习,尝试重写上面的代码以通过索引联接。你将会也想把设置 x 属性与设置文本内容交换!)

然而,选择器真正闪耀的地方是过渡!✨

在下面,字母从顶部进入,更新时水平滑动,然后从底部退出。这比上面的瞬时转变更容易理解。

92-6

好的过渡不仅仅是为了吸引注意力而让图表“舞动”;它们帮助观看者通过变动了解数据是如何变化的

良好的过渡保持对象的恒定性:在过渡之前表示特定事物(如字母 C )的图表元素应在整个过渡过程中和过渡之后表示相同的事物,从而允许观看者连续跟踪。相反,如果给定元素的含义在过渡期间发生变化,那么变动将毫无意义。

举个更实际的例子怎么样?

下图显示了按特定年龄组人口百分比排列的前十个州(以及华盛顿特区,外地居住者)。这表明犹他州的年轻人口比例过高,反映了 LDS 教会对养育家庭的重视。相比之下,佛罗里达州退休人口众多,许多人都在 70 岁或以上。

当你更改选定的年龄组时,请观察图表如何重新排序以反映排名的变化。x 轴同时重新缩放以适应新数据。

92-7

chart = {const svg = d3.create("svg").attr("viewBox", [0, 0, width, height]);console.info(data)// For the initial render, reference the current age non-reactively.const agedata = viewof agedata.value;const x = d3.scaleLinear().domain([0, d3.max(agedata, d => d.value)]).rangeRound([margin.left, width - margin.right]);const y = d3.scaleBand().domain(agedata.map(d => d.name)).rangeRound([margin.top, margin.top + 20 * data.names.length]);let bar = svg.append("g").attr("fill", "steelblue").selectAll("rect").data(agedata, d => d.name).join("rect").style("mix-blend-mode", "multiply").attr("x", x(0)).attr("y", d => y(d.name)).attr("width", d => x(d.value) - x(0)).attr("height", y.bandwidth() - 1);const gx = svg.append("g").call(xAxis, x);const gy = svg.append("g").call(yAxis, y);return Object.assign(svg.node(), {update(agedata) {const t = svg.transition().duration(750);gx.transition(t).call(xAxis, x.domain([0, d3.max(agedata, d => d.value)]));gy.transition(t).call(yAxis, y.domain(agedata.map(d => d.name)));bar = bar.data(agedata, d => d.name).call(bar => bar.transition(t).attr("width", d => x(d.value) - x(0)).attr("y", d => y(d.name)));}});
}

92-9

只有前 10 条可见,因为其余的隐藏在图表下方。因此,selection.join 是不需要的,因为没有条形加入或移除,它们只会更新。这不仅简化了代码,而且使过渡更有意义,因为进入或退出条形图的速度现在暗示它们在展示外的位置。

动画过渡通常由读者点击或在寻找答案时点击触发。接下来,让我们看看如何让图表响应此类查询。

Next

附录

92-10

根据源码,去除了平台依赖,提取了主要代码,有以下示例:

  • 示例 1
  • 示例 2

参考资料

  • Learn D3: Joins

这篇关于【译】Learn D3 入门文档:Joins的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/1019842

相关文章

C#实现将Office文档(Word/Excel/PDF/PPT)转为Markdown格式

《C#实现将Office文档(Word/Excel/PDF/PPT)转为Markdown格式》Markdown凭借简洁的语法、优良的可读性,以及对版本控制系统的高度兼容性,逐渐成为最受欢迎的文档格式... 目录为什么要将文档转换为 Markdown 格式使用工具将 Word 文档转换为 Markdown(.

详解如何使用Python构建从数据到文档的自动化工作流

《详解如何使用Python构建从数据到文档的自动化工作流》这篇文章将通过真实工作场景拆解,为大家展示如何用Python构建自动化工作流,让工具代替人力完成这些数字苦力活,感兴趣的小伙伴可以跟随小编一起... 目录一、Excel处理:从数据搬运工到智能分析师二、PDF处理:文档工厂的智能生产线三、邮件自动化:

Python实现自动化Word文档样式复制与内容生成

《Python实现自动化Word文档样式复制与内容生成》在办公自动化领域,高效处理Word文档的样式和内容复制是一个常见需求,本文将展示如何利用Python的python-docx库实现... 目录一、为什么需要自动化 Word 文档处理二、核心功能实现:样式与表格的深度复制1. 表格复制(含样式与内容)2

Python中OpenCV与Matplotlib的图像操作入门指南

《Python中OpenCV与Matplotlib的图像操作入门指南》:本文主要介绍Python中OpenCV与Matplotlib的图像操作指南,本文通过实例代码给大家介绍的非常详细,对大家的学... 目录一、环境准备二、图像的基本操作1. 图像读取、显示与保存 使用OpenCV操作2. 像素级操作3.

Maven项目中集成数据库文档生成工具的操作步骤

《Maven项目中集成数据库文档生成工具的操作步骤》在Maven项目中,可以通过集成数据库文档生成工具来自动生成数据库文档,本文为大家整理了使用screw-maven-plugin(推荐)的完... 目录1. 添加插件配置到 pom.XML2. 配置数据库信息3. 执行生成命令4. 高级配置选项5. 注意事

Python使用python-docx实现自动化处理Word文档

《Python使用python-docx实现自动化处理Word文档》这篇文章主要为大家展示了Python如何通过代码实现段落样式复制,HTML表格转Word表格以及动态生成可定制化模板的功能,感兴趣的... 目录一、引言二、核心功能模块解析1. 段落样式与图片复制2. html表格转Word表格3. 模板生

浅谈Redis Key 命名规范文档

《浅谈RedisKey命名规范文档》本文介绍了Redis键名命名规范,包括命名格式、具体规范、数据类型扩展命名、时间敏感型键名、规范总结以及实际应用示例,感兴趣的可以了解一下... 目录1. 命名格式格式模板:示例:2. 具体规范2.1 小写命名2.2 使用冒号分隔层级2.3 标识符命名3. 数据类型扩展命

POI从入门到实战轻松完成EasyExcel使用及Excel导入导出功能

《POI从入门到实战轻松完成EasyExcel使用及Excel导入导出功能》ApachePOI是一个流行的Java库,用于处理MicrosoftOffice格式文件,提供丰富API来创建、读取和修改O... 目录前言:Apache POIEasyPoiEasyExcel一、EasyExcel1.1、核心特性

Python中模块graphviz使用入门

《Python中模块graphviz使用入门》graphviz是一个用于创建和操作图形的Python库,本文主要介绍了Python中模块graphviz使用入门,具有一定的参考价值,感兴趣的可以了解一... 目录1.安装2. 基本用法2.1 输出图像格式2.2 图像style设置2.3 属性2.4 子图和聚

使用Python从PPT文档中提取图片和图片信息(如坐标、宽度和高度等)

《使用Python从PPT文档中提取图片和图片信息(如坐标、宽度和高度等)》PPT是一种高效的信息展示工具,广泛应用于教育、商务和设计等多个领域,PPT文档中常常包含丰富的图片内容,这些图片不仅提升了... 目录一、引言二、环境与工具三、python 提取PPT背景图片3.1 提取幻灯片背景图片3.2 提取