【问题标题】:Fabric.js: Get text bounding box width and heightFabric.js:获取文本边界框的宽度和高度
【发布时间】:2015-12-31 05:45:41
【问题描述】:

我正在使用 fabric.js。我想获得确切包含文本(由下面的红色框表示)的矩形的尺寸(“边界框”是正确的术语吗?)。即使我将填充更改为 0,默认的 fabric.js 框也有填充。

我尝试从织物画布中获取上下文,然后调用 .measureText(),但它没有提供我需要的边界框的完整信息。

编辑:

IText 对象似乎有几个组件:容器、选择区域和文本本身。在下图中,IText 框是浅蓝色线条。选择区域是浅蓝色填充。 红色框是我需要的....它是恰好包含文本本身的区域(甚至没有 1 个像素在这样的矩形之间以及文本中最极端的部分)。 getBoundingRectHeight 和 getBoundingRectWidth 方法(我相信都已弃用并被 getBoundingRect 取代)返回外部 IText 容器框(浅蓝色线)的高度/宽度。

注意:这是一个 8 像素的填充框(蓝线和蓝色填充之间的区域)。即使我将填充设置为 0,这些功能仍然无法满足我的需求。

【问题讨论】:

    标签: javascript html5-canvas fabricjs


    【解决方案1】:

    您是否尝试过每个织物对象上可用的getBoundingRectHeight()getBoundingRectWidth() 方法?

    【讨论】:

    • 我正在寻找“恰好包含文本的矩形”。我将编辑问题并添加文本对象、选择和文本本身之间差异的说明。
    • 你能用你的例子做一个小提琴吗?
    • 这是我需要的,在当前的 fabric.js 中是 getBoundingRect().widthgetBoundingRect().height
    【解决方案2】:

    以下内容摘自 W3C 的“HTML Canvas 2D Context, Editor's Draft 13 November 2014”。这是关于绘制文本一章的注释:

    使用 fillText() 和 strokeText() 渲染的字形可能会溢出 由字体大小(em 正方形大小)和返回的宽度给出的框 通过 measureText() (文本宽度)。这个版本的规范 不提供获取边界框尺寸的方法 文本。如果要渲染和删除文本,则需要注意 用来替换剪裁的画布的整个区域 区域覆盖,不仅仅是由 em 平方高度给出的框和 测量的文本宽度。

    目前,您似乎无法根据需要从 javascript 中确定边界框。您只能依靠重绘整个画布/剪辑区域。

    【讨论】:

      【解决方案3】:

      我不知道用于执行此操作的性能或资源。但它确实有效。感谢@Prestaul 的post 让我开始。这就是我想出的:

      function getBoundingBox(ctx, left, top, width, height) {
          var ret = {};
      
          // Get the pixel data from the canvas
          var data = ctx.getImageData(left, top, width, height).data;
          console.log(data);
          var first = false; 
          var last = false;
          var right = false;
          var left = false;
          var r = height;
          var w = 0;
          var c = 0;
          var d = 0;
      
          // 1. get bottom
          while(!last && r) {
              r--;
              for(c = 0; c < width; c++) {
                  if(data[r * width * 4 + c * 4 + 3]) {
                      console.log('last', r);
                      last = r+1;
                      ret.bottom = r+1;
                      break;
                  }
              }
          }
      
          // 2. get top
          r = 0;
          var checks = [];
          while(!first && r < last) {
      
              for(c = 0; c < width; c++) {
                  if(data[r * width * 4 + c * 4 + 3]) {
                      console.log('first', r);
                      first = r-1;
                      ret.top = r-1;
                      ret.height = last - first - 1;
                      break;
                  }
              }
              r++;
          }
      
          // 3. get right
          c = width;
          while(!right && c) {
              c--;
              for(r = 0; r < height; r++) {
                  if(data[r * width * 4 + c * 4 + 3]) {
                      console.log('last', r);
                      right = c+1;
                      ret.right = c+1;
                      break;
                  }
              }
          }
      
          // 4. get left
          c = 0;
          while(!left && c < right) {
      
              for(r = 0; r < height; r++) {
                  if(data[r * width * 4 + c * 4 + 3]) {
                      console.log('left', c-1);
                      left = c;
                      ret.left = c;
                      ret.width = right - left - 1;
                      break;
                  }
              }
              c++;
      
              // If we've got it then return the height
              if(left) {
                  return ret;    
              }
          }
      
          // We screwed something up...  What do you expect from free code?
          return false;
      }
      

      这是一个 jsfiddle 演示:http://jsfiddle.net/spencerw/j41jx0e2/

      【讨论】:

        猜你喜欢
        • 2022-12-12
        • 2022-01-17
        • 2017-03-15
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多