UNPKG

tui-image-editor.upgrade

Version:
985 lines (832 loc) 50.4 kB
/** * basic.js * @author NHN Ent. FE Development Team <dl_javascript@nhnent.com> * @fileoverview */ 'use strict'; var supportingFileAPI = !!(window.File && window.FileList && window.FileReader); var rImageType = /data:(image\/.+);base64,/; var shapeOptions = {}; var shapeType; var activeObjectId; // Buttons var $btns = $('.menu-item'); var $btnsActivatable = $btns.filter('.activatable'); var $inputImage = $('#input-image-file'); var $btnDownload = $('#btn-download'); var $btnUndo = $('#btn-undo'); var $btnRedo = $('#btn-redo'); var $btnClearObjects = $('#btn-clear-objects'); var $btnRemoveActiveObject = $('#btn-remove-active-object'); var $btnCrop = $('#btn-crop'); var $btnFlip = $('#btn-flip'); var $btnRotation = $('#btn-rotation'); var $btnDrawLine = $('#btn-draw-line'); var $btnDrawShape = $('#btn-draw-shape'); var $btnApplyCrop = $('#btn-apply-crop'); var $btnCancelCrop = $('#btn-cancel-crop'); var $btnFlipX = $('#btn-flip-x'); var $btnFlipY = $('#btn-flip-y'); var $btnResetFlip = $('#btn-reset-flip'); var $btnRotateClockwise = $('#btn-rotate-clockwise'); var $btnRotateCounterClockWise = $('#btn-rotate-counter-clockwise'); var $btnText = $('#btn-text'); var $btnTextStyle = $('.btn-text-style'); var $btnAddIcon = $('#btn-add-icon'); var $btnRegisterIcon = $('#btn-register-icon'); var $btnMaskFilter = $('#btn-mask-filter'); var $btnImageFilter = $('#btn-image-filter'); var $btnLoadMaskImage = $('#input-mask-image-file'); var $btnApplyMask = $('#btn-apply-mask'); var $btnClose = $('.close'); // Input etc. var $inputRotationRange = $('#input-rotation-range'); var $inputBrushWidthRange = $('#input-brush-width-range'); var $inputFontSizeRange = $('#input-font-size-range'); var $inputStrokeWidthRange = $('#input-stroke-width-range'); var $inputCheckTransparent = $('#input-check-transparent'); var $inputCheckGrayscale = $('#input-check-grayscale'); var $inputCheckInvert = $('#input-check-invert'); var $inputCheckSepia = $('#input-check-sepia'); var $inputCheckSepia2 = $('#input-check-sepia2'); var $inputCheckBlur = $('#input-check-blur'); var $inputCheckOld = $('#input-check-old'); var $inputCheckSharpen = $('#input-check-sharpen'); var $inputCheckEmboss = $('#input-check-emboss'); var $inputCheckRemoveWhite = $('#input-check-remove-white'); var $inputRangeRemoveWhiteThreshold = $('#input-range-remove-white-threshold'); var $inputRangeOldPercent = $('#input-range-old-percent'); var $inputRangeRemoveWhiteDistance = $('#input-range-remove-white-distance'); var $inputCheckBrightness = $('#input-check-brightness'); var $inputRangeBrightnessValue = $('#input-range-brightness-value'); var $inputCheckNoise = $('#input-check-noise'); var $inputRangeNoiseValue = $('#input-range-noise-value'); var $inputCheckGradientTransparency = $('#input-check-gradient-transparancy'); var $inputRangeGradientTransparencyValue = $('#input-range-gradient-transparency-value'); var $inputCheckPixelate = $('#input-check-pixelate'); var $inputRangePixelateValue = $('#input-range-pixelate-value'); var $inputCheckTint = $('#input-check-tint'); var $inputRangeTintOpacityValue = $('#input-range-tint-opacity-value'); var $inputCheckMultiply = $('#input-check-multiply'); var $inputCheckBlend = $('#input-check-blend'); var $inputCheckColorFilter = $('#input-check-color-filter'); var $inputRangeColorFilterValue = $('#input-range-color-filter-value'); // Sub menus var $displayingSubMenu = $(); var $cropSubMenu = $('#crop-sub-menu'); var $flipSubMenu = $('#flip-sub-menu'); var $rotationSubMenu = $('#rotation-sub-menu'); var $freeDrawingSubMenu = $('#free-drawing-sub-menu'); var $drawLineSubMenu = $('#draw-line-sub-menu'); var $drawShapeSubMenu = $('#draw-shape-sub-menu'); var $textSubMenu = $('#text-sub-menu'); var $iconSubMenu = $('#icon-sub-menu'); var $filterSubMenu = $('#filter-sub-menu'); var $imageFilterSubMenu = $('#image-filter-sub-menu'); // Select line type var $selectLine = $('[name="select-line-type"]'); // Select shape type var $selectShapeType = $('[name="select-shape-type"]'); // Select color of shape type var $selectColorType = $('[name="select-color-type"]'); //Select blend type var $selectBlendType = $('[name="select-blend-type"]'); // Image editor var imageEditor = new tui.ImageEditor('.tui-image-editor', { cssMaxWidth: 700, cssMaxHeight: 500, scaleToMax: true, selectionStyle: { cornerSize: 20, rotatingPointOffset: 70 }, noSelector: true }); // Color picker for free drawing var brushColorpicker = tui.component.colorpicker.create({ container: $('#tui-brush-color-picker')[0], color: '#000000' }); // Color picker for text palette var textColorpicker = tui.component.colorpicker.create({ container: $('#tui-text-color-picker')[0], color: '#000000' }); // Color picker for shape var shapeColorpicker = tui.component.colorpicker.create({ container: $('#tui-shape-color-picker')[0], color: '#000000' }); // Color picker for icon var iconColorpicker = tui.component.colorpicker.create({ container: $('#tui-icon-color-picker')[0], color: '#000000' }); var tintColorpicker = tui.component.colorpicker.create({ container: $('#tui-tint-color-picker')[0], color: '#000000' }); var multiplyColorpicker = tui.component.colorpicker.create({ container: $('#tui-multiply-color-picker')[0], color: '#000000' }); var blendColorpicker = tui.component.colorpicker.create({ container: $('#tui-blend-color-picker')[0], color: '#00FF00' }); // Common global functions // HEX to RGBA function hexToRGBa(hex, alpha) { var r = parseInt(hex.slice(1, 3), 16); var g = parseInt(hex.slice(3, 5), 16); var b = parseInt(hex.slice(5, 7), 16); var a = alpha || 1; return 'rgba(' + r + ', ' + g + ', ' + b + ', ' + a + ')'; } function base64ToBlob(data) { var mimeString = ''; var raw, uInt8Array, i, rawLength; raw = data.replace(rImageType, function(header, imageType) { mimeString = imageType; return ''; }); raw = atob(raw); rawLength = raw.length; uInt8Array = new Uint8Array(rawLength); // eslint-disable-line for (i = 0; i < rawLength; i += 1) { uInt8Array[i] = raw.charCodeAt(i); } return new Blob([uInt8Array], {type: mimeString}); } function resizeEditor() { var $editor = $('.tui-image-editor'); var $container = $('.tui-image-editor-canvas-container'); var height = parseFloat($container.css('max-height')); $editor.height(height); } function getBrushSettings() { var brushWidth = $inputBrushWidthRange.val(); var brushColor = brushColorpicker.getColor(); return { width: brushWidth, color: hexToRGBa(brushColor, 0.5) }; } function activateShapeMode() { if (imageEditor.getDrawingMode() !== 'SHAPE') { imageEditor.stopDrawingMode(); imageEditor.startDrawingMode('SHAPE'); } } function activateIconMode() { imageEditor.stopDrawingMode(); } function activateTextMode() { if (imageEditor.getDrawingMode() !== 'TEXT') { imageEditor.stopDrawingMode(); imageEditor.startDrawingMode('TEXT'); } } function setTextToolbar(obj) { var fontSize = obj.fontSize; var fontColor = obj.fill; $inputFontSizeRange.val(fontSize); textColorpicker.setColor(fontColor); } function setIconToolbar(obj) { var iconColor = obj.fill; iconColorpicker.setColor(iconColor); } function setShapeToolbar(obj) { var strokeColor, fillColor, isTransparent; var colorType = $selectColorType.val(); if (colorType === 'stroke') { strokeColor = obj.stroke; isTransparent = (strokeColor === 'transparent'); if (!isTransparent) { shapeColorpicker.setColor(strokeColor); } } else if (colorType === 'fill') { fillColor = obj.fill; isTransparent = (fillColor === 'transparent'); if (!isTransparent) { shapeColorpicker.setColor(fillColor); } } $inputCheckTransparent.prop('checked', isTransparent); $inputStrokeWidthRange.val(obj.strokeWidth); } function showSubMenu(type) { var $submenu; switch (type) { case 'shape': $submenu = $drawShapeSubMenu; break; case 'icon': $submenu = $iconSubMenu; break; case 'text': $submenu = $textSubMenu; break; default: $submenu = 0; } $displayingSubMenu.hide(); $displayingSubMenu = $submenu.show(); } function applyOrRemoveFilter(applying, type, options) { if (applying) { imageEditor.applyFilter(type, options).then(result => { console.log(result); }); } else { imageEditor.removeFilter(type); } } console.log(imageEditor, 12); // Attach image editor custom events imageEditor.on({ objectRemove: function(target) { console.log('remove'); imageEditor.removeActiveObject(); }, textEditing: function(target) { console.log('editing', target); var id = target.__fe_id; imageEditor.changeText(id, 'lalal'); }, objectRotateFix: function(data) { console.log('fix', data.angle); }, objectAdded: function(objectProps) { console.info(objectProps); }, undoStackChanged: function(length) { if (length) { $btnUndo.removeClass('disabled'); } else { $btnUndo.addClass('disabled'); } resizeEditor(); }, redoStackChanged: function(length) { if (length) { $btnRedo.removeClass('disabled'); } else { $btnRedo.addClass('disabled'); } resizeEditor(); }, objectScaled: function(obj) { if (obj.type === 'text') { $inputFontSizeRange.val(obj.fontSize); } }, addText: function(pos) { imageEditor.addText('双击编辑', { position: pos.originPosition, styles: { outerDecoration: { backgroundColor: '#ffecd0', borderColor: '#cd1b1e', borderLineWidth: 2, cornerSize: 40, radius: 10, offsetX: 24, offsetY: 12, tl: 'data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIxMjAiIGhlaWdodD0iMTIwIiB2aWV3Qm94PSIwIDAgMTIwIDEyMCI+ICA8bWV0YWRhdGE+PD94cGFja2V0IGJlZ2luPSLvu78iIGlkPSJXNU0wTXBDZWhpSHpyZVN6TlRjemtjOWQiPz48eDp4bXBtZXRhIHhtbG5zOng9ImFkb2JlOm5zOm1ldGEvIiB4OnhtcHRrPSJBZG9iZSBYTVAgQ29yZSA1LjYtYzEzOCA3OS4xNTk4MjQsIDIwMTYvMDkvMTQtMDE6MDk6MDEgICAgICAgICI+ICAgPHJkZjpSREYgeG1sbnM6cmRmPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5LzAyLzIyLXJkZi1zeW50YXgtbnMjIj4gICAgICA8cmRmOkRlc2NyaXB0aW9uIHJkZjphYm91dD0iIi8+ICAgPC9yZGY6UkRGPjwveDp4bXBtZXRhPiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgPD94cGFja2V0IGVuZD0idyI/PjwvbWV0YWRhdGE+PGRlZnM+ICAgIDxzdHlsZT4gICAgICAuY2xzLTEgeyAgICAgICAgZmlsbDogI2YxNDQ0NDsgICAgICAgIGZpbGwtcnVsZTogZXZlbm9kZDsgICAgICB9ICAgIDwvc3R5bGU+ICA8L2RlZnM+ICA8ZyBpZD0iVG9wX2xlZnQiPiAgICA8ZyBpZD0iVG9wX2xlZnQtMiIgZGF0YS1uYW1lPSJUb3BfbGVmdCI+ICAgICAgPHBhdGggaWQ9IuWchuinkuefqeW9ol83X+aLt+i0nV84IiBkYXRhLW5hbWU9IuWchuinkuefqeW9oiA3IOaLt+i0nSA4IiBjbGFzcz0iY2xzLTEiIGQ9Ik0xMjY3LjY5LDMwOWExLjU0LDEuNTQsMCwwLDEsMS41NCwxLjUzOHYzLjA3N2ExLjU0LDEuNTQsMCwwLDEtMy4wOCwwdi0zLjA3N0ExLjU0LDEuNTQsMCwwLDEsMTI2Ny42OSwzMDlabTAsOS44NDZhMS41NCwxLjU0LDAsMCwxLDEuNTQsMS41Mzl2My4wNzdhMS41NCwxLjU0LDAsMCwxLTMuMDgsMHYtMy4wNzdBMS41NCwxLjU0LDAsMCwxLDEyNjcuNjksMzE4Ljg0NlptMy42OS0zLjA3N2gzLjA4YTEuNTM5LDEuNTM5LDAsMSwxLDAsMy4wNzdoLTMuMDhBMS41MzksMS41MzksMCwwLDEsMTI3MS4zOCwzMTUuNzY5Wm0tOS44NCwwaDMuMDhhMS41MzksMS41MzksMCwwLDEsMCwzLjA3N2gtMy4wOEExLjUzOSwxLjUzOSwwLDEsMSwxMjYxLjU0LDMxNS43NjlaIiB0cmFuc2Zvcm09InRyYW5zbGF0ZSgtMTIxMyAtMjYwKSIvPiAgICAgIDxwYXRoIGlkPSLlnIbop5Lnn6nlvaJfN1/mi7fotJ1fOC0yIiBkYXRhLW5hbWU9IuWchuinkuefqeW9oiA3IOaLt+i0nSA4IiBjbGFzcz0iY2xzLTEiIGQ9Ik0xMjkyLjI1LDMyNWExLjI0NSwxLjI0NSwwLDAsMSwxLjI0LDEuMjQ0djIuNTE0YTEuMjQ1LDEuMjQ1LDAsMCwxLTIuNDksMHYtMi41MTRBMS4yNDcsMS4yNDcsMCwwLDEsMTI5Mi4yNSwzMjVabTAsOGExLjI0NSwxLjI0NSwwLDAsMSwxLjI0LDEuMjQ0djIuNTE0YTEuMjQ1LDEuMjQ1LDAsMCwxLTIuNDksMHYtMi41MTRBMS4yNDcsMS4yNDcsMCwwLDEsMTI5Mi4yNSwzMzNabTMtMi41aDIuNWExLjI1LDEuMjUsMCwwLDEsMCwyLjVoLTIuNUExLjI1LDEuMjUsMCwwLDEsMTI5NS4yNSwzMzAuNVptLTguMDEuMDFoMi41MmExLjI0NCwxLjI0NCwwLDAsMSwwLDIuNDg4aC0yLjUyQTEuMjQ0LDEuMjQ0LDAsMCwxLDEyODcuMjQsMzMwLjUxWiIgdHJhbnNmb3JtPSJ0cmFuc2xhdGUoLTEyMTMgLTI2MCkiLz4gICAgPC9nPiAgPC9nPjwvc3ZnPg==', tr: 'data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIxMjAiIGhlaWdodD0iMTIwIiB2aWV3Qm94PSIwIDAgMTIwIDEyMCI+ICA8bWV0YWRhdGE+PD94cGFja2V0IGJlZ2luPSLvu78iIGlkPSJXNU0wTXBDZWhpSHpyZVN6TlRjemtjOWQiPz48eDp4bXBtZXRhIHhtbG5zOng9ImFkb2JlOm5zOm1ldGEvIiB4OnhtcHRrPSJBZG9iZSBYTVAgQ29yZSA1LjYtYzEzOCA3OS4xNTk4MjQsIDIwMTYvMDkvMTQtMDE6MDk6MDEgICAgICAgICI+ICAgPHJkZjpSREYgeG1sbnM6cmRmPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5LzAyLzIyLXJkZi1zeW50YXgtbnMjIj4gICAgICA8cmRmOkRlc2NyaXB0aW9uIHJkZjphYm91dD0iIi8+ICAgPC9yZGY6UkRGPjwveDp4bXBtZXRhPiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgPD94cGFja2V0IGVuZD0idyI/PjwvbWV0YWRhdGE+PGRlZnM+ICAgIDxzdHlsZT4gICAgICAuY2xzLTEgeyAgICAgICAgZmlsbDogI2YxNDQ0NDsgICAgICAgIGZpbGwtcnVsZTogZXZlbm9kZDsgICAgICB9ICAgIDwvc3R5bGU+ICA8L2RlZnM+ICA8ZyBpZD0iVG9wX3JpZ2h0Ij4gICAgPGcgaWQ9IlRvcF9yaWdodC0yIiBkYXRhLW5hbWU9IlRvcF9yaWdodCI+ICAgICAgPHBhdGggaWQ9IuWchuinkuefqeW9ol83X+aLt+i0nV8zIiBkYXRhLW5hbWU9IuWchuinkuefqeW9oiA3IOaLt+i0nSAzIiBjbGFzcz0iY2xzLTEiIGQ9Ik0xNDcyLjUsMzI3YTIuNSwyLjUsMCwwLDEsMi41LDIuNXY1YTIuNSwyLjUsMCwwLDEtNSwwdi01QTIuNSwyLjUsMCwwLDEsMTQ3Mi41LDMyN1ptMCwxNmEyLjUsMi41LDAsMCwxLDIuNSwyLjV2NWEyLjUsMi41LDAsMCwxLTUsMHYtNUEyLjUsMi41LDAsMCwxLDE0NzIuNSwzNDNabTYtNWg1YTIuNSwyLjUsMCwwLDEsMCw1aC01QTIuNSwyLjUsMCwwLDEsMTQ3OC41LDMzOFptLTE2LDBoNWEyLjUsMi41LDAsMCwxLDAsNWgtNUEyLjUsMi41LDAsMCwxLDE0NjIuNSwzMzhaIiB0cmFuc2Zvcm09InRyYW5zbGF0ZSgtMTQzMyAtMjYwKSIvPiAgICAgIDxwYXRoIGlkPSLlnIbop5Lnn6nlvaJfN1/mi7fotJ1fNCIgZGF0YS1uYW1lPSLlnIbop5Lnn6nlvaIgNyDmi7fotJ0gNCIgY2xhc3M9ImNscy0xIiBkPSJNMTQ3NC42OSwzMDBhMS41NCwxLjU0LDAsMCwxLDEuNTQsMS41Mzh2My4wNzdhMS41NCwxLjU0LDAsMCwxLTMuMDgsMHYtMy4wNzdBMS41NCwxLjU0LDAsMCwxLDE0NzQuNjksMzAwWm0wLDkuODQ2YTEuNTQsMS41NCwwLDAsMSwxLjU0LDEuNTM5djMuMDc3YTEuNTQsMS41NCwwLDAsMS0zLjA4LDB2LTMuMDc3QTEuNTQsMS41NCwwLDAsMSwxNDc0LjY5LDMwOS44NDZabTMuNjktMy4wNzdoMy4wOGExLjUzOSwxLjUzOSwwLDEsMSwwLDMuMDc3aC0zLjA4QTEuNTM5LDEuNTM5LDAsMCwxLDE0NzguMzgsMzA2Ljc2OVptLTkuODQsMGgzLjA4YTEuNTM5LDEuNTM5LDAsMCwxLDAsMy4wNzdoLTMuMDhBMS41MzksMS41MzksMCwxLDEsMTQ2OC41NCwzMDYuNzY5WiIgdHJhbnNmb3JtPSJ0cmFuc2xhdGUoLTE0MzMgLTI2MCkiLz4gICAgICA8cGF0aCBpZD0i5ZyG6KeS55+p5b2iXzdf5ou36LSdXzUiIGRhdGEtbmFtZT0i5ZyG6KeS55+p5b2iIDcg5ou36LSdIDUiIGNsYXNzPSJjbHMtMSIgZD0iTTE0OTkuMjUsMzE2YTEuMjQ1LDEuMjQ1LDAsMCwxLDEuMjQsMS4yNDR2Mi41MTRhMS4yNDUsMS4yNDUsMCwwLDEtMi40OSwwdi0yLjUxNEExLjI0NywxLjI0NywwLDAsMSwxNDk5LjI1LDMxNlptMCw4YTEuMjQ1LDEuMjQ1LDAsMCwxLDEuMjQsMS4yNDR2Mi41MTRhMS4yNDUsMS4yNDUsMCwwLDEtMi40OSwwdi0yLjUxNEExLjI0NywxLjI0NywwLDAsMSwxNDk5LjI1LDMyNFptMy0yLjVoMi41YTEuMjUsMS4yNSwwLDAsMSwwLDIuNWgtMi41QTEuMjUsMS4yNSwwLDAsMSwxNTAyLjI1LDMyMS41Wm0tOC4wMS4wMWgyLjUyYTEuMjQ0LDEuMjQ0LDAsMCwxLDAsMi40ODhoLTIuNTJBMS4yNDQsMS4yNDQsMCwwLDEsMTQ5NC4yNCwzMjEuNTFaIiB0cmFuc2Zvcm09InRyYW5zbGF0ZSgtMTQzMyAtMjYwKSIvPiAgICAgIDxwYXRoIGlkPSLlnIbop5Lnn6nlvaJfN1/mi7fotJ1fNyIgZGF0YS1uYW1lPSLlnIbop5Lnn6nlvaIgNyDmi7fotJ0gNyIgY2xhc3M9ImNscy0xIiBkPSJNMTQ0OS4yNSwzMjVhMS4yNDUsMS4yNDUsMCwwLDEsMS4yNCwxLjI0NHYyLjUxNGExLjI0NSwxLjI0NSwwLDAsMS0yLjQ5LDB2LTIuNTE0QTEuMjQ3LDEuMjQ3LDAsMCwxLDE0NDkuMjUsMzI1Wm0wLDhhMS4yNDUsMS4yNDUsMCwwLDEsMS4yNCwxLjI0NHYyLjUxNGExLjI0NSwxLjI0NSwwLDAsMS0yLjQ5LDB2LTIuNTE0QTEuMjQ3LDEuMjQ3LDAsMCwxLDE0NDkuMjUsMzMzWm0zLTIuNWgyLjVhMS4yNSwxLjI1LDAsMCwxLDAsMi41aC0yLjVBMS4yNSwxLjI1LDAsMCwxLDE0NTIuMjUsMzMwLjVabS04LjAxLjAxaDIuNTJhMS4yNDQsMS4yNDQsMCwwLDEsMCwyLjQ4OGgtMi41MkExLjI0NCwxLjI0NCwwLDAsMSwxNDQ0LjI0LDMzMC41MVoiIHRyYW5zZm9ybT0idHJhbnNsYXRlKC0xNDMzIC0yNjApIi8+ICAgIDwvZz4gIDwvZz48L3N2Zz4=', bl: 'data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIxMjAiIGhlaWdodD0iMTIwIiB2aWV3Qm94PSIwIDAgMTIwIDEyMCI+ICA8bWV0YWRhdGE+PD94cGFja2V0IGJlZ2luPSLvu78iIGlkPSJXNU0wTXBDZWhpSHpyZVN6TlRjemtjOWQiPz48eDp4bXBtZXRhIHhtbG5zOng9ImFkb2JlOm5zOm1ldGEvIiB4OnhtcHRrPSJBZG9iZSBYTVAgQ29yZSA1LjYtYzEzOCA3OS4xNTk4MjQsIDIwMTYvMDkvMTQtMDE6MDk6MDEgICAgICAgICI+ICAgPHJkZjpSREYgeG1sbnM6cmRmPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5LzAyLzIyLXJkZi1zeW50YXgtbnMjIj4gICAgICA8cmRmOkRlc2NyaXB0aW9uIHJkZjphYm91dD0iIi8+ICAgPC9yZGY6UkRGPjwveDp4bXBtZXRhPiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgPD94cGFja2V0IGVuZD0idyI/PjwvbWV0YWRhdGE+PGRlZnM+ICAgIDxzdHlsZT4gICAgICAuY2xzLTEgeyAgICAgICAgZmlsbDogI2VhNGM0YzsgICAgICB9ICAgICAgLmNscy0xLCAuY2xzLTIsIC5jbHMtMywgLmNscy00LCAuY2xzLTUgeyAgICAgICAgc3Ryb2tlOiAjY2QxYjFlOyAgICAgICAgc3Ryb2tlLWxpbmVjYXA6IHJvdW5kOyAgICAgICAgc3Ryb2tlLWxpbmVqb2luOiByb3VuZDsgICAgICAgIHN0cm9rZS13aWR0aDogM3B4OyAgICAgIH0gICAgICAuY2xzLTEsIC5jbHMtMiwgLmNscy0zLCAuY2xzLTQgeyAgICAgICAgZmlsbC1ydWxlOiBldmVub2RkOyAgICAgIH0gICAgICAuY2xzLTIgeyAgICAgICAgZmlsbDogI2YzNjE2MTsgICAgICB9ICAgICAgLmNscy0zIHsgICAgICAgIGZpbGw6ICNmZjUxNTE7ICAgICAgfSAgICAgIC5jbHMtNCB7ICAgICAgICBmaWxsOiAjZmY2NzY3OyAgICAgIH0gICAgICAuY2xzLTUgeyAgICAgICAgZmlsbDogI2ZmYzY3MDsgICAgICB9ICAgICAgLmNscy02IHsgICAgICAgIGZvbnQtc2l6ZTogMTguNjY3cHg7ICAgICAgICBmaWxsOiAjY2QxYjFlOyAgICAgICAgdGV4dC1hbmNob3I6IG1pZGRsZTsgICAgICAgIGZvbnQtZmFtaWx5OiAiUGluZ0ZhbmcgU0MiOyAgICAgICAgZm9udC13ZWlnaHQ6IDYwMDsgICAgICB9ICAgIDwvc3R5bGU+ICA8L2RlZnM+ICA8ZyBpZD0iQm90dG9tX2xlZnQiPiAgICA8ZyBpZD0iQm90dG9tX2xlZnQtMiIgZGF0YS1uYW1lPSJCb3R0b21fbGVmdCI+ICAgICAgPGcgaWQ9Iue6ouWMhSI+ICAgICAgICA8cGF0aCBpZD0i5ZyG6KeS55+p5b2iXzEiIGRhdGEtbmFtZT0i5ZyG6KeS55+p5b2iIDEiIGNsYXNzPSJjbHMtMSIgZD0iTTEyOTQuNTcsNDI5Ljg4NmwxOS45LDguNDEzYTUuNjc2LDUuNjc2LDAsMCwxLDIuOTMsNy40NjdsLTEzLjQ0LDMxLjc4OWE1LjY2Niw1LjY2NiwwLDAsMS03LjM5LDMuMTA1bC0xOS45MS04LjQxMmE1LjY2NSw1LjY2NSwwLDAsMS0yLjkyLTcuNDY4bDEzLjQzLTMxLjc4OUE1LjY4MSw1LjY4MSwwLDAsMSwxMjk0LjU3LDQyOS44ODZaIiB0cmFuc2Zvcm09InRyYW5zbGF0ZSgtMTIxMyAtNDA2KSIvPiAgICAgICAgPHBhdGggaWQ9IuW9oueKtl8xMSIgZGF0YS1uYW1lPSLlvaLnirYgMTEiIGNsYXNzPSJjbHMtMiIgZD0iTTEyODUuNTMsNDM3LjEzM3MtMC44Myw2LjUyMiwxMi45NiwxMi40ODksMTcuMDcsMC45ODUsMTcuMDcuOTg1bDIuNTItNS45NDdhNy42NzksNy42NzksMCwwLDAtNS40Mi02Ljk2M2MtNS4wOC0yLjE1NS0xOC4wNi03LjYzNC0xOC4wNi03LjYzNHMtNS41OS0xLjUtNy40LDMuMTA1WiIgdHJhbnNmb3JtPSJ0cmFuc2xhdGUoLTEyMTMgLTQwNikiLz4gICAgICA8L2c+ICAgICAgPGcgaWQ9Iue6ouWMhS0yIiBkYXRhLW5hbWU9Iue6ouWMhSI+ICAgICAgICA8cGF0aCBpZD0i5ZyG6KeS55+p5b2iXzEtMiIgZGF0YS1uYW1lPSLlnIbop5Lnn6nlvaIgMSIgY2xhc3M9ImNscy0zIiBkPSJNMTI1My44Nyw0MTcuNzg4aDMwLjg1YTgsOCwwLDAsMSw4LDhWNDczLjlhOCw4LDAsMCwxLTgsOGgtMzAuODVhOCw4LDAsMCwxLTgtOFY0MjUuNzg4QTgsOCwwLDAsMSwxMjUzLjg3LDQxNy43ODhaIiB0cmFuc2Zvcm09InRyYW5zbGF0ZSgtMTIxMyAtNDA2KSIvPiAgICAgICAgPHBhdGggaWQ9IuW9oueKtl8xMS0yIiBkYXRhLW5hbWU9IuW9oueKtiAxMSIgY2xhc3M9ImNscy00IiBkPSJNMTI0Niw0MzJzMi41NCw4LjgyNCwyNCw5LDIzLTgsMjMtOHYtOXMtMi42NC02LjQwOS0xMS02Yy03Ljg3LS4wMTMtMjgsMC0yOCwwcy04LjE4LDEuMS04LDh2NloiIHRyYW5zZm9ybT0idHJhbnNsYXRlKC0xMjEzIC00MDYpIi8+ICAgICAgICA8Y2lyY2xlIGlkPSLmpK3lnIZfMiIgZGF0YS1uYW1lPSLmpK3lnIYgMiIgY2xhc3M9ImNscy01IiBjeD0iNTYuMyIgY3k9IjM1LjE3MiIgcj0iMTAuNDIiLz4gICAgICAgIDx0ZXh0IGlkPSJfIiBkYXRhLW5hbWU9IsKlIiBjbGFzcz0iY2xzLTYiIHRyYW5zZm9ybT0idHJhbnNsYXRlKDU2LjAzMiA0MC44MzYpIHNjYWxlKDAuNzQ0IDAuNzQzKSI+wqU8L3RleHQ+ICAgICAgPC9nPiAgICA8L2c+ICA8L2c+PC9zdmc+', br: 'data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIxMjAiIGhlaWdodD0iMTIwIiB2aWV3Qm94PSIwIDAgMTIwIDEyMCI+ICA8bWV0YWRhdGE+PD94cGFja2V0IGJlZ2luPSLvu78iIGlkPSJXNU0wTXBDZWhpSHpyZVN6TlRjemtjOWQiPz48eDp4bXBtZXRhIHhtbG5zOng9ImFkb2JlOm5zOm1ldGEvIiB4OnhtcHRrPSJBZG9iZSBYTVAgQ29yZSA1LjYtYzEzOCA3OS4xNTk4MjQsIDIwMTYvMDkvMTQtMDE6MDk6MDEgICAgICAgICI+ICAgPHJkZjpSREYgeG1sbnM6cmRmPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5LzAyLzIyLXJkZi1zeW50YXgtbnMjIj4gICAgICA8cmRmOkRlc2NyaXB0aW9uIHJkZjphYm91dD0iIi8+ICAgPC9yZGY6UkRGPjwveDp4bXBtZXRhPiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgPD94cGFja2V0IGVuZD0idyI/PjwvbWV0YWRhdGE+PGRlZnM+ICAgIDxzdHlsZT4gICAgICAuY2xzLTEgeyAgICAgICAgZmlsbDogI2Y5YjM1ODsgICAgICB9ICAgICAgLmNscy0xLCAuY2xzLTIsIC5jbHMtMyB7ICAgICAgICBzdHJva2U6ICNjZDFiMWU7ICAgICAgICBzdHJva2UtbGluZWNhcDogcm91bmQ7ICAgICAgICBzdHJva2UtbGluZWpvaW46IHJvdW5kOyAgICAgICAgc3Ryb2tlLXdpZHRoOiAzcHg7ICAgICAgICBmaWxsLXJ1bGU6IGV2ZW5vZGQ7ICAgICAgfSAgICAgIC5jbHMtMiB7ICAgICAgICBmaWxsOiAjZmZhYzQwOyAgICAgIH0gICAgICAuY2xzLTMgeyAgICAgICAgZmlsbDogI2ZlY2MyNDsgICAgICB9ICAgIDwvc3R5bGU+ICA8L2RlZnM+ICA8ZyBpZD0iQm90dG9tX3JpZ2h0Ij4gICAgPGcgaWQ9IkJvdHRvbV9yaWdodC0yIiBkYXRhLW5hbWU9IkJvdHRvbV9yaWdodCI+ICAgICAgPGcgaWQ9IuWFg+WunSI+ICAgICAgICA8cGF0aCBpZD0i5b2i54q2XzkiIGRhdGEtbmFtZT0i5b2i54q2IDkiIGNsYXNzPSJjbHMtMSIgZD0iTTE0ODQuNzksNDYwLjU2MnM5LjQ3LTE1LjEsMjEuNTUuNTIzbC0xLjU3LDcuMzMxLTE4LjkzLS41MjNaIiB0cmFuc2Zvcm09InRyYW5zbGF0ZSgtMTQzMyAtNDA2KSIvPiAgICAgICAgPHBhdGggaWQ9IuW9oueKtl84IiBkYXRhLW5hbWU9IuW9oueKtiA4IiBjbGFzcz0iY2xzLTIiIGQ9Ik0xNDgzLjIxLDQ1OS41MTVzMTAuNjgsOC41MzQsMjUuMjQsMGM0LjMtLjUsOC4yMiw2LjczNSwzLjE1LDE0LjY2MXMtMjIuODMsOS4xNjEtMjguOTIsMi42MTlDMTQ3NS40Nyw0NzAuNiwxNDc0LjU3LDQ2MC4xODIsMTQ4My4yMSw0NTkuNTE1WiIgdHJhbnNmb3JtPSJ0cmFuc2xhdGUoLTE0MzMgLTQwNikiLz4gICAgICA8L2c+ICAgICAgPGcgaWQ9IuWFg+WunS0yIiBkYXRhLW5hbWU9IuWFg+WunSI+ICAgICAgICA8cGF0aCBpZD0i5b2i54q2XzktMiIgZGF0YS1uYW1lPSLlvaLnirYgOSIgY2xhc3M9ImNscy0yIiBkPSJNMTQ0OS40Miw0NDguNDVzMTUuMTEtMjQuMDQxLDM0LjM3LjgzNGwtMi41MSwxMS42NzUtMzAuMTgtLjgzNFoiIHRyYW5zZm9ybT0idHJhbnNsYXRlKC0xNDMzIC00MDYpIi8+ICAgICAgICA8cGF0aCBpZD0i5b2i54q2XzgtMiIgZGF0YS1uYW1lPSLlvaLnirYgOCIgY2xhc3M9ImNscy0zIiBkPSJNMTQ0Ni45LDQ0Ni43ODJzMTcuMDQsMTMuNTkzLDQwLjI0LDBjNi44Ny0uNzg4LDEzLjEyLDEwLjcyOCw1LjAzLDIzLjM1MXMtMzYuNDEsMTQuNTg5LTQ2LjExLDQuMTY5QzE0MzQuNTUsNDY0LjQ0MiwxNDMzLjEyLDQ0Ny44NDYsMTQ0Ni45LDQ0Ni43ODJaIiB0cmFuc2Zvcm09InRyYW5zbGF0ZSgtMTQzMyAtNDA2KSIvPiAgICAgIDwvZz4gICAgPC9nPiAgPC9nPjwvc3ZnPg==' } } }).then(objectProps => { console.log(objectProps); let text = objectProps; }); }, objectActivated: function(obj) { activeObjectId = obj.id; if (obj.type === 'rect' || obj.type === 'circle' || obj.type === 'triangle') { showSubMenu('shape'); setShapeToolbar(obj); activateShapeMode(); } else if (obj.type === 'icon') { showSubMenu('icon'); setIconToolbar(obj); activateIconMode(); } else if (obj.type === 'text') { showSubMenu('text'); setTextToolbar(obj); activateTextMode(); } }, mousedown: function(event, originPointer) { if ($imageFilterSubMenu.is(':visible') && imageEditor.hasFilter('colorFilter')) { imageEditor.applyFilter('colorFilter', { x: parseInt(originPointer.x, 10), y: parseInt(originPointer.y, 10) }); } } }); // Attach button click event listeners $btns.on('click', function() { $btnsActivatable.removeClass('active'); }); $btnsActivatable.on('click', function() { $(this).addClass('active'); }); $btnUndo.on('click', function() { $displayingSubMenu.hide(); if (!$(this).hasClass('disabled')) { imageEditor.undo(); } }); $btnRedo.on('click', function() { $displayingSubMenu.hide(); if (!$(this).hasClass('disabled')) { imageEditor.redo(); } }); $btnClearObjects.on('click', function() { $displayingSubMenu.hide(); imageEditor.clearObjects(); }); $btnRemoveActiveObject.on('click', function() { $displayingSubMenu.hide(); imageEditor.removeObject(activeObjectId); }); $btnCrop.on('click', function() { const {height, width} = imageEditor.getCanvasSize(); const ajwh = (height > width ? width : height) / 2; // console.log(imageEditor._graphics.adjustCanvasDimension(500, 500)); imageEditor.startDrawingMode('CROPPER', { lockProportion: true, lockUniScaling: true, top: (height - ajwh) / 2, left: (width - ajwh) / 2, width: ajwh, height: ajwh, cornerStyle: 'cropper', cornerSize: 48, cornerWidth: 4, cornerColor: '#ffe626', cornerStrokeColor: '#fff', transparentCorners: false, lineWidth: 1, borderColor: '#fff' }); $displayingSubMenu.hide(); $displayingSubMenu = $cropSubMenu.show(); }); $btnFlip.on('click', function() { imageEditor.stopDrawingMode(); $displayingSubMenu.hide(); $displayingSubMenu = $flipSubMenu.show(); }); $btnRotation.on('click', function() { imageEditor.stopDrawingMode(); $displayingSubMenu.hide(); $displayingSubMenu = $rotationSubMenu.show(); }); $btnClose.on('click', function() { imageEditor.stopDrawingMode(); $displayingSubMenu.hide(); }); $btnApplyCrop.on('click', function() { imageEditor.crop(imageEditor.getCropzoneRect()).then(() => { imageEditor.stopDrawingMode(); resizeEditor(); }); }); $btnCancelCrop.on('click', function() { imageEditor.stopDrawingMode(); }); $btnFlipX.on('click', function() { imageEditor.flipX().then(status => { console.log('flipX: ', status.flipX); console.log('flipY: ', status.flipY); console.log('angle: ', status.angle); }); }); $btnFlipY.on('click', function() { imageEditor.flipY().then(status => { console.log('flipX: ', status.flipX); console.log('flipY: ', status.flipY); console.log('angle: ', status.angle); }); }); $btnResetFlip.on('click', function() { imageEditor.resetFlip().then(status => { console.log('flipX: ', status.flipX); console.log('flipY: ', status.flipY); console.log('angle: ', status.angle); }); }); $btnRotateClockwise.on('click', function() { imageEditor.rotate(30); }); $btnRotateCounterClockWise.on('click', function() { imageEditor.rotate(-30); }); $inputRotationRange.on('mousedown', function() { var changeAngle = function() { imageEditor.setAngle(parseInt($inputRotationRange.val(), 10)).catch(() => {}); }; $(document).on('mousemove', changeAngle); $(document).on('mouseup', function stopChangingAngle() { $(document).off('mousemove', changeAngle); $(document).off('mouseup', stopChangingAngle); }); }); $inputRotationRange.on('change', function() { imageEditor.setAngle(parseInt($inputRotationRange.val(), 10)).catch(() => {}); }); $inputBrushWidthRange.on('change', function() { imageEditor.setBrush({width: parseInt(this.value, 10)}); }); $inputImage.on('change', function(event) { var file; if (!supportingFileAPI) { alert('This browser does not support file-api'); } file = event.target.files[0]; imageEditor.loadImageFromFile(file).then(result => { console.log(result); imageEditor.clearUndoStack(); }); }); $btnDownload.on('click', function() { var imageName = imageEditor.getImageName(); var dataURL = imageEditor.toDataURL(); var blob, type, w; if (supportingFileAPI) { blob = base64ToBlob(dataURL); type = blob.type.split('/')[1]; if (imageName.split('.').pop() !== type) { imageName += '.' + type; } // Library: FileSaver - saveAs saveAs(blob, imageName); // eslint-disable-line } else { alert('This browser needs a file-server'); w = window.open(); w.document.body.innerHTML = '<img src=' + dataURL + '>'; } }); // control draw line mode $btnDrawLine.on('click', function() { imageEditor.stopDrawingMode(); $displayingSubMenu.hide(); $displayingSubMenu = $drawLineSubMenu.show(); $selectLine.eq(0).change(); }); $selectLine.on('change', function() { var mode = $(this).val(); var settings = getBrushSettings(); imageEditor.stopDrawingMode(); if (mode === 'freeDrawing') { imageEditor.startDrawingMode('FREE_DRAWING', settings); } else if(mode === 'mosaicDrawing') { settings.mosaic = true; settings.blocksize = 10; settings.isNew = true; imageEditor.startDrawingMode('FREE_DRAWING', settings); } else { imageEditor.startDrawingMode('LINE_DRAWING', settings); } }); brushColorpicker.on('selectColor', function(event) { imageEditor.setBrush({ color: hexToRGBa(event.color, 0.5) }); }); // control draw shape mode $btnDrawShape.on('click', function() { showSubMenu('shape'); // step 1. get options to draw shape from toolbar shapeType = $('[name="select-shape-type"]:checked').val(); shapeOptions.stroke = '#000000'; shapeOptions.fill = '#ffffff'; shapeOptions.strokeWidth = Number($inputStrokeWidthRange.val()); // step 2. set options to draw shape imageEditor.setDrawingShape(shapeType, shapeOptions); // step 3. start drawing shape mode activateShapeMode(); }); $selectShapeType.on('change', function() { shapeType = $(this).val(); imageEditor.setDrawingShape(shapeType); }); $inputCheckTransparent.on('change', function() { var colorType = $selectColorType.val(); var isTransparent = $(this).prop('checked'); var color; if (!isTransparent) { color = shapeColorpicker.getColor(); } else { color = 'transparent'; } if (colorType === 'stroke') { imageEditor.changeShape(activeObjectId, { stroke: color }); } else if (colorType === 'fill') { imageEditor.changeShape(activeObjectId, { fill: color }); } imageEditor.setDrawingShape(shapeType, shapeOptions); }); shapeColorpicker.on('selectColor', function(event) { var colorType = $selectColorType.val(); var isTransparent = $inputCheckTransparent.prop('checked'); var color = event.color; if (isTransparent) { return; } if (colorType === 'stroke') { imageEditor.changeShape(activeObjectId, { stroke: color }); } else if (colorType === 'fill') { imageEditor.changeShape(activeObjectId, { fill: color }); } imageEditor.setDrawingShape(shapeType, shapeOptions); }); $inputStrokeWidthRange.on('change', function() { var strokeWidth = Number($(this).val()); imageEditor.changeShape(activeObjectId, { strokeWidth: strokeWidth }); imageEditor.setDrawingShape(shapeType, shapeOptions); }); // control text mode $btnText.on('click', function() { showSubMenu('text'); activateTextMode(); }); $inputFontSizeRange.on('change', function() { imageEditor.changeTextStyle(activeObjectId, { fontSize: parseInt(this.value, 10) }); }); $btnTextStyle.on('click', function(e) { // eslint-disable-line var styleType = $(this).attr('data-style-type'); var styleObj; e.stopPropagation(); switch (styleType) { case 'b': styleObj = {fontWeight: 'bold'}; break; case 'i': styleObj = {fontStyle: 'italic'}; break; case 'u': styleObj = {textDecoration: 'underline'}; break; case 'l': styleObj = {textAlign: 'left'}; break; case 'c': styleObj = {textAlign: 'center'}; break; case 'r': styleObj = {textAlign: 'right'}; break; default: styleObj = {}; } imageEditor.changeTextStyle(activeObjectId, styleObj); }); textColorpicker.on('selectColor', function(event) { imageEditor.changeTextStyle(activeObjectId, { 'fill': event.color }); }); // control icon $btnAddIcon.on('click', function() { showSubMenu('icon'); activateIconMode(); }); function onClickIconSubMenu(event) { var element = event.target || event.srcElement; var iconType = $(element).attr('data-icon-type'); imageEditor.once('mousedown', function(e, originPointer) { imageEditor.addIcon(iconType, { left: originPointer.x, top: originPointer.y }).then(objectProps => { // console.log(objectProps); }); }); } $btnRegisterIcon.on('click', function() { $iconSubMenu.find('.menu-item').eq(3).after( '<li id="customArrow" class="menu-item icon-text" data-icon-type="customArrow">↑</li>' ); imageEditor.registerIcons({ customArrow: 'M 60 0 L 120 60 H 90 L 75 45 V 180 H 45 V 45 L 30 60 H 0 Z' }); $btnRegisterIcon.off('click'); $iconSubMenu.on('click', '#customArrow', onClickIconSubMenu); }); $iconSubMenu.on('click', '.icon-text', onClickIconSubMenu); iconColorpicker.on('selectColor', function(event) { imageEditor.changeIconColor(activeObjectId, event.color); }); // control mask filter $btnMaskFilter.on('click', function() { imageEditor.stopDrawingMode(); $displayingSubMenu.hide(); $displayingSubMenu = $filterSubMenu.show(); }); $btnImageFilter.on('click', function() { var filters = { 'grayscale': $inputCheckGrayscale, 'invert': $inputCheckInvert, 'sepia': $inputCheckSepia, 'sepia2': $inputCheckSepia2, 'blur': $inputCheckBlur, 'oldMaker': $inputCheckOld, 'shapren': $inputCheckSharpen, 'emboss': $inputCheckEmboss, 'removeWhite': $inputCheckRemoveWhite, 'brightness': $inputCheckBrightness, 'noise': $inputCheckNoise, 'gradientTransparency': $inputCheckGradientTransparency, 'pixelate': $inputCheckPixelate, 'tint': $inputCheckTint, 'multiply': $inputCheckMultiply, 'blend': $inputCheckBlend, 'colorFilter': $inputCheckColorFilter }; tui.util.forEach(filters, function($value, key) { $value.prop('checked', imageEditor.hasFilter(key)); }); $displayingSubMenu.hide(); $displayingSubMenu = $imageFilterSubMenu.show(); }); $btnLoadMaskImage.on('change', function() { var file; var imgUrl; if (!supportingFileAPI) { alert('This browser does not support file-api'); } file = event.target.files[0]; if (file) { imgUrl = URL.createObjectURL(file); imageEditor.loadImageFromURL(imageEditor.toDataURL(), 'FilterImage').then(() => { imageEditor.addImageObject(imgUrl).then(objectProps => { URL.revokeObjectURL(file); console.log(objectProps); }); }); } }); $btnApplyMask.on('click', function() { imageEditor.applyFilter('mask', { maskObjId: activeObjectId }).then(result => { console.log(result); }); }); $inputCheckGrayscale.on('change', function() { applyOrRemoveFilter(this.checked, 'Grayscale', null); }); $inputCheckInvert.on('change', function() { applyOrRemoveFilter(this.checked, 'Invert', null); }); $inputCheckSepia.on('change', function() { applyOrRemoveFilter(this.checked, 'Sepia', null); }); $inputCheckSepia2.on('change', function() { applyOrRemoveFilter(this.checked, 'Sepia2', null); }); $inputCheckBlur.on('change', function() { applyOrRemoveFilter(this.checked, 'Blur', null); }); $inputCheckOld.on('change', function() { applyOrRemoveFilter(this.checked, 'oldMaker', { percent: parseInt($inputRangeOldPercent.val(), 10) }); }); $inputCheckSharpen.on('change', function() { applyOrRemoveFilter(this.checked, 'Sharpen', null); }); $inputCheckEmboss.on('change', function() { applyOrRemoveFilter(this.checked, 'Emboss', null); }); $inputCheckRemoveWhite.on('change', function() { applyOrRemoveFilter(this.checked, 'removeWhite', { threshold: parseInt($inputRangeRemoveWhiteThreshold.val(), 10), distance: parseInt($inputRangeRemoveWhiteDistance.val(), 10) }); }); $inputRangeRemoveWhiteThreshold.on('change', function() { applyOrRemoveFilter($inputCheckRemoveWhite.is(':checked'), 'removeWhite', { threshold: parseInt(this.value, 10) }); }); $inputRangeOldPercent.on('change', function() { applyOrRemoveFilter($inputCheckOld.is(':checked'), 'oldMaker', { percent: parseInt(this.value, 10) }); }); $inputRangeRemoveWhiteDistance.on('change', function() { applyOrRemoveFilter($inputCheckRemoveWhite.is(':checked'), 'removeWhite', { distance: parseInt(this.value, 10) }); }); $inputCheckBrightness.on('change', function() { applyOrRemoveFilter(this.checked, 'brightness', { brightness: parseInt($inputRangeBrightnessValue.val(), 10) }); }); $inputRangeBrightnessValue.on('change', function() { applyOrRemoveFilter($inputCheckBrightness.is(':checked'), 'brightness', { brightness: parseInt(this.value, 10) }); }); $inputCheckNoise.on('change', function() { applyOrRemoveFilter(this.checked, 'noise', { noise: parseInt($inputRangeNoiseValue.val(), 10) }); }); $inputRangeNoiseValue.on('change', function() { applyOrRemoveFilter($inputCheckNoise.is(':checked'), 'noise', { noise: parseInt(this.value, 10) }); }); $inputCheckGradientTransparency.on('change', function() { applyOrRemoveFilter(this.checked, 'gradientTransparency', { threshold: parseInt($inputRangeGradientTransparencyValue.val(), 10) }); }); $inputRangeGradientTransparencyValue.on('change', function() { applyOrRemoveFilter($inputCheckGradientTransparency.is(':checked'), 'gradientTransparency', { threshold: parseInt(this.value, 10) }); }); $inputCheckPixelate.on('change', function() { applyOrRemoveFilter(this.checked, 'pixelate', { blocksize: parseInt($inputRangePixelateValue.val(), 10) }); }); $inputRangePixelateValue.on('change', function() { applyOrRemoveFilter($inputCheckPixelate.is(':checked'), 'pixelate', { blocksize: parseInt(this.value, 10) }); }); $inputCheckTint.on('change', function() { applyOrRemoveFilter(this.checked, 'tint', { color: tintColorpicker.getColor(), opacity: parseFloat($inputRangeTintOpacityValue.val()) }); }); tintColorpicker.on('selectColor', function(e) { applyOrRemoveFilter($inputCheckTint.is(':checked'), 'tint', { color: e.color }); }); $inputRangeTintOpacityValue.on('change', function() { applyOrRemoveFilter($inputCheckTint.is(':checked'), 'tint', { opacity: parseFloat($inputRangeTintOpacityValue.val()) }); }); $inputCheckMultiply.on('change', function() { applyOrRemoveFilter(this.checked, 'multiply', { color: multiplyColorpicker.getColor() }); }); multiplyColorpicker.on('selectColor', function(e) { applyOrRemoveFilter($inputCheckMultiply.is(':checked'), 'multiply', { color: e.color }); }); $inputCheckBlend.on('change', function() { applyOrRemoveFilter(this.checked, 'blend', { color: blendColorpicker.getColor(), mode: $selectBlendType.val() }); }); blendColorpicker.on('selectColor', function(e) { applyOrRemoveFilter($inputCheckBlend.is(':checked'), 'blend', { color: e.color }); }); $selectBlendType.on('change', function() { applyOrRemoveFilter($inputCheckBlend.is(':checked'), 'blend', { mode: this.value }); }); $inputCheckColorFilter.on('change', function() { applyOrRemoveFilter(this.checked, 'colorFilter', { color: '#FFFFFF', threshold: $inputRangeColorFilterValue.val() }); }); $inputRangeColorFilterVal