亲宝软件园·资讯

展开

D3.js入门之比例尺的使用与绘制

FinGet 人气:0

中国这么大,要在一张小小地图上画上中国,那么就需要按一定的比例缩小。D3 可视化画图,也是如此,例如:一个柱状图的最大值为10000,但是画布最大高度只有400,那么10000就只能被映射为400,那么8000、5000...又该映射成哪个值呢?

比例尺

D3中的比例尺大概有20多种(d3.scaleLineard3.scalePowd3.scaleTimed3.scaleBand等)。大体上可以分为三类:

常用比例尺

scaleLinear 线性比例尺

const scale = d3.scaleLinear() // 连续输入和连续输出
.domain([0, 500]) // 输入域 0 ~ 500
.range([0, 300]); // 输出域 0 ~ 300

console.log(scale(100)) // 60
console.log(scale(300)) // 180
console.log(scale(500)) // 300

scaleBand 有序序数比例尺

scaleBand:有助于创建条形图,同时考虑每个条形之间的间隔。域被指定为一组值(每个波段一个值),范围为波段的最小和最大范围(例如条形图的总宽度)。

实际上scaleBand会将范围拆分为n 个带区(其中n是域数组中的值的数量),并考虑在指定间隔的情况下计算条形图的位置和宽度。

const scale = d3.scaleBand()
  .domain([1,2,3,4])
  .range([0,100])

console.log(scale(1)) // 0
console.log(scale(3)) // 50
console.log(scale(4)) // 75

console.log(scale.bandwidth()) // 25 (100 分为4份,每份25(柱状图宽度))

d3.scaleTime() 时间比例尺

d3.scaleTime()类似于d3.scaleLinear()线性比例尺,只不过输入域变成了一个时间轴。

const scale = d3.scaleTime()
  .domain([new Date(2022, 0, 1), new Date(2022, 0, 31)])
  .range([0, 30])

console.log(scale3(new Date(2022, 0, 15))) // 14

scaleOrdinal 无序序数比例尺

const scale = d3.scaleOrdinal() // 离散输入和离散输出
  .domain(['jack', 'rose', 'john', 'lucy'])
  .range([10, 20, 30])
console.log(scale("jack")); // 10
console.log(scale("lucy")); // 10
console.log(scale("rose")); // 20
console.log(scale("john")); // 30

console.log(scale("finget")) // 20 输入域以外的值

const scale = d3.scaleOrdinal()
  .domain(['jack', 'rose', 'john', 'lucy'])
  .range([10, 20, 30])
  .unknown(23) // 指定未知输入域的输出值
console.log(scale("finget"))  // 23

如果输入域大于输出域,domain()的值按照顺序循环依次对应range()的值

scalePoint 点比例尺

// 创建从一组离散值映射到指定范围内等距的点
const scale = d3.scalePoint() // 离散输入和离散输出
  .domain(['jack', 'rose', 'john']) 
  .range([0, 100])
console.log(scale4('jack')) // 0
console.log(scale4('rose')) // 50
console.log(scale4('john')) // 100

console.log(scale4.step()) // 访问点之间的距离 50

scaleThreshold 阈值比例尺

// scaleThreshold 将连续数值输入映射到范围定义的离散值
let scaleThreshold = d3.scaleThreshold() // 连续输入和离散输出
  .domain([0, 10, 20])
  .range(['small', 'medium', 'large', 'xlarge'])
console.log(scaleThreshold(5)) // medium
console.log(scaleThreshold(15)) // large
console.log(scaleThreshold(25)) // xlarge
console.log(scaleThreshold(35)) // xlarge
console.log(scaleThreshold(45)) // xxlarge

如果指定了 domain 则将比例尺的输入范围设置为指定的数组。数组必须是升序排序的。值通常是数值,也可以是能进行排序的其他类型。如果输出域的值个数为 N + 1, 则输入域中值的个数必须为 N. 如果比 N 少则对应的输出域中多余的值会被忽略。如果多于 N 则会出现返回 undefined 的情况。如果没指定 domain 则返回比例尺当前的输入域。

// invertExtent 返回输出域中的值 value 对应的输入范围
console.log(scaleThreshold.invertExtent('small')) // [Infinity, 0]
console.log(scaleThreshold.invertExtent('medium')) // [0, 10]
console.log(scaleThreshold.invertExtent('large')) // [10, 20]
console.log(scaleThreshold.invertExtent('xlarge')) // [20, Infinity]

scaleQuantize 量化比例尺

const scale = d3.scaleQuantize() // 连续输入和离散输出
    .domain([0, 10])
    .range(['red', 'green', 'blue', 'pink'])

console.log(scale(-1)) // red
console.log(scale(2)) // red
console.log(scale(8)) // pink
console.log(scale(20)) // pink

console.log(scale.invertExtent('red')) // [0, 2.5]
console.log(scale.invertExtent('green')) // [2.5, 5]
console.log(scale.invertExtent('blue')) // [5, 7.5]
console.log(scale.invertExtent('pink')) // [7.5, 10]

颜色比例尺

D3提供了一些颜色比例尺:点击查看文档

d3.schemeCategory10
d3.schemeAccent
d3.schemeDark2
d3.schemePaired
d3.schemePastel1
d3.schemePastel2
d3.schemeSet1
d3.schemeSet2
d3.schemeSet3

// 定义一个序数颜色比例尺
let color = d3.scaleOrdinal(d3.schemeCategory10)
console.log(color(1)) // #1f77b4

总结

本章介绍了几种常用的比例尺,D3 还有一些比例尺可以查看官方文档了解:

d3.scaleIdentity() // 恒等比例尺
d3.scaleSqrt() // 乘方比例尺
d3.scalePow() // 类似scaleSqrt的乘方比例尺
d3.scaleLog() // 对数比例尺
d3.scaleQuantile() // 分位数比例尺

上述的各种使用比例尺的例子都相当于一个正序的过程,从domain的数据集映射到range数据集中,那么有没有逆序的过程呢?D3中提供了invert()以及invertExtent()方法可以实现这个过程。

加载全部内容

相关教程
猜你喜欢
用户评论