您好,登錄后才能下訂單哦!
使用fabric.js怎么實現(xiàn)一個明信片功能?針對這個問題,這篇文章詳細介紹了相對應(yīng)的分析和解答,希望可以幫助更多想解決這個問題的小伙伴找到更簡單易行的方法。
一、fabric.js是一個很好用的 canvas 操作插件
示例:pandas 是基于NumPy 的一種工具,該工具是為了解決數(shù)據(jù)分析任務(wù)而創(chuàng)建的。
二、代碼示例
代碼如下(示例):
<!DOCTYPE html> <html lang="en"> <head> <title>diy</title> <meta charset="utf-8"> <meta name="viewport" content="user-scalable=no, width=device-width, initial-scale=1, maximum-scale=1"> <meta http-equiv="Access-Control-Allow-Origin" content="*" /> <meta http-equiv="Expires" content="-1"> <meta http-equiv="Cache-Control" content="no-cache"> <meta http-equiv="Pragma" content="no-cache"> <script src="./js/jquery-3.4.1.min.js"></script> <script src="./js/fabric.js"></script> <script src="./js/customiseControls.min.js"></script> </head> <style> body{ margin: 0; padding: 0; border: 0; font-size: 100%; font-weight: normal; vertical-align: baseline; } .end{ position: fixed; top: 0; right: 0; width: 50px; height: 20px; background-color: #000000; color: #ffffff; font-size: 12px; line-height: 20px; z-index: 9999; } .canvasimg{ position: fixed; top: 0; left: 0; width: 50px; height: 20px; background-color: #000000; color: #ffffff; font-size: 12px; line-height: 20px; z-index: 9999; } .canvasimg input{ position: absolute; top: 0; left: 0; width: 100%; height: 100%; opacity: 0; } #inline-btn{ position: fixed; opacity: 0; z-index: 999; } #addinline-btn{ opacity: 0; position: fixed; z-index: 999; } .canvassrc{ position: fixed; top: 0; right: 0; width: 100%; height: 100%; z-index: 9999; } </style> <body> <div class="canvasimg"><input type="file" name="" id="canvasimg" class="canvasimgadd" type="file" accept="image/*" onchange="selectFileImage(this);" >添加圖片</div> <div class="end" onclick="linkcanvas()">生成圖片</div> <button id="inline-btn" onclick="canvasonclick()">刪除圖片按鈕</button> <button id="addinline-btn" onclick="copy()">復(fù)制圖片按鈕</button> <canvas id="c"></canvas> </body> </html> <script> //參考鏈接 //文末查看比較詳細的API中文解釋 //http://fabricjs.com/ fabric.js官網(wǎng) //diy功能需要有復(fù)制功能 刪除功能 放大縮小移動旋轉(zhuǎn) //添加新圖片 function selectFileImage(fileObj){ var file = fileObj.files['0']; var reader = new FileReader(); reader.readAsDataURL(file) reader.onload = function (e){ fabric.Image.fromURL(e.target.result, function (img) { img.scale(1).set({ left: webwidth - (webwidth / 2),//圖片左右居中 top: webheight - (webheight / 2), //圖片上下居中 ,屏幕高度-(圖片高度/2)的總值/2 angle: 0, //角度為0 originX: 'center', originY: 'center', }); //圖片默認寬度充滿屏幕一邊留白20 高度自適應(yīng) img.scaleToWidth(webwidth - 40) canvas.add(img).setActiveObject(img); //清除線條 img.hasBorders = false; //自定義圖片功能按鈕 , 隱藏多余功能按鈕,只保留4個角的按鈕 canvas.forEachObject(function (em) { em['setControlVisible']('mtr', false); em['setControlVisible']('mt', false); em['setControlVisible']('ml', false); em['setControlVisible']('mb', false); em['setControlVisible']('mr', false); em['setControlVisible']('mt', false); }) }); } } // 刪除按鈕 var btn = document.getElementById('inline-btn') // 添加按鈕 var addbtn = document.getElementById('addinline-btn') // 獲取屏幕高寬度 var webwidth = $(window).width() var webheight = $(window).height() //創(chuàng)建畫板 var canvas = new fabric.Canvas('c'); //canvas默認充滿屏幕 canvas.setWidth(webwidth) canvas.setHeight(webheight) //導(dǎo)入圖片 fabric.Image.fromURL('./imgs/2.jpg', function (img) { img.scale(1).set({ left: webwidth - (webwidth/2),//圖片左右居中 top: webheight-(webheight/2), //圖片上下居中 ,屏幕高度-(圖片高度/2)的總值/2 angle: 0, //角度為0 originX: 'center', originY: 'center', }); //圖片默認寬度充滿屏幕一邊留白20 高度自適應(yīng) img.scaleToWidth(webwidth-40) canvas.add(img).setActiveObject(img); //清除線條 img.hasBorders = false; //自定義圖片功能按鈕 , 隱藏多余功能按鈕,只保留4個角的按鈕 canvas.forEachObject(function(em){ em['setControlVisible']('mtr', false); em['setControlVisible']('mt', false); em['setControlVisible']('ml', false); em['setControlVisible']('mb', false); em['setControlVisible']('mr', false); em['setControlVisible']('mt', false); }) }); //取消多選 canvas.selection = false; //新建圖層不出現(xiàn)在頂層 canvas.preserveObjectStacking = true; //注:要自定義修改按鈕功能需要引入fabric的另一個叫customiseControls的JS插件 否則無法操作 //全局修改4個按鈕的功能 fabric.Canvas.prototype.customiseControls({ bl: { action: 'rotate' //添加圖片旋轉(zhuǎn)功能 }, // only is hasRotatingPoint is not set to false }, function () { canvas.renderAll(); }); //因為默認的按鈕樣式不是我們想要的 所以需要自定義一些icon在上面 fabric.Object.prototype.customiseCornerIcons({ tl: { icon: './img/+1@2x.png', //圖片路徑 cornerSize: 70, //按鈕點擊范圍 相當(dāng)于css的padding屬性 settings: { cornerSize: 25 //icon大小 }, }, tr: { icon: './img/X@2x.png', cornerSize: 70, settings: { cornerSize: 25 }, }, bl: { icon: './img/xuanzhuan@2x.png', cornerSize: 70, settings: { cornerSize: 25 }, }, br: { icon: './img/fangda@2x.png', cornerSize: 70, settings: { cornerSize: 25 }, }, }, function () { canvas.renderAll(); }); //按鈕跟隨圖片定位 function positionBtn(obj) { //獲取當(dāng)前選中圖片單位參數(shù) var absCoords = canvas.getAbsoluteCoords(obj); btn.style.width = '30px'; btn.style.height = '30px'; btn.style.opacity = '0'; btn.style.left = (absCoords.right - 30 / 2) + 'px'; btn.style.top = (absCoords.top - 30 / 2) + 'px'; addbtn.style.width = '30px'; addbtn.style.height = '30px'; addbtn.style.opacity = '0'; addbtn.style.left = (absCoords.left - 30 / 2) + 'px'; addbtn.style.top = (absCoords.leftTop - 30 / 2) + 'px'; } fabric.Canvas.prototype.getAbsoluteCoords = function (object) { return { right: object.aCoords.tr.x + this._offset.left, top:object.aCoords.tr.y + this._offset.top, left: object.aCoords.tl.x + this._offset.left, leftTop: object.aCoords.tl.y + this._offset.top, }; } //刪除當(dāng)前選中圖片 function canvasonclick(){ var t = canvas.getActiveObject() canvas.remove(t); } //拷貝當(dāng)前選中圖片 function copy(){ var _self = this; canvas.getActiveObject().clone(function (cloned) { _self.paste(cloned); canvas.discardActiveObject().renderAll() }) } function paste(_clipboard){ console.log(_clipboard) var t = canvas.getActiveObject(); // 再次克隆,這樣你就可以復(fù)制多個副本。 t.clone(function (clonedObj) { canvas.discardActiveObject(); clonedObj.set({ left: clonedObj.left + 20, top: clonedObj.top + 20, evented: true, hasBorders:false }); if (clonedObj.type === 'activeSelection') { // 活動選擇需要對畫布的引用。 clonedObj.canvas = canvas; clonedObj.forEachObject(function (obj) { canvas.add(obj); canvas.forEachObject(function (em) { em['setControlVisible']('mtr', false); em['setControlVisible']('mt', false); em['setControlVisible']('ml', false); em['setControlVisible']('mb', false); em['setControlVisible']('mr', false); em['setControlVisible']('mt', false); }) }); // 解決不可選擇的問題 clonedObj.setCoords(); } else { canvas.add(clonedObj); canvas.forEachObject(function (em) { em['setControlVisible']('mtr', false); em['setControlVisible']('mt', false); em['setControlVisible']('ml', false); em['setControlVisible']('mb', false); em['setControlVisible']('mr', false); em['setControlVisible']('mt', false); }) } }); } var store = {} //計算平均值 var getDistance = function (start, stop) { return Math.hypot(stop.x - start.x, stop.y - start.y); }; //監(jiān)聽positionBtn事件 鼠標以上點擊圖片時移動時觸發(fā)我們自定義的復(fù)制按鈕和刪除按鈕跟隨圖片定位以及雙指放大縮小功能 canvas.on('mouse:down',function(options){ //判斷是否點擊到了圖片單位 if(options.target){ //運行事件 positionBtn(options.target); //雙指放大縮小 store.pageX = options.e.changedTouches[0].clientX store.pageY = options.e.changedTouches[0].clientY if (options.e.changedTouches.length == 2) { store.pageY2 = options.e.changedTouches[1].clientY store.pageX2 = options.e.changedTouches[1].clientX } store.originScale = options.target.scaleX || 0.5; store.originleft = options.target.left; store.origintop = options.target.top; } }); canvas.on('mouse:move',function(options){ if(options.target){ positionBtn(options.target); if (options.e.changedTouches.length == 2) { if (!store.pageX2) { store.pageX2 = options.e.changedTouches[1].clientX } if (!store.pageY2) { store.pageY2 = options.e.changedTouches[1].clientY } var zoom = getDistance({ x: options.e.changedTouches[0].clientX, y: options.e.changedTouches[0].clientY }, { x: options.e.changedTouches[1].clientX, y: options.e.changedTouches[1].clientY }) / getDistance({ x: store.pageX, y: store.pageY }, { x: store.pageX2, y: store.pageY2 }); var newScale = store.originScale * zoom; if (newScale > 3) { newScale = 3; } options.target.scaleX = newScale; options.target.scaleY = newScale; canvas.renderAll(); } } }); canvas.on('mouse:up',function(options){ if(options.target){ positionBtn(options.target); store.pageY = 0 store.pageX = 0 store.pageY2 = 0 store.pageX2 = 0 store.originScale = options.target.scaleX store.originleft = options.target.left store.origintop = options.target.top } }); //生成明信片 function linkcanvas(){ let xheight = $('#c').height() let xwidth = $('#c').width() canvas.setBackgroundColor('rgba(255, 255, 255, 1)', canvas.renderAll.bind(canvas)); var exportedArt = this.canvas.toDataURL({ format: "jpeg", quality: 1.0, multiplier: 2.4, left: 0, top: 0, width: xwidth, height: xheight, }); $('body').append(`<img class="canvassrc" src="${exportedArt}"/>`) } </script>
關(guān)于使用fabric.js怎么實現(xiàn)一個明信片功能問題的解答就分享到這里了,希望以上內(nèi)容可以對大家有一定的幫助,如果你還有很多疑惑沒有解開,可以關(guān)注億速云行業(yè)資訊頻道了解更多相關(guān)知識。
免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點不代表本網(wǎng)站立場,如果涉及侵權(quán)請聯(lián)系站長郵箱:is@yisu.com進行舉報,并提供相關(guān)證據(jù),一經(jīng)查實,將立刻刪除涉嫌侵權(quán)內(nèi)容。