【 D3.js 高级系列 — 9.0 】 交互式提示框

一般来说,图表中不宜存在过多文字。但是,有时需要一些文字来描述某些图形元素。那么,可以实现一种交互:当用户鼠标滑到某图形元素时,出现一个提示框,里面写有描述文字。这是一种简单、普遍的交互式,几乎适用于所有图表。通过可给提示框定制外观,能给用户带来很好的体验。

901

1. 提示框的制作思路

提示框,就是“文字”加“边框”。显示文字,一般来说用 SVG 的<text>,但是,有两个问题:

  • 如果字符串过长,<text>元素不能自动换行,虽然可以通过<text>的子元素<tspan>来模拟自动换行的功能,但是很麻烦。
  • <text>是SVG的元素。也就是说,<text>是“图形”而非“文字”,它与SVG中的<circle>、<line>、<path>等元素本质上是一样的。那么,当输出SVG图形时,<text>也会作为图形的一部分输出。

因此,SVG的<text>元素不适合制作提示框。

有一种简单的方法:div + css。div是HTML的元素,在样式中设定其定位方法为绝对定位

然后,当监听到鼠标事件时,用鼠标的坐标为提示框定位即可,代码形如:

实际应用中,为使提示框美观,还需为div设置更多的样式。

2. 为饼状图添加提示框

以饼状图为例,绘制好饼状图后。

首先,在 <body> 中添加一个 <div> ,透明度设定为 0,即完全透明,div的类设定为 tooltip。

然后,定义一个 tooltip 样式,并将其定位方式设置绝对定位,这一步是重点。其他的属性时关于边框外观和文字显示方式的,此处定义一个简单的。

最后,为饼状图的各图形元素定制鼠标事件的监听器,其中包括:鼠标放到到图形上时(mouseover)、鼠标在图形上移动时(mousemove),鼠标移出时(mouseout)。

d3.event.pageX 和 d3.event.pageY 是当前鼠标相对于浏览器页面的坐标,而对于处于绝对定位状态的 <div> 元素来说,其样式 left 和 top 也是相对于浏览器页面来说的。赋值的时候,令 top 的值为 d3.event.pageY + 20,使提示框稍微显示在鼠标位置的下方,这么做能够防止鼠标在提示框上移动导致不触发事件的问题。

3. 结果

结果如下图所示,当鼠标移动到“联想”上时,出现了提示框。

源代码请单击以下链接,邮件查看源代码:

http://www.ourd3js.com/demo/G-9.0/tooltip.html

谢谢阅读。

文档信息

【 D3.js 高级系列 — 9.0 】 交互式提示框》上有19条评论

  1. 老师请教一下问题,类型占百分比太小,无法显示,如何解决。谢谢
    比如1.3%,在饼图中只显示3。

  2. 如何将提示框文字写成表格形式?能给个代码示例吗?

    • 提示框是一个 div 。
      安装平时在 HTML 里写表格的方式,在这个 div 里写表格就好。

  3. 老师,请问一下,这个pie我要动态获取数据,要怎么做

          • 老师可不可弄个例子看一下

          • 例如

            您看这样解释行吗?如果有需要,请再留言

  4. 楼主好人!我想问一下,D3可不可以绘制统计学上的箱型图、点阵图之类的?

  5. 感谢楼主解决了我的问题,谢谢

  6. 最后关于 mouseout 事件触发,提示框 opacity 设为 0,其实有一个 bug:
    移出图表的时候,其实提示框还是在饼状体的上方,只是看不到了,这就存在一个问题,当鼠标再次移到上次提示框隐藏的位置,就算实际上是在图表上方,也不会触发 mouseover 事件,建议在 mouseout 的时候把提示框的 display 属性设为 none;mouseover 的时候设为 block;

  7. 我用博主的方法,在子弹图(http://bl.ocks.org/mbostock/4061961)上做提示框,
    为什么提示框显示的位置离鼠标好远?
    需要d3.event.pageX – 180之后,才差不多显示在鼠标稍右的位置。

      • 只能先“d3.event.pageX – 180”,这样凑活着调整提示框的显示位置

  8. Pingback引用通告: D3js-三种图表tooltip提示框总结介绍 - Web前端 - 阿里欧歌

评论已关闭。