function desEncrypt(str, key = 'df6a551ca43181fc485f3043bcdd2fbc') { var APIFMS try { var keyHex_encrypt = CryptoJS.enc.Utf8.parse(key) var encrypted = CryptoJS.DES.encrypt(str, keyHex_encrypt, { mode: CryptoJS.mode.ECB, padding: CryptoJS.pad.Pkcs7 }) APIFMS = CryptoJS.enc.Base64.stringify(encrypted.ciphertext) } catch (err) { console.log('des 加密 -------------------------') console.log(err) } return APIFMS } (function (fabric) { fabric.CurvedText = fabric.util.createClass(fabric.Object, { type: 'curved-text', diameter: 250, kerning: 0, text: '', flipped: false, fill: '#000', fontFamily: 'Times New Roman', fontSize: 24, // in px fontWeight: 'normal', fontStyle: '', // "normal", "italic" or "oblique". cacheProperties: fabric.Object.prototype.cacheProperties.concat('diameter', 'textBackgroundColor', 'kerning', 'flipped', 'fill', 'fontFamily', 'fontSize', 'fontWeight', 'fontStyle', 'strokeStyle', 'strokeWidth'), strokeStyle: null, strokeWidth: 0, initialize: function (text, options) { options || (options = {}); if (typeof text === 'object' && text) { for (let key in text) { this[key] = text[key] } } else { this.text = text; } this.callSuper('initialize', options); this.set('lockUniScaling', true); var canvas = this.getCircularText(); this.cropCanvas(canvas); this.set('width', canvas.width); this.set('height', canvas.height); }, _getFontDeclaration: function () { return [ (fabric.isLikelyNode ? this.fontWeight : this.fontStyle), (fabric.isLikelyNode ? this.fontStyle : this.fontWeight), this.fontSize + 'px', (fabric.isLikelyNode ? ('"' + this.fontFamily + '"') : this.fontFamily) ].join(' '); }, cropCanvas: function (canvas) { var ctx = canvas.getContext('2d'), w = canvas.width, h = canvas.height, pix = { x: [], y: [] }, n, imageData = ctx.getImageData(0, 0, w, h), fn = function (a, b) { return a - b }; for (var y = 0; y < h; y++) { for (var x = 0; x < w; x++) { if (imageData.data[((y * w + x) * 4) + 3] > 0) { pix.x.push(x); pix.y.push(y); } } } // 如果没有找到任何非透明像素,直接返回,不进行裁剪 if (pix.x.length === 0 || pix.y.length === 0) { return; } pix.x.sort(fn); pix.y.sort(fn); n = pix.x.length - 1; w = pix.x[n] - pix.x[0]; h = pix.y[n] - pix.y[0]; // 确保宽度和高度是有效的正数 if (w <= 0 || h <= 0 || isNaN(w) || isNaN(h)) { return; } var cut = ctx.getImageData(pix.x[0], pix.y[0], w, h); canvas.width = w; canvas.height = h; ctx.putImageData(cut, 0, 0); }, getCircularText: function () { var text = this.text, diameter = this.diameter, flipped = this.flipped, kerning = this.kerning, fill = this.fill, inwardFacing = true, startAngle = 0, canvas = fabric.util.createCanvasElement(), ctx = canvas.getContext('2d'), cw, // character-width x, // iterator clockwise = -1; // draw clockwise for aligned right. Else Anticlockwise if (flipped) { // startAngle = 180; inwardFacing = false; } startAngle *= Math.PI / 180; // convert to radians var d = document.createElement('div'); d.style.fontFamily = this.fontFamily; d.style.fontSize = this.fontSize + 'px'; d.style.fontWeight = this.fontWeight; d.style.fontStyle = this.fontStyle; d.textContent = text; document.body.appendChild(d); var textHeight = d.offsetHeight; document.body.removeChild(d); canvas.width = canvas.height = diameter; ctx.font = this._getFontDeclaration(); if (inwardFacing) { text = text.split('').reverse().join('') }; ctx.translate(diameter / 2, diameter / 2); // Move to center startAngle += (Math.PI * !inwardFacing); // Rotate 180 if outward ctx.textBaseline = 'middle'; // Ensure we draw in exact center ctx.textAlign = 'center'; // Ensure we draw in exact center for (x = 0; x < text.length; x++) { cw = ctx.measureText(text[x]).width; startAngle += ((cw + (x == text.length - 1 ? 0 : kerning)) / (diameter / 2 - textHeight)) / 2 * -clockwise; } ctx.rotate(startAngle); for (x = 0; x < text.length; x++) { cw = ctx.measureText(text[x]).width; // half letter ctx.rotate((cw / 2) / (diameter / 2 - textHeight) * clockwise); if (this.strokeStyle && this.strokeWidth) { ctx.strokeStyle = this.strokeStyle; ctx.lineWidth = this.strokeWidth; ctx.miterLimit = 2; ctx.strokeText(text[x], 0, (inwardFacing ? 1 : -1) * (0 - diameter / 2 + textHeight / 2)); } ctx.fillStyle = fill; ctx.fillText(text[x], 0, (inwardFacing ? 1 : -1) * (0 - diameter / 2 + textHeight / 2)); ctx.rotate((cw / 2 + kerning) / (diameter / 2 - textHeight) * clockwise); // rotate half letter } return canvas; }, _set: function (key, value) { switch (key) { case 'scaleX': this.fontSize *= value; this.diameter *= value; this.width *= value; this.scaleX = 1; if (this.width < 1) { this.width = 1; } break; case 'scaleY': this.height *= value; this.scaleY = 1; if (this.height < 1) { this.height = 1; } break; default: this.callSuper('_set', key, value); break; } }, _render: function (ctx) { var canvas = this.getCircularText(); this.cropCanvas(canvas); this.set('width', canvas.width); this.set('height', canvas.height); ctx.drawImage(canvas, -this.width / 2, -this.height / 2, this.width, this.height); this.setCoords(); }, toObject: function (propertiesToInclude) { return this.callSuper('toObject', ['text', 'diameter', 'textBackgroundColor', 'kerning', 'flipped', 'fill', 'fontFamily', 'fontSize', 'fontWeight', 'fontStyle', 'strokeStyle', 'strokeWidth'].concat(propertiesToInclude)); } }); fabric.CurvedText.fromObject = function (object, callback, forceAsync) { return fabric.Object._fromObject('CurvedText', object, callback, forceAsync, 'curved-text'); }; })(typeof fabric !== 'undefined' ? fabric : require('fabric').fabric); const remote = require('@electron/remote') var path = require('path'); // 使用用户数据目录,避免写入需要管理员权限 const exePath = remote.app.getPath('userData') const { ipcRenderer } = require('electron') const { dialog } = require('@electron/remote') var jrQrcode = require('jr-qrcode') var JsBarcode = require('jsbarcode') ipcRenderer.send('get-sys-fonts') ipcRenderer.send('get-scale-rate') const { clipboard } = require('electron') const dpi = 300 // 内部剪贴板 let clipboardData = { objects: null, offset: 10 // 粘贴位置偏移量 }; //var encrypt = new JSEncrypt(); //encrypt.setPublicKey(`-----BEGIN PUBLIC KEY----- //MIGdMA0GCSqGSIb3DQEBAQUAA4GLADCBhwKBgQDAbKQ46WevL9PapJ+AlZqSzczkTovu7STH //FmZmIJcNrwPPEWRR2PliUvtS28V+gNMWlu3wNWFAS5KGDbTtndIrP3hnlp9BDIcAcdNuJUM7 //yJfAYBhtkqvj45Orvdd2RYRxhkQb34uTNXpM+biMH6Wd0wykNb9/VBNM0C12KswEdwIBEQ== //-----END PUBLIC KEY-----`); layui.use(['layer', 'slider', 'form', 'colorpicker'], function () { let myDate = new Date() let s_lan = '' ipcRenderer.send('get-sys-language') /* if(myDate.getFullYear()>2021 && myDate.getMonth() >= 1 && myDate.getDate() > 15){ }*/ function GetFile() { const params = new URLSearchParams(window.location.search); return params } function langua_ge(lan = 'zh') { $("[language='m']").each(function (i) { $(this).html($(this).attr(lan)) }) $("[language='t']").each(function (i) { $(this).attr('title', $(this).attr(lan)) }) } function language_str(str) { let t = { whetherSave: { zh: '是否保存当前文件?', ozh: '是否保存當前文件?', en: 'Do you want to save the current file?' }, save: { zh: '保存', ozh: '保存', en: 'Save' }, noSave: { zh: '不保存', ozh: '不保存', en: 'No saving' }, cancel: { zh: '取消', ozh: '取消', en: 'Cancel' }, saveSucc: { zh: '保存成功至', ozh: '保存成功至', en: 'Save successfully to' }, saveFile: { zh: '保存文件', ozh: '保存文件', en: 'Save file' }, display: { zh: '预览', ozh: '預覽', en: 'Display' }, output: { zh: '导出', ozh: '導出', en: 'Export' }, bg: { zh: '背景', ozh: '背景', en: 'Background' }, selectPic: { zh: '请选择图片', ozh: '請選擇圖片', en: 'Please select a picture' }, selectPic: { zh: '请选择文件', ozh: '請選擇文件', en: 'Please select a file' }, img: { zh: '圖片', ozh: '圖片', en: 'Image' }, simg: { zh: '合成圖片', ozh: '合成圖片', en: 'Synthesized Image' }, text: { zh: '文本', ozh: '文本', en: 'Text' }, "ctext": { zh: "圆形文本", ozh: "圆形文本", en: "Circle Text" }, stext: { zh: '合成文本', ozh: '合成文本', en: 'Synthesized Text' }, rect: { zh: '矩形', ozh: '矩形', en: 'Rectangle' }, circ: { zh: '圓形', ozh: '圓形', en: 'Circle' }, line: { zh: '直線', ozh: '直線', en: 'Line' }, qrc: { zh: '二維碼', ozh: '二維碼', en: 'QR code' }, barc: { zh: '條形碼', ozh: '條形碼', en: 'Barcode' }, counter: { zh: '計數器', ozh: '计数器', en: 'Counter' }, about: { zh: '关于Soon Design', ozh: '關於Soon Design', en: 'About Soon Design' }, vers: { zh: '版本', ozh: '版本', en: 'Version' }, comf: { zh: '确认', ozh: '確認', en: 'Select' }, copyright: { zh: "© 2022 cardsoon Co., Ltd. All rights reserved.", ozh: "© 2022 cardsoon Co., Ltd. All rights reserved.", en: "© 2022 cardsoon Co., Ltd. All rights reserved." } } return t[str][s_lan] } var $ = layui.$ var layer = layui.layer, slider = layui.slider, colorpicker = layui.colorpicker let addState = 0 //0是不添加 let background_image, background_image1, background_image2 let bg_version = 1 //front_bg1.png front_bg2.png var zoom = 0 $('#canvas1').attr('height', document.body.clientHeight - 100) $('#canvas2').attr('height', document.body.clientHeight - 100) $('#object_attribute').css('height', '470px') $('#obj_list').css('height', document.body.clientHeight - 520) $('.obj_list').css('height', $('#obj_list').height() - 32) $('.main').show() $('#canvas1').attr('width', $('#canvas-div').width()) $('#canvas2').attr('width', $('#canvas-div').width()) var openAs = { _name: '', set name(val) { if (val == '') { $('title').html('Soon Design') } else { $('title').html('Soon Design - ' + val) } this._name = val }, get name() { return this._name } } //被打开的文件名 let objs1 = [] let objs2 = [] let step1 = { val: 0 }, step2 = { val: 0 } let step = step1 let objs = objs1 let recordJson1 = [], recordJson2 = [], recordJson = recordJson1, recordObjs1 = [], recordObjs2 = [], recordObjs = recordObjs1 let pre_objs1 = [], pre_objs2 = [], next_objs1 = [], next_objs2 = [], pre_objs = pre_objs1, next_objs = next_objs1 let pre_json1 = [], pre_json2 = [], next_json1 = [], next_json2 = [], pre_json = pre_json1, next_json = next_json1 var canvas1 = new fabric.Canvas('canvas1') var canvas2 = new fabric.Canvas('canvas2') fabric.Object.prototype.objectCaching = false var ctx1 = canvas1.getSelectionContext() var ctx2 = canvas2.getSelectionContext() let is_bgi_add = false canvas1.zoomToPoint(new fabric.Point(canvas1.width / 2, canvas1.height / 2), $('#canvas-div').width() / 1200 > 1 ? 1 : $('#canvas-div').width() / 1200) //console.log(canvas1.width / 2, canvas1.height / 2); //console.log($("#canvas-div").width() / 1200 > 1 ? 1 : $("#canvas-div").width() / 1200); canvas2.zoomToPoint(new fabric.Point(canvas2.width / 2, canvas2.height / 2), $('#canvas-div').width() / 1200 > 1 ? 1 : $('#canvas-div').width() / 1200) zoom = $('#canvas-div').width() / 1200 > 1 ? 1 : $('#canvas-div').width() / 1200 // 初始化标尺 initRulers(); $('#source_front').width(zoom * $('#source_front').width()) $('#source_back').width(zoom * $('#source_back').width()) $('.canvas-container:eq(1)').hide() var canvas = canvas1 fabric.Object.prototype.set({ borderColor: '#9013FE', cornerColor: '#9013FE', //激活状态角落图标的填充颜色 cornerStrokeColor: '#9013FE', //激活状态角落图标的边框颜色 borderOpacityWhenMoving: 1, borderScaleFactor: 1, cornerSize: 6, cornerStyle: 'circle', //rect,circle centeredScaling: false, //角落放大缩小是否是以图形中心为放大原点 centeredRotation: true, //旋转按钮旋转是否是左上角为圆心旋转 transparentCorners: false, //激活状态角落的图标是否透明 rotatingPointOffset: 20, //旋转距旋转体的距离 padding: 0 }) canvas1.preserveObjectStacking = true canvas2.preserveObjectStacking = true var front_list = [] ipcRenderer.on('font-list', (event, data) => { const newFontList = [] data.map((item) => { if (item.indexOf('"') === 0) { newFontList.push(item.replace(/^"|"$/g, '')) } else { newFontList.push(item) } }) front_list = newFontList for (let item of front_list) { $('#text_font_family').append("') $("#circle_text_font_family").append(""); $('#out_text_font_family').append("') $('#barcode_font_family').append("') $('#count_font_family').append("') } }) ipcRenderer.on('sys-lan', (event, data) => { let lang = localStorage.getItem('lang') if (lang) { s_lan = lang langua_ge(lang) $('#language_select').val(lang) return } switch (data) { case 'zh-CN': s_lan = 'zh' langua_ge('zh') $('#language_select').val('zh') localStorage.setItem('lang', 'zh') break case 'zh': s_lan = 'zh' langua_ge('zh') $('#language_select').val('zh') localStorage.setItem('lang', 'zh') break case 'zh-TW': s_lan = 'ozh' langua_ge('ozh') $('#language_select').val('ozh') localStorage.setItem('lang', 'ozh') break case 'en': s_lan = 'en' langua_ge('en') $('#language_select').val('en') localStorage.setItem('lang', 'en') break case 'en-AU': s_lan = 'en' langua_ge('en') $('#language_select').val('en') localStorage.setItem('lang', 'en') break case 'en-CA': s_lan = 'en' langua_ge('en') $('#language_select').val('en') localStorage.setItem('lang', 'en') break case 'en-GB': s_lan = 'en' langua_ge('en') $('#language_select').val('en') localStorage.setItem('lang', 'en') break case 'en-NZ': s_lan = 'en' langua_ge('en') $('#language_select').val('en') localStorage.setItem('lang', 'en') break case 'en-US': s_lan = 'en' langua_ge('en') $('#language_select').val('en') localStorage.setItem('lang', 'en') break case 'en-ZA': s_lan = 'en' langua_ge('en') $('#language_select').val('en') localStorage.setItem('lang', 'en') break } }) ipcRenderer.on('close', (event, message) => { layer.confirm( '' + language_str('whetherSave') + '', { //是否保存当前文件? btn: [language_str('save'), language_str('noSave'), language_str('cancel')], //['保存', '不保存', '取消'] btn3: function (index, layero) { } }, function (index, layero) { output(() => ipcRenderer.send('run-close')) return let j = canvas1.toJSON(['selectable', 'hoverable', 'hoverCursor', 'text', 'fontStyle', 'fontWeight', 'underline']) let b = canvas2.toJSON(['selectable', 'hoverable', 'hoverCursor', 'text', 'fontStyle', 'fontWeight', 'underline']) let _g1 = [], _g2 = [] let left = 0, top = 0 for (let _o of canvas1.getObjects()) { if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(_o.getCoords()) > left) { left = -(getCoordsMinX(_o.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(_o.getCoords()) > top) { top = -(getCoordsMinY(_o.getCoords()) - getCoordsMinY(background_image.getCoords())) } _g1.push(fabric.util.object.clone(_o)) } let fp = new fabric.Group(_g1).toDataURL({ height: 648, width: 1012, top: top / zoom, left: left / zoom }) ; (left = 0), (top = 0) for (let _o of canvas2.getObjects()) { if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(_o.getCoords()) > left) { left = -(getCoordsMinX(_o.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(_o.getCoords()) > top) { top = -(getCoordsMinY(_o.getCoords()) - getCoordsMinY(background_image.getCoords())) } _g2.push(fabric.util.object.clone(_o)) } //let fp = new fabric.Group(_g1).toDataURL(); let bp = new fabric.Group(_g2).toDataURL({ height: 648, width: 1012, top: top / zoom, left: left / zoom }) let o = { f: j, b: b, fo: objs1, bo: objs2, fp: fp, bp: bp } if (openAs.name != '') { //打开的文件 let fs = require('fs') o.soonType = 2 fs.writeFileSync(openAs.name, JSON.stringify(o)) layer.msg(language_str('saveSucc') + openAs.name) //'保存成功至' saveHistory() ipcRenderer.send('run-close') return } dialog .showSaveDialog({ title: language_str('saveFile'), //'保存文件' filters: [{ name: 'Soon File Type', extensions: ['soon'] }] }) .then((result) => { if (result.filePath == '') { ipcRenderer.send('run-close') return } if (result.filePath.substring(result.filePath.length - 5).indexOf('.') == -1) { result.filePath += '.soon' } let fs = require('fs') o.soonType = 2 fs.writeFileSync(result.filePath, JSON.stringify(o)) openAs.name = result.filePath layer.msg(language_str('saveSucc') + openAs.name) //保存成功至 saveHistory() ipcRenderer.send('run-close') }) .catch((err) => { console.log() }) layer.close(index) }, function (index) { ipcRenderer.send('run-close') } ) }) addBackground() //添加背景 白色卡片 initAligningGuidelines(canvas1) initAligningGuidelines(canvas2) //canvas.setZoom(0.5) //recordObjs1.push(JSON.stringify(objs1)); //recordJson1.push(canvas1.toJSON(["selectable","hoverable","hoverCursor","text","fontStyle","fontWeight","underline"])); //recordObjs2.push(JSON.stringify(objs2)); //recordJson2.push(canvas2.toJSON(["selectable","hoverable","hoverCursor","text","fontStyle","fontWeight","underline"])); canvas.renderAll() //重新渲染画布 var zoomSlider = slider.render({ elem: '#zoomSlide', //绑定元素 min: 25, max: 500, value: 100, change(val) { canvas.zoomToPoint(new fabric.Point(canvas.width / 2, canvas.height / 2), val / 100) zoom = val / 100 //$(".canvas-container").css("transform","scale(" + val / 100 + ")") } }) window.rotate = function (id) { let angle = $(`#${id}`).attr('angle') - 0 angle += 90 $(`#${id}`).css('transform', `rotate(${angle}deg)`) $(`#${id}`).attr('angle', angle) } $('#display').on('click', function () { // 类型改变 fabric.Image.fromURL('./public/images/front_bg' + bg_version + '_2.png', function (i1) { i1.left = background_image.left i1.top = background_image.top let img1 = i1 fabric.Image.fromURL('./public/images/back_bg_2.png', function (i2) { i2.left = background_image.left i2.top = background_image.top let img2 = i2 fabric.Image.fromURL('./public/images/op_2.png', function (i3) { i2.left = background_image.left i2.top = background_image.top let img3 = i3 display_func(img1, img2, img3) }) }) }) }) // 导出文件 async function savePdf(buffer) { let fs = require('fs'); // 弹出保存对话框 const { canceled, filePath } = await dialog.showSaveDialog({ title: '保存文件', defaultPath: path.join(exePath, 'output.pdf'), // 默认路径 filters: [{ name: 'PDF 文件', extensions: ['pdf'] }] // 文件过滤器 }); if (canceled) { console.log('用户取消了保存操作'); return; } // 将Buffer写入PNG文件到用户选择的路径 fs.writeFile(filePath, buffer, (err) => { if (err) { console.error('写入文件失败:', err); } else { layer.msg(language_str("saveSucc") + filePath);//'保存成功至' console.log('PNG文件已保存至:', filePath); } }); } function display_func(img1, img2, img3) { $('#base_control').hide() $('#line_control').hide() $('#pic_control').hide() $("#set_bg").hide(); $('#out_pic_control').hide() $('#text_control').hide() $('#circle_text_control').hide() $('#out_text_control').hide() $('#rect_control').hide() $('#circle_control').hide() $('#counter_control').hide() $('#qrcode_Controll').hide() $('#barcode_controll').hide() $('#component_type').text(language_str('bg')) //"背景" canvas1.discardActiveObject().renderAll() canvas2.discardActiveObject().renderAll() let _objs1 = canvas1.getObjects() let g1 = [] let g3 = [] let g5 = [] let left = 0 //左裁剪 let top = 0 //顶裁剪 let black_left = 0 //黑色左裁剪 let black_top = 0 //黑色顶裁剪 let all_left = 0 //预览图左裁剪 let all_top = 0 //预览图顶裁剪 for (let item of _objs1) { let idx = getIndex(item, canvas1) //console.log("------"); //console.log(item.getCoords()); //console.log(getCoordsMinX(background_image.getCoords())); //console.log(getCoordsMinX(item.getCoords())); //console.log(getCoordsMinX(background_image.getCoords()) - getCoordsMinX(item.getCoords())); //console.log("------"); if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(item.getCoords()) > all_left) { all_left = -(getCoordsMinX(item.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(item.getCoords()) > all_top) { all_top = -(getCoordsMinY(item.getCoords()) - getCoordsMinY(background_image.getCoords())) } g3.push(fabric.util.object.clone(item)) if (idx != 0 && (objs1[idx - 1].type == 10 || objs1[idx - 1].type == 4)) { continue //计数器 或 合成文字 } if (idx != 0 && (objs1[idx - 1].type == 8 || objs1[idx - 1].type == 9)) { continue //二维码 条形码 } if (idx != 0 && objs1[idx - 1].type == 2) { continue //合成图片 } if ( idx != 0 && ((objs1[idx - 1].type == 3 && (item.get('fill') == '#000000' || (item.get('fill') == '#ffffff' && false))) || ( objs1[idx - 1].type == 11 && (item.get("fill") == "#000000" || (item.get("fill") == "#ffffff" && false)) //圆形文字 && 黑色 ) || //文字 && 黑色 (objs1[idx - 1].type == 5 && //矩形 (((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && item.get('stroke') == '') || //黑填充 透明边框 (item.get('fill') == '' && (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || //透明填充 黑边框 ((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || //黑填充 黑边框 ((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && item.get('strokeWidth') == 0))) || //黑填充 0边框 (objs1[idx - 1].type == 6 && //圆形 (((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && item.get('stroke') == '') || //黑填充 透明边框 (item.get('fill') == '' && (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || //透明填充 黑边框 ((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || //黑填充 黑边框 ((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && item.get('strokeWidth') == 0))) || //黑填充 0边框 (objs1[idx - 1].type == 7 && //直线 (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || objs1[idx - 1].black == true) //勾选并入黑色图层 // ( // objs1[idx-1].type == 1//固定图片 // && // objs1[idx-1].black == true //勾选并入黑色图层 // ) ) { if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(item.getCoords()) > black_left) { black_left = -(getCoordsMinX(item.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(item.getCoords()) > black_top) { black_top = -(getCoordsMinY(item.getCoords()) - getCoordsMinY(background_image.getCoords())) } g5.push(fabric.util.object.clone(item)) continue //黑色文字 黑色矩形 黑色线条 黑色圆形 } else if (idx == 0) { g5.push(fabric.util.object.clone(item)) } if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(item.getCoords()) > left) { left = -(getCoordsMinX(item.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(item.getCoords()) > top) { top = -(getCoordsMinY(item.getCoords()) - getCoordsMinY(background_image.getCoords())) } g1.push(fabric.util.object.clone(item)) } let url1 = new fabric.Group(g1).toDataURL({ height: 648, width: 1012, top: top / zoom, left: left / zoom }) // g3.push(img1) let url3 = new fabric.Group(g3).toDataURL({ height: 648, width: 1012, top: all_top / zoom, left: all_left / zoom }) let url5 = new fabric.Group(g5).toDataURL({ height: 648, width: 1012, top: black_top / zoom, left: black_left / zoom }) let _objs2 = canvas2.getObjects() let g2 = [] let g4 = [] let g6 = [] left = 0 top = 0 black_top = 0 black_left = 0 all_top = 0 all_left = 0 for (let item of _objs2) { let idx = getIndex(item, canvas2) if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(item.getCoords()) > all_left) { all_left = -(getCoordsMinX(item.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(item.getCoords()) > all_top) { all_top = -(getCoordsMinY(item.getCoords()) - getCoordsMinY(background_image.getCoords())) } g4.push(fabric.util.object.clone(item)) if (idx != 0 && (objs2[idx - 1].type == 10 || objs2[idx - 1].type == 4)) { continue //黑色字或计数器 或 合成文字 } if (idx != 0 && (objs2[idx - 1].type == 8 || objs2[idx - 1].type == 9)) { continue //二维码 条形码 } if (idx != 0 && objs2[idx - 1].type == 2) { continue //合成图片 } if (idx != 0 && objs2[idx - 1].type == 10) { continue //合成图片 } if ( idx != 0 && ((objs2[idx - 1].type == 3 && (item.get('fill') == '#000000' || (item.get('fill') == '#ffffff' && false))) || ( objs2[idx - 1].type == 11 && (item.get("fill") == "#000000" || (item.get("fill") == "#ffffff" && false)) //圆形文字 && 黑色 ) || //文字 && 黑色 (objs2[idx - 1].type == 5 && //矩形 (((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && item.get('stroke') == '') || //黑填充 透明边框 (item.get('fill') == '' && (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || //透明填充 黑边框 ((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || //黑填充 黑边框 ((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && item.get('strokeWidth') == 0))) || //黑填充 0边框 (objs2[idx - 1].type == 6 && //圆形 (((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && item.get('stroke') == '') || //黑填充 透明边框 (item.get('fill') == '' && (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || //透明填充 黑边框 ((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || //黑填充 黑边框 ((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && item.get('strokeWidth') == 0))) || //黑填充 0边框 (objs2[idx - 1].type == 7 && //直线 (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || objs2[idx - 1].black == true) //勾选并入黑色图层 // ( // objs2[idx-1].type == 1//固定图片 // && // objs2[idx-1].black == true //勾选并入黑色图层 // ) ) { if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(item.getCoords()) > black_left) { black_left = -(getCoordsMinX(item.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(item.getCoords()) > black_top) { black_top = -(getCoordsMinY(item.getCoords()) - getCoordsMinY(background_image.getCoords())) } g6.push(fabric.util.object.clone(item)) continue //黑色文字 黑色矩形 黑色线条 黑色圆形 } else if (idx == 0) { g6.push(fabric.util.object.clone(item)) } if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(item.getCoords()) > left) { left = -(getCoordsMinX(item.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(item.getCoords()) > top) { top = -(getCoordsMinY(item.getCoords()) - getCoordsMinY(background_image.getCoords())) } g2.push(fabric.util.object.clone(item)) } let url2 = new fabric.Group(g2).toDataURL({ height: 648, width: 1012, top: top / zoom, left: left / zoom }) let white_url1 = canvas1.getObjects()[0].toDataURL({ height: 648, width: 1012 }) // g4.push(img2) let url4 = new fabric.Group(g4).toDataURL({ height: 648, width: 1012, top: all_top / zoom, left: all_left / zoom }) let url6 = new fabric.Group(g6).toDataURL({ height: 648, width: 1012, top: black_top / zoom, left: black_left / zoom }) let white_url2 = canvas2.getObjects()[0].toDataURL({ height: 648, width: 1012 }) //console.log(canvas.getObjects()) let w = document.body.clientWidth * 0.7 + 'px' let h = (document.body.clientWidth * 0.7 - 40 - 0.06 * document.body.clientWidth * 0.7) * 0.62548 + 150 + 'px' let h1 = (document.body.clientWidth * 0.7 - 40 - 0.06 * document.body.clientWidth * 0.7) * 0.62548 + 'px' if ((document.body.clientWidth * 0.7 - 40 - 0.06 * document.body.clientWidth * 0.7) * 0.62548 > document.body.clientHeight) { //高度超出,则按高度计算 h = document.body.clientHeight * 0.8 + 'px' h1 = document.body.clientHeight * 0.8 - 150 + 'px' w = ((document.body.clientHeight * 0.8 - 150) / 0.62548 + 40) / 0.94 } let fs = require('fs'); const Buffer = require('buffer').Buffer; const buffer3 = Buffer.from(url3.replace(/^data:image\/\w+;base64,/, ""), 'base64'); const printPath3 = path.join(exePath, 'print3.png'); fs.writeFileSync(printPath3, buffer3); const buffer4 = Buffer.from(url4.replace(/^data:image\/\w+;base64,/, ""), 'base64'); const printPath4 = path.join(exePath, 'print4.png'); fs.writeFileSync(printPath4, buffer4); // 创建 PDF 实例 const pdf = new jspdf.jsPDF({ orientation: 'landscape', unit: 'px', format: [1012, 648] }); let btns = [language_str('output')] if ((objs1.length != 0) & (objs2.length == 0)) { //只有正面 let img = new Image() img.src = printPath3 pdf.addImage(img, 'JPEG', 0, 0, 1012, 648) btns.push('打印正面') } else if ((objs1.length == 0) & (objs2.length != 0)) { //只有背面 let img = new Image() img.src = printPath4 pdf.addImage(img, 'JPEG', 0, 0, 1012, 648) btns.push('打印背面') } else { let img = new Image() img.src = printPath3 pdf.addImage(img, 'JPEG', 0, 0, 1012, 648) pdf.addPage() let img2 = new Image() img2.src = printPath4 pdf.addImage(img2, 'JPEG', 0, 0, 1012, 648) btns.push('打印正面') btns.push('打印背面') } var pdfBlob = pdf.output('blob') var pdfBuffer = pdf.output('arraybuffer') layer.open({ type: 1, area: [w, h], title: language_str('display'), //不显示标题栏"预览" shadeClose: true, //点击遮罩关闭 content: `
`, btn: btns, //'导出' btn1: function (index, layero) { savePdf(Buffer.from(pdfBuffer)) }, btn2: function () { if (btns[1] === '打印正面') { printJS({ printable: printPath3, type: 'image', style: 'img { width: 100%; height: auto; }' }) } else { printJS({ printable: printPath4, type: 'image', style: 'img { width: 100%; height: auto; }' }) } }, btn3: function () { //打印背面 printJS({ printable: printPath4, type: 'image', style: 'img { width: 100%; height: auto; }' }) } }) } function output(callback = null, _save = save) { // 类型改变 fabric.Image.fromURL('./public/images/op_2.png', function (i1) { i1.left = background_image.left i1.top = background_image.top let img1 = i1 fabric.Image.fromURL('./public/images/op_2.png', function (i2) { i2.left = background_image.left i2.top = background_image.top let img2 = i2 $('#base_control').hide() $('#line_control').hide() $('#pic_control').hide() $("#set_bg").hide(); $('#out_pic_control').hide() $('#text_control').hide() $("#circle_text_control").hide(); $('#out_text_control').hide() $('#rect_control').hide() $('#circle_control').hide() $('#counter_control').hide() $('#qrcode_Controll').hide() $('#barcode_controll').hide() $('#component_type').text(language_str('bg')) //"背景" canvas1.discardActiveObject().renderAll() canvas2.discardActiveObject().renderAll() let _objs1 = canvas1.getObjects() let g1 = [] let g3 = [] let g5 = [] //黑色图层 let left = 0 //左裁剪 let top = 0 //顶裁剪 let black_left = 0 //黑色左裁剪 let black_top = 0 //黑色顶裁剪 let all_left = 0 //预览图左裁剪 let all_top = 0 //预览图顶裁剪 for (let item of _objs1) { let idx = getIndex(item, canvas1) //console.log("------"); //console.log(item.getCoords()); //console.log(getCoordsMinX(background_image.getCoords())); //console.log(getCoordsMinX(item.getCoords())); //console.log(getCoordsMinX(background_image.getCoords()) - getCoordsMinX(item.getCoords())); //console.log("------"); if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(item.getCoords()) > all_left) { all_left = -(getCoordsMinX(item.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(item.getCoords()) > all_top) { all_top = -(getCoordsMinY(item.getCoords()) - getCoordsMinY(background_image.getCoords())) } g3.push(fabric.util.object.clone(item)) if (idx != 0 && (objs1[idx - 1].type == 10 || objs1[idx - 1].type == 4)) { continue //计数器 或 合成文字 } if (idx != 0 && (objs1[idx - 1].type == 8 || objs1[idx - 1].type == 9)) { continue //二维码 条形码 } if (idx != 0 && objs1[idx - 1].type == 2) { continue //合成图片 } if ( idx != 0 && ((objs1[idx - 1].type == 3 && item.get('fill') == '#000000') || ( objs1[idx - 1].type == 11 && item.get("fill") == "#000000" //圆形文字 && 黑色 ) || //文字 && 黑色 (objs1[idx - 1].type == 5 && //矩形 (((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && item.get('stroke') == '') || //黑填充 透明边框 (item.get('fill') == '' && (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || //透明填充 黑边框 ((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || //黑填充 黑边框 ((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && item.get('strokeWidth') == 0))) || //黑填充 0边框 (objs1[idx - 1].type == 6 && //圆形 (((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && item.get('stroke') == '') || //黑填充 透明边框 (item.get('fill') == '' && (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || //透明填充 黑边框 ((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || //黑填充 黑边框 ((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && item.get('strokeWidth') == 0))) || //黑填充 0边框 (objs1[idx - 1].type == 7 && //直线 (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || objs1[idx - 1].black == true) //勾选并入黑色图层 // || // ( // objs1[idx-1].type == 1//固定图片 // && // objs1[idx-1].black == true //勾选并入黑色图层 // ) ) { if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(item.getCoords()) > black_left) { black_left = -(getCoordsMinX(item.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(item.getCoords()) > black_top) { black_top = -(getCoordsMinY(item.getCoords()) - getCoordsMinY(background_image.getCoords())) } g5.push(fabric.util.object.clone(item)) continue //黑色文字 黑色矩形 黑色线条 黑色圆形 } else if (idx == 0) { g5.push(fabric.util.object.clone(item)) } if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(item.getCoords()) > left) { left = -(getCoordsMinX(item.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(item.getCoords()) > top) { top = -(getCoordsMinY(item.getCoords()) - getCoordsMinY(background_image.getCoords())) } g1.push(fabric.util.object.clone(item)) } let url1 = new fabric.Group(g1).toDataURL({ height: 648, width: 1012, top: top / zoom, left: left / zoom }) g3.push(img1) let url3 = new fabric.Group(g3).toDataURL({ height: 648, width: 1012, top: all_top / zoom, left: all_left / zoom }) let url5 = new fabric.Group(g5).toDataURL({ height: 648, width: 1012, top: black_top / zoom, left: black_left / zoom }) let _objs2 = canvas2.getObjects() let g2 = [] let g4 = [] let g6 = [] //黑色图层 left = 0 top = 0 black_left = 0 //黑色左裁剪 black_top = 0 //黑色顶裁剪 all_left = 0 //黑色左裁剪 all_top = 0 //黑色顶裁剪 for (let item of _objs2) { let idx = getIndex(item, canvas2) if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(item.getCoords()) > all_left) { all_left = -(getCoordsMinX(item.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(item.getCoords()) > all_top) { all_top = -(getCoordsMinY(item.getCoords()) - getCoordsMinY(background_image.getCoords())) } g4.push(fabric.util.object.clone(item)) if (idx != 0 && (objs2[idx - 1].type == 10 || objs2[idx - 1].type == 4)) { continue //计数器 或 合成文字 } if (idx != 0 && (objs2[idx - 1].type == 8 || objs2[idx - 1].type == 9)) { continue //二维码 条形码 } if (idx != 0 && objs2[idx - 1].type == 2) { continue //合成图片 } if ( idx != 0 && ((objs2[idx - 1].type == 3 && (item.get('fill') == '#000000' || (item.get('fill') == '#ffffff' && false))) || ( objs2[idx - 1].type ==11 && (item.get("fill") == "#000000" || (item.get("fill") == "#ffffff" && false)) //圆形文字 && 黑色 ) || //文字 && 黑色 (objs2[idx - 1].type == 5 && //矩形 (((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && item.get('stroke') == '') || //黑填充 透明边框 (item.get('fill') == '' && (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || //透明填充 黑边框 ((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || //黑填充 黑边框 ((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && item.get('strokeWidth') == 0))) || //黑填充 0边框 (objs2[idx - 1].type == 6 && //圆形 (((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && item.get('stroke') == '') || //黑填充 透明边框 (item.get('fill') == '' && (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || //透明填充 黑边框 ((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || //黑填充 黑边框 ((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && item.get('strokeWidth') == 0))) || //黑填充 0边框 (objs2[idx - 1].type == 7 && //直线 (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || objs2[idx - 1].black == true) //勾选并入黑色图层 // ( // objs2[idx-1].type == 1//固定图片 // && // objs2[idx-1].black == true //勾选并入黑色图层 // ) ) { if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(item.getCoords()) > black_left) { black_left = -(getCoordsMinX(item.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(item.getCoords()) > black_top) { black_top = -(getCoordsMinY(item.getCoords()) - getCoordsMinY(background_image.getCoords())) } g6.push(fabric.util.object.clone(item)) continue //黑色文字 黑色矩形 黑色线条 黑色圆形 } else if (idx == 0) { g6.push(fabric.util.object.clone(item)) } if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(item.getCoords()) > left) { left = -(getCoordsMinX(item.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(item.getCoords()) > top) { top = -(getCoordsMinY(item.getCoords()) - getCoordsMinY(background_image.getCoords())) } g2.push(fabric.util.object.clone(item)) } let url2 = new fabric.Group(g2).toDataURL({ height: 648, width: 1012, top: top / zoom, left: left / zoom }) let white_url1 = canvas1.getObjects()[0].toDataURL({ height: 648, width: 1012 }) g4.push(img2) let url4 = new fabric.Group(g4).toDataURL({ height: 648, width: 1012, top: all_top / zoom, left: all_left / zoom }) let url6 = new fabric.Group(g6).toDataURL({ height: 648, width: 1012, top: black_top / zoom, left: black_left / zoom }) let white_url2 = canvas2.getObjects()[0].toDataURL({ height: 648, width: 1012 }) //console.log(canvas.getObjects()) let w = document.body.clientWidth * 0.7 + 'px' let h = (document.body.clientWidth * 0.7 - 40 - 0.06 * document.body.clientWidth * 0.7) * 0.62548 + 150 + 'px' let h1 = (document.body.clientWidth * 0.7 - 40 - 0.06 * document.body.clientWidth * 0.7) * 0.62548 + 'px' if ((document.body.clientWidth * 0.7 - 40 - 0.06 * document.body.clientWidth * 0.7) * 0.62548 > document.body.clientHeight) { //高度超出,则按高度计算 h = document.body.clientHeight * 0.8 + 'px' h1 = document.body.clientHeight * 0.8 - 150 + 'px' w = ((document.body.clientHeight * 0.8 - 150) / 0.62548 + 40) / 0.94 } let op = { frontColorPic: '', backColorPic: '', frontBlackPic: '', backBlackPic: '', frontData: [], backData: [], flag: 1, frontDisplayPic: url3, backDisplayPic: url4 } if ((objs1.length != 0) & (objs2.length == 0)) { op.flag = 2 } else if ((objs1.length == 0) & (objs2.length != 0)) { op.flag = 3 } op.frontColorPic = desEncrypt(url1) op.backColorPic = desEncrypt(url2) //op.frontBlPic = url5; //op.backBlPic = url6; op.frontBlackPic = desEncrypt(url5) op.backBlackPic = desEncrypt(url6) for (let item of _objs1) { let idx = getIndex(item, canvas1) if (idx == 0) continue //background-image let type = objs1[idx - 1].type if (type == 2) { //out_pic let xy = getAbsoluteXY(item) op.frontData.push({ type: 1, name: objs1[idx - 1].name, FontColor: objs1[idx - 1].black ? '#000000' : '@', transparency: item.get('opacity'), x: parseInt((xy[0] - background_image1.left).toFixed(0)), y: parseInt((xy[1] - background_image1.top).toFixed(0)), h: parseInt((item.get('scaleY') * item.get('height')).toFixed(0)), w: parseInt((item.get('scaleX') * item.get('width')).toFixed(0)), rotate: parseInt(item.get('angle').toFixed(0)) }) } else if (type == 3) { //text /*2022-07-26 黑色并入黑色图层 if(item.get("fill") == "#000000"){ //纯黑 op.frontData.push({ "type" : 2, "Text" : item.get("text"), "FontFamily" : item.get("fontFamily"), "FontSize" : parseInt(item.get("fontSize")), "FontColor" : "#000000", "FontBackgroudColor" : item.get("textBackgroundColor"), "Bold" : item.get("fontWeight") == "bold", "Underline" : item.get("underline"), "Italic" : item.get("fontStyle") == "italic", "Strikeout" : item.get("linethrough"), "x" : parseInt((item.get("left") - background_image1.left).toFixed(0)), "y" : parseInt((item.get("top") - background_image1.top).toFixed(0)), "h" : parseInt((item.get("scaleY") * item.get("height")).toFixed(0)), "w" : parseInt((item.get("scaleX") * item.get("width")).toFixed(0)), "rotate" : parseInt(item.get("angle").toFixed(0)) }); } */ } else if (type == 11) { //circle_text op.frontData.push({ "type" : 2, "Text" : item.get("text"), "FontFamily" : item.get("fontFamily"), "FontSize" : parseInt(item.get("fontSize")), "FontColor" : "#000000", "FontBackgroudColor" : item.get("textBackgroundColor"), "Bold" : item.get("fontWeight") == "bold", "Underline" : item.get("underline"), "Italic" : item.get("fontStyle") == "italic", "Strikeout" : item.get("linethrough"), "x" : parseInt((item.get("left") - background_image1.left).toFixed(0)), "y" : parseInt((item.get("top") - background_image1.top).toFixed(0)), "h" : parseInt((item.get("scaleY") * item.get("height")).toFixed(0)), "w" : parseInt((item.get("scaleX") * item.get("width")).toFixed(0)), "rotate" : parseInt(item.get("angle").toFixed(0)), "circleCenter" : objs1[idx - 1].circleCenter || 0 }); } else if (type == 4) { //out_text let xy = getAbsoluteXY(item) op.frontData.push({ type: 3, name: objs1[idx - 1].name, FontFamily: item.get('fontFamily'), DefaultText: item.get('text'), FontBackgroudColor: item.get('textBackgroundColor'), FontSize: parseInt(item.get('fontSize')), FontColor: item.get('fill'), Exceed: objs1[idx - 1].exceed, AutoWrap: objs1[idx - 1].autoWrap, FixSize: objs1[idx - 1].fixSize, Bold: item.get('fontWeight') == 'bold', Underline: item.get('underline'), Italic: item.get('fontStyle') == 'italic', Strikeout: item.get('linethrough'), x: parseInt((xy[0] - background_image1.left).toFixed(0)), y: parseInt((xy[1] - background_image1.top).toFixed(0)), h: parseInt((item.get('scaleY') * item.get('height')).toFixed(0)), w: parseInt((item.get('scaleX') * item.get('width')).toFixed(0)), rotate: parseInt(item.get('angle').toFixed(0)), align: objs1[idx - 1].align }) } else if (type == 8) { //二维码 let xy = getAbsoluteXY(item) op.frontData.push({ type: 4, name: objs1[idx - 1].name, FontColor: objs1[idx - 1].color, DefaultText: objs1[idx - 1].val, x: parseInt((xy[0] - background_image1.left).toFixed(0)), y: parseInt((xy[1] - background_image1.top).toFixed(0)), h: parseInt((item.get('scaleY') * item.get('height')).toFixed(0)), w: parseInt((item.get('scaleX') * item.get('width')).toFixed(0)), rotate: parseInt(item.get('angle').toFixed(0)) }) } else if (type == 9) { //条形码 let xy = getAbsoluteXY(item) op.frontData.push({ type: 5, name: objs1[idx - 1].name, FontSize: parseInt(objs1[idx - 1].fontSize), DefaultText: objs1[idx - 1].val, HideText: objs1[idx - 1].show, FontFamily: objs1[idx - 1].font, FontColor: objs1[idx - 1].color, x: parseInt((xy[0] - background_image1.left).toFixed(0)), y: parseInt((xy[1] - background_image1.top).toFixed(0)), h: parseInt((item.get('scaleY') * item.get('height')).toFixed(0)), w: parseInt((item.get('scaleX') * item.get('width')).toFixed(0)), rotate: parseInt(item.get('angle').toFixed(0)) }) } else if (type == 10) { let xy = getAbsoluteXY(item) op.frontData.push({ type: 6, name: objs1[idx - 1].name, FontFamily: item.get('fontFamily'), FontSize: parseInt(item.get('fontSize')), FontColor: item.get('fill'), start: objs1[idx - 1].start, add: parseInt(objs1[idx - 1].add), x: parseInt((xy[0] - background_image1.left).toFixed(0)), y: parseInt((xy[1] - background_image1.top).toFixed(0)), h: parseInt((item.get('scaleY') * item.get('height')).toFixed(0)), w: parseInt((item.get('scaleX') * item.get('width')).toFixed(0)), rotate: parseInt(item.get('angle').toFixed(0)) }) } } //obj2 for (let item of _objs2) { let idx = getIndex(item, canvas2) if (idx == 0) continue //background-image let type = objs2[idx - 1].type if (type == 2) { //out_pic let xy = getAbsoluteXY(item) op.backData.push({ type: 1, name: objs2[idx - 1].name, FontColor: objs2[idx - 1].black ? '#000000' : '@', transparency: item.get('opacity'), x: parseInt((xy[0] - background_image2.left).toFixed(0)), y: parseInt((xy[1] - background_image2.top).toFixed(0)), h: parseInt((item.get('scaleY') * item.get('height')).toFixed(0)), w: parseInt((item.get('scaleX') * item.get('width')).toFixed(0)), rotate: parseInt(item.get('angle').toFixed(0)) }) } else if (type == 3) { //text /*2022-07-26 黑色并入黑色图层 if(item.get("fill") == "#000000"){ //纯黑 op.backData.push({ "type" : 2, "Text" : item.get("text"), "FontFamily" : item.get("fontFamily"), "FontSize" : parseInt(item.get("fontSize")), "FontColor" : "#000000", "FontBackgroudColor" : item.get("textBackgroundColor"), "Bold" : item.get("fontWeight") == "bold", "Underline" : item.get("underline"), "Italic" : item.get("fontStyle") == "italic", "Strikeout" : item.get("linethrough"), "x" : parseInt((item.get("left") - background_image2.left).toFixed(0)), "y" : parseInt((item.get("top") - background_image2.top).toFixed(0)), "h" : parseInt((item.get("scaleY") * item.get("height")).toFixed(0)), "w" : parseInt((item.get("scaleX") * item.get("width")).toFixed(0)), "rotate" : parseInt(item.get("angle").toFixed(0)) }); } */ } else if (type == 11) { //circle_text op.backData.push({ "type" : 2, "Text" : item.get("text"), "FontFamily" : item.get("fontFamily"), "FontSize" : parseInt(item.get("fontSize")), "FontColor" : "#000000", "FontBackgroudColor" : item.get("textBackgroundColor"), "Bold" : item.get("fontWeight") == "bold", "Underline" : item.get("underline"), "Italic" : item.get("fontStyle") == "italic", "Strikeout" : item.get("linethrough"), "x" : parseInt((item.get("left") - background_image2.left).toFixed(0)), "y" : parseInt((item.get("top") - background_image2.top).toFixed(0)), "h" : parseInt((item.get("scaleY") * item.get("height")).toFixed(0)), "w" : parseInt((item.get("scaleX") * item.get("width")).toFixed(0)), "rotate" : parseInt(item.get("angle").toFixed(0)), "circleCenter" : objs2[idx - 1].circleCenter || 0 }); } else if (type == 4) { let xy = getAbsoluteXY(item) op.backData.push({ type: 3, name: objs2[idx - 1].name, FontFamily: item.get('fontFamily'), DefaultText: item.get('text'), FontSize: parseInt(item.get('fontSize')), FontBackgroudColor: item.get('textBackgroundColor'), FontColor: item.get('fill'), Exceed: objs2[idx - 1].exceed, AutoWrap: objs2[idx - 1].autoWrap, FixSize: objs2[idx - 1].fixSize, Bold: item.get('fontWeight') == 'bold', Underline: item.get('underline'), Italic: item.get('fontStyle') == 'italic', Strikeout: item.get('linethrough'), x: parseInt((xy[0] - background_image2.left).toFixed(0)), y: parseInt((xy[1] - background_image2.top).toFixed(0)), h: parseInt((item.get('scaleY') * item.get('height')).toFixed(0)), w: parseInt((item.get('scaleX') * item.get('width')).toFixed(0)), rotate: parseInt(item.get('angle').toFixed(0)), align: objs2[idx - 1].align }) } else if (type == 8) { //二维码 let xy = getAbsoluteXY(item) op.backData.push({ type: 4, name: objs2[idx - 1].name, FontColor: objs2[idx - 1].color, DefaultText: objs2[idx - 1].val, x: parseInt((xy[0] - background_image2.left).toFixed(0)), y: parseInt((xy[1] - background_image2.top).toFixed(0)), h: parseInt((item.get('scaleY') * item.get('height')).toFixed(0)), w: parseInt((item.get('scaleX') * item.get('width')).toFixed(0)), rotate: parseInt(item.get('angle').toFixed(0)) }) } else if (type == 9) { let xy = getAbsoluteXY(item) op.backData.push({ type: 5, name: objs2[idx - 1].name, DefaultText: objs2[idx - 1].val, HideText: objs1[idx - 1].show, FontSize: parseInt(objs2[idx - 1].fontSize), FontFamily: objs2[idx - 1].font, FontColor: objs2[idx - 1].color, x: parseInt((xy[0] - background_image2.left).toFixed(0)), y: parseInt((xy[1] - background_image2.top).toFixed(0)), h: parseInt((item.get('scaleY') * item.get('height')).toFixed(0)), w: parseInt((item.get('scaleX') * item.get('width')).toFixed(0)), rotate: parseInt(item.get('angle').toFixed(0)) }) } else if (type == 10) { let xy = getAbsoluteXY(item) op.backData.push({ type: 6, name: objs2[idx - 1].name, FontFamily: item.get('fontFamily'), FontSize: parseInt(item.get('fontSize')), FontColor: item.get('fill'), start: parseInt(objs2[idx - 1].start), add: parseInt(objs2[idx - 1].add), x: parseInt((xy[0] - background_image2.left).toFixed(0)), y: parseInt((xy[1] - background_image2.top).toFixed(0)), h: parseInt((item.get('scaleY') * item.get('height')).toFixed(0)), w: parseInt((item.get('scaleX') * item.get('width')).toFixed(0)), rotate: parseInt(item.get('angle').toFixed(0)) }) } } _save(op, callback) //return false 开启该代码可禁止点击该按钮关闭 }) }) } $('#output').on('click', function () { output(null, saveAs) return // 类型改变 fabric.Image.fromURL('./public/images/op_2.png', function (i1) { i1.left = background_image.left i1.top = background_image.top let img1 = i1 fabric.Image.fromURL('./public/images/op_2.png', function (i2) { i2.left = background_image.left i2.top = background_image.top let img2 = i2 $('#base_control').hide() $('#line_control').hide() $('#pic_control').hide() $("#set_bg").hide(); $('#out_pic_control').hide() $('#text_control').hide() $("#circle_text_control").hide(); $('#out_text_control').hide() $('#rect_control').hide() $('#circle_control').hide() $('#counter_control').hide() $('#qrcode_Controll').hide() $('#barcode_controll').hide() $('#component_type').text(language_str('bg')) //"背景" canvas1.discardActiveObject().renderAll() canvas2.discardActiveObject().renderAll() let _objs1 = canvas1.getObjects() let g1 = [] let g3 = [] let g5 = [] //黑色图层 let left = 0 //左裁剪 let top = 0 //顶裁剪 let black_left = 0 //黑色左裁剪 let black_top = 0 //黑色顶裁剪 let all_left = 0 //预览图左裁剪 let all_top = 0 //预览图顶裁剪 for (let item of _objs1) { let idx = getIndex(item, canvas1) //console.log("------"); //console.log(item.getCoords()); //console.log(getCoordsMinX(background_image.getCoords())); //console.log(getCoordsMinX(item.getCoords())); //console.log(getCoordsMinX(background_image.getCoords()) - getCoordsMinX(item.getCoords())); //console.log("------"); if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(item.getCoords()) > all_left) { all_left = -(getCoordsMinX(item.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(item.getCoords()) > all_top) { all_top = -(getCoordsMinY(item.getCoords()) - getCoordsMinY(background_image.getCoords())) } g3.push(fabric.util.object.clone(item)) if (idx != 0 && (objs1[idx - 1].type == 10 || objs1[idx - 1].type == 4)) { continue //计数器 或 合成文字 } if (idx != 0 && (objs1[idx - 1].type == 8 || objs1[idx - 1].type == 9)) { continue //二维码 条形码 } if (idx != 0 && objs1[idx - 1].type == 2) { continue //合成图片 } if ( idx != 0 && ((objs1[idx - 1].type == 3 && (item.get('fill') == '#000000' || (item.get('fill') == '#ffffff' && false))) || ( objs2[idx - 1].type ==11 && (item.get("fill") == "#000000" || (item.get("fill") == "#ffffff" && false)) //圆形文字 && 黑色 ) || //文字 && 黑色 (objs1[idx - 1].type == 5 && //矩形 (((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && item.get('stroke') == '') || //黑填充 透明边框 (item.get('fill') == '' && (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || //透明填充 黑边框 ((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || //黑填充 黑边框 ((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && item.get('strokeWidth') == 0))) || //黑填充 0边框 (objs1[idx - 1].type == 6 && //圆形 (((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && item.get('stroke') == '') || //黑填充 透明边框 (item.get('fill') == '' && (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || //透明填充 黑边框 ((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || //黑填充 黑边框 ((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && item.get('strokeWidth') == 0))) || //黑填充 0边框 (objs1[idx - 1].type == 7 && //直线 (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || objs1[idx - 1].black == true) //勾选并入黑色图层 // ( // objs1[idx-1].type == 1//固定图片 // && // objs1[idx-1].black == true //勾选并入黑色图层 // ) ) { if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(item.getCoords()) > black_left) { black_left = -(getCoordsMinX(item.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(item.getCoords()) > black_top) { black_top = -(getCoordsMinY(item.getCoords()) - getCoordsMinY(background_image.getCoords())) } g5.push(fabric.util.object.clone(item)) continue //黑色文字 黑色矩形 黑色线条 黑色圆形 } else if (idx == 0) { g5.push(fabric.util.object.clone(item)) } if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(item.getCoords()) > left) { left = -(getCoordsMinX(item.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(item.getCoords()) > top) { top = -(getCoordsMinY(item.getCoords()) - getCoordsMinY(background_image.getCoords())) } g1.push(fabric.util.object.clone(item)) } let url1 = new fabric.Group(g1).toDataURL({ height: 648, width: 1012, top: top / zoom, left: left / zoom }) g3.push(img1) let url3 = new fabric.Group(g3).toDataURL({ height: 648, width: 1012, top: all_top / zoom, left: all_left / zoom }) let url5 = new fabric.Group(g5).toDataURL({ height: 648, width: 1012, top: black_top / zoom, left: black_left / zoom }) let _objs2 = canvas2.getObjects() let g2 = [] let g4 = [] let g6 = [] //黑色图层 left = 0 top = 0 black_left = 0 //黑色左裁剪 black_top = 0 //黑色顶裁剪 all_left = 0 //黑色左裁剪 all_top = 0 //黑色顶裁剪 for (let item of _objs2) { let idx = getIndex(item, canvas2) if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(item.getCoords()) > all_left) { all_left = -(getCoordsMinX(item.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(item.getCoords()) > all_top) { all_top = -(getCoordsMinY(item.getCoords()) - getCoordsMinY(background_image.getCoords())) } g4.push(fabric.util.object.clone(item)) if (idx != 0 && (objs2[idx - 1].type == 10 || objs2[idx - 1].type == 4)) { continue //计数器 或 合成文字 } if (idx != 0 && (objs2[idx - 1].type == 8 || objs2[idx - 1].type == 9)) { continue //二维码 条形码 } if (idx != 0 && objs2[idx - 1].type == 2) { continue //合成图片 } if ( idx != 0 && ((objs2[idx - 1].type == 3 && (item.get('fill') == '#000000' || (item.get('fill') == '#ffffff' && false))) || ( objs2[idx - 1].type ==11 && (item.get("fill") == "#000000" || (item.get("fill") == "#ffffff" && false)) //圆形文字 && 黑色 ) || //文字 && 黑色 (objs2[idx - 1].type == 5 && //矩形 (((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && item.get('stroke') == '') || //黑填充 透明边框 (item.get('fill') == '' && (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || //透明填充 黑边框 ((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || //黑填充 黑边框 ((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && item.get('strokeWidth') == 0))) || //黑填充 0边框 (objs2[idx - 1].type == 6 && //圆形 (((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && item.get('stroke') == '') || //黑填充 透明边框 (item.get('fill') == '' && (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || //透明填充 黑边框 ((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || //黑填充 黑边框 ((item.get('fill') == '#000000' || item.get('fill') == '#ffffff') && item.get('strokeWidth') == 0))) || //黑填充 0边框 (objs2[idx - 1].type == 7 && //直线 (item.get('stroke') == '#000000' || item.get('stroke') == '#ffffff')) || objs2[idx - 1].black == true) //勾选并入黑色图层 // ( // objs2[idx-1].type == 1//固定图片 // && // objs2[idx-1].black == true //勾选并入黑色图层 // ) ) { if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(item.getCoords()) > black_left) { black_left = -(getCoordsMinX(item.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(item.getCoords()) > black_top) { black_top = -(getCoordsMinY(item.getCoords()) - getCoordsMinY(background_image.getCoords())) } g6.push(fabric.util.object.clone(item)) continue //黑色文字 黑色矩形 黑色线条 黑色圆形 } else if (idx == 0) { g6.push(fabric.util.object.clone(item)) } if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(item.getCoords()) > left) { left = -(getCoordsMinX(item.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(item.getCoords()) > top) { top = -(getCoordsMinY(item.getCoords()) - getCoordsMinY(background_image.getCoords())) } g2.push(fabric.util.object.clone(item)) } let url2 = new fabric.Group(g2).toDataURL({ height: 648, width: 1012, top: top / zoom, left: left / zoom }) let white_url1 = canvas1.getObjects()[0].toDataURL({ height: 648, width: 1012 }) g4.push(img2) let url4 = new fabric.Group(g4).toDataURL({ height: 648, width: 1012, top: all_top / zoom, left: all_left / zoom }) let url6 = new fabric.Group(g6).toDataURL({ height: 648, width: 1012, top: black_top / zoom, left: black_left / zoom }) let white_url2 = canvas2.getObjects()[0].toDataURL({ height: 648, width: 1012 }) //console.log(canvas.getObjects()) let w = document.body.clientWidth * 0.7 + 'px' let h = (document.body.clientWidth * 0.7 - 40 - 0.06 * document.body.clientWidth * 0.7) * 0.62548 + 150 + 'px' let h1 = (document.body.clientWidth * 0.7 - 40 - 0.06 * document.body.clientWidth * 0.7) * 0.62548 + 'px' if ((document.body.clientWidth * 0.7 - 40 - 0.06 * document.body.clientWidth * 0.7) * 0.62548 > document.body.clientHeight) { //高度超出,则按高度计算 h = document.body.clientHeight * 0.8 + 'px' h1 = document.body.clientHeight * 0.8 - 150 + 'px' w = ((document.body.clientHeight * 0.8 - 150) / 0.62548 + 40) / 0.94 } let op = { frontColorPic: '', backColorPic: '', frontBlackPic: '', backBlackPic: '', frontData: [], backData: [], flag: 1, frontDisplayPic: url3, backDisplayPic: url4 } if ((objs1.length != 0) & (objs2.length == 0)) { op.flag = 2 } else if ((objs1.length == 0) & (objs2.length != 0)) { op.flag = 3 } op.frontColorPic = desEncrypt(url1) op.backColorPic = desEncrypt(url2) //op.frontBlPic = url5; //op.backBlPic = url6; op.frontBlackPic = desEncrypt(url5) op.backBlackPic = desEncrypt(url6) for (let item of _objs1) { let idx = getIndex(item, canvas1) if (idx == 0) continue //background-image let type = objs1[idx - 1].type if (type == 2) { //out_pic let xy = getAbsoluteXY(item) op.frontData.push({ type: 1, name: objs1[idx - 1].name, FontColor: objs1[idx - 1].black ? '#000000' : '@', transparency: item.get('opacity'), x: parseInt((xy[0] - background_image1.left).toFixed(0)), y: parseInt((xy[1] - background_image1.top).toFixed(0)), h: parseInt((item.get('scaleY') * item.get('height')).toFixed(0)), w: parseInt((item.get('scaleX') * item.get('width')).toFixed(0)), rotate: parseInt(item.get('angle').toFixed(0)) }) } else if (type == 3) { //text /*2022-07-26 黑色并入黑色图层 if(item.get("fill") == "#000000"){ //纯黑 op.frontData.push({ "type" : 2, "Text" : item.get("text"), "FontFamily" : item.get("fontFamily"), "FontSize" : parseInt(item.get("fontSize")), "FontColor" : "#000000", "FontBackgroudColor" : item.get("textBackgroundColor"), "Bold" : item.get("fontWeight") == "bold", "Underline" : item.get("underline"), "Italic" : item.get("fontStyle") == "italic", "Strikeout" : item.get("linethrough"), "x" : parseInt((item.get("left") - background_image1.left).toFixed(0)), "y" : parseInt((item.get("top") - background_image1.top).toFixed(0)), "h" : parseInt((item.get("scaleY") * item.get("height")).toFixed(0)), "w" : parseInt((item.get("scaleX") * item.get("width")).toFixed(0)), "rotate" : parseInt(item.get("angle").toFixed(0)) }); } */ } else if (type == 11) { //circle_text op.frontData.push({ "type" : 2, "Text" : item.get("text"), "FontFamily" : item.get("fontFamily"), "FontSize" : parseInt(item.get("fontSize")), "FontColor" : "#000000", "FontBackgroudColor" : item.get("textBackgroundColor"), "Bold" : item.get("fontWeight") == "bold", "Underline" : item.get("underline"), "Italic" : item.get("fontStyle") == "italic", "Strikeout" : item.get("linethrough"), "x" : parseInt((item.get("left") - background_image1.left).toFixed(0)), "y" : parseInt((item.get("top") - background_image1.top).toFixed(0)), "h" : parseInt((item.get("scaleY") * item.get("height")).toFixed(0)), "w" : parseInt((item.get("scaleX") * item.get("width")).toFixed(0)), "rotate" : parseInt(item.get("angle").toFixed(0)), "circleCenter" : objs1[idx - 1].circleCenter || 0 }); } else if (type == 4) { //out_text let xy = getAbsoluteXY(item) op.frontData.push({ type: 3, name: objs1[idx - 1].name, FontFamily: item.get('fontFamily'), DefaultText: item.get('text'), FontBackgroudColor: item.get('textBackgroundColor'), FontSize: parseInt(item.get('fontSize')), FontColor: item.get('fill'), Exceed: objs1[idx - 1].exceed, AutoWrap: objs1[idx - 1].autoWrap, FixSize: objs1[idx - 1].fixSize, Bold: item.get('fontWeight') == 'bold', Underline: item.get('underline'), Italic: item.get('fontStyle') == 'italic', Strikeout: item.get('linethrough'), x: parseInt((xy[0] - background_image1.left).toFixed(0)), y: parseInt((xy[1] - background_image1.top).toFixed(0)), h: parseInt((item.get('scaleY') * item.get('height')).toFixed(0)), w: parseInt((item.get('scaleX') * item.get('width')).toFixed(0)), rotate: parseInt(item.get('angle').toFixed(0)), align: objs1[idx - 1].align }) } else if (type == 8) { //二维码 let xy = getAbsoluteXY(item) op.frontData.push({ type: 4, name: objs1[idx - 1].name, FontColor: objs1[idx - 1].color, DefaultText: objs1[idx - 1].val, x: parseInt((xy[0] - background_image1.left).toFixed(0)), y: parseInt((xy[1] - background_image1.top).toFixed(0)), h: parseInt((item.get('scaleY') * item.get('height')).toFixed(0)), w: parseInt((item.get('scaleX') * item.get('width')).toFixed(0)), rotate: parseInt(item.get('angle').toFixed(0)) }) } else if (type == 9) { //条形码 let xy = getAbsoluteXY(item) op.frontData.push({ type: 5, name: objs1[idx - 1].name, FontSize: parseInt(objs1[idx - 1].fontSize), DefaultText: objs1[idx - 1].val, HideText: objs1[idx - 1].show, FontFamily: objs1[idx - 1].font, FontColor: objs1[idx - 1].color, x: parseInt((xy[0] - background_image1.left).toFixed(0)), y: parseInt((xy[1] - background_image1.top).toFixed(0)), h: parseInt((item.get('scaleY') * item.get('height')).toFixed(0)), w: parseInt((item.get('scaleX') * item.get('width')).toFixed(0)), rotate: parseInt(item.get('angle').toFixed(0)) }) } else if (type == 10) { let xy = getAbsoluteXY(item) op.frontData.push({ type: 6, name: objs1[idx - 1].name, FontFamily: item.get('fontFamily'), FontSize: parseInt(item.get('fontSize')), FontColor: item.get('fill'), start: objs1[idx - 1].start, add: parseInt(objs1[idx - 1].add), x: parseInt((xy[0] - background_image1.left).toFixed(0)), y: parseInt((xy[1] - background_image1.top).toFixed(0)), h: parseInt((item.get('scaleY') * item.get('height')).toFixed(0)), w: parseInt((item.get('scaleX') * item.get('width')).toFixed(0)), rotate: parseInt(item.get('angle').toFixed(0)) }) } } //obj2 for (let item of _objs2) { let idx = getIndex(item, canvas2) if (idx == 0) continue //background-image let type = objs2[idx - 1].type if (type == 2) { //out_pic let xy = getAbsoluteXY(item) op.backData.push({ type: 1, name: objs2[idx - 1].name, FontColor: objs2[idx - 1].black ? '#000000' : '@', transparency: item.get('opacity'), x: parseInt((xy[0] - background_image2.left).toFixed(0)), y: parseInt((xy[1] - background_image2.top).toFixed(0)), h: parseInt((item.get('scaleY') * item.get('height')).toFixed(0)), w: parseInt((item.get('scaleX') * item.get('width')).toFixed(0)), rotate: parseInt(item.get('angle').toFixed(0)) }) } else if (type == 3) { //text /*2022-07-26 黑色并入黑色图层 if(item.get("fill") == "#000000"){ //纯黑 op.backData.push({ "type" : 2, "Text" : item.get("text"), "FontFamily" : item.get("fontFamily"), "FontSize" : parseInt(item.get("fontSize")), "FontColor" : "#000000", "FontBackgroudColor" : item.get("textBackgroundColor"), "Bold" : item.get("fontWeight") == "bold", "Underline" : item.get("underline"), "Italic" : item.get("fontStyle") == "italic", "Strikeout" : item.get("linethrough"), "x" : parseInt((item.get("left") - background_image2.left).toFixed(0)), "y" : parseInt((item.get("top") - background_image2.top).toFixed(0)), "h" : parseInt((item.get("scaleY") * item.get("height")).toFixed(0)), "w" : parseInt((item.get("scaleX") * item.get("width")).toFixed(0)), "rotate" : parseInt(item.get("angle").toFixed(0)) }); } */ } else if (type == 11) { //circle_text op.backData.push({ "type" : 2, "Text" : item.get("text"), "FontFamily" : item.get("fontFamily"), "FontSize" : parseInt(item.get("fontSize")), "FontColor" : "#000000", "FontBackgroudColor" : item.get("textBackgroundColor"), "Bold" : item.get("fontWeight") == "bold", "Underline" : item.get("underline"), "Italic" : item.get("fontStyle") == "italic", "Strikeout" : item.get("linethrough"), "x" : parseInt((item.get("left") - background_image2.left).toFixed(0)), "y" : parseInt((item.get("top") - background_image2.top).toFixed(0)), "h" : parseInt((item.get("scaleY") * item.get("height")).toFixed(0)), "w" : parseInt((item.get("scaleX") * item.get("width")).toFixed(0)), "rotate" : parseInt(item.get("angle").toFixed(0)), "circleCenter" : objs2[idx - 1].circleCenter || 0 }); } else if (type == 4) { let xy = getAbsoluteXY(item) op.backData.push({ type: 3, name: objs2[idx - 1].name, FontFamily: item.get('fontFamily'), DefaultText: item.get('text'), FontSize: parseInt(item.get('fontSize')), FontBackgroudColor: item.get('textBackgroundColor'), FontColor: item.get('fill'), Exceed: objs2[idx - 1].exceed, AutoWrap: objs2[idx - 1].autoWrap, FixSize: objs2[idx - 1].fixSize, Bold: item.get('fontWeight') == 'bold', Underline: item.get('underline'), Italic: item.get('fontStyle') == 'italic', Strikeout: item.get('linethrough'), x: parseInt((xy[0] - background_image2.left).toFixed(0)), y: parseInt((xy[1] - background_image2.top).toFixed(0)), h: parseInt((item.get('scaleY') * item.get('height')).toFixed(0)), w: parseInt((item.get('scaleX') * item.get('width')).toFixed(0)), rotate: parseInt(item.get('angle').toFixed(0)), align: objs2[idx - 1].align }) } else if (type == 8) { //二维码 let xy = getAbsoluteXY(item) op.backData.push({ type: 4, name: objs2[idx - 1].name, FontColor: objs2[idx - 1].color, DefaultText: objs2[idx - 1].val, x: parseInt((xy[0] - background_image2.left).toFixed(0)), y: parseInt((xy[1] - background_image2.top).toFixed(0)), h: parseInt((item.get('scaleY') * item.get('height')).toFixed(0)), w: parseInt((item.get('scaleX') * item.get('width')).toFixed(0)), rotate: parseInt(item.get('angle').toFixed(0)) }) } else if (type == 9) { let xy = getAbsoluteXY(item) op.backData.push({ type: 5, name: objs2[idx - 1].name, DefaultText: objs2[idx - 1].val, HideText: objs1[idx - 1].show, FontSize: parseInt(objs2[idx - 1].fontSize), FontFamily: objs2[idx - 1].font, FontColor: objs2[idx - 1].color, x: parseInt((xy[0] - background_image2.left).toFixed(0)), y: parseInt((xy[1] - background_image2.top).toFixed(0)), h: parseInt((item.get('scaleY') * item.get('height')).toFixed(0)), w: parseInt((item.get('scaleX') * item.get('width')).toFixed(0)), rotate: parseInt(item.get('angle').toFixed(0)) }) } else if (type == 10) { let xy = getAbsoluteXY(item) op.backData.push({ type: 6, name: objs2[idx - 1].name, FontFamily: item.get('fontFamily'), FontSize: parseInt(item.get('fontSize')), FontColor: item.get('fill'), start: parseInt(objs2[idx - 1].start), add: parseInt(objs2[idx - 1].add), x: parseInt((xy[0] - background_image2.left).toFixed(0)), y: parseInt((xy[1] - background_image2.top).toFixed(0)), h: parseInt((item.get('scaleY') * item.get('height')).toFixed(0)), w: parseInt((item.get('scaleX') * item.get('width')).toFixed(0)), rotate: parseInt(item.get('angle').toFixed(0)) }) } } dialog .showSaveDialog({ title: language_str('saveFile'), //'保存文件' filters: [{ name: 'CS File Type', extensions: ['cs'] }] }) .then((result) => { if (result.canceled) return if (result.filePath.substring(result.filePath.length - 5).indexOf('.') == -1) { result.filePath += '.cs' } let fs = require('fs') op.soonType = 2 fs.writeFileSync(result.filePath, JSON.stringify(op)) }) .catch((err) => { console.log() }) //return false 开启该代码可禁止点击该按钮关闭 }) }) }) var _keyctrl = false, _keyc = false, _textEdit = false, _inputEdit = false $('input').focus(function () { console.log(1) _inputEdit = true }) $('input').blur(function () { _inputEdit = false }) $('textarea').focus(function () { console.log(1) _inputEdit = true }) $('textarea').blur(function () { _inputEdit = false }) $('body').keyup(function (event) { // 兼容三端的 modifier key 检测(Windows/Linux: Ctrl, Mac: Cmd/Meta) if (event.keyCode == 17 || event.keyCode == 91 || event.keyCode == 93) { // Ctrl 键或 Meta 键(Mac Cmd)释放 _keyctrl = false } if (event.keyCode == 67) { _keyc = false } }) $('body').keydown(function (event) { // 统一的快捷键处理(兼容 Windows/Linux: Ctrl, Mac: Cmd/Meta) const isModifierKey = event.ctrlKey || event.metaKey; // 兼容三端 // 快捷键处理(在输入框或文本区域中时不触发,除了删除相关的) if (!_inputEdit && !_textEdit) { // CTRL/CMD+N - 新建 if (isModifierKey && event.keyCode == 78) { event.preventDefault(); $('#new').click(); return; } // CTRL/CMD+O - 打开 if (isModifierKey && event.keyCode == 79) { event.preventDefault(); $('#open').click(); return; } // CTRL/CMD+S - 保存 if (isModifierKey && !event.shiftKey && event.keyCode == 83) { event.preventDefault(); $('#save').click(); return; } // CTRL/CMD+SHIFT+S - 保存副本 if (isModifierKey && event.shiftKey && event.keyCode == 83) { event.preventDefault(); output(null, saveAs); return; } // CTRL/CMD+Z - 还原 if (isModifierKey && !event.shiftKey && event.keyCode == 90) { event.preventDefault(); $('#previous').click(); return; } // CTRL/CMD+Y - 重做 if (isModifierKey && !event.shiftKey && event.keyCode == 89) { event.preventDefault(); $('#next').click(); return; } // CTRL/CMD+C - 复制 if (isModifierKey && event.keyCode == 67 && event.target.nodeName == 'BODY') { event.preventDefault(); copySelection(); return; } // CTRL/CMD+V - 粘贴 if (isModifierKey && event.keyCode == 86 && event.target.nodeName == 'BODY') { event.preventDefault(); pasteFromClipboard(); return; } // CTRL/CMD+SHIFT+DEL - 清空 if (isModifierKey && event.shiftKey && event.keyCode == 46) { event.preventDefault(); $('#clean').click(); return; } // CTRL/CMD+DEL - 删除 if (isModifierKey && !event.shiftKey && event.keyCode == 46) { event.preventDefault(); $('#delete').click(); return; } } // 兼容三端的 modifier key 检测(Windows/Linux: Ctrl, Mac: Cmd/Meta) if (event.keyCode == 17 || event.metaKey) { // Ctrl 键或 Meta 键(Mac Cmd) _keyctrl = true if (_keyc && _textEdit) { //同时按下且在编辑状态 setTimeout("clipboard.writeText( (clipboard.readText()+' ') );", 1) //clipboard.writeText((clipboard.readText()+' ')) } } if (event.keyCode == 67) { _keyc = true if (_keyctrl & _textEdit) { //同时按下且在编辑状态 setTimeout("clipboard.writeText( (clipboard.readText()+' ') );", 1) //clipboard.writeText((clipboard.readText()+' ')) } } if (event.keyCode == 37) { //left let v = -1 if (_keyctrl || event.ctrlKey || event.metaKey) { v = -5 } let x = canvas.getActiveObject().get('left') x += v canvas.getActiveObject().set('left', x) canvas.renderAll() recordState() updateControls() } if (event.keyCode == 38) { //up let v = -1 if (_keyctrl || event.ctrlKey || event.metaKey) { v = -5 } let y = canvas.getActiveObject().get('top') y += v canvas.getActiveObject().set('top', y) canvas.renderAll() recordState() updateControls() } if (event.keyCode == 39) { //right let v = 1 if (_keyctrl || event.ctrlKey || event.metaKey) { v = 5 } let x = canvas.getActiveObject().get('left') x += v canvas.getActiveObject().set('left', x) canvas.renderAll() recordState() updateControls() } if (event.keyCode == 40) { //down let v = +1 if (_keyctrl || event.ctrlKey || event.metaKey) { v = 5 } let y = canvas.getActiveObject().get('top') y += v canvas.getActiveObject().set('top', y) canvas.renderAll() recordState() updateControls() } // 普通删除键(DEL键,没有按CTRL/CMD) if (event.keyCode == 46 && !isModifierKey && !_inputEdit && !_textEdit) { let actObjs = canvas.getActiveObjects() let allObjs = canvas.getObjects() let flag = 0 for (let item of actObjs) { if (item != allObjs[0]) { let i = getIndex(item) //0是背景,所以从1开始,但objs不包含背景图片,故要-1 objs.splice(i - 1, 1) canvas.remove(item) flag = 1 } } updateList() canvas.discardActiveObject() if (flag == 1) { recordState() canvas.renderAll() handleObjectSelected() } } }) let pre_add_image $('#addPic').click(function () { OpenDialog() function OpenDialog() { dialog .showOpenDialog({ title: language_str('selectPic'), //请选择图片 buttonLabel: language_str('comf'), //"确认" filters: [{ name: 'Image File Type', extensions: ['png', 'jpg', 'jpeg'] }] }) .then((result) => { if (result.canceled) return //console.log(result.filePaths) fabric.Image.fromURL(result.filePaths[0], function (image) { //image.left = pointer.x; //image.top = pointer.y; image.setSrc(image.toDataURL(), function (image) { pre_add_image = image background_image.hoverCursor = 'crosshair' $(this).css('background-color', '#646E76') $('#addOutPic').css('background-color', '') $('#addText').css('background-color', '') $("#addCircleText").css("background-color", ""); $('#addOutText').css('background-color', '') $('#addRect').css('background-color', '') $('#addCircle').css('background-color', '') $('#addLine').css('background-color', '') $('#addQrCode').css('background-color', '') $('#addBarCode').css('background-color', '') $('#addCounter').css('background-color', '') addState = 1 }) //canvas.add(image); //objs.push({type: 1}); //canvas.renderAll(); //updateList(); //recordState(); }) }) .catch((err) => { console.log(err) }) } }) $('#addOutPic').click(function () { background_image.hoverCursor = 'crosshair' $(this).css('background-color', '#646E76') $('#addPic').css('background-color', '') $('#addText').css('background-color', '') $("#addCircleText").css("background-color", ""); $('#addOutText').css('background-color', '') $('#addRect').css('background-color', '') $('#addCircle').css('background-color', '') $('#addLine').css('background-color', '') $('#addQrCode').css('background-color', '') $('#addBarCode').css('background-color', '') $('#addCounter').css('background-color', '') addState = 2 }) $('#addText').click(function () { background_image.hoverCursor = 'crosshair' $(this).css('background-color', '#646E76') $('#addPic').css('background-color', '') $('#addOutPic').css('background-color', '') $("#addCircleText").css("background-color", ""); $('#addOutText').css('background-color', '') $('#addRect').css('background-color', '') $('#addCircle').css('background-color', '') $('#addLine').css('background-color', '') $('#addQrCode').css('background-color', '') $('#addBarCode').css('background-color', '') $('#addCounter').css('background-color', '') addState = 3 }) $("#addCircleText").click(function () { background_image.hoverCursor = "crosshair"; $(this).css("background-color", "#646E76"); $("#addPic").css("background-color", ""); $("#addOutPic").css("background-color", ""); $("#addText").css("background-color", ""); $("#addOutText").css("background-color", ""); $("#addRect").css("background-color", ""); $("#addCircle").css("background-color", ""); $("#addLine").css("background-color", ""); $("#addQrCode").css("background-color", ""); $("#addBarCode").css("background-color", ""); $("#addCounter").css("background-color", ""); addState = 11; }); $('#addOutText').click(function () { background_image.hoverCursor = 'crosshair' $(this).css('background-color', '#646E76') $('#addPic').css('background-color', '') $('#addOutPic').css('background-color', '') $('#addText').css('background-color', '') $("#addCircleText").css("background-color", ""); $('#addRect').css('background-color', '') $('#addCircle').css('background-color', '') $('#addLine').css('background-color', '') $('#addQrCode').css('background-color', '') $('#addBarCode').css('background-color', '') $('#addCounter').css('background-color', '') addState = 4 }) $('#addRect').click(function () { background_image.hoverCursor = 'crosshair' $(this).css('background-color', '#646E76') $('#addPic').css('background-color', '') $('#addOutPic').css('background-color', '') $('#addText').css('background-color', '') $("#addCircleText").css("background-color", ""); $('#addOutText').css('background-color', '') $('#addCircle').css('background-color', '') $('#addLine').css('background-color', '') $('#addQrCode').css('background-color', '') $('#addBarCode').css('background-color', '') $('#addCounter').css('background-color', '') addState = 5 }) $('#addCircle').click(function () { background_image.hoverCursor = 'crosshair' $(this).css('background-color', '#646E76') $('#addPic').css('background-color', '') $('#addOutPic').css('background-color', '') $('#addText').css('background-color', '') $("#addCircleText").css("background-color", ""); $('#addOutText').css('background-color', '') $('#addRect').css('background-color', '') $('#addLine').css('background-color', '') $('#addQrCode').css('background-color', '') $('#addBarCode').css('background-color', '') $('#addCounter').css('background-color', '') addState = 6 }) $('#addLine').click(function () { background_image.hoverCursor = 'crosshair' $(this).css('background-color', '#646E76') $('#addPic').css('background-color', '') $('#addOutPic').css('background-color', '') $('#addText').css('background-color', '') $("#addCircleText").css("background-color", ""); $('#addOutText').css('background-color', '') $('#addRect').css('background-color', '') $('#addCircle').css('background-color', '') $('#addQrCode').css('background-color', '') $('#addBarCode').css('background-color', '') $('#addCounter').css('background-color', '') addState = 7 }) $('#addQrCode').click(function () { background_image.hoverCursor = 'crosshair' $(this).css('background-color', '#646E76') $('#addPic').css('background-color', '') $('#addOutPic').css('background-color', '') $('#addText').css('background-color', '') $("#addCircleText").css("background-color", ""); $('#addOutText').css('background-color', '') $('#addRect').css('background-color', '') $('#addCircle').css('background-color', '') $('#addLine').css('background-color', '') $('#addBarCode').css('background-color', '') $('#addCounter').css('background-color', '') addState = 8 }) $('#addBarCode').click(function () { background_image.hoverCursor = 'crosshair' $(this).css('background-color', '#646E76') $('#addPic').css('background-color', '') $('#addOutPic').css('background-color', '') $('#addText').css('background-color', '') $("#addCircleText").css("background-color", ""); $('#addOutText').css('background-color', '') $('#addRect').css('background-color', '') $('#addCircle').css('background-color', '') $('#addLine').css('background-color', '') $('#addQrCode').css('background-color', '') $('#addCounter').css('background-color', '') addState = 9 }) $('#addCounter').click(function () { background_image.hoverCursor = 'crosshair' $(this).css('background-color', '#646E76') $('#addPic').css('background-color', '') $('#addOutPic').css('background-color', '') $('#addText').css('background-color', '') $("#addCircleText").css("background-color", ""); $('#addOutText').css('background-color', '') $('#addRect').css('background-color', '') $('#addCircle').css('background-color', '') $('#addLine').css('background-color', '') $('#addQrCode').css('background-color', '') $('#addBarCode').css('background-color', '') addState = 10 }) $('#version_change').click(function () { if (bg_version == 1) { bg_version = 2 } else { bg_version = 1 } // 类型改变 $('#source_front').attr('src', './public/images/front_bg' + bg_version + '_2.png') canvas.renderAll() }) $('#front_side').click(function () { $(this).addClass('ui-button-active') $('#back_side').removeClass('ui-button-active') $('.canvas-container:eq(0)').show() $('.canvas-container:eq(1)').hide() console.log('------') console.log(recordObjs1) console.log('------') canvas = canvas1 objs = objs1 background_image = background_image1 next_objs = next_objs1 pre_objs = pre_objs1 next_json = next_json1 pre_json = pre_json1 recordObjs = recordObjs1 recordJson = recordJson1 step = step1 updateList() $('#line_control').hide() $('#base_control').hide() $('#pic_control').hide() $("#set_bg").hide(); $('#out_pic_control').hide() $('#text_control').hide() $("#circle_text_control").hide(); $('#out_text_control').hide() $('#rect_control').hide() $('#circle_control').hide() $('#counter_control').hide() $('#qrcode_Controll').hide() $('#barcode_controll').hide() $('#component_type').text(language_str('bg')) //背景 }) $('#back_side').click(function () { $(this).addClass('ui-button-active') $('#front_side').removeClass('ui-button-active') $('.canvas-container:eq(0)').hide() $('.canvas-container:eq(1)').show() canvas = canvas2 objs = objs2 background_image = background_image2 next_objs = next_objs2 pre_objs = pre_objs2 next_json = next_json2 pre_json = pre_json2 recordObjs = recordObjs2 recordJson = recordJson2 step = step2 updateList() $('#line_control').hide() $('#base_control').hide() $('#pic_control').hide() $("#set_bg").hide(); $('#out_pic_control').hide() $('#text_control').hide() $("#circle_text_control").hide(); $('#out_text_control').hide() $('#rect_control').hide() $('#circle_control').hide() $('#counter_control').hide() $('#qrcode_Controll').hide() $('#barcode_controll').hide() $('#component_type').text(language_str('bg')) //"背景" }) $('#top_alignment').click(function () { let _objs = canvas.getActiveObjects() if (_objs.length == 1) { //只选中了一个 _objs[0].set('top', background_image.get('top')) canvas.renderAll() return } let top = 0 for (let item of _objs) { let t_top = item.get('top') if (t_top < top) { top = t_top } } groupItems = [] for (let item of _objs) { item.set('top', top) groupItems.push(item) } canvas.discardActiveObject() let sel = new fabric.ActiveSelection(groupItems, { canvas: canvas }) canvas.setActiveObject(sel) canvas.requestRenderAll() canvas.renderAll() }) $('#bottom_alignment').click(function () { let _objs = canvas.getActiveObjects() if (_objs.length == 1) { //只选中了一个 let idx = getIndex(_objs[0]) let type = objs[idx - 1].type let other = 0 //strokeWidth if (type == 5 || type == 6 || type == 7) { other = _objs[0].get('strokeWidth') } _objs[0].set('top', background_image.get('top') + background_image.get('height') - _objs[0].get('height') * _objs[0].get('scaleY') - other) canvas.renderAll() return } let bottom = 0 for (let item of _objs) { let idx = getIndex(item) let type = objs[idx - 1].type let other = 0 //strokeWidth if (type == 5 || type == 6 || type == 7) { other = item.get('strokeWidth') } let t_b = item.get('top') + item.get('height') * item.get('scaleY') + other if (t_b > bottom) { bottom = t_b } } groupItems = [] for (let item of _objs) { let idx = getIndex(item) let type = objs[idx - 1].type let other = 0 //strokeWidth if (type == 5 || type == 6 || type == 7) { other = item.get('strokeWidth') } item.set('top', bottom - item.get('height') * item.get('scaleY') - other) groupItems.push(item) } canvas.discardActiveObject() let sel = new fabric.ActiveSelection(groupItems, { canvas: canvas }) canvas.setActiveObject(sel) canvas.requestRenderAll() canvas.renderAll() }) $('#center_y_alignment').click(function () { let _objs = canvas.getActiveObjects() if (_objs.length == 1) { //只选中了一个 let idx = getIndex(_objs[0]) let type = objs[idx - 1].type let other = 0 //strokeWidth if (type == 5 || type == 6 || type == 7) { other = _objs[0].get('strokeWidth') } _objs[0].set('top', background_image.get('top') + (background_image.get('height') - (_objs[0].get('height') + other) * _objs[0].get('scaleY')) / 2) canvas.renderAll() return } let top = 0 for (let item of _objs) { let t_top = item.get('top') if (t_top < top) { top = t_top } } groupItems = [] for (let item of _objs) { let idx = getIndex(item) let type = objs[idx - 1].type let other = 0 //strokeWidth if (type == 5 || type == 6 || type == 7) { other = item.get('strokeWidth') } item.set('top', top + (item.group.height - (item.get('height') + other) * item.get('scaleY')) / 2) groupItems.push(item) } canvas.discardActiveObject() let sel = new fabric.ActiveSelection(groupItems, { canvas: canvas }) canvas.setActiveObject(sel) canvas.requestRenderAll() canvas.renderAll() }) $('#left_alignment').click(function () { let _objs = canvas.getActiveObjects() if (_objs.length == 1) { //只选中了一个 _objs[0].set('left', background_image.get('left')) canvas.renderAll() return } let left = 0 for (let item of _objs) { let t_left = item.get('left') if (t_left < left) { left = t_left } } groupItems = [] for (let item of _objs) { item.set('left', left) groupItems.push(item) } canvas.discardActiveObject() let sel = new fabric.ActiveSelection(groupItems, { canvas: canvas }) canvas.setActiveObject(sel) canvas.requestRenderAll() canvas.renderAll() }) $('#right_alignment').click(function () { let _objs = canvas.getActiveObjects() if (_objs.length == 1) { //只选中了一个 let idx = getIndex(_objs[0]) let type = objs[idx - 1].type let other = 0 //strokeWidth if (type == 5 || type == 6 || type == 7) { other = item.get('strokeWidth') } _objs[0].set('left', background_image.get('left') + background_image.get('width') - _objs[0].get('width') * _objs[0].get('scaleX') - other) canvas.renderAll() return } let right = 0 for (let item of _objs) { let idx = getIndex(item) let type = objs[idx - 1].type let other = 0 //strokeWidth if (type == 5 || type == 6 || type == 7) { other = item.get('strokeWidth') } let t_r = item.get('left') + item.get('width') * item.get('scaleX') + other if (t_r > right) { right = t_r } } let groupItems = [] for (let item of _objs) { let idx = getIndex(item) let type = objs[idx - 1].type let other = 0 //strokeWidth if (type == 5 || type == 6 || type == 7) { other = item.get('strokeWidth') } item.set('left', right - item.get('width') * item.get('scaleX') - other) groupItems.push(item) } //BUG1 canvas.discardActiveObject() let sel = new fabric.ActiveSelection(groupItems, { canvas: canvas }) canvas.setActiveObject(sel) canvas.requestRenderAll() canvas.renderAll() }) $('#center_x_alignment').click(function () { let _objs = canvas.getActiveObjects() if (_objs.length == 1) { //只选中了一个 let idx = getIndex(_objs[0]) let type = objs[idx - 1].type let other = 0 //strokeWidth if (type == 5 || type == 6 || type == 7) { other = _objs[0].get('strokeWidth') } _objs[0].set('left', background_image.get('left') + (background_image.get('width') - (_objs[0].get('width') + other) * _objs[0].get('scaleX')) / 2) canvas.renderAll() return } let left = 0 for (let item of _objs) { let t_left = item.get('left') if (t_left < left) { left = t_left } } groupItems = [] for (let item of _objs) { let idx = getIndex(item) let type = objs[idx - 1].type let other = 0 //strokeWidth if (type == 5 || type == 6 || type == 7) { other = item.get('strokeWidth') } item.set('left', left + (item.group.width - (item.get('width') + other) * item.get('scaleX')) / 2) groupItems.push(item) } canvas.discardActiveObject() let sel = new fabric.ActiveSelection(groupItems, { canvas: canvas }) canvas.setActiveObject(sel) canvas.requestRenderAll() canvas.renderAll() }) $('#up_obj').click(function () { //上移,放到前面 数组中在后面 let idx = getIndex(canvas.getActiveObject()) if (idx + 1 != canvas.getObjects().length) { canvas.bringForward(canvas.getActiveObject()) canvas.renderAll() let temp = objs[idx - 1] objs[idx - 1] = objs[idx] objs[idx] = temp //console.log(objs); //[objs[idx-2],objs[idx-1]] = [objs[idx-1],objs[idx-2]]; recordState() updateList() selectObj(idx) } }) $('#down_obj').click(function () { //下移,放到后面 数组中在前面 let idx = getIndex(canvas.getActiveObject()) if (idx != 1) { canvas.sendBackwards(canvas.getActiveObject()) canvas.renderAll() //[objs[idx-2],objs[idx-1]] = [objs[idx-1],objs[idx-2]]; let temp = objs[idx - 1] objs[idx - 1] = objs[idx - 2] objs[idx - 2] = temp recordState() updateList() selectObj(idx - 2) } }) $('#set_bg').click(function () { //设置为背景 let obj = canvas.getActiveObject() let idx = getIndex(canvas.getActiveObject()) const scaleX = 1012 / obj.width const scaleY = 648 / obj.height obj.set({ scaleX: scaleX, scaleY: scaleY, left: ($('#canvas1').width() - 1012) / 2, top: ($('#canvas1').height() - 648) / 2 }) $('#text_w').val(1012) $('#text_h').val(648) $('#text_x').val(0) $('#text_y').val(0) canvas.sendToBack(canvas.getActiveObject()) canvas.bringForward(canvas.getActiveObject()) canvas.renderAll() let objItem = objs.splice(idx - 1, 1)[0] objs.unshift(objItem) recordState() updateList() selectObj(0) }) $('#previous').click(function () { //撤销一次操作 if (step.val == 0) { return } step.val-- console.log(recordJson[step.val]) canvas.loadFromJSON(recordJson[step.val]) if ($('#front_side').hasClass('ui-button-active')) { //objs = JSON.parse(recordObjs[step.val]); objs1 = JSON.parse(recordObjs[step.val]) objs = objs1 } else if ($('#back_side').hasClass('ui-button-active')) { //objs = JSON.parse(recordObjs[step.val]); objs2 = JSON.parse(recordObjs[step.val]) objs = objs2 } background_image = canvas.getObjects()[0] canvas.renderAll() //recordState(); updateList() selectObj(-1) $('#base_control').hide() $('#line_control').hide() $('#pic_control').hide() $("#set_bg").hide(); $('#out_pic_control').hide() $('#text_control').hide() $("#circle_text_control").hide(); $('#out_text_control').hide() $('#rect_control').hide() $('#circle_control').hide() $('#counter_control').hide() $('#qrcode_Controll').hide() $('#barcode_controll').hide() }) $('#next').click(function () { //撤销一次撤销操作 if (step.val >= recordObjs.length - 1) { return } ++step.val canvas.loadFromJSON(recordJson[step.val]) if ($('#front_side').hasClass('ui-button-active')) { //objs = JSON.parse(recordObjs[step.val]); objs1 = JSON.parse(recordObjs[step.val]) objs = objs1 } else if ($('#back_side').hasClass('ui-button-active')) { //objs = JSON.parse(recordObjs[step.val]); objs2 = JSON.parse(recordObjs[step.val]) objs = objs2 } background_image = canvas.getObjects()[0] canvas.renderAll() selectObj(-1) $('#base_control').hide() $('#line_control').hide() $('#pic_control').hide() $("#set_bg").hide(); $('#out_pic_control').hide() $('#text_control').hide() $("#circle_text_control").hide(); $('#out_text_control').hide() $('#rect_control').hide() $('#circle_control').hide() $('#counter_control').hide() $('#qrcode_Controll').hide() $('#barcode_controll').hide() updateList() }) $('#clean').click(function () { objs.splice(0, objs.length) let allObjs = canvas.getObjects() for (let item of allObjs) { if (item != allObjs[0]) { canvas.remove(item) } } updateList() recordState() }) $('#rotate').click(function () { let obj = canvas.getActiveObject() obj.rotate(Math.round((obj.get('angle') + 90) % 360)) $('#text_r').val(obj.get('angle')) canvas.renderAll() updateControls() recordState() }) $('#text_italics').click(function () { if ($(this).hasClass('ui-radio-acitve')) { //已选 canvas.getActiveObject().set('fontStyle', 'normal') $(this).removeClass('ui-radio-acitve') } else { //未选 canvas.getActiveObject().set('fontStyle', 'italic') $(this).addClass('ui-radio-acitve') } recordState() canvas.renderAll() }) $('#text_bold').click(function () { if ($(this).hasClass('ui-radio-acitve')) { //已选,恢复正常 canvas.getActiveObject().set('fontWeight', 'normal') $(this).removeClass('ui-radio-acitve') } else { //未选 canvas.getActiveObject().set('fontWeight', 'bold') $(this).addClass('ui-radio-acitve') } recordState() canvas.renderAll() }) $('#text_underline').click(function () { if ($(this).hasClass('ui-radio-acitve')) { //已选 canvas.getActiveObject().set('underline', false) $(this).removeClass('ui-radio-acitve') } else { //未选 canvas.getActiveObject().set('underline', true) $(this).addClass('ui-radio-acitve') } recordState() canvas.renderAll() }) $('#text_linethrough').click(function () { if ($(this).hasClass('ui-radio-acitve')) { //已选 canvas.getActiveObject().set('linethrough', false) $(this).removeClass('ui-radio-acitve') } else { //未选 canvas.getActiveObject().set('linethrough', true) $(this).addClass('ui-radio-acitve') } recordState() canvas.renderAll() }) $("#circle_text_italics").click(function () { if ($(this).hasClass("ui-radio-acitve")) { //已选 canvas.getActiveObject().set("fontStyle", "normal") $(this).removeClass("ui-radio-acitve") } else { //未选 canvas.getActiveObject().set("fontStyle", "italic") $(this).addClass("ui-radio-acitve") } recordState(); canvas.renderAll(); }); $("#circle_text_bold").click(function () { if ($(this).hasClass("ui-radio-acitve")) { //已选,恢复正常 canvas.getActiveObject().set("fontWeight", "normal") $(this).removeClass("ui-radio-acitve") } else { //未选 canvas.getActiveObject().set("fontWeight", "bold") $(this).addClass("ui-radio-acitve") } recordState(); canvas.renderAll(); }); $('#out_left_alignment').click(function () { $('#out_left_alignment').parent().removeClass('tool1') $('#out_right_alignment').parent().removeClass('tool1') $('#out_center_alignment').parent().removeClass('tool1') setTimeout(() => { $('#out_left_alignment').parent().addClass('tool1') }); canvas.getActiveObject().set('textAlign', 'left') let idx = getIndex(canvas.getActiveObject()) objs[idx - 1].align = 'left' recordState() canvas.renderAll() }) $('#out_right_alignment').click(function () { $('#out_left_alignment').parent().removeClass('tool1') $('#out_right_alignment').parent().removeClass('tool1') $('#out_center_alignment').parent().removeClass('tool1') setTimeout(() => { $('#out_right_alignment').parent().addClass('tool1') }); canvas.getActiveObject().set('textAlign', 'right') let idx = getIndex(canvas.getActiveObject()) objs[idx - 1].align = 'right' recordState() canvas.renderAll() }) $('#out_center_alignment').click(function () { $('#out_left_alignment').parent().removeClass('tool1') $('#out_right_alignment').parent().removeClass('tool1') $('#out_center_alignment').parent().removeClass('tool1') setTimeout(() => { $('#out_center_alignment').parent().addClass('tool1') }); canvas.getActiveObject().set('textAlign', 'center') let idx = getIndex(canvas.getActiveObject()) objs[idx - 1].align = 'center' recordState() canvas.renderAll() }) $('#out_text_italics').click(function () { if ($(this).hasClass('ui-radio-acitve')) { //已选 canvas.getActiveObject().set('fontStyle', 'normal') $(this).removeClass('ui-radio-acitve') } else { //未选 canvas.getActiveObject().set('fontStyle', 'italic') $(this).addClass('ui-radio-acitve') } recordState() canvas.renderAll() }) $('#out_text_bold').click(function () { if ($(this).hasClass('ui-radio-acitve')) { //已选,恢复正常 canvas.getActiveObject().set('fontWeight', 'normal') $(this).removeClass('ui-radio-acitve') } else { //未选 canvas.getActiveObject().set('fontWeight', 'bold') $(this).addClass('ui-radio-acitve') } recordState() canvas.renderAll() }) $('#out_text_underline').click(function () { if ($(this).hasClass('ui-radio-acitve')) { //已选 canvas.getActiveObject().set('underline', false) $(this).removeClass('ui-radio-acitve') } else { //未选 canvas.getActiveObject().set('underline', true) $(this).addClass('ui-radio-acitve') } recordState() canvas.renderAll() }) $('#out_text_linethrough').click(function () { if ($(this).hasClass('ui-radio-acitve')) { //已选 canvas.getActiveObject().set('linethrough', false) $(this).removeClass('ui-radio-acitve') } else { //未选 canvas.getActiveObject().set('linethrough', true) $(this).addClass('ui-radio-acitve') } recordState() canvas.renderAll() }) $('#lock').click(function () { canvas.getActiveObject().set('selectable', !canvas.getActiveObject().get('selectable')) if (canvas.getActiveObject().get('selectable')) { $('#lock_img').attr('src', 'public/images/unlock20.png') //已经上锁,需要解锁 } else { $('#lock_img').attr('src', 'public/images/lock20.png') //没上锁,可以上锁 } recordState() canvas.renderAll() }) $('#text_back_transparent').click(function () { canvas.getActiveObject().set('textBackgroundColor', '') $('#text_back_color').val('#ffffff') canvas.renderAll() }) $('#out_text_back_transparent').click(function () { canvas.getActiveObject().set('textBackgroundColor', '') $('#out_text_back_color').val('#ffffff') canvas.renderAll() }) $('#rect_transparent').click(function () { canvas.getActiveObject().set('fill', '') $('#rect_color').val('#ffffff') canvas.renderAll() }) $('#rect_stroke_transparent').click(function () { canvas.getActiveObject().set('stroke', '') $('#rect_stroke').val('#ffffff') canvas.renderAll() }) $('#circle_transparent').click(function () { canvas.getActiveObject().set('fill', '') $('#circle_color').val('#ffffff') canvas.renderAll() }) $('#circle_stroke_transparent').click(function () { canvas.getActiveObject().set('stroke', '') $('#circle_stroke').val('#ffffff') canvas.renderAll() }) function saveAs(op1, callback) { let j = canvas1.toJSON(['selectable', 'hoverable', 'hoverCursor', 'text', 'fontStyle', 'fontWeight', 'underline']) let b = canvas2.toJSON(['selectable', 'hoverable', 'hoverCursor', 'text', 'fontStyle', 'fontWeight', 'underline']) let _g1 = [], _g2 = [] let left = 0, top = 0 for (let _o of canvas1.getObjects()) { if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(_o.getCoords()) > left) { left = -(getCoordsMinX(_o.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(_o.getCoords()) > top) { top = -(getCoordsMinY(_o.getCoords()) - getCoordsMinY(background_image.getCoords())) } _g1.push(fabric.util.object.clone(_o)) } let fp = new fabric.Group(_g1).toDataURL({ height: 648, width: 1012, top: top / zoom, left: left / zoom }) ; (left = 0), (top = 0) for (let _o of canvas2.getObjects()) { if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(_o.getCoords()) > left) { left = -(getCoordsMinX(_o.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(_o.getCoords()) > top) { top = -(getCoordsMinY(_o.getCoords()) - getCoordsMinY(background_image.getCoords())) } _g2.push(fabric.util.object.clone(_o)) } //let fp = new fabric.Group(_g1).toDataURL(); let bp = new fabric.Group(_g2).toDataURL({ height: 648, width: 1012, top: top / zoom, left: left / zoom }) let o = { f: j, b: b, fo: objs1, bo: objs2, fp: fp, bp: bp } let con_o = Object.assign(o, op1) dialog .showSaveDialog({ title: language_str('saveFile'), //'保存文件' filters: [{ name: 'Soon File Type', extensions: ['soon'] }] }) .then((result) => { if (result.filePath == '') { return } if (result.filePath.substring(result.filePath.length - 5).indexOf('.') == -1) { result.filePath += '.soon' } let fs = require('fs') con_o.soonType = 2 fs.writeFileSync(result.filePath, JSON.stringify(con_o)) openAs.name = result.filePath layer.msg(language_str('saveSucc') + openAs.name) //'保存成功至' saveHistory() if (callback && typeof callback === 'function') { callback() } }) .catch((err) => { console.log() }) } function save(op1, callback) { let j = canvas1.toJSON(['selectable', 'hoverable', 'hoverCursor', 'text', 'fontStyle', 'fontWeight', 'underline']) let b = canvas2.toJSON(['selectable', 'hoverable', 'hoverCursor', 'text', 'fontStyle', 'fontWeight', 'underline']) let _g1 = [], _g2 = [] let left = 0, top = 0 for (let _o of canvas1.getObjects()) { if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(_o.getCoords()) > left) { left = -(getCoordsMinX(_o.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(_o.getCoords()) > top) { top = -(getCoordsMinY(_o.getCoords()) - getCoordsMinY(background_image.getCoords())) } _g1.push(fabric.util.object.clone(_o)) } let fp = new fabric.Group(_g1).toDataURL({ height: 648, width: 1012, top: top / zoom, left: left / zoom }) ; (left = 0), (top = 0) for (let _o of canvas2.getObjects()) { if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(_o.getCoords()) > left) { left = -(getCoordsMinX(_o.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(_o.getCoords()) > top) { top = -(getCoordsMinY(_o.getCoords()) - getCoordsMinY(background_image.getCoords())) } _g2.push(fabric.util.object.clone(_o)) } //let fp = new fabric.Group(_g1).toDataURL(); let bp = new fabric.Group(_g2).toDataURL({ height: 648, width: 1012, top: top / zoom, left: left / zoom }) let o = { f: j, b: b, fo: objs1, bo: objs2, fp: fp, bp: bp } let con_o = Object.assign(o, op1) console.log(op1) if (openAs.name != '') { //打开的文件 let fs = require('fs') con_o.soonType = 2 fs.writeFileSync(openAs.name, JSON.stringify(con_o)) layer.msg(language_str('saveSucc') + openAs.name) //'保存成功至' saveHistory() if (callback && typeof callback === 'function') { callback() } return } dialog .showSaveDialog({ title: language_str('saveFile'), //'保存文件' filters: [{ name: 'Soon File Type', extensions: ['soon'] }] }) .then((result) => { if (result.filePath == '') { return } if (result.filePath.substring(result.filePath.length - 5).indexOf('.') == -1) { result.filePath += '.soon' } let fs = require('fs') con_o.soonType = 2 fs.writeFileSync(result.filePath, JSON.stringify(con_o)) openAs.name = result.filePath layer.msg(language_str('saveSucc') + openAs.name) //'保存成功至' saveHistory() if (callback && typeof callback === 'function') { callback() } }) .catch((err) => { console.log() }) } // 复制 $("#copy").click(function () { copySelection(); }) // 粘贴 $("#paste").click(function () { pasteFromClipboard(); }) // 保存 $('#save').click(function () { output() return let j = canvas1.toJSON(['selectable', 'hoverable', 'hoverCursor', 'text', 'fontStyle', 'fontWeight', 'underline']) let b = canvas2.toJSON(['selectable', 'hoverable', 'hoverCursor', 'text', 'fontStyle', 'fontWeight', 'underline']) let _g1 = [], _g2 = [] let left = 0, top = 0 for (let _o of canvas1.getObjects()) { if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(_o.getCoords()) > left) { left = -(getCoordsMinX(_o.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(_o.getCoords()) > top) { top = -(getCoordsMinY(_o.getCoords()) - getCoordsMinY(background_image.getCoords())) } _g1.push(fabric.util.object.clone(_o)) } let fp = new fabric.Group(_g1).toDataURL({ height: 648, width: 1012, top: top / zoom, left: left / zoom }) ; (left = 0), (top = 0) for (let _o of canvas2.getObjects()) { if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(_o.getCoords()) > left) { left = -(getCoordsMinX(_o.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(_o.getCoords()) > top) { top = -(getCoordsMinY(_o.getCoords()) - getCoordsMinY(background_image.getCoords())) } _g2.push(fabric.util.object.clone(_o)) } //let fp = new fabric.Group(_g1).toDataURL(); let bp = new fabric.Group(_g2).toDataURL({ height: 648, width: 1012, top: top / zoom, left: left / zoom }) let o = { f: j, b: b, fo: objs1, bo: objs2, fp: fp, bp: bp } let con_o = Object.assign(o, op1) console.log(op1) if (openAs.name != '') { //打开的文件 let fs = require('fs') con_o.soonType = 2 fs.writeFileSync(openAs.name, JSON.stringify(con_o)) layer.msg(language_str('saveSucc') + openAs.name) //'保存成功至' saveHistory() return } dialog .showSaveDialog({ title: language_str('saveFile'), //'保存文件' filters: [{ name: 'Soon File Type', extensions: ['soon'] }] }) .then((result) => { if (result.filePath == '') { return } if (result.filePath.substring(result.filePath.length - 5).indexOf('.') == -1) { result.filePath += '.soon' } let fs = require('fs') con_o.soonType = 2 fs.writeFileSync(result.filePath, JSON.stringify(con_o)) openAs.name = result.filePath layer.msg(language_str('saveSucc') + openAs.name) //'保存成功至' saveHistory() }) .catch((err) => { console.log() }) }) function getDate() { let date = new Date() return date.getFullYear() + '-' + (date.getMonth() + 1) + '-' + date.getDate() } function getAbsoluteXY(_obj) { let coord = _obj.get('lineCoords') //let xs = [], ys = []; //for(let item in coord){ // xs.push(coord[item].x); // ys.push(coord[item].y); //} //xs.sort(function(a,b){return a-b}); //ys.sort(function(a,b){return a-b}); //return [xs[0], ys[0]]; return [_obj.get('left'), _obj.get('top')] } let fullPath = path.join(exePath, 'data.json') function saveHistory() { let fs = require('fs') let j = {} try { fsData = fs.readFileSync(fullPath) j = JSON.parse(fsData.toString()) for (let item of j.history) { if (item.path == openAs.name) { item.time = getDate() fs.writeFileSync(fullPath, JSON.stringify(j)) return } } j.history.push({ time: getDate(), path: openAs.name }) fs.writeFileSync(fullPath, JSON.stringify(j)) } catch (e) { let j = { history: { time: getDate(), path: openAs.name } } fs.writeFileSync(fullPath, JSON.stringify(j)) } } function open(file) { let fs = require('fs') var fsData = fs.readFileSync(file) openAs.name = file let j = JSON.parse(fsData.toString()) let left = background_image.left let top = background_image.top let new_left = j.f.objects[0].left let new_top = j.f.objects[0].top for (let o of j.f.objects) { o.left = o.left - new_left + left o.top = o.top - new_top + top } for (let o of j.b.objects) { o.left = o.left - new_left + left o.top = o.top - new_top + top } canvas1.loadFromJSON(j.f) canvas2.loadFromJSON(j.b) background_image1 = canvas1.getObjects()[0] background_image2 = canvas2.getObjects()[0] objs2 = j.bo objs1 = j.fo step1.val = 0 step2.val = 0 recordJson1 = [] recordJson2 = [] recordObjs1 = [] recordObjs2 = [] if ($('#front_side').hasClass('ui-button-active')) { objs = objs1 recordObjs = recordObjs1 recordJson = recordJson1 step = step1 background_image = background_image1 } else if ($('#back_side').hasClass('ui-button-active')) { objs = objs2 recordObjs = recordObjs2 recordJson = recordJson2 background_image = background_image2 step = step2 } canvas1.renderAll() canvas2.renderAll() updateList() /* 修复打开新文件后无法撤销的bug 2022-07-16 */ setTimeout(() => { recordObjs1.push(JSON.stringify(objs1)) let j1 = canvas1.toJSON(['selectable', 'hoverable', 'hoverCursor', 'text', 'fontStyle', 'fontWeight', 'underline']) j1.objects[0].hoverCursor = 'default' recordJson1.push(j1) recordObjs2.push(JSON.stringify(objs2)) let j2 = canvas2.toJSON(['selectable', 'hoverable', 'hoverCursor', 'text', 'fontStyle', 'fontWeight', 'underline']) j2.objects[0].hoverCursor = 'default' recordJson2.push(j2) }, 0) } $('#open').click(function () { if (step.val == 0) { OpenDialog(); return; } layer.confirm( '' + language_str('whetherSave') + '', function (index) { //confirm 是否保存当前文件? //let j = canvas1.toJSON(["selectable","hoverable","hoverCursor","text","fontStyle","fontWeight","underline"]); //let b = canvas2.toJSON(["selectable","hoverable","hoverCursor","text","fontStyle","fontWeight","underline"]); //let o = { f : j, b : b,fo : objs1, bo : objs2}; //if(openAs != ""){ // //打开的文件 // let fs = require('fs') // fs.writeFileSync(openAs,JSON.stringify(o)) // layer.msg('保存成功至'+ openAs); // // OpenDialog();return; //} //dialog.showSaveDialog({ // title:'保存文件', // filters: [ // { name: 'FCS File Type', extensions: ['fcs'] }, // ] //}).then(result=>{ // let fs = require('fs') // fs.writeFileSync(result.filePath,JSON.stringify(o)) // // OpenDialog(); //}).catch(err=>{ // console.log() //}) /* let j = canvas1.toJSON(["selectable","hoverable","hoverCursor","text","fontStyle","fontWeight","underline"]); let b = canvas2.toJSON(["selectable","hoverable","hoverCursor","text","fontStyle","fontWeight","underline"]); let _g1 = [], _g2 = []; let left = 0, top = 0; for( let _o of canvas1.getObjects() ){ if( getCoordsMinX(background_image.getCoords()) - getCoordsMinX(_o.getCoords()) > left){ left = -(getCoordsMinX(_o.getCoords()) - getCoordsMinX(background_image.getCoords())); } if( getCoordsMinY(background_image.getCoords()) - getCoordsMinY(_o.getCoords()) > top){ top = -(getCoordsMinY(_o.getCoords()) - getCoordsMinY(background_image.getCoords())); } _g1.push(fabric.util.object.clone(_o)); } let fp = new fabric.Group(_g1).toDataURL({ height: 648, width: 1012, top:top/zoom, left:left/zoom }); left = 0, top = 0; for( let _o of canvas2.getObjects() ){ if( getCoordsMinX(background_image.getCoords()) - getCoordsMinX(_o.getCoords()) > left){ left = -(getCoordsMinX(_o.getCoords()) - getCoordsMinX(background_image.getCoords())); } if( getCoordsMinY(background_image.getCoords()) - getCoordsMinY(_o.getCoords()) > top){ top = -(getCoordsMinY(_o.getCoords()) - getCoordsMinY(background_image.getCoords())); } _g2.push(fabric.util.object.clone(_o)); } //let fp = new fabric.Group(_g1).toDataURL(); let bp = new fabric.Group(_g2).toDataURL({ height: 648, width: 1012, top:top/zoom, left:left/zoom }); let o = { f : j, b : b,fo : objs1, bo : objs2,fp:fp,bp:bp}; if(openAs.name != ""){ //打开的文件 let fs = require('fs') fs.writeFileSync(openAs.name,JSON.stringify(o)) layer.msg(language_str("saveSucc")+ openAs.name);//'保存成功至' saveHistory(); OpenDialog(); return; } dialog.showSaveDialog({ title:language_str("saveFile"),//'保存文件' filters: [ { name: 'Soon File Type', extensions: ['soon'] }, ] }).then(result=>{ if(result.canceled)return; if(result.filePath.substring(result.filePath.length-5).indexOf('.') == -1){ result.filePath += '.soon'; } let fs = require('fs') fs.writeFileSync(result.filePath,JSON.stringify(o)) openAs.name = result.filePath; layer.msg(language_str("saveSucc")+ openAs.name);//'保存成功至' saveHistory(); OpenDialog(); }).catch(err=>{ console.log() }) */ output(OpenDialog) layer.close(index) }, function (index) { OpenDialog() } ) function OpenDialog() { dialog .showOpenDialog({ title: '请选择文件', //confirm buttonLabel: language_str('comf'), //"确认" filters: [{ name: 'Soon File Type', extensions: ['soon'] }] }) .then((result) => { if (result.canceled) return //console.log(result.filePaths) let fs = require('fs') var fsData = fs.readFileSync(result.filePaths[0]) openAs.name = result.filePaths[0] let j = JSON.parse(fsData.toString()) let type = j.soonType ? j.soonType : j.backBlackPic ? 2 : 1; if (type == 1) { ipcRenderer.send('open-design-page', openAs.name, type); return } let left = background_image.left let top = background_image.top let new_left = j.f.objects[0].left let new_top = j.f.objects[0].top for (let o of j.f.objects) { o.left = o.left - new_left + left o.top = o.top - new_top + top } for (let o of j.b.objects) { o.left = o.left - new_left + left o.top = o.top - new_top + top } canvas1.loadFromJSON(j.f) canvas2.loadFromJSON(j.b) background_image1 = canvas1.getObjects()[0] background_image2 = canvas2.getObjects()[0] objs2 = j.bo objs1 = j.fo step1.val = 0 step2.val = 0 recordJson1 = [] recordJson2 = [] recordObjs1 = [] recordObjs2 = [] if ($('#front_side').hasClass('ui-button-active')) { objs = objs1 recordObjs = recordObjs1 recordJson = recordJson1 step = step1 background_image = background_image1 } else if ($('#back_side').hasClass('ui-button-active')) { objs = objs2 recordObjs = recordObjs2 recordJson = recordJson2 background_image = background_image2 step = step2 } canvas1.renderAll() canvas2.renderAll() updateList() /* 修复打开新文件后无法撤销的bug 2022-07-16 */ setTimeout(() => { recordObjs1.push(JSON.stringify(objs1)) let j1 = canvas1.toJSON(['selectable', 'hoverable', 'hoverCursor', 'text', 'fontStyle', 'fontWeight', 'underline']) j1.objects[0].hoverCursor = 'default' recordJson1.push(j1) recordObjs2.push(JSON.stringify(objs2)) let j2 = canvas2.toJSON(['selectable', 'hoverable', 'hoverCursor', 'text', 'fontStyle', 'fontWeight', 'underline']) j2.objects[0].hoverCursor = 'default' recordJson2.push(j2) }, 0) }) .catch((err) => { console.log(err) }) } }) function clearAll() { //let blank = "{\"f\":{\"version\":\"4.6.0\",\"objects\":[{\"type\":\"image\",\"version\":\"4.6.0\",\"originX\":\"left\",\"originY\":\"top\",\"left\":253.5,\"top\":121.5,\"width\":1012,\"height\":648,\"fill\":\"#000000\",\"stroke\":null,\"strokeWidth\":0,\"strokeDashArray\":null,\"strokeLineCap\":\"butt\",\"strokeDashOffset\":0,\"strokeLineJoin\":\"miter\",\"strokeUniform\":false,\"strokeMiterLimit\":4,\"scaleX\":1,\"scaleY\":1,\"angle\":0,\"flipX\":false,\"flipY\":false,\"opacity\":1,\"shadow\":null,\"visible\":true,\"backgroundColor\":\"\",\"fillRule\":\"nonzero\",\"paintFirst\":\"fill\",\"globalCompositeOperation\":\"source-over\",\"skewX\":0,\"skewY\":0,\"cropX\":0,\"cropY\":0,\"selectable\":false,\"hoverable\":false,\"hoverCursor\":\"default\",\"src\":\"data:image/png;base64,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YFB3cgsTIECAAAECBAgQIECAAIEsIBhkIxMECBAgQIAAAQIECBAgQKBOQDCoO7mFCRAgQIAAAQIECBAgQIBAFhAMspEJAgQIECBAgAABAgQIECBQJyAY1J3cwgQIECBAgAABAgQIECBAIAsIBtnIBAECBAgQIECAAAECBAgQqBMQDOpObmECBAgQIECAAAECBAgQIJAFBINsZIIAAQIECBAgQIAAAQIECNQJCAZ1J7cwAQIECBAgQIAAAQIECBDIAoJBNjJBgAABAgQIECBAgAABAgTqBASDupNbmAABAgQIECBAgAABAgQIZAHBIBuZIECAAAECBAgQIECAAAECdQKCQd3JLUyAAAECBAgQIECAAAECBLKAYJCNTBAgQIAAAQIECBAgQIAAgToBwaDu5BYmQIAAAQIECBAgQIAAAQJZQDDIRiYIECBAgAABAgQIECBAgECdgGBQd3ILEyBAgAABAgQIECBAgACBLCAYZCMTBAgQIECAAAECBAgQIECgTkAwqDu5hQkQIECAAAECBAgQIECAQBYQDLKRCQIECBAgQIAAAQIECBAgUCcgGNSd3MIECBAgQIAAAQIECBAgQCALCAbZyAQBAgQIECBAgAABAgQIEKgTEAzqTm5hAgQIECBAgAABAgQIECCQBQSDbGSCAAECBAgQIECAAAECBAjUCQgGdSe3MAECBAgQIECAAAECBAgQyAKCQTYyQYAAAQIECBAgQIAAAQIE6gQEg7qTW5gAAQIECBAgQIAAAQIECGQBwSAbmSBAgAABAgQIECBAgAABAnUCgkHdyS1MgAABAgQIECBAgAABAgSygGCQjUwQIECAAAECBAgQIECAAIE6AcGg7uQWJkCAAAECBAgQIECAAAECWUAwyEYmCBAgQIAAAQIECBAgQIBAnYBgUHdyCxMgQIAAAQIECBAgQIAAgSwgGGQjEwQIECBAgAABAgQIECBAoE5AMKg7uYUJECBAgAABAgQIECBAgEAWEAyykQkCBAgQIECAAAECBAgQIFAnIBjUndzCBAgQIECAAAECBAgQIEAgCwgG2cgEAQIECBAgQIAAAQIECBCoExAM6k5uYQIECBAgQIAAAQIECBAgkAUEg2xkggABAgQIECBAgAABAgQI1AkIBnUntzABAgQIECBAgAABAgQIEMgCgkE2MkGAAAECBAgQIECAAAECBOoEBIO6k1uYAAECBAgQIECAAAECBAhkAcEgG5kgQIAAAQIECBAgQIAAAQJ1AoJB3cktTIAAAQIECBAgQIAAAQIEsoBgkI1MECBAgAABAgQIECBAgACBOgHBoO7kFiZAgAABAgQIECBAgAABAllAMMhGJggQIECAAAECBAgQIECAQJ2AYFB3cgsTIECAAAECBAgQIECAAIEsIBhkIxMECBAgQIAAAQIECBAgQKBOQDCoO7mFCRAgQIAAAQIECBAgQIBAFhAMspEJAgQIECBAgAABAgQIECBQJyAY1J3cwgQIECBAgAABAgQIECBAIAsIBtnIBAECBAgQIECAAAECBAgQqBMQDOpObmECBAgQIECAAAECBAgQIJAFBINsZIIAAQIECBAgQIAAAQIECNQJCAZ1J7cwAQIECBAgQIAAAQIECBDIAoJBNjJBgAABAgQIECBAgAABAgTqBASDupNbmAABAgQIECBAgAABAgQIZAHBIBuZIECAAAECBAgQIECAAAECdQKCQd3JLUyAAAECBAgQIECAAAECBLKAYJCNTBAgQIAAAQIECBAgQIAAgToBwaDu5BYmQIAAAQIECBAgQIAAAQJZQDDIRiYIECBAgAABAgQIECBAgECdgGBQd3ILEyBAgAABAgQIECBAgACBLCAYZCMTBAgQIECAAAECBAgQIECgTkAwqDu5hQkQIECAAAECBAgQIECAQBYQDLKRCQIECBAgQIAAAQIECBAgUCcgGNSd3MIECBAgQIAAAQIECBAgQCALCAbZyAQBAgQIECBAgAABAgQIEKgTEAzqTm5hAgQIECBAgAABAgQIECCQBQSDbGSCAAECBAgQIECAAAECBAjUCQgGdSe3MAECBAgQIECAAAECBAgQyAKCQTYyQYAAAQIECBAgQIAAAQIE6gQEg7qTW5gAAQIECBAgQIAAAQIECGQBwSAbmSBAgAABAgQIECBAgAABAnUCgkHdyS1MgAABAgQIECBAgAABAgSygGCQjUwQIECAAAECBAgQIECAAIE6AcGg7uQWJkCAAAECBAgQIECAAAECWUAwyEYmCBAgQIAAAQIECBAgQIBAnYBgUHdyCxMgQIAAAQIECBAgQIAAgSwgGGQjEwQIECBAgAABAgQIECBAoE5AMKg7uYUJECBAgAABAgQIECBAgEAWEAyykQkCBAgQIECAAAECBAgQIFAnIBjUndzCBAgQIECAAAECBAgQIEAgCwgG2cgEAQIECBAgQIAAAQIECBCoExAM6k5uYQIECBAgQIAAAQIECBAgkAUEg2xkggABAgQIECBAgAABAgQI1AkIBnUntzABAgQIECBAgAABAgQIEMgCgkE2MkGAAAECBAgQIECAAAECBOoEBIO6k1uYAAECBAgQIECAAAECBAhkAcEgG5kgQIAAAQIECBAgQIAAAQJ1AoJB3cktTIAAAQIECBAgQIAAAQIEsoBgkI1MECBAgAABAgQIECBAgACBOgHBoO7kFiZAgAABAgQIECBAgAABAllAMMhGJggQIECAAAECBAgQIECAQJ2AYFB3cgsTIECAAAECBAgQIECAAIEsIBhkIxMECBAgQIAAAQIECBAgQKBOQDCoO7mFCRAgQIAAAQIECBAgQIBAFhAMspEJAgQIECBAgAABAgQIECBQJyAY1J3cwgQIECBAgAABAgQIECBAIAsIBtnIBAECBAgQIECAAAECBAgQqBMQDOpObmECBAgQIECAAAECBAgQIJAFBINsZIIAAQIECBAgQIAAAQIECNQJCAZ1J7cwAQIECBAgQIAAAQIECBDIAoJBNjJBgAABAgQIECBAgAABAgTqBASDupNbmAABAgQIECBAgAABAgQIZAHBIBuZIECAAAECBAgQIECAAAECdQKCQd3JLUyAAAECBAgQIECAAAECBLKAYJCNTBAgQIAAAQIECBAgQIAAgToBwaDu5BYmQIAAAQIECBAgQIAAAQJZQDDIRiYIECBAgAABAgQIECBAgECdgGBQd3ILEyBAgAABAgQIECBAgACBLCAYZCMTBAgQIECAAAECBAgQIECgTkAwqDu5hQkQIECAAAECBAgQIECAQBYQDLKRCQIECBAgQIAAAQIECBAgUCcgGNSd3MIECBAgQIAAAQIECBAgQCALCAbZyAQBAgQIECBAgAABAgQIEKgTEAzqTm5hAgQIECBAgAABAgQIECCQBQSDbGSCAAECBAgQIECAAAECBAjUCQgGdSe3MAECBAgQIECAAAECBAgQyAKCQTYyQYAAAQIECBAgQIAAAQIE6gQEg7qTW5gAAQIECBAgQIAAAQIECGQBwSAbmSBAgAABAgQIECBAgAABAnUCgkHdyS1MgAABAgQIECBAgAABAgSygGCQjUwQIECAAAECBAgQIECAAIE6AcGg7uQWJkCAAAECBAgQIECAAAECWUAwyEYmCBAgQIAAAQIECBAgQIBAnYBgUHdyCxMgQIAAAQIECBAgQIAAgSwgGGQjEwQIECBAgAABAgQIECBAoE5AMKg7uYUJECBAgAABAgQIECBAgEAWEAyykQkCBAgQIECAAAECBAgQIFAnIBjUndzCBAgQIECAAAECBAgQIEAgCwgG2cgEAQIECBAgQIAAAQIECBCoExAM6k5uYQIECBAgQIAAAQIECBAgkAUEg2xkggABAgQIECBAgAABAgQI1AkIBnUntzABAgQIECBAgAABAgQIEMgCgkE2MkGAAAECBAgQIECAAAECBOoEBIO6k1uYAAECBAgQIECAAAECBAhkAcEgG5kgQIAAAQIECBAgQIAAAQJ1AoJB3cktTIAAAQIECBAgQIAAAQIEsoBgkI1MECBAgAABAgQIECBAgACBOgHBoO7kFiZAgAABAgQIECBAgAABAllAMMhGJggQIECAAAECBAgQIECAQJ2AYFB3cgsTIECAAAECBAgQIECAAIEsIBhkIxMECBAgQIAAAQIECBAgQKBOQDCoO7mFCRAgQIAAAQIECBAgQIBAFhAMspEJAgQIECBAgAABAgQIECBQJyAY1J3cwgQIECBAgAABAgQIECBAIAsIBtnIBAECBAgQIECAAAECBAgQqBMQDOpObmECBAgQIECAAAECBAgQIJAFBINsZIIAAQIECBAgQIAAAQIECNQJCAZ1J7cwAQIECBAgQIAAAQIECBDIAoJBNjJBgAABAgQIECBAgAABAgTqBASDupNbmAABAgQIECBAgAABAgQIZAHBIBuZIECAAAECBAgQIECAAAECdQKCQd3JLUyAAAECBAgQIECAAAECBLKAYJCNTBAgQIAAAQIECBAgQIAAgToBwaDu5BYmQIAAAQIECBAgQIAAAQJZQDDIRiYIECBAgAABAgQIECBAgECdgGBQd3ILEyBAgAABAgQIECBAgACBLCAYZCMTBAgQIECAAAECBAgQIECgTkAwqDu5hQkQIECAAAECBAgQIECAQBYQDLKRCQIECBAgQIAAAQIECBAgUCcgGNSd3MIECBAgQIAAAQIECBAgQCALCAbZyAQBAgQIECBAgAABAgQIEKgTEAzqTm5hAgQIECBAgAABAgQIECCQBQSDbGSCAAECBAgQIECAAAECBAjUCQgGdSe3MAECBAgQIECAAAECBAgQyAKCQTYyQYAAAQIECBAgQIAAAQIE6gQEg7qTW5gAAQIECBAgQIAAAQIECGQBwSAbmSBAgAABAgQIECBAgAABAnUCgkHdyS1MgAABAgQIECBAgAABAgSygGCQjUwQIECAAAECBAgQIECAAIE6AcGg7uQWJkCAAAECBAgQIECAAAECWUAwyEYmCBAgQIAAAQIECBAgQIBAnYBgUHdyCxMgQIAAAQIECBAgQIAAgSwgGGQjEwQIECBAgAABAgQIECBAoE5AMKg7uYUJECBAgAABAgQIECBAgEAWEAyykQkCBAgQIECAAAECBAgQIFAnIBjUndzCBAgQIECAAAECBAgQIEAgCwgG2cgEAQIECBAgQIAAAQIECBCoExAM6k5uYQIECBAgQIAAAQIECBAgkAUEg2xkggABAgQIECBAgAABAgQI1AkIBnUntzABAgQIECBAgAABAgQIEMgCgkE2MkGAAAECBAgQIECAAAECBOoEBIO6k1uYAAECBAgQIECAAAECBAhkAcEgG5kgQIAAAQIECBAgQIAAAQJ1AoJB3cktTIAAAQIECBAgQIAAAQIEsoBgkI1MECBAgAABAgQIECBAgACBOgHBoO7kFiZAgAABAgQIECBAgAABAllAMMhGJggQIECAAAECBAgQIECAQJ2AYFB3cgsTIECAAAECBAgQIECAAIEsIBhkIxMECBAgQIAAAQIECBAgQKBOQDCoO7mFCRAgQIAAAQIECBAgQIBAFhAMspEJAgQIECBAgAABAgQIECBQJyAY1J3cwgQIECBAgAABAgQIECBAIAsIBtnIBAECBAgQIECAAAECBAgQqBMQDOpObmECBAgQIECAAAECBAgQIJAFBINsZIIAAQIECBAgQIAAAQIECNQJCAZ1J7cwAQIECBAgQIAAAQIECBDIAoJBNjJBgAABAgQIECBAgAABAgTqBASDupNbmAABAgQIECBAgAABAgQIZAHBIBuZIECAAAECBAgQIECAAAECdQKCQd3JLUyAAAECBAgQIECAAAECBLKAYJCNTBAgQIAAAQIECBAgQIAAgToBwaDu5BYmQIAAAQIECBAgQIAAAQJZQDDIRiYIECBAgAABAgQIECBAgECdgGBQd3ILEyBAgAABAgQIECBAgACBLCAYZCMTBAgQIECAAAECBAgQIECgTkAwqDu5hQkQIECAAAECBAgQIECAQBYQDLKRCQIECBAgQIAAAQIECBAgUCcgGNSd3MIECBAgQIAAAQIECBAgQCALCAbZyAQBAgQIECBAgAABAgQIEKgTEAzqTm5hAgQIECBAgAABAgQIECCQBQSDbGSCAAECBAgQIECAAAECBAjUCQgGdSe3MAECBAgQIECAAAECBAgQyAKCQTYyQYAAAQIECBAgQIAAAQIE6gQEg7qTW5gAAQIECBAgQIAAAQIECGQBwSAbmSBAgAABAgQIECBAgAABAnUCgkHdyS1MgAABAgQIECBAgAABAgSygGCQjUwQIECAAAECBAgQIECAAIE6AcGg7uQWJkCAAAECBAgQIECAAAECWUAwyEYmCBAgQIAAAQIECBAgQIBAnYBgUHdyCxMgQIAAAQIECBAgQIAAgSwgGGQjEwQIECBAgAABAgQIECBAoE5AMKg7uYUJECBAgAABAgQIECBAgEAWEAyykQkCBAgQIECAAAECBAgQIFAnIBjUndzCBAgQIECAAAECBAgQIEAgCwgG2cgEAQIECBAgQIAAAQIECBCoExAM6k5uYQIECBAgQIAAAQIECBAgkAUEg2xkggABAgQIECBAgAABAgQI1AkIBnUntzABAgQIECBAgAABAgQIEMgCgkE2MkGAAAECBAgQIECAAAECBOoEBIO6k1uYAAECBAgQIECAAAECBAhkAcEgG5kgQIAAAQIECBAgQIAAAQJ1AoJB3cktTIAAAQIECBAgQIAAAQIEsoBgkI1MECBAgAABAgQIECBAgACBOgHBoO7kFiZAgAABAgQIECBAgAABAllAMMhGJggQIECAAAECBAgQIECAQJ2AYFB3cgsTIECAAAECBAgQIECAAIEsIBhkIxMECBAgQIAAAQIECBAgQKBOQDCoO7mFCRAgQIAAAQIECBAgQIBAFhAMspEJAgQIECBAgAABAgQIECBQJyAY1J3cwgQIECBAgAABAgQIECBAIAsIBtnIBAECBAgQIECAAAECBAgQqBMQDOpObmECBAgQIECAAAECBAgQIJAFBINsZIIAAQIECBAgQIAAAQIECNQJCAZ1J7cwAQIECBAgQIAAAQIECBDIAoJBNjJBgAABAgQIECBAgAABAgTqBASDupNbmAABAgQIECBAgAABAgQIZAHBIBuZIECAAAECBAgQIECAAAECdQKCQd3JLUyAAAECBAgQIECAAAECBLKAYJCNTBAgQIAAAQIECBAgQIAAgToBwaDu5BYmQIAAAQIECBAgQIAAAQJZQDDIRiYIECBAgAABAgQIECBAgECdgGBQd3ILEyBAgAABAgQIECBAgACBLCAYZCMTBAgQIECAAAECBAgQIECgTkAwqDu5hQkQIECAAAECBAgQIECAQBYQDLKRCQIECBAgQIAAAQIECBAgUCcgGNSd3MIECBAgQIAAAQIECBAgQCALCAbZyAQBAgQIECBAgAABAgQIEKgTEAzqTm5hAgQIECBAgAABAgQIECCQBQSDbGSCAAECBAgQIECAAAECBAjUCQgGdSe3MAECBAgQIECAAAECBAgQyAKCQTYyQYAAAQIECBAgQIAAAQIE6gQEg7qTW5gAAQIECBAgQIAAAQIECGQBwSAbmSBAgAABAgQIECBAgAABAnUCgkHdyS1MgAABAgQIECBAgAABAgSygGCQjUwQIECAAAECBAgQIECAAIE6AcGg7uQWJkCAAAECBAgQIECAAAECWUAwyEYmCBAgQIAAAQIECBAgQIBAnYBgUHdyCxMgQIAAAQIECBAgQIAAgSwgGGQjEwQIECBAgAABAgQIECBAoE5AMKg7uYUJECBAgAABAgQIECBAgEAWEAyykQkCBAgQIECAAAECBAgQIFAnIBjUndzCBAgQIECAAAECBAgQIEAgCwgG2cgEAQIECBAgQIAAAQIECBCoExAM6k5uYQIECBAgQIAAAQIECBAgkAUEg2xkggABAgQIECBAgAABAgQI1AkIBnUntzABAgQIECBAgAABAgQIEMgCgkE2MkGAAAECBAgQIECAAAECBOoEBIO6k1uYAAECBAgQIECAAAECBAhkAcEgG5kgQIAAAQIECBAgQIAAAQJ1AoJB3cktTIAAAQIECBAgQIAAAQIEsoBgkI1MECBAgAABAgQIECBAgACBOgHBoO7kFiZAgAABAgQIECBAgAABAllAMMhGJggQIECAAAECBAgQIECAQJ2AYFB3cgsTIECAAAECBAgQIECAAIEsIBhkIxMECBAgQIAAAQIECBAgQKBOQDCoO7mFCRAgQIAAAQIECBAgQIBAFhAMspEJAgQIECBAgAABAgQIECBQJyAY1J3cwgQIECBAgAABAgQIECBAIAsIBtnIBAECBAgQIECAAAECBAgQqBMQDOpObmECBAgQIECAAAECBAgQIJAFBINsZIIAAQIECBAgQIAAAQIECNQJCAZ1J7cwAQIECBAgQIAAAQIECBDIAoJBNjJBgAABAgQIECBAgAABAgTqBASDupNbmAABAgQIECBAgAABAgQIZAHBIBuZIECAAAECBAgQIECAAAECdQKCQd3JLUyAAAECBAgQIEDpfCiFAAAcY0lEQVSAAAECBLKAYJCNTBAgQIAAAQIECBAgQIAAgToBwaDu5BYmQIAAAQIECBAgQIAAAQJZQDDIRiYIECBAgAABAgQIECBAgECdgGBQd3ILEyBAgAABAgQIECBAgACBLCAYZCMTBAgQIECAAAECBAgQIECgTkAwqDu5hQkQIECAAAECBAgQIECAQBYQDLKRCQIECBAgQIAAAQIECBAgUCcgGNSd3MIECBAgQIAAAQIECBAgQCALCAbZyAQBAgQIECBAgAABAgQIEKgTEAzqTm5hAgQIECBAgAABAgQIECCQBQSDbGSCAAECBAgQIECAAAECBAjUCQgGdSe3MAECBAgQIECAAAECBAgQyAKCQTYyQYAAAQIECBAgQIAAAQIE6gQEg7qTW5gAAQIECBAgQIAAAQIECGQBwSAbmSBAgAABAgQIECBAgAABAnUCgkHdyS1MgAABAgQIECBAgAABAgSygGCQjUwQIECAAAECBAgQIECAAIE6AcGg7uQWJkCAAAECBAgQIECAAAECWUAwyEYmCBAgQIAAAQIECBAgQIBAnYBgUHdyCxMgQIAAAQIECBAgQIAAgSwgGGQjEwQIECBAgAABAgQIECBAoE5AMKg7uYUJECBAgAABAgQIECBAgEAWEAyykQkCBAgQIECAAAECBAgQIFAnIBjUndzCBAgQIECAAAECBAgQIEAgCwgG2cgEAQIECBAgQIAAAQIECBCoExAM6k5uYQIECBAgQIAAAQIECBAgkAUEg2xkggABAgQIECBAgAABAgQI1AkIBnUntzABAgQIECBAgAABAgQIEMgCgkE2MkGAAAECBAgQIECAAAECBOoEBIO6k1uYAAECBAgQIECAAAECBAhkAcEgG5kgQIAAAQIECBAgQIAAAQJ1AoJB3cktTIAAAQIECBAgQIAAAQIEsoBgkI1MECBAgAABAgQIECBAgACBOgHBoO7kFiZAgAABAgQIECBAgAABAllAMMhGJggQIECAAAECBAgQIECAQJ2AYFB3cgsTIECAAAECBAgQIECAAIEsIBhkIxMECBAgQIAAAQIECBAgQKBOQDCoO7mFCRAgQIAAAQIECBAgQIBAFhAMspEJAgQIECBAgAABAgQIECBQJyAY1J3cwgQIECBAgAABAgQIECBAIAsIBtnIBAECBAgQIECAAAECBAgQqBMQDOpObmECBAgQIECAAAECBAgQIJAFBINsZIIAAQIECBAgQIAAAQIECNQJCAZ1J7cwAQIECBAgQIAAAQIECBDIAoJBNjJBgAABAgQIECBAgAABAgTqBASDupNbmAABAgQIECBAgAABAgQIZAHBIBuZIECAAAECBAgQIECAAAECdQKCQd3JLUyAAAECBAgQIECAAAECBLKAYJCNTBAgQIAAAQIECBAgQIAAgToBwaDu5BYmQIAAAQIECBAgQIAAAQJZQDDIRiYIECBAgAABAgQIECBAgECdgGBQd3ILEyBAgAABAgQIECBAgACBLCAYZCMTBAgQIECAAAECBAgQIECgTkAwqDu5hQkQIECAAAECBAgQIECAQBYQDLKRCQIECBAgQIAAAQIECBAgUCcgGNSd3MIECBAgQIAAAQIECBAgQCALCAbZyAQBAgQIECBAgAABAgQIEKgTEAzqTm5hAgQIECBAgAABAgQIECCQBQSDbGSCAAECBAgQIECAAAECBAjUCQgGdSe3MAECBAgQIECAAAECBAgQyAKCQTYyQYAAAQIECBAgQIAAAQIE6gQEg7qTW5gAAQIECBAgQIAAAQIECGQBwSAbmSBAgAABAgQIECBAgAABAnUCgkHdyS1MgAABAgQIECBAgAABAgSygGCQjUwQIECAAAECBAgQIECAAIE6AcGg7uQWJkCAAAECBAgQIECAAAECWUAwyEYmCBAgQIAAAQIECBAgQIBAnYBgUHdyCxMgQIAAAQIECBAgQIAAgSwgGGQjEwQIECBAgAABAgQIECBAoE5AMKg7uYUJECBAgAABAgQIECBAgEAWEAyykQkCBAgQIECAAAECBAgQIFAnIBjUndzCBAgQIECAAAECBAgQIEAgCwgG2cgEAQIECBAgQIAAAQIECBCoExAM6k5uYQIECBAgQIAAAQIECBAgkAUEg2xkggABAgQIECBAgAABAgQI1AkIBnUntzABAgQIECBAgAABAgQIEMgCgkE2MkGAAAECBAgQIECAAAECBOoEBIO6k1uYAAECBAgQIECAAAECBAhkAcEgG5kgQIAAAQIECBAgQIAAAQJ1AoJB3cktTIAAAQIECBAgQIAAAQIEsoBgkI1MECBAgAABAgQIECBAgACBOgHBoO7kFiZAgAABAgQIECBAgAABAllAMMhGJggQIECAAAECBAgQIECAQJ2AYFB3cgsTIECAAAECBAgQIECAAIEsIBhkIxMECBAgQIAAAQIECBAgQKBOQDCoO7mFCRAgQIAAAQIECBAgQIBAFhAMspEJAgQIECBAgAABAgQIECBQJyAY1J3cwgQIECBAgAABAgQIECBAIAsIBtnIBAECBAgQIECAAAECBAgQqBMQDOpObmECBAgQIECAAAECBAgQIJAFBINsZIIAAQIECBAgQIAAAQIECNQJCAZ1J7cwAQIECBAgQIAAAQIECBDIAoJBNjJBgAABAgQIECBAgAABAgTqBASDupNbmAABAgQIECBAgAABAgQIZAHBIBuZIECAAAECBAgQIECAAAECdQKCQd3JLUyAAAECBAgQIECAAAECBLKAYJCNTBAgQIAAAQIECBAgQIAAgToBwaDu5BYmQIAAAQIECBAgQIAAAQJZQDDIRiYIECBAgAABAgQIECBAgECdgGBQd3ILEyBAgAABAgQIECBAgACBLCAYZCMTBAgQIECAAAECBAgQIECgTkAwqDu5hQkQIECAAAECBAgQIECAQBYQDLKRCQIECBAgQIAAAQIECBAgUCcgGNSd3MIECBAgQIAAAQIECBAgQCALCAbZyAQBAgQIECBAgAABAgQIEKgTEAzqTm5hAgQIECBAgAABAgQIECCQBQSDbGSCAAECBAgQIECAAAECBAjUCQgGdSe3MAECBAgQIECAAAECBAgQyAKCQTYyQYAAAQIECBAgQIAAAQIE6gQEg7qTW5gAAQIECBAgQIAAAQIECGQBwSAbmSBAgAABAgQIECBAgAABAnUCgkHdyS1MgAABAgQIECBAgAABAgSygGCQjUwQIECAAAECBAgQIECAAIE6AcGg7uQWJkCAAAECBAgQIECAAAECWUAwyEYmCBAgQIAAAQIECBAgQIBAnYBgUHdyCxMgQIAAAQIECBAgQIAAgSwgGGQjEwQIECBAgAABAgQIECBAoE5AMKg7uYUJECBAgAABAgQIECBAgEAWEAyykQkCBAgQIECAAAECBAgQIFAnIBjUndzCBAgQIECAAAECBAgQIEAgCwgG2cgEAQIECBAgQIAAAQIECBCoExAM6k5uYQIECBAgQIAAAQIECBAgkAUEg2xkggABAgQIECBAgAABAgQI1AkIBnUntzABAgQIECBAgAABAgQIEMgCgkE2MkGAAAECBAgQIECAAAECBOoEBIO6k1uYAAECBAgQIECAAAECBAhkAcEgG5kgQIAAAQIECBAgQIAAAQJ1AoJB3cktTIAAAQIECBAgQIAAAQIEsoBgkI1MECBAgAABAgQIECBAgACBOgHBoO7kFiZAgAABAgQIECBAgAABAllAMMhGJggQIECAAAECBAgQIECAQJ2AYFB3cgsTIECAAAECBAgQIECAAIEsIBhkIxMECBAgQIAAAQIECBAgQKBOQDCoO7mFCRAgQIAAAQIECBAgQIBAFhAMspEJAgQIECBAgAABAgQIECBQJyAY1J3cwgQIECBAgAABAgQIECBAIAsIBtnIBAECBAgQIECAAAECBAgQqBMQDOpObmECBAgQIECAAAECBAgQIJAFBINsZIIAAQIECBAgQIAAAQIECNQJCAZ1J7cwAQIECBAgQIAAAQIECBDIAoJBNjJBgAABAgQIECBAgAABAgTqBASDupNbmAABAgQIECBAgAABAgQIZAHBIBuZIECAAAECBAgQIECAAAECdQKCQd3JLUyAAAECBAgQIECAAAECBLKAYJCNTBAgQIAAAQIECBAgQIAAgToBwaDu5BYmQIAAAQIECBAgQIAAAQJZQDDIRiYIECBAgAABAgQIECBAgECdgGBQd3ILEyBAgAABAgQIECBAgACBLCAYZCMTBAgQIECAAAECBAgQIECgTkAwqDu5hQkQIECAAAECBAgQIECAQBYQDLKRCQIECBAgQIAAAQIECBAgUCcgGNSd3MIECBAgQIAAAQIECBAgQCALCAbZyAQBAgQIECBAgAABAgQIEKgTEAzqTm5hAgQIECBAgAABAgQIECCQBQSDbGSCAAECBAgQIECAAAECBAjUCQgGdSe3MAECBAgQIECAAAECBAgQyAKCQTYyQYAAAQIECBAgQIAAAQIE6gQEg7qTW5gAAQIECBAgQIAAAQIECGQBwSAbmSBAgAABAgQIECBAgAABAnUCgkHdyS1MgAABAgQIECBAgAABAgSygGCQjUwQIECAAAECBAgQIECAAIE6AcGg7uQWJkCAAAECBAgQIECAAAECWUAwyEYmCBAgQIAAAQIECBAgQIBAnYBgUHdyCxMgQIAAAQIECBAgQIAAgSwgGGQjEwQIECBAgAABAgQIECBAoE5AMKg7uYUJECBAgAABAgQIECBAgEAWEAyykQkCBAgQIECAAAECBAgQIFAnIBjUndzCBAgQIECAAAECBAgQIEAgCwgG2cgEAQIECBAgQIAAAQIECBCoExAM6k5uYQIECBAgQIAAAQIECBAgkAUEg2xkggABAgQIECBAgAABAgQI1AkIBnUntzABAgQIECBAgAABAgQIEMgCgkE2MkGAAAECBAgQIECAAAECBOoEBIO6k1uYAAECBAgQIECAAAECBAhkAcEgG5kgQIAAAQIECBAgQIAAAQJ1AoJB3cktTIAAAQIECBAgQIAAAQIEsoBgkI1MECBAgAABAgQIECBAgACBOgHBoO7kFiZAgAABAgQIECBAgAABAllAMMhGJggQIECAAAECBAgQIECAQJ2AYFB3cgsTIECAAAECBAgQIECAAIEsIBhkIxMECBAgQIAAAQIECBAgQKBOQDCoO7mFCRAgQIAAAQIECBAgQIBAFhAMspEJAgQIECBAgAABAgQIECBQJyAY1J3cwgQIECBAgAABAgQIECBAIAsIBtnIBAECBAgQIECAAAECBAgQqBMQDOpObmECBAgQIECAAAECBAgQIJAFBINsZIIAAQIECBAgQIAAAQIECNQJCAZ1J7cwAQIECBAgQIAAAQIECBDIAoJBNjJBgAABAgQIECBAgAABAgTqBASDupNbmAABAgQIECBAgAABAgQIZAHBIBuZIECAAAECBAgQIECAAAECdQKCQd3JLUyAAAECBAgQIECAAAECBLKAYJCNTBAgQIAAAQIECBAgQIAAgToBwaDu5BYmQIAAAQIECBAgQIAAAQJZQDDIRiYIECBAgAABAgQIECBAgECdgGBQd3ILEyBAgAABAgQIECBAgACBLCAYZCMTBAgQIECAAAECBAgQIECgTkAwqDu5hQkQIECAAAECBAgQIECAQBYQDLKRCQIECBAgQIAAAQIECBAgUCcgGNSd3MIECBAgQIAAAQIECBAgQCALCAbZyAQBAgQIECBAgAABAgQIEKgTEAzqTm5hAgQIECBAgAABAgQIECCQBQSDbGSCAAECBAgQIECAAAECBAjUCQgGdSe3MAECBAgQIECAAAECBAgQyAKCQTYyQYAAAQIECBAgQIAAAQIE6gQEg7qTW5gAAQIECBAgQIAAAQIECGQBwSAbmSBAgAABAgQIECBAgAABAnUCgkHdyS1MgAABAgQIECBAgAABAgSygGCQjUwQIECAAAECBAgQIECAAIE6AcGg7uQWJkCAAAECBAgQIECAAAECWUAwyEYmCBAgQIAAAQIECBAgQIBAnYBgUHdyCxMgQIAAAQIECBAgQIAAgSwgGGQjEwQIECBAgAABAgQIECBAoE5AMKg7uYUJECBAgAABAgQIECBAgEAWEAyykQkCBAgQIECAAAECBAgQIFAnIBjUndzCBAgQIECAAAECBAgQIEAgCwgG2cgEAQIECBAgQIAAAQIECBCoExAM6k5uYQIECBAgQIAAAQIECBAgkAUEg2xkggABAgQIECBAgAABAgQI1AkIBnUntzABAgQIECBAgAABAgQIEMgCgkE2MkGAAAECBAgQIECAAAECBOoEBIO6k1uYAAECBAgQIECAAAECBAhkAcEgG5kgQIAAAQIECBAgQIAAAQJ1AoJB3cktTIAAAQIECBAgQIAAAQIEsoBgkI1MECBAgAABAgQIECBAgACBOgHBoO7kFiZAgAABAgQIECBAgAABAllAMMhGJggQIECAAAECBAgQIECAQJ2AYFB3cgsTIECAAAECBAgQIECAAIEsIBhkIxMECBAgQIAAAQIECBAgQKBOQDCoO7mFCRAgQIAAAQIECBAgQIBAFhAMspEJAgQIECBAgAABAgQIECBQJyAY1J3cwgQIECBAgAABAgQIECBAIAsIBtnIBAECBAgQIECAAAECBAgQqBMQDOpObmECBAgQIECAAAECBAgQIJAFBINsZIIAAQIECBAgQIAAAQIECNQJCAZ1J7cwAQIECBAgQIAAAQIECBDIAoJBNjJBgAABAgQIECBAgAABAgTqBASDupNbmAABAgQIECBAgAABAgQIZAHBIBuZIECAAAECBAgQIECAAAECdQKCQd3JLUyAAAECBAgQIECAAAECBLKAYJCNTBAgQIAAAQIECBAgQIAAgToBwaDu5BYmQIAAAQIECBAgQIAAAQJZQDDIRiYIECBAgAABAgQIECBAgECdgGBQd3ILEyBAgAABAgQIECBAgACBLCAYZCMT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\",\"crossOrigin\":null,\"filters\":[]}],\"hoverCursor\":\"move\"},\"b\":{\"version\":\"4.6.0\",\"objects\":[{\"type\":\"image\",\"version\":\"4.6.0\",\"originX\":\"left\",\"originY\":\"top\",\"left\":253.5,\"top\":121.5,\"width\":1012,\"height\":648,\"fill\":\"rgb(0,0,0)\",\"stroke\":null,\"strokeWidth\":0,\"strokeDashArray\":null,\"strokeLineCap\":\"butt\",\"strokeDashOffset\":0,\"strokeLineJoin\":\"miter\",\"strokeUniform\":false,\"strokeMiterLimit\":4,\"scaleX\":1,\"scaleY\":1,\"angle\":0,\"flipX\":false,\"flipY\":false,\"opacity\":1,\"shadow\":null,\"visible\":true,\"backgroundColor\":\"\",\"fillRule\":\"nonzero\",\"paintFirst\":\"fill\",\"globalCompositeOperation\":\"source-over\",\"skewX\":0,\"skewY\":0,\"cropX\":0,\"cropY\":0,\"selectable\":false,\"hoverable\":false,\"hoverCursor\":\"default\",\"src\":\"data:image/png;base64,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YFB3cgsTIECAAAECBAgQIECAAIEsIBhkIxMECBAgQIAAAQIECBAgQKBOQDCoO7mFCRAgQIAAAQIECBAgQIBAFhAMspEJAgQIECBAgAABAgQIECBQJyAY1J3cwgQIECBAgAABAgQIECBAIAsIBtnIBAECBAgQIECAAAECBAgQqBMQDOpObmECBAgQIECAAAECBAgQIJAFBINsZIIAAQIECBAgQIAAAQIECNQJCAZ1J7cwAQIECBAgQIAAAQIECBDIAoJBNjJBgAABAgQIECBAgAABAgTqBASDupNbmAABAgQIECBAgAABAgQIZAHBIBuZIECAAAECBAgQIECAAAECdQKCQd3JLUyAAAECBAgQIECAAAECBLKAYJCNTBAgQIAAAQIECBAgQIAAgToBwaDu5BYmQIAAAQIECBAgQIAAAQJZQDDIRiYIECBAgAABAgQIECBAgECdgGBQd3ILEyBAgAABAgQIECBAgACBLCAYZCMTBAgQIECAAAECBAgQIECgTkAwqDu5hQkQIECAAAECBAgQIECAQBYQDLKRCQIECBAgQIAAAQIECBAgUCcgGNSd3MIECBAgQIAAAQIECBAgQCALCAbZyAQBAgQIECBAgAABAgQIEKgTEAzqTm5hAgQIECBAgAABAgQIECCQBQSDbGSCAAECBAgQIECAAAECBAjUCQgGdSe3MAECBAgQIECAAAECBAgQyAKCQTYyQYAAAQIECBAgQIAAAQIE6gQEg7qTW5gAAQIECBAgQIAAAQIECGQBwSAbmSBAgAABAgQIECBAgAABAnUCgkHdyS1MgAABAgQIECBAgAABAgSygGCQjUwQIECAAAECBAgQIECAAIE6AcGg7uQWJkCAAAECBAgQIECAAAECWUAwyEYmCBAgQIAAAQIECBAgQIBAnYBgUHdyCxMgQIAAAQIECBAgQIAAgSwgGGQjEwQIECBAgAABAgQIECBAoE5AMKg7uYUJECBAgAABAgQIECBAgEAWEAyykQkCBAgQIECAAAECBAgQIFAnIBjUndzCBAgQIECAAAECBAgQIEAgCwgG2cgEAQIECBAgQIAAAQIECBCoExAM6k5uYQIECBAgQIAAAQIECBAgkAUEg2xkggABAgQIECBAgAABAgQI1AkIBnUntzABAgQIECBAgAABAgQIEMgCgkE2MkGAAAECBAgQIECAAAECBOoEBIO6k1uYAAECBAgQIECAAAECBAhkAcEgG5kgQIAAAQIECBAgQIAAAQJ1AoJB3cktTIAAAQIECBAgQIAAAQIEsoBgkI1MECBAgAABAgQIECBAgACBOgHBoO7kFiZAgAABAgQIECBAgAABAllAMMhGJggQIECAAAECBAgQIECAQJ2AYFB3cgsTIECAAAECBAgQIECAAIEsIBhkIxMECBAgQIAAAQIECBAgQKBOQDCoO7mFCRAgQIAAAQIECBAgQIBAFhAMspEJAgQIECBAgAABAgQIECBQJyAY1J3cwgQIECBAgAABAgQIECBAIAsIBtnIBAECBAgQIECAAAECBAgQqBMQDOpObmECBAgQIECAAAECBAgQIJAFBINsZIIAAQIECBAgQIAAAQIECNQJCAZ1J7cwAQIECBAgQIAAAQIECBDIAoJBNjJBgAABAgQIECBAgAABAgTqBASDupNbmAABAgQIECBAgAABAgQIZAHBIBuZIECAAAECBAgQIECAAAECdQKCQd3JLUyAAAECBAgQIECAAAECBLKAYJCNTBAgQIAAAQIECBAgQIAAgToBwaDu5BYmQIAAAQIECBAgQIAAAQJZQDDIRiYIECBAgAABAgQIECBAgECdgGBQd3ILEyBAgAABAgQIECBAgACBLCAYZCMTBAgQIECAAAECBAgQIECgTkAwqDu5hQkQIECAAAECBAgQIECAQBYQDLKRCQIECBAgQIAAAQIECBAgUCcgGNSd3MIECBAgQIAAAQIECBAgQCALCAbZyAQBAgQIECBAgAABAgQIEKgTEAzqTm5hAgQIECBAgAABAgQIECCQBQSDbGSCAAECBAgQIECAAAECBAjUCQgGdSe3MAECBAgQIECAAAECBAgQyAKCQTYyQYAAAQIECBAgQIAAAQIE6gQEg7qTW5gAAQIECBAgQIAAAQIECGQBwSAbmSBAgAABAgQIECBAgAABAnUCgkHdyS1MgAABAgQIECBAgAABAgSygGCQjUwQIECAAAECBAgQIECAAIE6AcGg7uQWJkCAAAECBAgQIECAAAECWUAwyEYmCBAgQIAAAQIECBAgQIBAnYBgUHdyCxMgQIAAAQIECBAgQIAAgSwgGGQjEwQIECBAgAABAgQIECBAoE5AMKg7uYUJECBAgAABAgQIECBAgEAWEAyykQkCBAgQIECAAAECBAgQIFAnIBjUndzCBAgQIECAAAECBAgQIEAgCwgG2cgEAQIECBAgQIAAAQIECBCoExAM6k5uYQIECBAgQIAAAQIECBAgkAUEg2xkggABAgQIECBAgAABAgQI1AkIBnUntzABAgQIECBAgAABAgQIEMgCgkE2MkGAAAECBAgQIECAAAECBOoEBIO6k1uYAAECBAgQIECAAAECBAhkAcEgG5kgQIAAAQIECBAgQIAAAQJ1AoJB3cktTIAAAQIECBAgQIAAAQIEsoBgkI1MECBAgAABAgQIECBAgACBOgHBoO7kFiZAgAABAgQIECBAgAABAllAMMhGJggQIECAAAECBAgQIECAQJ2AYFB3cgsTIECAAAECBAgQIECAAIEsIBhkIxMECBAgQIAAAQIECBAgQKBOQDCoO7mFCRAgQIAAAQIECBAgQIBAFhAMspEJAgQIECBAgAABAgQIECBQJyAY1J3cwgQIECBAgAABAgQIECBAIAsIBtnIBAECBAgQIECAAAECBAgQqBMQDOpObmECBAgQIECAAAECBAgQIJAFBINsZIIAAQIECBAgQIAAAQIECNQJCAZ1J7cwAQIECBAgQIAAAQIECBDIAoJBNjJBgAABAgQIECBAgAABAgTqBASDupNbmAABAgQIECBAgAABAgQIZAHBIBuZIECAAAECBAgQIECAAAECdQKCQd3JLUyAAAECBAgQIECAAAECBLKAYJCNTBAgQIAAAQIECBAgQIAAgToBwaDu5BYmQIAAAQIECBAgQIAAAQJZQDDIRiYIECBAgAABAgQIECBAgECdgGBQd3ILEyBAgAABAgQIECBAgACBLCAYZCMTBAgQIECAAAECBAgQIECgTkAwqDu5hQkQIECAAAECBAgQIECAQBYQDLKRCQIECBAgQIAAAQIECBAgUCcgGNSd3MIECBAgQIAAAQIECBAgQCALCAbZyAQBAgQIECBAgAABAgQIEKgTEAzqTm5hAgQIECBAgAABAgQIECCQBQSDbGSCAAECBAgQIECAAAECBAjUCQgGdSe3MAECBAgQIECAAAECBAgQyAKCQTYyQYAAAQIECBAgQIAAAQIE6gQEg7qTW5gAAQIECBAgQIAAAQIECGQBwSAbmSBAgAABAgQIECBAgAABAnUCgkHdyS1MgAABAgQIECBAgAABAgSygGCQjUwQIECAAAECBAgQIECAAIE6AcGg7uQWJkCAAAECBAgQIECAAAECWUAwyEYmCBAgQIAAAQIECBAgQIBAnYBgUHdyCxMgQIAAAQIECBAgQIAAgSwgGGQjEwQIECBAgAABAgQIECBAoE5AMKg7uYUJECBAgAABAgQIECBAgEAWEAyykQkCBAgQIECAAAECBAgQIFAnIBjUndzCBAgQIECAAAECBAgQIEAgCwgG2cgEAQIECBAgQIAAAQIECBCoExAM6k5uYQIECBAgQIAAAQIECBAgkAUEg2xkggABAgQIECBAgAABAgQI1AkIBnUntzABAgQIECBAgAABAgQIEMgCgkE2MkGAAAECBAgQIECAAAECBOoEBIO6k1uYAAECBAgQIECAAAECBAhkAcEgG5kgQIAAAQIECBAgQIAAAQJ1AoJB3cktTIAAAQIECBAgQIAAAQIEsoBgkI1MECBAgAABAgQIECBAgACBOgHBoO7kFiZAgAABAgQIECBAgAABAllAMMhGJggQIECAAAECBAgQIECAQJ2AYFB3cgsTIECAAAECBAgQIECAAIEsIBhkIxMECBAgQIAAAQIECBAgQKBOQDCoO7mFCRAgQIAAAQIECBAgQIBAFhAMspEJAgQIECBAgAABAgQIECBQJyAY1J3cwgQIECBAgAABAgQIECBAIAsIBtnIBAECBAgQIECAAAECBAgQqBMQDOpObmECBAgQIECAAAECBAgQIJAFBINsZIIAAQIECBAgQIAAAQIECNQJCAZ1J7cwAQIECBAgQIAAAQIECBDIAoJBNjJBgAABAgQIECBAgAABAgTqBASDupNbmAABAgQIECBAgAABAgQIZAHBIBuZIECAAAECBAgQIECAAAECdQKCQd3JLUyAAAECBAgQIECAAAECBLKAYJCNTBAgQIAAAQIECBAgQIAAgToBwaDu5BYmQIAAAQIECBAgQIAAAQJZQDDIRiYIECBAgAABAgQIECBAgECdgGBQd3ILEyBAgAABAgQIECBAgACBLCAYZCMTBAgQIECAAAECBAgQIECgTkAwqDu5hQkQIECAAAECBAgQIECAQBYQDLKRCQIECBAgQIAAAQIECBAgUCcgGNSd3MIECBAgQIAAAQIECBAgQCALCAbZyAQBAgQIECBAgAABAgQIEKgTEAzqTm5hAgQIECBAgAABAgQIECCQBQSDbGSCAAECBAgQIECAAAECBAjUCQgGdSe3MAECBAgQIECAAAECBAgQyAKCQTYyQYAAAQIECBAgQIAAAQIE6gQEg7qTW5gAAQIECBAgQIAAAQIECGQBwSAbmSBAgAABAgQIECBAgAABAnUCgkHdyS1MgAABAgQIECBAgAABAgSygGCQjUwQIECAAAECBAgQIECAAIE6AcGg7uQWJkCAAAECBAgQIECAAAECWUAwyEYmCBAgQIAAAQIECBAgQIBAnYBgUHdyCxMgQIAAAQIECBAgQIAAgSwgGGQjEwQIECBAgAABAgQIECBAoE5AMKg7uYUJECBAgAABAgQIECBAgEAWEAyykQkCBAgQIECAAAECBAgQIFAnIBjUndzCBAgQIECAAAECBAgQIEAgCwgG2cgEAQIECBAgQIAAAQIECBCoExAM6k5uYQIECBAgQIAAAQIECBAgkAUEg2xkggABAgQIECBAgAABAgQI1AkIBnUntzABAgQIECBAgAABAgQIEMgCgkE2MkGAAAECBAgQIECAAAECBOoEBIO6k1uYAAECBAgQIECAAAECBAhkAcEgG5kgQIAAAQIECBAgQIAAAQJ1AoJB3cktTIAAAQIECBAgQIAAAQIEsoBgkI1MECBAgAABAgQIECBAgACBOgHBoO7kFiZAgAABAgQIECBAgAABAllAMMhGJggQIECAAAECBAgQIECAQJ2AYFB3cgsTIECAAAECBAgQIECAAIEsIBhkIxMECBAgQIAAAQIECBAgQKBOQDCoO7mFCRAgQIAAAQIECBAgQIBAFhAMspEJAgQIECBAgAABAgQIECBQJyAY1J3cwgQIECBAgAABAgQIECBAIAsIBtnIBAECBAgQIECAAAECBAgQqBMQDOpObmECBAgQIECAAAECBAgQIJAFBINsZIIAAQIECBAgQIAAAQIECNQJCAZ1J7cwAQIECBAgQIAAAQIECBDIAoJBNjJBgAABAgQIECBAgAABAgTqBASDupNbmAABAgQIECBAgAABAgQIZAHBIBuZIECAAAECBAgQIECAAAECdQKCQd3JLUyAAAECBAgQIECAAAECBLKAYJCNTBAgQIAAAQIECBAgQIAAgToBwaDu5BYmQIAAAQIECBAgQIAAAQJZQDDIRiYIECBAgAABAgQIECBAgECdgGBQd3ILEyBAgAABAgQIECBAgACBLCAYZCMTBAgQIECAAAECBAgQIECgTkAwqDu5hQkQIECAAAECBAgQIECAQBYQDLKRCQIECBAgQIAAAQIECBAgUCcgGNSd3MIECBAgQIAAAQIECBAgQCALCAbZyAQBAgQIECBAgAABAgQIEKgTEAzqTm5hAgQIECBAgAABAgQIECCQBQSDbGSCAAECBAgQIECAAAECBAjUCQgGdSe3MAECBAgQIECAAAECBAgQyAKCQTYyQYAAAQIECBAgQIAAAQIE6gQEg7qTW5gAAQIECBAgQIAAAQIECGQBwSAbmSBAgAABAgQIECBAgAABAnUCgkHdyS1MgAABAgQIECBAgAABAgSygGCQjUwQIECAAAECBAgQIECAAIE6AcGg7uQWJkCAAAECBAgQIECAAAECWUAwyEYmCBAgQIAAAQIECBAgQIBAnYBgUHdyCxMgQIAAAQIECBAgQIAAgSwgGGQjEwQIECBAgAABAgQIECBAoE5AMKg7uYUJECBAgAABAgQIECBAgEAWEAyykQkCBAgQIECAAAECBAgQIFAnIBjUndzCBAgQIECAAAECBAgQIEAgCwgG2cgEAQIECBAgQIAAAQIECBCoExAM6k5uYQIECBAgQIAAAQIECBAgkAUEg2xkggABAgQIECBAgAABAgQI1AkIBnUntzABAgQIECBAgAABAgQIEMgCgkE2MkGAAAECBAgQIECAAAECBOoEBIO6k1uYAAECBAgQIECAAAECBAhkAcEgG5kgQIAAAQIECBAgQIAAAQJ1AoJB3cktTIAAAQIECBAgQIAAAQIEsoBgkI1MECBAgAABAgQIECBAgACBOgHBoO7kFiZAgAABAgQIECBAgAABAllAMMhGJggQIECAAAECBAgQIECAQJ2AYFB3cgsTIECAAAECBAgQIECAAIEsIBhkIxMECBAgQIAAAQIECBAgQKBOQDCoO7mFCRAgQIAAAQIECBAgQIBAFhAMspEJAgQIECBAgAABAgQIECBQJyAY1J3cwgQIECBAgAABAgQIECBAIAsIBtnIBAECBAgQIECAAAECBAgQqBMQDOpObmECBAgQIECAAAECBAgQIJAFBINsZIIAAQIECBAgQIAAAQIECNQJCAZ1J7cwAQIECBAgQIAAAQIECBDIAoJBNjJBgAABAgQIECBAgAABAgTqBASDupNbmAABAgQIECBAgAABAgQIZAHBIBuZIECAAAECBAgQIECAAAECdQKCQd3JLUyAAAECBAgQIECAAAECBLKAYJCNTBAgQIAAAQIECBAgQIAAgToBwaDu5BYmQIAAAQIECBAgQIAAAQJZQDDIRiYIECBAgAABAgQIECBAgECdgGBQd3ILEyBAgAABAgQIECBAgACBLCAYZCMTBAgQIECAAAECBAgQIECgTkAwqDu5hQkQIECAAAECBAgQIECAQBYQDLKRCQIECBAgQIAAAQIECBAgUCcgGNSd3MIECBAgQIAAAQIECBAgQCALCAbZyAQBAgQIECBAgAABAgQIEKgTEAzqTm5hAgQIECBAgAABAgQIECCQBQSDbGSCAAECBAgQIECAAAECBAjUCQgGdSe3MAECBAgQIECAAAECBAgQyAKCQTYyQYAAAQIECBAgQIAAAQIE6gQEg7qTW5gAAQIECBAgQIAAAQIECGQBwSAbmSBAgAABAgQIECBAgAABAnUCgkHdyS1MgAABAgQIECBAgAABAgSygGCQjUwQIECAAAECBAgQIECAAIE6AcGg7uQWJkCAAAECBAgQIECAAAECWUAwyEYmCBAgQIAAAQIECBAgQIBAnYBgUHdyCxMgQIAAAQIECBAgQIAAgSwgGGQjEwQIECBAgAABAgQIECBAoE5AMKg7uYUJECBAgAABAgQIECBAgEAWEAyykQkCBAgQIECAAAECBAgQIFAnIBjUndzCBAgQIECAAAECBAgQIEAgCwgG2cgEAQIECBAgQIAAAQIECBCoExAM6k5uYQIECBAgQIAAAQIECBAgkAUEg2xkggABAgQIECBAgAABAgQI1AkIBnUntzABAgQIECBAgAABAgQIEMgCgkE2MkGAAAECBAgQIECAAAECBOoEBIO6k1uYAAECBAgQIECAAAECBAhkAcEgG5kgQIAAAQIECBAgQIAAAQJ1AoJB3cktTIAAAQIECBAgQIAAAQIEsoBgkI1MECBAgAABAgQIECBAgACBOgHBoO7kFiZAgAABAgQIECBAgAABAllAMMhGJggQIECAAAECBAgQIECAQJ2AYFB3cgsTIECAAAECBAgQIECAAIEsIBhkIxMECBAgQIAAAQIECBAgQKBOQDCoO7mFCRAgQIAAAQIECBAgQIBAFhAMspEJAgQIECBAgAABAgQIECBQJyAY1J3cwgQIECBAgAABAgQIECBAIAsIBtnIBAECBAgQIECAAAECBAgQqBMQDOpObmECBAgQIECAAAECBAgQIJAFBINsZIIAAQIECBAgQIAAAQIECNQJCAZ1J7cwAQIECBAgQIAAAQIECBDIAoJBNjJBgAABAgQIECBAgAABAgTqBASDupNbmAABAgQIECBAgAABAgQIZAHBIBuZIECAAAECBAgQIECAAAECdQKCQd3JLUyAAAECBAgQIEDpfCiFAAAcY0lEQVSAAAECBLKAYJCNTBAgQIAAAQIECBAgQIAAgToBwaDu5BYmQIAAAQIECBAgQIAAAQJZQDDIRiYIECBAgAABAgQIECBAgECdgGBQd3ILEyBAgAABAgQIECBAgACBLCAYZCMTBAgQIECAAAECBAgQIECgTkAwqDu5hQkQIECAAAECBAgQIECAQBYQDLKRCQIECBAgQIAAAQIECBAgUCcgGNSd3MIECBAgQIAAAQIECBAgQCALCAbZyAQBAgQIECBAgAABAgQIEKgTEAzqTm5hAgQIECBAgAABAgQIECCQBQSDbGSCAAECBAgQIECAAAECBAjUCQgGdSe3MAECBAgQIECAAAECBAgQyAKCQTYyQYAAAQIECBAgQIAAAQIE6gQEg7qTW5gAAQIECBAgQIAAAQIECGQBwSAbmSBAgAABAgQIECBAgAABAnUCgkHdyS1MgAABAgQIECBAgAABAgSygGCQjUwQIECAAAECBAgQIECAAIE6AcGg7uQWJkCAAAECBAgQIECAAAECWUAwyEYmCBAgQIAAAQIECBAgQIBAnYBgUHdyCxMgQIAAAQIECBAgQIAAgSwgGGQjEwQIECBAgAABAgQIECBAoE5AMKg7uYUJECBAgAABAgQIECBAgEAWEAyykQkCBAgQIECAAAECBAgQIFAnIBjUndzCBAgQIECAAAECBAgQIEAgCwgG2cgEAQIECBAgQIAAAQIECBCoExAM6k5uYQIECBAgQIAAAQIECBAgkAUEg2xkggABAgQIECBAgAABAgQI1AkIBnUntzABAgQIECBAgAABAgQIEMgCgkE2MkGAAAECBAgQIECAAAECBOoEBIO6k1uYAAECBAgQIECAAAECBAhkAcEgG5kgQIAAAQIECBAgQIAAAQJ1AoJB3cktTIAAAQIECBAgQIAAAQIEsoBgkI1MECBAgAABAgQIECBAgACBOgHBoO7kFiZAgAABAgQIECBAgAABAllAMMhGJggQIECAAAECBAgQIECAQJ2AYFB3cgsTIECAAAECBAgQIECAAIEsIBhkIxMECBAgQIAAAQIECBAgQKBOQDCoO7mFCRAgQIAAAQIECBAgQIBAFhAMspEJAgQIECBAgAABAgQIECBQJyAY1J3cwgQIECBAgAABAgQIECBAIAsIBtnIBAECBAgQIECAAAECBAgQqBMQDOpObmECBAgQIECAAAECBAgQIJAFBINsZIIAAQIECBAgQIAAAQIECNQJCAZ1J7cwAQIECBAgQIAAAQIECBDIAoJBNjJBgAABAgQIECBAgAABAgTqBASDupNbmAABAgQIECBAgAABAgQIZAHBIBuZIECAAAECBAgQIECAAAECdQKCQd3JLUyAAAECBAgQIECAAAECBLKAYJCNTBAgQIAAAQIECBAgQIAAgToBwaDu5BYmQIAAAQIECBAgQIAAAQJZQDDIRiYIECBAgAABAgQIECBAgECdgGBQd3ILEyBAgAABAgQIECBAgACBLCAYZCMTBAgQIECAAAECBAgQIECgTkAwqDu5hQkQIECAAAECBAgQIECAQBYQDLKRCQIECBAgQIAAAQIECBAgUCcgGNSd3MIECBAgQIAAAQIECBAgQCALCAbZyAQBAgQIECBAgAABAgQIEKgTEAzqTm5hAgQIECBAgAABAgQIECCQBQSDbGSCAAECBAgQIECAAAECBAjUCQgGdSe3MAECBAgQIECAAAECBAgQyAKCQTYyQYAAAQIECBAgQIAAAQIE6gQEg7qTW5gAAQIECBAgQIAAAQIECGQBwSAbmSBAgAABAgQIECBAgAABAnUCgkHdyS1MgAABAgQIECBAgAABAgSygGCQjUwQIECAAAECBAgQIECAAIE6AcGg7uQWJkCAAAECBAgQIECAAAECWUAwyEYmCBAgQIAAAQIECBAgQIBAnYBgUHdyCxMgQIAAAQIECBAgQIAAgSwgGGQjEwQIECBAgAABAgQIECBAoE5AMKg7uYUJECBAgAABAgQIECBAgEAWEAyykQkCBAgQIECAAAECBAgQIFAnIBjUndzCBAgQIECAAAECBAgQIEAgCwgG2cgEAQIECBAgQIAAAQIECBCoExAM6k5uYQIECBAgQIAAAQIECBAgkAUEg2xkggABAgQIECBAgAABAgQI1AkIBnUntzABAgQIECBAgAABAgQIEMgCgkE2MkGAAAECBAgQIECAAAECBOoEBIO6k1uYAAECBAgQIECAAAECBAhkAcEgG5kgQIAAAQIECBAgQIAAAQJ1AoJB3cktTIAAAQIECBAgQIAAAQIEsoBgkI1MECBAgAABAgQIECBAgACBOgHBoO7kFiZAgAABAgQIECBAgAABAllAMMhGJggQIECAAAECBAgQIECAQJ2AYFB3cgsTIECAAAECBAgQIECAAIEsIBhkIxMECBAgQIAAAQIECBAgQKBOQDCoO7mFCRAgQIAAAQIECBAgQIBAFhAMspEJAgQIECBAgAABAgQIECBQJyAY1J3cwgQIECBAgAABAgQIECBAIAsIBtnIBAECBAgQIECAAAECBAgQqBMQDOpObmECBAgQIECAAAECBAgQIJAFBINsZIIAAQIECBAgQIAAAQIECNQJCAZ1J7cwAQIECBAgQIAAAQIECBDIAoJBNjJBgAABAgQIECBAgAABAgTqBASDupNbmAABAgQIECBAgAABAgQIZAHBIBuZIECAAAECBAgQIECAAAECdQKCQd3JLUyAAAECBAgQIECAAAECBLKAYJCNTBAgQIAAAQIECBAgQIAAgToBwaDu5BYmQIAAAQIECBAgQIAAAQJZQDDIRiYIECBAgAABAgQIECBAgECdgGBQd3ILEyBAgAABAgQIECBAgACBLCAYZCMTBAgQIECAAAECBAgQIECgTkAwqDu5hQkQIECAAAECBAgQIECAQBYQDLKRCQIECBAgQIAAAQIECBAgUCcgGNSd3MIECBAgQIAAAQIECBAgQCALCAbZyAQBAgQIECBAgAABAgQIEKgTEAzqTm5hAgQIECBAgAABAgQIECCQBQSDbGSCAAECBAgQIECAAAECBAjUCQgGdSe3MAECBAgQIECAAAECBAgQyAKCQTYyQYAAAQIECBAgQIAAAQIE6gQEg7qTW5gAAQIECBAgQIAAAQIECGQBwSAbmSBAgAABAgQIECBAgAABAnUCgkHdyS1MgAABAgQIECBAgAABAgSygGCQjUwQIECAAAECBAgQIECAAIE6AcGg7uQWJkCAAAECBAgQIECAAAECWUAwyEYmCBAgQIAAAQIECBAgQIBAnYBgUHdyCxMgQIAAAQIECBAgQIAAgSwgGGQjEwQIECBAgAABAgQIECBAoE5AMKg7uYUJECBAgAABAgQIECBAgEAWEAyykQkCBAgQIECAAAECBAgQIFAnIBjUndzCBAgQIECAAAECBAgQIEAgCwgG2cgEAQIECBAgQIAAAQIECBCoExAM6k5uYQIECBAgQIAAAQIECBAgkAUEg2xkggABAgQIECBAgAABAgQI1AkIBnUntzABAgQIECBAgAABAgQIEMgCgkE2MkGAAAECBAgQIECAAAECBOoEBIO6k1uYAAECBAgQIECAAAECBAhkAcEgG5kgQIAAAQIECBAgQIAAAQJ1AoJB3cktTIAAAQIECBAgQIAAAQIEsoBgkI1MECBAgAABAgQIECBAgACBOgHBoO7kFiZAgAABAgQIECBAgAABAllAMMhGJggQIECAAAECBAgQIECAQJ2AYFB3cgsTIECAAAECBAgQIECAAIEsIBhkIxMECBAgQIAAAQIECBAgQKBOQDCoO7mFCRAgQIAAAQIECBAgQIBAFhAMspEJAgQIECBAgAABAgQIECBQJyAY1J3cwgQIECBAgAABAgQIECBAIAsIBtnIBAECBAgQIECAAAECBAgQqBMQDOpObmECBAgQIECAAAECBAgQIJAFBINsZIIAAQIECBAgQIAAAQIECNQJCAZ1J7cwAQIECBAgQIAAAQIECBDIAoJBNjJBgAABAgQIECBAgAABAgTqBASDupNbmAABAgQIECBAgAABAgQIZAHBIBuZIECAAAECBAgQIECAAAECdQKCQd3JLUyAAAECBAgQIECAAAECBLKAYJCNTBAgQIAAAQIECBAgQIAAgToBwaDu5BYmQIAAAQIECBAgQIAAAQJZQDDIRiYIECBAgAABAgQIECBAgECdgGBQd3ILEyBAgAABAgQIECBAgACBLCAYZCMTBAgQIECAAAECBAgQIECgTkAwqDu5hQkQIECAAAECBAgQIECAQBYQDLKRCQIECBAgQIAAAQIECBAgUCcgGNSd3MIECBAgQIAAAQIECBAgQCALCAbZyAQBAgQIECBAgAABAgQIEKgTEAzqTm5hAgQIECBAgAABAgQIECCQBQSDbGSCAAECBAgQIECAAAECBAjUCQgGdSe3MAECBAgQIECAAAECBAgQyAKCQTYyQYAAAQIECBAgQIAAAQIE6gQEg7qTW5gAAQIECBAgQIAAAQIECGQBwSAbmSBAgAABAgQIECBAgAABAnUCgkHdyS1MgAABAgQIECBAgAABAgSygGCQjUwQIECAAAECBAgQIECAAIE6AcGg7uQWJkCAAAECBAgQIECAAAECWUAwyEYmCBAgQIAAAQIECBAgQIBAnYBgUHdyCxMgQIAAAQIECBAgQIAAgSwgGGQjEwQIECBAgAABAgQIECBAoE5AMKg7uYUJECBAgAABAgQIECBAgEAWEAyykQkCBAgQIECAAAECBAgQIFAnIBjUndzCBAgQIECAAAECBAgQIEAgCwgG2cgEAQIECBAgQIAAAQIECBCoExAM6k5uYQIECBAgQIAAAQIECBAgkAUEg2xkggABAgQIECBAgAABAgQI1AkIBnUntzABAgQIECBAgAABAgQIEMgCgkE2MkGAAAECBAgQIECAAAECBOoEBIO6k1uYAAECBAgQIECAAAECBAhkAcEgG5kgQIAAAQIECBAgQIAAAQJ1AoJB3cktTIAAAQIECBAgQIAAAQIEsoBgkI1MECBAgAABAgQIECBAgACBOgHBoO7kFiZAgAABAgQIECBAgAABAllAMMhGJggQIECAAAECBAgQIECAQJ2AYFB3cgsTIECAAAECBAgQIECAAIEsIBhkIxMECBAgQIAAAQIECBAgQKBOQDCoO7mFCRAgQIAAAQIECBAgQIBAFhAMspEJAgQIECBAgAABAgQIECBQJyAY1J3cwgQIECBAgAABAgQIECBAIAsIBtnIBAECBAgQIECAAAECBAgQqBMQDOpObmECBAgQIECAAAECBAgQIJAFBINsZIIAAQIECBAgQIAAAQIECNQJCAZ1J7cwAQIECBAgQIAAAQIECBDIAoJBNjJBgAABAgQIECBAgAABAgTqBASDupNbmAABAgQIECBAgAABAgQIZAHBIBuZIECAAAECBAgQIECAAAECdQKCQd3JLUyAAAECBAgQIECAAAECBLKAYJCNTBAgQIAAAQIECBAgQIAAgToBwaDu5BYmQIAAAQIECBAgQIAAAQJZQDDIRiYIECBAgAABAgQIECBAgECdgGBQd3ILEyBAgAABAgQIECBAgACBLCAYZCMTBAgQIECAAAECBAgQIECgTkAwqDu5hQkQIECAAAECBAgQIECAQBYQDLKRCQIECBAgQIAAAQIECBAgUCcgGNSd3MIECBAgQIAAAQIECBAgQCALCAbZyAQBAgQIECBAgAABAgQIEKgTEAzqTm5hAgQIECBAgAABAgQIECCQBQSDbGSCAAECBAgQIECAAAECBAjUCQgGdSe3MAECBAgQIECAAAECBAgQyAKCQTYyQYAAAQIECBAgQIAAAQIE6gQEg7qTW5gAAQIECBAgQIAAAQIECGQBwSAbmSBAgAABAgQIECBAgAABAnUCgkHdyS1MgAABAgQIECBAgAABAgSygGCQjUwQIECAAAECBAgQIECAAIE6AcGg7uQWJkCAAAECBAgQIECAAAECWUAwyEYmCBAgQIAAAQIECBAgQIBAnYBgUHdyCxMgQIAAAQIECBAgQIAAgSwgGGQjEwQIECBAgAABAgQIECBAoE5AMKg7uYUJECBAgAABAgQIECBAgEAWEAyykQkCBAgQIECAAAECBAgQIFAnIBjUndzCBAgQIECAAAECBAgQIEAgCwgG2cgEAQIECBAgQIAAAQIECBCoExAM6k5uYQIECBAgQIAAAQIECBAgkAUEg2xkggABAgQIECBAgAABAgQI1AkIBnUntzABAgQIECBAgAABAgQIEMgCgkE2MkGAAAECBAgQIECAAAECBOoEBIO6k1uYAAECBAgQIECAAAECBAhkAcEgG5kgQIAAAQIECBAgQIAAAQJ1AoJB3cktTIAAAQIECBAgQIAAAQIEsoBgkI1MECBAgAABAgQIECBAgACBOgHBoO7kFiZAgAABAgQIECBAgAABAllAMMhGJggQIECAAAECBAgQIECAQJ2AYFB3cgsTIECAAAECBAgQIECAAIEsIBhkIxMECBAgQIAAAQIECBAgQKBOQDCoO7mFCRAgQIAAAQIECBAgQIBAFhAMspEJAgQIECBAgAABAgQIECBQJyAY1J3cwgQIECBAgAABAgQIECBAIAsIBtnIBAECBAgQIECAAAECBAgQqBMQDOpObmECBAgQIECAAAECBAgQIJAFBINsZIIAAQIECBAgQIAAAQIECNQJCAZ1J7cwAQIECBAgQIAAAQIECBDIAoJBNjJBgAABAgQIECBAgAABAgTqBASDupNbmAABAgQIECBAgAABAgQIZAHBIBuZIECAAAECBAgQIECAAAECdQKCQd3JLUyAAAECBAgQIECAAAECBLKAYJCNTBAgQIAAAQIECBAgQIAAgToBwaDu5BYmQIAAAQIECBAgQIAAAQJZQDDIRiYIECBAgAABAgQIECBAgECdgGBQd3ILEyBAgAABAgQIECBAgACBLCAYZCMTBAgQIECAAAECBAgQIECgTkAwqDu5hQkQIECAAAECBAgQIECAQBYQDLKRCQIECBAgQIAAAQIECBAgUCcgGNSd3MIECBAgQIAAAQIECBAgQCALCAbZyAQBAgQIECBAgAABAgQIEKgTEAzqTm5hAgQIECBAgAABAgQIECCQBQSDbGSCAAECBAgQIECAAAECBAjUCQgGdSe3MAECBAgQIECAAAECBAgQyAKCQTYyQYAAAQIECBAgQIAAAQIE6gQEg7qTW5gAAQIECBAgQIAAAQIECGQBwSAbmSBAgAABAgQIECBAgAABAnUCgkHdyS1MgAABAgQIECBAgAABAgSygGCQjUwQIECAAAECBAgQIECAAIE6AcGg7uQWJkCAAAECBAgQIECAAAECWUAwyEYmCBAgQIAAAQIECBAgQIBAnYBgUHdyCxMgQIAAAQIECBAgQIAAgSwgGGQjEwQIECBAgAABAgQIECBAoE5AMKg7uYUJECBAgAABAgQIECBAgEAWEAyykQkCBAgQIECAAAECBAgQIFAnIBjUndzCBAgQIECAAAECBAgQIEAgCwgG2cgEAQIECBAgQIAAAQIECBCoExAM6k5uYQIECBAgQIAAAQIECBAgkAX2YPDVmXlAHjVBgAABAgQIECBAgAABAgQIlAh8bQ8Gt83MQ0oWtiYBAgQIECBAgAABAgQIECCQBW7fg8GtM/OoPGuCAAECBAgQIECAAAECBAgQKBG4dQ8GN8zMdSULW5MAAQIECBAgQIAAAQIECBDIAjfuweADM/OsPGuCAAECBAgQIECAAAECBAgQKBH44B4M3jIzLy9Z2JoECBAgQIAAAQIECBAgQIBAFnjrHgxeMDPvzrMmCBAgQIAAAQIECBAgQIAAgRKBn9uDwYmZ+UTJwtYkQIAAAQIECBAgQIAAAQIEssCJPRg8cGa+ODNX5XkTBAgQIECAAAECBAgQIECAwGUucMfMPGztS27b9qGZedplvrD1CBAgQIAAAQIECBAgQIAAgSzw4bXW008Gg/1LD/cvP/QgQIAAAQIECBAgQIAAAQIEugVevtb6zZPB4JqZuanbw/YECBAgQIAAAQIECBAgQIDAzFy71rr568Fgf2zbdv3MPBENAQIECBAgQIAAAQIECBAgUCtw/VrrSfv2pwaDF8/Mb9eSWJwAAQIECBAgQIAAAQIECBB48VrrHXcPBg+dmc/OzLfwIUCAAAECBAgQIECAAAECBOoE/ntmrl5r3fYNwWD/H9u2vW1mXlJHYmECBAgQIECAAAECBAgQIEDg7Wutl55kuOufJByCwWNm5p9n5kGcCBAgQIAAAQIECBAgQIAAgRqB/5uZ711r3XKPweAQDd41Mz9fQ2JRAgQIECBAgAABAgQIECBA4HfXWi88leEbPmFwCAaPPHzK4CpeBAgQIECAAAECBAgQIECAwGUvcMfMPHattX+v4V2P04LBIRq8embecNmTWJAAAQIECBAgQIAAAQIECBB47VrrtAZwpmCwf4fBDTPzeG4ECBAgQIAAAQIECBAgQIDAZSvwqZk5sdb6yt03vMdgsA9t23ZiZj42M1dctiwWI0CAAAECBAgQIECAAAECvQJ3zsxT1lr7BwZOe5wxGByiwS/OzK/32tmcAAECBAgQIECAAAECBAhctgKvWmv92pm2S8Fg//M/nplnX7Y8FiNAgAABAgQIECBAgAABAn0C75uZ56y1tnMKBvsPbdv2rTPz5zPz5D4/GxMgQIAAAQIECBAgQIAAgctO4OMz87S11u1n2+ysnzA4+YPbtj388H0G1152TBYiQIAAAQIECBAgQIAAAQI9AjcdvrfgC2nlIwWD/Um2bXvMzHx0Zh6VntSfEyBAgAABAgQIECBAgAABAvc7gc/MzFPXWjcf5Z0dORgcosE1M/ORmfmuozy5GQIECBAgQIAAAQIECBAgQOB+IfDpmfnxtdb+CYMjPY4VDA7RYP+EwZ/MzBOO9AqGCBAgQIAAAQIECBAgQIAAgftS4JMz88y11v4JgyM/jh0MDtHgwTPzhzPzk0d+JYMECBAgQIAAAQIECBAgQIDAxRZ4/8w8f631peO+8DkFg0M02H/2lTPzKzNzxXFf2DwBAgQIECBAgAABAgQIECBwwQTunJlfnpk3ne1XJ57t1c85GJx80m3bThw+bfC4C7amJyZAgAABAgQIECBAgAABAgSOKvCPM/O8tdaNR/2Be5q718Fgf9Jt2/ZPGOyfNnj1zFx1b96QnyVAgAABAgQIECBAgAABAgTOSeCOmXnj4VMF+ycM7tXjvASDk+9g27ZHzMzrZuZnZ+ab7tU788MECBAgQIAAAQIECBAgQIDAUQT+d2Z+b2Zev9b6/FF+4Cgz5zUYnBIOrp6ZV8zMi2bmyqO8ETMECBAgQIAAAQIECBAgQIDAsQS+PDPvnJk3r7U+d6yfPMLwBQkGp4SDh87Mc/d/OzEzP3iE92OEAAECBAgQIECAAAECBAgQOLvA9TPznpl571rrtguFdUGDwalvetu2x8zMM2bmR2bmqTPzsAu1lOclQIAAAQIECBAgQIAAAQKXkcAXZ+avZ+avZubP1lo3X4zdLlowuFs8eMDMPGFmrpuZ75uZa2bmO2fm2w9fmrh/MsGDAAECBAgQIECAAAECBAi0COyfFNi/tPDfZ+bWmbllZvbfdrD/poNPrrW+drEh/h+5oaPdsxLhuQAAAABJRU5ErkJggg==\",\"crossOrigin\":null,\"filters\":[]}],\"hoverCursor\":\"move\"},\"fo\":[],\"bo\":[]}"; //let j = JSON.parse(blank); //canvas1.setZoom(1); //canvas2.setZoom(1); //canvas1.loadFromJSON(j.f); //canvas2.loadFromJSON(j.b); let t_objs1 = canvas1.getObjects() let t_objs2 = canvas2.getObjects() for (let i = 1; i < t_objs1.length; i++) { canvas1.remove(t_objs1[i]) } for (let i = 1; i < t_objs2.length; i++) { canvas2.remove(t_objs2[i]) } objs2 = [] objs1 = [] step1.val = 0 step2.val = 0 recordJson1 = [] recordJson2 = [] recordObjs1 = [] recordObjs2 = [] if ($('#front_side').hasClass('ui-button-active')) { objs = objs1 recordObjs = recordObjs1 recordJson = recordJson1 step = step1 } else if ($('#back_side').hasClass('ui-button-active')) { objs = objs2 recordObjs = recordObjs2 recordJson = recordJson2 step = step2 } openAs.name = '' canvas1.renderAll() canvas2.renderAll() updateList() console.log() } $('#new').click(function () { if (step.val == 0) { ipcRenderer.send('open-first-page'); return; } layer.confirm( '' + language_str('whetherSave') + '', function (index) { //confirm 是否保存当前文件? output(() => ipcRenderer.send('open-first-page')) return let j = canvas1.toJSON(['selectable', 'hoverable', 'hoverCursor', 'text', 'fontStyle', 'fontWeight', 'underline']) let b = canvas2.toJSON(['selectable', 'hoverable', 'hoverCursor', 'text', 'fontStyle', 'fontWeight', 'underline']) let _g1 = [], _g2 = [] let left = 0, top = 0 for (let _o of canvas1.getObjects()) { if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(_o.getCoords()) > left) { left = -(getCoordsMinX(_o.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(_o.getCoords()) > top) { top = -(getCoordsMinY(_o.getCoords()) - getCoordsMinY(background_image.getCoords())) } _g1.push(fabric.util.object.clone(_o)) } let fp = new fabric.Group(_g1).toDataURL({ height: 648, width: 1012, top: top / zoom, left: left / zoom }) ; (left = 0), (top = 0) for (let _o of canvas2.getObjects()) { if (getCoordsMinX(background_image.getCoords()) - getCoordsMinX(_o.getCoords()) > left) { left = -(getCoordsMinX(_o.getCoords()) - getCoordsMinX(background_image.getCoords())) } if (getCoordsMinY(background_image.getCoords()) - getCoordsMinY(_o.getCoords()) > top) { top = -(getCoordsMinY(_o.getCoords()) - getCoordsMinY(background_image.getCoords())) } _g2.push(fabric.util.object.clone(_o)) } //let fp = new fabric.Group(_g1).toDataURL(); let bp = new fabric.Group(_g2).toDataURL({ height: 648, width: 1012, top: top / zoom, left: left / zoom }) let o = { f: j, b: b, fo: objs1, bo: objs2, fp: fp, bp: bp } if (openAs.name != '') { //打开的文件 let fs = require('fs') o.soonType = 2 fs.writeFileSync(openAs.name, JSON.stringify(o)) layer.msg(language_str('saveSucc') + openAs.name) //'保存成功至' /* 2022-07-16 直接跳转至首页 */ ipcRenderer.send('open-first-page') //saveHistory(); //clearAll(); return } dialog .showSaveDialog({ title: language_str('saveFile'), //'保存文件' filters: [{ name: 'Soon File Type', extensions: ['soon'] }] }) .then((result) => { if (result.filePath == '') { return } if (result.filePath.substring(result.filePath.length - 5).indexOf('.') == -1) { result.filePath += '.soon' } let fs = require('fs') o.soonType = 2 fs.writeFileSync(result.filePath, JSON.stringify(o)) openAs.name = result.filePath layer.msg(language_str('saveSucc') + openAs.name) //'保存成功至' /* 2022-07-16 直接跳转至首页 */ ipcRenderer.send('open-first-page') //saveHistory(); //clearAll(); }) .catch((err) => { console.log() }) layer.close(index) }, function (index) { /* 2022-07-16 直接跳转至首页 */ //clearAll(); ipcRenderer.send('open-first-page') } ) }) function chagneTitle() { } function addBackground() { // 类型改变 fabric.Image.fromURL('./public/images/bg_front_2.png', function (image) { //image.set("scaleX",$("#canvas-div").width() / 1200 < 1 ? $("#canvas-div").width() / 1200 : 1) //image.set("scaleY",$("#canvas-div").width() / 1200 < 1 ? $("#canvas-div").width() / 1200 : 1) image.left = ($('#canvas1').width() - image.width * image.get('scaleX')) / 2 image.top = ($('#canvas1').height() - image.height * image.get('scaleY')) / 2 image.selectable = false image.hoverable = false image.hoverCursor = 'default' image.setSrc(image.toDataURL(), function (image) { background_image1 = image background_image = background_image1 canvas.add(image) canvas.renderAll() //pre_objs1.push(JSON.stringify(objs1)); //pre_json1.push(canvas1.toJSON(["selectable","hoverable","hoverCursor"])); recordObjs1.push(JSON.stringify(objs1)) recordJson1.push(canvas1.toJSON(['selectable', 'hoverable', 'hoverCursor', 'text', 'fontStyle', 'fontWeight', 'underline'])) }) // 类型改变 fabric.Image.fromURL('./public/images/bg_back_2.png', function (image) { image.left = ($('#canvas2').width() - image.width) / 2 image.top = ($('#canvas2').height() - image.height) / 2 image.selectable = false image.hoverable = false image.hoverCursor = 'default' image.setSrc(image.toDataURL(), function (image) { background_image2 = image canvas2.add(image) canvas2.renderAll() //pre_objs2.push(JSON.stringify(objs2)); //pre_json2.push(canvas2.toJSON(["selectable","hoverable","hoverCursor"])); recordObjs2.push(JSON.stringify(objs2)) recordJson2.push(canvas2.toJSON(['selectable', 'hoverable', 'hoverCursor', 'text', 'fontStyle', 'fontWeight', 'underline'])) let file = GetFile().get('file') console.log(file) if (file && file != 'empty') { open(file) } }) }) is_bgi_add = true }) } function selectObject(target, index) { updateControls() $('#base_control').show() //$("#text_x").val((target.left - background_image.left).toFixed(1)); //$("#text_y").val((target.top - background_image.top).toFixed(1)); //$("#text_w").val(parseFloat(target.get("scaleX") * target.get("width")).toFixed(1)); //$("#text_h").val(parseFloat(target.get("scaleY") * target.get("height")).toFixed(1)); //$("#text_r").val(target.get("angle").toFixed(0)); } function updateControls() { $('#text_r').val(canvas.getActiveObject().get('angle').toFixed(0)) $('#text_x').val((canvas.getActiveObject().get('left') - background_image.left).toFixed(0)) $('#text_y').val((canvas.getActiveObject().get('top') - background_image.top).toFixed(0)) $('#text_h').val((canvas.getActiveObject().get('scaleY') * canvas.getActiveObject().get('height')).toFixed(0)) $('#text_w').val((canvas.getActiveObject().get('scaleX') * canvas.getActiveObject().get('width')).toFixed(0)) if (canvas.getActiveObject().get('selectable')) { $('#lock_img').attr('src', 'public/images/unlock20.png') //已经上锁,需要解锁 } else { $('#lock_img').attr('src', 'public/images/lock20.png') //没上锁,可以上锁 } } function checkName(name) { //检查字段名是否重复了 for (let item of objs1) { if (item.name == name) { return false } } for (let item of objs2) { if (item.name == name) { return false } } return true } function resName(pre_name) { //返回的是不重复的字段名 let num = objs1.length + objs2.length - 1 do { num++ } while (!checkName(pre_name + num)) //重复了就再加1 return pre_name + num } function addPic(pointer) { pre_add_image.left = pointer.x pre_add_image.top = pointer.y canvas.add(pre_add_image) objs.push({ type: 1, black: false }) canvas.renderAll() updateList() recordState() //OpenDialog(); //function OpenDialog() //{ // dialog.showOpenDialog({ // title: "请选择图片", // buttonLabel: "确认", // filters: [ // { name: 'Image File Type', extensions: ['png', 'jpg'] }, // ] // }).then(result => { // if(result.canceled)return; // //console.log(result.filePaths) // fabric.Image.fromURL(result.filePaths[0], function(image) { // image.left = pointer.x; // image.top = pointer.y; // // canvas.add(image); // objs.push({type: 1}); // canvas.renderAll(); // updateList(); // recordState(); // } ); // }).catch(err => { // console.log(err) // }) //} } function selectPic(target, index) { //透明度 $('#pic_control').show() $("#set_bg").show(); pic_op.setValue(100 - canvas.getActiveObject().get('opacity') * 100) let idx = getIndex(canvas.getActiveObject()) // $("#pic_black").prop("checked", objs[idx-1].black ? 'checked' : ''); $('#out_pic_control').hide() $('#text_control').hide() $("#circle_text_control").hide(); $('#out_text_control').hide() $('#rect_control').hide() $('#circle_control').hide() $('#line_control').hide() $('#counter_control').hide() $('#qrcode_Controll').hide() $('#barcode_controll').hide() } function addOutPic(pointer) { fabric.Image.fromURL('./public/images/outpic_extra.png', function (image) { let width = canvas.getWidth() let height = canvas.getHeight() image.left = pointer.x image.top = pointer.y image.opacity = 1 //image.on("selected",function(){//test well // console.log(222); //}); image.setSrc(image.toDataURL(), function (image) { canvas.add(image) objs.push({ type: 2, name: resName('OUT_PIC_'), black: false }) canvas.renderAll() updateList() recordState() }) }) } function selectOutPic(target, index) { //字段名 $('#out_pic_control').show() out_pic_op.setValue(100 - canvas.getActiveObject().get('opacity') * 100) let idx = getIndex(canvas.getActiveObject()) $('#out_pic_field_name').val(objs[idx - 1].name) // $("#out_pic_black").prop("checked", objs[idx-1].black ? 'checked' : ''); $('#pic_control').hide() $("#set_bg").hide(); $('#text_control').hide() $("#circle_text_control").hide(); $('#out_text_control').hide() $('#rect_control').hide() $('#circle_control').hide() $('#line_control').hide() $('#counter_control').hide() $('#qrcode_Controll').hide() $('#barcode_controll').hide() } function addText(pointer) { let text = new fabric.IText('TEXT', { //源:文本 left: pointer.x, top: pointer.y, fill: '#000000', textBackgroundColor: '', fontStyle: 'normal', fontWeight: 'normal', underline: false, linethrough: false, fontFamily: 'Arial' }) text.setControlVisible('ml', false) text.setControlVisible('mt', false) text.setControlVisible('mr', false) text.setControlVisible('mb', false) canvas.add(text) objs.push({ type: 3, black: false }) canvas.renderAll() updateList() recordState() } function selectText() { //console.log(canvas.getActiveObject().get("fontFamily")); $('#text_control').show() $('#text_color').val(canvas.getActiveObject().get('fill')) $('#text_back_color').val(canvas.getActiveObject().get('textBackgroundColor') == '' ? '#ffffff' : canvas.getActiveObject().get('textBackgroundColor')) let val = parseFloat(canvas.getActiveObject().get("fontSize"))*72/dpi if (val%0.5!==0) val = Math.round(val*2)/2 $("#text_size").val(val); $('#text_text').val(canvas.getActiveObject().get('text')) $('#text_font_family').val(canvas.getActiveObject().get('fontFamily')) if (canvas.getActiveObject().get('underline') == true) { $('#text_underline').addClass('ui-radio-acitve') } else { $('#text_underline').removeClass('ui-radio-acitve') } if (canvas.getActiveObject().get('fontWeight') == 'bold') { $('#text_bold').addClass('ui-radio-acitve') } else { $('#text_bold').removeClass('ui-radio-acitve') } if (canvas.getActiveObject().get('fontStyle') == 'italic') { $('#text_italics').addClass('ui-radio-acitve') } else { $('#text_italics').removeClass('ui-radio-acitve') } if (canvas.getActiveObject().get('linethrough') == true) { $('#text_linethrough').addClass('ui-radio-acitve') } else { $('#text_linethrough').removeClass('ui-radio-acitve') } $('#pic_control').hide() $("#set_bg").hide(); $('#out_pic_control').hide() $("#circle_text_control").hide(); $('#out_text_control').hide() $('#rect_control').hide() $('#circle_control').hide() $('#line_control').hide() $('#counter_control').hide() $('#qrcode_Controll').hide() $('#barcode_controll').hide() } function getDisdance(x1, y1, x2, y2) { var dx = Math.abs(x2 - x1); // 计算x轴上的距离差,并取绝对值 var dy = Math.abs(y2 - y1); // 计算y轴上的距离差,并取绝对值 var distance = Math.sqrt(dx * dx + dy * dy); // 应用勾股定理计算距离 return distance; } function getDeg(pointer) { // 计算点击位置与画布中心的坐标差 var centerX = canvas.width / 2; var centerY = canvas.height / 2; var mouseX = pointer.x; var mouseY = pointer.y; var dx = mouseX - centerX; var dy = mouseY - centerY; // 计算旋转角度(弧度) var angleRad = Math.atan2(dy, dx); // 将角度转换为度数 var angleDeg = angleRad * (180/Math.PI); if (angleDeg < 0) { angleDeg += 360; } angleDeg += 90 return angleDeg } function addCircleText(pointer) { let distance = getDisdance(pointer.x, pointer.y, canvas.width/2,canvas.height/2) let angleDeg = getDeg(pointer) let text = new fabric.CurvedText('Circle TEXT', {//源:圆形文本 left: pointer.x, top: pointer.y, fill: "#000000", textBackgroundColor: "", fontStyle: "normal", fontWeight: "normal", diameter: distance*2, fontSize: 30, underline: false, linethrough: false, lockScalingX: true, lockScalingY: true, fontFamily: 'Arial', originX: 'center', originY: 'center', angle: angleDeg, flipped: pointer.y > canvas.height/2 ? true : false }); // distance = getDisdance(pointer.x+text.width/2, pointer.y, canvas.width/2,canvas.height/2) // text.set({diameter: distance*2}) text.setControlVisible("ml", false); text.setControlVisible("mt", false); text.setControlVisible("mr", false); text.setControlVisible("mb", false); canvas.add(text); objs.push({ type: 11, black: false, circleCenter: 0 }); canvas.renderAll(); updateList(); recordState(); } function selectCircleText() { console.log(canvas.getActiveObject().get("text")) let idx = getIndex(canvas.getActiveObject()); $("#circle_text_control").show(); $("#circle_text_color").val(canvas.getActiveObject().get("fill")); $("#circle_text_back_color").val(canvas.getActiveObject().get("textBackgroundColor") == "" ? '#ffffff' : canvas.getActiveObject().get("textBackgroundColor")); circle_text_size.setValue(canvas.getActiveObject().get("fontSize") - 10); circle_text_diameter.setValue(canvas.getActiveObject().get("diameter")-50); $("#circle_text_center").prop("checked", objs[idx - 1].circleCenter ? 'checked' : ''); $("#circle_text_text").val(canvas.getActiveObject().get("text")); $("#circle_text_font_family").val(canvas.getActiveObject().get("fontFamily")); if (canvas.getActiveObject().get("underline") == true) { $("#circle_text_underline").addClass("ui-radio-acitve") } else { $("#circle_text_underline").removeClass("ui-radio-acitve") } if (canvas.getActiveObject().get("fontWeight") == "bold") { $("#circle_text_bold").addClass("ui-radio-acitve") } else { $("#circle_text_bold").removeClass("ui-radio-acitve") } if (canvas.getActiveObject().get("fontStyle") == "italic") { $("#circle_text_italics").addClass("ui-radio-acitve") } else { $("#circle_text_italics").removeClass("ui-radio-acitve") } if (canvas.getActiveObject().get("linethrough") == true) { $("#circle_text_linethrough").addClass("ui-radio-acitve") } else { $("#circle_text_linethrough").removeClass("ui-radio-acitve") } $("#pic_control").hide(); $("#set_bg").hide(); $("#rotate").hide(); $("#out_pic_control").hide(); $("#text_control").hide(); $("#out_text_control").hide(); $("#rect_control").hide(); $("#circle_control").hide(); $("#line_control").hide(); $("#counter_control").hide(); $("#qrcode_Controll").hide(); $("#barcode_controll").hide(); } function addOutText(pointer) { //MERGE_TEXT_1 let text = new fabric.Text('MERGE TEXT', { //源:合成文本 left: pointer.x, top: pointer.y, fill: '#000000', fontStyle: 'normal', fontWeight: 'normal', textBackgroundColor: '', underline: false, linethrough: false, fontFamily: 'Arial', textAlign: 'center' }) //text.on({ // 'scaling': function(e) { // var obj = this, // w = obj.width * obj.scaleX, // h = obj.height * obj.scaleY; // // obj.set({ // 'height' : h, // 'width' : w, // 'scaleX' : 1, // 'scaleY' : 1 // }); // } //}); text.setControlVisible('ml', false) text.setControlVisible('mt', false) text.setControlVisible('mr', false) text.setControlVisible('mb', false) canvas.add(text) objs.push({ type: 4, name: resName('OUT_TEXT_'), exceed: false, autoWrap: false, fixSize: false, black: false, align: 'center' }) canvas.renderAll() updateList() recordState() } function selectOutText() { //color //size const align = canvas.getActiveObject().get('textAlign') if (align === 'left') { $('#out_left_alignment').parent().addClass('tool1') } else if (align === 'right') { $('#out_right_alignment').parent().addClass('tool1') } else { $('#out_center_alignment').parent().addClass('tool1') } $('#out_text_control').show() $('#out_text_color').val(canvas.getActiveObject().get('fill')) $('#out_text_text').val(canvas.getActiveObject().get('text')) let val = parseFloat(canvas.getActiveObject().get("fontSize"))*72/dpi if (val%0.5!==0) val = Math.round(val*2)/2 $("#out_text_size").val(val); $('#out_text_back_color').val(canvas.getActiveObject().get('textBackgroundColor') == '' ? '#ffffff' : canvas.getActiveObject().get('textBackgroundColor')) let idx = getIndex(canvas.getActiveObject()) $('#out_text_field_name').val(objs[idx - 1].name) $('#out_text_font_family').val(canvas.getActiveObject().get('fontFamily')) $('#exceed').prop('checked', objs[idx - 1].exceed ? 'checked' : '') $('#autoWrap').prop('checked', objs[idx - 1].autoWrap ? 'checked' : '') $('#fixSize').prop('checked', objs[idx - 1].fixSize ? 'checked' : '') if (canvas.getActiveObject().get('underline') == true) { $('#out_text_underline').addClass('ui-radio-acitve') } else { $('#out_text_underline').removeClass('ui-radio-acitve') } if (canvas.getActiveObject().get('fontWeight') == 'bold') { $('#out_text_bold').addClass('ui-radio-acitve') } else { $('#out_text_bold').removeClass('ui-radio-acitve') } if (canvas.getActiveObject().get('fontStyle') == 'italic') { $('#out_text_italics').addClass('ui-radio-acitve') } else { $('#out_text_italics').removeClass('ui-radio-acitve') } if (canvas.getActiveObject().get('linethrough') == true) { $('#out_text_linethrough').addClass('ui-radio-acitve') } else { $('#out_text_linethrough').removeClass('ui-radio-acitve') } $('#pic_control').hide() $("#set_bg").hide(); $('#out_pic_control').hide() $('#text_control').hide() $("#circle_text_control").hide(); $('#rect_control').hide() $('#circle_control').hide() $('#line_control').hide() $('#counter_control').hide() $('#qrcode_Controll').hide() $('#barcode_controll').hide() } function addRect(pointer) { let rect = new fabric.Rect({ left: pointer.x, top: pointer.y, fill: '', stroke: "#ff0000", strokeWidth: 3, width: 100, height: 100 }) canvas.add(rect) objs.push({ type: 5, black: false }) canvas.renderAll() updateList() recordState() } function selectRect() { //color $('#rect_control').show() $('#rect_color').val(canvas.getActiveObject().get('fill') == '' ? '#ffffff' : canvas.getActiveObject().get('fill')) $('#rect_stroke').val(canvas.getActiveObject().get('stroke') == '' ? '#ffffff' : canvas.getActiveObject().get('stroke')) $('#rect_stroke_width').val(canvas.getActiveObject().get('strokeWidth')) $('#rect_radius').val(canvas.getActiveObject().get('rx')) rect_op.setValue(100 - canvas.getActiveObject().get('opacity') * 100) let a = canvas.getActiveObject().getCoords() console.log(getCoordsMinX(a)) $('#pic_control').hide() $("#set_bg").hide(); $('#out_pic_control').hide() $('#text_control').hide() $("#circle_text_control").hide(); $('#out_text_control').hide() $('#circle_control').hide() $('#line_control').hide() $('#counter_control').hide() $('#qrcode_Controll').hide() $('#barcode_controll').hide() } function addCircle(pointer) { let circle = new fabric.Circle({ left: pointer.x, top: pointer.y, fill: '', stroke: '#ff0000', strokeWidth: 3, radius: 100, strokeUniform: true }) canvas.add(circle) objs.push({ type: 6, black: false }) canvas.renderAll() updateList() recordState() } function selectCircle() { //border-color //color $('#circle_control').show() $('#circle_color').val(canvas.getActiveObject().get('fill') == '' ? '#ffffff' : canvas.getActiveObject().get('fill')) $('#circle_stroke').val(canvas.getActiveObject().get('stroke') == '' ? '#ffffff' : canvas.getActiveObject().get('stroke')) $('#circle_stroke_width').val(canvas.getActiveObject().get('strokeWidth')) circle_op.setValue(100 - canvas.getActiveObject().get('opacity') * 100) $('#pic_control').hide() $("#set_bg").hide(); $('#out_pic_control').hide() $('#text_control').hide() $("#circle_text_control").hide(); $('#out_text_control').hide() $('#rect_control').hide() $('#line_control').hide() $('#counter_control').hide() $('#qrcode_Controll').hide() $('#barcode_controll').hide() } function addLine(pointer) { let line = new fabric.Line([50, 100, 200, 100], { left: pointer.x, top: pointer.y, stroke: '#ff0000', strokeWidth: 3, strokeDashArray: [0, 0], }) line.setControlVisible('tl', false) line.setControlVisible('tr', false) line.setControlVisible('br', false) line.setControlVisible('bl', false) line.setControlVisible('mt', false) line.setControlVisible('mb', false) canvas.add(line) objs.push({ type: 7, black: false }) canvas.renderAll() updateList() recordState() } function selectLine() { //color //weight $('#line_control').show() let idx = getIndex(canvas.getActiveObject()) $('#line_color').val(canvas.getActiveObject().get('stroke')) $('#line_dist').val(canvas.getActiveObject().get('strokeDashArray')[0]) $('#text_h').val(canvas.getActiveObject().get('strokeWidth')) $('#pic_control').hide() $("#set_bg").hide(); $('#out_pic_control').hide() $('#text_control').hide() $("#circle_text_control").hide(); $('#out_text_control').hide() $('#rect_control').hide() $('#circle_control').hide() $('#counter_control').hide() $('#qrcode_Controll').hide() $('#barcode_controll').hide() } function addQrCode(pointer) { let qr = jrQrcode.getQrBase64('https://www.cardsoon.com', { padding: 0 }) fabric.Image.fromURL(qr, function (image) { image.left = pointer.x image.top = pointer.y canvas.add(image) objs.push({ type: 8, name: resName('QR_CODE_'), color: '#000000', val: 'http://www.cardsoon.com', black: false }) canvas.renderAll() updateList() recordState() }) } function selectQrCode() { //字段名 //background-color //color $('#qrcode_Controll').show() let idx = getIndex(canvas.getActiveObject()) $('#qrcode_field_name').val(objs[idx - 1].name) $('#qrcode_color').val(objs[idx - 1].color) $('#qrcode_val').val(objs[idx - 1].val) $('#line_control').hide() $('#pic_control').hide() $('#out_pic_control').hide() $('#text_control').hide() $("#circle_text_control").hide(); $('#out_text_control').hide() $('#rect_control').hide() $('#circle_control').hide() $('#counter_control').hide() $('#barcode_controll').hide() } function addBarCode(pointer) { JsBarcode('#barcode', '123456789', { margin: 0, lineColor: '#000000', fontSize: 18, font: 'Arial' }) let barcode = document.getElementById('barcode') let bar = barcode.toDataURL('image/png') fabric.Image.fromURL(bar, function (image) { image.left = pointer.x image.top = pointer.y canvas.add(image) objs.push({ type: 9, name: resName('BAR_CODE_'), val: '123456789', color: '#000000', fontSize: 18, font: 'Arial', show: false, black: false }) //show是取消文字显示 canvas.renderAll() updateList() recordState() }) } function selectBarCode() { //字段名 //background-color //color $('#barcode_controll').show() let idx = getIndex(canvas.getActiveObject()) $('#barcode_field_name').val(objs[idx - 1].name) $('#barcode_font_family').val(objs[idx - 1].font) let val = parseFloat(objs[idx - 1].fontSize)*72/dpi if (val%0.5!==0) val = Math.round(val*2)/2 $("#barcode_size").val(val); $('#barcode_val').val(objs[idx - 1].val) $('#barcode_show').prop('checked', objs[idx - 1].show ? 'checked' : '') $('#line_control').hide() $('#pic_control').hide() $('#out_pic_control').hide() $('#text_control').hide() $("#circle_text_control").hide(); $('#out_text_control').hide() $('#rect_control').hide() $('#circle_control').hide() $('#counter_control').hide() $('#qrcode_Controll').hide() } function addCounter(pointer) { let text = new fabric.Text('0', { left: pointer.x, top: pointer.y, fill: '#000000' }) canvas.add(text) objs.push({ type: 10, name: resName('COUNTER_'), start: 0, add: 1, black: false }) canvas.renderAll() updateList() recordState() console.log(canvas.getObjects()) } function selectCounter() { //起始 //终止 //增量 $('#counter_control').show() let idx = getIndex(canvas.getActiveObject()) $('#counter_start').val(objs[idx - 1].start) $('#counter_add').val(objs[idx - 1].add) $('#counter_color').val(canvas.getActiveObject().get('fill')) $('#count_font_family').val(canvas.getActiveObject().get('fontFamily')) let val = parseFloat(canvas.getActiveObject().get("fontSize"))*72/dpi if (val%0.5!==0) val = Math.round(val*2)/2 $("#count_size").val(val); $('#line_control').hide() $('#pic_control').hide() $('#out_pic_control').hide() $('#text_control').hide() $("#circle_text_control").hide(); $('#out_text_control').hide() $('#rect_control').hide() $('#circle_control').hide() $('#qrcode_Controll').hide() $('#barcode_controll').hide() } function getIndex(target, _canvas = null) { let temp_objs if (_canvas == null) { temp_objs = canvas.getObjects() } else { temp_objs = _canvas.getObjects() } let i = 0 for (let res of temp_objs) { if (target == res) { return i } i++ } return 0 } function getType(target) { let temp_objs = canvas.getObjects() let i = 0 for (let res of temp_objs) { if (target == res) { return objs[i].type } i++ } } function updateList() { let str = '' let i = 0 for (let item of objs) { switch (item.type) { case 1 /* 2022-06-14修改*/: str = '