如何使用 d3.js 将圆环图的标签拆分为多行?

How do I split labels for my donut chart to multiple lines using d3.js?

我正在用我的圆环图显示标签;

this.graphGroup
      .selectAll('allLabels')
      .data(data_ready)
      .enter()
      .append('text').style('font-size', '24px')
      .text(d => {
        return d.data.name;   //LINE 1
      })
      .attr('transform',`${calculatedValue}`)
      .style('text-anchor', 'start');

我想使用这个答案 How do I include newlines in labels in D3 charts? 但是在添加标签之后添加代码,

this.graphGroup
    .selectAll('text')
    .each
    ( function (d) {
      var el = this.d3.select(this);
      console.log(el);
      var words = d.name.split(' ');
      console.log(words);
      el.text('');

      for (var i = 0; i < words.length; i++) {
        var tspan = el.append('tspan').text(words[i]);
        if (i > 0)
          tspan.attr('x', 0).attr('dy', '15');
      }
    });

当我在第一个 selection 上使用 each() 时,我收到一条错误消息,指出 selection 未定义。我尝试在第 1 行添加代码,但我只能将文本传递到 d3.text().

如何才能正确拆分标签?

编辑:我也有一个错误说我的局部变量 d3 未定义,但它在创建 graphGroup 和所有其他 selections 时有效,然后我直接从 d3 导入 select。

我找到答案了;如果在该选择上调用了 data() 函数,则 each() 不起作用,因此直接来自链接 post 的答案将不起作用。

另一种选择是对创建的每个文本元素使用 call(),就像这样;

this.graphGroup
      .selectAll('allLabels')
      .data(data_ready)
      .enter()
      .append('text').style('font-size', '24px')
      .attr('transform',`${calculatedValue}`)
      .style('text-anchor', 'start')
      .text(d => {
        return d.data.name;
      })
      .call(lineBreak, 40);

其中 lineBreak 是我定义的另一个函数,传递到函数中的第一个参数将是对循环元素的引用,在这种情况下,不同的文本元素。

换行函数:

function lineBreak(text, width) {
      text.each(function () {
        var el = d3.select(this);
        let words = el.text().split(' ');
        let wordsFormatted = [];

        let string = '';
        for (let i = 0; i < words.length; i++) {
          if (words[i].length + string.length <= width) {
            string = string + words[i] + ' ';
          }
          else {
            wordsFormatted.push(string);
            string = words[i] + ' ';
          }
        }
        wordsFormatted.push(string);

        el.text('');
        for (var i = 0; i < wordsFormatted.length; i++) {
          var tspan = el.append('tspan').text(wordsFormatted[i]);
          if (i > 0)
            tspan.attr('x', 0).attr('dy', '20');
        }
      });
    }

将优化此功能,稍后再编辑。谢谢!