简体   繁体   English

FabricJS - 从 JSON 保存/获取画布时保留事件

[英]FabricJS - Preserve events on saving / getting canvas from JSON

Is there a way to "preserve" events when saving canvas to JSON and then get them bonded back on loadFromJSON有没有办法在将画布保存到 JSON 时“保留”事件,然后将它们绑定回loadFromJSON

In the link below I've created an element redBox and bonded an event "moving" on it.在下面的链接中,我创建了一个元素redBox并在其上绑定了一个“移动”事件。 After "restoring" canvas from JSON that event no longer available and it makes sense why...从 JSON“恢复”画布后,该事件不再可用,这是有道理的为什么......

The problem is, based on requirements, I have no idea what element could be in the JSON and what event was previously applied to it.问题是,根据要求,我不知道 JSON 中可能包含哪些元素以及之前对其应用了哪些事件。 Basically, I need dynamically apply all possible events on that particular element.基本上,我需要在该特定元素上动态应用所有可能的事件。

http://jsfiddle.net/redlive/rwdt6rwj/ http://jsfiddle.net/redlive/rwdt6rwj/

 fabric.util.object.extend(fabric.Image.prototype, { toObject: function() { return fabric.util.object.extend(this.callSuper('toObject'), { sanboxValues: this.get('sanboxValues'), imgSrc: this.get('imgSrc') } // name: this.get('name'), ); }, ddpLoadImage: function(imgSrc, sanboxValues){ this.setSrc(imgSrc, function(img){ const {scaleFactor} = sanboxValues; img.scale( 1 / scaleFactor ).setCoords(); img.set({ clipTo: function(ctx){ const {x, y, width, height, scaleFactor} = this.sanboxValues; ctx.rect( x * scaleFactor - width / 2, y * scaleFactor - height / 2, width * scaleFactor, height * scaleFactor ); } }); image.canvas.renderAll() }, { sanboxValues, imgSrc }); } }); let store; const canvas = new fabric.Canvas('paper'); const canvasOriginalSize = { width: 600, height: 600 }; const image = new fabric.Image('', { left: 50, top: 50, }); const redBox = new fabric.Rect({ left: 0, top: 0, width: 50, height: 50, fill: 'red' }); const page = new fabric.Rect({ left: 50, top: 50, width: 300, height: 300 }); canvas.add(page); canvas.add(image); canvas.add(redBox); canvas.renderAll(); canvas.on("object:modified", function(obj){ console.log(obj.target); }); redBox.on("moving", function(obj){ console.log('Moving redBox'); }); const scaleFactor = 1; const imgSrc = ['https://picsum.photos/', page.width * scaleFactor,'/', page.height * scaleFactor].join(''); const x = 10, y = 7, width = page.width, height = page.height; image.ddpLoadImage(imgSrc, {x, y, width, height, scaleFactor}); $("#save").on('click', function(){ store = canvas.toJSON(); console.log(store); }); $("#restore").on('click', function(){ canvas.loadFromJSON(store, function(){ canvas.getObjects().forEach((obj)=>{ if (obj.type === 'image') { obj.ddpLoadImage(obj.imgSrc, obj.sanboxValues); } }); canvas.renderAll(); }); });
 #paper { border: solid 1px red; }
 <script src="//cdnjs.cloudflare.com/ajax/libs/fabric.js/2.2.3/fabric.js"></script> <script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script> <img id="image" /> <canvas id="paper" width="400" height="400" style="border:1px solid #ccc"></canvas> <button id="save">Save to JSON</button> <button id="restore">Restore form JSON</button>

You have to again attach events to objects.您必须再次将事件附加到对象。 In loadFromJSON 3rd arguments which is reviver having object from json and fabric object.loadFromJSON第三个参数中,这是具有来自 json 和结构对象的对象的 reviver。 Add event to fabric objects.将事件添加到结构对象。

DEMO演示

 fabric.util.object.extend(fabric.Image.prototype, { toObject: function() { return fabric.util.object.extend(this.callSuper('toObject'), { sanboxValues: this.get('sanboxValues'), imgSrc: this.get('imgSrc') } // name: this.get('name'), ); }, ddpLoadImage: function(imgSrc, sanboxValues) { this.setSrc(imgSrc, function(img) { const { scaleFactor } = sanboxValues; img.scale(1 / scaleFactor).setCoords(); img.set({ clipTo: function(ctx) { const { x, y, width, height, scaleFactor } = this.sanboxValues; ctx.rect( x * scaleFactor - width / 2, y * scaleFactor - height / 2, width * scaleFactor, height * scaleFactor ); } }); image.canvas.renderAll() }, { sanboxValues, imgSrc }); } }); let store; const canvas = new fabric.Canvas('paper'); const canvasOriginalSize = { width: 600, height: 600 }; const image = new fabric.Image('', { left: 50, top: 50, }); const redBox = new fabric.Rect({ left: 0, top: 0, width: 50, height: 50, fill: 'red', rectType: 'eventedRect' }); const page = new fabric.Rect({ left: 50, top: 50, width: 300, height: 300 }); canvas.add(page,image,redBox); canvas.on("object:modified", function(obj) { console.log(obj.target); }); redBox.on("moving", rectMoving); function rectMoving(obj) { console.log('Moving redBox'); }; const scaleFactor = 1; const imgSrc = ['https://picsum.photos/', page.width * scaleFactor, '/', page.height * scaleFactor].join(''); const x = 10, y = 7, width = page.width, height = page.height; image.ddpLoadImage(imgSrc, { x, y, width, height, scaleFactor }); $("#save").on('click', function() { store = canvas.toJSON(['rectType']); console.log(store); }); $("#restore").on('click', function() { canvas.loadFromJSON(store, function() { canvas.renderAll(); },function(o,object){ if (object.rectType == 'eventedRect') { object.on("moving", rectMoving); } if (object.type === 'image') { object.ddpLoadImage(object.imgSrc, object.sanboxValues); } }); });
 #paper { border: solid 1px red; }
 <script src="//cdnjs.cloudflare.com/ajax/libs/fabric.js/2.2.3/fabric.js"></script> <script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script> <img id="image" /> <canvas id="paper" width="400" height="400" style="border:1px solid #ccc"></canvas> <button id="save">Save to JSON</button> <button id="restore">Restore form JSON</button>

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM