复制并粘贴在fabric.js 2.0 beta6

时间:2017-08-23 13:33:11

标签: javascript canvas fabricjs

我在fabric.js 2.x beta6之前使用此代码来复制和粘贴内容并且工作正常:

function copy() {
    var activeObject = canvas.getActiveObject(),
        activeGroup = canvas.getActiveGroup();

    if (activeGroup) {
        _clipboard = activeGroup;
    } else if (activeObject) {
        _clipboard = activeObject;
    }
    return false;
}

function paste() {
    var activeObject = canvas.getActiveObject(),
        activeGroup = canvas.getActiveGroup();
    canvas.discardActiveObject();
    if (_clipboard.size) {

        _clipboard.clone(function (clonedObj) {
            canvas.discardActiveGroup();
            clonedObj.set({
                left: clonedObj.left + 10,
                top: clonedObj.top + 10,
                evented: true
            });

            clonedObj.forEachObject(function (obj) {
                obj.set('active', true);
                canvas.add(obj);
            });

            canvas.setActiveGroup(clonedObj).renderAll();
        });
    } else {
        _clipboard.clone(function (clonedObj) {
            clonedObj
                .set("top", _clipboard.top + 5)
                .set("left", _clipboard.left + 5)
                .setCoords();

            canvas
                .add(clonedObj)
                .setActiveObject(clonedObj)
                .renderAll();
        });
    }
}

由于在新版本中,选择过程已经简化了很多,并且已经删除了一些方法(参见此处):

http://fabricjs.com/v2-breaking-changes-2

请参阅此文档,一般请参阅此链接:

http://fabricjs.com/changelog

以上解决方案将不再适用。所以我试图将我的脚本采用到这样的新测试版中:

function copy() {
    var activeObject = canvas.getActiveObject();
        _clipboard = activeObject;
       console.log(_clipboard);
}


function paste() {
    var activeObject = canvas.getActiveObject();
    canvas.discardActiveObject();
    if (_clipboard.size) {

        _clipboard.clone(function (clonedObj) {
            canvas.discardActiveObject();
            clonedObj.set({
                left: clonedObj.left + 10,
                top: clonedObj.top + 10,
                evented: true,
                active: true
            });

            clonedObj.forEachObject(function (obj) {
                obj.set('active', true);
                canvas.add(obj);
            });

            canvas.setActiveObject(clonedObj);
            canvas.requestRenderAll;
        });
    } else {
        _clipboard.clone(function (clonedObj) {
            canvas.discardActiveObject();
            clonedObj.set("top", _clipboard.top + 5);
            clonedObj.set("left", _clipboard.left + 5);
            clonedObj.set('active', true);
            clonedObj.setCoords();



            canvas.add(clonedObj);
            canvas.setActiveObject(clonedObj);
            canvas.requestRenderAll;
        });
    }
}

我面临以下问题:

  1. 我无法复制和粘贴多个选定的(未分组) 对象
  2. 复制并粘贴分组对象的工作,但一旦取消选择粘贴的对象,就无法再次选择。
  3. 请参阅此小提琴:https://jsfiddle.net/sharksinn/wta4pdpz/1/

    编辑:这是工作和更新的小提琴:

    https://jsfiddle.net/sharksinn/wta4pdpz/13/

1 个答案:

答案 0 :(得分:1)

我是来自fabricjs问题跟踪器的人。

那么有几点可以更好地理解选择过程。一个在文档中突出显示,即使您保存引用,也不应该在尝试使用它之前丢弃activeObject。 在取消选择时,activeSelection的确就像autodestroy一样,因此引用它会返回对取消选择后为空的对象的引用。

这是一个建议:

function copy() {
// clone what are you copying since you may want copy and paste on different moment.
// and you do not want the changes happened later to reflect on the copy.
// maybe.
  canvas.getActiveObject().clone(function(cloned) {
    _clipboard = cloned;
  });
}

function paste() {
// clone again, so you can do multiple copies.
  _clipboard.clone(function(clonedObj) {
    canvas.discardActiveObject();
    clonedObj.set({
      left: clonedObj.left + 10,
      top: clonedObj.top + 10,
      evented: true,
    });
    if (clonedObj.type === 'activeSelection') {
        // active selection needs a reference to the canvas.
        clonedObj.canvas = canvas;
        clonedObj.forEachObject(function (obj) {
            canvas.add(obj);
        });
        // this should solve the unselectability
        clonedObj.setCoords();
    } else {
       canvas.add(clonedObj);
    }
    canvas.setActiveObject(clonedObj);
    canvas.requestRenderAll();
 });
}

虽然我无法尝试此代码,但我可以说这或多或少是正确的轨道。 在任何情况下粘贴设置位置时,如果您有activeSelection或其他内容,则拆分逻辑,然后执行setActiveObject和render请求。