D3.js学习(五)

上一节我们已经学习了如何设置填充区域,其实理解了他的实现原理还是非常简单了。这一节中, 我们主要学习多条曲线的绘制,以及给不同的曲线指定不同的纵坐标。

新的数据

由于我们要画两条曲线,所以我们要在原来的基础上新增一组测试数据,现在我们的数据是这样的:

date    close    open
1-May-12    58.13    3.41
30-Apr-12    53.98    4.55
27-Apr-12    67.00    6.78
26-Apr-12    89.70    7.85
25-Apr-12    99.00    8.92
24-Apr-12    130.28    9.92
23-Apr-12    166.70    10.13
20-Apr-12    234.98    12.23
19-Apr-12    345.44    13.45
18-Apr-12    443.34    16.04
17-Apr-12    543.70    18.03
16-Apr-12    580.13    21.02
13-Apr-12    605.23    22.34
12-Apr-12    622.77    20.15
11-Apr-12    626.20    21.26
10-Apr-12    628.44    31.04
9-Apr-12    636.23    35.04
5-Apr-12    633.68    41.02
4-Apr-12    624.31    43.05
3-Apr-12    629.32    46.03
2-Apr-12    618.63    51.03
30-Mar-12    599.55    53.42
29-Mar-12    609.86    57.82
28-Mar-12    617.62    59.01
27-Mar-12    614.48    56.03
26-Mar-12    606.98    58.01

我们把data-close作为一个数据集,把data-open作为一个数据集。现在我们把这些数据存在文件data2.tsv中,并将文件导入:

//Get the data
  d3.tsv("../data/data2.tsv", function(error, data){
    data.forEach(function(d){
      d.date = parseDate(d.date);
      d.close = +d.close;
      d.open = +d.open;
    });

.csharpcode,.csharpcode pre { font-size: small; color: black; font-family: consolas, "Courier New", courier, monospace; background-color: #ffffff }
.csharpcode pre { margin: 0em }
.csharpcode .rem { color: #008000 }
.csharpcode .kwrd { color: #0000ff }
.csharpcode .str { color: #006080 }
.csharpcode .op { color: #0000c0 }
.csharpcode .preproc { color: #cc6633 }
.csharpcode .asp { background-color: #ffff00 }
.csharpcode .html { color: #800000 }
.csharpcode .attr { color: #ff0000 }
.csharpcode .alt { background-color: #f4f4f4; width: 100%; margin: 0em }
.csharpcode .lnum { color: #606060 }

在这里需要注意的是,记得要做一个数据的转换,确保d.open中存储的是一个数字!

定义新的曲线

像前面定义曲线一样,我们定义第二天曲线的时候完全可以按照定义第一条曲线的方法进行定义:

//定义线条2
  var valueline2 = d3.svg.line()
    .interpolate("basis")
    .x(function(d){ return x(d.date) })
    .y(function(d){ return y(d.open) });

.csharpcode,.csharpcode pre { font-size: small; color: black; font-family: consolas, "Courier New", courier, monospace; background-color: #ffffff }
.csharpcode pre { margin: 0em }
.csharpcode .rem { color: #008000 }
.csharpcode .kwrd { color: #0000ff }
.csharpcode .str { color: #006080 }
.csharpcode .op { color: #0000c0 }
.csharpcode .preproc { color: #cc6633 }
.csharpcode .asp { background-color: #ffff00 }
.csharpcode .html { color: #800000 }
.csharpcode .attr { color: #ff0000 }
.csharpcode .alt { background-color: #f4f4f4; width: 100%; margin: 0em }
.csharpcode .lnum { color: #606060 }

绘制新的曲线

为了区别于第一条曲线,我们给新的曲线添加一个样式,把它变成抢眼的红色:

//绘制线条2
    svg.append("path")
      .attr("class", "line")
      .style("stroke", "red")
      .attr("d", valueline2(data));

.csharpcode,.csharpcode pre { font-size: small; color: black; font-family: consolas, "Courier New", courier, monospace; background-color: #ffffff }
.csharpcode pre { margin: 0em }
.csharpcode .rem { color: #008000 }
.csharpcode .kwrd { color: #0000ff }
.csharpcode .str { color: #006080 }
.csharpcode .op { color: #0000c0 }
.csharpcode .preproc { color: #cc6633 }
.csharpcode .asp { background-color: #ffff00 }
.csharpcode .html { color: #800000 }
.csharpcode .attr { color: #ff0000 }
.csharpcode .alt { background-color: #f4f4f4; width: 100%; margin: 0em }
.csharpcode .lnum { color: #606060 }

这样,我们的曲线就绘制成功啦,效果如下:

改进

虽然我们已经把图形绘制出来,但是,我们的代码还是不完善的,比方说,如果我的d.open有个值非常非常大,他比d.close中的任何一个值都要大很多,那么我们图形绘制出来会变成什么效果呢?

红色线条是不是跑到画布外面去了!也就是说我们的画布已经无法容纳这个最大的d.open值了,因为我们之前设置y轴的规模(domain)时用的是d.close的最大值:

 y.domain([0, d3.max(data, function(d){
      return d.close;
    })]);

.csharpcode,.csharpcode pre { font-size: small; color: black; font-family: consolas, "Courier New", courier, monospace; background-color: #ffffff }
.csharpcode pre { margin: 0em }
.csharpcode .rem { color: #008000 }
.csharpcode .kwrd { color: #0000ff }
.csharpcode .str { color: #006080 }
.csharpcode .op { color: #0000c0 }
.csharpcode .preproc { color: #cc6633 }
.csharpcode .asp { background-color: #ffff00 }
.csharpcode .html { color: #800000 }
.csharpcode .attr { color: #ff0000 }
.csharpcode .alt { background-color: #f4f4f4; width: 100%; margin: 0em }
.csharpcode .lnum { color: #606060 }

所以,我们要对它进行一个改进,我们要取两组值中的最大值:

y.domain([0, d3.max(data, function(d){
      return Math.max(d.close, d.open);
    })]);

这样,我们就解决了图像超出画布的问题了,不过我们的数据怎么变化,都是适应的:

.csharpcode,.csharpcode pre { font-size: small; color: black; font-family: consolas, "Courier New", courier, monospace; background-color: #ffffff }
.csharpcode pre { margin: 0em }
.csharpcode .rem { color: #008000 }
.csharpcode .kwrd { color: #0000ff }
.csharpcode .str { color: #006080 }
.csharpcode .op { color: #0000c0 }
.csharpcode .preproc { color: #cc6633 }
.csharpcode .asp { background-color: #ffff00 }
.csharpcode .html { color: #800000 }
.csharpcode .attr { color: #ff0000 }
.csharpcode .alt { background-color: #f4f4f4; width: 100%; margin: 0em }
.csharpcode .lnum { color: #606060 }

两条纵坐标轴

仔细观察原来的数据,我们会发现,d.open的值相对于d.close的取发展趋势更加平稳。但是,如果我们要更好的体现它的细节(也就是把趋势放大)的话改怎么做呢?很简单,给他们设置不同的坐标轴!

//定义坐标轴的范围
 
  var x = d3.time.scale().range([0, width]);
  var y = d3.scale.linear().range([height, 0]);
  var y2 = d3.scale.linear().range([height, 0]);

.csharpcode,.csharpcode pre { font-size: small; color: black; font-family: consolas, "Courier New", courier, monospace; background-color: #ffffff }
.csharpcode pre { margin: 0em }
.csharpcode .rem { color: #008000 }
.csharpcode .kwrd { color: #0000ff }
.csharpcode .str { color: #006080 }
.csharpcode .op { color: #0000c0 }
.csharpcode .preproc { color: #cc6633 }
.csharpcode .asp { background-color: #ffff00 }
.csharpcode .html { color: #800000 }
.csharpcode .attr { color: #ff0000 }
.csharpcode .alt { background-color: #f4f4f4; width: 100%; margin: 0em }
.csharpcode .lnum { color: #606060 }

y跟y2的范围(也就是像素高)应该是一样的。我们把y2的tick标签放在右边,这样看起来会更对称:

//定义坐标轴
  var xAxis = d3.svg.axis().scale(x).orient("bottom").ticks(5);
  var yAxis = d3.svg.axis().scale(y).orient("left").ticks(5);
  var y2Axis = d3.svg.axis().scale(y2).orient("right").ticks(5);

.csharpcode,.csharpcode pre { font-size: small; color: black; font-family: consolas, "Courier New", courier, monospace; background-color: #ffffff }
.csharpcode pre { margin: 0em }
.csharpcode .rem { color: #008000 }
.csharpcode .kwrd { color: #0000ff }
.csharpcode .str { color: #006080 }
.csharpcode .op { color: #0000c0 }
.csharpcode .preproc { color: #cc6633 }
.csharpcode .asp { background-color: #ffff00 }
.csharpcode .html { color: #800000 }
.csharpcode .attr { color: #ff0000 }
.csharpcode .alt { background-color: #f4f4f4; width: 100%; margin: 0em }
.csharpcode .lnum { color: #606060 }
.csharpcode,.csharpcode pre { font-size: small; color: black; font-family: consolas, "Courier New", courier, monospace; background-color: #ffffff }
.csharpcode pre { margin: 0em }
.csharpcode .rem { color: #008000 }
.csharpcode .kwrd { color: #0000ff }
.csharpcode .str { color: #006080 }
.csharpcode .op { color: #0000c0 }
.csharpcode .preproc { color: #cc6633 }
.csharpcode .asp { background-color: #ffff00 }
.csharpcode .html { color: #800000 }
.csharpcode .attr { color: #ff0000 }
.csharpcode .alt { background-color: #f4f4f4; width: 100%; margin: 0em }
.csharpcode .lnum { color: #606060 }

现在,我们还需要修改一下我们的valueline,让valueline2使用y2作为纵轴方向的基准:

//定义线条1
  var valueline = d3.svg.line()
    .interpolate("basis")
    .x(function(d){return x(d.date);})
    .y(function(d){return y(d.close);});
  //定义线条2
  var valueline2 = d3.svg.line()
    .interpolate("basis")
    .x(function(d){ return x(d.date) })
    .y(function(d){ return y2(d.open) });

.csharpcode,.csharpcode pre { font-size: small; color: black; font-family: consolas, "Courier New", courier, monospace; background-color: #ffffff }
.csharpcode pre { margin: 0em }
.csharpcode .rem { color: #008000 }
.csharpcode .kwrd { color: #0000ff }
.csharpcode .str { color: #006080 }
.csharpcode .op { color: #0000c0 }
.csharpcode .preproc { color: #cc6633 }
.csharpcode .asp { background-color: #ffff00 }
.csharpcode .html { color: #800000 }
.csharpcode .attr { color: #ff0000 }
.csharpcode .alt { background-color: #f4f4f4; width: 100%; margin: 0em }
.csharpcode .lnum { color: #606060 }

同时,我们还要给他们设置不同的规模:

//Scale(规模) the range of the data
    x.domain(d3.extent(data, function(d){
      return d.date;
    }));
    y.domain([0, d3.max(data, function(d){
      return d.close;
    })]);
    y2.domain([0, d3.max(data, function(d){
      return d.open;
    })]);

.csharpcode,.csharpcode pre { font-size: small; color: black; font-family: consolas, "Courier New", courier, monospace; background-color: #ffffff }
.csharpcode pre { margin: 0em }
.csharpcode .rem { color: #008000 }
.csharpcode .kwrd { color: #0000ff }
.csharpcode .str { color: #006080 }
.csharpcode .op { color: #0000c0 }
.csharpcode .preproc { color: #cc6633 }
.csharpcode .asp { background-color: #ffff00 }
.csharpcode .html { color: #800000 }
.csharpcode .attr { color: #ff0000 }
.csharpcode .alt { background-color: #f4f4f4; width: 100%; margin: 0em }
.csharpcode .lnum { color: #606060 }

最后,我们再来绘制它们!

//绘制x坐标轴
svg.append("g")
  .attr("class", "x axis")
  .attr("transform", "translate(0," + height + ")")
  .call(xAxis);
//绘制y坐标轴
svg.append("g")
  .attr("class", "y axis")
  .call(yAxis);
//绘制y2坐标轴
svg.append("g")
  .attr("class", "y axis")
  .attr("transform", "translate(" + width + ", 0)")
  .style("fill", "red")
  .call(y2Axis);

.csharpcode,.csharpcode pre { font-size: small; color: black; font-family: consolas, "Courier New", courier, monospace; background-color: #ffffff }
.csharpcode pre { margin: 0em }
.csharpcode .rem { color: #008000 }
.csharpcode .kwrd { color: #0000ff }
.csharpcode .str { color: #006080 }
.csharpcode .op { color: #0000c0 }
.csharpcode .preproc { color: #cc6633 }
.csharpcode .asp { background-color: #ffff00 }
.csharpcode .html { color: #800000 }
.csharpcode .attr { color: #ff0000 }
.csharpcode .alt { background-color: #f4f4f4; width: 100%; margin: 0em }
.csharpcode .lnum { color: #606060 }

最后的效果如下:

下一节,我们将学习如何x轴的tick标签很多的情况下,如何旋转标签,使他们更便于阅读!

原文地址:https://www.cnblogs.com/magic-xxj/p/9186347.html

时间: 2024-08-02 13:25:51

D3.js学习(五)的相关文章

d3.js学习11

单元素动画transition().duration(duration) var body = d3.select("body"), duration = 5000; body.append("div") .classed("box",true) .style("background-color","#e9967a") .transition() .duration(duration) .style(&qu

d3.js学习笔记(1)

很早之前就知道d3,当初看到它的时候,第一反应就是"我去,怎么这么炫酷",但是一直没有学(自己太懒了),最近可能是五月病犯了,不想看书,不想写代码,不想看论文,不想写论文,虽然什么事情都不想做,不过还是找点事情做吧,那就学学d3呗,说不定将来什么时候就用到了呢. 这篇博客主要从源码的角度去学习,所以对于没有接触过d3的朋友,请先看完下面的资料. 学习资料 学习嘛,当然得找到好的资料咯,下面是我昨天看的一些文章,在d3的github上都能够找到,毕竟最好的学习资料就是官网的文档.教程和源

d3.js学习9

d3.js数据可视化实战手册 学习笔记 插值器Interpolation 给定值域,往中间填值并打印出来 字符插值 var data=[]; var sizeScale=d3.scale.linear() .domain([0,9]) .range([ "italic bold 12px/30px Georgia, serif", "italic bold 120px/180px Georgia, serif" ]); for(var i=0;i<10;i++

d3.js学习

画svg图像 1.添加svg元素 2.添加g元素,g元素是一个分组的元素,相当于html中的div元素 3.画图像 4.画坐标轴 ----------------------------------------------------------------------------- d3画闲线性曲线例子 html: <!DOCTYPE html><html lang="en"><head> <meta charset="UTF-8&

d3.js学习1

官网: http://d3js.org/ 范例: https://github.com/mbostock/d3/wiki/Gallery 引用: //在线引用 <script src="http://d3js.org/d3.v3.min.js" charset="utf-8"></script> //或下载到本地 <head> <meta charset="utf-8"> <title>

d3.js学习笔记

入门好文:http://www.ourd3js.com/wordpress/?p=51 d3.js和d3.min.js内容一样,后者是压缩过的,适合发行版本,前者适合开发人员. 1.选择集(满足css选择符的要求)主要和数据绑定一起使用 d3.select() d3.selectAll() var body = d3.select("body") 2.数据绑定(实质就是在选择集的元素对象里面添加一个变量,并赋值) p.text(function(d,i)){return d+"

d3.js学习3

Enter-update-exit模式 select.data(data),代表selection图形与data数据的交集->Update Mode select.data(data).enter(),代表data数据排除selection图形与data数据的交集->Enter Mode select.exit,移除所有数据,代表selection图形的部分->Exit Mode E-U-E即为d3.js的基础 数组数据绑定 var data=[10,15,24,46,13,6,96,1

D3.js学习记录

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en"> <head> <meta h

d3.js学习6

加载server数据d3.json(url,callback) 首先准备一些json数据,将上一篇的js数据转化为json格式并存储 var data=[ {expense:10,category:"Retail"}, {expense:15,category:"Gas"}, {expense:30,category:"Retail"}, {expense:50,category:"Dining"}, {expense:80,