KonvaJS:如何在调整大小时更改文本类的属性(fontSize,高度和宽度)?

时间:2018-09-10 05:32:25

标签: javascript konvajs

我试图在KonvaJS中调整文本层的大小。我的代码如下:

var Canvas = (function() {
    var funct = {};
    var stageWidth,stageHeight,stage,layer,circle,rect,myPlayer,textNode,tr;

    funct.stageInit = function(){
      stage = new Konva.Stage({
        container: 'canvas',
        width: stageWidth,
        height: stageHeight
      });

      layer = new Konva.Layer();
      stage.add(layer);

      funct.addText();
      funct.makeTextResizeable();
      layer.draw();
    }

    funct.addText = function(){
      textNode = new Konva.Text({
        text: 'Some text here',
        x: 50,
        y: 50,
        width: 50,
        height: 50,
        fontSize: 20,
        draggable: true,
      });

      layer.add(textNode);

      textNode.on('dblclick', () => {
        // create textarea over canvas with absolute position

        // first we need to find its positon
        var textPosition = textNode.getAbsolutePosition();
        var stageBox = stage.getContainer().getBoundingClientRect();

        var areaPosition = {
          x: textPosition.x + stageBox.left,
          y: textPosition.y + stageBox.top
        };


        // create textarea and style it
        var textarea = document.createElement('textarea');
        document.body.appendChild(textarea);

        textarea.value = textNode.text();
        textarea.style.position = 'absolute';
        textarea.style.top = areaPosition.y + 'px';
        textarea.style.left = areaPosition.x + 'px';
        textarea.style.width = textNode.width();
        textarea.style.zIndex = 15;

        textarea.focus();


        textarea.addEventListener('keydown', function (e) {
          if (e.keyCode === 13) {
            textNode.text(textarea.value);
            layer.draw();
            document.body.removeChild(textarea);
          }
        });
      });
    }

    funct.makeTextResizeable = function(){
      tr = new Konva.Transformer({
        boundBoxFunc: function (oldBoundBox, newBoundBox) {
          if (newBoundBox.width > 200) {
            return oldBoundBox;
          }
          textNode.attrs.fontSize = (newBoundBox.width/oldBoundBox.width)*textNode.attrs.fontSize;
          textNode.attrs.width = (newBoundBox.width/oldBoundBox.width)*textNode.attrs.width;
          textNode.attrs.height = (newBoundBox.width/oldBoundBox.width)*textNode.attrs.height;
          console.log(textNode.attrs.fontSize);
          return newBoundBox
        },
        isTransforming: function(){
          console.log('a');
        }
      });
      layer.add(tr);
      tr.attachTo(textNode);
    }

    funct.fitStageIntoParentContainer = function(){
      var container = document.querySelector('#canvas-container');
      var containerWidth = container.offsetWidth;
      var scale = containerWidth / stageWidth;

      stage.width(stageWidth * scale);
      stage.height(stageHeight * scale);
      stage.scale({ x: scale, y: scale });
      stage.draw();
    }

    funct.Onresize = function(){
      window.addEventListener('resize', function(){
        funct.fitStageIntoParentContainer();
      });
    }

    funct.init = function(){
      stageHeight = $('.vjs-poster').height();
      stageWidth =  $('.vjs-poster').width();
      funct.stageInit();
      funct.Onresize();
    }
    return funct;
  })();  

我想允许通过拖动并相应地更改字体大小来调整文本层的大小。我还希望根据文字层的大小来包装/展开文字。

https://jsfiddle.net/gentrobot/5gk1h67u/

要求是能够在运行时动态添加文本,调整其大小和位置,然后获取文本的最终大小,文本容器和文本容器的坐标以进行保存。然后,根据这些信息,将生成具有动态添加的文本的HTML,该文本位于主元素上。

我可以调整文本的大小,但是调整大小时无法流畅地进行调整,也不能自动换行。但是,一旦完成,我也可以提取最终坐标和大小。

1 个答案:

答案 0 :(得分:1)

在转换文本时,可能不需要更改scale。您可以在每个transform事件中将其重置:

tr.on('transform', function() {
     textNode.setAttrs({
         width: textNode.width() * textNode.scaleX(),
         height: textNode.height() * textNode.scaleY(),
         scaleX: 1,
         scaleY: 1,
     });
})

为了获得更好的用户体验,您可以限制一些大小:

  tr = new Konva.Transformer({
    boundBoxFunc: function (oldBoundBox, newBoundBox) {
      if (newBoundBox.width > 200 || newBoundBox.width < textNode.fontSize()) {
        return oldBoundBox;
      } else if (newBoundBox.height < textNode.fontSize()) {
        return oldBoundBox;
      }
      return newBoundBox
    }
});

演示:https://jsfiddle.net/dgL1kvcb/1/

如果在转换时也需要更改fontSize,则需要定义其逻辑。如果要同时改变换行和字体大小怎么办?