【问题标题】:Checking text overflow on SVG textpath & jquery检查 SVG 文本路径和 jquery 上的文本溢出
【发布时间】:2017-02-05 02:30:21
【问题描述】:

首先,我在这里查看了所有可能的相关答案,但似乎没有一个能带来我需要的答案,所以我在这里。 给定一个 svg 文本路径:

<svg viewBox="0 0 900 900"
     xmlns="http://www.w3.org/2000/svg" 
     xmlns:xlink="http://www.w3.org/1999/xlink"
     id="mysvg"
     >
  <defs>
      <path id="myPath" d="M70 110 C 70 140, 110 140, 110 110" stroke="black" fill="transparent"/>
  </defs>

  <use xlink:href="#myPath" fill="none" stroke="red"  />

  <text id="names" font-family="Verdana" font-size="10" text-anchor="middle" >
    <textPath xlink:href="#myPath" startOffset="50%">
      My text is going to exceed at some point…
    </textPath>
  </text>
</svg>

此时文本超出了文本路径

我找不到通过 jquery 检查可能溢出的方法。此命令实际上不会返回 undefined:

alert($("text#names").attr("textLength") );

我正在尝试检查是否有溢出,以使文本达到最大长度左右。

【问题讨论】:

    标签: javascript jquery html svg


    【解决方案1】:

    我在调整字体大小时遇到​​了同样的问题,这样给定的文本将以尽可能大的字体大小绘制而不会溢出。使用纯 JS 非常简单。

    1) 确定 np.文本元素中具有最小字体大小的字符数:

    textElement.css('font-size', 1);                                                        
    var allCharCount = textElement[0].getNumberOfChars();                                   
    

    2)然后将字体大小设置为任意值并再次确定长度

    var hasOverflow = allCharCount != textElement[0].getNumberOfChars();                
    

    getNumberOfChars() 只会返回编号。绘制的字符集。如果有溢出,这个数字会比原来的整个字符串小。

    【讨论】:

    • 感谢您的意见。将尽快尝试并让您知道;)
    • @6infinity8:我没有找到任何其他解决方案。你知道吗?
    • @REDSOFTADAIR 对于简单的曲线(弧线和直线),事实证明您可以轻松增加路径的长度,例如将其加倍,然后通过比较 path.getTotalLength() / 2 和 @987654325 的值来检测溢出@。这对我来说已经足够了,否则你也可以查看我最后一个仅适用于 Chrome 的答案:stackoverflow.com/a/57043365/4413709
    【解决方案2】:

    看起来text.getNumberOfChars() 在编写另一个答案后发生了变化,现在返回字符串中的字符总数,无论它们是否被渲染。

    我解决这个问题的方法是:

    • 更改&lt;textPath&gt; 元素以绘制更长的路径,然后使用text.getComputedLength() 计算文本长度
    • &lt;textPath&gt;改回原来的路径,重新计算长度
    • 如果原始路径上的长度小于较长路径上的长度,则说明存在溢出。

    const textPath = document.querySelector('textPath');
    
    const checkClipped = () => {
      textPath.setAttribute('xlink:href', '#fullWidthPath');
      const fullLength = textPath.getComputedTextLength();
      textPath.setAttribute('xlink:href', '#myPath');
      const curvedLength = textPath.getComputedTextLength();
      return fullLength > curvedLength;
    }
    
    const findLongestString = () => {
      const text = textPath.innerHTML;
      if (checkClipped()) {
        const newText = text.substring(0, text.length - 1);
        textPath.innerHTML = newText;
        return findLongestString(newText);
      } else {
        return text;
      }
    }
    
    console.log(findLongestString())
    <svg viewBox="0 0 200 200" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" id="mysvg">
      <defs>
          <path id="myPath" d="M70 110 C 70 140, 110 140, 110 110" stroke="black" fill="transparent"/>
          <path id="fullWidthPath" d="M 0 0 L 0 10000" />
      </defs>
    
      <use xlink:href="#myPath" fill="none" stroke="red"  />
    
      <text id="names" font-family="Verdana" font-size="10" text-anchor="middle" >
        <textPath xlink:href="#myPath" startOffset="50%">
          My text is going to exceed at some point…
        </textPath>
      </text>
    </svg>

    【讨论】:

      猜你喜欢
      • 2011-10-11
      • 2015-03-05
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-05-29
      • 2019-06-08
      • 2016-07-18
      相关资源
      最近更新 更多