将 FontAwesome 图标添加到 D3 图形

IT技术 javascript d3.js font-awesome
2021-02-18 05:22:11

我试图在我的 D3 节点中设置一个带有FontAwesome的图标而不是文本。这是原来的实现,文字如下:

g.append('svg:text')
    .attr('x', 0)
    .attr('y', 4)
    .attr('class', 'id')
    .text(function(d) { return d.label; });

现在我尝试使用图标:

g.append('svg:i')
   .attr('x', 0)
   .attr('y', 4)
   .attr('class', 'id icon-fixed-width icon-user');

但这不起作用,即使标记是正确的,并且正确命中 CSS 规则:图标不可见。

知道为什么吗?

这是相关的jsbin

编辑

我找到了插入图像的替代方法:http : //bl.ocks.org/mbostock/950642

node.append("image")
    .attr("xlink:href", "https://github.com/favicon.ico")
    .attr("x", -8)
    .attr("y", -8)
    .attr("width", 16)
    .attr("height", 16);

这正是我想要做的,但它不适<i>用于 FontAwesome 使用的元素。

6个回答

您需要在普通文本元素中使用正确的 Unicode,然后将字体系列设置为“FontAwesome”,如下所示:

 node.append('text')
    .attr('font-family', 'FontAwesome')
    .attr('font-size', function(d) { return d.size+'em'} )
    .text(function(d) { return '\uf118' }); 

这个确切的代码将呈现一个“图标微笑”图标。可以在此处找到所有 FontAwesome 图标的 unicode:

http://fortawesome.github.io/Font-Awesome/cheatsheet/

请注意,您需要将备忘单中的代码从 HTML/CSS unicode 格式调整为 Javascript unicode 格式,以便&#xf118;必须\uf118在您的 javascript 中编写

此解决方案不适用于Font Awesome 5.6.3您还需要设置.attr('font-family', 'Font Awesome 5 Free').attr('font-weight', 900)
2021-04-15 05:22:11
它对我不起作用……我使用了与上面列出的完全相同的代码,但没有按预期获得绘图。我需要在本地安装字体吗?我正在使用 FontAws 的 cdn 版本并想知道这是否与它有关(它在其他任何地方都可以完美运行,但 D3)
2021-04-21 05:22:11
谢谢 Carles,我通过将 attr 更改为 font-family 和 font-size 的样式来使其工作
2021-04-22 05:22:11
如何使用 FAB 或 FAR 图标?
2021-04-22 05:22:11
谢谢!这完美地工作。我陷入了几个陷阱。首先值得注意的是它<text>是一个 svg 标签(我将它作为 html 标签查找)。我在将图标居中放置在节点中时遇到了问题(在我的例子中是圆圈) - 还有样式问题,因为 CSS 优先于属性,并且我为<text>元素设置了样式作为参考,我将粘贴我的最终解决方案作为答案。
2021-05-15 05:22:11

感谢所有回答。我的最终解决方案基于 CarlesAndres 的回答:

g.append('text')
    .attr('text-anchor', 'middle')
    .attr('dominant-baseline', 'central')
    .attr('font-family', 'FontAwesome')
    .attr('font-size', '20px')
    .text(function(d) { return ICON_UNICODE[d.nodeType]; });

小心你的 CSS:它优先于 SVG 属性。

这是它的外观:

节点图

foreignObject解决方案相比,这样做的好处是事件由 D3 正确处理。

ICON_UNICODE是 font-awesome 4.0.3对象:gist.github.com/forresto/8254791
2021-04-17 05:22:11
嗨,你能把为你做这件事的代码片段发给我吗?出于某种原因,当我使用上面附加的代码时,我没有显示任何图像?你是如何存储图像的unicode的?谢谢
2021-04-26 05:22:11
您可能需要该ICON_UNICODE数组。
2021-05-09 05:22:11
谢谢,这有效。查看其他答案后,我仍然错过了最终在您的示例代码中偶然发现的字体系列设置。基于 Stackoverflow 的终生编程😂
2021-05-11 05:22:11
@jeckyll2hide 快速说明: .attr 应该是 .style 以显示图标。这是从 D3.JS 版本 3.5.3 开始的。试图只编辑您的答案,但这是行不通的。
2021-05-12 05:22:11

我真的是 d3 的新手,但是 font awesome 通过为<i>具有 class 属性元素设置样式来工作

我发现的唯一方法是附加 aforeignObject并在其上设置 font awesome 所需的相关 HTML。

参考:

https://developer.mozilla.org/en-US/docs/Web/SVG/Element/foreignObject?redirectlocale=en-US&redirectslug=SVG%2FElement%2FforeignObject

http://fortawesome.github.io/Font-Awesome/examples/

代码:

g.append('svg:foreignObject')
    .attr("width", 100)
    .attr("height", 100)
    .append("xhtml:body")
    .html('<i class="icon-fixed-width icon-user"></i>');

演示:http : //jsbin.com/eFAZABe/3/

因为还没有人提到对异物的不完整浏览器支持:caniuse.com/#feat=svg-html
2021-04-23 05:22:11
我正在检查是否可以用另一种方式
2021-05-02 05:22:11
抱歉,尝试过 tspan 和其他,但我发现的唯一方法是使用 foreignObject
2021-05-05 05:22:11
您的解决方案很有趣,但是有异物会使样式变得复杂。例如,body CSS 样式会自动应用(在我的例子中,这使得图标的背景在节点图中可见)。我更喜欢没有这个foreignObject的解决方案,但我不知道这是否可能。
2021-05-06 05:22:11
谢谢。ForeignObject 的另一个问题是它不中继事件。您可以在此处看到该问题:jsbin.com/eFAZABe/6:当您尝试链接节点时,该图标会阻止 onMouseOver。在最初的问题中,我添加了一个链接到一个示例,该示例使用图像来实现类似的效果(但我需要字体真棒图标)
2021-05-07 05:22:11

鉴于其他答案不再有效(因为 d3js 已同时更新)并且由于兼容性问题不是一个好的使用解决方案svg:foreignObject,这里是一个无需使用任何黑客即可工作的答案:

.append("text")      // Append a text element
.attr("class", "fa") // Give it the font-awesome class
.text("\uf005");     // Specify your icon in unicode (https://fontawesome.com/cheatsheet)

这是一个工作示例(单击“运行代码片段”,d3 代码输出三颗星):

var icons = [1, 2, 3];

d3.select("body")
  .selectAll(".text")
  .data(icons)
  .enter()
  .append("text")       // Append a text element
  .attr("class", "fa")  // Give it the font-awesome class
  .text("\uf005");      // Specify your icon in unicode
<link href="https://use.fontawesome.com/releases/v5.6.3/css/all.css" rel="stylesheet"/>
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/5.16.0/d3.min.js"></script>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.5.1/jquery.min.js"></script>

@AhmadKarim D3.js 版本已过时。我添加了一个较新的版本,现在它又可以工作了,见上文。
2021-04-18 05:22:11
荣誉!此解决方案也适用于Font Awesome 5.6.3并且从 4 迁移不需要任何额外的努力
2021-04-20 05:22:11

我知道这个问题很老,已解决,但是 - 今天这对我有用。

这个网站

svg.append('svg:foreignObject')
    .attr("width", 50)
    .attr("height", 50)
    .append("xhtml:body")
    .html('<i class="fa fa-user"></i>');

但是对于我的图表,我删除了 append xhtml:body,否则它不会让我设置 x 和 y 坐标。

该元素将采用您设置的字体的宽度和高度。

d3.select('svg')
    .append('svg:foreignObject')
    .attr('class', 'handle')
    .attr('x',  +getLeftBarPosition(i+1, 'handle')[0] + +getLeftBarPosition(i+1, 'handle')[1])
    .attr('y', state.barHeight/2)
    .html('<i class="fa fa-user"></i>')