工具提示显示在两个不在Firefox中的单独行中

kri*_*a_v 3 d3.js

我正在添加一个带有<br>html标签的工具提示.它在chrome中运行良好但在firefox上运行不正常.

我的代码:

var dot = svg.append("g")
      .attr("class", "dots")
      .selectAll(".dot")
      .data(interpolateData(1))
      .enter().append("circle")
      .attr("class", "dot")

  // Add a title.
  dot.append("title")
     .each(function() {


      var d = d3.select(this);
d3.select(this).select("title")
       .html(function(d,i) { return d.name + ": " + Math.round(Number(d.avg)) + " avg each month <br>" + d.name + ": Build of "  + Math.round(Number(d.Checkin)) + " hrs each month";});
Run Code Online (Sandbox Code Playgroud)

工具提示应该以2行显示.它在chrome中工作正常但在firefox中没有.

Ame*_*aBR 5

SVG <title>元素在浏览器之间处理不一致,因为它具有类似的功能,但与HTML title属性相比具有不同的规则.浏览器似乎有选择地选择它们适用于SVG的HTML规则以及如何应用.

SVG <title>元素的规格说明:

  • 标题主要用于辅助功能.

  • 浏览器可以将标题显示为工具提示.

  • 但是,必须显示独立SVG文档中的顶级标题(通常在标题栏中,与HTML <title>元素相同).

  • 标题可能包含来自其他名称空间的内容,具有适当的XML名称空间属性,但没有迹象表明在创建工具提示时应如何呈现这些内容.

  • 任何不在另一个名称空间中的内容都应该受到一般SVG空格处理规则的约束,这些规则要求忽略换行符.

HTML title属性规格表明:

  • 标题代表关于该元素的其他"咨询信息".

  • 浏览器必须向用户提供标题信息,最好是以与设备无关的方式(尽管大多数只在悬停时显示).

  • 显示工具提示时,必须遵守属性中的换行符.

  • 不允许其他标记(因为它是属性,而不是HTML代码).

但...

浏览器制造商重复使用代码显示HTML工具提示以显示SVG工具提示,因此事情变得令人困惑.

跟随这个小提琴(记住这适用于HTML文档中的内联SVG):http://fiddle.jshell.net/5npxba9L/6/

  • SVG中的硬换行和额外空格<title>:

    • 保存在铬36,歌剧24和Firefox 31(即,HTML属性规则被应用)

    • 在IE 11中被忽略(即,应用了SVG空白规则)

  • <br/>SVG中的标记元素<title>:

    • 从Firefox 31中的工具提示中删除

    • 在Chrome 36,Opera 24和IE 11中显示为换行符

    • 当使用XML名称空间前缀时,在所有浏览器中都被完全忽略(这在XHTML文档中可能有所不同)

  • SVG中的其他标记元素<title>,例如SVG <tspan>元素:

    • 从Firefox 31和IE 11中的工具提示中删除

    • 在Chrome和Opera中显示为纯文本(即打印出的尖括号)

  • 在HTML标题属性中保留硬换行符和额外的空格,并且在所有测试的浏览器中(正确地)将额外标记呈现为纯文本

因此,完全hacky而不是根据规范获取内联SVG中的多行工具提示的方法是使用两个 <br/>标记(未命名空间或默认命名空间中的更改)和<title>元素中的硬换行符:

<svg>
    <circle cx="250" r="50">
        <title><span xmlns="http://www.w3.org/1999/xhtml">Title with <br/>
a line break</span></title>
    </circle>
</svg>
Run Code Online (Sandbox Code Playgroud)

适用于当前版本的Chrome,Opera,Firefox和IE(尚未在Safari或移动设备上测试),尽管基于webkit的浏览器将创建一个额外的空白行.

但是请注意:selection.html()在大多数浏览器中,您将无法使用d3 方法创建上述标记,因为该函数依赖于HTMLElement.innerHTMLDOM属性,而该属性未在SVG元素上定义.您需要分别创建文本节点和<br>元素.最简单的方法是使用虚拟HTML元素作为父元素,使用innerHTML属性创建混合内容,然后将其附加到title元素:

dot.enter().append("circle")
      .attr("class", "dot")
      .attr("r", "50")
      .attr("cx", function(d,i){return i*100 + 50;})
  .append("title")
  .append(function(d, i){
      //when the parameter to `append()` is a function
      //it will be run for each element in the active selection
      //(in this case, the title elements)
      //and must return the actual element node to append.

      var span = document.createElement("span");
      span.innerHTML = "This is element <br/>\n #" + i;
      //the \n will be converted in Javascript to a line break
      return span;
  });
Run Code Online (Sandbox Code Playgroud)

http://fiddle.jshell.net/cLLsgdmk/

这一切都是好奇心.如果您需要更可靠的解决方案,请按照Lars的回答获取如何创建<foreignObject>工具提示的链接,或者查看此Codepen演示,了解有关如何使用Javascript覆盖绝对位于<div>SVG顶部的信息.