Let's Make a Bar Chart

选择一个元素

在d3中, 一般使用d3.select选择单个元素. 或者d3.selectAll选择匹配的所有元素.

const body = d3.select('body');
const div = body.append('div');
div.html('Hello world!');

const section = d3.selectAll('section');
const div = section.append('div');
div.html('Hello, world!');

链式方法

类似jQuery, 支持链式写法.

d3.select('body').append('div').html('Hello, world!');

SVG简介

SVG中的<g>元素用来组合对象的容器. 添加到g元素上的变换会应用到其所有的子元素上.
translate(x, y)用来移动对象, x/y分别对应坐标x/y轴.
rect绘制矩形, 需要提供width和height.
text绘制文本, 需要提供x/y坐标位置.

绘制柱状图

整体效果如下:


image.png

这里由四部分组成:

  • 柱状图部分(使用rect进行绘制)
  • 显示柱状图的值部分(使用text进行绘制)
  • x轴部分(使用d3.axisBottom进行绘制)
  • y轴部分(使用d3.axisLeft进行绘制)

柱状图部分

    d3.select('.chart').attr('width', width + 50).attr('height', height + 50)
      .selectAll('rect').data(data)
      .enter().append('rect')
      .attrs({ x: (d, i) => x(i), y: d => y(d), width: barWidth, height: d => height - y(d) })
      .style('fill', 'green');

这里先selectAll所有的rect(还未创建), 赋值其data, 然后通过enter后append(创建)多个rect. 通过设置其属性x, y, width, height进行rect的绘制.
这里x(i), y(i)中的x, y分别为函数, 是从domain向range的转换.

文本部分

    d3.select('.chart').selectAll('text').data(data)
      .enter().append('text')
      .attrs({ x: (d, i) => x(i) + 10, y: d => y(d) })
      .text(d => d)

这里只需要简单的设置文本的x,y和text即可.

x/y坐标轴代码

    const y = d3.scaleLinear().domain([0, d3.max(data)]).range([height, 0]);
    const x = d3.scaleBand().domain(d3.range(20)).range([0, width]);

    const gx = d3.select('.chart').append('g').attr('transform', `translate(0,${height})`);
    const xAxis = d3.axisBottom(x);

    const gy = d3.select('.chart').append('g').attr('transform', `translate(0,0)`);
    const yAxis = d3.axisLeft(y);

    gx.call(xAxis);
    gy.call(yAxis);
  • domain向range的转换: domain通常为实际数据的值, 例如区间为0~20, 而range为实际绘图区域的区间, 例如0~960px, 则设置后, 输入20定位到像素960px.
  • d3.axisBottom为d3封装的x轴坐标, d3.axisLeft为d3封装的y轴左侧坐标.

源码

https://github.com/leicj/d3/blob/master/src/components/bar.js

©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 219,869评论 6 508
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 93,716评论 3 396
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 166,223评论 0 357
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 59,047评论 1 295
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 68,089评论 6 395
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 51,839评论 1 308
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 40,516评论 3 420
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 39,410评论 0 276
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 45,920评论 1 319
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 38,052评论 3 340
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 40,179评论 1 352
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 35,868评论 5 346
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 41,522评论 3 331
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 32,070评论 0 22
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 33,186评论 1 272
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 48,487评论 3 375
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 45,162评论 2 356

推荐阅读更多精彩内容