博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
D3.js使用过程中的常见问题(D3版本D3V4)
阅读量:5146 次
发布时间:2019-06-13

本文共 7500 字,大约阅读时间需要 25 分钟。

目录

前言

        上一回合写到《》代码中D3结合了react全家桶来写可能有点副格略高。在这里回归原点,整理好D3使用过程中或者学习过程中遇到过的常见问题。这里主要是新手专区,把新手入门D3时常见的问题记录下来,D3高手不喜勿喷,当然也延续了自己的习惯,持续更新,把常见的问题记录下来好处就是平时可以当自己的Q&A顺手拿来使用,毕竟人的大脑有限。

       

一、学习D3我必须要学习好SVG矢量图码?

我觉得得SVG适量图是必须的,为什么要学习SVG图呢?因为D3.js堪称SVG中的jQuery,稍稍熟悉点jQuery的话,会更容易上手D3,当然你如果想用D3输出Canvas图或者你牛逼哄哄的说老子就只用D3来玩Canvas怎么嘀也可以,但SVG图操作起来更加灵活,更加方便调试,在Chrome中调试SVG图更加直观。D3只是一个作图工具,你完全也可以手写SVG的XML代码来完成作图,如下面是一个手画简单柱状图:

4
8
15
16
23
42
View Code

 

二、如何理解D3给Dom节点绑定数据时的Update、Enter和Exit模式

代码如下:

// Update…var p4 = d3.select("#my_p_4")  .selectAll("p") // 选择所有的P元素  .data([4, 8, 15, 16, 23, 40]) // 给所有的P元素相应绑定数据(当然P元素有可能与数组元素个数不相等,则要转入下面的Enter和exit操作)  .text(function (d) { return d; }); // 改变所有的P元素的text为相应的数组的值p4.enter().append("p") // 如果原有P节点元素小于数组的元素个数,则要给父节点append节点补足    .text(function (d) { return d; });// Exit…p4.exit().remove(); // 如果原有P节点元素大于数组的元素个数,则要执行删除操作,以保证p节点元素个数与传入的data数组元素个数相当

 

三、D3绑定数据时用datum与data有什么不一样?

用data是给所有的节点去绑定对应的data里面的数组元素值并一一匹配,而使用datum是给所有的节点绑定一样的数据值。

 

四、SVG图中用attr来设置属性和用style来设置样式时,用style来设置样式的权重会更高

style设置权重其实比用css样式表来设置更高,代码如下:

d3.select("#my_chart_2 rect").style("width", 20) // 同样设宽度用style生效.attr("width", 40); // 同样设宽度用attr权重没style高,会失效

 

五、D3使用链式写法时,写完transition动画后不能链着继续写append添加元素操作

一般可以这么操作,先定义变量暂存节点再单独写动画或者单独写append追加元素操作,代码如下:

var g = chart.append("g")        .style('fill-opacity', 0);          .transition()        .duration(1000)        .style('fill-opacity', 1); // 动画渐现          /*g.selectAll("rect") // 绘画所有的矩形            .data(data)            .enter()            .append("path")...        */

 

六、如何给path设置缓动?

如画饼图时,想加上缓动动画,代码如下:

let arc = d3.arc() // 定义单个圆弧            .innerRadius(0)            .padAngle(0);
let pie = d3.pie() // 定义饼图            .sort(null)            .value(function (d) { return d.population; });
g.selectAll(".arc") // 画环图            .data(pie(data))            .enter().append("path")                .attr("cursor", "pointer")            .attr("class", "arc")            .attr('stroke', function (d) { return colors(d.data.age); })            .style("fill", function (d) { return colors(d.data.age); })            .each(function(d) { // 储存当前起始与终点的角度、并设为相等                let tem = {...d, endAngle: d.startAngle};                d.outerRadius = radius - 10;                this._currentData = tem;             })            .transition()            .duration(100)            .delay(function (d, i) { return i * 100; })            .attrTween("d", function(next) { // 动态设置d属性、生成缓动画              var i = d3.interpolate(this._currentData, next);              this._currentData = i(0); // 重设当前角度              return function(t) {                return arc(i(t));              };            });

或者单独定义好缓动函数,代码如下:

g.selectAll(".arc") // 画环图            .data(pie(data))            .enter().append("path")            .each(function(d) { // 储存当前起始与终点的角度、并设为相等                let tem = {...d, endAngle: d.startAngle};                d.outerRadius = radius - 10;                this._currentData = tem;             })            .on("mouseover", arcTween(radius + 50, 0))        .on("mouseout", arcTween(radius - 10, 150))            .attr("cursor", "pointer")            .attr("class", "arc")            .style("fill", function (d) { return colors(d.data.age); })            .transition()            .duration(750)            .attrTween("d", function(next) { // 动态设置d属性、生成动画              var i = d3.interpolate(this._currentData, next);              this._currentData = i(0); // 重设当前角度              return function(t) {                return arc(i(t));              };            });               function arcTween(outerRadius, delay) { // 设置缓动函数          return function() {            d3.select(this).transition().delay(delay).attrTween("d", function(d) {              var i = d3.interpolate(d.outerRadius, outerRadius);              return function(t) { d.outerRadius = i(t); return arc(d); };            });          };        }

 

七、D3普通的缓动动画

如果想要给柱图添加每条柱由左到右按顺序缓动弹出,代码如下:

g.selectAll(".bar")// 画柱图            .data(data)            .enter().append("rect")            .attr("x", function (d) { return x(d.letter); })            .attr("y", height) // 控制动画由下而上            .attr("width", x.bandwidth())            .attr("height", 0) // 控制动画由下而上            .transition()            .duration(200)            .ease(d3.easeBounceInOut) // 这里还有d3.easeLinear、d3.easeCubicOut等等多种效果,可自行查看API             .delay(function (d, i) { return i * 200; })            .attr("y", function (d) { return y(d.frequency); })            .attr("height", function (d) { return height - y(d.frequency); });

 

八、给节点添加title,鼠标mouseover显示普通提示文本效果

当需要hover提示文本效果时,可以添加title,或者如果想要更加丰富的自定义效果可以使用开源的d3插件d3-tip,也可以自己写一个hover效果,实现起来的思想就是on('mouseover',callback)方式,代码如下:

g.append("g")//            .selectAll('rect')            .data(data)            .enter()            .append('rect')             //...            .append('title') // 在后面添加title            .text(function(d) { return d.name; });

 

九、getBBox按长方形获取节点的大小、长宽及坐标等等信息

在应用场景中,我们经常也会遇到要获得某元素的长宽等信息,实现代码如下:

label.insert("rect", "text") // 生成背景白块            .datum(function () { return this.nextSibling.getBBox(); }) // 这里在text前插入一个rect,并按照text的属性来设置长宽及坐标            .attr('fill', '#fff')             .attr("x", function (d) { return d.x; })            .attr("y", function (d) { return d.y; })            .attr("width", function (d) { return d.width; })            .attr("height", function (d) { return d.height; });

 

十、使用遮罩制作动画

当你实现不想花那么多时间去在作图时实现动画,可以考虑在SVG遮罩里面加动画来实现同样的效果,代码如下:

chart.append("defs").append("clipPath") // 添加长方形方块,遮罩作用            .attr("id", "clip")           .append("rect")            .attr("height", height)            .attr("width", 0) // 用遮罩实现线动画            .transition()            .duration(1000)                       .attr("width", width);        let serie = g.selectAll(".serie") // 生成两线条            .data(series)            .enter().append("g")              .attr("class", "serie");        serie.append("path") // 绘画线条            .attr('clip-path', 'url(#clip)')                     .attr("class", "line")            .style("stroke", function (d) { return z(d[0].key); })            .attr('fill', 'none')            .attr("d", line);

 

十一、D3常用的SVG元素类型有哪些?

circle, line, rect, path, svg, g, defs, clipPath, text, title

 

十二、D3对svg元素设置位置一般有两种方式,使用坐标x、y或者使用transform来设置。

一般来说,是两者配合使用,transform后再设置x, y坐标或者再结合dx, dy位置来设置节点的位置。

 

十三、数据可视化(不限D3)于要了解的一些基础概念

x轴, y轴, tick, legend, serie, brush, zoom, 散点, 线状图, 面积图, 柱状图, 饼图, 打包图, 弦图, 打包图, 雷达图, 力向导图, 树状图, 堆栈图, 组合线状/组合柱状图, 标签云图, geomap地图等

对应到D3API中必备的知识:d3-selection(D3 选择器)  d3-shape(D3 作图图形图)  d3-transition(D3 过渡动画)  d3-axis(D3 坐标)  d3-scale(D3 比例尺生成工具)

 

十四、笛卡尔坐标绘图适合制作普通线状、柱状等图;极坐标绘图适合制作螺旋形图表

如笛卡尔坐标画线会用到普通的d3.line,而极坐标画线会用到d3.lineRadial。

 

交流与学习

  1. 本文作者  欢迎大家留言及多多指教
  2. 版权声明:欢迎转载学习 => 请标注信息来源于

 

转载于:https://www.cnblogs.com/fastmover/p/7794519.html

你可能感兴趣的文章
【转】清空mysql一个库中的所有表的数据
查看>>
基于wxPython的python代码统计工具
查看>>
淘宝JAVA中间件Diamond详解(一)---简介&快速使用
查看>>
一种简单的数据库性能测试方法
查看>>
如何给JavaScript文件传递参数
查看>>
Hadoop HBase概念学习系列之物理视图(又名为物理模型)(九)
查看>>
Hadoop HBase概念学习系列之HBase里的宽表设计概念(表设计)(二十七)
查看>>
Kettle学习系列之Kettle能做什么?(三)
查看>>
ExtJS 4.2 业务开发(一)主页搭建
查看>>
webpack Import 动态文件
查看>>
电脑没有安装iis,但是安装了.NET环境,如何调试网站发布的程序
查看>>
【Mac + GitHub】之在另一台Mac电脑上下载GitHub的SSH链接报错
查看>>
Day03:Selenium,BeautifulSoup4
查看>>
Java NIO系列教程(九) ServerSocketChannel
查看>>
awk变量
查看>>
mysql_对于DQL 的简单举例
查看>>
postgis几何操作函数集
查看>>
ACM题目————还是畅通工程
查看>>
CentOS7使用firewalld打开关闭防火墙与端口
查看>>
35. Search Insert Position(C++)
查看>>