{"version":3,"sources":["webpack:///webpack/bootstrap","webpack:///./cartridges/app_intimissimi/cartridge/client/default/js/components/modal.js","webpack:///./node_modules/tingle.js/dist/tingle.min.js","webpack:///./cartridges/app_intimissimi/cartridge/client/default/js/util/form.js","webpack:///./cartridges/app_intimissimi/cartridge/client/default/js/util/common.js","webpack:///./cartridges/app_intimissimi/cartridge/client/default/js/product/sizePanel.js","webpack:///./cartridges/app_intimissimi/cartridge/client/default/js/analytics/helpers/helper.js","webpack:///./cartridges/app_intimissimi/cartridge/client/default/js/product/base.js","webpack:///./cartridges/app_intimissimi/cartridge/client/default/js/product/wishlistHeart.js","webpack:///./node_modules/fabric/dist/fabric.js","webpack:///./cartridges/app_intimissimi/cartridge/client/default/js/productTileComponent/productTile.js","webpack:///./cartridges/app_intimissimi/cartridge/client/default/js/components/productSlider.js","webpack:///(webpack)/buildin/global.js","webpack:///./cartridges/app_intimissimi/cartridge/client/default/js/productTileComponent/productTileCarousel.js","webpack:///./cartridges/app_intimissimi/cartridge/client/default/js/product/quickView.js","webpack:///./cartridges/app_intimissimi/cartridge/client/default/js/product/notify.js","webpack:///./cartridges/app_intimissimi/cartridge/client/default/js/product/productBox.js","webpack:///./cartridges/app_intimissimi/cartridge/client/default/js/customCarousel.js","webpack:///./cartridges/app_intimissimi/cartridge/client/default/js/customize.js","webpack:///(webpack)/node_modules/buffer/index.js","webpack:///./node_modules/base64-js/index.js","webpack:///./node_modules/ieee754/index.js","webpack:///./node_modules/isarray/index.js","webpack:///./cartridges/app_intimissimi/cartridge/client/default/js/personalization/generateSvgForOTP.js","webpack:///./cartridges/app_intimissimi/cartridge/client/default/js/personalization/selectors.js","webpack:///./cartridges/app_intimissimi/cartridge/client/default/js/personalization/classes.js","webpack:///./cartridges/app_intimissimi/cartridge/client/default/js/product/detail.js","webpack:///./assets/scripts/util/common.js","webpack:///./cartridges/app_intimissimi/cartridge/client/default/js/product/smartGiftHelper.js","webpack:///./assets/scripts/util/url.js","webpack:///./cartridges/app_intimissimi/cartridge/client/default/js/util/render.js","webpack:///./cartridges/app_intimissimi/cartridge/client/default/js/checkout/giftcard.js","webpack:///./cartridges/app_intimissimi/cartridge/client/default/js/giftCardDetails.js","webpack:///./cartridges/app_intimissimi/cartridge/client/default/js/giftcard/giftcardAddToCart.js","webpack:///./cartridges/app_intimissimi/cartridge/client/default/js/giftcard/giftcardBalance.js"],"names":["installedModules","__webpack_require__","moduleId","exports","module","i","l","modules","call","m","c","d","name","getter","o","Object","defineProperty","enumerable","get","r","Symbol","toStringTag","value","t","mode","__esModule","ns","create","key","bind","n","object","property","prototype","hasOwnProperty","p","s","footer","cssClass","modalOptions","closeMethods","onClose","modal","destroy","onOpen","$","addClass","beforeClose","length","removeClass","tingle","selectorID","contentModal","document","getElementById","setContent","innerHTML","html","ModalShowHide","selector","newModalType","toPropagateClick","classToPreventHide","this","$el","_scrollposition","isOpenTypeCustom","isOpen","events","_scrollPosition","window","pageYOffset","parent","scrollTo","on","e","target","hasClass","closest","data","hide","stopPropagation","define","beforeOpen","stickyFooter","closeLabel","opts","init","modalBoxFooter","style","width","modalBox","clientWidth","left","offsetLeft","createElement","classList","add","indexOf","display","forEach","modalCloseBtn","modalCloseBtnIcon","modalCloseBtnLabel","appendChild","modalBoxContent","_events","clickCloseBtn","close","clickOverlay","resize","checkOverflow","keyboardNav","addEventListener","which","clientX","parentElement","contains","a","removeEventListener","arguments","h","transition","OTransition","MozTransition","WebkitTransition","body","insertBefore","firstChild","addFooter","parentNode","removeChild","open","removeProperty","removeAttribute","top","setStickyFooter","remove","getContent","setFooterContent","getFooterContent","isOverflow","clientHeight","addFooterBtn","split","console","warn","innerHeight","addInputClearIcon","inputItem","$inputFieldContainer","clearIconTopPos","outerHeight","find","append","css","formElement","payload","form","empty","Foundation","MediaQuery","atLeast","selects","chosen","disable_search","each","ariaLabel","attr","next","fields","keys","feedbackElement","children","Array","isArray","join","siblings","show","error","index","currentTarget","val","firstNameIdList","lastNameIdList","firstNameId","lastNameId","parents","after","swapFirstLastName","parentSelector","fieldErrors","trigger","cardFieldSelector","cardTypeSelector","cleave","Cleave","creditCard","onCreditCardTypeChanged","type","creditCardTypes","amex","cardType","visa","mastercard","discover","jcb","diners","unknown","wasAmexSelected","serializedArray","serializeArray","item","getRawValue","param","task","requestAnimationFrame","preventDefault","off","url","method","hideSpinner","spinner","start","Promise","resolve","reject","ajax","success","response","stop","include","map","el","htmlMap","querySelector","params","newUrl","encodeURIComponent","cookie","filter","trim","expires","days","date","Date","setTime","getTime","toGMTString","parts","pop","shift","navigator","maxTouchPoints","msMaxTouchPoints","idName","openSizePanel","_self","infoURL","dataType","product","readyToOrder","sizeDisplayValue","text","pid","id","ADDTOCART","ADDTOCART_BUNDLE","PERSONALIZE","WISHILIST","SMARTGIFT","operation","Types","$sizeElements","bundleQuantity","element","parseInt","stopSpinner","selectedSize","removeAttr","testEnabled","productGenderMap","1","2","3","4","5","6","brandsMapping","ListType","getSkuCodes","sku","substring","color","size","replace","formatStringForAnalytics","str","toLowerCase","formatStringProductPropertyIfExists","avoidFormatting","getFormatSkuForAnalytics","formatFloatProductPropertyIfExists","parseFloat","formatIntegerProductPropertyIfExists","stringOrNotAvailable","String","numberOrZero","getStringAnalyticsValueFromStorage","sessionStorage","getItem","formattedSku","match","toUpperCase","skuComponents","isTestEnabled","getAvailableListTypes","listingItemsBaseClass","types","push","getSkuComponents","getProductGender","sapCategoryCode","categoryCode","getProductBaseInfo","colorObject","promo","promotions","enabled","appliedPromotions","productType","components","k","variationAttributes","variationAttribute","attributeId","j","values","selected","selectedVariation","formatProductForAnalytics","formatStringProductSalePropertyIfExists","checkPage","location","href","formatString","format4DigitNumber","number","toString","insertParameter","encodeURI","x","kvp","search","substr","insertParam","existsParameter","hasParam","pushObject","dataLayer","log","getFormatSku","formatNameForAnalytics","formatSkus","skus","formattedSkus","getProductNameEngFromPdp","getFormatedNewsletterPreferenceBrands","list","brandsStr","brand","getListId","container","provider","getProductList","items","obj","eq","item_list_name","item_list_id","quantity","getGrandTotal","getAppliedCoupon","coupon","getUpsellingMessage","upsellingMessage","vals","localStorage","setItem","getBeginCheckoutData","context","upselling_message","currency","helperData","getTypeOfAccount","typeOfAccount","storeGtmData","item_id","item_variant","JSON","stringify","getGtmData","GTMData","GTMItem","parse","setBonusProductData","$container","isMiniCartOpen","getPidValue","attributeSelectQuickAdd","selectedValueUrl","$productContainer","imagesShouldUpdate","handleVariantResponseQuickAdd","updateOptions","options","updateQuantities","quantities","selectedQuantity","activatePromoAnimationMessage","reactivatePromoAnimationMessage","promotionId","pdpCalloutMsgText","attributeSelect","ignoreCTA","prevObject","analyticsPromotion","isSize","variation","handleVariantResponse","handleVariationUrlsSelectSizeModal","variationUrls","handlePromotionTag","handleVariationUrlsSelectNotifyModal","handleVariationComingSoonNotifyModal","handleVariationComingSoon","comingSoon","handleVariationWishlistModal","updateImageSaveForLater","getPID","promoContainer","promoMessage","promoLoyaltyMessage","selectorPrefix","onSaleSelected","price","saleType","discountValue","calloutMsg","totalQuantityPrice","handleInexistentSizeQuickView","handleWishlistContainer","err","responseJSON","redirectUrl","current_url","pathname","localized_error_page","protocol","host","then","sizePanel","afterSizeSelection","getQuantitySelector","getQuantitySelected","updateAttrs","attrs","variantType","attrsWithSwatches","attrValue","$attrValue","$swatchAnchor","displayValue","displayName","images","swatch","outerHTML","selectable","isSoldout","processSwatchValues","$attr","resetUrl","$attrValueMobile","variationUrl","isComingSoon","selectedSizeSpan","prop","lowAvailability","toggleClass","disabled","$sizeSelectorContainer","processNonSwatchValues","updateScanTrustLink","$productAuthenticity","scanTrustUrlWithParams","updateAvailability","availabilityValue","availabilityMessages","availability","messages","orderable","message","resources","info_selectforstock","available","isSizeInexistent","option","$optionEl","valueEl","updateColorFamily","colorFamily","updatePrices","priceSelector","priceInfoSelector","$oldPriceInfoSelector","$regularPriceInfoDiscountSelector","$oldPriceInfoDiscountSelector","$pricePercentage","$priceSelector","$priceInfoSelector","$priceInfoInSaleContainerSelector","$priceInfoInSaleContainerSelector2","$omnibusPricelForSpecificCountries","onSalesInfoPrice","replaceWith","currentCountryOmnibus","isRegularOmnibusCountry","sales","formattedPriceInfo","tooltip_omnibus","oldPriceOmnibus","priceInfoDiscountValue","formatted","doubleCurrency","$doubleCurrencyContainer","innerContent","New","isGreen","small","title","partTypes","comp","percentage","material","endTag","mainComposition","primaryImageUrls","slick","selectedProductUrl","large","imageUrl","idx","$carouselInner","$imgContainer","slidesToShow","slidesToScroll","dots","arrows","infinite","responsive","breakpoint","settings","resizedUrls","sizes","scaleWidth","$imgContainerDesktop","$imgZoomModal","$imgZoomModalMobile","newCarouselSlideHtml","replaceAll","$galleryItemContainer","$zoomTemplate","videoUrl","videoURL","tmpl","clone","setAttribute","$secondItem","insertAfter","videoBlock","load","autoplay","videoListener","updatePrimaryImagesSlider","careAndMaintenance","countryEnabled","PersonalizationEnabledCountries","isPersonalizedVal","positions","showButton","updateModelSize","modelSize","promotionClass","cleanId","allocation","comingSoons","customizations","personalizationImgTop","personalizationImgDown","link","linkPlp","optionsHtml","getAddToCartUrl","$html","parseHTML","$results","undefined","handlePostCartAdd","cookies","cookieSizebaySessionId","startsWith","urlSessionId","getAttribute","fetch","ok","Error","json","createCookie","callSizebayAPI","brandURL","currentCountry","includes","permaURL","urlSizebay","URL","searchParams","has","set","device","referrerURL","referrerPolicy","headers","accept","tenant_id","referer","hostname","updateQuantityPicker","source","calculateWatchedTime","video","currentTime","duration","triggerVideoInteractionEvent","action","fullPageLoad","$videoBlockContainer","$videoPlayMiniatureIcon","percentageWatched","firstPlayback","watchedFullVideo","videoStartInSeconds","videoEndInSeconds","myVideo","onended","onplaying","onpause","loop","pause","paused","play","reorderSwatches","$swatchContainer","$soldoutColorsContainers","$lastNonSoldoutColorContainer","not","last","freeGiftDetailsModal","bonusProductModal","methods","colorAttribute","colorAttributeQuickAddListing","sizeAttribute","sizeAttributeQuickAddListing","sizeAttributeQuickAddPDP","sizeAttributeSet","addToCart","careAndMaintenanceClick","personalizationButton","sizeTU","quickAddListener","NotifyHelper","notifyMeModal","checkSoldoutAvailability","SmartGiftHelper","run","registerAttributionTokenSending","loadGoogleRecommendations","createNextPageToken","isSizeSelected","newModalFromString","runPersonalizationListener","description","firstPart","firstPartSplit","firstPartSKU","productId","first","colorValue","selectedColor","updateProductDetailUrl","$productTile","startCarouselTileImageFunction","selectedValue","isPdp","isPeronalizePage","sizeData","skuData","decodeURI","splitSkuData","originalEvent","code","$sizeSelected","addToCartFromListing","$button","$target","$input","newValue","addToCartUrl","pidsObj","setPids","_openStickySizeSelectorModal","isPersonalizedProduct","personalizationTextFont","personalizationText","personalizationTextColor","personalizationColorPref","PersonalizationColor","personalizationColor","personalizationColorJson","alt","src","lastIndexOf","personalizationPositionKey","customizationClassPref","CustomizationClass","customizationClass","customizationClassJson","category","personalizationTextSVG","personalizationFullSVG","personalizationSmallSVG","uniqueIdentifiers","random","Math","personalizedObj","isDate","isLove","GTMItemListName","GTMItemListId","GTMIndex","uniqueIdentifier","toggle","is","animate","scrollTop","offset","qty","pidSet","uid","buttonAdd","promoId","childProducts","uuid","completePromoItems","completePromoItemsLabel","quantityTotal","cart","numItems","cartModel","click","mustAdd","showQuickAddItems","sizeChecked","quantitySelected","attributesUpdateUrl","attributionToken","$googleConfig","servingConfig","nodeToAppendTo","cgid","route","appendTo","$googleAttributionToken","previousPageToken","searchTerm","displayMessageAndChangeIcon","icon","isAddAction","wishlistTotal","sender","updateAriaLabelForWishlistLink","blur","offsetTop","closeNotification","setTimeout","showWishlistNotification","renderedTemplate","newItems","oldItems","oldIdx","splice","updateWishlistInternalState","addDefinitelyToWishlist","productID","btn","addURL","removeURL","optionId","optionVal","shouldAdd","isAdding","added","labelAddWishlist","labelRemoveWishlist","checkItemInWishlist","itemCode","highlightIconsForAllItemsInWishlist","itemsInWishlist","plpWishlist","productDetailWishlist","moveToWishlistHelper","$btn","moveToWishlistHelperSaveForLater","addToWishlist","sizeModal","newModalFromSelector","$clickedButton","sizeValue","$inputToClick","_","global","sqrt","atan2","pow","PiBy180","PiBy2","couldUseAttachEvent","parseEl","supportsOpacity","supportsFilters","reOpacity","setOpacity","proto","toFixed","min","max","degreesToRadians","originXOffset","originYOffset","fabric","version","HTMLDocument","Document","implementation","createHTMLDocument","virtualWindow","require","JSDOM","decodeURIComponent","features","FetchExternalResources","jsdomImplForWrapper","implForWrapper","nodeCanvas","Canvas","DOMParser","copyGLTo2DDrawImage","gl","pipelineState","glCanvas","canvas","targetCanvas","ctx","getContext","translate","height","scale","sourceY","drawImage","copyGLTo2DPutImageData","dWidth","destinationWidth","dHeight","destinationHeight","numBytes","u8","Uint8Array","imageBuffer","u8Clamped","Uint8ClampedArray","readPixels","RGBA","UNSIGNED_BYTE","imgData","ImageData","putImageData","isTouchSupported","isLikelyNode","Buffer","SHARED_ATTRIBUTES","DPI","reNum","rePathCommand","reNonWord","fontPaths","iMatrix","svgNS","perfLimitSizeTotal","maxCacheSideLimit","minCacheSideLimit","charWidthsCache","textureSize","disableStyleCopyPaste","enableGLFiltering","devicePixelRatio","webkitDevicePixelRatio","mozDevicePixelRatio","browserShadowBlurConstant","arcToSegmentsCache","boundsOfCurveCache","cachesBoundsOfCurve","forceGLPutImageData","initFilterBackend","isWebglSupported","maxTextureSize","WebglFilterBackend","tileSize","Canvas2dFilterBackend","_removeEventListener","eventName","handler","__eventListeners","eventListener","util","array","fill","observe","stopObserving","fire","listenersForEvent","len","Observable","Collection","_objects","apply","_onObjectAdded","renderOnAddRemove","requestRenderAll","insertAt","nonSplicing","objects","somethingRemoved","_onObjectRemoved","forEachObject","callback","getObjects","concat","isEmpty","complexity","reduce","memo","current","CommonMethods","_setOptions","_initGradient","filler","colorStops","Gradient","_initPattern","Pattern","_initClipping","clipTo","functionBody","getFunctionBody","Function","_setObject","_set","PI","cos","angle","sin","sign","removeFromArray","getRandomInt","floor","degrees","radiansToDegrees","radians","rotatePoint","point","origin","subtractEquals","v","rotateVector","Point","y","addEquals","vector","transformPoint","ignoreOffset","makeBoundingBoxFromPoints","points","transform","xPoints","minX","yPoints","minY","invertTransform","fractionDigits","Number","parseUnit","fontSize","unit","exec","Text","DEFAULT_SVG_FONT_SIZE","falseFunction","getKlass","namespace","string","camelize","charAt","slice","resolveNamespace","getSvgAttributes","attributes","loadImage","crossOrigin","img","createImage","onLoadCallback","onload","onerror","loadImageInDom","div","position","enlivenObjects","reviver","enlivenedObjects","numLoadedObjects","numTotalObjects","onLoaded","fromObject","enlivenPatterns","patterns","numLoadedPatterns","numPatterns","enlivenedPatterns","pattern","groupSVGElements","elements","path","centerPoint","Group","sourcePath","populateWithProperties","destination","properties","drawDashedLine","x2","y2","da","dx","dy","rot","dc","di","draw","save","moveTo","rotate","restore","createCanvasElement","copyCanvasElement","newCanvas","toDataURL","canvasEl","format","quality","clipContext","receiver","beginPath","clip","multiplyTransformMatrices","b","is2x2","qrDecompose","denom","scaleX","scaleY","skewX","skewY","translateX","translateY","calcRotateMatrix","theta","calcDimensionsMatrix","scaleMatrix","flipX","flipY","multiply","tan","composeMatrix","matrix","customTransformMatrix","resetObjectTransform","saveObjectTransform","fn","isTransparent","tolerance","_isTransparent","imageData","getImageData","parsePreserveAspectRatioAttribute","attribute","align","meetOrSlice","aspectRatioAttrs","alignX","alignY","clearFabricFontCache","fontFamily","limitDimsByArea","ar","maximumArea","roughWidth","perfLimitSizeY","capValue","findScaleToFit","findScaleToCover","matrixToSVG","NUM_FRACTION_DIGITS","_join","arcToSegments","toX","toY","rx","ry","sweep","rotateX","argsString","th","sinTh","cosTh","fromX","fromY","px","py","rx2","abs","ry2","py2","px2","pl","root","cx","cy","cx1","cy1","mTheta","calcVectorAngle","dtheta","segments","ceil","result","mDelta","mT","th3","segmentToBezier","th2","costh2","sinth2","costh3","sinth3","ux","uy","vx","vy","ta","tb","getBoundsOfCurve","x0","y0","x1","y1","x3","y3","t1","t2","b2ac","sqrtb2ac","tvalues","bounds","mt","jlen","drawArc","fx","fy","coords","segs","segsNorm","bezierCurveTo","getBoundsOfArc","tx","ty","bound","byProperty","condition","invoke","args","value1","value2","extend","deep","Element","getWholeChar","charCodeAt","isNaN","prev","character","capitalize","firstLetterOnly","escapeXml","graphemeSplit","textstring","chr","graphemes","emptyFunction","IS_DONTENUM_BUGGY","addMethods","klass","superclass","constructor","returnValue","valueOf","Subclass","callSuper","methodName","parentMethod","_this","superClassMethod","createClass","initialize","subclasses","attachEvent","addListener","removeListener","getPointer","event","scroll","getScrollLeftTop","_evt","touchProp","changedTouches","getTouchInfo","clientY","opacity","es","currentStyle","hasLayout","zoom","test","setStyle","styles","elementStyle","cssText","styleFloat","_slice","sliceCanConvertNodelists","getElementStyle","selectProp","toArray","arrayLike","childNodes","makeElement","tagName","className","htmlFor","docElement","documentElement","scrollLeft","nodeType","arr","defaultView","getComputedStyle","makeElementUnselectable","onselectstart","unselectable","makeElementSelectable","getScript","headEl","getElementsByTagName","scriptEl","loading","onreadystatechange","readyState","getById","wrapElement","wrapper","replaceChild","getElementOffset","docElem","scrollLeftTop","doc","ownerDocument","box","offsetAttributes","borderLeftWidth","borderTopWidth","paddingLeft","paddingTop","getBoundingClientRect","clientLeft","clientTop","getNodeCanvas","impl","_canvas","_image","cleanUpJsdomNode","_currentSrc","_attributes","_classList","emptyFn","request","onComplete","xhr","XMLHttpRequest","parameters","addParamToUrl","setRequestHeader","send","noop","defaultEasing","_requestAnimFrame","webkitRequestAnimationFrame","mozRequestAnimationFrame","oRequestAnimationFrame","msRequestAnimationFrame","_cancelAnimFrame","cancelAnimationFrame","clearTimeout","requestAnimFrame","timestamp","time","finish","onChange","abort","easing","startValue","endValue","byValue","onStart","tick","ticktime","timePerc","valuePerc","cancelAnimFrame","animateColor","fromColor","toColor","startColor","Color","getSource","endColor","begin","end","pos","posValue","colorEasing","normalize","asin","elastic","easeInBounce","easeOutBounce","ease","easeInQuad","easeOutQuad","easeInOutQuad","easeInCubic","easeOutCubic","easeInOutCubic","easeInQuart","easeOutQuart","easeInOutQuart","easeInQuint","easeOutQuint","easeInOutQuint","easeInSine","easeOutSine","easeInOutSine","easeInExpo","easeOutExpo","easeInOutExpo","easeInCirc","easeOutCirc","easeInOutCirc","easeInElastic","easeOutElastic","easeInOutElastic","easeInBack","easeOutBack","easeInOutBack","easeInOutBounce","attributesMap","visibility","colorAttributes","stroke","fSize","cPath","normalizeAttr","normalizeValue","parentAttributes","parsed","transformMatrix","parseTransformAttribute","visible","fillIndex","strokeIndex","getSvgRegex","RegExp","_getMultipleNodes","nodeNames","nodeName","nodeList","nodeArray","elementMatchesRule","selectors","firstMatching","parentMatching","selectorMatches","doesSomeParentMatch","matcher","classNames","elementById","node","nodelist","svgValidTagNamesRegEx","svgViewBoxElementsRegEx","svgInvalidAncestorsRegEx","svgValidParentsRegEx","cssRules","gradientDefs","clipPaths","skewMatrix","commaWsp","reTransformList","reTransform","attributeValue","matrices","translateMatrix","rotateMatrix","multiplierX","multiplierY","combinedMatrix","reViewBoxAttrValue","applyViewboxTransform","viewBoxWidth","viewBoxHeight","viewBoxAttr","widthAttr","heightAttr","preserveAspectRatio","missingViewBox","missingDimAttr","toBeParsed","parsedDim","widthDiff","heightDiff","viewboxTransform","createElementNS","recursivelyParseGradientsXlink","gradient","xlinkAttr","referencedGradient","hasAttribute","referenceClone","cloneNode","parseSVGDocument","parsingOptions","xlink","el2","currentTrans","oldLength","el3","setAttributeNS","nodeValue","parseUseDirectives","svgUid","__uid","descendants","selectNodes","hasAncestorWithNodeName","getGradientDefs","getCSSRules","parseElements","instances","reFontDeclaration","parseFontDeclaration","oStyle","fontStyle","fontWeight","lineHeight","elList","parseAttributes","parentFontSize","ownAttributes","cssAttrs","rule","getGlobalStylesForElement","parseStyleAttribute","normalizedAttr","normalizedValue","normalizedStyle","font","mergedAttrs","setAlpha","getAlpha","toRgba","_setStrokeFillOpacity","ElementsParser","chunk","pair","parseStyleString","parseStyleObject","parsePointsAttribute","parsedPoints","allRules","styleContents","textContent","ruleObj","propertyValuePairs","_rule","loadSVGFromURL","xml","responseXML","ActiveXObject","responseText","async","loadXML","results","_options","allElements","loadSVGFromString","parser","parseFromString","regexUrl","numElements","createObjects","createObject","findTag","fromElement","createCallback","checkIfDone","resolveGradient","Image","_originalElement","_removeTransformMatrix","resolveClipPath","extractPropertyDefinition","storage","regex","lastIndex","gradientDef","opacityAttr","createClipPathCallback","_newObj","fillRule","clipRule","usingElement","objTransformInv","gTransform","clipPath","calcTransformMatrix","clipPathTag","clipPathOwner","setPositionByOrigin","that","scalarAdd","scalar","scalarAddEquals","subtract","scalarSubtract","scalarSubtractEquals","multiplyEquals","divide","divideEquals","lt","lte","gt","gte","lerp","distanceFrom","midPointFrom","setXY","setX","setY","setFromPoint","swap","Intersection","status","appendPoint","appendPoints","intersectLineLine","a1","a2","b1","b2","uaT","ubT","uB","ua","ub","intersectLinePolygon","inter","intersectPolygonPolygon","points1","points2","intersectPolygonRectangle","r1","r2","topRight","bottomLeft","inter1","inter2","inter3","inter4","_tryParsingColor","setSource","hue2rgb","q","colorNameMap","sourceFromHex","sourceFromRgb","sourceFromHsl","_rgbToHsl","g","round","_source","toRgb","toHsl","hsl","toHsla","toHex","toHexa","alpha","toGrayscale","average","currentAlpha","toBlackWhite","threshold","overlayWith","otherColor","otherSource","reRGBa","reHSLa","reHex","aliceblue","antiquewhite","aqua","aquamarine","azure","beige","bisque","black","blanchedalmond","blue","blueviolet","brown","burlywood","cadetblue","chartreuse","chocolate","coral","cornflowerblue","cornsilk","crimson","cyan","darkblue","darkcyan","darkgoldenrod","darkgray","darkgrey","darkgreen","darkkhaki","darkmagenta","darkolivegreen","darkorange","darkorchid","darkred","darksalmon","darkseagreen","darkslateblue","darkslategray","darkslategrey","darkturquoise","darkviolet","deeppink","deepskyblue","dimgray","dimgrey","dodgerblue","firebrick","floralwhite","forestgreen","fuchsia","gainsboro","ghostwhite","gold","goldenrod","gray","grey","green","greenyellow","honeydew","hotpink","indianred","indigo","ivory","khaki","lavender","lavenderblush","lawngreen","lemonchiffon","lightblue","lightcoral","lightcyan","lightgoldenrodyellow","lightgray","lightgrey","lightgreen","lightpink","lightsalmon","lightseagreen","lightskyblue","lightslategray","lightslategrey","lightsteelblue","lightyellow","lime","limegreen","linen","magenta","maroon","mediumaquamarine","mediumblue","mediumorchid","mediumpurple","mediumseagreen","mediumslateblue","mediumspringgreen","mediumturquoise","mediumvioletred","midnightblue","mintcream","mistyrose","moccasin","navajowhite","navy","oldlace","olive","olivedrab","orange","orangered","orchid","palegoldenrod","palegreen","paleturquoise","palevioletred","papayawhip","peachpuff","peru","pink","plum","powderblue","purple","rebeccapurple","red","rosybrown","royalblue","saddlebrown","salmon","sandybrown","seagreen","seashell","sienna","silver","skyblue","slateblue","slategray","slategrey","snow","springgreen","steelblue","teal","thistle","tomato","turquoise","violet","wheat","white","whitesmoke","yellow","yellowgreen","fromRgb","fromSource","fromRgba","fromHsl","fromHsla","fromHex","isShortNotation","isRGBa","oColor","getColorStop","multiplier","colorAlpha","keyValuePairs","__convertPercentUnitsToValues","instance","svgOptions","gradientUnits","propValue","finalValue","offsetX","offsetY","gradientTransform","addColorStop","toObject","propertiesToInclude","toSVG","markup","commonAttributes","needsSwap","withViewport","additionalTransform","sort","pathOffset","reverse","minRadius","percentageShift","colorStop","toLive","stops","createLinearGradient","createRadialGradient","colorStopEls","getLinearCoords","getRadialCoords","forObject","repeat","patternTransform","setOptions","patternSource","patternWidth","patternHeight","patternOffsetX","patternOffsetY","patternImgSrc","complete","naturalWidth","naturalHeight","createPattern","Shadow","affectStroke","includeDefaultValues","nonScaling","_parseShadow","shadow","shadowStr","offsetsAndBlur","reOffsetsAndBlur","fBoxX","fBoxY","StaticCanvas","CANVAS_INIT_ERROR","renderAndResetBound","renderAndReset","requestRenderAllBound","_initStatic","backgroundColor","backgroundImage","overlayColor","overlayImage","stateful","controlsAboveOverlay","allowTouchScrolling","imageSmoothingEnabled","viewportTransform","backgroundVpt","overlayVpt","onBeforeScaleRotate","enableRetinaScaling","vptCoords","skipOffscreen","cb","_createLowerCanvas","_initOptions","_setImageSmoothing","interactive","_initRetinaScaling","setOverlayImage","setBackgroundImage","setBackgroundColor","setOverlayColor","calcOffset","_isRetinaScaling","getRetinaScaling","scaleRatio","__initRetinaScaling","lowerCanvasEl","contextContainer","upperCanvasEl","contextTop","_offset","image","__setBgOverlayImage","__setBgOverlayColor","webkitImageSmoothingEnabled","mozImageSmoothingEnabled","msImageSmoothingEnabled","oImageSmoothingEnabled","_createCanvasElement","_applyCanvasStyle","getWidth","getHeight","setWidth","setDimensions","setHeight","dimensions","cssValue","cssOnly","_setBackstoreDimension","hasLostContext","backstoreOnly","_setCssDimension","_isCurrentlyDrawing","freeDrawingBrush","_setBrushStyles","cacheCanvasEl","wrapperEl","getZoom","setViewportTransform","vpt","activeObject","_activeObject","group","setCoords","calcViewportBoundaries","zoomToPoint","before","setZoom","absolutePan","relativePan","getElement","setupState","clearContext","clearRect","clear","_hasITextHandlers","_mouseUpITextHandler","_iTextInstances","renderAll","canvasToDrawOn","renderCanvas","isRendering","iVpt","tl","br","tr","bl","cancelRequestedRender","_renderBackground","_renderObjects","drawControls","shouldCache","_transformDone","renderCache","forClipping","drawClipPathOnCanvas","_renderOverlay","globalCompositeOperation","zoomX","zoomY","_cacheCanvas","cacheTranslationX","cacheTranslationY","render","_renderBackgroundOrOverlay","needsVpt","lineTo","closePath","fillStyle","getCenter","centerObjectH","_centerObject","getCenterPoint","centerObjectV","centerObject","center","viewportCenterObject","vpCenter","getVpCenter","viewportCenterObjectH","viewportCenterObjectV","toDatalessJSON","toDatalessObject","_toObjectMethod","_toObjects","_toObject","__serializeBgOverlay","excludeFromExport","originalValue","bgImage","overlay","background","svgViewportTransformation","_setSVGPreamble","_setSVGHeader","clipPathId","_setSVGBgOverlayColor","_setSVGBgOverlayImage","_setSVGObjects","suppressPreamble","encoding","viewBox","createSVGFontFacesMarkup","createSVGRefElementsMarkup","createSVGClipPathMarkup","toClipPathSVG","shouldTransform","row","rowIndex","charIndex","fontList","_setSVGObject","finalWidth","finalHeight","sendToBack","objs","activeSelection","unshift","bringToFront","sendBackwards","intersecting","newIdx","objsMoved","_findNewLowerIndex","intersectsWithObject","isContainedWithinObject","bringForward","_findNewUpperIndex","dispose","DataURLExporter","EMPTY_JSON","supports","setLineDash","toJSON","createPNGStream","createJPEGStream","BaseBrush","strokeLineCap","strokeLineJoin","strokeMiterLimit","strokeDashArray","setShadow","strokeStyle","lineWidth","lineCap","miterLimit","lineJoin","_saveAndTransform","_setShadow","shadowColor","shadowBlur","shadowOffsetX","shadowOffsetY","needsFullRender","_resetShadow","PencilBrush","decimate","_points","_drawSegment","p1","p2","midPoint","quadraticCurveTo","onMouseDown","pointer","_isMainEvent","_prepareForDrawing","_captureDrawingPath","_render","onMouseMove","oldEnd","onMouseUp","_finalizeAndAddPath","_reset","_addPoint","pointerPoint","convertPointsToSVGPath","multSignX","multSignY","manyPoints","createPath","pathData","Path","strokeWidth","decimatePoints","distance","adjustedDistance","lastPoint","newPoints","CircleBrush","drawDot","addPoint","dot","arc","radius","originalRenderOnAddRemove","circles","circle","Circle","originX","originY","circleRadius","circleColor","SprayBrush","density","dotWidth","dotWidthVariance","randomOpacity","optimizeOverlapping","sprayChunks","addSprayChunk","sprayChunkPoints","rects","ilen","sprayChunk","rect","Rect","_getOptimizedRects","uniqueRects","uniqueRectsArray","globalAlpha","fillRect","PatternBrush","getPatternSrc","patternCanvas","patternCtx","getPatternSrcFunction","getPattern","topLeft","_getLeftTopCoords","supportLineDash","STROKE_OFFSET","_initInteractive","_createCacheCanvas","uniScaleTransform","uniScaleKey","centeredScaling","centeredRotation","centeredKey","altActionKey","selection","selectionKey","altSelectionKey","selectionColor","selectionDashArray","selectionBorderColor","selectionLineWidth","selectionFullyContained","hoverCursor","moveCursor","defaultCursor","freeDrawingCursor","rotationCursor","notAllowedCursor","containerClass","perPixelTargetFind","targetFindTolerance","skipTargetFind","isDrawingMode","preserveObjectStacking","snapAngle","snapThreshold","stopContextMenu","fireRightClick","fireMiddleClick","targets","_hoveredTarget","_hoveredTargets","_currentTransform","_groupSelector","_initWrapperElement","_createUpperCanvas","_initEventListeners","_chooseObjectsToRender","objsToRender","activeGroupObjects","activeObjects","getActiveObjects","contextTopDirty","renderTopLayer","_drawSelection","renderTop","_resetCurrentTransform","original","_shouldCenterTransform","mouseXSign","mouseYSign","containsPoint","xy","_normalizePointer","_findTargetCorner","invertedM","vptPointer","restorePointerVpt","isTargetTransparent","normalizedPointer","targetRelativeX","targetRelativeY","_cacheContext","contextCache","originalColor","selectionBackgroundColor","_renderControls","hasBorders","transparentCorners","_isSelectionKeyPressed","_shouldClearSelection","evented","centerTransform","altKey","_getOriginFromCorner","corner","_getActionFromCorner","alreadySelected","_setupCurrentTransform","ex","ey","lastX","lastY","shiftKey","_beforeTransform","_translateObject","newLeft","newTop","moveX","moveY","_changeSkewTransformOrigin","mouseMove","by","origins","0","skew","originA","originB","flipSign","skewSign","_skewObject","skewed","lockSkewingX","lockSkewingY","actualMouseByOrigin","constraintPosition","actualMouseByCenter","toLocalPoint","lastMouseByCenter","dim","_getTransformedDimensions","translateToOriginPoint","_setObjectSkew","localMouse","_dim","newDim","dimNoSkew","otherBy","_otherBy","_by","newDimMouse","atan","_scaleObject","lockScalingX","lockScalingY","lockScalingFlip","scaled","_setLocalMouse","_setObjectScale","forbidScalingX","forbidScalingY","changeX","changeY","newScaleX","newScaleY","Textbox","w","getMinWidth","_scaleObjectEqually","_flipObject","dist","lastDist","signX","signY","padding","_rotateObject","lockRotation","lastAngle","curAngle","hasRotated","rightAngleLocked","leftAngleLocked","setCursor","cursor","groupSelector","aleft","atop","_setLineDash","strokeRect","findTarget","skipGroup","activeTarget","activeTargetSubs","aObjects","_searchPossibleTargets","_checkTarget","globalPointer","isEditing","subTarget","objToCheck","pointerToUse","subTargetCheck","ignoreZoom","_absolutePointer","_pointer","cssScale","boundsWidth","boundsHeight","bottom","right","retinaScaling","lowerCanvasClass","_copyCanvasStyle","fromEl","toEl","getSelectionContext","getSelectionElement","getActiveObject","active","_discardActiveObject","_fireSelectionEvents","oldObjects","somethingChanged","removed","opt","oldObject","deselected","updated","setActiveObject","currentActives","_setActiveObject","onSelect","onDeselect","discardActiveObject","removeListeners","originalProperties","_realizeGroupTransformOnObject","_unwindGroupTransformOnObject","originalValues","realizeTransform","clearContextTop","cursorOffset","mr","mb","ml","addEventOptions","passive","checkClick","button","cursorMap","mainTouchId","_bindEvents","addOrRemove","_getEventPrefix","enablePointerEvents","functor","eventjsFunctor","canvasElement","eventTypePrefix","_onResize","_onMouseDown","_onMouseMove","_onMouseOut","_onMouseEnter","_onMouseWheel","_onContextMenu","_onDoubleClick","_onDragOver","_onDragEnter","_onDragLeave","_onDrop","_onTouchStart","eventjs","_onGesture","_onDrag","_onOrientationChange","_onShake","_onLongPress","_onMouseUp","_onTouchEnd","eventsBound","_simpleEventHandler","self","__onTransformGesture","__onDrag","__onMouseWheel","_target","hiddenTextarea","focus","currentTransform","__onOrientationChange","__onShake","__onLongPress","_fireEnterLeaveEvents","_cacheTransformEventData","_handleEvent","_resetTransformEventData","getPointerId","evt","identifier","pointerId","isPrimary","touches","__onMouseDown","__onMouseUp","_willAddMouseDown","__onMouseMove","_shouldRender","shouldRender","isClick","_onMouseUpInDrawingMode","_finalizeCurrentTransform","actionPerformed","_maybeGroupObjects","isMoving","_setCursorFromEvent","__corner","eventType","subTargets","absolutePointer","_scaling","hasStateChanged","_addEventOptions","_fire","_onMouseDownInDrawingMode","_onMouseMoveInDrawingMode","_previousPointer","shouldGroup","_shouldGroup","_handleGrouping","saveState","_transformObject","_fireOverOutEvents","fireSyntheticInOutEvents","oldTarget","evtOut","canvasEvtOut","evtIn","canvasEvtIn","_draggedoverTarget","config","inOpt","outOpt","inFires","targetChanged","previousTarget","nextTarget","reset","_beforeScaleTransform","_performTransformAction","_onScale","_isUniscalePossible","currentAction","getCornerCursor","actionIsDisabled","_getRotatedCornerCursor","hasRotatingPoint","_updateActiveSelection","_createActiveSelection","currentActiveObjects","removeWithUpdate","addWithUpdate","_createGroup","groupObjects","exitEditing","ActiveSelection","_groupSelectedObjects","aGroup","_collectObjects","currentObject","selectionX1Y1","selectionX2Y2","allowIntersect","intersectsWithRect","isContainedWithinRect","toCanvasElement","cropping","scaledWidth","scaledHeight","originalWidth","originalHeight","newZoom","vp","originalInteractive","newVp","originalRetina","originalContextTop","loadFromDatalessJSON","loadFromJSON","serialized","_enlivenObjects","_setBgOverlay","enlivenedCanvasClip","__setupCanvas","loaded","cbIfLoaded","__setBgOverlay","enlivedObject","_toDataURL","_toDataURLWithMultiplier","toDataURLWithMultiplier","cloneWithoutData","backgroundImageOpacity","backgroundImageStretch","supportsLineDash","objectCaching","cornerSize","borderColor","borderDashArray","cornerColor","cornerStrokeColor","cornerStyle","cornerDashArray","strokeDashOffset","borderOpacityWhenMoving","borderScaleFactor","minScaleLimit","hasControls","rotatingPointOffset","lockMovementX","lockMovementY","lockUniScaling","statefullCache","noScaleCache","strokeUniform","dirty","paintFirst","stateProperties","cacheProperties","inverted","absolutePositioned","_cacheProperties","_updateCacheCanvas","_limitCacheSize","dims","limitedDims","capped","_getCacheCanvasDimensions","objectScale","getTotalObjectScaling","neededX","neededY","drawingWidth","drawingHeight","minCacheSize","dimensionsChanged","cacheWidth","cacheHeight","zoomChanged","shouldRedraw","additionalWidth","additionalHeight","shouldResizeCanvas","canvasWidth","canvasHeight","sizeGrowing","setTransform","calcOwnMatrix","_removeDefaultValues","getObjectScaling","retina","getObjectOpacity","shouldConstrainValue","isChanged","groupNeedsUpdate","_constrainScale","isOnACache","setOnGroup","getViewportTransform","isNotVisible","isOnScreen","_setupCompositeOperation","drawSelectionBackground","_setOpacity","drawCacheOnCanvas","_removeCacheCanvas","drawObject","propertySet","isCacheDirty","hasStroke","hasFill","needsItsOwnCache","ownCaching","willDrawShadow","drawClipPathOnCache","originalFill","originalStroke","_setClippingProperties","_setStrokeStyles","_setFillStyles","_drawClipPath","skipCanvas","_getNonTransformedDimensions","_removeShadow","decl","lineDashOffset","dashArray","alternative","styleOverride","drawBorders","forActiveSelection","drawBordersInGroup","scaling","multX","multY","_applyPatternGradientTransform","_renderPaintInOrder","_renderStroke","_renderFill","_renderDashedStroke","_applyPatternForTransformedGradient","pCtx","pCanvas","_findCenterFromElement","_assignTransformMatrixProps","preserveAspectRatioOptions","cropX","cropY","objectForm","_fromObject","cloneAsImage","utils","origParams","originalGroup","originalShadow","withoutTransform","withoutShadow","boundingRect","getBoundingRect","shadowOffset","originalCanvas","isType","setGradient","setPatternFill","setColor","shouldCenterOrigin","_setOriginToCenter","_resetOrigin","centerH","viewportCenterH","centerV","viewportCenterV","viewportCenter","getLocalPointer","pClicked","objectLeftTop","createAccessors","extraParam","enlivedProps","translateToGivenOrigin","fromOriginX","fromOriginY","toOriginX","toOriginY","translateToCenterPoint","leftTop","getPointByOrigin","adjustPosition","to","offsetFrom","offsetTo","hypotFull","getScaledWidth","xFull","yFull","_originalOriginX","_originalOriginY","originPoint","multiplyMatrices","oCoords","aCoords","ownMatrixCache","matrixCache","getCoords","absolute","calculate","calcCoords","pointTL","pointBR","other","lines","_getImageLines","_findCrossPoints","_containsCenterOfCanvas","isPartiallyOnScreen","topline","rightline","bottomline","leftline","xi","iLine","xcount","lineKey","getScaledHeight","scaleToWidth","boundingRectFactor","scaleToHeight","_calcRotateMatrix","_calcTranslateMatrix","startMatrix","finalMatrix","cosP","sinP","cosPSinP","cosPMinusSinP","mtr","skipAbsolute","_setCornerCoords","transformMatrixKey","sep","prefix","cache","tMatrix","_calcDimensionsTransformMatrix","flipping","dimX","dimY","noSkew","_finalizeDimensions","bbox","_calculateCurrentDimensions","getSvgColorString","getSvgStyles","skipShadow","getSvgFilter","getSvgSpanStyles","useWhiteSpace","term","textDecoration","getSvgTextDecoration","deltaY","decoration","getSvgCommons","getSvgTransform","full","getSvgTransformMatrix","_setSVGBg","textBgRects","_getFillAttributes","_createBaseSVGMarkup","_toSVG","_createBaseClipPathSVGMarkup","objectMarkup","commonPieces","clipPathMarkup","noStyle","styleInfo","shadowInfo","withShadow","vectorEffect","absoluteClipPath","addPaintOrder","originalSet","saveProps","props","tmpObj","_isEqual","origValue","currentValue","firstPass","dashedPropertySet","_controlsVisibility","isControlVisible","newTheta","cornerHypotenuse","cosHalfOffset","sinHalfOffset","wh","drawRotatingPoint","rotateHeight","scaleOffset","_drawControl","control","controlName","_getControlsVisibility","setControlVisible","setControlsVisibility","FX_DURATION","fxCenterObjectH","callbacks","fxCenterObjectV","fxRemove","skipCallbacks","propsToAnimate","_animate","propPair","from","valueProgress","timeProgress","coordProps","makeEdgeToOriginGetter","propertyNames","originValues","axis1","axis2","dimension","nearest","farthest","Line","_setWidthHeight","_getLeftToOriginX","_getTopToOriginY","calcLinePoints","origStrokeStyle","xMult","yMult","ATTRIBUTE_NAMES","parsedAttributes","pi","startAngle","endAngle","setRadius","svgString","startX","startY","endX","endY","largeFlag","getRadiusX","getRadiusY","Triangle","widthBy2","heightBy2","piBy2","Ellipse","getRx","getRy","_initRxRy","isRounded","Polyline","_setPositionDimensions","correctLeftTop","calcDim","_calcDimensions","fromSVG","diffX","diffY","commonRender","fromElementGenerator","_class","Polygon","_toString","commandLengths","repeatedCommands","M","fromArray","_parsePath","_renderPathCommands","tempX","tempY","previous","subpathStartX","subpathStartY","controlX","controlY","_getOffsetTransform","digits","currentPath","coordsStr","coordsParsed","re","command","commandLength","repeatedCommand","klen","aX","aY","pathUrl","useSetOnGroup","isAlreadyGrouped","_updateObjectsACoords","_calcBounds","_updateObjectsCoords","_updateObjectCoords","objectLeft","objectTop","_restoreObjectsState","_includeDefaultValues","objsToObject","originalDefaults","_obj","ownCache","_restoreObjectState","toActiveSelection","ungroupOnCanvas","setObjectsCoords","onlyWidthHeight","iLen","jLen","_getBounds","minXY","maxXY","enlivedClipPath","toGroup","newGroup","childrenOverride","srcFromAttribute","_lastScaleX","_lastScaleY","_filterScalingX","_filterScalingY","minimumScaleTrigger","cacheKey","filters","_initElement","_element","setElement","removeTexture","_initConfig","applyFilters","resizeFilter","applyResizeFilters","backend","filterBackend","evictCachesForKey","setCrossOrigin","getOriginalSize","_stroke","filterObj","getSrc","hasCrop","strokeSvg","imageMarkup","getSvgSrc","origFill","filtered","setSrc","minimumScale","elementToFilter","_filteredEl","sourceWidth","sourceHeight","isNeutralState","imgElement","_needsResize","elementToDraw","elWidth","elHeight","sX","sY","sW","sH","maxDestW","maxDestH","_resetWidthHeight","CSS_CANVAS","_initFilters","pAR","rWidth","rHeight","pWidth","pHeight","_object","resizeFilters","fromURL","imgOptions","_getAngleValueForStraighten","straighten","fxStraighten","straightenObject","fxStraightenObject","testPrecision","precision","fragmentSource","fragmentShader","createShader","FRAGMENT_SHADER","shaderSource","compileShader","getShaderParameter","COMPILE_STATUS","setupGLContext","captureGPUInfo","isSupported","getParameter","MAX_TEXTURE_SIZE","precisions","webGlPrecision","createWebGLCanvas","aPosition","Float32Array","chooseFastestCopyGLTo2DMethod","canUseImageData","canMeasurePerf","performance","canUseArrayBuffer","ArrayBuffer","canUseUint8Clamped","copyGLTo2D","startTime","drawImageTime","testContext","now","glOptions","premultipliedAlpha","depth","stencil","antialias","clearColor","cachedTexture","getCachedTexture","sourceTexture","createTexture","targetTexture","originalTexture","passes","webgl","programCache","pass","tempFbo","createFramebuffer","bindFramebuffer","FRAMEBUFFER","applyTo","resizeCanvasIfNeeded","bindTexture","TEXTURE_2D","deleteTexture","deleteFramebuffer","clearWebGLCaches","textureCache","textureImageSource","texture","texParameteri","TEXTURE_MAG_FILTER","NEAREST","TEXTURE_MIN_FILTER","TEXTURE_WRAP_S","CLAMP_TO_EDGE","TEXTURE_WRAP_T","texImage2D","uniqueId","gpuInfo","renderer","vendor","ext","getExtension","UNMASKED_RENDERER_WEBGL","UNMASKED_VENDOR_WEBGL","sourceElement","originalEl","originalImageData","BaseFilter","vertexSource","createProgram","vertexShader","VERTEX_SHADER","getShaderInfoLog","program","attachShader","linkProgram","getProgramParameter","LINK_STATUS","getProgramInfoLog","attributeLocations","getAttributeLocations","uniformLocations","getUniformLocations","uStepW","getUniformLocation","uStepH","getAttribLocation","sendAttributeData","aPositionData","attributeLocation","buffer","createBuffer","bindBuffer","ARRAY_BUFFER","enableVertexAttribArray","vertexAttribPointer","FLOAT","bufferData","STATIC_DRAW","_setupFrameBuffer","framebufferTexture2D","COLOR_ATTACHMENT0","_swapTextures","temp","main","mainParameter","applyToWebGL","applyTo2d","retrieveShader","shader","useProgram","uniform1f","sendUniformData","viewport","drawArrays","TRIANGLE_STRIP","bindAdditionalTexture","textureUnit","activeTexture","TEXTURE0","unbindAdditionalTexture","getMainParameter","setMainParameter","createHelpLayer","helpLayer","mainP","ColorMatrix","colorsOnly","uColorMatrix","uConstants","constants","uniformMatrix4fv","uniform4fv","Brightness","brightness","uBrightness","Convolute","opaque","Convolute_3_1","Convolute_3_0","Convolute_5_1","Convolute_5_0","Convolute_7_1","Convolute_7_0","Convolute_9_1","Convolute_9_0","dstOff","scx","scy","srcOff","wt","weights","side","halfSide","sw","sh","output","createImageData","dst","alphaFac","uMatrix","uOpaque","uHalfSize","uSize","uniform1fv","Grayscale","lightness","luminosity","uMode","uniform1i","Invert","invert","uInvert","Noise","noise","rand","uNoise","uSeed","Pixelate","blocksize","_i","_j","_iLen","_jLen","uBlocksize","RemoveColor","useAlpha","lowC","highC","uLow","uHigh","Brownie","Vintage","Kodachrome","Technicolor","Polaroid","Sepia","BlackWhite","BlendColor","screen","diff","lighten","darken","exclusion","tint","buildSource","tg","alpha1","uColor","BlendImage","mask","TEXTURE1","calculateMatrix","canvas1","blendData","blendImage","uTransformMatrix","uImage","uniformMatrix3fv","Resize","resizeType","lanczosLobes","uDelta","uTaps","uniform2fv","horizontal","taps","filterWindow","getFilterWindow","generateShader","tempScale","getTaps","lobeFunction","lanczosCreate","offsets","fragmentSourceTOP","dW","dH","lobes","xx","rcpScaleX","rcpScaleY","newData","oW","oH","sliceByTwo","hermiteFastResize","bilinearFiltering","lanczosResize","tmpCanvas","mult","doneW","doneH","stepW","stepH","dX","dY","srcData","destImg","destData","lanczos","ratioX","ratioY","rcpRatioX","rcpRatioY","range2X","range2Y","cacheLanc","icenter","process","u","weight","fX","fY","xDiff","yDiff","chnl","origPix","w4","pixels","destImage","destPixels","ratioW","ratioH","ratioWHalf","ratioHHalf","img2","data2","weightsAlpha","gxR","gxG","gxB","gxA","centerY","yy","centerX","w0","Contrast","contrast","contrastF","uContrast","Saturation","saturation","adjust","uSaturation","Blur","aspectRatio","simpleBlur","canvas2","blurLayer1","blurLayer2","percent","ctx1","ctx2","nSamples","newImageData","delta","chooseRightDelta","blurScale","Gamma","gamma","rInv","gInv","bInv","rVals","gVals","bVals","uGamma","uniform3fv","Composed","subFilters","some","HueRotation","rotation","rad","aThird","aThirdSqtSin","OneMinusCos","_dimensionAffectingProps","_reNewline","_reSpacesAndTabs","_reSpaceAndTab","_reWords","underline","overline","linethrough","textAlign","superscript","baseline","subscript","textBackgroundColor","_fontSizeFraction","_fontSizeMult","charSpacing","_measuringContext","_styleProperties","__charBounds","CACHE_FONT_SIZE","MIN_TEXT_WIDTH","__skipDimension","initDimensions","getMeasuringContext","_splitText","newLines","_splitTextIntoLines","textLines","_textLines","graphemeLines","_unwrappedTextLines","_unwrappedLines","_text","graphemeText","_clearCache","calcTextWidth","cursorWidth","enlargeSpaces","calcTextHeight","diffSpace","currentLineWidth","numberOfSpaces","accumulatedSpace","line","charBound","spaces","isEndOfWrapping","getLineWidth","kernedWidth","lineIndex","missingNewlineOffset","_setTextStyles","_renderTextLinesBackground","_renderTextDecoration","_renderText","_renderTextStroke","_renderTextFill","charStyle","forMeasuring","textBaseline","_getFontDeclaration","maxWidth","_renderTextLine","_renderChars","styleHas","heightOfLine","lineLeftOffset","lastColor","charBox","currentColor","lineTopOffset","leftOffset","_getLeftOffset","topOffset","_getTopOffset","boxStart","boxWidth","getHeightOfLine","_getLineLeftOffset","getValueOfPropertyAt","getFontCache","cacheProp","_applyCharStyles","styleDeclaration","_measureChar","_char","previousChar","prevCharStyle","coupleWidth","previousWidth","fontCache","couple","stylesAreEqual","fontMultiplier","measureText","getHeightOfChar","measureLine","lineInfo","_measureLine","_getWidthOfCharSpacing","grapheme","prevGrapheme","graphemeInfo","lineBounds","_getGraphemeBox","numOfSpaces","skipLeft","getCompleteStyleDeclaration","prevStyle","info","previousBox","__lineHeights","maxHeight","_renderTextCommon","lineHeights","isEmptyStyles","actualStyle","nextStyle","timeToRender","isJustify","charsToRender","shortCut","_renderChar","_hasStyleChanged","_getStyleDeclaration","fullDecl","shouldFill","shouldStroke","fillText","strokeText","setSuperscript","_setScript","setSubscript","schema","loc","get2DCursorLocation","setSelectionStyles","thisStyle","_hasStyleChangedForSvg","__lineWidths","_shouldClearDimensionCache","shouldClear","_forceClearCache","_size","_dy","lastDecoration","currentDecoration","currentFill","lastFill","styleObject","family","fontIsGeneric","genericFonts","newLine","newText","additionalProperties","needsDims","_key","parsedAnchor","textAnchor","originalStrokeWidth","textHeightScaleFactor","scaledDiff","textHeight","offX","p3","cleanStyle","letterCount","stylePropertyValue","stylesCount","allStyleObjectPropertiesMatch","graphemeCount","removeStyle","lineNum","charNum","_extendStyles","_getLineStyle","_setLineStyle","_setStyleDeclaration","selectionStart","skipWrapping","getSelectionStyles","startIndex","endIndex","selectionEnd","getStyleAtPosition","lineStyle","_deleteStyleDeclaration","_deleteLineStyle","parseDecoration","IText","editable","editingBorderColor","cursorColor","cursorDelay","cursorDuration","caching","_reSpace","_currentCursorOpacity","_selectionDirection","_abortCursorAnimation","__widthOfSpace","inCompositionMode","initBehavior","setSelectionStart","_updateAndFire","setSelectionEnd","_fireSelectionChanged","_updateTextarea","initDelayedCursor","cursorOffsetCache","renderCursorOrSelection","skipRestore","_clearTextArea","boundaries","_getCursorBoundaries","renderCursor","renderSelection","_getCursorBoundariesOffsets","cursorPosition","cursorLocation","charHeight","__isMousedown","startLine","endLine","startChar","endChar","realLineHeight","lineOffset","boxEnd","compositionColor","getCurrentCharFontSize","cp","_getCurrentCharIndex","getCurrentCharColor","initAddedHandler","initRemovedHandler","initCursorSelectionHandlers","initDoubleClickSimulation","mouseMoveHandler","_initCanvasHandlers","_removeCanvasHandlers","_tick","_currentTickState","_animateCursor","targetOpacity","completeMethod","tickState","isAborted","_onTickComplete","_cursorTimeout1","_currentTickCompleteState","restart","delay","abortCursorAnimation","_cursorTimeout2","selectAll","getSelectedText","findWordBoundaryLeft","startFrom","findWordBoundaryRight","findLineBoundaryLeft","findLineBoundaryRight","searchWordBoundary","direction","selectWord","newSelectionStart","newSelectionEnd","selectLine","enterEditing","exitEditingOnOthers","initHiddenTextarea","_saveEditingProps","_setEditingProps","_textBeforeEdit","initMouseMoveHandler","getSelectionStartFromPointer","currentStart","currentEnd","__selectionStartOnMouseDown","restartCursorIfNeeded","fromStringToGraphemeSelection","smallerTextStart","graphemeStart","smallerTextEnd","fromGraphemeToStringSelection","newSelection","updateTextareaPosition","updateFromTextArea","_calcTextareaPosition","desiredPosition","compositionStart","upperCanvas","upperCanvasWidth","upperCanvasHeight","_savedProps","_restoreEditingProps","isTextChanged","_removeExtraneousStyles","removeStyleFromTo","styleObj","cursorStart","cursorEnd","lineStart","charStart","lineEnd","charEnd","shiftLineStyles","numericChar","clonedStyles","numericLine","insertNewlineStyleObject","copiedStyle","currentCharStyle","newLineStyles","somethingAdded","isEndOfLine","numIndex","styleCarriedOver","insertCharStyleObject","currentLineStyles","currentLineStylesCloned","numericIndex","newStyle","insertNewStyleBlock","insertedText","cursorLoc","addedLines","linesLength","setSelectionStartEndWithShift","setSelectionInBoundaries","__lastClickTime","__lastLastClickTime","__lastPointer","__newClickTime","newPointer","isTripleClick","_stopEvent","__lastIsEditing","__lastSelected","initMousedownHandler","initMouseupHandler","initClicks","doubleClickHandler","tripleClickHandler","_mouseDownHandler","setCursorByClick","_mouseDownHandlerBefore","mouseUpHandler","currentActive","mouseOffset","prevWidth","_getNewSelectionStartFromOffset","distanceBtwLastCharAndCursor","distanceBtwNextCharAndCursor","onKeyDown","onKeyUp","onInput","copy","paste","onCompositionStart","onCompositionUpdate","onCompositionEnd","_clickHandlerInitialized","onClick","keysMap","9","27","33","34","35","36","37","38","39","40","ctrlKeysMapUp","67","88","ctrlKeysMapDown","65","keyCode","ctrlKey","metaKey","stopImmediatePropagation","_copyDone","fromPaste","removedText","removeFrom","removeTo","nextText","charCount","nextCharCount","charDiff","textareaSelection","backDelete","copiedText","copiedTextStyle","compositionEnd","_getClipboardData","clipboardData","_getWidthBeforeCursor","widthBeforeCursor","getDownCursorOffset","isRight","selectionProp","_getSelectionForOffset","indexOnOtherLine","_getIndexOnLine","getUpCursorOffset","textBeforeCursor","charWidth","foundMatch","widthOfCharsOnLine","indexOnLine","leftEdge","rightEdge","offsetFromLeftEdge","moveCursorDown","_moveCursorUpOrDown","moveCursorUp","moveCursorWithShift","moveCursorWithoutShift","moveCursorLeft","_moveCursorLeftOrRight","_move","_moveLeft","_moveRight","moveCursorLeftWithoutShift","change","moveCursorLeftWithShift","moveCursorRight","actionName","moveCursorRightWithShift","moveCursorRightWithoutShift","changed","removeChars","insertChars","multipleSpacesRegex","_getSVGLeftTopOffsets","textAndBg","_getSVGTextAndBg","textTop","textLeft","_wrapSVGTextAndBg","lineTop","textSpans","textTopOffset","textLeftOffset","_setSVGTextLineBg","_setSVGTextLineText","_createTextCharSpan","styleDecl","shouldUseWhitespace","styleProps","fillStyles","dySpan","_pushTextBgRect","fillColor","_getSVGLineTopOffset","lastHeight","minWidth","dynamicMinWidth","__cachedLines","_wordJoiners","splitByGrapheme","_styleMap","_generateStyleMap","textInfo","realLineCount","realLineCharCount","isWrapping","nextOffset","shouldLimit","mapNextLine","_wrapText","desiredWidth","wrapped","_wrapLine","_measureWord","word","charOffset","_line","reservedSpace","words","infix","wordWidth","infixWidth","largestWordWidth","lineJustStarted","additionalSpace","linesToKeep","PRODUCT_GRID_PLP","initProdTileCarousel","initSlotCarousel","QUICKADD_BUTTON","openQuickAdd","PREVENT_DEFAULT","onResizeFunction","QUICKADD_CLOSE","QUICKADD_PROCEEDBUTTON","QUICKADD_SIZEBUTTON","isOpened","STYLE_QUICKADD_SIZEBUTTON_SELECTED","QUICKADD_MODAL_OPEN","containerClassName","$this","$modal","$modalForSlider","isCompletePromo","genericAjaxCall","newDOMModal","closeQuickAddShoppable","prepareAddToCart","searchSelectedSize","openQuickAddShoppable","$quickAddOutsideModal","prepend","analytics","slideDown","closeQuickAdd","forceLockScroll","exc","forceUnlockScroll","slideUp","closeQuickButton","closeAllQuickAdd","allQAopen","selectSize","sizeButton","prepareData","makeAddToCart","dataValue","history","scrollRestoration","variableWidth","$tileCarousel","IMAGE_CONTAINER_CAROUSEL_CLASS","lazyloadclass","lazyVideos","querySelectorAll","lazyVideoObserver","IntersectionObserver","entries","isIntersecting","videoSource","dataset","unobserve","lazyVideo","previousLabel","nextLabel","lazyLoad","draggable","accessibility","showQuickview","observeQuickBuy","productUrl","destroyModal","fillModalElement","newModal","actualDiv","notifyMeAction","notifyMeDiv","paramUrl","htmlContent","innerText","quickAddFlow","rsp","FormHelpers","productName","cta","email","isValid","validateEmail","queryString","analyticsSku","dataForm","owner","messageComingSoon","duplicate","carousel","swipe","swipeToSlide","touchMove","gotoPDP","startCarouselTileImage","afterAttributesSelectionEvent","additionalData","newPriceData","checkCarouselLength","carouselContainer","carouselWidth","outerWidth","carouselItemsNumber","carouselItemsWidth","carouselItemsWidthSum","carouselScrolled","ready","carouselScroll","dir","customizePosition","customizeSide","customizeText","customizeFont","customizePattern","customizeColor","allowedCharactersRegex","canvasText","canvasRect","canvasGroup","canvasImage","topBack","leftBack","badWords","loadingTime","isStepTwo","rectColor","switchDisable","initText","textInput","SELECTORS","fontsButtons","colorsButtons","initVariables","pixelText","initCanvas","imageToLoad","imgFront","transformX","transformY","personalizationCanvas","transformOrigin","zoomButton","canvasRatio","initForm","updateCanvasElem","elem","choicePosition","page","mainChoice","showOtherSide","stepOne","stepTwo","termsBottomDesktop","CLASSES","pageStepOne","pageStepTwo","selectPosition","imgBack","hotspotOne","hotspotTwo","updateCanvas","defer","imagesNumber","loadComplete","jQuery","Deferred","one","promise","imageFront","imageBack","topPercentage","leftPercentage","topBackPercentage","leftBackPercentage","$position1","$position2","backChoicePosition","personalizeAddToCart","canvasOptions","svgAllFormat","generateSvgForOTP","base64FullSVG","base64TextFullSVG","base64TextSmallSVG","termsAndConditionsModal","analyticsCustomizeAction","pageClose","positionChoice","badWordsFlag","editTextOnCanvas","colorName","scaleValue","base64","ieee754","kMaxLength","TYPED_ARRAY_SUPPORT","RangeError","__proto__","arg","encodingOrOffset","allocUnsafe","TypeError","byteOffset","byteLength","fromArrayLike","fromArrayBuffer","isEncoding","actual","write","fromString","isBuffer","checked","assertSize","isView","loweredCase","utf8ToBytes","base64ToBytes","slowToString","hexSlice","utf8Slice","asciiSlice","latin1Slice","base64Slice","utf16leSlice","bidirectionalIndexOf","arrayIndexOf","indexSize","arrLength","valLength","read","buf","readUInt16BE","foundIndex","found","hexWrite","remaining","strLen","utf8Write","blitBuffer","asciiWrite","byteArray","asciiToBytes","latin1Write","base64Write","ucs2Write","units","hi","lo","utf16leToBytes","fromByteArray","res","secondByte","thirdByte","fourthByte","tempCodePoint","firstByte","codePoint","bytesPerSequence","codePoints","MAX_ARGUMENTS_LENGTH","fromCharCode","decodeCodePointsArray","SlowBuffer","alloc","INSPECT_MAX_BYTES","foo","subarray","typedArraySupport","poolSize","_augment","species","configurable","allocUnsafeSlow","_isBuffer","compare","swap16","swap32","swap64","equals","inspect","thisStart","thisEnd","thisCopy","targetCopy","isFinite","_arr","ret","out","bytes","checkOffset","checkInt","objectWriteUInt16","littleEndian","objectWriteUInt32","checkIEEE754","writeFloat","noAssert","writeDouble","newBuf","sliceLen","readUIntLE","mul","readUIntBE","readUInt8","readUInt16LE","readUInt32LE","readUInt32BE","readIntLE","readIntBE","readInt8","readInt16LE","readInt16BE","readInt32LE","readInt32BE","readFloatLE","readFloatBE","readDoubleLE","readDoubleBE","writeUIntLE","writeUIntBE","writeUInt8","writeUInt16LE","writeUInt16BE","writeUInt32LE","writeUInt32BE","writeIntLE","limit","sub","writeIntBE","writeInt8","writeInt16LE","writeInt16BE","writeInt32LE","writeInt32BE","writeFloatLE","writeFloatBE","writeDoubleLE","writeDoubleBE","targetStart","INVALID_BASE64_RE","Infinity","leadSurrogate","toByteArray","stringtrim","base64clean","b64","lens","getLens","validLen","placeHoldersLen","tmp","Arr","_byteLength","curByte","revLookup","uint8","extraBytes","maxChunkLength","len2","encodeChunk","lookup","num","isLE","mLen","nBytes","eLen","eMax","eBias","nBits","NaN","rt","LN2","createSvgFromCanvas","canvasToConvert","svg","canvasNode","computeCurrentlyVisibleImage","handleDetailsTabs","clickedTab","openQuickView","modalClass","setMinHeightPromoPanel","_array","_array2","maxHeightTitle","crossSellItems","getProductVariationGroup","requestUrl","isSizeChange","$result","$completePromoData","$completePromoSection","$completePromoProducts","$completePromoContainer","$completeLookData","$completeLookSection","$completeLookProducts","quickview","closeAllOpenMenus","removeNulls","updatePrimaryImagesSlide","enableImageSlideHeightObservers","imgNode","MutationObserver","mutationsList","observer","mutation","attributeName","childList","subtree","slickNode","initializePrimaryImagesSlider","primaryImages","carouselItems","ProductHelpers","showSpinner","updateAttribute","updateAddToCart","getCrossSellItems","afterUpdateImages","recentlyViewedItems","buyNowQuichview","suggedtedProductsPDP","observeCurtainTap","removeNullCrossSell","pdpCrossSell","handleAccordionsInPDP","changeAddToBagButton","$buyNowCta","initProductTile","cs","$csItem","$detailsAccordionShipping","$detailsAccordionDescription","basketBeforeRemovedProduct","basketObserverEnabled","basketAlreadyFetched","addSmartGift","enableAnalyticsBasketObserver","analyticsDataButton","basketButtonsSelector","SGBasket","getSkus","getSkusQuantity","eachSuggestion","dataSuggestion","suggestionLength","suggestionItem","infoSuggestion","imgSuggestion","hrefSuggestion","skuCode","skuUrl","recommendedItems","nameEng","addRecommendedItems","addItem","state","basket","removedProduct","targetWidgetNode","setAnalyticsProductIndex","getBasket","productIndex","triggerRemoveProduct","needle","qsKeyToUpdate","urlObject","qsKey","qsValue","replaceState","environment","_completeMatch","varName","renderTemplate","processBalanceAjaxCall","ajaxUrl","giftCardType","giftCardNumber","giftCardPin","captcha","gcType","responseData","amount","isResocard","expiryDate","firstName","isExpired","grecaptcha","checkGiftCardInputFields","isGiftCardCodeEmpty","isGiftCardPinEmpty","processBalance","retriveGiftCardBalanceFooter","retriveGiftCardBalance","applyGiftcard","amountText","messageRemainedAmount","coversTotalAmount","order","customer","getGiftCardBalance","handleGiftcardInput","checkingGiftCardType","formatDate","formatPattern","getDate","getMonth","getFullYear","GiftCard","selectedOccasion","selectedSwatchIndex","occasionElement","swatchesContainer","swatchesElement","colorsSection","colorsContainer","colorsElement","giftCardImage","giftCardPriceBanner","amounts","manualAmount","sliderConfig","centerMode","focusOnSelect","speed","firstOccasionName","firstColorId","_selectOccasion","colorCode","giftCardEventListeners","formListeners","initializeDateSelector","initParsleyValidator","initSwatches","initModalPreview","processInclude","GiftcardHelper","productHelpers","occasionName","swatchIndex","colorId","_selectSwatch","$selectedSwatchContainer","_selectColorsList","$selectedColorList","_selectColor","$selectedColor","$carousel","applyRendering","selectedImageUrl","selectedImageUrlArray","selectedImageName","newOccasionSelection","newSwatchSelection","newColorSelection","$firstAmountOption","firstAmountOptionValue","parsedValue","minimumValue","maximumValue","textlen","firstDate","year","month","day","formattedDate","formattedExpiryDate","fdatepicker","disableDblClickSelection","leftArrow","rightArrow","closeIcon","closeButton","initialDate","startDate","ev","getTimezoneOffset","datestring","expiry","parsley","currentSlide","nextSlide","modalBigContent","giftCardHtmlPreview","amountSelectorOk","minAmount","maxAmount","errors","validator","validate","country","destinationName","destinationMail","senderName","dateString","imgCode","productGender","URLSearchParams","shippingDate","imageCode","giftcardGender","smooth"],"mappings":"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","file":"giftCardDetails.min.js","sourcesContent":[" \t// The module cache\n \tvar installedModules = {};\n\n \t// The require function\n \tfunction __webpack_require__(moduleId) {\n\n \t\t// Check if module is in cache\n \t\tif(installedModules[moduleId]) {\n \t\t\treturn installedModules[moduleId].exports;\n \t\t}\n \t\t// Create a new module (and put it into the cache)\n \t\tvar module = installedModules[moduleId] = {\n \t\t\ti: moduleId,\n \t\t\tl: false,\n \t\t\texports: {}\n \t\t};\n\n \t\t// Execute the module function\n \t\tmodules[moduleId].call(module.exports, module, module.exports, __webpack_require__);\n\n \t\t// Flag the module as loaded\n \t\tmodule.l = true;\n\n \t\t// Return the exports of the module\n \t\treturn module.exports;\n \t}\n\n\n \t// expose the modules object (__webpack_modules__)\n \t__webpack_require__.m = modules;\n\n \t// expose the module cache\n \t__webpack_require__.c = installedModules;\n\n \t// define getter function for harmony exports\n \t__webpack_require__.d = function(exports, name, getter) {\n \t\tif(!__webpack_require__.o(exports, name)) {\n \t\t\tObject.defineProperty(exports, name, { enumerable: true, get: getter });\n \t\t}\n \t};\n\n \t// define __esModule on exports\n \t__webpack_require__.r = function(exports) {\n \t\tif(typeof Symbol !== 'undefined' && Symbol.toStringTag) {\n \t\t\tObject.defineProperty(exports, Symbol.toStringTag, { value: 'Module' });\n \t\t}\n \t\tObject.defineProperty(exports, '__esModule', { value: true });\n \t};\n\n \t// create a fake namespace object\n \t// mode & 1: value is a module id, require it\n \t// mode & 2: merge all properties of value into the ns\n \t// mode & 4: return value when already ns object\n \t// mode & 8|1: behave like require\n \t__webpack_require__.t = function(value, mode) {\n \t\tif(mode & 1) value = __webpack_require__(value);\n \t\tif(mode & 8) return value;\n \t\tif((mode & 4) && typeof value === 'object' && value && value.__esModule) return value;\n \t\tvar ns = Object.create(null);\n \t\t__webpack_require__.r(ns);\n \t\tObject.defineProperty(ns, 'default', { enumerable: true, value: value });\n \t\tif(mode & 2 && typeof value != 'string') for(var key in value) __webpack_require__.d(ns, key, function(key) { return value[key]; }.bind(null, key));\n \t\treturn ns;\n \t};\n\n \t// getDefaultExport function for compatibility with non-harmony modules\n \t__webpack_require__.n = function(module) {\n \t\tvar getter = module && module.__esModule ?\n \t\t\tfunction getDefault() { return module['default']; } :\n \t\t\tfunction getModuleExports() { return module; };\n \t\t__webpack_require__.d(getter, 'a', getter);\n \t\treturn getter;\n \t};\n\n \t// Object.prototype.hasOwnProperty.call\n \t__webpack_require__.o = function(object, property) { return Object.prototype.hasOwnProperty.call(object, property); };\n\n \t// __webpack_public_path__\n \t__webpack_require__.p = \"\";\n\n\n \t// Load entry module and return exports\n \treturn __webpack_require__(__webpack_require__.s = 121);\n","import tingle from 'tingle.js';\n\n/* eslint-disable new-cap */\n\n/**\n * This function retrieves another page of content to display in the content search grid\n * @param {Boolean} footer - HTML string\n * @return {Tingle} - https://robinparisi.github.io/tingle/\n */\nconst newModal = (footer, cssClass = []) => {\n // set optionts\n const modalOptions = {\n closeMethods: ['overlay', 'button', 'escape'],\n cssClass,\n onClose: () => {\n modal.destroy();\n },\n onOpen: () => { $('html').addClass('html-tingle-enabled'); },\n beforeClose: () => {\n if (($('.jsPersonalizationToolModal.tingle-modal--visible').length <= 0) || ($('.tingle-modal.tingle-modal--visible').length < 2)) {\n $('html').removeClass('html-tingle-enabled');\n }\n return true;\n }\n };\n if (footer) { modalOptions.footer = true; };\n\n // create modal\n const modal = new tingle.modal(modalOptions);\n\n return modal;\n};\n\n/**\n * This function retrieves another page of content to display in the content search grid\n * @param {String} selectorID - ID of the modal DOM element to clone\n * @return {Tingle} - https://robinparisi.github.io/tingle/\n */\nconst newModalFromSelector = (selectorID, footer, cssClass = [], onClose = null) => {\n // set optionts\n const modalOptions = {\n closeMethods: ['overlay', 'escape'],\n cssClass,\n onClose: () => {\n modal.destroy();\n if (typeof onClose === 'function') {\n onClose();\n }\n },\n onOpen: () => { $('html').addClass('html-tingle-enabled'); },\n beforeClose: () => {\n if (($('.jsPersonalizationToolModal.tingle-modal--visible').length <= 0) || ($('.tingle-modal.tingle-modal--visible').length < 2)) {\n $('html').removeClass('html-tingle-enabled');\n }\n return true;\n }\n };\n if (footer) { modalOptions.footer = true; };\n\n // create modal\n const modal = new tingle.modal(modalOptions);\n\n // clone content\n if (selectorID) {\n const contentModal = document.getElementById(selectorID);\n if (contentModal) {\n modal.setContent(contentModal.innerHTML);\n }\n }\n\n return modal;\n};\n\n/**\n * This function retrieves another page of content to display in the content search grid\n * @param {String} html - HTML string\n * @return {Tingle} - https://robinparisi.github.io/tingle/\n */\nconst newModalFromString = (html, footer, cssClass = [], onOpen, onClose) => {\n // set optionts\n const modalOptions = {\n closeMethods: ['overlay', 'button', 'escape'],\n cssClass,\n onClose: () => {\n modal.destroy();\n if (typeof onClose === 'function') {\n onClose();\n }\n },\n onOpen: () => {\n $('html').addClass('html-tingle-enabled');\n if (typeof onOpen === 'function') {\n onOpen();\n }\n },\n beforeClose: () => {\n if (($('.jsPersonalizationToolModal.tingle-modal--visible').length <= 0) || ($('.tingle-modal.tingle-modal--visible').length < 2)) {\n $('html').removeClass('html-tingle-enabled');\n }\n return true;\n }\n };\n if (footer) { modalOptions.footer = true; };\n\n // create modal\n const modal = new tingle.modal(modalOptions);\n\n // add content\n if (html) {\n modal.setContent(html);\n }\n\n return modal;\n};\n\n/**\n * This function creates a modal starting from supplied options\n * @return {Tingle} - https://robinparisi.github.io/tingle/\n */\nconst newModalWithOptions = (modalOptions) => {\n // create modal\n const modal = new tingle.modal(modalOptions);\n\n return modal;\n};\n\n// modal with forced choice\nconst newModalWithSelector = (html, footer, cssClass = [], onOpen, onClose) => {\n // set optionts\n const modalOptions = {\n closeMethods: [],\n cssClass,\n onClose: () => {\n modal.destroy();\n if (typeof onClose === 'function') {\n onClose();\n }\n },\n onOpen: () => {\n $('html').addClass('html-tingle-enabled');\n if (typeof onOpen === 'function') {\n onOpen();\n }\n },\n beforeClose: () => {\n if (($('.jsPersonalizationToolModal.tingle-modal--visible').length <= 0) || ($('.tingle-modal.tingle-modal--visible').length < 2)) {\n $('html').removeClass('html-tingle-enabled');\n }\n return true;\n }\n };\n if (footer) { modalOptions.footer = true; };\n\n // create modal\n const modal = new tingle.modal(modalOptions);\n\n // add content\n if (html) {\n modal.setContent(html);\n }\n\n return modal;\n};\n\n/**\n * This class creates a modal without copying or moving any HTML,\n * but simply showing and hiding an existing Node.\n * This is to avoid problems with manipulated elements such as Google Maps\n */\nclass ModalShowHide {\n constructor (selector = '', newModalType, toPropagateClick, classToPreventHide) {\n this.$el = $(selector);\n this.selector = selector;\n this._scrollposition = 0;\n this.toPropagateClick = toPropagateClick;\n this.classToPreventHide = classToPreventHide;\n if (newModalType) {\n this.isOpenTypeCustom = false;\n } else {\n this.isOpen = false;\n }\n\n this.events();\n }\n\n show (newModalType) {\n if (newModalType) {\n if (this.isOpenTypeCustom) {\n return;\n }\n this.isOpenTypeCustom = true;\n } else {\n if (this.isOpen) {\n return;\n }\n this.isOpen = true;\n }\n\n // mimic tingle scroll lock\n this._scrollPosition = window.pageYOffset;\n $('body').addClass('tingle-enabled');\n $('html').addClass('html-tingle-enabled');\n this.$el.parent('.tingle-modal').addClass('tingle-modal--visible');\n }\n\n hide (newModalType) {\n if (newModalType) {\n if (!this.isOpenTypeCustom) {\n return;\n }\n this.isOpenTypeCustom = false;\n } else {\n if (!this.isOpen) {\n return;\n }\n this.isOpen = false;\n }\n\n // mimic tingle scroll lock\n if (($('.jsPersonalizationToolModal.tingle-modal--visible').length <= 0) || ($('.tingle-modal.tingle-modal--visible').length < 2)) {\n $('body').removeClass('tingle-enabled');\n $('html').removeClass('html-tingle-enabled');\n window.scrollTo(0, this._scrollPosition);\n }\n this.$el.parent('.tingle-modal').removeClass('tingle-modal--visible');\n }\n\n events () {\n $('body').on('click', '.tingle-modal', (e) => {\n if ($(e.target).hasClass('tingle-modal') || !$(e.target).closest(this.classToPreventHide)) {\n var newModalType = $(e.target).data('modalType') || null;\n this.hide(newModalType);\n e.stopPropagation();\n }\n });\n $('body').on('click', '.modal-close', (e) => {\n var newModalType = $(e.target).data('modalType') || null;\n this.hide(newModalType);\n e.stopPropagation();\n });\n\n if (!this.toPropagateClick) {\n $('body').on('click', this.selector, (e) => {\n e.stopPropagation();\n });\n }\n }\n};\n\nexport {\n newModal,\n newModalFromSelector,\n newModalFromString,\n newModalWithOptions,\n ModalShowHide,\n newModalWithSelector\n};\n","!function(t,o){\"function\"==typeof define&&define.amd?define(o):\"object\"==typeof exports?module.exports=o():t.tingle=o()}(this,function(){function t(t){var o={onClose:null,onOpen:null,beforeOpen:null,beforeClose:null,stickyFooter:!1,footer:!1,cssClass:[],closeLabel:\"Close\",closeMethods:[\"overlay\",\"button\",\"escape\"]};this.opts=r({},o,t),this.init()}function o(){this.modalBoxFooter&&(this.modalBoxFooter.style.width=this.modalBox.clientWidth+\"px\",this.modalBoxFooter.style.left=this.modalBox.offsetLeft+\"px\")}function e(){this.modal=document.createElement(\"div\"),this.modal.classList.add(\"tingle-modal\"),0!==this.opts.closeMethods.length&&this.opts.closeMethods.indexOf(\"overlay\")!==-1||this.modal.classList.add(\"tingle-modal--noOverlayClose\"),this.modal.style.display=\"none\",this.opts.cssClass.forEach(function(t){\"string\"==typeof t&&this.modal.classList.add(t)},this),this.opts.closeMethods.indexOf(\"button\")!==-1&&(this.modalCloseBtn=document.createElement(\"button\"),this.modalCloseBtn.classList.add(\"tingle-modal__close\"),this.modalCloseBtnIcon=document.createElement(\"span\"),this.modalCloseBtnIcon.classList.add(\"tingle-modal__closeIcon\"),this.modalCloseBtnIcon.innerHTML=\"×\",this.modalCloseBtnLabel=document.createElement(\"span\"),this.modalCloseBtnLabel.classList.add(\"tingle-modal__closeLabel\"),this.modalCloseBtnLabel.innerHTML=this.opts.closeLabel,this.modalCloseBtn.appendChild(this.modalCloseBtnIcon),this.modalCloseBtn.appendChild(this.modalCloseBtnLabel)),this.modalBox=document.createElement(\"div\"),this.modalBox.classList.add(\"tingle-modal-box\"),this.modalBoxContent=document.createElement(\"div\"),this.modalBoxContent.classList.add(\"tingle-modal-box__content\"),this.modalBox.appendChild(this.modalBoxContent),this.opts.closeMethods.indexOf(\"button\")!==-1&&this.modal.appendChild(this.modalCloseBtn),this.modal.appendChild(this.modalBox)}function s(){this.modalBoxFooter=document.createElement(\"div\"),this.modalBoxFooter.classList.add(\"tingle-modal-box__footer\"),this.modalBox.appendChild(this.modalBoxFooter)}function i(){this._events={clickCloseBtn:this.close.bind(this),clickOverlay:l.bind(this),resize:this.checkOverflow.bind(this),keyboardNav:n.bind(this)},this.opts.closeMethods.indexOf(\"button\")!==-1&&this.modalCloseBtn.addEventListener(\"click\",this._events.clickCloseBtn),this.modal.addEventListener(\"mousedown\",this._events.clickOverlay),window.addEventListener(\"resize\",this._events.resize),document.addEventListener(\"keydown\",this._events.keyboardNav)}function n(t){this.opts.closeMethods.indexOf(\"escape\")!==-1&&27===t.which&&this.isOpen()&&this.close()}function l(t){this.opts.closeMethods.indexOf(\"overlay\")!==-1&&!d(t.target,\"tingle-modal\")&&t.clientX=t},t.prototype.checkOverflow=function(){this.modal.classList.contains(\"tingle-modal--visible\")&&(this.isOverflow()?this.modal.classList.add(\"tingle-modal--overflow\"):this.modal.classList.remove(\"tingle-modal--overflow\"),!this.isOverflow()&&this.opts.stickyFooter?this.setStickyFooter(!1):this.isOverflow()&&this.opts.stickyFooter&&(o.call(this),this.setStickyFooter(!0)))},{modal:t}});","/**\n * Remove all validation. Should be called every time before revalidating form\n * @param {element} form - Form to be cleared\n * @returns {void}\n */\nconst clearFormErrors = (form) => {\n $(form).find('.form-control.is-invalid').removeClass('is-invalid');\n $(form).find('.login-form-error').empty();\n $(form).find('.login-form-error').removeClass('login-form-error-block');\n $(form)\n .find('.login-form-error-generic')\n .removeClass('login-form-error-block')\n .addClass('hidden');\n};\n\n// If ja-JP language set, swap name and last name input form\nconst swapFirstLastName = () => {\n if ($('meta[http-equiv=content-language]').attr('content') != 'ja-JP') {\n return;\n }\n\n var firstNameIdList = [\n 'shippingFirstName', // 'Checkout' page\n 'nameformemail', // 'Send us an e-mail' page\n 'registration-form-fname', // 'Register' page\n 'billingFirstName', // 'Edit Billing' page\n 'firstName', // 'Add Address' page\n 'name-frm', // 'Fiscal code calc' modal\n ];\n\n var lastNameIdList = [\n 'shippingLastName',\n 'secondnameformemail',\n 'registration-form-lname',\n 'billingLastName',\n 'lastName',\n 'surname-frm',\n ];\n\n for (var i = 0; i < firstNameIdList.length; i++) {\n var firstNameId = firstNameIdList[i];\n var lastNameId = lastNameIdList[i];\n\n // Skip to next loop if one input doesn't exist\n if (!$('#' + firstNameId).length || !$('#' + lastNameId).length) {\n continue;\n }\n\n // Check two inputs are next to each other\n if (\n $('#' + firstNameId)\n .parents('.cell')\n .next('.cell')\n .find('#' + lastNameId)\n .length\n ) {\n $('#' + lastNameId)\n .closest('.cell')\n .after($('#' + firstNameId).closest('.cell'));\n\n // Adjust padding on 'Register' page\n if (i == 2) {\n $('#' + firstNameId)\n .parents('.register-form-final-padding-right')\n .removeClass('register-form-final-padding-right')\n .addClass('register-form-final-padding-left');\n $('#' + lastNameId)\n .parents('.register-form-final-padding-left')\n .removeClass('register-form-final-padding-left')\n .addClass('register-form-final-padding-right');\n }\n }\n }\n};\n\nexport const addInputClearIcon = (inputItem) => {\n var $inputFieldContainer = $(inputItem).closest(\n '.form-fields-item__label:not(.form-fields-item__label--select)'\n );\n var clearIconTopPos =\n $(inputItem).outerHeight() / 2 +\n ($('.form-fields-item__input-label', $inputFieldContainer).length > 0\n ? $('.form-fields-item__input-label', $inputFieldContainer).outerHeight(true)\n : 0);\n\n if ($inputFieldContainer.find('.form-fields-item__clearIcon').length === 0) {\n $inputFieldContainer.append('');\n }\n $('.form-fields-item__clearIcon', $inputFieldContainer).css('top', clearIconTopPos);\n\n if (inputItem.value !== '') {\n $(inputItem).addClass('cc-isPrefilled');\n }\n\n $(inputItem)\n .on('focus', function () {\n $inputFieldContainer.addClass('focused');\n $(this).removeClass('cc-isPrefilled');\n })\n .on('blur', function () {\n $inputFieldContainer.removeClass('focused');\n });\n};\nclass FormHelpers {\n init(formElement, payload) {\n // clear form validation first\n clearFormErrors(formElement);\n $('.alert', formElement).remove();\n\n // Chosen select\n if (Foundation.MediaQuery.atLeast('medium')) {\n const selects = $('select.chosen, select.custom-select');\n selects.chosen({ disable_search: true });\n selects.each(function () {\n const ariaLabel = $(this).attr('aria-label');\n \n $(this).next('.chosen-container')\n .find('.chosen-search-input')\n .attr('aria-label', ariaLabel);\n });\n }\n\n if (typeof payload === 'object' && payload.fields) {\n Object.keys(payload.fields).forEach(function (key) {\n if (payload.fields[key]) {\n var feedbackElement = $(formElement)\n .find('[name=\"' + key + '\"]')\n .parent()\n .children('.invalid-feedback');\n\n if (feedbackElement.length > 0) {\n if (Array.isArray(payload[key])) {\n feedbackElement.html(payload.fields[key].join('
'));\n } else {\n feedbackElement.html(payload.fields[key]);\n }\n feedbackElement.siblings('.form-control').addClass('is-invalid');\n feedbackElement.show();\n }\n }\n });\n }\n if (payload && payload.error) {\n $(formElement).find('.login-form-error').html(payload.error.join('
'));\n $(formElement).find('.login-form-error').addClass('login-form-error-block');\n }\n\n $('input[type=text], input[type=email], input[type=number]').each(function (index, inputItem) {\n if ($(inputItem).attr('name') !== 'q') {\n addInputClearIcon(inputItem);\n }\n });\n\n $('.form-fields-item__clearIcon').on('click touchstart', function (e) {\n $(e.currentTarget).siblings('.form-fields-item__input-field').val('');\n });\n\n swapFirstLastName();\n }\n\n /**\n * Display error messages and highlight form fields with errors.\n * @param {string} parentSelector - the form which contains the fields\n * @param {Object} fieldErrors - the fields with errors\n */\n loadFormErrors(parentSelector, fieldErrors) {\n // eslint-disable-line\n // Display error messages and highlight form fields with errors.\n $.each(fieldErrors, (attr) => {\n $('*[name=' + attr + ']', parentSelector)\n .addClass('is-invalid')\n .siblings('.invalid-feedback')\n .html(fieldErrors[attr])\n .show();\n });\n if (fieldErrors.length) {\n $(`*[name=${fieldErrors[0]}]`).trigger('focus');\n }\n }\n\n /**\n * Clear the form errors.\n * @param {string} parentSelector - the parent form selector.\n */\n clearPreviousErrors(parentSelector) {\n $(parentSelector).find('.form-control.is-invalid').removeClass('is-invalid');\n $('.error-message').hide();\n }\n\n handleAmexNumber(cardFieldSelector, cardTypeSelector) {\n var cleave = new Cleave(cardFieldSelector, {\n creditCard: true,\n onCreditCardTypeChanged: (type) => {\n const creditCardTypes = {\n amex: 'Amex',\n };\n\n const cardType =\n creditCardTypes[\n Object.keys(creditCardTypes).indexOf(type) > -1 ? type : 'unknown'\n ];\n $(cardTypeSelector).val(cardType);\n $('.card-number-wrapper').attr('data-type', type);\n if (type === 'visa' || type === 'mastercard' || type === 'discover') {\n $('#securityCode').attr('maxlength', 3);\n } else {\n $('#securityCode').attr('maxlength', 4);\n }\n },\n });\n\n $(cardFieldSelector).data('cleave', cleave);\n }\n handleCreditCardNumber(cardFieldSelector, cardTypeSelector) {\n var cleave = new Cleave(cardFieldSelector, {\n creditCard: true,\n onCreditCardTypeChanged: (type) => {\n const creditCardTypes = {\n visa: 'Visa',\n mastercard: 'Master Card',\n amex: 'Amex',\n discover: 'Discover',\n jcb: 'jcb',\n diners: 'diners',\n unknown: 'Unknown',\n };\n\n const cardType =\n creditCardTypes[\n Object.keys(creditCardTypes).indexOf(type) > -1 ? type : 'unknown'\n ];\n $(cardTypeSelector).val(cardType);\n $('.card-number-wrapper').attr('data-type', type);\n if (type === 'visa' || type === 'mastercard' || type === 'discover') {\n $('#securityCode').attr('maxlength', 3);\n } else {\n $('#securityCode').attr('maxlength', 4);\n }\n },\n });\n\n $(cardFieldSelector).data('cleave', cleave);\n }\n\n serializeData(form, wasAmexSelected) {\n const serializedArray = form.serializeArray();\n\n serializedArray.forEach((item) => {\n if (item.name.indexOf('cardNumber') > -1) {\n if (wasAmexSelected === true) {\n item.value = $('#cardNumberAmex').data('cleave').getRawValue(); // eslint-disable-line\n } else {\n item.value = $('#cardNumber').data('cleave').getRawValue(); // eslint-disable-line\n }\n }\n });\n\n return $.param(serializedArray);\n }\n}\n\nconst formHelpers = new FormHelpers();\nexport default formHelpers;\n","/**\n * Core SFRA function for run everything everywhere\n * @param {Function || Object} include - stuff to run\n */\nconst processInclude = (include) => {\n if (typeof include === 'function') {\n include();\n } else if (typeof include === 'object') {\n Object.keys(include).forEach(function (key) {\n if (typeof include[key] === 'function') {\n include[key]();\n }\n });\n }\n};\n\n// Enqueues tasks to be executed afterwards\nfunction enqueueTask(task) {\n window.requestAnimationFrame(task);\n}\n\n/**\n * Parses the html for a modal window\n * @param {string} html - representing the body and footer of the modal window\n *\n * @return {Object} - Object with properties body and footer.\n */\nconst parseHtml = (html, map) => {\n const el = document.createElement('div');\n el.innerHTML = html;\n\n let htmlMap = {};\n for (var key in map) {\n if (map.hasOwnProperty(key)) {\n htmlMap[key] = el.querySelector(map[key]);\n }\n }\n\n return htmlMap;\n};\n\n/**\n * appends params to a url\n * @param {string} url - Original url\n * @param {Object} params - Parameters to append\n * @returns {string} result url with appended parameters\n */\nconst appendToUrl = (url, params) => {\n var newUrl = url;\n newUrl +=\n (newUrl.indexOf('?') !== -1 ? '&' : '?') +\n Object.keys(params)\n .map(function (key) {\n return key + '=' + encodeURIComponent(params[key]);\n })\n .join('&');\n\n return newUrl;\n};\n\nconst lockScroll = () => {\n $('body, html').css('overflow-y', 'hidden');\n};\n\nconst unlockScroll = () => {\n $('body, html').css('overflow-y', '');\n};\n\n/**\n * function for force lock scroll when open a modal or a drawer.\n * CAN CREATE SOME ISSUE WITH TOUCH EVENT - CHECK ON REAL DEVICE\n * the event is for prevent scrolling in iOS device\n */\nfunction forceLockScroll() {\n $('body, html,.page')\n .css({'overflow-y': 'hidden', 'touch-action': 'none'})\n .on('touchmove', preventDefault);\n}\n\nfunction forceUnlockScroll() {\n $('body, html,.page')\n .css({'overflow-y': '', 'touch-action': ''})\n .off('touchmove', preventDefault);\n}\n\nfunction preventDefault(e) {\n e.preventDefault();\n}\n\nconst cookieExists = (name) => {\n return document.cookie.split(';').filter((item) => {\n return item.trim().indexOf(`${name}=`) === 0;\n }).length;\n};\n\nconst createCookie = (name, value = false, days = 0) => {\n var expires;\n if (days) {\n var date = new Date();\n date.setTime(date.getTime() + days * 24 * 60 * 60 * 1000);\n expires = '; expires=' + date.toGMTString();\n } else {\n expires = '';\n }\n document.cookie = name + '=' + value + expires + '; path=/';\n};\n\nconst getCookie = (name) => {\n var value = '; ' + document.cookie;\n var parts = value.split('; ' + name + '=');\n if (parts.length == 2) return parts.pop().split(';').shift();\n return '';\n};\n\nconst deleteCookie = (name) => {\n document.cookie = name + '=; Path=/; Expires=Thu, 01 Jan 1970 00:00:01 GMT;';\n};\n\nconst isTouchDevice = () => {\n return (\n 'ontouchstart' in window || navigator.maxTouchPoints > 0 || navigator.msMaxTouchPoints > 0\n );\n};\n\n/**\n * Generic Ajax Call\n * @param {string} url - url for the ajax call\n * @param {string} method - default GET (is possible to use POST,PUT)\n * @param {object} data - use in POST method\n * @param {boolean} hideSpinner - default false, use true to hide the spinner\n * @returns Promise with the response of the ajax call\n */\nfunction genericAjaxCall(url, method = 'GET', data = {}, hideSpinner = false) {\n if (!url) {\n console.error('Missing Url in ajax call');\n return;\n }\n if (hideSpinner !== true) {\n $.spinner().start();\n }\n return new Promise((resolve, reject) => {\n $.ajax({\n url: url,\n method: method,\n data: data,\n success: function (response) {\n if (hideSpinner !== true) {\n $.spinner().stop();\n }\n resolve(response);\n },\n error: function (error) {\n if (hideSpinner !== true) {\n $.spinner().stop();\n }\n console.error(error);\n reject(error);\n },\n });\n });\n}\n\nexport {\n appendToUrl,\n cookieExists,\n createCookie,\n deleteCookie,\n enqueueTask,\n forceLockScroll,\n forceUnlockScroll,\n genericAjaxCall,\n getCookie,\n isTouchDevice,\n lockScroll,\n parseHtml,\n preventDefault,\n processInclude,\n unlockScroll,\n};\n","import { ModalShowHide } from '../components/modal';\n\nclass SizePanel {\n #mobileSizeModal;\n Types = {\n ADDTOCART: 'add_to_cart',\n ADDTOCART_BUNDLE: 'add_to_cart_bundle',\n PERSONALIZE: 'personalize',\n WISHILIST: 'wishlist',\n SMARTGIFT: 'smartgift'\n }\n\n init (idName = '#size-panel-mobile') {\n this.idName = idName\n this.#onPanelOpenerClick();\n this.#onNotifyMeSizeClicked();\n this.#onCloseSizeModalMobile();\n this.#mobileSizeModal = new ModalShowHide(this.idName);\n this.#mobileSizeModal.hide();\n }\n\n openSizePanel (operation) {\n if (Foundation.MediaQuery.atLeast('large')) {\n $('.js-page-size-box').addClass('cc-sizeBox-isOpen');\n } else {\n this.#mobileSizeModal.show();\n }\n $(this.idName).data('operation', operation);\n if (operation === this.Types.ADDTOCART_BUNDLE) {\n let $sizeElements = $(\"[data-attr='size'] input,[data-attr='size-mobile'] input\");\n let bundleQuantity = $('.js-add-to-cart-multipack').data('bundle-quantity');\n $sizeElements.each(function (element){\n if(parseInt($(this).attr('data-allocation'), 10) < parseInt(bundleQuantity, 10)) {\n $(this).closest('label').addClass('cc-no-bundle');\n }\n })\n } else {\n $('.cc-no-bundle').removeClass('cc-no-bundle');\n }\n if(operation === this.Types.WISHILIST) {\n $('.notifyMe,.wishlistOnly').addClass('select-size-for-wishlist');\n } else {\n $('.notifyMe,.wishlistOnly').removeClass('select-size-for-wishlist');\n }\n }\n\n #closeSizePanel () {\n if (Foundation.MediaQuery.atLeast('large')) {\n $('.pdp-size-box').removeClass('cc-sizeBox-isOpen');\n } else {\n this.#mobileSizeModal.hide();\n }\n $('.pdp-size-box .js-sizeBox-openPanel').removeClass('cc-sizeBox-openPanel_error');\n $('#newsletter-error-msg').hide();\n $(this.idName).data('operation', '');\n $('.notifyMe,.wishlistOnly').removeClass('select-size-for-wishlist');\n $('.cc-no-bundle').removeClass('cc-no-bundle');\n }\n\n #onPanelOpenerClick () {\n $('.pdp-size-box .js-sizeBox-openPanel').on('click', e => {\n if ($('.pdp-size-box').hasClass('cc-sizeBox-isOpen')) {\n this.#closeSizePanel();\n } else {\n this.openSizePanel();\n }\n });\n $('.js-pdpStickyBar-size-openPanel').on('click', e => {\n if ($('.js-pdpStickyBar-select').hasClass('cc-sizeBox-isOpen')) {\n $('.js-pdpStickyBar-select').removeClass('cc-sizeBox-isOpen');\n } else {\n $('.js-pdpStickyBar-select').addClass('cc-sizeBox-isOpen');\n }\n });\n }\n\n afterSizeSelection (data, type) {\n let operation = $(this.idName).data('operation');\n this.#closeSizePanel();\n let stopSpinner = true;\n let selectedSize = $('[data-attr=\"size\"] input:checked');\n if (!selectedSize.length) {\n $('.pdp-size-box').removeClass('size-selected');\n return stopSpinner;\n } else {\n $('#newsletter-error-msg').hide();\n }\n if (type !== 'size') {\n return stopSpinner;\n }\n let sizeDisplayValue = selectedSize.closest('label').find('.js-size-button__span').text();\n $('.pdp-size-box .js-sizeBox-openPanel').attr('aria-invalid', 'false');\n $('.pdp-size-box .selected-size-value').text(sizeDisplayValue);\n $('.pdp-size-box').addClass('size-selected');\n if ($('.js-add-to-cart-multipack').length > 0) {\n let bundleQuantity = $('.js-add-to-cart-multipack').data('bundle-quantity');\n if(parseInt($(selectedSize).attr('data-allocation'), 10) < parseInt(bundleQuantity, 10)) {\n $('.js-add-to-cart-multipack').attr('disabled', true);\n } else {\n $('.js-add-to-cart-multipack').removeAttr('disabled');\n }\n }\n\n stopSpinner = false;\n switch (operation) {\n case this.Types.ADDTOCART:\n $('#add-to-cart-cta-pdp').trigger('click');\n break;\n case this.Types.ADDTOCART_BUNDLE:\n $('#add-to-cart-multipack-cta-pdp').trigger('click');\n break;\n case this.Types.PERSONALIZE:\n $('#personalizeButton .persButt').trigger('click');\n break\n case this.Types.WISHILIST:\n $('body').trigger('wishlist:add-pid', {pid: data.product.id});\n break;\n case this.Types.SMARTGIFT:\n $('.add-to-cart-actions .js-smart-gift').trigger('click');\n $('#smartgiftButton').trigger('click');\n break;\n default:\n stopSpinner = true;\n }\n return stopSpinner;\n }\n\n #onNotifyMeSizeClicked () {\n const _self = this;\n $('.notifyMe,.wishlistOnly').on('click', (e) => {\n if (!$(e.currentTarget).hasClass('select-size-for-wishlist')) {\n return;\n }\n e.preventDefault();\n e.stopPropagation();\n $.spinner().start();\n const infoURL = $(e.currentTarget).closest('label').find('input').data('url');\n $.ajax({\n url: infoURL,\n type: 'get',\n dataType: 'json',\n success: function (data) {\n if (data.product.readyToOrder) {\n if ($(e.currentTarget).hasClass('wishlistOnly')) {\n let sizeDisplayValue = $(e.currentTarget).closest('label').find('.size-list-item-display-value').text();\n $('.pdp-size-box .selected-size-value').text(sizeDisplayValue);\n $('.pdp-size-box').addClass('size-selected');\n }\n const pid = encodeURIComponent(data.product.id)\n $('body').trigger('wishlist:add-pid', {pid: pid});\n } else {\n $.spinner().stop();\n _self.#closeSizePanel();\n }\n },\n error: function () {\n $.spinner().stop();\n _self.#closeSizePanel();\n }\n });\n });\n\n $('body').on('wishlist:update', () => {\n $.spinner().stop();\n _self.#closeSizePanel();\n });\n }\n\n #onCloseSizeModalMobile () {\n const _self = this;\n $('body').on('click', '.size-selector-mobile-modal', () => {\n _self.#closeSizePanel();\n });\n }\n}\n\nconst sizePanel = new SizePanel();\nexport default sizePanel;\n","'use strict';\n\nvar testEnabled = false;\n\nlet productGenderMap = {\n 1: 'Woman',\n 2: 'Man',\n 3: 'Girl',\n 4: 'Boy',\n 5: 'Unisex',\n 6: 'Baby'\n};\n\nlet brandsMapping = {\n 'CALZEDONIA': 'clz',\n 'INTIMISSIMI': 'int',\n 'TEZENIS': 'tzn',\n 'FALCONERI': 'flc',\n 'SIGNORVINO': 'sgv',\n 'ATELIER_EME': 'eme'\n};\n\nvar ListType = {\n 'listing': {\n 'class': 'category',\n 'value': 'listing',\n 'associatedObject': '.search-results'\n },\n 'wishlist': {\n 'class': 'wishlist-container',\n 'value': 'wishlist',\n 'associatedObject': '.wishlistItemCards'\n },\n 'search': {\n 'class': 'search',\n 'value': 'search',\n 'associatedObject': '.search-results'\n },\n 'completeYourLook': {\n 'class': 'completeYourLook',\n 'value': 'complete_your_look',\n 'associatedObject': '.completeYourLookContainer'\n },\n 'recentlyViewed': {\n 'class': 'recentlyViewed',\n 'value': 'recently_viewed',\n 'associatedObject': '.recentlyViewedContainer'\n },\n 'suggestedProducts': {\n 'class': 'suggestedProducts',\n 'value': 'suggested_products',\n 'associatedObject': '.suggestedProductsContainer'\n },\n 'filteredProducts': {\n 'class': 'filteredProducts',\n 'value': 'filter_applied',\n 'associatedObject': '.filteredProducts'\n },\n 'bestSellers': {\n 'class': 'bestSellers',\n 'value': 'best_sellers',\n 'associatedObject': '.bestSellers'\n },\n 'cmBestSellers': {\n 'class': 'cmBestSellers',\n 'value': 'best_sellers',\n 'associatedObject': '.cm-bestsellerCarousel-carouselWrapper .cm-carouselCustom.js-plp-productGrid'\n },\n 'sortDecreasing': {\n 'class': 'sortDecreasing',\n 'value': 'sorting_decreasing_price',\n 'associatedObject': '.sortDecreasing'\n },\n 'sortIncreasing': {\n 'class': 'sortIncreasing',\n 'value': 'sorting_increasing_price',\n 'associatedObject': '.sortIncreasing'\n },\n 'newArrivals': {\n 'class': 'newArrivals',\n 'value': 'new_arrivals',\n 'associatedObject': '.newArrivals'\n },\n 'cmNewArrivals': {\n 'class': 'cmNewArrivals',\n 'value': 'new_arrivals',\n 'associatedObject': '.cm-productCarousel-cardWrp.cm-carouselCustom'\n },\n 'completeYourLookMiniCart': {\n 'class': 'completeYourLookMiniCart',\n 'value': 'complete_your_look_minicart',\n 'associatedObject': '.miniCartCrossSellContainer-carousel'\n },\n 'js-suggestedForYou': {\n 'class': 'js-suggestedForYou',\n 'value': 'suggested_for_you',\n 'associatedObject': '.js-slotCarousel_suggestedProducts-carousel'\n },\n 'js-completeThePromo': {\n 'class': 'completeThePromo',\n 'value': 'complete_your_look',\n 'associatedObject': '.js-completeThePromoContainer'\n },\n 'js-youMayAlsoLike': {\n 'class': 'js-youMayAlsoLike',\n 'value': 'you_may_also_like',\n 'associatedObject': '.js-youMayAlsoLikeContainer'\n }\n};\n\nfunction getProductGender (product) {\n if (product.sapCategoryCode) {\n let categoryCode = product.sapCategoryCode;\n return productGenderMap[parseInt(categoryCode[categoryCode.length - 1])];\n }\n return '';\n}\n\nfunction insertParam (key, value) {\n key = encodeURI(key); value = encodeURI(value);\n\n var kvp = document.location.search.substr(1).split('&');\n\n var i = kvp.length; var x; while (i--) {\n x = kvp[i].split('=');\n\n if (x[0] === key) {\n x[1] = value;\n kvp[i] = x.join('=');\n break;\n }\n }\n\n if (i < 0) { kvp[kvp.length] = [key, value].join('='); }\n\n // this will reload the page, it's likely better to store this until finished\n document.location.search = kvp.join('&');\n}\n\nfunction hasParam (key) {\n key = encodeURI(key);\n\n return document.location.search.substr(1).indexOf(key) !== -1;\n}\n\nfunction getSkuCodes (sku) {\n if (sku.length >= 13) {\n let style = sku.substring(0, 9).trim();\n let color = sku.substring(9, 13).trim();\n let size = sku.substring(13).trim().replace('~', '/');\n return { id: style, color: color, size: size };\n } else {\n let color = sku.split('_')[1];\n return { id: sku, color: color };\n }\n}\n\nfunction formatStringForAnalytics (str) {\n return ('' + str).split(' ').join('_').toLowerCase().replace(/-/g, '_');\n}\n\nfunction formatStringProductPropertyIfExists (product, property, avoidFormatting = false) {\n if (property in product) {\n if (property === 'item_sfcc') {\n product[property] = '' + getFormatSkuForAnalytics(product[property]);\n } else if (avoidFormatting) {\n product[property] = '' + product[property];\n } else {\n product[property] = formatStringForAnalytics(product[property]);\n }\n }\n return product;\n}\n\n/* function formatStringProductPricePropertyIfExists (product, property, avoidFormatting = false) {\n if (property in product) {\n if (avoidFormatting) {\n product[property] = '' + product[property];\n } else {\n product[property] = formatStringForAnalytics(product[property]);\n }\n if (product['discount'] && product['discount'] < 0) {\n product[property] = '0.00';\n product['discount'] = 0.00;\n }\n }\n return product;\n} */\n\nfunction formatStringProductSalePropertyIfExists (product, property, avoidFormatting = false) {\n if (property in product) {\n if (avoidFormatting) {\n product[property] = '' + product[property];\n } else {\n product[property] = formatStringForAnalytics(product[property]);\n }\n if (product['discount'] && parseFloat(product['discount'])) {\n product[property] = 'yes';\n }\n }\n return product;\n}\n\nfunction formatFloatProductPropertyIfExists (product, property) {\n if (property in product) {\n product[property] = (product[property] <= 0) ? 0.00 : parseFloat(product[property]);\n }\n return product;\n}\n\nfunction formatIntegerForAnalytics (value) {\n return parseInt(value);\n}\n\nfunction formatIntegerProductPropertyIfExists (product, property) {\n if (property in product) {\n product[property] = formatIntegerForAnalytics(product[property]);\n }\n return product;\n}\n\nfunction stringOrNotAvailable (s) {\n return (s !== null && typeof s !== 'undefined' && String(s)) || 'not_available';\n}\n\nfunction numberOrZero (n) {\n return parseFloat(n) || 0;\n}\n\nfunction getStringAnalyticsValueFromStorage (key) {\n return stringOrNotAvailable(window.sessionStorage.getItem(key));\n}\n\nfunction getNumberAnalyticsValueFromStorage (key) {\n return numberOrZero(window.sessionStorage.getItem(key));\n}\n\nfunction getFormatSkuForAnalytics (sku) {\n let id, color, size, formattedSku;\n if (sku.toLowerCase().indexOf('color') !== -1) { // variant group\n id = sku.split('_')[0].trim();\n color = sku.split('_')[2].trim();\n formattedSku = id + '_' + color;\n } else {\n if (sku.match('[^_]+_[^_]+_[^_]+')) {\n return sku.toUpperCase();\n }\n let skuComponents = getSkuCodes(sku);\n id = skuComponents.id;\n color = skuComponents.color;\n size = skuComponents.size;\n if (color && size) {\n formattedSku = id + '_' + color + '_' + size;\n } else { // master product\n formattedSku = id;\n }\n }\n return formattedSku.toUpperCase().replace(/_+/g, '_');\n}\n\nmodule.exports = {\n\n isTestEnabled () {\n return testEnabled;\n },\n\n getAvailableListTypes (listingItemsBaseClass) {\n let types = [];\n\n for (let key in ListType) {\n if (ListType.hasOwnProperty(key)) {\n if ($(listingItemsBaseClass + '.' + ListType[key].class).length > 0) {\n let item = ListType[key];\n types.push(item);\n }\n }\n }\n\n return types;\n },\n\n getSkuComponents (sku) {\n return getSkuCodes(sku);\n },\n\n getProductGender (product) {\n return getProductGender(product);\n },\n\n getProductBaseInfo (product) {\n let id = '';\n let color = '';\n let size = '';\n\n let colorObject = null;\n\n let promo = 'no_promotion';\n if ('promotions' in product && product.promotions && product.promotions.length > 0) {\n promo = product.promotions.map(function (el) { return el.enabled ? el.id : null; }).filter(function (el) { return el !== null; }).join('-');\n } else if ('appliedPromotions' in product && product.appliedPromotions && product.appliedPromotions.length > 0) {\n promo = product.appliedPromotions.map(function (el) { return el.name; }).join('-');\n }\n\n if (product.productType === 'variant') {\n let components = getSkuCodes(product.id);\n id = components.id;\n color = components.color;\n size = components.size;\n\n for (let k in product.variationAttributes) {\n const variationAttribute = product.variationAttributes[k];\n if (variationAttribute.attributeId === 'color') {\n if ('values' in variationAttribute) {\n for (let j in variationAttribute.values) {\n if (variationAttribute.values[j].selected === true) {\n colorObject = variationAttribute.values[j];\n break;\n }\n }\n } else {\n colorObject = variationAttribute;\n }\n break;\n }\n }\n } else if (product.productType === 'variationGroup') {\n // in this case the user only chose the color, and not the size\n id = product.id.split('_')[0].trim();\n color = product.id.split('_')[2].trim();\n\n let selectedVariation;\n\n for (let k in product.variationAttributes) {\n const variationAttribute = product.variationAttributes[k];\n if (variationAttribute.attributeId === 'color') {\n for (let j in variationAttribute.values) {\n if (variationAttribute.values[j].selected === true) {\n colorObject = variationAttribute.values[j];\n break;\n }\n }\n }\n if (selectedVariation !== undefined) {\n break;\n }\n }\n }\n\n return {\n id: id,\n color: color,\n colorObject: colorObject,\n size: size,\n promo: promo\n };\n },\n\n formatProductForAnalytics (product) {\n product = formatStringProductPropertyIfExists(product, 'item_name');\n product = formatStringProductPropertyIfExists(product, 'item_brand');\n product = formatStringProductPropertyIfExists(product, 'item_list_name');\n product = formatStringProductPropertyIfExists(product, 'item_list_id');\n product = formatStringProductPropertyIfExists(product, 'item_variant', true);\n product = formatFloatProductPropertyIfExists(product, 'price');\n product = formatStringProductPropertyIfExists(product, 'item_category');\n product = formatStringProductPropertyIfExists(product, 'item_category2');\n product = formatStringProductPropertyIfExists(product, 'item_category3');\n product = formatStringProductPropertyIfExists(product, 'item_category4');\n product = formatStringProductPropertyIfExists(product, 'item_category5');\n product = formatIntegerProductPropertyIfExists(product, 'quantity');\n product = formatStringProductPropertyIfExists(product, 'size', true);\n product = formatStringProductSalePropertyIfExists(product, 'item_on_sale');\n product = formatStringProductPropertyIfExists(product, 'item_availability');\n product = formatStringProductPropertyIfExists(product, 'coupon');\n product = formatStringProductPropertyIfExists(product, 'item_color');\n product = formatStringProductPropertyIfExists(product, 'item_sfcc');\n product = formatStringProductPropertyIfExists(product, 'item_customization');\n product = formatStringProductPropertyIfExists(product, 'item_sustainable');\n product = formatFloatProductPropertyIfExists(product, 'discount');\n return product;\n },\n\n checkPage (str) {\n return window.location.href.toLowerCase().indexOf(str) !== -1;\n },\n\n // Formatting\n formatString (str) {\n return formatStringForAnalytics(str);\n },\n\n format4DigitNumber (number) {\n if (number < 0) {\n return '0000';\n } else if (number < 10) {\n return '000' + number;\n } else if (number < 100) {\n return '00' + number;\n } else if (number < 1000) {\n return '0' + number;\n }\n return number.toString();\n },\n\n // URL Parameters\n insertParameter (key, value) {\n insertParam(key, value);\n },\n existsParameter (key) {\n return hasParam(key);\n },\n\n // Push on DataLayer\n push (pushObject, log = true) {\n // eslint-disable-next-line\n dataLayer.push(pushObject);\n\n if (log && testEnabled) {\n console.info(pushObject);\n }\n },\n\n log (data, inline = false) {\n if (!testEnabled) {\n return;\n }\n if (inline) {\n console.info('Analytics: ' + data);\n } else {\n console.info('Analytics: ');\n console.info(data);\n }\n },\n\n getFormatSku (sku) {\n return getFormatSkuForAnalytics(sku);\n },\n\n formatNameForAnalytics (name) {\n if (!name) {\n return '';\n }\n let formattedPlus = name.toLowerCase().replace(/[+]/g, '_plus_');\n let formattedName = formattedPlus.replace(/\\W/g, '_');\n let analyticsName = formattedName.split('_').filter((el) => { return el; }).join('_');\n return analyticsName;\n },\n\n formatSkus (skus) {\n let formattedSkus = '';\n for (let i = 0; i < skus.length; i++) {\n let formattedSku = getFormatSkuForAnalytics(skus[i]).replace(/\\W/g, '_');\n if (i === 0) {\n formattedSkus += formattedSku;\n } else {\n formattedSkus += '-' + formattedSku;\n }\n }\n return formattedSkus;\n },\n\n getProductNameEngFromPdp () {\n let nameEng = $('.analytics.product').data('name');\n return nameEng;\n },\n\n getFormatedNewsletterPreferenceBrands (list) {\n let brandsStr = '';\n for (let brand of list) {\n brandsStr += brandsMapping[brand] + '-';\n }\n\n brandsStr = brandsStr.substring(0, brandsStr.length - 1);\n\n return brandsStr;\n },\n\n getListId (container, provider) {\n let list = '';\n if (container && $(container).parents('.analytics-mini-cart').length > 0) {\n list = 'minicart';\n } else if ($(container).parents('.js-site-search-suggestions-products').length > 0) { // Search results\n list = 'plp';\n } else if ($('.page[data-action=\"Product-Show\"]').length > 0) {\n list = 'pdp';\n } else if ($('.page[data-action=\"Search-Show\"]').length > 0) {\n list = $('.page.js-page-home-gender').length > 0 ? 'home' : 'plp';\n } else if ($('.page[data-action=\"Cart-Show\"]').length > 0 || $('.page[data-action=\"Checkout-Begin\"]').length > 0) {\n list = 'cart';\n } else if ($('.page[data-action=\"Wishlist-Show\"]').length > 0) {\n list = 'wishlist';\n }\n\n if (list && provider && (list === 'pdp' || list === 'home' || list === 'cart')) {\n list = `${provider}_${list}`;\n }\n\n return list;\n },\n\n getProductList () {\n let items = [];\n let container = $('.analytics.checkout.checkout-product');\n\n for (let i = 0; i < container.length; i++) {\n let obj = container.eq(i).data();\n\n // Fix values for MEC-30160\n if (obj.item_list_name === 'not_available') {\n obj.item_list_name = 'listing'\n }\n \n if (obj.item_list_id === 'not_available') {\n obj.item_list_id = 'pdp'\n }\n\n if (obj.id !== 'PERS_PROD') {\n obj['quantity'] = obj.quantity;\n obj['index'] = i;\n items.push(this.formatProductForAnalytics(obj));\n }\n }\n return items;\n },\n\n getGrandTotal () {\n return $('.analytics-totals').data('grand-total');\n },\n\n getAppliedCoupon () {\n const coupon = [];\n $('#couponCode.coupon-code-field--applied').val() && coupon.push($('#couponCode.coupon-code-field--applied').val());\n $('.analytics-shipping-discount').length && coupon.push('shipping_discount');\n $('.analytics-order-discount').length && coupon.push('order_discount');\n return coupon.join(',');\n },\n\n getUpsellingMessage () {\n let upsellingMessage = 'no_message';\n const vals = [];\n $('.analytics-message').each(function () {\n if (vals.indexOf($(this).data('analytics-type')) === -1) {\n vals.push($(this).data('analytics-type'));\n }\n });\n if (vals.length > 0) {\n upsellingMessage = vals.join('-');\n }\n localStorage.setItem('upsellingMessage', upsellingMessage);\n return upsellingMessage;\n },\n\n getBeginCheckoutData (context) {\n return {\n upselling_message: this.getUpsellingMessage(),\n currency: context.helperData.currency,\n value: this.getGrandTotal(),\n coupon: this.getAppliedCoupon(),\n items: this.getProductList()\n };\n },\n\n getTypeOfAccount () {\n let typeOfAccount = 'only_registration';\n if ($('.loyalty-flag:checked').length === 1) {\n typeOfAccount = 'profile_loyalty';\n }\n return typeOfAccount;\n },\n storeGtmData (data) {\n if (data && data.item_list_name && data.item_list_id && (data.index || data.index === 0)) {\n if (data.item_id && data.item_variant) {\n window.sessionStorage.setItem('GTM_' + data.item_id + '_color_' + data.item_variant, JSON.stringify({'item_list_name': data.item_list_name, 'item_list_id': data.item_list_id, 'index': data.index}));\n }\n // Adding values for color change event\n window.sessionStorage.setItem('GTM_item_list_name', data.item_list_name);\n window.sessionStorage.setItem('GTM_item_list_id', data.item_list_id);\n window.sessionStorage.setItem('GTM_index', data.index);\n }\n },\n getGtmData (data) {\n const GTMData = {};\n if (data && data.item_id && data.item_variant) {\n const GTMItem = JSON.parse(window.sessionStorage.getItem('GTM_' + data.item_id + '_color_' + data.item_variant)) || {};\n GTMData.item_list_name = stringOrNotAvailable(GTMItem.item_list_name);\n GTMData.item_list_id = stringOrNotAvailable(GTMItem.item_list_id);\n GTMData.index = numberOrZero(GTMItem.index);\n } else {\n GTMData.item_list_name = getStringAnalyticsValueFromStorage('GTM_item_list_name');\n GTMData.item_list_id = getStringAnalyticsValueFromStorage('GTM_item_list_id');\n GTMData.index = getNumberAnalyticsValueFromStorage('GTM_index');\n }\n return GTMData;\n },\n setBonusProductData ($container, index) {\n $container.data('item_list_name', 'free_product');\n $container.data('item_list_id', this.getListId());\n $container.data('index', index);\n $container.data('discount', $container.data('price'));\n $container.data('price', 0);\n }\n};\n","import NotifyHelper from './notify';\nimport SmartGiftHelper from './smartGiftHelper';\nimport { startCarouselTileImageFunction } from './productBox';\nimport { updatePrimaryImagesSlider } from './detail';\nimport sizePanel from './sizePanel';\nimport { addToCartFromListing } from './quickView.js';\nimport { newModalFromString } from '../components/modal';\nimport { runPersonalizationListener } from '../customize';\nimport { updateProductDetailUrl } from 'util/url';\nimport { createCookie } from '../util/common';\nimport { getGtmData } from '../analytics/helpers/helper';\nimport { handleWishlistContainer } from './wishlistHeart.js';\n\nconst isMiniCartOpen = () => {\n return localStorage.getItem('isMiniCartOpen') === 'true';\n};\n\nfunction isChooseBonusProductModalOpen () {\n return ($('.js-chooseBonusProductModal').length > 0);\n}\n\nfunction isQuickUpdateFromModal () {\n return $('.js-quickUpdateModal').length > 0;\n}\n\nconst isMobileDevice = () => {\n return !Foundation.MediaQuery.atLeast('large');\n};\n/**\n * Move close button inside modal content box\n */\nconst moveModalCloseButton = () => {\n var close = document.querySelector('.tingle-modal__close');\n var modalContent = document.querySelector('.tingle-modal-box__content');\n modalContent.appendChild(close);\n};\n\n/**\n * Retrieves the relevant pid value\n * @param {jquery} $el - DOM container for a given add to cart button\n * @return {string} - value to be used when adding product to cart\n */\nconst getPidValue = ($el) => {\n let pid;\n\n if ($('.quickview-modal').hasClass('tingle-modal--visible') && !$('.product-set').length) {\n pid = $('.quickview-modal').find('.product-quickview').data('pid');\n } else if ($('.product-set-detail').length || $('.product-set').length) {\n pid = $($el).closest('.product-detail').find('.product-id').text();\n } else if ($('.modal-size-show').length) {\n pid = $('.modal-size-show').find('.js-add-to-cart').data('pid');\n } else if (isMiniCartOpen()) {\n pid = $($el).data('pid');\n } else {\n pid = $('.product-detail:not(\".bundle-item\")').data('pid');\n }\n\n return pid;\n};\n\n/**\n * updates the product view when a product attribute of quickAdd is selected or deselected or when\n * changing quantity\n * @param {string} selectedValueUrl - the Url for the selected variation value\n * @param {jQuery} $productContainer - DOM element for current product\n * @param {string} type - type of filter selected\n */\nconst attributeSelectQuickAdd = (selectedValueUrl, $productContainer, type = '_', imagesShouldUpdate = true) => {\n if (selectedValueUrl) {\n $('body').trigger('product:beforeAttributeSelect', {\n url: selectedValueUrl,\n container: $productContainer\n });\n\n $.ajax({\n url: selectedValueUrl,\n method: 'GET',\n success: data => {\n handleVariantResponseQuickAdd(data, $productContainer, imagesShouldUpdate);\n updateOptions(data.product.options, $productContainer);\n updateQuantities(data.product.quantities, $productContainer);\n $productContainer.attr('data-pid', data.product.id);\n $productContainer.find('.add-to-cart-quick-add').attr('data-pid', data.product.id);\n $productContainer.find('.add-to-cart-quick-add').attr('data-quantity', data.product.selectedQuantity);\n if ($productContainer.find('.add-to-cart-quick-add').data('mustAdd') === true) {\n $productContainer.find('.add-to-cart-quick-add').trigger('click');\n } else {\n $productContainer.find('.js-panel-opener-size-quick-add').trigger('click');\n $.spinner().stop();\n }\n },\n error: () => {\n $.spinner().stop();\n }\n });\n }\n};\n\nconst activatePromoAnimationMessage = () => {\n $('.js-pdpPromo').removeClass('hide');\n};\n\nconst reactivatePromoAnimationMessage = (promotionId, pdpCalloutMsgText) => {\n $('.js-pdpPromo').attr('data-promotion-id', promotionId);\n $('.js-pdpPromo-message').html(pdpCalloutMsgText);\n activatePromoAnimationMessage();\n};\n\n/**\n * updates the product view when a product attribute is selected or deselected or when changing quantity\n * @param {string} selectedValueUrl - the Url for the selected variation value\n * @param {jQuery} $productContainer - DOM element for current product\n * @param {string} type - type of filter selected\n * @param {boolean} imagesShouldUpdate - update images on attribute selection\n * @param {boolean} ignoreCTA - add immediately to cart without clicking on CTA\n */\nconst attributeSelect = (selectedValueUrl, $productContainer, type = '_', imagesShouldUpdate = true, ignoreCTA = false) => {\n if (selectedValueUrl) {\n // destroyPrimaryImagesSlider();\n $productContainer.prevObject.analyticsPromotion = false;\n\n $('body').trigger('product:beforeAttributeSelect', {\n url: selectedValueUrl,\n container: $productContainer\n });\n\n $.ajax({\n url: selectedValueUrl,\n method: 'GET',\n success: data => {\n var isSize = data.variation.isSize;\n var isQuickViewModal = $productContainer.hasClass('product-quickview');\n\n if (isQuickViewModal && type !== 'color') {\n imagesShouldUpdate = false;\n }\n\n handleVariantResponse(data, $productContainer, imagesShouldUpdate, type);\n\n // Update PDP link if we are in QuickView and a color was selected\n if (type === 'color' && $('.quickview-modal').length) {\n let container = $('.quickview-modal').find('.see-product-details-link');\n container.attr('href', data.product.url);\n }\n\n handleVariationUrlsSelectSizeModal(data.variation.variationUrls);\n handlePromotionTag(data.product ,$productContainer);\n handleVariationUrlsSelectNotifyModal(data.product.variationAttributes[1].values);\n handleVariationComingSoonNotifyModal(data.product.variationAttributes[1].values);\n handleVariationComingSoon(data.product.comingSoon);\n handleVariationWishlistModal(data.product.variationAttributes[1].values);\n\n // here we check if the selected product has the size, if not we put a flag on isToLoad\n if (isSize == false) {\n $('#pidToAdd').attr('isToLoad', 'true');\n } else {\n $('#pidToAdd').attr('isToLoad', 'false');\n }\n $('.persButtonPdpPers').attr('disabled', false);\n $('#custom-page').attr('data-pid', data.product.id);\n $('.js-personalizeButtonCheckout').removeClass('disabled');\n $('.js-personalizeButtonCheckout').attr('disabled', false);\n updateOptions(data.product.options, $productContainer);\n updateQuantities(data.product.quantities, $productContainer);\n updateImageSaveForLater(data.product, $productContainer);\n if ($('.product-detail-keeper').length) {\n var pid = getPID(data.product);\n try {\n $($productContainer).find('.product-set').attr('data-pid', pid);\n } catch (e) {\n }\n $('.product-detail-keeper').attr('data-variant-pid', encodeURIComponent(pid));\n }\n\n if (isSize) {\n $('body').trigger('product:afterAttributeSelect', {\n data: data,\n container: $productContainer,\n type: type\n });\n }\n\n if (type === 'color') {\n if (data.product.promotions && data.product.promotions.length > 0) {\n const promoContainer = $('.js-promo-loyalty-message-pdp-underprice');\n const promoMessage = data.product.promotions[0].promoLoyaltyMessage;\n if (promoContainer && promoMessage && promoMessage.length) {\n promoContainer.html(promoMessage);\n } else {\n promoContainer.html('');\n }\n } else {\n $('.js-promo-loyalty-message-pdp-underprice').html('');\n }\n }\n\n const _updateInformation = (product) => {\n let selectorPrefix = '';\n if (product.variationAttributes[0].onSaleSelected || product.price.saleType) {\n selectorPrefix = '.onSaleContainer';\n } else {\n selectorPrefix = '.notOnSaleContainer';\n }\n\n $productContainer.find(selectorPrefix + ' .js-discount-msg').addClass('hidden');\n $productContainer.find(selectorPrefix + ' .js-promo-msg').addClass('hidden');\n\n if (product.price.discountValue) {\n $productContainer.prevObject.analyticsPromotion = true;\n $productContainer.find(selectorPrefix + ' .js-discount-msg')\n .html(`(${product.price.discountValue}%)`)\n .removeClass('hidden');\n if (product.promotions && product.promotions.length > 0) {\n if (product.promotions[0].calloutMsg) {\n $productContainer.find(selectorPrefix + ' .js-promo-msg')\n .html(product.promotions[0].calloutMsg)\n .removeClass('hidden');\n } else if (product.promotions[1] && product.promotions[1].calloutMsg) {\n $productContainer.find(selectorPrefix + ' .js-promo-msg')\n .html(product.promotions[1].calloutMsg)\n .removeClass('hidden');\n }\n }\n } else if (product.promotions && product.promotions.length > 0) {\n $productContainer.prevObject.analyticsPromotion = true;\n if (product.promotions[0].calloutMsg) {\n $productContainer.find(selectorPrefix + ' .js-promo-msg')\n .html(product.promotions[0].calloutMsg)\n .removeClass('hidden');\n } else if (product.promotions[1] && product.promotions[1].calloutMsg) {\n $productContainer.find(selectorPrefix + ' .js-promo-msg')\n .html(product.promotions[1].calloutMsg)\n .removeClass('hidden');\n }\n }\n };\n\n if (type !== 'size') {\n _updateInformation(data.product);\n }\n\n if ($('.modal-size-show').length) {\n $.spinner().stop();\n if (type === 'size') {\n $('body').trigger('quickBuy:addToCart', data);\n }\n }\n\n if ($('.js-customizePage').length > 0 && data.totalQuantityPrice) {\n $('.js-personalizePrice').text(data.totalQuantityPrice);\n }\n\n handleInexistentSizeQuickView(data);\n handleWishlistContainer(data.product.id);\n },\n error: function (err) {\n if (err.responseJSON.redirectUrl) {\n window.location.href = err.responseJSON.redirectUrl;\n } else {\n let current_url = window.location.pathname.split('/');\n var localized_error_page = window.location.protocol + '://' + window.location.host;\n for (var i = 0; i < current_url.length; i++) {\n if (current_url[i] !== 'product') {\n localized_error_page += '/' + current_url[i];\n } else {\n localized_error_page += '/404/';\n break;\n }\n }\n console.log('localized_error_page = ' + localized_error_page);\n window.location.href = localized_error_page;\n }\n $.spinner().stop();\n }\n }).then(function (data) {\n let stopSpinner = sizePanel.afterSizeSelection(data, type);\n if (stopSpinner) {\n $.spinner().stop();\n }\n if (ignoreCTA) {\n $('.js-prod-select-size-modal').find('button.js-add-to-cart').trigger('click');\n }\n if (type === 'color') {\n if (data.product.promotions.length === 0) {\n $('.js-pdpPromo').addClass('hide');\n } else if (data.product.promotions[0].id && data.product.promotions[0].id != $('.js-pdpPromo').attr('data-promotion-id')) {\n reactivatePromoAnimationMessage(data.product.promotions[0].id, data.product.promotions[0].pdpCalloutMsgText);\n } else {\n $('.js-pdpPromo').removeClass('hide');\n }\n }\n });\n }\n};\n\n/**\n * Retrieve contextual quantity selector\n * @param {jquery} $el - DOM container for the relevant quantity\n * @return {jquery} - quantity selector DOM container\n */\nconst getQuantitySelector = ($el) => {\n return $el && $('.set-items').length ?\n $($el).closest('.product-detail').find('.quantity-select') :\n $('.quantity-select');\n};\n\n/**\n * Retrieves the value associated with the Quantity pull-down menu\n * @param {jquery} $el - DOM container for the relevant quantity\n * @return {string} - value found in the quantity input\n */\nconst getQuantitySelected = ($el) => {\n let quantity = 1;\n if ($el.hasClass('js-add-to-cart-multipack') && $el.data('bundle-quantity')) {\n quantity = $el.data('bundle-quantity');\n } else if ($el.closest('.js-complete-your-promo-quick-view').length > 0) {\n quantity = $el.closest('.wrapper-inner-quick-bottom').find('.js-quick-quantity').val();\n } else if (getQuantitySelector($el).val()) {\n quantity = getQuantitySelector($el).val();\n }\n return quantity;\n};\n\n/**\n * Process the attribute values for an attribute that has image swatches\n *\n * @param {Object} attr - Attribute\n * @param {string} attr.id - Attribute ID\n * @param {Object[]} attr.values - Array of attribute value objects\n * @param {string} attr.values.value - Attribute coded value\n * @param {string} attr.values.url - URL to de/select an attribute value of the product\n * @param {boolean} attr.values.isSelectable - Flag as to whether an attribute value can be\n * selected. If there is no variant that corresponds to a specific combination of attribute\n * values, an attribute may be disabled in the Product Detail Page\n * @param {jQuery} $productContainer - DOM container for a given product\n */\nconst processSwatchValues = (attr, $productContainer) => {\n attr.values.forEach(attrValue => {\n const $attrValue = $productContainer.find(`[data-attr=\"${attr.id}\"] [data-attr-value=\"${attrValue.value}\"]`);\n const $swatchAnchor = $attrValue.parent();\n\n if (attrValue.selected) {\n $productContainer.find('.attribute-label').text(attrValue.id.toLowerCase() + ' - ' + attrValue.displayValue.toLowerCase());\n if ($('.js-pdpStickyBar-colorWrapper').length > 0) {\n $('.js-pdpStickyBar-colorWrapper .label-inside').text(attr.displayName + ': ' + attrValue.displayValue.toLowerCase() + ' - ' + attrValue.id.toLowerCase());\n $('.js-pdpStickyBar-colorWrapper img').attr('src', attrValue.images.swatch[0].url);\n $('.js-pdpStickyBar-colorWrapper img').attr('alt', attrValue.displayValue.toLowerCase() + ' - ' + attrValue.id.toLowerCase());\n }\n if ($attrValue[0]) {\n $productContainer.find(`[data-opener=\"${attr.id}\"] .attribute-selection`).html($attrValue[0].outerHTML);\n $attrValue.addClass('selected');\n }\n } else {\n $attrValue.removeClass('selected');\n }\n\n if (attrValue.url) {\n $swatchAnchor.attr('href', attrValue.url);\n } else {\n $swatchAnchor.removeAttr('href');\n }\n\n // Disable if not selectable\n $attrValue.removeClass('selectable unselectable soldout');\n $attrValue.addClass((attrValue.selectable || attrValue.isSoldout) ? 'selectable' : 'unselectable');\n if (attrValue.isSoldout) {\n $attrValue.addClass('soldout');\n }\n });\n};\n\n/**\n * Process attribute values associated with an attribute that does not have image swatches\n *\n * @param {Object} attr - Attribute\n * @param {string} attr.id - Attribute ID\n * @param {Object[]} attr.values - Array of attribute value objects\n * @param {string} attr.values.value - Attribute coded value\n * @param {string} attr.values.url - URL to de/select an attribute value of the product\n * @param {boolean} attr.values.isSelectable - Flag as to whether an attribute value can be\n * selected. If there is no variant that corresponds to a specific combination of attribute\n * values, an attribute may be disabled in the Product Detail Page\n * @param {jQuery} $productContainer - DOM container for a given product\n */\nconst processNonSwatchValues = (attr, $productContainer, variantType) => {\n const $attr = `[data-attr=\"${attr.id}\"]`;\n const $defaultOption = $productContainer.find(`${$attr} .select-${attr.id} option:first`);\n $defaultOption.attr('value', attr.resetUrl);\n $productContainer.find(`[data-opener=\"${attr.id}\"] .attribute-selection`).html('');\n\n $productContainer.find('.js-intProductDetail-size-item').addClass('hide');\n attr.values.forEach(attrValue => {\n if ($('.page').data('action') && $('.page').data('action').toLowerCase().indexOf('product-show') > -1 && $('#personalize-page') && !$productContainer.hasClass('js-complete-your-promo-quick-view')) {\n $productContainer = $('.js-intProductDetail');\n }\n const $attrValue = $productContainer.find(`${$attr} [data-attr-value=\"${attrValue.value}\"]`);\n const $attrValueMobile = $productContainer.find(`.size-panel-mobile-content [data-attr-value=\"${attrValue.value}_mobile\"]`);\n $attrValue.attr('value', attrValue.url).removeAttr('disabled');\n $attrValueMobile.attr('value', attrValue.variationUrl);\n if (!attrValue.selected) {\n $attrValueMobile.removeAttr('disabled');\n }\n $attrValue.attr('disabled', !attrValue.selectable);\n if (attrValue.isComingSoon && $productContainer.hasClass('product-quickview')) {\n $attrValue.attr('disabled', attrValue.isComingSoon);\n }\n\n if (attrValue.selected && attrValue.selectable && attrValue.id !== 'TU') {\n $productContainer.find(`[data-opener=\"${attr.id}\"] .attribute-selection`).html(attrValue.displayValue);\n $productContainer.find('.product-quickview').data('pid', attrValue.sku);\n }\n\n if (attrValue.selected && attrValue.selectable) {\n const selectedSizeSpan = $productContainer.find('.js-selected-size');\n\n if (selectedSizeSpan.length) {\n selectedSizeSpan.text(attrValue.displayValue);\n }\n }\n\n if ($attrValue.length > 1) {\n $attrValue.each((i, el) => {\n $(el).prop('checked', attrValue.selected && attrValue.selectable);\n });\n } else {\n $attrValue.prop('checked', attrValue.selected && attrValue.selectable);\n }\n\n if (variantType !== 'size') {\n if (!attrValue.selectable || attrValue.isComingSoon) {\n if ($('#isNotifyActive').val() == 'true') {\n $attrValue.siblings().addClass('notifyMe');\n $attrValueMobile.siblings().addClass('notifyMe');\n } else {\n $attrValue.siblings().addClass('wishlistOnly');\n $attrValueMobile.siblings().addClass('wishlistOnly');\n }\n } else {\n $attrValue.siblings().removeClass('notifyMe wishlistOnly');\n $attrValueMobile.siblings().removeClass('notifyMe wishlistOnly');\n }\n if (attrValue.lowAvailability) {\n $attrValue.siblings().addClass('low-stock');\n $attrValueMobile.siblings().addClass('low-stock');\n } else {\n $attrValue.siblings().removeClass('low-stock');\n $attrValueMobile.siblings().removeClass('low-stock');\n }\n }\n\n // Toggle size if disabled or not\n $attrValue.closest('label').toggleClass('hide', attrValue.disabled);\n $attrValueMobile.closest('label').toggleClass('hide', attrValue.disabled);\n\n // Toggle size in stickybar\n $('.js-pdpStickyBar').find('#' + $attrValue[0].id.replace('/', '\\\\/')).closest('label').toggleClass('hide', attrValue.disabled);\n\n // Same check on quick view mobile\n $attrValue.closest('.label-wrapper').toggleClass('hide', attrValue.disabled);\n\n // Toggle selectable size on cart quickview\n if ($('.quickview-modal').length) {\n $attrValue.closest('.boolean-field').toggleClass('cc-cartQuickView_selectedSize', attrValue.selected);\n }\n });\n\n // Update also size selection modal\n const $sizeSelectorContainer = $('#fis-select-size');\n attr.values.forEach(attrValue => {\n const $attrValue = $sizeSelectorContainer.find(`[data-attr-value=\"${attrValue.value}\"]`);\n $attrValue.attr('disabled', !attrValue.selectable);\n if (attrValue.isComingSoon && $productContainer.hasClass('product-quickview')) {\n $attrValue.attr('disabled', attrValue.isComingSoon);\n }\n\n if ($('#isNotifyActive').val() == 'true') {\n if (!attrValue.selectable || attrValue.isComingSoon) {\n $attrValue.addClass('notifyMe notifyPopup');\n $attrValue.find('.notifyIcon').removeClass('hide');\n } else {\n $attrValue.removeClass('notifyMe notifyPopup');\n $attrValue.find('.notifyIcon').addClass('hide');\n }\n } else {\n if (!attrValue.selectable) {\n $attrValue.addClass('wishlistOnly');\n } else {\n $attrValue.removeClass('wishlistOnly');\n }\n }\n\n // Toggle size if disabled or not\n $attrValue.parent('li').toggleClass('hide', attrValue.disabled);\n\n // TODO: improve check. Force size selection of quick add on PDP mobile\n if (!Foundation.MediaQuery.atLeast('large') && $productContainer.closest('.product-quickview').length) {\n $productContainer.find(`.mobile-attributes-container input[id=\"${attrValue.value}\"]`).prop('checked', attrValue.selected && attrValue.selectable);\n }\n });\n};\n\n/**\n * Routes the handling of attribute processing depending on whether the attribute has image\n * swatches or not\n *\n * @param {Object} attrs - Attribute\n * @param {string} attr.id - Attribute ID\n * @param {string} variantType - Size or Color selection\n * @param {jQuery} $productContainer - DOM element for a given product\n */\nconst updateAttrs = (attrs, $productContainer, variantType) => {\n // Currently, the only attribute type that has image swatches is Color.\n const attrsWithSwatches = ['color'];\n\n if ($('.js-personalizeButtonModal').attr('data-personalized') === 'true') {\n $productContainer = $('.fis-select-size');\n }\n\n attrs.forEach(attr => {\n if (attrsWithSwatches.indexOf(attr.attributeId) > -1) {\n processSwatchValues(attr, $productContainer);\n } else {\n processNonSwatchValues(attr, $productContainer, variantType);\n }\n });\n};\n\nconst updateScanTrustLink = (attr, $productContainer) => {\n let $productAuthenticity = $productContainer.find('.cc-details-authenticity-paragraph');\n if ($productAuthenticity.length > 0) {\n $productAuthenticity.find('.js-update-scantrustUrl').attr('href', attr.scanTrustUrlWithParams);\n } \n}\n\n/**\n * Updates the availability status in the Product Detail Page\n *\n * @param {Object} response - Ajax response object after an\n * attribute value has been [de]selected\n * @param {jQuery} $productContainer - DOM element for a given product\n */\nconst updateAvailability = (response, $productContainer) => {\n let availabilityValue = '';\n let availabilityMessages = response.product.availability.messages;\n if (!response.product.readyToOrder) {\n availabilityValue = `
${response.resources.info_selectforstock}
`;\n } else if (response.product.availability.orderable) {\n availabilityMessages.forEach(message => {\n availabilityValue += `
${message}
`;\n });\n }\n\n if ($('.js-personalizeButtonModal').length > 0) {\n $productContainer = $('.tingle-modal-box__content');\n }\n\n $('.js-soldOut-message').addClass('hidden');\n if (!response.product.available || response.product.comingSoon || response.product.isSizeInexistent) {\n $('.js-soldOut-message').removeClass('hidden');\n $('.js-selected-size:not(.js-selected-size-not-available)').text('-');\n }\n\n $($productContainer).trigger('product:updateAvailability', {\n product: response.product,\n $productContainer: $productContainer,\n message: availabilityValue,\n resources: response.resources\n });\n\n if ($productContainer.hasClass('js-intProductDetail')) {\n if (response.product.isSoldout === true) {\n $productContainer.addClass('cc-isSoldOut js-isSoldOut');\n } else {\n $productContainer.removeClass('cc-isSoldOut js-isSoldOut');\n }\n }\n};\n\n/**\n * Generates html for quick add form\n *\n * @param {string} pid - pid used to get variation\n * @param {string} url - url of the Controller\n * @return Compiled HTML\n */\nconst showQuickAddItems = (pid, url) => {\n if ($('.js-modal-quick-add-size-quantity').attr('data-pid') === pid) {\n $('.js-modal-quick-add-size-quantity').removeClass('hidden');\n return;\n }\n $('.select-size-quick-add-container').empty();\n $.spinner().start();\n $.ajax({\n url: url,\n method: 'GET',\n data: {\n pid: pid\n },\n success: function (data) {\n $('.select-size-quick-add-container[data-pid=\"' + pid + '\"]').html(data);\n const $productContainer = $('.select-size-quick-add-container[data-pid=\"' + pid + '\"]').closest('.product-detail-quick-add');\n $productContainer.find('.add-to-cart-quick-add').attr('data-quantity', 1);\n var selectedValue = $productContainer.find('.add-to-cart-quick-add').attr('data-size-selected');\n if (selectedValue) {\n $productContainer.find('[data-attr-id=\"' + selectedValue + '\"]').attr('checked', true);\n $productContainer.find('.add-to-cart-quick-add').attr('data-size-available', true);\n } else {\n $productContainer.find('.add-to-cart-quick-add').attr('data-size-available', false);\n $productContainer.find('.size-selected').empty();\n }\n $.spinner().stop();\n },\n error: function () {\n $.spinner().stop();\n }\n });\n};\n\n/**\n * @typedef UpdatedOptionValue\n * @type Object\n * @property {string} id - Option value ID for look up\n * @property {string} url - Updated option value selection URL\n */\n\n/**\n * @typedef OptionSelectionResponse\n * @type Object\n * @property {string} priceHtml - Updated price HTML code\n * @property {Object} options - Updated Options\n * @property {string} options.id - Option ID\n * @property {UpdatedOptionValue[]} options.values - Option values\n */\n\n/**\n * Updates DOM using post-option selection Ajax response\n *\n * @param {OptionSelectionResponse} options - Ajax response options from selecting a product option\n * @param {jQuery} $productContainer - DOM element for current product\n */\nconst updateOptions = (options, $productContainer) => {\n options.forEach(option => {\n const $optionEl = $productContainer.find(`.product-option[data-option-id*=\"${option.id}\"]`);\n option.values.forEach(value => {\n const valueEl = $optionEl.find(`option[data-value-id*=\"${value.id}\"]`);\n valueEl.val(value.url);\n });\n\n option.values.forEach(value => {\n const valueEl = $optionEl.find(`input[id=\"${value.id}\"]`);\n valueEl.data('href', value.url);\n valueEl.attr('href', value.url);\n });\n });\n};\n\nconst updateColorFamily = (product, $productContainer) => {\n $productContainer.find('.family-color').text(product.colorFamily.toLowerCase() + ' - ');\n\n for (let attr of product.variationAttributes) {\n if (attr.attributeId === 'color') {\n if (attr.onSaleSelected) {\n $productContainer.find('.product-color-sales.on-sale').removeClass('hidden');\n $productContainer.find('.product-color-sales.not-on-sale').addClass('hidden');\n } else {\n $productContainer.find('.product-color-sales.on-sale').addClass('hidden');\n $productContainer.find('.product-color-sales.not-on-sale').removeClass('hidden');\n }\n }\n }\n};\n\nconst updatePrices = (product, $productContainer, resources) => {\n if (!product.variationAttributes ||\n !product.variationAttributes[0] ||\n product.variationAttributes[0].attributeId !== 'color') {\n return;\n }\n let selectorPrefix = '';\n if (product.variationAttributes[0].onSaleSelected || product.price.discountValue) {\n selectorPrefix = '.onSaleContainer';\n } else {\n selectorPrefix = '.notOnSaleContainer';\n }\n const priceSelector = selectorPrefix + '.prices .price';\n const priceInfoSelector = ':not(.js-omnibusLabel-wrapper) > .cc-priceOmnibusLabel .price-info';\n const $oldPriceInfoSelector = $(':not(.js-omnibusLabel-wrapper) > .cc-priceOmnibusLabel .js-oldPriceInfo');\n const $regularPriceInfoDiscountSelector = $('.js-priceInfo-discountValue');\n const $oldPriceInfoDiscountSelector = $('.js-oldPriceInfo-discountValue');\n const $pricePercentage = $('.js-pricePercentage');\n const $priceSelector = $(priceSelector, $productContainer).length ?\n $(priceSelector, $productContainer) :\n $(priceSelector);\n const $priceInfoSelector = $(priceInfoSelector, $productContainer).length ?\n $(priceInfoSelector, $productContainer) :\n $(priceInfoSelector);\n const priceInfoInSaleContainerSelector = '.cc-intProductDetail-colors .cc-priceOmnibusLabel .price-info';\n const $priceInfoInSaleContainerSelector = $(priceInfoInSaleContainerSelector, $productContainer);\n const priceInfoInSaleContainerSelector2 = '.cc-intProductDetail-colors .cc-priceOmnibusLabel .js-oldPriceInfo';\n const $priceInfoInSaleContainerSelector2 = $(priceInfoInSaleContainerSelector2, $productContainer);\n const $omnibusPricelForSpecificCountries = $('.js-intProductDetail-attributes-wrapper .js-priceOmnibusLabel .price-info');\n window.onSalesInfoPrice = $priceInfoInSaleContainerSelector.text();\n $priceSelector.replaceWith(product.price.html);\n const currentCountryOmnibus = $oldPriceInfoSelector.closest('.js-omnibusStack').data('currentcountry');\n const isRegularOmnibusCountry = $oldPriceInfoSelector.closest('.js-omnibusStack').data('omnibuscountry');\n if (product.price.sales.formattedPriceInfo) {\n $priceInfoSelector.parent().show();\n $priceInfoSelector.html(product.price.sales.formattedPriceInfo);\n const isCountryWithTooltip = currentCountryOmnibus === 'IT' || currentCountryOmnibus === 'ES' || currentCountryOmnibus === 'SI';\n if (isCountryWithTooltip && resources.tooltip_omnibus && $('i.omnibus-tooltip').length === 0) {\n $('.product-main-price.onSaleContainer .price').append('i

' + resources.tooltip_omnibus + '

');\n }\n if (isRegularOmnibusCountry) {\n $oldPriceInfoSelector.parent().show();\n $oldPriceInfoDiscountSelector.html(product.price.sales.oldPriceOmnibus.priceInfoDiscountValue + '%');\n $oldPriceInfoDiscountSelector.show();\n }\n $oldPriceInfoSelector.html(product.price.list.formatted);\n $regularPriceInfoDiscountSelector.html(product.price.discountValue + '%');\n $priceInfoInSaleContainerSelector.parent().addClass('hidden');\n $priceInfoInSaleContainerSelector2.parent().addClass('hidden');\n $omnibusPricelForSpecificCountries.parent().addClass('hidden');\n window.onSalesInfoPrice = product.price.sales.formattedPriceInfo;\n $priceInfoInSaleContainerSelector2.html(product.price.sales.oldPriceOmnibus.price);\n $pricePercentage.hide();\n } else {\n $priceInfoSelector.parent().hide();\n $priceInfoSelector.html('');\n if (window.onSalesInfoPrice) {\n if (currentCountryOmnibus === 'IT' || currentCountryOmnibus === 'ES' || currentCountryOmnibus === 'SI') {\n $omnibusPricelForSpecificCountries.parent().removeClass('hidden');\n $omnibusPricelForSpecificCountries.html(window.onSalesInfoPrice);\n } else if (isRegularOmnibusCountry) {\n $priceInfoInSaleContainerSelector.parent().removeClass('hidden');\n $priceInfoInSaleContainerSelector.html(window.onSalesInfoPrice);\n $priceInfoInSaleContainerSelector2.parent().removeClass('hidden');\n } else {\n $priceInfoInSaleContainerSelector.parent().removeClass('hidden');\n $priceInfoInSaleContainerSelector.html(window.onSalesInfoPrice);\n }\n }\n $oldPriceInfoSelector.parent().hide();\n $oldPriceInfoSelector.html('');\n if (product.price.discountValue) {\n $pricePercentage.show();\n }\n }\n\n if (product.doubleCurrency && product.doubleCurrency.html) {\n const $doubleCurrencyContainer = $('#descriptionSidebar .js-priceSecondCurrency', $productContainer);\n const innerContent = $(product.doubleCurrency.html).html();\n $doubleCurrencyContainer.html(innerContent);\n }\n\n $productContainer.find(selectorPrefix + ' .js-discount-msg').addClass('hidden');\n $productContainer.find(selectorPrefix + ' .js-promo-msg').addClass('hidden');\n if (product.price.discountValue) {\n $productContainer.find(selectorPrefix + ' .js-discount-msg')\n .html(`(${product.price.discountValue}%)`)\n .removeClass('hidden');\n if (product.promotions && product.promotions.length > 0) {\n if (product.promotions[0].calloutMsg) {\n $productContainer.find(selectorPrefix + ' .js-promo-msg')\n .html(product.promotions[0].calloutMsg)\n .removeClass('hidden');\n } else if (product.promotions[1] && product.promotions[1].calloutMsg) {\n $productContainer.find(selectorPrefix + ' .js-promo-msg')\n .html(product.promotions[1].calloutMsg)\n .removeClass('hidden');\n }\n }\n } else if (product.promotions && product.promotions.length > 0) {\n if (product.promotions[0].calloutMsg) {\n $productContainer.find(selectorPrefix + ' .js-promo-msg')\n .html(product.promotions[0].calloutMsg)\n .removeClass('hidden');\n } else if (product.promotions[1] && product.promotions[1].calloutMsg) {\n $productContainer.find(selectorPrefix + ' .js-promo-msg')\n .html(product.promotions[1].calloutMsg)\n .removeClass('hidden');\n }\n }\n\n $productContainer.find(selectorPrefix + ' .js-loyalty').addClass('hidden');\n $productContainer.find(selectorPrefix + ' .js-loyaltysale').addClass('hidden');\n if (product.price.saleType) {\n let saleType = product.price.saleType;\n if (saleType === 'loyalty1' || saleType === 'loyalty2' || saleType === 'loyalty3' || saleType === 'loyalty4') {\n saleType = 'loyalty';\n } else if (saleType === 'loyaltysale1' || saleType === 'loyaltysale2' || saleType === 'loyaltysale3' || saleType === 'loyaltysale4') {\n saleType = 'loyaltysale';\n }\n $productContainer.find(selectorPrefix + ' .js-' + saleType).removeClass('hidden');\n }\n\n if (product.comingSoon) {\n $productContainer.find('.comingSoonBox').removeClass('hide');\n $productContainer.find('.comingSoonLabel-pdp').removeClass('hidden');\n $productContainer.find(selectorPrefix + ' .js-new-msg').addClass('hidden');\n $productContainer.find(selectorPrefix + ' .js-green-msg').addClass('hidden');\n // $productContainer.find(selectorPrefix + '.js-promo-msg').addClass('hidden');\n } else {\n $productContainer.find('.comingSoonBox').addClass('hide');\n $productContainer.find('.comingSoonLabel-pdp').addClass('hidden');\n $productContainer.find(selectorPrefix + ' .js-new-msg').addClass('hidden');\n $productContainer.find(selectorPrefix + ' .js-green-msg').addClass('hidden');\n if (product.New) {\n $productContainer.find(selectorPrefix + ' .js-new-msg').removeClass('hidden');\n }\n if (product.isGreen) {\n $productContainer.find(selectorPrefix + ' .js-new-msg').addClass('hidden');\n $productContainer.find(selectorPrefix + ' .js-green-msg').removeClass('hidden');\n }\n // $productContainer.find(selectorPrefix + '.js-promo-msg').removeClass('hidden');\n }\n};\n\n/**\n * Parses JSON from Ajax call made whenever an attribute value is [de]selected\n * @param {Object} response - response from Ajax call\n * @param {Object} response.product - Product object\n * @param {string} response.product.id - Product ID\n * @param {Object[]} response.product.variationAttributes - Product attributes\n * @param {Object[]} response.product.images - Product images\n * @param {boolean} response.product.hasRequiredAttrsSelected - Flag as to whether all required\n * attributes have been selected. Used partially to\n * determine whether the Add to Cart button can be enabled\n * @param {jQuery} $productContainer - DOM element for a given product.\n */\nconst handleVariantResponseQuickAdd = (response, $productContainer, imagesShouldUpdate = true) => {\n if (response.product.variationAttributes) {\n updateAttrs(response.product.variationAttributes, $productContainer);\n }\n\n updateAvailability(response, $productContainer);\n\n $('body').trigger('product:updateAddToCartQuickAdd', {\n product: response.product,\n $productContainer: $productContainer\n }).trigger('product:statusUpdate', response.product);\n};\n\nconst updateImageSaveForLater = (product, $productContainer) => {\n $productContainer.find('.js-product-image-saveForLater').attr('src', product.images.small[0].url);\n $productContainer.find('.js-product-image-saveForLater').attr('alt', product.images.small[0].url);\n $productContainer.find('.js-product-image-saveForLater').attr('title', product.images.small[0].title);\n};\n\n/**\n * Parses JSON from Ajax call made whenever an attribute value is [de]selected\n * @param {Object} response - response from Ajax call\n * @param {Object} response.product - Product object\n * @param {string} response.product.id - Product ID\n * @param {Object[]} response.product.variationAttributes - Product attributes\n * @param {Object[]} response.product.images - Product images\n * @param {boolean} response.product.hasRequiredAttrsSelected - Flag as to whether all required\n * attributes have been selected. Used partially to\n * determine whether the Add to Cart button can be enabled\n * @param {jQuery} $productContainer - DOM element for a given product.\n */\nconst handleVariantResponse = (response, $productContainer, imagesShouldUpdate = true, variantType) => {\n if (response.product.variationAttributes) {\n updateAttrs(response.product.variationAttributes, $productContainer, variantType);\n updateColorFamily(response.product, $productContainer);\n updateScanTrustLink(response, $productContainer);\n }\n const $container = $('.js-composition-info');\n\n if (response.product.partTypes) {\n $container.empty();\n const html = `
`;\n $container.append(html);\n\n for (var k = 0; k < response.product.partTypes.length; k++) {\n if (k == 0) {\n var type = `${response.product.partTypes[k].type}: `;\n $container.append(type);\n }\n if (k < response.product.partTypes.length - 1) {\n if (response.product.partTypes[k].type == response.product.partTypes[k + 1].type) {\n var comp = `${response.product.partTypes[k].percentage} % ${response.product.partTypes[k].material}, `;\n $container.append(comp);\n } else {\n var comp = `${response.product.partTypes[k].percentage} % ${response.product.partTypes[k].material}`;\n var type = `
${response.product.partTypes[k + 1].type}: `;\n\n $container.append(comp);\n $container.append(type);\n }\n } else {\n var comp = `${response.product.partTypes[k].percentage} % ${response.product.partTypes[k].material} `;\n $container.append(comp);\n }\n }\n const endTag = `
`;\n $container.append(endTag);\n } else if (response.product.mainComposition) {\n $container.empty();\n const html = `
`;\n $container.append(html);\n\n for (var k = 0; k < response.product.mainComposition.length; k++) {\n if (k == response.product.mainComposition.length - 1) {\n var comp = `${response.product.mainComposition[k].percentage} % ${response.product.mainComposition[k].material} `;\n } else {\n var comp = `${response.product.mainComposition[k].percentage} % ${response.product.mainComposition[k].material}, `;\n }\n\n $container.append(comp);\n }\n const endTag = `
`;\n $container.append(endTag);\n }\n\n // Update primary images\n if (imagesShouldUpdate) {\n const primaryImageUrls = response.product.images;\n if ($productContainer.hasClass('product-quickview:not(.product-quickview--get-product)')) {\n if ($productContainer.find('.carousel-inner').hasClass('slick-initialized')) {\n $productContainer.find('.carousel-inner').slick('destroy');\n }\n $productContainer.find('.carousel-inner').empty();\n $productContainer.find('.product-link-carousel').attr('href', response.product.selectedProductUrl);\n\n primaryImageUrls.large.forEach((imageUrl, idx) => {\n let $carouselInner = $($('#outer').html());\n $productContainer.find('.carousel-inner').append($carouselInner);\n\n let $imgContainer = $carouselInner.find('img');\n $imgContainer.data('index', idx);\n $imgContainer.attr('id', null);\n $imgContainer.attr('src', imageUrl.url).removeClass('hidden');\n });\n\n if (Foundation.MediaQuery.atLeast('large')) {\n $productContainer.find('.carousel-inner').slick({\n slidesToShow: 1,\n slidesToScroll: 1,\n dots: false\n });\n }\n } else if ($productContainer.hasClass('product-quickview--get-product')) {\n if ($productContainer.find('.carousel-inner').hasClass('slick-initialized')) {\n $productContainer.find('.carousel-inner').slick('destroy');\n }\n $productContainer.find('.carousel-inner').empty();\n $productContainer.find('.product-link-carousel').attr('href', response.product.selectedProductUrl);\n\n primaryImageUrls.large.forEach((imageUrl, idx) => {\n let $carouselInner = $($('#outer').html());\n $productContainer.find('.carousel-inner').append($carouselInner);\n\n let $imgContainer = $carouselInner.find('img');\n $imgContainer.data('index', idx);\n $imgContainer.attr('id', null);\n $imgContainer.attr('src', imageUrl.url).removeClass('hidden');\n });\n\n $productContainer.find('.carousel-inner').slick({\n dots: false,\n arrows: false,\n slidesToShow: 2.35,\n infinite: false,\n slidesToScroll: 1,\n responsive: [\n {\n breakpoint: 1023,\n settings: {\n slidesToShow: 2.5\n }\n }]\n });\n } else {\n $('.mobile-gallery').slick('slickUnfilter');\n $productContainer.find('.primary-images .carousel-item').addClass('hidden');\n $productContainer.find('.js-intProductDetail-images-container .desktop-gallery-item').addClass('hidden');\n $productContainer.find('.cc-intProductDetail-images').addClass('hidden');\n $('#zoomModal').data('numberOfImages', primaryImageUrls.large.length);\n // For each image check if tag is generated otherwise generate it and change its src\n primaryImageUrls.large.forEach((imageUrl, idx) => {\n var resizedUrls = '';\n if (imageUrl.resizedUrls) {\n var srcSetArray = imageUrl.resizedUrls.map((element, index) => {\n return element + ' ' + imageUrl.sizes[index].scaleWidth + 'w';\n });\n resizedUrls = srcSetArray.join(',');\n }\n let $imgContainer = $productContainer.find('.primary-images').find(`img[data-index=\"${idx}\"]`);\n let $imgContainerDesktop = $productContainer.find('.js-intProductDetail-images-container').find(`img[data-index=\"${idx}\"]`);\n let $imgZoomModal = $productContainer.find('.js-zoomModal').find(`img[data-index=\"${idx}\"]`);\n let $imgZoomModalMobile = $productContainer.find('.js-zoomModalMobile').find(`img[data-index=\"${idx}\"]`);\n\n if (!$imgContainer.length) {\n let newCarouselSlideHtml = $('#outer').html().replaceAll('{imgIdx}', idx);\n $productContainer.find('.primary-images').slick('slickAdd', newCarouselSlideHtml);\n $imgContainer = $productContainer.find(`.primary-images img[data-index=\"${idx}\"]`);\n }\n if (!$imgContainerDesktop.length) {\n let $galleryItemContainer = $($('#outer-desktop').html().replaceAll('{imgIdx}', idx));\n $productContainer.find('.js-intProductDetail-images-container').append($galleryItemContainer);\n\n $imgContainerDesktop = $galleryItemContainer.find('img');\n $imgContainerDesktop.attr('data-index', idx);\n }\n if (!$imgZoomModal.length) {\n let $zoomTemplate = $($('#zoom-template').html());\n $productContainer.find('.js-zoomModal-content').append($zoomTemplate);\n\n $imgZoomModal = $zoomTemplate.find('img');\n $imgZoomModal.attr('data-index', idx);\n }\n\n if (!$imgZoomModalMobile.length) {\n let $zoomTemplate = $($('#zoom-template').html().replaceAll('{imgIdx}', idx));\n $productContainer.find('.js-zoomModal-content').append($zoomTemplate);\n\n $imgZoomModalMobile = $zoomTemplate.find('img');\n $imgZoomModalMobile.attr('data-index', idx);\n }\n\n if (imageUrl.resizedUrls) {\n $productContainer.find('.primary-images').find(`img[data-index=\"${idx}\"]`).attr('data-srcset', resizedUrls);\n $productContainer.find('.js-intProductDetail-images-container').find(`img[data-index=\"${idx}\"]`).attr('data-srcset', resizedUrls);\n if ($imgZoomModal.length) {\n $imgZoomModal.attr('srcset', resizedUrls).attr('data-srcset', resizedUrls);\n }\n if ($imgZoomModalMobile.length) {\n $imgZoomModalMobile.attr('srcset', resizedUrls).attr('data-srcset', resizedUrls);\n }\n }\n $imgZoomModalMobile.attr('src', imageUrl.url).attr('data-src', imageUrl.url).removeClass('hidden');\n $imgZoomModal.attr('src', imageUrl.url).attr('data-src', imageUrl.url).removeClass('hidden');\n $productContainer.find(`.cc-intProductDetail-images[data-index=\"${idx}\"]`).removeClass('hidden');\n $productContainer.find('.primary-images').find(`img[data-index=\"${idx}\"]`).attr('src', imageUrl.url).attr('data-src', imageUrl.url).removeClass('lazyloaded').addClass('lazyload');\n $productContainer.find('.js-intProductDetail-images-container').find(`img[data-index=\"${idx}\"]`).attr('src', imageUrl.url).attr('data-src', imageUrl.url).removeClass('lazyloaded').addClass('lazyload');\n $productContainer.find('.primary-images').find(`.carousel-item[data-index=${idx}]`).removeClass('hidden');\n $productContainer.find('.js-intProductDetail-images-container').find(`.desktop-gallery-item[data-index=${idx}]`).removeClass('hidden');\n });\n const videoUrl = response.product.videoURL;\n $('.primary-images .js-productVideoContainer').remove();\n $('.js-intProductDetail-images-container .js-productVideoContainer').remove();\n if (videoUrl) {\n // insert primary video in mobile carousel\n let tmpl = $('.js-productVideoContainerOuter').clone()[0];\n tmpl.setAttribute('class', 'carousel-item cc-productVideoContaner js-productVideoContainer');\n $productContainer.find('.primary-images').slick('slickAdd', tmpl, 2, true);\n\n // insert primary video in desktop gallery\n tmpl = $($('#pdp-video-template-desktop').html());\n let $secondItem = $productContainer.find('.js-intProductDetail-images-container .desktop-gallery-item')[1];\n tmpl.insertAfter($secondItem);\n\n $productContainer.find('.js-productVideoContainer source').attr('src', videoUrl);\n\n let videoBlock = $productContainer.find('.js-productVideoContainer video');\n if (videoBlock && videoBlock.length > 0) {\n videoBlock[0].load();\n videoBlock[0].autoplay = true;\n }\n videoListener();\n }\n $('.primary-images').slick('slickGoTo', 0);\n $('.primary-images').slick('slickFilter', ':not(.hidden)');\n if (primaryImageUrls.small.length > 0) {\n $('.still-life-img').data('still-life', primaryImageUrls.small[0].url);\n }\n\n updatePrimaryImagesSlider(primaryImageUrls.large);\n }\n }\n\n // Update pricing\n if (response.product.price) {\n updatePrices(response.product, $productContainer, response.resources);\n }\n\n updateAvailability(response, $productContainer);\n // Enable \"Add to Cart\" button if all required attributes have been selected\n $('button.js-add-to-cart, button.add-to-cart-global, button.update-cart-product-global').trigger('product:updateAddToCart', {\n product: response.product,\n $productContainer: $productContainer\n }).trigger('product:statusUpdate', response.product);\n\n if ($('.js-personalizeButtonModal').length == 0) {\n careAndMaintenance(response.product.id);\n }\n\n var countryEnabled = window.PersonalizationEnabledCountries.PersonalizationEnabledCountries;\n if (response.variation.isPersonalizedVal && response.variation.positions > 0 && countryEnabled) {\n showButton(response);\n } else {\n $('#personalizeButton').addClass('hidden');\n }\n\n updateModelSize(response, $productContainer);\n};\n\nconst updateModelSize = (response, $productContainer) => {\n $('.js-product-model-size').addClass('hide');\n var modelSize = response.product.modelSize;\n if (!modelSize) {\n return;\n }\n\n $('.js-product-model-size').removeClass('hide').find('.js-modelSizeValue').text(modelSize);\n};\n\nconst handleVariationUrlsSelectSizeModal = (variationUrls) => {\n variationUrls.forEach(function (element) {\n $('#whislistSizeSelection-' + element.id).attr('data-attr-info-url', element.variationUrl);\n });\n};\nconst handlePromotionTag = (product, $productContainer) => {\n $productContainer.find('.js-promo-msg').addClass('hidden');\n if (product.promotions && product.promotions.length > 0) {\n for (var i = 0; i < product.promotions.length; i++) {\n if (product.promotions[i].promotionClass === 'PRODUCT' && product.promotions[i].calloutMsg) {\n $productContainer.find('.js-promo-msg').html(product.promotions[i].calloutMsg).removeClass('hidden');\n break;\n }\n }\n }\n};\n\nconst handleVariationUrlsSelectNotifyModal = (variationUrls) => {\n variationUrls.forEach(function (element) {\n if ((element.id).indexOf('/') != -1) {\n let cleanId = (element.id).split('/')[0] + '\\\\/' + (element.id).split('/')[1];\n $('#' + cleanId).attr('data-url', element.variationUrl);\n $('#' + cleanId).parent().attr('sku', element.sku);\n $('.add-size-saveForLater input[data-attr-value=\"' + cleanId + '\"]').parent().removeClass('disabled');\n if (!element.selectable) {\n $('.add-size-saveForLater input[data-attr-value=\"' + cleanId + '\"][data-sku=\"' + element.sku + '\"]').parent().addClass('disabled');\n }\n } else {\n $('#' + element.id).attr('data-url', element.variationUrl);\n $('#' + element.id).parent().attr('data-sku', element.sku);\n $('#' + element.id).attr('data-sku', element.sku);\n $('#' + element.id).attr('data-allocation', element.allocation);\n $('#' + element.id).parent().find('.js-container').removeClass('notifyPopup').removeClass('notifyMe');\n $('#' + element.id + '_mobile').parent().find('.js-container').removeClass('notifyPopup').removeClass('notifyMe');\n $('.js-add-size-saveForLater input[data-attr-value=\"' + element.id + '\"]').parent().removeClass('cc-disabled');\n $('.js-add-size-saveForLater input[data-attr-value=\"' + element.id + '\"]').parent().removeClass('cc-selected');\n if (element.selectable === false) {\n $('.js-add-size-saveForLater input[data-attr-value=\"' + element.id + '\"]').parent().addClass('cc-disabled');\n }\n if (element.selected === true) {\n $('.js-add-size-saveForLater input[data-attr-value=\"' + element.id + '\"]').parent().addClass('cc-selected');\n }\n if (element.allocation === 0 || element.isComingSoon) {\n $('.js-add-size-saveForLater input[data-attr-value=\"' + element.id + '\"]').parent().addClass('cc-disabled');\n $('#' + element.id).parent().find('.js-container').addClass('notifyMe').addClass('notifyPopup');\n $('#' + element.id + '_mobile').parent().find('.js-container').addClass('notifyMe').addClass('notifyPopup');\n }\n }\n });\n};\n\nconst handleVariationComingSoonNotifyModal = (comingSoons) => {\n comingSoons.forEach(function (element) {\n if ((element.id).indexOf('/') != -1) {\n let cleanId = (element.id).split('/')[0] + '\\\\/' + (element.id).split('/')[1];\n $('#' + cleanId).attr('data-isComingSoon', element.isComingSoon);\n } else {\n $('#' + element.id).attr('data-isComingSoon', element.isComingSoon);\n }\n });\n};\nconst handleVariationComingSoon = (comingSoons) => {\n if (!comingSoons) {\n $('.marketing-budge.js-comingSoonBox').addClass('hide');\n $('.js-comingSoonBox.pdp-comingSoonBox').addClass('hide');\n } else {\n $('.marketing-budge.js-comingSoonBox').removeClass('hide');\n $('.js-comingSoonBox.pdp-comingSoonBox').removeClass('hide');\n }\n};\n\nconst handleVariationWishlistModal = (variationUrls) => {\n variationUrls.forEach(function (element) {\n if ((element.id).indexOf('/') != -1) {\n let cleanId = (element.id).split('/')[0] + '\\\\/' + (element.id).split('/')[1];\n $('#fis-select-size-wishlist').find('#whislistSizeSelection').find('button*[data-attr-value=\"' + cleanId + '\"]').attr('data-attr-info-url', element.variationUrl);\n $('#fis-select-size-wishlist').find('#whislistSizeSelection').find('button*[data-attr-value=\"' + cleanId + '\"]').attr('data-attr-selectable', element.selectable ? 'selectable' : 'not-selectable');\n } else {\n $('#fis-select-size-wishlist').find('#whislistSizeSelection').find('button*[data-attr-value=\"' + element.id + '\"]').attr('data-attr-info-url', element.variationUrl);\n $('#fis-select-size-wishlist').find('#whislistSizeSelection').find('button*[data-attr-value=\"' + element.id + '\"]').attr('data-attr-selectable', element.selectable ? 'selectable' : 'not-selectable');\n }\n });\n};\n\n/**\n * This is a workaround for inexisting sizes for the cart's quick view.\n * It should be handled at decorator level but the list of actual variants is incoherent.\n */\nconst handleInexistentSizeQuickView = (data) => {\n if (!data.product.isSizeInexistent || !$('.quickview-modal').length) {\n return;\n }\n\n $('.product-content-size').find('input[data-size-id]').removeClass('hide')\n .closest('.boolean-field').removeClass('hide')\n .closest('.label-wrapper').removeClass('hide');\n};\n\nfunction showButton (response) {\n // $('#iconPersMobile').removeClass('hidden');\n if (response.variation.isPersonalizedVal === true) {\n $('#personalizeButton').removeClass('hidden');\n } else {\n $('#personalizeButton').addClass('hidden');\n }\n $('#personalizeButton')\n .attr('product-id', response.product.id)\n .attr('data-positions', response.variation.positions)\n .attr('data-customizations', response.variation.customizations)\n .attr('data-personalizationImgTop', response.variation.personalizationImgTop)\n .attr('data-personalizationImgDown', response.variation.personalizationImgDown);\n\n var link = $('#personalizeButton').attr('data-url') + '?pid=' + response.product.id +\n '&positions=' + response.variation.positions +\n '&quantity=' + response.product.selectedQuantity;\n $('#personalizeButton a').attr('href', link);\n $('#personalizeButton button').attr('data-url', link);\n\n var linkPlp = $('#personalizeButton').attr('data-url') + '?pid=' + response.product.id +\n '&positions=' + response.variation.positions +\n '&quantity=' + response.product.selectedQuantity +\n '&sizeAttribute=' + $('.persButtonPdpPers').attr('size-attribute');\n\n $('#persButtonPdpPersLink').attr('href', linkPlp);\n}\n\nfunction careAndMaintenance (pid) {\n $('#main-and-care-label-wash-description').removeClass('hidden');\n $('#main-and-care-label').addClass('hidden');\n\n if (!$('#main-and-care').length) {\n return;\n }\n\n $.ajax({\n url: $('#main-and-care').attr('data-url'),\n data: {\n pid: pid\n },\n method: 'GET',\n success: data => {\n $('#cm-container').empty().html(data.html);\n $.spinner().stop();\n },\n error: () => {\n $.spinner().stop();\n }\n });\n}\n\n/**\n * @typespec UpdatedQuantity\n * @type Object\n * @property {boolean} selected - Whether the quantity has been selected\n * @property {string} value - The number of products to purchase\n * @property {string} url - Compiled URL that specifies variation attributes, product ID, options,\n * etc.\n */\n\n/**\n * Updates the quantity DOM elements post Ajax call\n * @param {UpdatedQuantity[]} quantities -\n * @param {jQuery} $productContainer - DOM container for a given product\n */\nconst updateQuantities = (quantities, $productContainer) => {\n if (!($productContainer.parent('.bonus-product-item').length > 0)) {\n const optionsHtml = quantities.map(quantity => {\n const selected = quantity.selected ? 'selected' : '';\n return ``;\n }).join('');\n if ($productContainer.hasClass('product-detail-quick-add')) {\n $('.quantity-select-quick-add').empty().html(optionsHtml);\n } else {\n getQuantitySelector($productContainer).empty().html(optionsHtml);\n }\n }\n};\n\n/**\n * Retrieves url to use when adding a product to the cart\n *\n * @return {string} - The provided URL to use when adding a product to the cart\n */\nconst getAddToCartUrl = () => {\n return $('.add-to-cart-url').val();\n};\n\n/**\n * Parses the html for a modal window\n * @param {string} html - representing the body and footer of the modal window\n *\n * @return {Object} - Object with properties body and footer.\n */\nconst parseHtml = html => {\n var $html = $('
').append($.parseHTML(html));\n\n var body = '';\n let $results = $html.find('.choice-of-bonus-product');\n for (let i = 0; i < $results.length; i++) {\n body += $results[i].outerHTML;\n }\n var footer = $html.find('.modal-footer').children().html();\n\n return {\n body: body,\n footer: footer\n };\n};\n\n// Generates a PID based on the current selected attributes\nconst getPID = (product) => {\n if (typeof product === 'string') {\n return product.trim();\n }\n\n // size and color have already been selected. In this case, the variation\n // group is built with the style of the product, 'color' and the selected\n // color variation\n if (product.productType === 'variant') {\n let sku = product.id;\n return sku;\n } else if (product.productType === 'variationGroup') {\n // in this case the user only chose the color, and not the size\n let pid = product.id.split('_')[0].trim();\n\n let selectedVariation;\n\n for (let k in product.variationAttributes) {\n const variationAttribute = product.variationAttributes[k];\n if (variationAttribute.attributeId === 'color') {\n for (let j in variationAttribute.values) {\n if (variationAttribute.values[j].selected === true) {\n selectedVariation = variationAttribute.values[j].value;\n break;\n }\n }\n }\n if (selectedVariation !== undefined) {\n break;\n }\n }\n\n return pid + '_color_' + selectedVariation;\n }\n\n return '';\n};\n\n/**\n * Updates the Mini-Cart quantity value after the customer has pressed the \"Add to Cart\" button\n * @param {string} response - ajax response from clicking the add to cart button\n */\nconst handlePostCartAdd = (response) => {\n $('.js-mainHeader-minicart').trigger('count:update', response);\n \n const cookies = document.cookie.split(';');\n let cookieSizebaySessionId = null;\n for (let i = 0; i < cookies.length; i++) {\n const cookie = cookies[i].trim();\n if (cookie.startsWith('SIZEBAY_SESSION_ID_V4')) {\n cookieSizebaySessionId = cookie.substring('SIZEBAY_SESSION_ID_V4='.length).replaceAll('\"', '');\n break;\n }\n };\n\n if (cookieSizebaySessionId === null) {\n let urlSessionId = document.querySelector('#sizebayAddProduct').getAttribute('data-sizebaysessionidurl');\n fetch(urlSessionId)\n .then(response => {\n if (!response.ok) {\n throw new Error('Network response was not ok');\n }\n return response.json();\n })\n .then(data => {\n createCookie('SIZEBAY_SESSION_ID_V4', data);\n callSizebayAPI(data);\n })\n } else {\n callSizebayAPI(cookieSizebaySessionId);\n }\n};\n\nfunction callSizebayAPI(data) {\n let url = document.querySelector('#sizebayAddProduct').getAttribute('data-sizebay-link') + '=' + data;\n let brandURL = document.querySelector('#sizebayAddProduct').getAttribute('data-referrer-sizebay-link');\n let currentCountry = document.querySelector('#sizebayAddProduct').getAttribute('data-sizebay-locale');\n if (!brandURL.includes(currentCountry)) {\n brandURL += '/' + currentCountry + '/';\n }\n let permaURL = brandURL + document.querySelector('.analytics.product.hidden').getAttribute('data-item_id');\n let urlSizebay = new URL(url);\n if (urlSizebay.searchParams.has('sid') && urlSizebay.searchParams.get('sid') === 'null') {\n urlSizebay.searchParams.set('sid', data.trim().replace(/^\"|\"$/g, ''));\n url = urlSizebay.toString();\n }\n let payload = JSON.stringify({\n \"products\": [\n {\n \"permalink\": permaURL\n }\n ],\n \"tenantId\": 2399\n });\n\n let device = $('.cc-intProductDetail-left-content .cell .js-intProductDetail-images-container.cc-intProductDetail-images-container').css('display') === 'block' ? 'mobile' : 'desktop';\n let referrerURL = new URL(window.location.href);\n try {\n fetch(url, {\n method: 'POST',\n body: payload,\n referrerPolicy: \"origin-when-cross-origin\",\n headers: {\n \"content-type\": \"application/json\",\n accept: \"application/json\",\n tenant_id: '2399',\n device: device,\n referer: referrerURL.hostname\n }\n });\n } catch (error) {\n console.error(\"Error: \", error);\n }\n}\n\nfunction updateQuantityPicker (source) {\n if (source === null || source.closest('.js-pdpStickyBar-btn').length > 0 || source.closest('.js-customizePage').length > 0) {\n source = $('.attribute-container.quantity');\n } else {\n source = source.closest('.attribute-container.quantity');\n }\n\n let value = parseInt(source.find('.js-quantity-value').html());\n if (value === 10) {\n source.find('.js-quantity-button[data-action=\"increase\"]').addClass('disabled');\n source.find('.js-quantity-button[data-action=\"decrease\"]').removeClass('disabled');\n if ($('.js-pdpStickyBar-btn').length > 0) {\n $('.js-pdpStickyBar-btn .js-quantity-button[data-action=\"increase\"]').addClass('disabled');\n $('.js-pdpStickyBar-btn .js-quantity-button[data-action=\"decrease\"]').removeClass('disabled');\n }\n } else if (value === 1) {\n source.find('.js-quantity-button[data-action=\"decrease\"]').addClass('disabled');\n source.find('.js-quantity-button[data-action=\"increase\"]').removeClass('disabled');\n if ($('.js-pdpStickyBar-btn').length > 0) {\n $('.js-pdpStickyBar-btn .js-quantity-button[data-action=\"decrease\"]').addClass('disabled');\n $('.js-pdpStickyBar-btn .js-quantity-button[data-action=\"increase\"]').removeClass('disabled');\n }\n } else {\n source.find('.js-quantity-button[data-action=\"increase\"]').removeClass('disabled');\n source.find('.js-quantity-button[data-action=\"decrease\"]').removeClass('disabled');\n if ($('.js-pdpStickyBar-btn').length > 0) {\n $('.js-pdpStickyBar-btn .js-quantity-button[data-action=\"increase\"]').removeClass('disabled');\n $('.js-pdpStickyBar-btn .js-quantity-button[data-action=\"decrease\"]').removeClass('disabled');\n }\n }\n}\n\nconst calculateWatchedTime = (video) => {\n let percentageWatched = video.currentTime * 100 / video.duration;\n return percentageWatched;\n};\n\nconst triggerVideoInteractionEvent = (action, fullPageLoad) => {\n $('body').trigger('analytics:videoInteraction', {action: action, fullPageLoad: fullPageLoad});\n};\n\nconst videoListener = (fullPageLoad = false) => {\n const $videoBlockContainer = $('.js-productVideoContainer');\n const $videoPlayMiniatureIcon = $('.productVideoMiniatureMobile.js-productVideoMiniatureMobile').find('.videoMiniatureIcon');\n let percentageWatched = 0;\n let firstPlayback = true;\n let watchedFullVideo = false;\n let videoStartInSeconds = 0;\n let videoEndInSeconds = 0;\n if ($videoBlockContainer.length > 0 && !$videoBlockContainer.hasClass('hidden')) {\n var myVideo = $videoBlockContainer.find('video')[0];\n myVideo.onended = function () {\n myVideo.currentTime = 0;\n };\n myVideo.onplaying = function () {\n if (myVideo.autoplay) {\n triggerVideoInteractionEvent('auto_play', fullPageLoad);\n }\n myVideo.autoplay = false;\n };\n myVideo.onpause = function () {\n if (!firstPlayback) {\n watchedFullVideo = videoEndInSeconds - videoStartInSeconds > myVideo.duration;\n triggerVideoInteractionEvent('pause', fullPageLoad);\n if (watchedFullVideo) {\n triggerVideoInteractionEvent('full_view', fullPageLoad);\n } else if (percentageWatched >= 25 && percentageWatched < 50) {\n triggerVideoInteractionEvent('view25', fullPageLoad);\n } else if (percentageWatched >= 50 && percentageWatched < 75) {\n triggerVideoInteractionEvent('view50', fullPageLoad);\n } else if (percentageWatched >= 75 && percentageWatched < 100) {\n triggerVideoInteractionEvent('view75', fullPageLoad);\n } else if (percentageWatched === 100) {\n triggerVideoInteractionEvent('full_view', fullPageLoad);\n }\n }\n firstPlayback = false;\n };\n $('.js-pauseVideoIcon').on('click', function () {\n myVideo.loop = false;\n percentageWatched = calculateWatchedTime(myVideo);\n videoEndInSeconds = new Date().getTime() / 1000;\n myVideo.pause();\n myVideo.currentTime = 0;\n $videoBlockContainer.find('.js-pauseVideoIcon').addClass('hide');\n $videoBlockContainer.find('.js-playVideoIcon').removeClass('hide');\n $videoPlayMiniatureIcon.removeClass('black-border');\n });\n $('.js-playVideoIcon').on('click', function () {\n myVideo.loop = true;\n $videoBlockContainer.find('.js-pauseVideoIcon').removeClass('hide');\n $videoBlockContainer.find('.js-playVideoIcon').addClass('hide');\n $videoPlayMiniatureIcon.addClass('black-border');\n if (myVideo.paused && !myVideo.autoplay) {\n triggerVideoInteractionEvent('play', fullPageLoad);\n }\n videoStartInSeconds = new Date().getTime() / 1000;\n myVideo.play();\n });\n }\n};\n\n/**\n * reorder the swatches in $swatchContainer in order to push the soldout ones at the end\n */\nconst reorderSwatches = ($swatchContainer) => {\n if ($swatchContainer.find('span.swatch-value.soldout').length === 0) {\n return;\n }\n var $soldoutColorsContainers = $swatchContainer.find('span.swatch-value.soldout').closest('div');\n var $lastNonSoldoutColorContainer = $swatchContainer.find('span.swatch-value').closest('div').not($soldoutColorsContainers).last();\n $soldoutColorsContainers.insertAfter($lastNonSoldoutColorContainer);\n};\n\nclass ProductHelpers {\n constructor () {\n this.freeGiftDetailsModal = 'freeGiftDetailsModal';\n this.bonusProductModal = null;\n this.methods = {\n getPidValue: function ($el) {\n return getPidValue($el);\n }\n };\n }\n\n run () {\n this.colorAttribute();\n this.colorAttributeQuickAddListing();\n this.sizeAttribute();\n this.sizeAttributeQuickAddListing();\n this.sizeAttributeQuickAddPDP();\n this.sizeAttributeSet();\n this.quantity();\n this.availability();\n this.addToCart();\n // this.selectBonusProduct();\n // this.removeBonusProduct();\n // this.enableBonusProductSelection();\n // this.showMoreBonusProducts();\n // this.closeBonusProductModal();\n // this.enableAddAfterBonusColorSelection();\n // this.removeSizePickerPopup();\n // this.addBonusProductsToCart();\n // this.handleBonusSize();\n // this.handleBonusColor();\n // this.removeColorPickerPopup();\n this.careAndMaintenanceClick();\n this.personalizationButton();\n this.sizeTU();\n this.quickAddListener();\n videoListener(true);\n NotifyHelper.notifyMeModal();\n this.checkSoldoutAvailability();\n SmartGiftHelper.run();\n sizePanel.init();\n this.registerAttributionTokenSending();\n this.loadGoogleRecommendations();\n this.createNextPageToken();\n }\n\n personalizationButton () {\n $('body').on('click', '.persButt', (e) => {\n e.preventDefault();\n // Simulate disabled button with class to allow click and event\n if ($(e.currentTarget).data('disabled') || !this.isSizeSelected()) {\n // If no size is selected, open modal to choose one\n\n if ($(e.currentTarget).closest('.quickview-modal').length) {\n // QuickView (Open the other modal type)\n\n let modal = $('.js-modal-quick-size-quantity');\n // First check if it is open\n if (modal.hasClass('open')) {\n // Check if size is selected, then add to cart\n } else {\n // Show it\n modal.removeClass('hidden').addClass('open');\n modal.find('.slick-slider.slick-initialized').slick('refresh');\n\n modal.find('.js-close-select-size').on('click', function (e) {\n modal.addClass('hidden').removeClass('open');\n });\n }\n } else if (!($(e.currentTarget).hasClass('persButtMobile') && !$('.pdp-buy-look-container').hasClass('hidden'))) {\n sizePanel.openSizePanel(sizePanel.Types.PERSONALIZE);\n }\n\n // Prevent further progress until a size is selected\n e.preventDefault();\n } else {\n if ($('.jsPersonalizationToolModal').length === 0) {\n let url = $(e.currentTarget).attr('data-url') || $(e.currentTarget).data('url');\n $.get(url, function (data) {\n if (data && data !== '') {\n let modal = newModalFromString(data, true, ['jsPersonalizationToolModal'], () => {\n // TODO: On Open Actions\n $('.tingle-modal .close').on('click touchstart', function (e) {\n e.preventDefault();\n modal.close();\n modal.destroy();\n });\n }, () => {\n // TODO: On Close Actions\n $('[data-attr=\"size\"] input.js-mobile-size-selected').prop('checked', true);\n });\n $(modal.modalBox).addClass('rightModalAttribute cc-detailsPopup-modalBox rightModalAttribute_sizeXtraLarge');\n modal.open();\n runPersonalizationListener();\n }\n });\n }\n }\n });\n }\n\n careAndMaintenanceClick () {\n $(document).on('click', '.js-caremaintenance-container ul.tabs li', function () {\n $('.js-caremaintenance-container ul.tabs li').removeClass('current');\n $('.tab-content').removeClass('current');\n $(this).addClass('current');\n const description = $(this).data('tab');\n $(`#${description}`).addClass('current');\n });\n }\n\n colorAttribute () {\n $('body').on('click', '[data-attr=\"color\"] a', e => {\n e.preventDefault();\n if ($(e.currentTarget).attr('disabled') || $(e.currentTarget).find('.swatch-value').hasClass('selected')) {\n return;\n }\n var $productContainer = $(e.currentTarget).closest('.set-item');\n if (!$productContainer.length) {\n $productContainer = $(e.currentTarget).closest('.product-detail');\n }\n\n if (!$productContainer.length && $(e.currentTarget).hasClass('saveToLater')) {\n $productContainer = $('.wishlist-product-card').closest('.product-detail');\n }\n\n let imagesShouldUpdate = true;\n if ($productContainer.hasClass('cart-line-item')) {\n imagesShouldUpdate = false;\n }\n attributeSelect(e.currentTarget.href, $productContainer, 'color', imagesShouldUpdate);\n let color = $productContainer.prevObject.children('span').data('attr-value');\n var firstPart = $productContainer.attr('data-pid');\n var firstPartSplit = firstPart.split('_');\n var firstPartSKU = '';\n if (firstPartSplit.length > 1) {\n firstPartSKU = firstPartSplit[0];\n } else {\n firstPartSKU = firstPart;\n }\n\n var sku = null;\n let splitSku = firstPartSKU ? firstPartSKU.replace(/\\s+/g, '_').split('_') : [];\n let productId = splitSku[0];\n\n if ($('.page[data-action=\"Product-Show\"]').length > 0) {\n let size = $('.selected-size-value').first().text().trim();\n $('#analyticsSelectedColor').val(color);\n\n sku = size && size !== 'false' ? productId + '_' + color + '_' + size : productId + '_' + color;\n $('body').trigger('product:didChangeColor', {sku: sku});\n } else if ($('.page[data-action=\"Cart-Show\"]').length > 0) {\n let selectedSize = $('.cc-cartQuickView_selectedSize').attr('for');\n let colorValue = $(e.currentTarget).data('color-value');\n $('#analyticsSelectedColor').val(colorValue);\n\n sku = selectedSize ? productId + '_' + colorValue + '_' + selectedSize : productId + '_' + colorValue;\n $('body').trigger('product:didChangeColor', {sku: sku});\n }\n });\n\n $('body').on('click', '.product-detail [data-attr=\"color\"] a', e => {\n if ($(e.currentTarget).parents('.quickview-modal').length !== 0) {\n return;\n }\n // Get new color to push to query string\n var selectedColor = $(e.currentTarget).data('color-value');\n if (!selectedColor) {\n return;\n }\n // Perform URL query string update\n updateProductDetailUrl('_col_', selectedColor);\n });\n }\n\n colorAttributeQuickAddListing () {\n $('body').on('click', '[data-attr=\"color-listing\"] a', e => {\n e.preventDefault();\n if ($(e.currentTarget).attr('disabled') || $(e.currentTarget).find('.swatch-value').hasClass('selected')) {\n return;\n }\n\n var url = $(e.currentTarget).attr('href');\n $.spinner().start();\n $.ajax({\n url: url,\n type: 'GET',\n success: function (data) {\n const $productTile = $(e.target).closest('.product-tile-cell');\n $productTile.html(data);\n startCarouselTileImageFunction($productTile.find('.js-tileImageCarousel'));\n $('body').trigger('product:didChangeColor');\n $.spinner().stop();\n },\n error: function () {\n $.spinner().stop();\n }\n });\n });\n }\n\n sizeAttribute () {\n $('body').on('change', '[data-attr=\"size\"] input', e => {\n e.preventDefault();\n $('.size-available').attr('available', true);\n const selectedValue = $(e.currentTarget).attr('value');\n $('#size').attr('size-attribute', $(e.currentTarget).attr('data-attr-value'));\n $('.persButtonPdpPers').attr('size-attribute', $(e.currentTarget).attr('data-attr-value'));\n if (selectedValue === 'null') {\n return;\n }\n\n let $productContainer = $(e.currentTarget).closest('.set-item');\n if (!$productContainer.length) {\n if ($(e.currentTarget).hasClass('js-add-size-saveForLater')) {\n var sku = $(e.currentTarget).data('sku');\n $productContainer = $(e.currentTarget).closest('.cart-line-item-sku-' + sku);\n } else {\n $productContainer = $(e.currentTarget).closest('.product-detail');\n }\n }\n if ($(e.currentTarget).closest('.product-quickview') && $(e.currentTarget).closest('.product-quickview').length) {\n $('.selectSizeQuickView').removeClass('toSelect');\n }\n if ($(e.currentTarget).closest('.js-complete-your-promo-quick-view')) {\n $(e.currentTarget).closest('.js-complete-your-promo-quick-view').find('.add-to-cart-global').data('disabled', false);\n }\n\n let ignoreCTA = $('.js-prod-select-size-modal').length && !Foundation.MediaQuery.atLeast('large');\n let isPdp = $('.page').data('action') && $('.page').data('action').toLowerCase().indexOf('product-show') > -1;\n let isPeronalizePage = $('#personalize-page');\n if (isPdp && isPeronalizePage) {\n $productContainer = $('.js-intProductDetail');\n }\n if ($('.js-complete-your-promo-quick-view').length > 0) {\n $productContainer = $('.js-complete-your-promo-quick-view');\n }\n if (isPdp && $('.js-prod-select-size-modal').length || isPeronalizePage && $('.js-prod-select-size-modal').length) {\n ignoreCTA = false;\n }\n\n let imagesShouldUpdate = true;\n if ($productContainer.hasClass('cart-line-item') || $productContainer.hasClass('js-complete-your-promo-quick-view') ) {\n imagesShouldUpdate = false;\n }\n attributeSelect(selectedValue, $productContainer, 'size', imagesShouldUpdate, ignoreCTA);\n var sizeData = $(e.currentTarget).data('attr-value');\n var skuData = $productContainer.data('variant-pid');\n skuData = skuData ? decodeURI(skuData).replace(/\\s+/g, '_') : '';\n\n let color = $('#analyticsSelectedColor').val();\n let splitSkuData = skuData ? skuData.split('_') : [];\n\n skuData = splitSkuData.length >= 2 && color.trim().length > 0 ? splitSkuData[0] + '_' + color : skuData;\n\n if ($('.page[data-action=\"Product-Show\"]').length > 0) {\n $('body').trigger('product:didChangeSize', { size: sizeData, sku: skuData });\n } else if ($('.page[data-action=\"Cart-Show\"]').length > 0) {\n $('body').trigger('product:didChangeSize', { size: sizeData, sku: skuData });\n }\n });\n $('.js-container').on('keydown', function (e) {\n if (e.type === 'keydown' && e.originalEvent.code === 'Enter') {\n $(e.currentTarget).trigger('click');\n }\n });\n $('body').on('change', '[data-attr=\"size-mobile\"] input', e => {\n e.preventDefault();\n $(\"[data-attr='size-mobile'] input\")\n .removeClass('js-mobile-size-selected')\n .closest('.js-intProductDetail-size-item')\n .removeClass('cc-intProductDetail-size-item_selected');\n $(e.currentTarget)\n .addClass('js-mobile-size-selected')\n .closest('.js-intProductDetail-size-item')\n .addClass('cc-intProductDetail-size-item_selected');\n let selectedSize = $(e.currentTarget).data('size-id');\n let $sizeSelectedeElem = $(`[data-size-id=\"${selectedSize}\"]`);\n $sizeSelectedeElem.each(function (element) {\n $(this).closest('.js-intProductDetail-size-item').addClass('cc-intProductDetail-size-item_selected');\n });\n $('js-sizeBox-openPanel').attr('');\n $('.js-selectedSizeMobile').text($(e.currentTarget).data('size-value'));\n $('#product-error-msg-mobile').addClass('invisible');\n $('#product-error-msg').hide();\n });\n $('body').on('click', '.js-linkMobileModalConfirmSize', e => {\n let $sizeSelected = $(\"[data-attr='size-mobile'] input.js-mobile-size-selected\");\n $('.size-available').attr('available', true);\n const selectedValue = $sizeSelected.attr('value');\n $('#size').attr('size-attribute', $sizeSelected.attr('data-attr-value'));\n $('.persButtonPdpPers').attr('size-attribute', $sizeSelected.attr('data-attr-value'));\n if (selectedValue === undefined || selectedValue === null || selectedValue === 'null') {\n $('#product-error-msg-mobile').removeClass('invisible');\n return;\n }\n $('#product-error-msg-mobile').addClass('invisible');\n\n let $productContainer = $sizeSelected.closest('.set-item');\n if (!$productContainer.length) {\n $productContainer = $sizeSelected.closest('.product-detail');\n }\n if ($sizeSelected.closest('.product-quickview') && $sizeSelected.closest('.product-quickview').length) {\n $('.selectSizeQuickView').removeClass('toSelect');\n }\n\n let ignoreCTA = $('.js-prod-select-size-modal').length && !Foundation.MediaQuery.atLeast('large');\n let isPdp = $('.page').data('action') && $('.page').data('action').toLowerCase().indexOf('product-show') > -1;\n let isPeronalizePage = $('#personalize-page');\n if (isPdp && $('.js-prod-select-size-modal').length || isPeronalizePage && $('.js-prod-select-size-modal').length) {\n ignoreCTA = false;\n }\n\n let imagesShouldUpdate = true;\n if ($productContainer.hasClass('cart-line-item')) {\n imagesShouldUpdate = false;\n }\n attributeSelect(selectedValue, $productContainer, 'size', imagesShouldUpdate, ignoreCTA);\n var sizeData = null;\n var skuData = null;\n if ($('.page[data-action=\"Product-Show\"]').length > 0) {\n sizeData = $sizeSelected.attr('data-attr-value');\n skuData = $productContainer.data('master-pid');\n }\n $('body').trigger('product:didChangeSize', { size: sizeData, sku: skuData });\n });\n $('body').on('change', '[data-attr=\"size\"] input', e => {\n e.preventDefault();\n $(\"[data-attr='size'] input\")\n .removeClass('js-mobile-size-selected')\n .closest('.js-intProductDetail-size-item')\n .removeClass('cc-intProductDetail-size-item_selected');\n $(e.currentTarget)\n .addClass('js-mobile-size-selected');\n let selectedSize = $(e.currentTarget).data('size-id');\n let $sizeSelectedeElem = $(`[data-size-id=\"${selectedSize}\"]`);\n $sizeSelectedeElem.each(function (element) {\n $(this).closest('.js-intProductDetail-size-item').addClass('cc-intProductDetail-size-item_selected');\n });\n $('#product-error-msg').hide();\n });\n }\n\n sizeAttributeQuickAddListing () {\n $('body').on('click', '.quick-buy-sizes-item', function (e) {\n e.preventDefault();\n\n const selectedValue = $(e.currentTarget).data('url');\n if (selectedValue === 'null') {\n return;\n }\n\n let $productContainer = $(e.currentTarget).closest('.product-tile');\n let imagesShouldUpdate = true;\n if ($productContainer.hasClass('cart-line-item')) {\n imagesShouldUpdate = false;\n }\n attributeSelect(selectedValue, $productContainer, 'size', imagesShouldUpdate, true);\n $('body').trigger('product:didChangeSize');\n });\n\n $('body').on('quickBuy:addToCart', function (e, data) {\n if (!$('.modal-size-show').length) {\n return;\n }\n\n $('.modal-size-show').find('.js-add-to-cart').data('pid', data.product.id).trigger('click');\n $('body').trigger('quickBuy:afterAddToCart');\n });\n }\n\n sizeAttributeQuickAddPDP () {\n if ($('.page').data('action') !== 'Product-Show') {\n return;\n }\n $('body').on('click', '.js-quick-buy-sizes-item-pdp', function (e) {\n e.preventDefault();\n if ($(this).hasClass('disable') || !$(this).data('variant')) {\n return false;\n }\n\n var url = $(this).data('variant');\n $.spinner().start();\n $.ajax({\n url: url,\n type: 'GET',\n dataType: 'json',\n success: function (response) {\n $.spinner().stop();\n const $productContainer = $(e.target);\n\n // For minicart promo carousel\n var promotionId = $productContainer.closest('.product').find('.promotion-info-plp').data('promo-id') || false;\n\n if (response.product.available && !response.product.comingSoon) {\n addToCartFromListing(response.product.id, promotionId, $productContainer);\n } else {\n $('body').trigger('product:afterAddToCartFailed', {\n ...response,\n $productContainer\n });\n }\n },\n error: function (err) {\n console.error('ErrorCase: ' + err.message);\n $.spinner().stop();\n }\n });\n });\n }\n\n sizeAttributeSet () {\n $('.set-size').on('click', function (e) {\n $($(e.currentTarget).closest('.product-content-size')[0]).children('.set-size').children('.radio-label-set').removeClass('setsize-selected');\n $(e.currentTarget).children('.radio-label-set').addClass('setsize-selected');\n const selectedValue = e.currentTarget.children[0].value;\n if (selectedValue === 'null') {\n return;\n }\n\n var $productContainer = $(e.currentTarget).closest('.product-detail');\n attributeSelect(selectedValue, $productContainer, 'size', false);\n\n $('body').trigger('product:didChangeSize');\n });\n }\n\n isSizeSelected () {\n if ($('.page-checkout').length > 0 || $('.cart-page').length > 0 || $('.modal-size-show').length > 0 || isMiniCartOpen()) {\n return true;\n }\n return $('[data-attr=\"size\"] input:checked').length > 0;\n };\n\n quantity () {\n updateQuantityPicker(null);\n\n $('body').on('click', '.js-quantity-button', function (e) {\n const $button = $(this);\n var $target = $button.closest('.quantity').find('.js-quantity-value');\n var $input = $button.closest('.quantity').find('.quantity-select');\n if ($button.hasClass('js-quantity-button-quick-add')) {\n $target = $button.closest('.quantity').find('.js-quantity-value-quick-add');\n $input = $button.closest('.quantity').find('.quantity-select-quick-add');\n }\n const value = parseInt($target.text());\n if ($button.data('action') === 'increase' && value < 10 && !$button.hasClass('disabled')) {\n let newValue = value + 1;\n $('.js-quantity-value').text(newValue);\n $input.val(newValue);\n\n $('.update-cart-url').data('selected-quantity', newValue);\n $(`[data-opener=\"QNT\"] .attribute-selection`).html(newValue);\n\n updateQuantityPicker($button);\n $input.trigger('change');\n } else if ($button.data('action') === 'decrease' && value > 1 && !$button.hasClass('disabled')) {\n let newValue = value - 1;\n $('.js-quantity-value').text(newValue);\n $input.val(newValue);\n $('.update-cart-url').data('selected-quantity', newValue);\n $(`[data-opener=\"QNT\"] .attribute-selection`).html(newValue);\n\n updateQuantityPicker($button);\n $input.trigger('change');\n }\n });\n }\n\n availability () {\n $('body').on('change', '.quantity-select', e => {\n e.preventDefault();\n\n var $productContainer = $(e.currentTarget).closest('.product-detail');\n if (!$productContainer.length) {\n $productContainer = $(e.currentTarget).closest('.modal-content').find('.product-quickview');\n }\n if (!$productContainer.length) {\n $productContainer = $(e.currentTarget).closest('.product-tile-modal');\n }\n\n if ($('.bundle-items', $productContainer).length === 0) {\n attributeSelect($(e.currentTarget).find('option:selected').data('url'),\n $productContainer, '_', false);\n }\n });\n $('body').on('change', '.quantity-select-quick-add', e => {\n e.preventDefault();\n\n var $productContainer = $(e.currentTarget).closest('.product-detail-quick-add');\n if ($('.bundle-items', $productContainer).length === 0) {\n attributeSelectQuickAdd($(e.currentTarget).find('option:selected').data('url'),\n $productContainer, '_', false);\n }\n });\n }\n\n addToCart () {\n $('body').on('click', 'button.js-add-to-cart, button.add-to-cart-global, button.js-add-to-cart-multipack', (e) => {\n const _openStickySizeSelectorModal = (target) => {\n if ($(e.currentTarget).hasClass('add-to-cart-multipack')) {\n sizePanel.openSizePanel(sizePanel.Types.ADDTOCART_BUNDLE);\n } else if ($(e.currentTarget).closest('.js-pdpStickyBar-btn').length > 0) {\n $('.js-pdpStickyBar-select').addClass('cc-sizeBox-isOpen');\n } else {\n if ($('.cc-intProductDetail-size-item_selected').length === 0) {\n $('#product-error-msg-mobile').removeClass('invisible');\n }\n sizePanel.openSizePanel(sizePanel.Types.ADDTOCART);\n }\n $('.pdp-size-box .js-sizeBox-openPanel').addClass('cc-sizeBox-openPanel_error');\n $('#product-error-msg').show();\n $('.pdp-size-box .js-sizeBox-openPanel').attr('aria-invalid', 'true');\n };\n\n let addToCartUrl;\n let pid;\n let pidsObj;\n let setPids;\n let isPersonalizedProduct = $('.js-personalizeButtonCheckout').length > 0;\n\n let target = e.currentTarget;\n if ($(target).closest('.js-addToCartStickyBar').length > 0) {\n // open the size modal\n _openStickySizeSelectorModal(target);\n return;\n }\n if ($(target).closest('.js-addToCartStickyBar').length > 0) {\n // close quickview modal\n _openStickySizeSelectorModal(target);\n }\n\n var $productContainer = $(e.currentTarget).closest('.product-detail');\n\n if (!$productContainer.length) {\n $productContainer = $(e.currentTarget).closest('.quickview-modal').find('.product-detail');\n }\n\n if (!$productContainer.length) {\n $productContainer = $('.quickview-modal').find('.product-detail');\n }\n\n if (!$productContainer.length) {\n $productContainer = $('.product-detail');\n }\n\n const GTMItem = getGtmData({\n item_id: $('.analytics.product').attr('data-item_id'),\n item_variant: $('.analytics.product').attr('data-item_variant')\n });\n\n // here we add the personalized product - if there is the personalizeButtonCheckout button, we are adding a pers product\n if (isPersonalizedProduct) {\n var text = $('.form-text').val();\n\n // here we check the symbolType - in personalization we store the symbols with a number. Here we substitute them with character\n /*\n if ($('.form-symbolType').val() != '') {\n var symbol = $('.form-symbol').val();\n\n switch (symbol) {\n case '1':\n symbol = '/_%*_';\n break;\n case '2':\n symbol = '-_%*_';\n break;\n case '3':\n symbol = '__%*_';\n break;\n case '4':\n symbol = '*_%*_';\n break;\n }\n\n switch ($('.form-symbolType').val()) {\n case 'letters':\n switch ($('.form-text').val().length) {\n case 1:\n text = $('.form-text').val()[0] + symbol;\n break;\n case 2:\n text = $('.form-text').val()[0] + symbol + $('.form-text').val()[1];\n break;\n case 3:\n text = $('.form-text').val()[0] + $('.form-text').val()[1] + symbol + $('.form-text').val()[2];\n break;\n case 4:\n text = $('.form-text').val()[0] + $('.form-text').val()[1] + symbol + $('.form-text').val()[2] + $('.form-text').val()[3];\n break;\n }\n\n break;\n case 'nameSymbol':\n text = $('.form-text').val() + symbol;\n break;\n case 'symbolName':\n text = symbol + $('.form-text').val();\n break;\n default:\n text = $('.form-text').val();\n }\n }\n */\n var personalizationText = text;\n var personalizationTextFont;\n personalizationTextFont = $('.form-font').val().indexOf('GillSansNova') > -1\n ? 'Avant'\n : ($('.form-font').val().indexOf('Didot') > -1\n ? 'Didot'\n : $('.form-font').val().indexOf('Altastgreeting') > -1\n ? 'Altastgreeting'\n : '');\n\n var personalizationColorPref = window.PersonalizationColor.personalizationColor;\n var personalizationColorJson = JSON.parse(personalizationColorPref);\n\n var personalizationTextColor;\n for (var i = 0; i < personalizationColorJson.length; i++) {\n if (personalizationColorJson[i].alt === $('.form-color').val()) {\n var src = personalizationColorJson[i].src;\n src = src.substring(0, src.lastIndexOf('.'));\n personalizationTextColor = src;\n }\n }\n\n var personalizationPositionKey = $('.form-position').val();\n\n // ----\n\n var customizationClassPref = window.CustomizationClass.customizationClass;\n var customizationClassJson = JSON.parse(customizationClassPref);\n var category = $('#category').attr('category-attribute');\n personalizationPositionKey = (customizationClassJson[category]['customizationPositions'] === 1)\n ? customizationClassJson[category]['0']\n : customizationClassJson[category][($('.form-position').val()).toString()];\n\n // ----\n\n var personalizationTextSVG = $('#base64').attr('data-fullTextSVG');\n var personalizationFullSVG = $('#base64').attr('data-fullSVG');\n var personalizationSmallSVG = $('#base64').attr('data-smallSVG');\n\n $.spinner().start();\n\n addToCartUrl = $('#custom-page').attr('data-url');\n var quantity = $('.js-quantity-value').html();\n var uniqueIdentifiers = {};\n for (var i = 0; i < quantity; i++) {\n var random = Math.random();\n var id = 'uniqueIdentifier' + i;\n uniqueIdentifiers[id] = random;\n }\n uniqueIdentifiers = JSON.stringify(uniqueIdentifiers);\n\n if ($('#pidToAdd').attr('pidRecentlyAdded') == undefined) {\n // $('#custom-page').attr('data-pid', $('#pidToAdd').attr('data-pid'));\n $('#pidToAdd').attr('isToLoad', 'false');\n }\n\n if ($('#pidToAdd').attr('isToLoad') == 'true') {\n $('#custom-page').attr('data-pid', $('#pidToAdd').attr('pidRecentlyAdded'));\n }\n\n $('#pidToAdd').attr('pidRecentlyAdded', $('.personalizeButtonBtn').attr('product-id'));\n\n if (quantity > 1) {\n var form = {\n pid: $('.personalizeButtonBtn').attr('product-id'),\n quantity: quantity,\n personalizedObj: true,\n uniqueIdentifiers: uniqueIdentifiers, // Random value\n personalizationText: personalizationText,\n personalizationTextFont: personalizationTextFont,\n personalizationTextColor: personalizationTextColor,\n personalizationPositionKey: personalizationPositionKey,\n personalizationTextSVG: personalizationTextSVG,\n personalizationFullSVG: personalizationFullSVG,\n personalizationSmallSVG: personalizationSmallSVG,\n isDate: $('.choice-item.choice-item-3').hasClass('active'),\n isLove: $('#love').hasClass('active'),\n GTMItemListName: GTMItem.item_list_name,\n GTMItemListId: GTMItem.item_list_id,\n GTMIndex: GTMItem.index\n };\n } else {\n var form = {\n pid: $('.personalizeButtonBtn').attr('product-id'),\n quantity: quantity,\n personalizedObj: true,\n uniqueIdentifier: Math.random(), // Random value\n personalizationText: personalizationText,\n personalizationTextFont: personalizationTextFont,\n personalizationTextColor: personalizationTextColor,\n personalizationPositionKey: personalizationPositionKey,\n personalizationTextSVG: personalizationTextSVG,\n personalizationFullSVG: personalizationFullSVG,\n personalizationSmallSVG: personalizationSmallSVG,\n isDate: $('.choice-item.choice-item-3').hasClass('active'),\n isLove: $('#love').hasClass('active'),\n GTMItemListName: GTMItem.item_list_name,\n GTMItemListId: GTMItem.item_list_id,\n GTMIndex: GTMItem.index\n };\n }\n $('.js-customizePage .js-customizePage-icon_pageClose').trigger('click');\n } else {\n // ------\n if (!$(e.currentTarget).hasClass('product-set')) {\n // Simulate disabled button with class to allow click and event\n if ($(e.currentTarget).data('disabled') || !this.isSizeSelected()) {\n $('.persButtonPdpAdd').show();\n $('.persButtonPdpPers').hide();\n // If no size is selected, open modal to choose one\n if (!$('.cc-text.selected-size-msg.show-when-size-selected')) {\n $('#newsletter-error-msg').toggle();\n }\n if ($(e.currentTarget).closest('.quickview-modal').length) {\n // QuickView (Open the other modal type)\n\n let modal = $('.js-modal-quick-size-quantity');\n // First check if it is open\n if (modal.hasClass('open')) {\n // Check if size is selected, then add to cart\n } else {\n // Show it\n modal.removeClass('hidden').addClass('open');\n modal.find('.slick-slider.slick-initialized').slick('refresh');\n\n modal.find('.js-close-select-size').on('click', function (e) {\n modal.addClass('hidden').removeClass('open');\n });\n if ($('.js-modal-quick-size-quantity [data-attr=\"size\"] input#TU:checked').length > 0\n && $('.quickview-modal .global-availability').data('ready-to-order')) {\n $('.quickview-modal').find('button.add-to-cart-global').data('disabled', false);\n }\n if (Foundation.MediaQuery.is('small')) {\n $('.quickview-modal .wrapper-details').animate({\n scrollTop: $('.wrapper-inner-quick-bottom').eq(0).offset().top\n }, 500);\n }\n }\n } else {\n _openStickySizeSelectorModal(e.currentTarget);\n }\n\n // Prevent further progress until a size is selected\n return;\n }\n }\n\n $('body').trigger('product:beforeAddToCart', e.currentTarget);\n\n if ($('.set-items').length && $(e.currentTarget).hasClass('add-to-cart-global')) {\n setPids = [];\n\n $('.product-detail').each(function () {\n if (!$(e.currentTarget).hasClass('product-set-detail')) {\n setPids.push({\n pid: $(e.currentTarget).find('.product-id').text(),\n qty: $(e.currentTarget).find('.quantity-select').val(),\n options: []\n });\n }\n });\n pidsObj = JSON.stringify(setPids);\n }\n\n pid = getPidValue($(e.currentTarget));\n // console.log(pid);\n\n if ($(target).closest('div.js-pdpStickyBar-btn').length > 0) {\n $productContainer.addClass('analytics-addToCart-sticky');\n }\n\n addToCartUrl = getAddToCartUrl();\n\n let uid = $(e.currentTarget).data('uid');\n\n var pidSet;\n var buttonAdd = $('button.js-add-to-cart, button.add-to-cart-global, button.update-cart-product-global');\n\n for (var j = 0; j < buttonAdd.length; j++) {\n if (uid === $(buttonAdd[i]).data('uid')) {\n pidSet = $(buttonAdd[i]).attr('data-pid');\n }\n }\n\n var promoId = $('.js-promo-msg.marketing-budge', $productContainer).first().data('promotion-id') || false;\n\n // ------\n var form = {\n pid: pid || pidSet,\n pidsObj: pidsObj,\n childProducts: [],\n quantity: getQuantitySelected($(e.currentTarget)),\n uuid: uid,\n promoId: promoId,\n GTMItemListName: GTMItem.item_list_name,\n GTMItemListId: GTMItem.item_list_id,\n GTMIndex: GTMItem.index\n };\n\n if (!$('.bundle-item').length) {\n form.options = [];\n }\n\n if ($('.js-complete-your-promo').length > 0) {\n $('.js-complete-the-promo-status').val($('.js-complete-the-promo-status').val() - form.quantity);\n form.completePromoItems = $('.js-complete-the-promo-status').val();\n $productContainer.addClass('analytics-completeYourPromo');\n }\n }\n\n $(e.currentTarget).trigger('updateAddToCartFormData', form);\n $('body').trigger('updateQuickAddToCartModal', form);\n if (addToCartUrl) {\n $.ajax({\n url: addToCartUrl,\n method: 'POST',\n data: form,\n success: data => {\n $.spinner().stop();\n if (data.error && isPersonalizedProduct) {\n $('.content-input-err').removeClass('hidden');\n } else {\n if (data.completePromoItemsLabel && data.completePromoItemsLabel !== '' && $('.js-completeYourPromo-header_remaining').length > 0) {\n $('.js-completeYourPromo-header_remaining').html(data.completePromoItemsLabel);\n if (form.completePromoItems === '0') {\n $('.js-completeYourPromo-header_remaining').addClass('cc-cartPromotionModal-footer_completed');\n }\n }\n $('body').trigger('product:afterAddToCart', {\n ...data,\n form,\n $productContainer\n });\n data.quantityTotal = data.cart ? data.cart.numItems : data.cartModel.numItems;\n handlePostCartAdd(data);\n }\n },\n error: () => {\n $.spinner().stop();\n }\n });\n }\n });\n }\n\n /*\n selectBonusProduct () {\n $('body').on('click', '.select-bonus-product', function () {\n var $choiceOfBonusProduct = $(this).parents('.choice-of-bonus-product');\n var pid = $(this).data('pid');\n var maxPids = $('.choose-bonus-product-dialog').data('total-qty');\n var submittedQty = parseInt($(this).parents('.choice-of-bonus-product').find('.bonus-quantity-select').val(), 10);\n var totalQty = 0;\n $.each($('#chooseBonusProductModal .selected-bonus-products .selected-pid'), function () {\n totalQty += $(this).data('qty');\n });\n totalQty += submittedQty;\n var optionID = $(this).parents('.choice-of-bonus-product').find('.product-option').data('option-id');\n var valueId = $(this).parents('.choice-of-bonus-product').find('.options-select option:selected').data('valueId');\n if (totalQty <= maxPids) {\n const selectedBonusProductHtml = `\n
\n\n
${$choiceOfBonusProduct.find('.product-name').html()}
'\n
\n \n
\n
`;\n\n $('#chooseBonusProductModal .selected-bonus-products').append(selectedBonusProductHtml);\n $('.pre-cart-products').html(totalQty);\n $('.selected-bonus-products .bonus-summary').removeClass('alert-danger');\n } else {\n $('.selected-bonus-products .bonus-summary').addClass('alert-danger');\n }\n });\n }\n */\n\n sizeTU () {\n if (document.getElementById('TU')) {\n document.getElementById('TU').click();\n }\n }\n\n quickAddListener () {\n $('body').on('click', '.js-panel-opener-size-quick-add', function (e, data) {\n /** open/close quickAdd modal**/\n e.preventDefault();\n if ($(this).find('.icon-toggle-top.triangle-dropdown-pdp').hasClass('icon-toggle-opened')) {\n $('.js-modal-quick-add-size-quantity').addClass('hidden');\n $('.product-detail-quick-add .icon-toggle-top.triangle-dropdown-pdp').removeClass('icon-toggle-opened');\n $('.product-detail-quick-add .size-opener-opened').addClass('hidden');\n $('.product-detail-quick-add .size-opener-closed').removeClass('hidden');\n } else {\n $('.product-detail-quick-add .icon-toggle-top.triangle-dropdown-pdp').removeClass('icon-toggle-opened');\n $(this).find('.icon-toggle-top.triangle-dropdown-pdp').addClass('icon-toggle-opened');\n var mustAdd = (data && data.mustAdd === true) || false;\n $(this).closest('.product-detail-quick-add').find('.add-to-cart-quick-add').data('mustAdd', mustAdd);\n const pid = $(this).attr('data-pid');\n const url = $(this).attr('data-get-url');\n $(this).find('.size-opener-opened').removeClass('hidden');\n $(this).find('.size-opener-closed').addClass('hidden');\n showQuickAddItems(pid, url);\n }\n });\n\n $('body').on('click', '.js-close-select-size-quick-add', function (e) {\n /** close quickAdd modal**/\n e.preventDefault();\n $('.js-modal-quick-add-size-quantity').addClass('hidden');\n $('.product-detail-quick-add .icon-toggle-top.triangle-dropdown-pdp').removeClass('icon-toggle-opened');\n $('.product-detail-quick-add .size-opener-opened').addClass('hidden');\n $('.product-detail-quick-add .size-opener-closed').removeClass('hidden');\n });\n\n $('body').on('change', '[data-attr=\"size_qa\"] input ', e => {\n /** change size and update attribute for the cart**/\n e.preventDefault();\n const selectedValue = $(e.currentTarget).attr('value');\n if (selectedValue === 'null') {\n return;\n }\n\n let $productContainer = $(e.currentTarget).closest('.product-detail-quick-add');\n if ($productContainer && $productContainer.length > 0) {\n attributeSelectQuickAdd(selectedValue, $productContainer, '_', false);\n $productContainer.find('.add-to-cart-quick-add').attr('data-size-available', true);\n $productContainer.find('.add-to-cart-quick-add').attr('data-size-selected', $(e.currentTarget).data('attr-id'));\n $productContainer.find('.add-to-cart-quick-add').removeClass('item-added-quick');\n }\n $('body').trigger('product:didChangeSize');\n });\n\n $('body').on('product:updateAddToCartQuickAdd', (e, response) => {\n /** manage response variation after size selection **/\n let availabilityValue = '';\n let availabilityMessages = response.product.availability.messages;\n var $productContainer = response.$productContainer;\n $productContainer.find('.response-message-quick-add').empty();\n if ($productContainer.find('[data-attr=\"size_qa\"] input:checked') && $productContainer.find('[data-attr=\"size_qa\"] input:checked').length > 0) {\n var sizeChecked = $productContainer.find('[data-attr=\"size_qa\"] input:checked').attr('data-display-value');\n $productContainer.find('.size-selected').text(sizeChecked);\n $productContainer.find('.response-message-quick-add').addClass('hidden');\n $productContainer.find('.add-to-cart-quick-add').attr('data-size-available', true);\n $productContainer.find('.add-to-cart-quick-add').attr('data-pid', response.product.id);\n $productContainer.find('.response-error-quick-add').addClass('hidden');\n }\n if (!response.product.readyToOrder) {\n $productContainer.find('.add-to-cart-quick-add').attr('data-disabled', true);\n $productContainer.find('.add-to-cart-quick-add').attr('disabled', true);\n } else if (!response.product.available || response.product.comingSoon) {\n $productContainer.find('.add-to-cart-quick-add').attr('data-disabled', true);\n $productContainer.find('.add-to-cart-quick-add').attr('disabled', true);\n availabilityMessages.forEach(message => {\n availabilityValue += `
${message}
`;\n });\n $productContainer.find('.response-message-quick-add').html(availabilityValue);\n } else {\n $productContainer.find('.add-to-cart-quick-add').attr('data-disabled', false);\n $productContainer.find('.add-to-cart-quick-add').attr('disabled', false);\n }\n });\n\n $('body').on('click', 'button.add-to-cart-quick-add', (e) => {\n if ($(e.currentTarget).closest('.completeYourLookContainer').length > 0) {\n localStorage.setItem('prevlisttypeforcart', localStorage.getItem('listtypeforcart'));\n localStorage.setItem('listtypeforcart', 'complete_your_look');\n }\n\n let addToCartUrl;\n let pidsObj;\n const $productContainer = $(e.currentTarget).closest('.product-detail-quick-add');\n // Simulate disabled button with class to allow click and event\n if ($(e.currentTarget).attr('data-size-available') !== 'true') {\n $productContainer.find('.response-message-quick-add').removeClass('hidden');\n return;\n } else if ($(e.currentTarget).attr('data-disabled') === 'true' || $(e.currentTarget).attr('data-disabled') === 'NaN') {\n return;\n }\n $productContainer.find('.response-message-quick-add').addClass('hidden');\n $productContainer.find('.response-error-quick-add').addClass('hidden');\n\n $('body').trigger('product:beforeAddToCart', e.currentTarget);\n\n let pid = $(e.currentTarget).attr('data-pid');\n let uid = $(e.currentTarget).attr('data-uid');\n let quantitySelected = parseInt($(e.currentTarget).attr('data-quantity')) || 1;\n\n addToCartUrl = getAddToCartUrl();\n\n let promoId = false;\n if ($('.promoCrossSellEnabled').length > 0) {\n promoId = $('.js-promo-msg.marketing-budge').first().data('promotion-id') || false;\n }\n\n const GTMItem = getGtmData({\n item_id: $('.analytics.product').attr('data-item_id'),\n item_variant: $('.analytics.product').attr('data-item_variant')\n });\n\n var form = {\n pid: pid,\n pidsObj: pidsObj,\n childProducts: [],\n quantity: quantitySelected,\n uuid: uid,\n promoId: promoId,\n GTMItemListName: GTMItem.item_list_name,\n GTMItemListId: GTMItem.item_list_id,\n GTMIndex: GTMItem.index\n };\n\n $(e.currentTarget).trigger('updateAddToCartFormData', form);\n if (addToCartUrl) {\n $.ajax({\n url: addToCartUrl,\n method: 'POST',\n data: form,\n success: data => {\n $.spinner().stop();\n if (data.error) {\n $productContainer.find('.response-error-quick-add').removeClass('hidden');\n } else {\n $('body').trigger('product:afterAddToCart', {\n ...data,\n form,\n $productContainer\n });\n data.quantityTotal = data.cart.numItems;\n handlePostCartAdd(data);\n $productContainer.find('.add-to-cart-quick-add').addClass('item-added-quick');\n $('.js-modal-quick-add-size-quantity').addClass('hidden');\n $('.product-detail-quick-add .icon-toggle-top.triangle-dropdown-pdp').removeClass('icon-toggle-opened');\n $('.product-detail-quick-add .size-opener-opened').addClass('hidden');\n $('.product-detail-quick-add .size-opener-closed').removeClass('hidden');\n }\n },\n error: () => {\n $.spinner().stop();\n }\n });\n }\n });\n }\n\n checkSoldoutAvailability () {\n if ($('.page').data('action') !== 'Product-Show') {\n return;\n }\n var $productContainer = $('div.product-detail.container').first();\n var attributesUpdateUrl = $productContainer.data('variationAttrUpdate');\n if (!attributesUpdateUrl) {\n return;\n }\n $.ajax({\n url: attributesUpdateUrl,\n method: 'GET',\n dataType: 'json',\n success: data => {\n if (data.product && data.product.variationAttributes) {\n updateAttrs(data.product.variationAttributes, $productContainer);\n updateAvailability(data, $productContainer);\n $('body').trigger('product:updateAddToCart', {\n product: data.product,\n $productContainer: $productContainer\n });\n // reorder swatches in order to push soldout colors in the laste positions\n reorderSwatches($('.js-carousel-select-color.not-sale-container'));\n reorderSwatches($('.js-carousel-select-color.on-sale-container'));\n }\n }\n });\n }\n registerAttributionTokenSending () {\n $('body').on('click', '.js-google-recommendations-container .js-prodTile', function () {\n const attributionToken = $(this).closest('.js-google-recommendations-container').data('attributionToken');\n createCookie('attribution_token', attributionToken);\n });\n }\n loadGoogleRecommendations () {\n const $googleConfig = $('.js-googleRecommendationConfig');\n if ($googleConfig.length) {\n const url = $('#googleRecommendationsUrl').val();\n const servingConfig = $googleConfig.data('servingConfig');\n const nodeToAppendTo = $googleConfig.data('nodeToAppendTo');\n const cgid = $('#primaryCategoryId').val();\n const sku = $('#variationGroupSku').val();\n const route = $('.page').data('action');\n\n $.ajax({\n type: 'GET',\n url: url,\n data: {\n cgid: cgid,\n sku: sku,\n route: route,\n servingConfig: servingConfig\n },\n success: function (html) {\n const $outputContainer = $(nodeToAppendTo).find('.google-recommendation-results');\n if (!$outputContainer.length) {\n $('
').appendTo(nodeToAppendTo);\n }\n $(nodeToAppendTo).find('.google-recommendation-results').empty().append(html);\n },\n error: function () {\n $('#youMayAlsoLikeContainer').addClass('hidden');\n }\n });\n }\n }\n\n createNextPageToken () {\n const $googleAttributionToken = $('.js-google-search-token');\n if ($googleAttributionToken.length) {\n const attributionToken = $googleAttributionToken.data('attributiontoken');\n const previousPageToken = $googleAttributionToken.data('nextpagetoken');\n const url = new URL(window.location.href);\n const searchTerm = url.searchParams.get('q');\n createCookie('prev_search_query', searchTerm);\n createCookie('search_attribution_token', attributionToken);\n if (previousPageToken !== null) {\n createCookie('previousPageToken', previousPageToken);\n }\n }\n }\n}\n\nconst productHelpers = new ProductHelpers();\nexport default productHelpers;\nexport {\n moveModalCloseButton,\n parseHtml,\n activatePromoAnimationMessage,\n updateColorFamily,\n updatePrices,\n updateAvailability,\n updateOptions,\n updateQuantities,\n isMiniCartOpen,\n isChooseBonusProductModalOpen,\n isQuickUpdateFromModal,\n isMobileDevice\n};\n","'use strict';\n\nimport {\n newModalFromSelector\n} from '../components/modal';\n\nimport sizePanel from './sizePanel';\n\n// Checks if size is selected before adding to wishlist\nfunction isSizeSelected () {\n if ($('.page-checkout').length > 0 || $('.cart-page').length > 0) {\n return true;\n }\n if ($('.form-control.pdp-size-box.checkbox-size').length > 0 || $('.form-control.pdp-size-box.checkbox-quickview-mobile').length > 0) {\n return ($('.form-control.pdp-size-box.checkbox-size input:checked').length > 0 || $('.form-control.pdp-size-box.checkbox-quickview-mobile input:checked').length > 0);\n } else {\n return $('[data-attr=\"size\"] input:checked').length > 0;\n }\n};\n\n\n/**\n * Adapts FE to the current state of the wishlist:\n * - Add / Remove the `added` class to the correct target (either button or icon)\n * - Shows the \"correctly added\" / \"correctly removed\" notification\n * - Triggers ADD event for analytics\n * - Add/remove the PID from the ID in page to always have the correct state\n * (updateWishlistInternalState)\n * @param {string} data - data returned from the server's ajax call\n * @param {Object} icon - icon that was clicked to toggle a product to the wishlist\n * @param {boolean} isAddAction - if the te action was add or remove\n */\nfunction displayMessageAndChangeIcon (data, icon, isAddAction) {\n if (data.success) {\n $('body').trigger('wishlist:update', data.wishlistTotal);\n\n if (icon) {\n if (isAddAction) {\n if ($('.page').data('action') === 'Product-Show' && $('.js-pdpStickyBar').length > 0) {\n $('.wishlist-icon').addClass('added');\n $('.wishlist-icon').find('use').attr('href', icon.data('full-heart'));\n } else {\n icon.addClass('added');\n icon.find('use').attr('href', icon.data('full-heart'));\n }\n let sender = icon.data('analytics-sender') ? icon.data('analytics-sender') : '';\n $('body').trigger('wishlist:add', { sku: data.pid, sender: sender });\n } else {\n if ($('.page').data('action') === 'Product-Show' && $('.js-pdpStickyBar').length > 0) {\n $('.wishlist-icon').removeClass('added');\n $('.wishlist-icon').find('use').attr('href', icon.data('empty-heart'));\n } else {\n icon.removeClass('added');\n icon.find('use').attr('href', icon.data('empty-heart'));\n }\n }\n updateAriaLabelForWishlistLink($('.wishlist-icon'));\n icon.blur();\n }\n\n showWishlistNotification(data.renderedTemplate);\n\n updateWishlistInternalState(data.pid, isAddAction);\n }\n}\n\nfunction showWishlistNotification (html) {\n $('body').append(html);\n let offsetTop = 12;\n if (Foundation.MediaQuery.atLeast('large')) {\n offsetTop = $('.js-mainHeader').outerHeight() + 10;\n }\n $('.js-add-to-wishlist-notification').css({\n top: offsetTop\n });\n\n function closeNotification () {\n $('.js-add-to-wishlist-notification').off('click', '.js-close-notification');\n $('.js-add-to-wishlist-notification').remove();\n }\n\n $('.js-add-to-wishlist-notification').on('click', '.js-close-notification', closeNotification);\n\n setTimeout(closeNotification, 5000);\n}\n\n/**\n * Updates the internal state of the wishlist with the new item:\n * - adds the item in the state if the item was added\n * - removes the item if the item was removed\n * @param {string} pid - The PID of the product changed in the wishlist\n * @param {boolean} isAddAction - true if the item has been added, false is it has been removed\n */\nfunction updateWishlistInternalState (pid, isAddAction) {\n /** @type {Array.} */\n let oldItems = $('#wishlistItems').val().split(',');\n let newItems;\n if (isAddAction) {\n oldItems.push(pid);\n newItems = oldItems.join(',');\n } else {\n let oldIdx = oldItems.indexOf(pid);\n if (oldIdx > -1) {\n oldItems.splice(oldIdx, 1);\n newItems = oldItems.join(',');\n }\n }\n $('#wishlistItems').val(newItems);\n};\n\nfunction addDefinitelyToWishlist (sender, productID, e) {\n // If productID is set then it means that it belongs to an unavailable size\n // Add or remove from wishlist now!\n\n var btn = sender;\n var addURL = btn.data('href');\n var removeURL = btn.data('remove');\n\n let pid = '';\n if (productID === null) {\n pid = $('.product-detail-keeper').attr('data-variant-pid');\n } else {\n pid = productID;\n }\n var optionId = btn.closest('.product-detail-keeper').find('.product-option').attr('data-option-id');\n var optionVal = btn.closest('.product-detail-keeper').find('.options-select option:selected').attr('data-value-id');\n optionId = optionId || null;\n optionVal = optionVal || null;\n\n var shouldAdd = !btn.hasClass('added');\n\n if (!(addURL && removeURL) || !pid) {\n return;\n }\n\n $.spinner().start();\n $.ajax({\n url: shouldAdd ? addURL : removeURL,\n type: shouldAdd ? 'post' : 'get',\n dataType: 'json',\n data: {\n pid: pid,\n optionId: optionId,\n optionVal: optionVal\n },\n success: function (data) {\n // if (productID === null) {\n // displayMessageAndChangeIcon(data, btn, shouldAdd);\n // }\n if ($('.size-available').attr('available') != 'false') {\n displayMessageAndChangeIcon(data, btn, shouldAdd);\n }\n\n $('body').trigger('wishlist:changedSuccessfully', {\n data: data,\n isAdding: shouldAdd,\n pid: pid\n });\n var $productContainer = $(e.currentTarget).closest('.product-detail');\n\n if (!$productContainer.length) {\n $productContainer = $(e.currentTarget).closest('.quickview-modal').find('.product-detail');\n }\n\n if (!$productContainer.length) {\n $productContainer = $('.quickview-modal').find('.product-detail');\n }\n\n if (!$productContainer.length) {\n $productContainer = $('.product-detail');\n }\n if (shouldAdd) {\n $('body').trigger('product:afterAddToWishlist', { ...data, $productContainer });\n } else {\n $('body').trigger('product:afterRemoveFromWishlist');\n }\n $('body').trigger('wishlist:update', data.wishlistTotal);\n\n $.spinner().stop();\n },\n error: function (err) {\n $.spinner().stop();\n $('body').trigger('product:failedAddToWishlist');\n displayMessageAndChangeIcon(err, btn, shouldAdd);\n }\n });\n}\n\nfunction updateAriaLabelForWishlistLink (product) {\n var added = $(product).hasClass('added');\n var labelAddWishlist = product.data('label-add-wishlist');\n var labelRemoveWishlist = product.data('label-remove-wishlist');\n if (added) {\n product.attr('aria-label', labelRemoveWishlist);\n } else {\n product.attr('aria-label', labelAddWishlist);\n }\n}\n\nmodule.exports = {\n handleWishlistContainer: function (item) {\n if (module.exports.checkItemInWishlist(item)) {\n $('.wishlist-icon').addClass('added');\n $('.wishlist-icon').find('use').attr('href', $('.wishlist-icon').data('full-heart'));\n } else {\n $('.wishlist-icon').removeClass('added');\n $('.wishlist-icon').find('use').attr('href', $('.wishlist-icon').data('empty-heart'));\n }\n updateAriaLabelForWishlistLink($('.wishlist-icon'));\n },\n\n checkItemInWishlist: function (itemCode) {\n return $('#wishlistItems').length > 0 && $('#wishlistItems').val().split(',').indexOf(itemCode) > -1;\n },\n\n /**\n * Add the `added' class to the wishlist icon if the item is available in the wishlist.\n * It is not possible to do it in ISML because both the PDP and the PLP are cached\n *\n * Read the DOM element `#wishlistItems` and adds the `added` class to all the\n * `plp-wishlist` or `add-to-wish-list` items available in>\n * - quickview\n * - PDP\n * - PLP\n */\n highlightIconsForAllItemsInWishlist: function () {\n if (!$('#wishlistItems').length) {\n return;\n }\n\n var itemsInWishlist = $('#wishlistItems').val().split(',');\n for (var i = 0; i < itemsInWishlist.length; i++) {\n var itemCode = itemsInWishlist[i];\n\n let plpWishlist = $(`.product[data-pid=\"${itemCode}\"] .plp-wishlist`);\n let productDetailWishlist = $(`.product-detail[data-pid=\"${itemCode}\"] .add-to-wish-list`);\n\n plpWishlist.addClass('added');\n updateAriaLabelForWishlistLink(plpWishlist);\n plpWishlist.find('use').attr('xlink:href', plpWishlist.data('full-heart'));\n plpWishlist.blur();\n\n productDetailWishlist.addClass('added');\n updateAriaLabelForWishlistLink(productDetailWishlist);\n productDetailWishlist.find('use').attr('xlink:href', productDetailWishlist.data('full-heart'));\n productDetailWishlist.blur();\n }\n },\n\n moveToWishlistHelper: function (e) {\n if (!e) {\n return;\n }\n e.preventDefault();\n\n var $btn = $(e.currentTarget);\n var url = $btn.data('href');\n var pid = $btn.data('pid');\n\n $.spinner().start();\n return $.ajax({\n url: url,\n type: 'post',\n dataType: 'json',\n data: {\n pid: pid,\n optionId: null,\n optionVal: null\n },\n success: function (data) {\n displayMessageAndChangeIcon(data, null);\n },\n error: function (err) {\n displayMessageAndChangeIcon(err, null);\n }\n });\n },\n\n\n moveToWishlistHelperSaveForLater: function (e) {\n if (!e) {\n return;\n }\n e.preventDefault();\n\n var $btn = $(e.currentTarget);\n var url = $btn.data('href');\n var pid = $btn.data('pid');\n\n $.spinner().start();\n return $.ajax({\n url: url,\n type: 'post',\n dataType: 'json',\n data: {\n pid: pid,\n optionId: null,\n optionVal: null\n },\n success: function (data) {\n //displayMessageAndChangeIcon(data, null);\n },\n error: function (err) {\n displayMessageAndChangeIcon(err, null);\n }\n });\n },\n\n /**\n * Adds the current item referenced by the current target to the wishlist\n * and updates the front-end\n */\n addToWishlist () {\n $('body').on('click', '.add-to-wish-list', (e) => {\n e.preventDefault();\n let target = $(e.currentTarget);\n // Simulate disabled button with class to allow click and event\n if (($(e.currentTarget).hasClass('add-to-wish-list-quickview-mobile') && !isSizeSelected()) || ($(e.currentTarget).hasClass('wishlistButtMobile') && !$('.pdp-buy-look-container').hasClass('hidden'))) {\n return;\n } else if (!isSizeSelected()) {\n // If no size is selected, open modal to choose one\n if (target.closest('.product-quickview').length) {\n this.sizeModal = newModalFromSelector('fis-select-size-wishlist', false, ['js-prod-select-size-modal']);\n this.sizeModal.open();\n\n $(this.sizeModal.modalBox).find('.add-to-wish-list-confirm').attr('disabled', true);\n\n $(this.sizeModal.modalBox)\n .on('click', '.modal__closeIcon', (e) => {\n this.sizeModal.close();\n this.sizeModal.destroy();\n })\n .on('click', '.size-selector', (e) => {\n const $clickedButton = $(e.currentTarget);\n const sizeValue = $clickedButton.data('size-fixed');\n $clickedButton.closest('ul').find('button').not(e.currentTarget).removeClass('selected');\n $clickedButton.addClass('selected');\n\n const $inputToClick = $('[data-attr=\"size\"] input').filter(`[data-size-fixed=\"${sizeValue}\"]`);\n\n if ($clickedButton.data('attr-selectable') === 'selectable' && $inputToClick.prop('disabled') === false) {\n // Select size in PDP by passing click to attribute selector click only if selectable\n $inputToClick.trigger('click');\n $(this.sizeModal.modalBox).find('.add-to-wish-list-confirm').prop('disabled', false);\n $('.size-available').attr('available', true);\n } else {\n // Only if the size is not available\n let infoURL = $clickedButton.data('attr-info-url');\n if ($('.product-quickview').length > 0) {\n $('.product-quickview').find('.wishlist-icon').removeClass('added');\n $('.product-quickview').find('.wishlist-icon').find('use').attr('xlink:href', $('.wishlist-icon').data('empty-heart'));\n }\n var _self = this;\n $.spinner().start();\n $.ajax({\n url: infoURL,\n type: 'get',\n dataType: 'json',\n success: function (data) {\n $(_self.sizeModal.modalBox)\n .find('.add-to-wish-list-confirm')\n .prop('disabled', !data.product.readyToOrder);\n $('.product-detail-keeper').attr('data-variant-pid', encodeURIComponent(data.product.id));\n $('.product-detail').data('pid', data.product.id);\n $('.size-available').attr('available', false);\n $.spinner().stop();\n },\n error: function () {\n $.spinner().stop();\n }\n });\n }\n });\n\n $(this.sizeModal.modalBox).on('click', '.add-to-wish-list-confirm', (e) => {\n // Add to wishlist definitely\n let pid = null;\n if ($('.product-detail')) {\n pid = $('.product-detail').data('pid');\n } else if ($('.product-quickview')) {\n pid = $('.product-quickview').data('pid');\n }\n addDefinitelyToWishlist(target, pid, e);\n });\n\n $('body').on('product:afterAddToWishlist', (e) => {\n if (this.sizeModal.modal) {\n this.sizeModal.close();\n this.sizeModal.destroy();\n }\n });\n\n $('body').on('product:failedAddToWishlist', (e) => {\n if (this.sizeModal.modal) {\n this.sizeModal.close();\n this.sizeModal.destroy();\n }\n });\n } else {\n sizePanel.openSizePanel(sizePanel.Types.WISHILIST);\n $('.pdp-size-box .js-sizeBox-openPanel').addClass('cc-sizeBox-openPanel_error');\n }\n return;\n }\n addDefinitelyToWishlist(target, null, e);\n });\n\n $('body').on('wishlist:add-pid', (_, d) => {\n const target = $('.add-to-wish-list').eq(0);\n addDefinitelyToWishlist(target, d.pid, {currentTarget: target});\n });\n }\n};\n","/* build: `node build.js modules=ALL exclude=gestures,accessors requirejs minifier=uglifyjs` */\n/*! Fabric.js Copyright 2008-2015, Printio (Juriy Zaytsev, Maxim Chernyak) */\n\nvar fabric = fabric || { version: '3.6.6' };\nif (typeof exports !== 'undefined') {\n exports.fabric = fabric;\n}\n/* _AMD_START_ */\nelse if (typeof define === 'function' && define.amd) {\n define([], function() { return fabric; });\n}\n/* _AMD_END_ */\nif (typeof document !== 'undefined' && typeof window !== 'undefined') {\n if (document instanceof (typeof HTMLDocument !== 'undefined' ? HTMLDocument : Document)) {\n fabric.document = document;\n }\n else {\n fabric.document = document.implementation.createHTMLDocument('');\n }\n fabric.window = window;\n}\nelse {\n // assume we're running under node.js when document/window are not present\n var jsdom = require('jsdom');\n var virtualWindow = new jsdom.JSDOM(\n decodeURIComponent('%3C!DOCTYPE%20html%3E%3Chtml%3E%3Chead%3E%3C%2Fhead%3E%3Cbody%3E%3C%2Fbody%3E%3C%2Fhtml%3E'),\n {\n features: {\n FetchExternalResources: ['img']\n },\n resources: 'usable'\n }).window;\n fabric.document = virtualWindow.document;\n fabric.jsdomImplForWrapper = require('jsdom/lib/jsdom/living/generated/utils').implForWrapper;\n fabric.nodeCanvas = require('jsdom/lib/jsdom/utils').Canvas;\n fabric.window = virtualWindow;\n DOMParser = fabric.window.DOMParser;\n}\n\n/**\n * True when in environment that supports touch events\n * @type boolean\n */\nfabric.isTouchSupported = 'ontouchstart' in fabric.window || 'ontouchstart' in fabric.document ||\n (fabric.window && fabric.window.navigator && fabric.window.navigator.maxTouchPoints > 0);\n\n/**\n * True when in environment that's probably Node.js\n * @type boolean\n */\nfabric.isLikelyNode = typeof Buffer !== 'undefined' &&\n typeof window === 'undefined';\n\n/* _FROM_SVG_START_ */\n/**\n * Attributes parsed from all SVG elements\n * @type array\n */\nfabric.SHARED_ATTRIBUTES = [\n 'display',\n 'transform',\n 'fill', 'fill-opacity', 'fill-rule',\n 'opacity',\n 'stroke', 'stroke-dasharray', 'stroke-linecap', 'stroke-dashoffset',\n 'stroke-linejoin', 'stroke-miterlimit',\n 'stroke-opacity', 'stroke-width',\n 'id', 'paint-order', 'vector-effect',\n 'instantiated_by_use', 'clip-path'\n];\n/* _FROM_SVG_END_ */\n\n/**\n * Pixel per Inch as a default value set to 96. Can be changed for more realistic conversion.\n */\nfabric.DPI = 96;\nfabric.reNum = '(?:[-+]?(?:\\\\d+|\\\\d*\\\\.\\\\d+)(?:[eE][-+]?\\\\d+)?)';\nfabric.rePathCommand = /([-+]?((\\d+\\.\\d+)|((\\d+)|(\\.\\d+)))(?:[eE][-+]?\\d+)?)/ig;\nfabric.reNonWord = /[ \\n\\.,;!\\?\\-]/;\nfabric.fontPaths = { };\nfabric.iMatrix = [1, 0, 0, 1, 0, 0];\nfabric.svgNS = 'http://www.w3.org/2000/svg';\n\n/**\n * Pixel limit for cache canvases. 1Mpx , 4Mpx should be fine.\n * @since 1.7.14\n * @type Number\n * @default\n */\nfabric.perfLimitSizeTotal = 2097152;\n\n/**\n * Pixel limit for cache canvases width or height. IE fixes the maximum at 5000\n * @since 1.7.14\n * @type Number\n * @default\n */\nfabric.maxCacheSideLimit = 4096;\n\n/**\n * Lowest pixel limit for cache canvases, set at 256PX\n * @since 1.7.14\n * @type Number\n * @default\n */\nfabric.minCacheSideLimit = 256;\n\n/**\n * Cache Object for widths of chars in text rendering.\n */\nfabric.charWidthsCache = { };\n\n/**\n * if webgl is enabled and available, textureSize will determine the size\n * of the canvas backend\n * @since 2.0.0\n * @type Number\n * @default\n */\nfabric.textureSize = 2048;\n\n/**\n * When 'true', style information is not retained when copy/pasting text, making\n * pasted text use destination style.\n * Defaults to 'false'.\n * @type Boolean\n * @default\n */\nfabric.disableStyleCopyPaste = false;\n\n/**\n * Enable webgl for filtering picture is available\n * A filtering backend will be initialized, this will both take memory and\n * time since a default 2048x2048 canvas will be created for the gl context\n * @since 2.0.0\n * @type Boolean\n * @default\n */\nfabric.enableGLFiltering = true;\n\n/**\n * Device Pixel Ratio\n * @see https://developer.apple.com/library/safari/documentation/AudioVideo/Conceptual/HTML-canvas-guide/SettingUptheCanvas/SettingUptheCanvas.html\n */\nfabric.devicePixelRatio = fabric.window.devicePixelRatio ||\n fabric.window.webkitDevicePixelRatio ||\n fabric.window.mozDevicePixelRatio ||\n 1;\n/**\n * Browser-specific constant to adjust CanvasRenderingContext2D.shadowBlur value,\n * which is unitless and not rendered equally across browsers.\n *\n * Values that work quite well (as of October 2017) are:\n * - Chrome: 1.5\n * - Edge: 1.75\n * - Firefox: 0.9\n * - Safari: 0.95\n *\n * @since 2.0.0\n * @type Number\n * @default 1\n */\nfabric.browserShadowBlurConstant = 1;\n\n/**\n * This object contains the result of arc to beizer conversion for faster retrieving if the same arc needs to be converted again.\n * It was an internal variable, is accessible since version 2.3.4\n */\nfabric.arcToSegmentsCache = { };\n\n/**\n * This object keeps the results of the boundsOfCurve calculation mapped by the joined arguments necessary to calculate it.\n * It does speed up calculation, if you parse and add always the same paths, but in case of heavy usage of freedrawing\n * you do not get any speed benefit and you get a big object in memory.\n * The object was a private variable before, while now is appended to the lib so that you have access to it and you\n * can eventually clear it.\n * It was an internal variable, is accessible since version 2.3.4\n */\nfabric.boundsOfCurveCache = { };\n\n/**\n * If disabled boundsOfCurveCache is not used. For apps that make heavy usage of pencil drawing probably disabling it is better\n * @default true\n */\nfabric.cachesBoundsOfCurve = true;\n\n/**\n * Skip performance testing of setupGLContext and force the use of putImageData that seems to be the one that works best on\n * Chrome + old hardware. if your users are experiencing empty images after filtering you may try to force this to true\n * this has to be set before instantiating the filtering backend ( before filtering the first image )\n * @type Boolean\n * @default false\n */\nfabric.forceGLPutImageData = false;\n\nfabric.initFilterBackend = function() {\n if (fabric.enableGLFiltering && fabric.isWebglSupported && fabric.isWebglSupported(fabric.textureSize)) {\n console.log('max texture size: ' + fabric.maxTextureSize);\n return (new fabric.WebglFilterBackend({ tileSize: fabric.textureSize }));\n }\n else if (fabric.Canvas2dFilterBackend) {\n return (new fabric.Canvas2dFilterBackend());\n }\n};\n\n\nif (typeof document !== 'undefined' && typeof window !== 'undefined') {\n // ensure globality even if entire library were function wrapped (as in Meteor.js packaging system)\n window.fabric = fabric;\n}\n\n\n(function() {\n\n /**\n * @private\n * @param {String} eventName\n * @param {Function} handler\n */\n function _removeEventListener(eventName, handler) {\n if (!this.__eventListeners[eventName]) {\n return;\n }\n var eventListener = this.__eventListeners[eventName];\n if (handler) {\n eventListener[eventListener.indexOf(handler)] = false;\n }\n else {\n fabric.util.array.fill(eventListener, false);\n }\n }\n\n /**\n * Observes specified event\n * @deprecated `observe` deprecated since 0.8.34 (use `on` instead)\n * @memberOf fabric.Observable\n * @alias on\n * @param {String|Object} eventName Event name (eg. 'after:render') or object with key/value pairs (eg. {'after:render': handler, 'selection:cleared': handler})\n * @param {Function} handler Function that receives a notification when an event of the specified type occurs\n * @return {Self} thisArg\n * @chainable\n */\n function observe(eventName, handler) {\n if (!this.__eventListeners) {\n this.__eventListeners = { };\n }\n // one object with key/value pairs was passed\n if (arguments.length === 1) {\n for (var prop in eventName) {\n this.on(prop, eventName[prop]);\n }\n }\n else {\n if (!this.__eventListeners[eventName]) {\n this.__eventListeners[eventName] = [];\n }\n this.__eventListeners[eventName].push(handler);\n }\n return this;\n }\n\n /**\n * Stops event observing for a particular event handler. Calling this method\n * without arguments removes all handlers for all events\n * @deprecated `stopObserving` deprecated since 0.8.34 (use `off` instead)\n * @memberOf fabric.Observable\n * @alias off\n * @param {String|Object} eventName Event name (eg. 'after:render') or object with key/value pairs (eg. {'after:render': handler, 'selection:cleared': handler})\n * @param {Function} handler Function to be deleted from EventListeners\n * @return {Self} thisArg\n * @chainable\n */\n function stopObserving(eventName, handler) {\n if (!this.__eventListeners) {\n return this;\n }\n\n // remove all key/value pairs (event name -> event handler)\n if (arguments.length === 0) {\n for (eventName in this.__eventListeners) {\n _removeEventListener.call(this, eventName);\n }\n }\n // one object with key/value pairs was passed\n else if (arguments.length === 1 && typeof arguments[0] === 'object') {\n for (var prop in eventName) {\n _removeEventListener.call(this, prop, eventName[prop]);\n }\n }\n else {\n _removeEventListener.call(this, eventName, handler);\n }\n return this;\n }\n\n /**\n * Fires event with an optional options object\n * @deprecated `fire` deprecated since 1.0.7 (use `trigger` instead)\n * @memberOf fabric.Observable\n * @alias trigger\n * @param {String} eventName Event name to fire\n * @param {Object} [options] Options object\n * @return {Self} thisArg\n * @chainable\n */\n function fire(eventName, options) {\n if (!this.__eventListeners) {\n return this;\n }\n\n var listenersForEvent = this.__eventListeners[eventName];\n if (!listenersForEvent) {\n return this;\n }\n\n for (var i = 0, len = listenersForEvent.length; i < len; i++) {\n listenersForEvent[i] && listenersForEvent[i].call(this, options || { });\n }\n this.__eventListeners[eventName] = listenersForEvent.filter(function(value) {\n return value !== false;\n });\n return this;\n }\n\n /**\n * @namespace fabric.Observable\n * @tutorial {@link http://fabricjs.com/fabric-intro-part-2#events}\n * @see {@link http://fabricjs.com/events|Events demo}\n */\n fabric.Observable = {\n observe: observe,\n stopObserving: stopObserving,\n fire: fire,\n\n on: observe,\n off: stopObserving,\n trigger: fire\n };\n})();\n\n\n/**\n * @namespace fabric.Collection\n */\nfabric.Collection = {\n\n _objects: [],\n\n /**\n * Adds objects to collection, Canvas or Group, then renders canvas\n * (if `renderOnAddRemove` is not `false`).\n * in case of Group no changes to bounding box are made.\n * Objects should be instances of (or inherit from) fabric.Object\n * Use of this function is highly discouraged for groups.\n * you can add a bunch of objects with the add method but then you NEED\n * to run a addWithUpdate call for the Group class or position/bbox will be wrong.\n * @param {...fabric.Object} object Zero or more fabric instances\n * @return {Self} thisArg\n * @chainable\n */\n add: function () {\n this._objects.push.apply(this._objects, arguments);\n if (this._onObjectAdded) {\n for (var i = 0, length = arguments.length; i < length; i++) {\n this._onObjectAdded(arguments[i]);\n }\n }\n this.renderOnAddRemove && this.requestRenderAll();\n return this;\n },\n\n /**\n * Inserts an object into collection at specified index, then renders canvas (if `renderOnAddRemove` is not `false`)\n * An object should be an instance of (or inherit from) fabric.Object\n * Use of this function is highly discouraged for groups.\n * you can add a bunch of objects with the insertAt method but then you NEED\n * to run a addWithUpdate call for the Group class or position/bbox will be wrong.\n * @param {Object} object Object to insert\n * @param {Number} index Index to insert object at\n * @param {Boolean} nonSplicing When `true`, no splicing (shifting) of objects occurs\n * @return {Self} thisArg\n * @chainable\n */\n insertAt: function (object, index, nonSplicing) {\n var objects = this._objects;\n if (nonSplicing) {\n objects[index] = object;\n }\n else {\n objects.splice(index, 0, object);\n }\n this._onObjectAdded && this._onObjectAdded(object);\n this.renderOnAddRemove && this.requestRenderAll();\n return this;\n },\n\n /**\n * Removes objects from a collection, then renders canvas (if `renderOnAddRemove` is not `false`)\n * @param {...fabric.Object} object Zero or more fabric instances\n * @return {Self} thisArg\n * @chainable\n */\n remove: function() {\n var objects = this._objects,\n index, somethingRemoved = false;\n\n for (var i = 0, length = arguments.length; i < length; i++) {\n index = objects.indexOf(arguments[i]);\n\n // only call onObjectRemoved if an object was actually removed\n if (index !== -1) {\n somethingRemoved = true;\n objects.splice(index, 1);\n this._onObjectRemoved && this._onObjectRemoved(arguments[i]);\n }\n }\n\n this.renderOnAddRemove && somethingRemoved && this.requestRenderAll();\n return this;\n },\n\n /**\n * Executes given function for each object in this group\n * @param {Function} callback\n * Callback invoked with current object as first argument,\n * index - as second and an array of all objects - as third.\n * Callback is invoked in a context of Global Object (e.g. `window`)\n * when no `context` argument is given\n *\n * @param {Object} context Context (aka thisObject)\n * @return {Self} thisArg\n * @chainable\n */\n forEachObject: function(callback, context) {\n var objects = this.getObjects();\n for (var i = 0, len = objects.length; i < len; i++) {\n callback.call(context, objects[i], i, objects);\n }\n return this;\n },\n\n /**\n * Returns an array of children objects of this instance\n * Type parameter introduced in 1.3.10\n * since 2.3.5 this method return always a COPY of the array;\n * @param {String} [type] When specified, only objects of this type are returned\n * @return {Array}\n */\n getObjects: function(type) {\n if (typeof type === 'undefined') {\n return this._objects.concat();\n }\n return this._objects.filter(function(o) {\n return o.type === type;\n });\n },\n\n /**\n * Returns object at specified index\n * @param {Number} index\n * @return {Self} thisArg\n */\n item: function (index) {\n return this._objects[index];\n },\n\n /**\n * Returns true if collection contains no objects\n * @return {Boolean} true if collection is empty\n */\n isEmpty: function () {\n return this._objects.length === 0;\n },\n\n /**\n * Returns a size of a collection (i.e: length of an array containing its objects)\n * @return {Number} Collection size\n */\n size: function() {\n return this._objects.length;\n },\n\n /**\n * Returns true if collection contains an object\n * @param {Object} object Object to check against\n * @return {Boolean} `true` if collection contains an object\n */\n contains: function(object) {\n return this._objects.indexOf(object) > -1;\n },\n\n /**\n * Returns number representation of a collection complexity\n * @return {Number} complexity\n */\n complexity: function () {\n return this._objects.reduce(function (memo, current) {\n memo += current.complexity ? current.complexity() : 0;\n return memo;\n }, 0);\n }\n};\n\n\n/**\n * @namespace fabric.CommonMethods\n */\nfabric.CommonMethods = {\n\n /**\n * Sets object's properties from options\n * @param {Object} [options] Options object\n */\n _setOptions: function(options) {\n for (var prop in options) {\n this.set(prop, options[prop]);\n }\n },\n\n /**\n * @private\n * @param {Object} [filler] Options object\n * @param {String} [property] property to set the Gradient to\n */\n _initGradient: function(filler, property) {\n if (filler && filler.colorStops && !(filler instanceof fabric.Gradient)) {\n this.set(property, new fabric.Gradient(filler));\n }\n },\n\n /**\n * @private\n * @param {Object} [filler] Options object\n * @param {String} [property] property to set the Pattern to\n * @param {Function} [callback] callback to invoke after pattern load\n */\n _initPattern: function(filler, property, callback) {\n if (filler && filler.source && !(filler instanceof fabric.Pattern)) {\n this.set(property, new fabric.Pattern(filler, callback));\n }\n else {\n callback && callback();\n }\n },\n\n /**\n * @private\n * @param {Object} [options] Options object\n */\n _initClipping: function(options) {\n if (!options.clipTo || typeof options.clipTo !== 'string') {\n return;\n }\n\n var functionBody = fabric.util.getFunctionBody(options.clipTo);\n if (typeof functionBody !== 'undefined') {\n this.clipTo = new Function('ctx', functionBody);\n }\n },\n\n /**\n * @private\n */\n _setObject: function(obj) {\n for (var prop in obj) {\n this._set(prop, obj[prop]);\n }\n },\n\n /**\n * Sets property to a given value. When changing position/dimension -related properties (left, top, scale, angle, etc.) `set` does not update position of object's borders/controls. If you need to update those, call `setCoords()`.\n * @param {String|Object} key Property name or object (if object, iterate over the object properties)\n * @param {Object|Function} value Property value (if function, the value is passed into it and its return value is used as a new one)\n * @return {fabric.Object} thisArg\n * @chainable\n */\n set: function(key, value) {\n if (typeof key === 'object') {\n this._setObject(key);\n }\n else {\n if (typeof value === 'function' && key !== 'clipTo') {\n this._set(key, value(this.get(key)));\n }\n else {\n this._set(key, value);\n }\n }\n return this;\n },\n\n _set: function(key, value) {\n this[key] = value;\n },\n\n /**\n * Toggles specified property from `true` to `false` or from `false` to `true`\n * @param {String} property Property to toggle\n * @return {fabric.Object} thisArg\n * @chainable\n */\n toggle: function(property) {\n var value = this.get(property);\n if (typeof value === 'boolean') {\n this.set(property, !value);\n }\n return this;\n },\n\n /**\n * Basic getter\n * @param {String} property Property name\n * @return {*} value of a property\n */\n get: function(property) {\n return this[property];\n }\n};\n\n\n(function(global) {\n\n var sqrt = Math.sqrt,\n atan2 = Math.atan2,\n pow = Math.pow,\n PiBy180 = Math.PI / 180,\n PiBy2 = Math.PI / 2;\n\n /**\n * @namespace fabric.util\n */\n fabric.util = {\n\n /**\n * Calculate the cos of an angle, avoiding returning floats for known results\n * @static\n * @memberOf fabric.util\n * @param {Number} angle the angle in radians or in degree\n * @return {Number}\n */\n cos: function(angle) {\n if (angle === 0) { return 1; }\n if (angle < 0) {\n // cos(a) = cos(-a)\n angle = -angle;\n }\n var angleSlice = angle / PiBy2;\n switch (angleSlice) {\n case 1: case 3: return 0;\n case 2: return -1;\n }\n return Math.cos(angle);\n },\n\n /**\n * Calculate the sin of an angle, avoiding returning floats for known results\n * @static\n * @memberOf fabric.util\n * @param {Number} angle the angle in radians or in degree\n * @return {Number}\n */\n sin: function(angle) {\n if (angle === 0) { return 0; }\n var angleSlice = angle / PiBy2, sign = 1;\n if (angle < 0) {\n // sin(-a) = -sin(a)\n sign = -1;\n }\n switch (angleSlice) {\n case 1: return sign;\n case 2: return 0;\n case 3: return -sign;\n }\n return Math.sin(angle);\n },\n\n /**\n * Removes value from an array.\n * Presence of value (and its position in an array) is determined via `Array.prototype.indexOf`\n * @static\n * @memberOf fabric.util\n * @param {Array} array\n * @param {*} value\n * @return {Array} original array\n */\n removeFromArray: function(array, value) {\n var idx = array.indexOf(value);\n if (idx !== -1) {\n array.splice(idx, 1);\n }\n return array;\n },\n\n /**\n * Returns random number between 2 specified ones.\n * @static\n * @memberOf fabric.util\n * @param {Number} min lower limit\n * @param {Number} max upper limit\n * @return {Number} random value (between min and max)\n */\n getRandomInt: function(min, max) {\n return Math.floor(Math.random() * (max - min + 1)) + min;\n },\n\n /**\n * Transforms degrees to radians.\n * @static\n * @memberOf fabric.util\n * @param {Number} degrees value in degrees\n * @return {Number} value in radians\n */\n degreesToRadians: function(degrees) {\n return degrees * PiBy180;\n },\n\n /**\n * Transforms radians to degrees.\n * @static\n * @memberOf fabric.util\n * @param {Number} radians value in radians\n * @return {Number} value in degrees\n */\n radiansToDegrees: function(radians) {\n return radians / PiBy180;\n },\n\n /**\n * Rotates `point` around `origin` with `radians`\n * @static\n * @memberOf fabric.util\n * @param {fabric.Point} point The point to rotate\n * @param {fabric.Point} origin The origin of the rotation\n * @param {Number} radians The radians of the angle for the rotation\n * @return {fabric.Point} The new rotated point\n */\n rotatePoint: function(point, origin, radians) {\n point.subtractEquals(origin);\n var v = fabric.util.rotateVector(point, radians);\n return new fabric.Point(v.x, v.y).addEquals(origin);\n },\n\n /**\n * Rotates `vector` with `radians`\n * @static\n * @memberOf fabric.util\n * @param {Object} vector The vector to rotate (x and y)\n * @param {Number} radians The radians of the angle for the rotation\n * @return {Object} The new rotated point\n */\n rotateVector: function(vector, radians) {\n var sin = fabric.util.sin(radians),\n cos = fabric.util.cos(radians),\n rx = vector.x * cos - vector.y * sin,\n ry = vector.x * sin + vector.y * cos;\n return {\n x: rx,\n y: ry\n };\n },\n\n /**\n * Apply transform t to point p\n * @static\n * @memberOf fabric.util\n * @param {fabric.Point} p The point to transform\n * @param {Array} t The transform\n * @param {Boolean} [ignoreOffset] Indicates that the offset should not be applied\n * @return {fabric.Point} The transformed point\n */\n transformPoint: function(p, t, ignoreOffset) {\n if (ignoreOffset) {\n return new fabric.Point(\n t[0] * p.x + t[2] * p.y,\n t[1] * p.x + t[3] * p.y\n );\n }\n return new fabric.Point(\n t[0] * p.x + t[2] * p.y + t[4],\n t[1] * p.x + t[3] * p.y + t[5]\n );\n },\n\n /**\n * Returns coordinates of points's bounding rectangle (left, top, width, height)\n * @param {Array} points 4 points array\n * @param {Array} [transform] an array of 6 numbers representing a 2x3 transform matrix\n * @return {Object} Object with left, top, width, height properties\n */\n makeBoundingBoxFromPoints: function(points, transform) {\n if (transform) {\n for (var i = 0; i < points.length; i++) {\n points[i] = fabric.util.transformPoint(points[i], transform);\n }\n }\n var xPoints = [points[0].x, points[1].x, points[2].x, points[3].x],\n minX = fabric.util.array.min(xPoints),\n maxX = fabric.util.array.max(xPoints),\n width = maxX - minX,\n yPoints = [points[0].y, points[1].y, points[2].y, points[3].y],\n minY = fabric.util.array.min(yPoints),\n maxY = fabric.util.array.max(yPoints),\n height = maxY - minY;\n\n return {\n left: minX,\n top: minY,\n width: width,\n height: height\n };\n },\n\n /**\n * Invert transformation t\n * @static\n * @memberOf fabric.util\n * @param {Array} t The transform\n * @return {Array} The inverted transform\n */\n invertTransform: function(t) {\n var a = 1 / (t[0] * t[3] - t[1] * t[2]),\n r = [a * t[3], -a * t[1], -a * t[2], a * t[0]],\n o = fabric.util.transformPoint({ x: t[4], y: t[5] }, r, true);\n r[4] = -o.x;\n r[5] = -o.y;\n return r;\n },\n\n /**\n * A wrapper around Number#toFixed, which contrary to native method returns number, not string.\n * @static\n * @memberOf fabric.util\n * @param {Number|String} number number to operate on\n * @param {Number} fractionDigits number of fraction digits to \"leave\"\n * @return {Number}\n */\n toFixed: function(number, fractionDigits) {\n return parseFloat(Number(number).toFixed(fractionDigits));\n },\n\n /**\n * Converts from attribute value to pixel value if applicable.\n * Returns converted pixels or original value not converted.\n * @param {Number|String} value number to operate on\n * @param {Number} fontSize\n * @return {Number|String}\n */\n parseUnit: function(value, fontSize) {\n var unit = /\\D{0,2}$/.exec(value),\n number = parseFloat(value);\n if (!fontSize) {\n fontSize = fabric.Text.DEFAULT_SVG_FONT_SIZE;\n }\n switch (unit[0]) {\n case 'mm':\n return number * fabric.DPI / 25.4;\n\n case 'cm':\n return number * fabric.DPI / 2.54;\n\n case 'in':\n return number * fabric.DPI;\n\n case 'pt':\n return number * fabric.DPI / 72; // or * 4 / 3\n\n case 'pc':\n return number * fabric.DPI / 72 * 12; // or * 16\n\n case 'em':\n return number * fontSize;\n\n default:\n return number;\n }\n },\n\n /**\n * Function which always returns `false`.\n * @static\n * @memberOf fabric.util\n * @return {Boolean}\n */\n falseFunction: function() {\n return false;\n },\n\n /**\n * Returns klass \"Class\" object of given namespace\n * @memberOf fabric.util\n * @param {String} type Type of object (eg. 'circle')\n * @param {String} namespace Namespace to get klass \"Class\" object from\n * @return {Object} klass \"Class\"\n */\n getKlass: function(type, namespace) {\n // capitalize first letter only\n type = fabric.util.string.camelize(type.charAt(0).toUpperCase() + type.slice(1));\n return fabric.util.resolveNamespace(namespace)[type];\n },\n\n /**\n * Returns array of attributes for given svg that fabric parses\n * @memberOf fabric.util\n * @param {String} type Type of svg element (eg. 'circle')\n * @return {Array} string names of supported attributes\n */\n getSvgAttributes: function(type) {\n var attributes = [\n 'instantiated_by_use',\n 'style',\n 'id',\n 'class'\n ];\n switch (type) {\n case 'linearGradient':\n attributes = attributes.concat(['x1', 'y1', 'x2', 'y2', 'gradientUnits', 'gradientTransform']);\n break;\n case 'radialGradient':\n attributes = attributes.concat(['gradientUnits', 'gradientTransform', 'cx', 'cy', 'r', 'fx', 'fy', 'fr']);\n break;\n case 'stop':\n attributes = attributes.concat(['offset', 'stop-color', 'stop-opacity']);\n break;\n }\n return attributes;\n },\n\n /**\n * Returns object of given namespace\n * @memberOf fabric.util\n * @param {String} namespace Namespace string e.g. 'fabric.Image.filter' or 'fabric'\n * @return {Object} Object for given namespace (default fabric)\n */\n resolveNamespace: function(namespace) {\n if (!namespace) {\n return fabric;\n }\n\n var parts = namespace.split('.'),\n len = parts.length, i,\n obj = global || fabric.window;\n\n for (i = 0; i < len; ++i) {\n obj = obj[parts[i]];\n }\n\n return obj;\n },\n\n /**\n * Loads image element from given url and passes it to a callback\n * @memberOf fabric.util\n * @param {String} url URL representing an image\n * @param {Function} callback Callback; invoked with loaded image\n * @param {*} [context] Context to invoke callback in\n * @param {Object} [crossOrigin] crossOrigin value to set image element to\n */\n loadImage: function(url, callback, context, crossOrigin) {\n if (!url) {\n callback && callback.call(context, url);\n return;\n }\n\n var img = fabric.util.createImage();\n\n /** @ignore */\n var onLoadCallback = function () {\n callback && callback.call(context, img);\n img = img.onload = img.onerror = null;\n };\n\n img.onload = onLoadCallback;\n /** @ignore */\n img.onerror = function() {\n fabric.log('Error loading ' + img.src);\n callback && callback.call(context, null, true);\n img = img.onload = img.onerror = null;\n };\n\n // data-urls appear to be buggy with crossOrigin\n // https://github.com/kangax/fabric.js/commit/d0abb90f1cd5c5ef9d2a94d3fb21a22330da3e0a#commitcomment-4513767\n // see https://code.google.com/p/chromium/issues/detail?id=315152\n // https://bugzilla.mozilla.org/show_bug.cgi?id=935069\n if (url.indexOf('data') !== 0 && crossOrigin) {\n img.crossOrigin = crossOrigin;\n }\n\n // IE10 / IE11-Fix: SVG contents from data: URI\n // will only be available if the IMG is present\n // in the DOM (and visible)\n if (url.substring(0,14) === 'data:image/svg') {\n img.onload = null;\n fabric.util.loadImageInDom(img, onLoadCallback);\n }\n\n img.src = url;\n },\n\n /**\n * Attaches SVG image with data: URL to the dom\n * @memberOf fabric.util\n * @param {Object} img Image object with data:image/svg src\n * @param {Function} callback Callback; invoked with loaded image\n * @return {Object} DOM element (div containing the SVG image)\n */\n loadImageInDom: function(img, onLoadCallback) {\n var div = fabric.document.createElement('div');\n div.style.width = div.style.height = '1px';\n div.style.left = div.style.top = '-100%';\n div.style.position = 'absolute';\n div.appendChild(img);\n fabric.document.querySelector('body').appendChild(div);\n /**\n * Wrap in function to:\n * 1. Call existing callback\n * 2. Cleanup DOM\n */\n img.onload = function () {\n onLoadCallback();\n div.parentNode.removeChild(div);\n div = null;\n };\n },\n\n /**\n * Creates corresponding fabric instances from their object representations\n * @static\n * @memberOf fabric.util\n * @param {Array} objects Objects to enliven\n * @param {Function} callback Callback to invoke when all objects are created\n * @param {String} namespace Namespace to get klass \"Class\" object from\n * @param {Function} reviver Method for further parsing of object elements,\n * called after each fabric object created.\n */\n enlivenObjects: function(objects, callback, namespace, reviver) {\n objects = objects || [];\n\n var enlivenedObjects = [],\n numLoadedObjects = 0,\n numTotalObjects = objects.length;\n\n function onLoaded() {\n if (++numLoadedObjects === numTotalObjects) {\n callback && callback(enlivenedObjects.filter(function(obj) {\n // filter out undefined objects (objects that gave error)\n return obj;\n }));\n }\n }\n\n if (!numTotalObjects) {\n callback && callback(enlivenedObjects);\n return;\n }\n\n objects.forEach(function (o, index) {\n // if sparse array\n if (!o || !o.type) {\n onLoaded();\n return;\n }\n var klass = fabric.util.getKlass(o.type, namespace);\n klass.fromObject(o, function (obj, error) {\n error || (enlivenedObjects[index] = obj);\n reviver && reviver(o, obj, error);\n onLoaded();\n });\n });\n },\n\n /**\n * Create and wait for loading of patterns\n * @static\n * @memberOf fabric.util\n * @param {Array} patterns Objects to enliven\n * @param {Function} callback Callback to invoke when all objects are created\n * called after each fabric object created.\n */\n enlivenPatterns: function(patterns, callback) {\n patterns = patterns || [];\n\n function onLoaded() {\n if (++numLoadedPatterns === numPatterns) {\n callback && callback(enlivenedPatterns);\n }\n }\n\n var enlivenedPatterns = [],\n numLoadedPatterns = 0,\n numPatterns = patterns.length;\n\n if (!numPatterns) {\n callback && callback(enlivenedPatterns);\n return;\n }\n\n patterns.forEach(function (p, index) {\n if (p && p.source) {\n new fabric.Pattern(p, function(pattern) {\n enlivenedPatterns[index] = pattern;\n onLoaded();\n });\n }\n else {\n enlivenedPatterns[index] = p;\n onLoaded();\n }\n });\n },\n\n /**\n * Groups SVG elements (usually those retrieved from SVG document)\n * @static\n * @memberOf fabric.util\n * @param {Array} elements SVG elements to group\n * @param {Object} [options] Options object\n * @param {String} path Value to set sourcePath to\n * @return {fabric.Object|fabric.Group}\n */\n groupSVGElements: function(elements, options, path) {\n var object;\n if (elements && elements.length === 1) {\n return elements[0];\n }\n if (options) {\n if (options.width && options.height) {\n options.centerPoint = {\n x: options.width / 2,\n y: options.height / 2\n };\n }\n else {\n delete options.width;\n delete options.height;\n }\n }\n object = new fabric.Group(elements, options);\n if (typeof path !== 'undefined') {\n object.sourcePath = path;\n }\n return object;\n },\n\n /**\n * Populates an object with properties of another object\n * @static\n * @memberOf fabric.util\n * @param {Object} source Source object\n * @param {Object} destination Destination object\n * @return {Array} properties Properties names to include\n */\n populateWithProperties: function(source, destination, properties) {\n if (properties && Object.prototype.toString.call(properties) === '[object Array]') {\n for (var i = 0, len = properties.length; i < len; i++) {\n if (properties[i] in source) {\n destination[properties[i]] = source[properties[i]];\n }\n }\n }\n },\n\n /**\n * Draws a dashed line between two points\n *\n * This method is used to draw dashed line around selection area.\n * See dotted stroke in canvas\n *\n * @param {CanvasRenderingContext2D} ctx context\n * @param {Number} x start x coordinate\n * @param {Number} y start y coordinate\n * @param {Number} x2 end x coordinate\n * @param {Number} y2 end y coordinate\n * @param {Array} da dash array pattern\n */\n drawDashedLine: function(ctx, x, y, x2, y2, da) {\n var dx = x2 - x,\n dy = y2 - y,\n len = sqrt(dx * dx + dy * dy),\n rot = atan2(dy, dx),\n dc = da.length,\n di = 0,\n draw = true;\n\n ctx.save();\n ctx.translate(x, y);\n ctx.moveTo(0, 0);\n ctx.rotate(rot);\n\n x = 0;\n while (len > x) {\n x += da[di++ % dc];\n if (x > len) {\n x = len;\n }\n ctx[draw ? 'lineTo' : 'moveTo'](x, 0);\n draw = !draw;\n }\n\n ctx.restore();\n },\n\n /**\n * Creates canvas element\n * @static\n * @memberOf fabric.util\n * @return {CanvasElement} initialized canvas element\n */\n createCanvasElement: function() {\n return fabric.document.createElement('canvas');\n },\n\n /**\n * Creates a canvas element that is a copy of another and is also painted\n * @param {CanvasElement} canvas to copy size and content of\n * @static\n * @memberOf fabric.util\n * @return {CanvasElement} initialized canvas element\n */\n copyCanvasElement: function(canvas) {\n var newCanvas = fabric.util.createCanvasElement();\n newCanvas.width = canvas.width;\n newCanvas.height = canvas.height;\n newCanvas.getContext('2d').drawImage(canvas, 0, 0);\n return newCanvas;\n },\n\n /**\n * since 2.6.0 moved from canvas instance to utility.\n * @param {CanvasElement} canvasEl to copy size and content of\n * @param {String} format 'jpeg' or 'png', in some browsers 'webp' is ok too\n * @param {Number} quality <= 1 and > 0\n * @static\n * @memberOf fabric.util\n * @return {String} data url\n */\n toDataURL: function(canvasEl, format, quality) {\n return canvasEl.toDataURL('image/' + format, quality);\n },\n\n /**\n * Creates image element (works on client and node)\n * @static\n * @memberOf fabric.util\n * @return {HTMLImageElement} HTML image element\n */\n createImage: function() {\n return fabric.document.createElement('img');\n },\n\n /**\n * @static\n * @memberOf fabric.util\n * @deprecated since 2.0.0\n * @param {fabric.Object} receiver Object implementing `clipTo` method\n * @param {CanvasRenderingContext2D} ctx Context to clip\n */\n clipContext: function(receiver, ctx) {\n ctx.save();\n ctx.beginPath();\n receiver.clipTo(ctx);\n ctx.clip();\n },\n\n /**\n * Multiply matrix A by matrix B to nest transformations\n * @static\n * @memberOf fabric.util\n * @param {Array} a First transformMatrix\n * @param {Array} b Second transformMatrix\n * @param {Boolean} is2x2 flag to multiply matrices as 2x2 matrices\n * @return {Array} The product of the two transform matrices\n */\n multiplyTransformMatrices: function(a, b, is2x2) {\n // Matrix multiply a * b\n return [\n a[0] * b[0] + a[2] * b[1],\n a[1] * b[0] + a[3] * b[1],\n a[0] * b[2] + a[2] * b[3],\n a[1] * b[2] + a[3] * b[3],\n is2x2 ? 0 : a[0] * b[4] + a[2] * b[5] + a[4],\n is2x2 ? 0 : a[1] * b[4] + a[3] * b[5] + a[5]\n ];\n },\n\n /**\n * Decomposes standard 2x3 matrix into transform components\n * @static\n * @memberOf fabric.util\n * @param {Array} a transformMatrix\n * @return {Object} Components of transform\n */\n qrDecompose: function(a) {\n var angle = atan2(a[1], a[0]),\n denom = pow(a[0], 2) + pow(a[1], 2),\n scaleX = sqrt(denom),\n scaleY = (a[0] * a[3] - a[2] * a [1]) / scaleX,\n skewX = atan2(a[0] * a[2] + a[1] * a [3], denom);\n return {\n angle: angle / PiBy180,\n scaleX: scaleX,\n scaleY: scaleY,\n skewX: skewX / PiBy180,\n skewY: 0,\n translateX: a[4],\n translateY: a[5]\n };\n },\n\n /**\n * Returns a transform matrix starting from an object of the same kind of\n * the one returned from qrDecompose, useful also if you want to calculate some\n * transformations from an object that is not enlived yet\n * @static\n * @memberOf fabric.util\n * @param {Object} options\n * @param {Number} [options.angle] angle in degrees\n * @return {Number[]} transform matrix\n */\n calcRotateMatrix: function(options) {\n if (!options.angle) {\n return fabric.iMatrix.concat();\n }\n var theta = fabric.util.degreesToRadians(options.angle),\n cos = fabric.util.cos(theta),\n sin = fabric.util.sin(theta);\n return [cos, sin, -sin, cos, 0, 0];\n },\n\n /**\n * Returns a transform matrix starting from an object of the same kind of\n * the one returned from qrDecompose, useful also if you want to calculate some\n * transformations from an object that is not enlived yet.\n * is called DimensionsTransformMatrix because those properties are the one that influence\n * the size of the resulting box of the object.\n * @static\n * @memberOf fabric.util\n * @param {Object} options\n * @param {Number} [options.scaleX]\n * @param {Number} [options.scaleY]\n * @param {Boolean} [options.flipX]\n * @param {Boolean} [options.flipY]\n * @param {Number} [options.skewX]\n * @param {Number} [options.skewX]\n * @return {Number[]} transform matrix\n */\n calcDimensionsMatrix: function(options) {\n var scaleX = typeof options.scaleX === 'undefined' ? 1 : options.scaleX,\n scaleY = typeof options.scaleY === 'undefined' ? 1 : options.scaleY,\n scaleMatrix = [\n options.flipX ? -scaleX : scaleX,\n 0,\n 0,\n options.flipY ? -scaleY : scaleY,\n 0,\n 0],\n multiply = fabric.util.multiplyTransformMatrices,\n degreesToRadians = fabric.util.degreesToRadians;\n if (options.skewX) {\n scaleMatrix = multiply(\n scaleMatrix,\n [1, 0, Math.tan(degreesToRadians(options.skewX)), 1],\n true);\n }\n if (options.skewY) {\n scaleMatrix = multiply(\n scaleMatrix,\n [1, Math.tan(degreesToRadians(options.skewY)), 0, 1],\n true);\n }\n return scaleMatrix;\n },\n\n /**\n * Returns a transform matrix starting from an object of the same kind of\n * the one returned from qrDecompose, useful also if you want to calculate some\n * transformations from an object that is not enlived yet\n * @static\n * @memberOf fabric.util\n * @param {Object} options\n * @param {Number} [options.angle]\n * @param {Number} [options.scaleX]\n * @param {Number} [options.scaleY]\n * @param {Boolean} [options.flipX]\n * @param {Boolean} [options.flipY]\n * @param {Number} [options.skewX]\n * @param {Number} [options.skewX]\n * @param {Number} [options.translateX]\n * @param {Number} [options.translateY]\n * @return {Number[]} transform matrix\n */\n composeMatrix: function(options) {\n var matrix = [1, 0, 0, 1, options.translateX || 0, options.translateY || 0],\n multiply = fabric.util.multiplyTransformMatrices;\n if (options.angle) {\n matrix = multiply(matrix, fabric.util.calcRotateMatrix(options));\n }\n if (options.scaleX || options.scaleY || options.skewX || options.skewY || options.flipX || options.flipY) {\n matrix = multiply(matrix, fabric.util.calcDimensionsMatrix(options));\n }\n return matrix;\n },\n\n /**\n * Returns a transform matrix that has the same effect of scaleX, scaleY and skewX.\n * Is deprecated for composeMatrix. Please do not use it.\n * @static\n * @deprecated since 3.4.0\n * @memberOf fabric.util\n * @param {Number} scaleX\n * @param {Number} scaleY\n * @param {Number} skewX\n * @return {Number[]} transform matrix\n */\n customTransformMatrix: function(scaleX, scaleY, skewX) {\n return fabric.util.composeMatrix({ scaleX: scaleX, scaleY: scaleY, skewX: skewX });\n },\n\n /**\n * reset an object transform state to neutral. Top and left are not accounted for\n * @static\n * @memberOf fabric.util\n * @param {fabric.Object} target object to transform\n */\n resetObjectTransform: function (target) {\n target.scaleX = 1;\n target.scaleY = 1;\n target.skewX = 0;\n target.skewY = 0;\n target.flipX = false;\n target.flipY = false;\n target.rotate(0);\n },\n\n /**\n * Extract Object transform values\n * @static\n * @memberOf fabric.util\n * @param {fabric.Object} target object to read from\n * @return {Object} Components of transform\n */\n saveObjectTransform: function (target) {\n return {\n scaleX: target.scaleX,\n scaleY: target.scaleY,\n skewX: target.skewX,\n skewY: target.skewY,\n angle: target.angle,\n left: target.left,\n flipX: target.flipX,\n flipY: target.flipY,\n top: target.top\n };\n },\n\n /**\n * Returns string representation of function body\n * @param {Function} fn Function to get body of\n * @return {String} Function body\n */\n getFunctionBody: function(fn) {\n return (String(fn).match(/function[^{]*\\{([\\s\\S]*)\\}/) || {})[1];\n },\n\n /**\n * Returns true if context has transparent pixel\n * at specified location (taking tolerance into account)\n * @param {CanvasRenderingContext2D} ctx context\n * @param {Number} x x coordinate\n * @param {Number} y y coordinate\n * @param {Number} tolerance Tolerance\n */\n isTransparent: function(ctx, x, y, tolerance) {\n\n // If tolerance is > 0 adjust start coords to take into account.\n // If moves off Canvas fix to 0\n if (tolerance > 0) {\n if (x > tolerance) {\n x -= tolerance;\n }\n else {\n x = 0;\n }\n if (y > tolerance) {\n y -= tolerance;\n }\n else {\n y = 0;\n }\n }\n\n var _isTransparent = true, i, temp,\n imageData = ctx.getImageData(x, y, (tolerance * 2) || 1, (tolerance * 2) || 1),\n l = imageData.data.length;\n\n // Split image data - for tolerance > 1, pixelDataSize = 4;\n for (i = 3; i < l; i += 4) {\n temp = imageData.data[i];\n _isTransparent = temp <= 0;\n if (_isTransparent === false) {\n break; // Stop if colour found\n }\n }\n\n imageData = null;\n\n return _isTransparent;\n },\n\n /**\n * Parse preserveAspectRatio attribute from element\n * @param {string} attribute to be parsed\n * @return {Object} an object containing align and meetOrSlice attribute\n */\n parsePreserveAspectRatioAttribute: function(attribute) {\n var meetOrSlice = 'meet', alignX = 'Mid', alignY = 'Mid',\n aspectRatioAttrs = attribute.split(' '), align;\n\n if (aspectRatioAttrs && aspectRatioAttrs.length) {\n meetOrSlice = aspectRatioAttrs.pop();\n if (meetOrSlice !== 'meet' && meetOrSlice !== 'slice') {\n align = meetOrSlice;\n meetOrSlice = 'meet';\n }\n else if (aspectRatioAttrs.length) {\n align = aspectRatioAttrs.pop();\n }\n }\n //divide align in alignX and alignY\n alignX = align !== 'none' ? align.slice(1, 4) : 'none';\n alignY = align !== 'none' ? align.slice(5, 8) : 'none';\n return {\n meetOrSlice: meetOrSlice,\n alignX: alignX,\n alignY: alignY\n };\n },\n\n /**\n * Clear char widths cache for the given font family or all the cache if no\n * fontFamily is specified.\n * Use it if you know you are loading fonts in a lazy way and you are not waiting\n * for custom fonts to load properly when adding text objects to the canvas.\n * If a text object is added when its own font is not loaded yet, you will get wrong\n * measurement and so wrong bounding boxes.\n * After the font cache is cleared, either change the textObject text content or call\n * initDimensions() to trigger a recalculation\n * @memberOf fabric.util\n * @param {String} [fontFamily] font family to clear\n */\n clearFabricFontCache: function(fontFamily) {\n fontFamily = (fontFamily || '').toLowerCase();\n if (!fontFamily) {\n fabric.charWidthsCache = { };\n }\n else if (fabric.charWidthsCache[fontFamily]) {\n delete fabric.charWidthsCache[fontFamily];\n }\n },\n\n /**\n * Given current aspect ratio, determines the max width and height that can\n * respect the total allowed area for the cache.\n * @memberOf fabric.util\n * @param {Number} ar aspect ratio\n * @param {Number} maximumArea Maximum area you want to achieve\n * @return {Object.x} Limited dimensions by X\n * @return {Object.y} Limited dimensions by Y\n */\n limitDimsByArea: function(ar, maximumArea) {\n var roughWidth = Math.sqrt(maximumArea * ar),\n perfLimitSizeY = Math.floor(maximumArea / roughWidth);\n return { x: Math.floor(roughWidth), y: perfLimitSizeY };\n },\n\n capValue: function(min, value, max) {\n return Math.max(min, Math.min(value, max));\n },\n\n /**\n * Finds the scale for the object source to fit inside the object destination,\n * keeping aspect ratio intact.\n * respect the total allowed area for the cache.\n * @memberOf fabric.util\n * @param {Object | fabric.Object} source\n * @param {Number} source.height natural unscaled height of the object\n * @param {Number} source.width natural unscaled width of the object\n * @param {Object | fabric.Object} destination\n * @param {Number} destination.height natural unscaled height of the object\n * @param {Number} destination.width natural unscaled width of the object\n * @return {Number} scale factor to apply to source to fit into destination\n */\n findScaleToFit: function(source, destination) {\n return Math.min(destination.width / source.width, destination.height / source.height);\n },\n\n /**\n * Finds the scale for the object source to cover entirely the object destination,\n * keeping aspect ratio intact.\n * respect the total allowed area for the cache.\n * @memberOf fabric.util\n * @param {Object | fabric.Object} source\n * @param {Number} source.height natural unscaled height of the object\n * @param {Number} source.width natural unscaled width of the object\n * @param {Object | fabric.Object} destination\n * @param {Number} destination.height natural unscaled height of the object\n * @param {Number} destination.width natural unscaled width of the object\n * @return {Number} scale factor to apply to source to cover destination\n */\n findScaleToCover: function(source, destination) {\n return Math.max(destination.width / source.width, destination.height / source.height);\n },\n\n /**\n * given an array of 6 number returns something like `\"matrix(...numbers)\"`\n * @memberOf fabric.util\n * @param {Array} trasnform an array with 6 numbers\n * @return {String} transform matrix for svg\n * @return {Object.y} Limited dimensions by Y\n */\n matrixToSVG: function(transform) {\n return 'matrix(' + transform.map(function(value) {\n return fabric.util.toFixed(value, fabric.Object.NUM_FRACTION_DIGITS);\n }).join(' ') + ')';\n }\n };\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function() {\n\n var _join = Array.prototype.join;\n\n /* Adapted from http://dxr.mozilla.org/mozilla-central/source/content/svg/content/src/nsSVGPathDataParser.cpp\n * by Andrea Bogazzi code is under MPL. if you don't have a copy of the license you can take it here\n * http://mozilla.org/MPL/2.0/\n */\n function arcToSegments(toX, toY, rx, ry, large, sweep, rotateX) {\n var argsString = _join.call(arguments);\n if (fabric.arcToSegmentsCache[argsString]) {\n return fabric.arcToSegmentsCache[argsString];\n }\n\n var PI = Math.PI, th = rotateX * PI / 180,\n sinTh = fabric.util.sin(th),\n cosTh = fabric.util.cos(th),\n fromX = 0, fromY = 0;\n\n rx = Math.abs(rx);\n ry = Math.abs(ry);\n\n var px = -cosTh * toX * 0.5 - sinTh * toY * 0.5,\n py = -cosTh * toY * 0.5 + sinTh * toX * 0.5,\n rx2 = rx * rx, ry2 = ry * ry, py2 = py * py, px2 = px * px,\n pl = rx2 * ry2 - rx2 * py2 - ry2 * px2,\n root = 0;\n\n if (pl < 0) {\n var s = Math.sqrt(1 - pl / (rx2 * ry2));\n rx *= s;\n ry *= s;\n }\n else {\n root = (large === sweep ? -1.0 : 1.0) *\n Math.sqrt( pl / (rx2 * py2 + ry2 * px2));\n }\n\n var cx = root * rx * py / ry,\n cy = -root * ry * px / rx,\n cx1 = cosTh * cx - sinTh * cy + toX * 0.5,\n cy1 = sinTh * cx + cosTh * cy + toY * 0.5,\n mTheta = calcVectorAngle(1, 0, (px - cx) / rx, (py - cy) / ry),\n dtheta = calcVectorAngle((px - cx) / rx, (py - cy) / ry, (-px - cx) / rx, (-py - cy) / ry);\n\n if (sweep === 0 && dtheta > 0) {\n dtheta -= 2 * PI;\n }\n else if (sweep === 1 && dtheta < 0) {\n dtheta += 2 * PI;\n }\n\n // Convert into cubic bezier segments <= 90deg\n var segments = Math.ceil(Math.abs(dtheta / PI * 2)),\n result = [], mDelta = dtheta / segments,\n mT = 8 / 3 * Math.sin(mDelta / 4) * Math.sin(mDelta / 4) / Math.sin(mDelta / 2),\n th3 = mTheta + mDelta;\n\n for (var i = 0; i < segments; i++) {\n result[i] = segmentToBezier(mTheta, th3, cosTh, sinTh, rx, ry, cx1, cy1, mT, fromX, fromY);\n fromX = result[i][4];\n fromY = result[i][5];\n mTheta = th3;\n th3 += mDelta;\n }\n fabric.arcToSegmentsCache[argsString] = result;\n return result;\n }\n\n function segmentToBezier(th2, th3, cosTh, sinTh, rx, ry, cx1, cy1, mT, fromX, fromY) {\n var costh2 = fabric.util.cos(th2),\n sinth2 = fabric.util.sin(th2),\n costh3 = fabric.util.cos(th3),\n sinth3 = fabric.util.sin(th3),\n toX = cosTh * rx * costh3 - sinTh * ry * sinth3 + cx1,\n toY = sinTh * rx * costh3 + cosTh * ry * sinth3 + cy1,\n cp1X = fromX + mT * ( -cosTh * rx * sinth2 - sinTh * ry * costh2),\n cp1Y = fromY + mT * ( -sinTh * rx * sinth2 + cosTh * ry * costh2),\n cp2X = toX + mT * ( cosTh * rx * sinth3 + sinTh * ry * costh3),\n cp2Y = toY + mT * ( sinTh * rx * sinth3 - cosTh * ry * costh3);\n\n return [\n cp1X, cp1Y,\n cp2X, cp2Y,\n toX, toY\n ];\n }\n\n /*\n * Private\n */\n function calcVectorAngle(ux, uy, vx, vy) {\n var ta = Math.atan2(uy, ux),\n tb = Math.atan2(vy, vx);\n if (tb >= ta) {\n return tb - ta;\n }\n else {\n return 2 * Math.PI - (ta - tb);\n }\n }\n\n /**\n * Draws arc\n * @param {CanvasRenderingContext2D} ctx\n * @param {Number} fx\n * @param {Number} fy\n * @param {Array} coords\n */\n fabric.util.drawArc = function(ctx, fx, fy, coords) {\n var rx = coords[0],\n ry = coords[1],\n rot = coords[2],\n large = coords[3],\n sweep = coords[4],\n tx = coords[5],\n ty = coords[6],\n segs = [[], [], [], []],\n segsNorm = arcToSegments(tx - fx, ty - fy, rx, ry, large, sweep, rot);\n\n for (var i = 0, len = segsNorm.length; i < len; i++) {\n segs[i][0] = segsNorm[i][0] + fx;\n segs[i][1] = segsNorm[i][1] + fy;\n segs[i][2] = segsNorm[i][2] + fx;\n segs[i][3] = segsNorm[i][3] + fy;\n segs[i][4] = segsNorm[i][4] + fx;\n segs[i][5] = segsNorm[i][5] + fy;\n ctx.bezierCurveTo.apply(ctx, segs[i]);\n }\n };\n\n /**\n * Calculate bounding box of a elliptic-arc\n * @param {Number} fx start point of arc\n * @param {Number} fy\n * @param {Number} rx horizontal radius\n * @param {Number} ry vertical radius\n * @param {Number} rot angle of horizontal axe\n * @param {Number} large 1 or 0, whatever the arc is the big or the small on the 2 points\n * @param {Number} sweep 1 or 0, 1 clockwise or counterclockwise direction\n * @param {Number} tx end point of arc\n * @param {Number} ty\n */\n fabric.util.getBoundsOfArc = function(fx, fy, rx, ry, rot, large, sweep, tx, ty) {\n\n var fromX = 0, fromY = 0, bound, bounds = [],\n segs = arcToSegments(tx - fx, ty - fy, rx, ry, large, sweep, rot);\n\n for (var i = 0, len = segs.length; i < len; i++) {\n bound = getBoundsOfCurve(fromX, fromY, segs[i][0], segs[i][1], segs[i][2], segs[i][3], segs[i][4], segs[i][5]);\n bounds.push({ x: bound[0].x + fx, y: bound[0].y + fy });\n bounds.push({ x: bound[1].x + fx, y: bound[1].y + fy });\n fromX = segs[i][4];\n fromY = segs[i][5];\n }\n return bounds;\n };\n\n /**\n * Calculate bounding box of a beziercurve\n * @param {Number} x0 starting point\n * @param {Number} y0\n * @param {Number} x1 first control point\n * @param {Number} y1\n * @param {Number} x2 secondo control point\n * @param {Number} y2\n * @param {Number} x3 end of beizer\n * @param {Number} y3\n */\n // taken from http://jsbin.com/ivomiq/56/edit no credits available for that.\n function getBoundsOfCurve(x0, y0, x1, y1, x2, y2, x3, y3) {\n var argsString;\n if (fabric.cachesBoundsOfCurve) {\n argsString = _join.call(arguments);\n if (fabric.boundsOfCurveCache[argsString]) {\n return fabric.boundsOfCurveCache[argsString];\n }\n }\n\n var sqrt = Math.sqrt,\n min = Math.min, max = Math.max,\n abs = Math.abs, tvalues = [],\n bounds = [[], []],\n a, b, c, t, t1, t2, b2ac, sqrtb2ac;\n\n b = 6 * x0 - 12 * x1 + 6 * x2;\n a = -3 * x0 + 9 * x1 - 9 * x2 + 3 * x3;\n c = 3 * x1 - 3 * x0;\n\n for (var i = 0; i < 2; ++i) {\n if (i > 0) {\n b = 6 * y0 - 12 * y1 + 6 * y2;\n a = -3 * y0 + 9 * y1 - 9 * y2 + 3 * y3;\n c = 3 * y1 - 3 * y0;\n }\n\n if (abs(a) < 1e-12) {\n if (abs(b) < 1e-12) {\n continue;\n }\n t = -c / b;\n if (0 < t && t < 1) {\n tvalues.push(t);\n }\n continue;\n }\n b2ac = b * b - 4 * c * a;\n if (b2ac < 0) {\n continue;\n }\n sqrtb2ac = sqrt(b2ac);\n t1 = (-b + sqrtb2ac) / (2 * a);\n if (0 < t1 && t1 < 1) {\n tvalues.push(t1);\n }\n t2 = (-b - sqrtb2ac) / (2 * a);\n if (0 < t2 && t2 < 1) {\n tvalues.push(t2);\n }\n }\n\n var x, y, j = tvalues.length, jlen = j, mt;\n while (j--) {\n t = tvalues[j];\n mt = 1 - t;\n x = (mt * mt * mt * x0) + (3 * mt * mt * t * x1) + (3 * mt * t * t * x2) + (t * t * t * x3);\n bounds[0][j] = x;\n\n y = (mt * mt * mt * y0) + (3 * mt * mt * t * y1) + (3 * mt * t * t * y2) + (t * t * t * y3);\n bounds[1][j] = y;\n }\n\n bounds[0][jlen] = x0;\n bounds[1][jlen] = y0;\n bounds[0][jlen + 1] = x3;\n bounds[1][jlen + 1] = y3;\n var result = [\n {\n x: min.apply(null, bounds[0]),\n y: min.apply(null, bounds[1])\n },\n {\n x: max.apply(null, bounds[0]),\n y: max.apply(null, bounds[1])\n }\n ];\n if (fabric.cachesBoundsOfCurve) {\n fabric.boundsOfCurveCache[argsString] = result;\n }\n return result;\n }\n\n fabric.util.getBoundsOfCurve = getBoundsOfCurve;\n\n})();\n\n\n(function() {\n\n var slice = Array.prototype.slice;\n\n /**\n * Invokes method on all items in a given array\n * @memberOf fabric.util.array\n * @param {Array} array Array to iterate over\n * @param {String} method Name of a method to invoke\n * @return {Array}\n */\n function invoke(array, method) {\n var args = slice.call(arguments, 2), result = [];\n for (var i = 0, len = array.length; i < len; i++) {\n result[i] = args.length ? array[i][method].apply(array[i], args) : array[i][method].call(array[i]);\n }\n return result;\n }\n\n /**\n * Finds maximum value in array (not necessarily \"first\" one)\n * @memberOf fabric.util.array\n * @param {Array} array Array to iterate over\n * @param {String} byProperty\n * @return {*}\n */\n function max(array, byProperty) {\n return find(array, byProperty, function(value1, value2) {\n return value1 >= value2;\n });\n }\n\n /**\n * Finds minimum value in array (not necessarily \"first\" one)\n * @memberOf fabric.util.array\n * @param {Array} array Array to iterate over\n * @param {String} byProperty\n * @return {*}\n */\n function min(array, byProperty) {\n return find(array, byProperty, function(value1, value2) {\n return value1 < value2;\n });\n }\n\n /**\n * @private\n */\n function fill(array, value) {\n var k = array.length;\n while (k--) {\n array[k] = value;\n }\n return array;\n }\n\n /**\n * @private\n */\n function find(array, byProperty, condition) {\n if (!array || array.length === 0) {\n return;\n }\n\n var i = array.length - 1,\n result = byProperty ? array[i][byProperty] : array[i];\n if (byProperty) {\n while (i--) {\n if (condition(array[i][byProperty], result)) {\n result = array[i][byProperty];\n }\n }\n }\n else {\n while (i--) {\n if (condition(array[i], result)) {\n result = array[i];\n }\n }\n }\n return result;\n }\n\n /**\n * @namespace fabric.util.array\n */\n fabric.util.array = {\n fill: fill,\n invoke: invoke,\n min: min,\n max: max\n };\n\n})();\n\n\n(function() {\n /**\n * Copies all enumerable properties of one js object to another\n * this does not and cannot compete with generic utils.\n * Does not clone or extend fabric.Object subclasses.\n * This is mostly for internal use and has extra handling for fabricJS objects\n * it skips the canvas property in deep cloning.\n * @memberOf fabric.util.object\n * @param {Object} destination Where to copy to\n * @param {Object} source Where to copy from\n * @return {Object}\n */\n\n function extend(destination, source, deep) {\n // JScript DontEnum bug is not taken care of\n // the deep clone is for internal use, is not meant to avoid\n // javascript traps or cloning html element or self referenced objects.\n if (deep) {\n if (!fabric.isLikelyNode && source instanceof Element) {\n // avoid cloning deep images, canvases,\n destination = source;\n }\n else if (source instanceof Array) {\n destination = [];\n for (var i = 0, len = source.length; i < len; i++) {\n destination[i] = extend({ }, source[i], deep);\n }\n }\n else if (source && typeof source === 'object') {\n for (var property in source) {\n if (property === 'canvas') {\n destination[property] = extend({ }, source[property]);\n }\n else if (source.hasOwnProperty(property)) {\n destination[property] = extend({ }, source[property], deep);\n }\n }\n }\n else {\n // this sounds odd for an extend but is ok for recursive use\n destination = source;\n }\n }\n else {\n for (var property in source) {\n destination[property] = source[property];\n }\n }\n return destination;\n }\n\n /**\n * Creates an empty object and copies all enumerable properties of another object to it\n * @memberOf fabric.util.object\n * TODO: this function return an empty object if you try to clone null\n * @param {Object} object Object to clone\n * @return {Object}\n */\n function clone(object, deep) {\n return extend({ }, object, deep);\n }\n\n /** @namespace fabric.util.object */\n fabric.util.object = {\n extend: extend,\n clone: clone\n };\n fabric.util.object.extend(fabric.util, fabric.Observable);\n})();\n\n\n(function() {\n\n /**\n * Camelizes a string\n * @memberOf fabric.util.string\n * @param {String} string String to camelize\n * @return {String} Camelized version of a string\n */\n function camelize(string) {\n return string.replace(/-+(.)?/g, function(match, character) {\n return character ? character.toUpperCase() : '';\n });\n }\n\n /**\n * Capitalizes a string\n * @memberOf fabric.util.string\n * @param {String} string String to capitalize\n * @param {Boolean} [firstLetterOnly] If true only first letter is capitalized\n * and other letters stay untouched, if false first letter is capitalized\n * and other letters are converted to lowercase.\n * @return {String} Capitalized version of a string\n */\n function capitalize(string, firstLetterOnly) {\n return string.charAt(0).toUpperCase() +\n (firstLetterOnly ? string.slice(1) : string.slice(1).toLowerCase());\n }\n\n /**\n * Escapes XML in a string\n * @memberOf fabric.util.string\n * @param {String} string String to escape\n * @return {String} Escaped version of a string\n */\n function escapeXml(string) {\n return string.replace(/&/g, '&')\n .replace(/\"/g, '"')\n .replace(/'/g, ''')\n .replace(//g, '>');\n }\n\n /**\n * Divide a string in the user perceived single units\n * @memberOf fabric.util.string\n * @param {String} textstring String to escape\n * @return {Array} array containing the graphemes\n */\n function graphemeSplit(textstring) {\n var i = 0, chr, graphemes = [];\n for (i = 0, chr; i < textstring.length; i++) {\n if ((chr = getWholeChar(textstring, i)) === false) {\n continue;\n }\n graphemes.push(chr);\n }\n return graphemes;\n }\n\n // taken from mdn in the charAt doc page.\n function getWholeChar(str, i) {\n var code = str.charCodeAt(i);\n\n if (isNaN(code)) {\n return ''; // Position not found\n }\n if (code < 0xD800 || code > 0xDFFF) {\n return str.charAt(i);\n }\n\n // High surrogate (could change last hex to 0xDB7F to treat high private\n // surrogates as single characters)\n if (0xD800 <= code && code <= 0xDBFF) {\n if (str.length <= (i + 1)) {\n throw 'High surrogate without following low surrogate';\n }\n var next = str.charCodeAt(i + 1);\n if (0xDC00 > next || next > 0xDFFF) {\n throw 'High surrogate without following low surrogate';\n }\n return str.charAt(i) + str.charAt(i + 1);\n }\n // Low surrogate (0xDC00 <= code && code <= 0xDFFF)\n if (i === 0) {\n throw 'Low surrogate without preceding high surrogate';\n }\n var prev = str.charCodeAt(i - 1);\n\n // (could change last hex to 0xDB7F to treat high private\n // surrogates as single characters)\n if (0xD800 > prev || prev > 0xDBFF) {\n throw 'Low surrogate without preceding high surrogate';\n }\n // We can pass over low surrogates now as the second component\n // in a pair which we have already processed\n return false;\n }\n\n\n /**\n * String utilities\n * @namespace fabric.util.string\n */\n fabric.util.string = {\n camelize: camelize,\n capitalize: capitalize,\n escapeXml: escapeXml,\n graphemeSplit: graphemeSplit\n };\n})();\n\n\n(function() {\n\n var slice = Array.prototype.slice, emptyFunction = function() { },\n\n IS_DONTENUM_BUGGY = (function() {\n for (var p in { toString: 1 }) {\n if (p === 'toString') {\n return false;\n }\n }\n return true;\n })(),\n\n /** @ignore */\n addMethods = function(klass, source, parent) {\n for (var property in source) {\n\n if (property in klass.prototype &&\n typeof klass.prototype[property] === 'function' &&\n (source[property] + '').indexOf('callSuper') > -1) {\n\n klass.prototype[property] = (function(property) {\n return function() {\n\n var superclass = this.constructor.superclass;\n this.constructor.superclass = parent;\n var returnValue = source[property].apply(this, arguments);\n this.constructor.superclass = superclass;\n\n if (property !== 'initialize') {\n return returnValue;\n }\n };\n })(property);\n }\n else {\n klass.prototype[property] = source[property];\n }\n\n if (IS_DONTENUM_BUGGY) {\n if (source.toString !== Object.prototype.toString) {\n klass.prototype.toString = source.toString;\n }\n if (source.valueOf !== Object.prototype.valueOf) {\n klass.prototype.valueOf = source.valueOf;\n }\n }\n }\n };\n\n function Subclass() { }\n\n function callSuper(methodName) {\n var parentMethod = null,\n _this = this;\n\n // climb prototype chain to find method not equal to callee's method\n while (_this.constructor.superclass) {\n var superClassMethod = _this.constructor.superclass.prototype[methodName];\n if (_this[methodName] !== superClassMethod) {\n parentMethod = superClassMethod;\n break;\n }\n // eslint-disable-next-line\n _this = _this.constructor.superclass.prototype;\n }\n\n if (!parentMethod) {\n return console.log('tried to callSuper ' + methodName + ', method not found in prototype chain', this);\n }\n\n return (arguments.length > 1)\n ? parentMethod.apply(this, slice.call(arguments, 1))\n : parentMethod.call(this);\n }\n\n /**\n * Helper for creation of \"classes\".\n * @memberOf fabric.util\n * @param {Function} [parent] optional \"Class\" to inherit from\n * @param {Object} [properties] Properties shared by all instances of this class\n * (be careful modifying objects defined here as this would affect all instances)\n */\n function createClass() {\n var parent = null,\n properties = slice.call(arguments, 0);\n\n if (typeof properties[0] === 'function') {\n parent = properties.shift();\n }\n function klass() {\n this.initialize.apply(this, arguments);\n }\n\n klass.superclass = parent;\n klass.subclasses = [];\n\n if (parent) {\n Subclass.prototype = parent.prototype;\n klass.prototype = new Subclass();\n parent.subclasses.push(klass);\n }\n for (var i = 0, length = properties.length; i < length; i++) {\n addMethods(klass, properties[i], parent);\n }\n if (!klass.prototype.initialize) {\n klass.prototype.initialize = emptyFunction;\n }\n klass.prototype.constructor = klass;\n klass.prototype.callSuper = callSuper;\n return klass;\n }\n\n fabric.util.createClass = createClass;\n})();\n\n\n(function () {\n // since ie10 or ie9 can use addEventListener but they do not support options, i need to check\n var couldUseAttachEvent = !!fabric.document.createElement('div').attachEvent;\n /**\n * Adds an event listener to an element\n * @function\n * @memberOf fabric.util\n * @param {HTMLElement} element\n * @param {String} eventName\n * @param {Function} handler\n */\n fabric.util.addListener = function(element, eventName, handler, options) {\n element && element.addEventListener(eventName, handler, couldUseAttachEvent ? false : options);\n };\n\n /**\n * Removes an event listener from an element\n * @function\n * @memberOf fabric.util\n * @param {HTMLElement} element\n * @param {String} eventName\n * @param {Function} handler\n */\n fabric.util.removeListener = function(element, eventName, handler, options) {\n element && element.removeEventListener(eventName, handler, couldUseAttachEvent ? false : options);\n };\n\n function getTouchInfo(event) {\n var touchProp = event.changedTouches;\n if (touchProp && touchProp[0]) {\n return touchProp[0];\n }\n return event;\n }\n\n fabric.util.getPointer = function(event) {\n var element = event.target,\n scroll = fabric.util.getScrollLeftTop(element),\n _evt = getTouchInfo(event);\n return {\n x: _evt.clientX + scroll.left,\n y: _evt.clientY + scroll.top\n };\n };\n})();\n\n\n(function () {\n\n /**\n * Cross-browser wrapper for setting element's style\n * @memberOf fabric.util\n * @param {HTMLElement} element\n * @param {Object} styles\n * @return {HTMLElement} Element that was passed as a first argument\n */\n function setStyle(element, styles) {\n var elementStyle = element.style;\n if (!elementStyle) {\n return element;\n }\n if (typeof styles === 'string') {\n element.style.cssText += ';' + styles;\n return styles.indexOf('opacity') > -1\n ? setOpacity(element, styles.match(/opacity:\\s*(\\d?\\.?\\d*)/)[1])\n : element;\n }\n for (var property in styles) {\n if (property === 'opacity') {\n setOpacity(element, styles[property]);\n }\n else {\n var normalizedProperty = (property === 'float' || property === 'cssFloat')\n ? (typeof elementStyle.styleFloat === 'undefined' ? 'cssFloat' : 'styleFloat')\n : property;\n elementStyle[normalizedProperty] = styles[property];\n }\n }\n return element;\n }\n\n var parseEl = fabric.document.createElement('div'),\n supportsOpacity = typeof parseEl.style.opacity === 'string',\n supportsFilters = typeof parseEl.style.filter === 'string',\n reOpacity = /alpha\\s*\\(\\s*opacity\\s*=\\s*([^\\)]+)\\)/,\n\n /** @ignore */\n setOpacity = function (element) { return element; };\n\n if (supportsOpacity) {\n /** @ignore */\n setOpacity = function(element, value) {\n element.style.opacity = value;\n return element;\n };\n }\n else if (supportsFilters) {\n /** @ignore */\n setOpacity = function(element, value) {\n var es = element.style;\n if (element.currentStyle && !element.currentStyle.hasLayout) {\n es.zoom = 1;\n }\n if (reOpacity.test(es.filter)) {\n value = value >= 0.9999 ? '' : ('alpha(opacity=' + (value * 100) + ')');\n es.filter = es.filter.replace(reOpacity, value);\n }\n else {\n es.filter += ' alpha(opacity=' + (value * 100) + ')';\n }\n return element;\n };\n }\n\n fabric.util.setStyle = setStyle;\n\n})();\n\n\n(function() {\n\n var _slice = Array.prototype.slice;\n\n /**\n * Takes id and returns an element with that id (if one exists in a document)\n * @memberOf fabric.util\n * @param {String|HTMLElement} id\n * @return {HTMLElement|null}\n */\n function getById(id) {\n return typeof id === 'string' ? fabric.document.getElementById(id) : id;\n }\n\n var sliceCanConvertNodelists,\n /**\n * Converts an array-like object (e.g. arguments or NodeList) to an array\n * @memberOf fabric.util\n * @param {Object} arrayLike\n * @return {Array}\n */\n toArray = function(arrayLike) {\n return _slice.call(arrayLike, 0);\n };\n\n try {\n sliceCanConvertNodelists = toArray(fabric.document.childNodes) instanceof Array;\n }\n catch (err) { }\n\n if (!sliceCanConvertNodelists) {\n toArray = function(arrayLike) {\n var arr = new Array(arrayLike.length), i = arrayLike.length;\n while (i--) {\n arr[i] = arrayLike[i];\n }\n return arr;\n };\n }\n\n /**\n * Creates specified element with specified attributes\n * @memberOf fabric.util\n * @param {String} tagName Type of an element to create\n * @param {Object} [attributes] Attributes to set on an element\n * @return {HTMLElement} Newly created element\n */\n function makeElement(tagName, attributes) {\n var el = fabric.document.createElement(tagName);\n for (var prop in attributes) {\n if (prop === 'class') {\n el.className = attributes[prop];\n }\n else if (prop === 'for') {\n el.htmlFor = attributes[prop];\n }\n else {\n el.setAttribute(prop, attributes[prop]);\n }\n }\n return el;\n }\n\n /**\n * Adds class to an element\n * @memberOf fabric.util\n * @param {HTMLElement} element Element to add class to\n * @param {String} className Class to add to an element\n */\n function addClass(element, className) {\n if (element && (' ' + element.className + ' ').indexOf(' ' + className + ' ') === -1) {\n element.className += (element.className ? ' ' : '') + className;\n }\n }\n\n /**\n * Wraps element with another element\n * @memberOf fabric.util\n * @param {HTMLElement} element Element to wrap\n * @param {HTMLElement|String} wrapper Element to wrap with\n * @param {Object} [attributes] Attributes to set on a wrapper\n * @return {HTMLElement} wrapper\n */\n function wrapElement(element, wrapper, attributes) {\n if (typeof wrapper === 'string') {\n wrapper = makeElement(wrapper, attributes);\n }\n if (element.parentNode) {\n element.parentNode.replaceChild(wrapper, element);\n }\n wrapper.appendChild(element);\n return wrapper;\n }\n\n /**\n * Returns element scroll offsets\n * @memberOf fabric.util\n * @param {HTMLElement} element Element to operate on\n * @return {Object} Object with left/top values\n */\n function getScrollLeftTop(element) {\n\n var left = 0,\n top = 0,\n docElement = fabric.document.documentElement,\n body = fabric.document.body || {\n scrollLeft: 0, scrollTop: 0\n };\n\n // While loop checks (and then sets element to) .parentNode OR .host\n // to account for ShadowDOM. We still want to traverse up out of ShadowDOM,\n // but the .parentNode of a root ShadowDOM node will always be null, instead\n // it should be accessed through .host. See http://stackoverflow.com/a/24765528/4383938\n while (element && (element.parentNode || element.host)) {\n\n // Set element to element parent, or 'host' in case of ShadowDOM\n element = element.parentNode || element.host;\n\n if (element === fabric.document) {\n left = body.scrollLeft || docElement.scrollLeft || 0;\n top = body.scrollTop || docElement.scrollTop || 0;\n }\n else {\n left += element.scrollLeft || 0;\n top += element.scrollTop || 0;\n }\n\n if (element.nodeType === 1 && element.style.position === 'fixed') {\n break;\n }\n }\n\n return { left: left, top: top };\n }\n\n /**\n * Returns offset for a given element\n * @function\n * @memberOf fabric.util\n * @param {HTMLElement} element Element to get offset for\n * @return {Object} Object with \"left\" and \"top\" properties\n */\n function getElementOffset(element) {\n var docElem,\n doc = element && element.ownerDocument,\n box = { left: 0, top: 0 },\n offset = { left: 0, top: 0 },\n scrollLeftTop,\n offsetAttributes = {\n borderLeftWidth: 'left',\n borderTopWidth: 'top',\n paddingLeft: 'left',\n paddingTop: 'top'\n };\n\n if (!doc) {\n return offset;\n }\n\n for (var attr in offsetAttributes) {\n offset[offsetAttributes[attr]] += parseInt(getElementStyle(element, attr), 10) || 0;\n }\n\n docElem = doc.documentElement;\n if ( typeof element.getBoundingClientRect !== 'undefined' ) {\n box = element.getBoundingClientRect();\n }\n\n scrollLeftTop = getScrollLeftTop(element);\n\n return {\n left: box.left + scrollLeftTop.left - (docElem.clientLeft || 0) + offset.left,\n top: box.top + scrollLeftTop.top - (docElem.clientTop || 0) + offset.top\n };\n }\n\n /**\n * Returns style attribute value of a given element\n * @memberOf fabric.util\n * @param {HTMLElement} element Element to get style attribute for\n * @param {String} attr Style attribute to get for element\n * @return {String} Style attribute value of the given element.\n */\n var getElementStyle;\n if (fabric.document.defaultView && fabric.document.defaultView.getComputedStyle) {\n getElementStyle = function(element, attr) {\n var style = fabric.document.defaultView.getComputedStyle(element, null);\n return style ? style[attr] : undefined;\n };\n }\n else {\n getElementStyle = function(element, attr) {\n var value = element.style[attr];\n if (!value && element.currentStyle) {\n value = element.currentStyle[attr];\n }\n return value;\n };\n }\n\n (function () {\n var style = fabric.document.documentElement.style,\n selectProp = 'userSelect' in style\n ? 'userSelect'\n : 'MozUserSelect' in style\n ? 'MozUserSelect'\n : 'WebkitUserSelect' in style\n ? 'WebkitUserSelect'\n : 'KhtmlUserSelect' in style\n ? 'KhtmlUserSelect'\n : '';\n\n /**\n * Makes element unselectable\n * @memberOf fabric.util\n * @param {HTMLElement} element Element to make unselectable\n * @return {HTMLElement} Element that was passed in\n */\n function makeElementUnselectable(element) {\n if (typeof element.onselectstart !== 'undefined') {\n element.onselectstart = fabric.util.falseFunction;\n }\n if (selectProp) {\n element.style[selectProp] = 'none';\n }\n else if (typeof element.unselectable === 'string') {\n element.unselectable = 'on';\n }\n return element;\n }\n\n /**\n * Makes element selectable\n * @memberOf fabric.util\n * @param {HTMLElement} element Element to make selectable\n * @return {HTMLElement} Element that was passed in\n */\n function makeElementSelectable(element) {\n if (typeof element.onselectstart !== 'undefined') {\n element.onselectstart = null;\n }\n if (selectProp) {\n element.style[selectProp] = '';\n }\n else if (typeof element.unselectable === 'string') {\n element.unselectable = '';\n }\n return element;\n }\n\n fabric.util.makeElementUnselectable = makeElementUnselectable;\n fabric.util.makeElementSelectable = makeElementSelectable;\n })();\n\n (function() {\n\n /**\n * Inserts a script element with a given url into a document; invokes callback, when that script is finished loading\n * @memberOf fabric.util\n * @param {String} url URL of a script to load\n * @param {Function} callback Callback to execute when script is finished loading\n */\n function getScript(url, callback) {\n var headEl = fabric.document.getElementsByTagName('head')[0],\n scriptEl = fabric.document.createElement('script'),\n loading = true;\n\n /** @ignore */\n scriptEl.onload = /** @ignore */ scriptEl.onreadystatechange = function(e) {\n if (loading) {\n if (typeof this.readyState === 'string' &&\n this.readyState !== 'loaded' &&\n this.readyState !== 'complete') {\n return;\n }\n loading = false;\n callback(e || fabric.window.event);\n scriptEl = scriptEl.onload = scriptEl.onreadystatechange = null;\n }\n };\n scriptEl.src = url;\n headEl.appendChild(scriptEl);\n // causes issue in Opera\n // headEl.removeChild(scriptEl);\n }\n\n fabric.util.getScript = getScript;\n })();\n\n function getNodeCanvas(element) {\n var impl = fabric.jsdomImplForWrapper(element);\n return impl._canvas || impl._image;\n };\n\n function cleanUpJsdomNode(element) {\n if (!fabric.isLikelyNode) {\n return;\n }\n var impl = fabric.jsdomImplForWrapper(element);\n if (impl) {\n impl._image = null;\n impl._canvas = null;\n // unsure if necessary\n impl._currentSrc = null;\n impl._attributes = null;\n impl._classList = null;\n }\n }\n\n fabric.util.getById = getById;\n fabric.util.toArray = toArray;\n fabric.util.makeElement = makeElement;\n fabric.util.addClass = addClass;\n fabric.util.wrapElement = wrapElement;\n fabric.util.getScrollLeftTop = getScrollLeftTop;\n fabric.util.getElementOffset = getElementOffset;\n fabric.util.getElementStyle = getElementStyle;\n fabric.util.getNodeCanvas = getNodeCanvas;\n fabric.util.cleanUpJsdomNode = cleanUpJsdomNode;\n\n})();\n\n\n(function() {\n\n function addParamToUrl(url, param) {\n return url + (/\\?/.test(url) ? '&' : '?') + param;\n }\n\n function emptyFn() { }\n\n /**\n * Cross-browser abstraction for sending XMLHttpRequest\n * @memberOf fabric.util\n * @param {String} url URL to send XMLHttpRequest to\n * @param {Object} [options] Options object\n * @param {String} [options.method=\"GET\"]\n * @param {String} [options.parameters] parameters to append to url in GET or in body\n * @param {String} [options.body] body to send with POST or PUT request\n * @param {Function} options.onComplete Callback to invoke when request is completed\n * @return {XMLHttpRequest} request\n */\n function request(url, options) {\n options || (options = { });\n\n var method = options.method ? options.method.toUpperCase() : 'GET',\n onComplete = options.onComplete || function() { },\n xhr = new fabric.window.XMLHttpRequest(),\n body = options.body || options.parameters;\n\n /** @ignore */\n xhr.onreadystatechange = function() {\n if (xhr.readyState === 4) {\n onComplete(xhr);\n xhr.onreadystatechange = emptyFn;\n }\n };\n\n if (method === 'GET') {\n body = null;\n if (typeof options.parameters === 'string') {\n url = addParamToUrl(url, options.parameters);\n }\n }\n\n xhr.open(method, url, true);\n\n if (method === 'POST' || method === 'PUT') {\n xhr.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded');\n }\n\n xhr.send(body);\n return xhr;\n }\n\n fabric.util.request = request;\n})();\n\n\n/**\n * Wrapper around `console.log` (when available)\n * @param {*} [values] Values to log\n */\nfabric.log = console.log;\n\n/**\n * Wrapper around `console.warn` (when available)\n * @param {*} [values] Values to log as a warning\n */\nfabric.warn = console.warn;\n\n\n(function() {\n\n function noop() {\n return false;\n }\n\n function defaultEasing(t, b, c, d) {\n return -c * Math.cos(t / d * (Math.PI / 2)) + c + b;\n }\n\n /**\n * Changes value from one to another within certain period of time, invoking callbacks as value is being changed.\n * @memberOf fabric.util\n * @param {Object} [options] Animation options\n * @param {Function} [options.onChange] Callback; invoked on every value change\n * @param {Function} [options.onComplete] Callback; invoked when value change is completed\n * @param {Number} [options.startValue=0] Starting value\n * @param {Number} [options.endValue=100] Ending value\n * @param {Number} [options.byValue=100] Value to modify the property by\n * @param {Function} [options.easing] Easing function\n * @param {Number} [options.duration=500] Duration of change (in ms)\n * @param {Function} [options.abort] Additional function with logic. If returns true, onComplete is called.\n */\n function animate(options) {\n\n requestAnimFrame(function(timestamp) {\n options || (options = { });\n\n var start = timestamp || +new Date(),\n duration = options.duration || 500,\n finish = start + duration, time,\n onChange = options.onChange || noop,\n abort = options.abort || noop,\n onComplete = options.onComplete || noop,\n easing = options.easing || defaultEasing,\n startValue = 'startValue' in options ? options.startValue : 0,\n endValue = 'endValue' in options ? options.endValue : 100,\n byValue = options.byValue || endValue - startValue;\n\n options.onStart && options.onStart();\n\n (function tick(ticktime) {\n // TODO: move abort call after calculation\n // and pass (current,valuePerc, timePerc) as arguments\n time = ticktime || +new Date();\n var currentTime = time > finish ? duration : (time - start),\n timePerc = currentTime / duration,\n current = easing(currentTime, startValue, byValue, duration),\n valuePerc = Math.abs((current - startValue) / byValue);\n if (abort()) {\n onComplete(endValue, 1, 1);\n return;\n }\n if (time > finish) {\n onChange(endValue, 1, 1);\n onComplete(endValue, 1, 1);\n return;\n }\n else {\n onChange(current, valuePerc, timePerc);\n requestAnimFrame(tick);\n }\n })(start);\n });\n }\n\n var _requestAnimFrame = fabric.window.requestAnimationFrame ||\n fabric.window.webkitRequestAnimationFrame ||\n fabric.window.mozRequestAnimationFrame ||\n fabric.window.oRequestAnimationFrame ||\n fabric.window.msRequestAnimationFrame ||\n function(callback) {\n return fabric.window.setTimeout(callback, 1000 / 60);\n };\n\n var _cancelAnimFrame = fabric.window.cancelAnimationFrame || fabric.window.clearTimeout;\n\n /**\n * requestAnimationFrame polyfill based on http://paulirish.com/2011/requestanimationframe-for-smart-animating/\n * In order to get a precise start time, `requestAnimFrame` should be called as an entry into the method\n * @memberOf fabric.util\n * @param {Function} callback Callback to invoke\n * @param {DOMElement} element optional Element to associate with animation\n */\n function requestAnimFrame() {\n return _requestAnimFrame.apply(fabric.window, arguments);\n }\n\n function cancelAnimFrame() {\n return _cancelAnimFrame.apply(fabric.window, arguments);\n }\n\n fabric.util.animate = animate;\n fabric.util.requestAnimFrame = requestAnimFrame;\n fabric.util.cancelAnimFrame = cancelAnimFrame;\n})();\n\n\n(function() {\n // Calculate an in-between color. Returns a \"rgba()\" string.\n // Credit: Edwin Martin \n // http://www.bitstorm.org/jquery/color-animation/jquery.animate-colors.js\n function calculateColor(begin, end, pos) {\n var color = 'rgba('\n + parseInt((begin[0] + pos * (end[0] - begin[0])), 10) + ','\n + parseInt((begin[1] + pos * (end[1] - begin[1])), 10) + ','\n + parseInt((begin[2] + pos * (end[2] - begin[2])), 10);\n\n color += ',' + (begin && end ? parseFloat(begin[3] + pos * (end[3] - begin[3])) : 1);\n color += ')';\n return color;\n }\n\n /**\n * Changes the color from one to another within certain period of time, invoking callbacks as value is being changed.\n * @memberOf fabric.util\n * @param {String} fromColor The starting color in hex or rgb(a) format.\n * @param {String} toColor The starting color in hex or rgb(a) format.\n * @param {Number} [duration] Duration of change (in ms).\n * @param {Object} [options] Animation options\n * @param {Function} [options.onChange] Callback; invoked on every value change\n * @param {Function} [options.onComplete] Callback; invoked when value change is completed\n * @param {Function} [options.colorEasing] Easing function. Note that this function only take two arguments (currentTime, duration). Thus the regular animation easing functions cannot be used.\n * @param {Function} [options.abort] Additional function with logic. If returns true, onComplete is called.\n */\n function animateColor(fromColor, toColor, duration, options) {\n var startColor = new fabric.Color(fromColor).getSource(),\n endColor = new fabric.Color(toColor).getSource();\n\n options = options || {};\n\n fabric.util.animate(fabric.util.object.extend(options, {\n duration: duration || 500,\n startValue: startColor,\n endValue: endColor,\n byValue: endColor,\n easing: function (currentTime, startValue, byValue, duration) {\n var posValue = options.colorEasing\n ? options.colorEasing(currentTime, duration)\n : 1 - Math.cos(currentTime / duration * (Math.PI / 2));\n return calculateColor(startValue, byValue, posValue);\n }\n }));\n }\n\n fabric.util.animateColor = animateColor;\n\n})();\n\n\n(function() {\n\n function normalize(a, c, p, s) {\n if (a < Math.abs(c)) {\n a = c;\n s = p / 4;\n }\n else {\n //handle the 0/0 case:\n if (c === 0 && a === 0) {\n s = p / (2 * Math.PI) * Math.asin(1);\n }\n else {\n s = p / (2 * Math.PI) * Math.asin(c / a);\n }\n }\n return { a: a, c: c, p: p, s: s };\n }\n\n function elastic(opts, t, d) {\n return opts.a *\n Math.pow(2, 10 * (t -= 1)) *\n Math.sin( (t * d - opts.s) * (2 * Math.PI) / opts.p );\n }\n\n /**\n * Cubic easing out\n * @memberOf fabric.util.ease\n */\n function easeOutCubic(t, b, c, d) {\n return c * ((t = t / d - 1) * t * t + 1) + b;\n }\n\n /**\n * Cubic easing in and out\n * @memberOf fabric.util.ease\n */\n function easeInOutCubic(t, b, c, d) {\n t /= d / 2;\n if (t < 1) {\n return c / 2 * t * t * t + b;\n }\n return c / 2 * ((t -= 2) * t * t + 2) + b;\n }\n\n /**\n * Quartic easing in\n * @memberOf fabric.util.ease\n */\n function easeInQuart(t, b, c, d) {\n return c * (t /= d) * t * t * t + b;\n }\n\n /**\n * Quartic easing out\n * @memberOf fabric.util.ease\n */\n function easeOutQuart(t, b, c, d) {\n return -c * ((t = t / d - 1) * t * t * t - 1) + b;\n }\n\n /**\n * Quartic easing in and out\n * @memberOf fabric.util.ease\n */\n function easeInOutQuart(t, b, c, d) {\n t /= d / 2;\n if (t < 1) {\n return c / 2 * t * t * t * t + b;\n }\n return -c / 2 * ((t -= 2) * t * t * t - 2) + b;\n }\n\n /**\n * Quintic easing in\n * @memberOf fabric.util.ease\n */\n function easeInQuint(t, b, c, d) {\n return c * (t /= d) * t * t * t * t + b;\n }\n\n /**\n * Quintic easing out\n * @memberOf fabric.util.ease\n */\n function easeOutQuint(t, b, c, d) {\n return c * ((t = t / d - 1) * t * t * t * t + 1) + b;\n }\n\n /**\n * Quintic easing in and out\n * @memberOf fabric.util.ease\n */\n function easeInOutQuint(t, b, c, d) {\n t /= d / 2;\n if (t < 1) {\n return c / 2 * t * t * t * t * t + b;\n }\n return c / 2 * ((t -= 2) * t * t * t * t + 2) + b;\n }\n\n /**\n * Sinusoidal easing in\n * @memberOf fabric.util.ease\n */\n function easeInSine(t, b, c, d) {\n return -c * Math.cos(t / d * (Math.PI / 2)) + c + b;\n }\n\n /**\n * Sinusoidal easing out\n * @memberOf fabric.util.ease\n */\n function easeOutSine(t, b, c, d) {\n return c * Math.sin(t / d * (Math.PI / 2)) + b;\n }\n\n /**\n * Sinusoidal easing in and out\n * @memberOf fabric.util.ease\n */\n function easeInOutSine(t, b, c, d) {\n return -c / 2 * (Math.cos(Math.PI * t / d) - 1) + b;\n }\n\n /**\n * Exponential easing in\n * @memberOf fabric.util.ease\n */\n function easeInExpo(t, b, c, d) {\n return (t === 0) ? b : c * Math.pow(2, 10 * (t / d - 1)) + b;\n }\n\n /**\n * Exponential easing out\n * @memberOf fabric.util.ease\n */\n function easeOutExpo(t, b, c, d) {\n return (t === d) ? b + c : c * (-Math.pow(2, -10 * t / d) + 1) + b;\n }\n\n /**\n * Exponential easing in and out\n * @memberOf fabric.util.ease\n */\n function easeInOutExpo(t, b, c, d) {\n if (t === 0) {\n return b;\n }\n if (t === d) {\n return b + c;\n }\n t /= d / 2;\n if (t < 1) {\n return c / 2 * Math.pow(2, 10 * (t - 1)) + b;\n }\n return c / 2 * (-Math.pow(2, -10 * --t) + 2) + b;\n }\n\n /**\n * Circular easing in\n * @memberOf fabric.util.ease\n */\n function easeInCirc(t, b, c, d) {\n return -c * (Math.sqrt(1 - (t /= d) * t) - 1) + b;\n }\n\n /**\n * Circular easing out\n * @memberOf fabric.util.ease\n */\n function easeOutCirc(t, b, c, d) {\n return c * Math.sqrt(1 - (t = t / d - 1) * t) + b;\n }\n\n /**\n * Circular easing in and out\n * @memberOf fabric.util.ease\n */\n function easeInOutCirc(t, b, c, d) {\n t /= d / 2;\n if (t < 1) {\n return -c / 2 * (Math.sqrt(1 - t * t) - 1) + b;\n }\n return c / 2 * (Math.sqrt(1 - (t -= 2) * t) + 1) + b;\n }\n\n /**\n * Elastic easing in\n * @memberOf fabric.util.ease\n */\n function easeInElastic(t, b, c, d) {\n var s = 1.70158, p = 0, a = c;\n if (t === 0) {\n return b;\n }\n t /= d;\n if (t === 1) {\n return b + c;\n }\n if (!p) {\n p = d * 0.3;\n }\n var opts = normalize(a, c, p, s);\n return -elastic(opts, t, d) + b;\n }\n\n /**\n * Elastic easing out\n * @memberOf fabric.util.ease\n */\n function easeOutElastic(t, b, c, d) {\n var s = 1.70158, p = 0, a = c;\n if (t === 0) {\n return b;\n }\n t /= d;\n if (t === 1) {\n return b + c;\n }\n if (!p) {\n p = d * 0.3;\n }\n var opts = normalize(a, c, p, s);\n return opts.a * Math.pow(2, -10 * t) * Math.sin((t * d - opts.s) * (2 * Math.PI) / opts.p ) + opts.c + b;\n }\n\n /**\n * Elastic easing in and out\n * @memberOf fabric.util.ease\n */\n function easeInOutElastic(t, b, c, d) {\n var s = 1.70158, p = 0, a = c;\n if (t === 0) {\n return b;\n }\n t /= d / 2;\n if (t === 2) {\n return b + c;\n }\n if (!p) {\n p = d * (0.3 * 1.5);\n }\n var opts = normalize(a, c, p, s);\n if (t < 1) {\n return -0.5 * elastic(opts, t, d) + b;\n }\n return opts.a * Math.pow(2, -10 * (t -= 1)) *\n Math.sin((t * d - opts.s) * (2 * Math.PI) / opts.p ) * 0.5 + opts.c + b;\n }\n\n /**\n * Backwards easing in\n * @memberOf fabric.util.ease\n */\n function easeInBack(t, b, c, d, s) {\n if (s === undefined) {\n s = 1.70158;\n }\n return c * (t /= d) * t * ((s + 1) * t - s) + b;\n }\n\n /**\n * Backwards easing out\n * @memberOf fabric.util.ease\n */\n function easeOutBack(t, b, c, d, s) {\n if (s === undefined) {\n s = 1.70158;\n }\n return c * ((t = t / d - 1) * t * ((s + 1) * t + s) + 1) + b;\n }\n\n /**\n * Backwards easing in and out\n * @memberOf fabric.util.ease\n */\n function easeInOutBack(t, b, c, d, s) {\n if (s === undefined) {\n s = 1.70158;\n }\n t /= d / 2;\n if (t < 1) {\n return c / 2 * (t * t * (((s *= (1.525)) + 1) * t - s)) + b;\n }\n return c / 2 * ((t -= 2) * t * (((s *= (1.525)) + 1) * t + s) + 2) + b;\n }\n\n /**\n * Bouncing easing in\n * @memberOf fabric.util.ease\n */\n function easeInBounce(t, b, c, d) {\n return c - easeOutBounce (d - t, 0, c, d) + b;\n }\n\n /**\n * Bouncing easing out\n * @memberOf fabric.util.ease\n */\n function easeOutBounce(t, b, c, d) {\n if ((t /= d) < (1 / 2.75)) {\n return c * (7.5625 * t * t) + b;\n }\n else if (t < (2 / 2.75)) {\n return c * (7.5625 * (t -= (1.5 / 2.75)) * t + 0.75) + b;\n }\n else if (t < (2.5 / 2.75)) {\n return c * (7.5625 * (t -= (2.25 / 2.75)) * t + 0.9375) + b;\n }\n else {\n return c * (7.5625 * (t -= (2.625 / 2.75)) * t + 0.984375) + b;\n }\n }\n\n /**\n * Bouncing easing in and out\n * @memberOf fabric.util.ease\n */\n function easeInOutBounce(t, b, c, d) {\n if (t < d / 2) {\n return easeInBounce (t * 2, 0, c, d) * 0.5 + b;\n }\n return easeOutBounce(t * 2 - d, 0, c, d) * 0.5 + c * 0.5 + b;\n }\n\n /**\n * Easing functions\n * See Easing Equations by Robert Penner\n * @namespace fabric.util.ease\n */\n fabric.util.ease = {\n\n /**\n * Quadratic easing in\n * @memberOf fabric.util.ease\n */\n easeInQuad: function(t, b, c, d) {\n return c * (t /= d) * t + b;\n },\n\n /**\n * Quadratic easing out\n * @memberOf fabric.util.ease\n */\n easeOutQuad: function(t, b, c, d) {\n return -c * (t /= d) * (t - 2) + b;\n },\n\n /**\n * Quadratic easing in and out\n * @memberOf fabric.util.ease\n */\n easeInOutQuad: function(t, b, c, d) {\n t /= (d / 2);\n if (t < 1) {\n return c / 2 * t * t + b;\n }\n return -c / 2 * ((--t) * (t - 2) - 1) + b;\n },\n\n /**\n * Cubic easing in\n * @memberOf fabric.util.ease\n */\n easeInCubic: function(t, b, c, d) {\n return c * (t /= d) * t * t + b;\n },\n\n easeOutCubic: easeOutCubic,\n easeInOutCubic: easeInOutCubic,\n easeInQuart: easeInQuart,\n easeOutQuart: easeOutQuart,\n easeInOutQuart: easeInOutQuart,\n easeInQuint: easeInQuint,\n easeOutQuint: easeOutQuint,\n easeInOutQuint: easeInOutQuint,\n easeInSine: easeInSine,\n easeOutSine: easeOutSine,\n easeInOutSine: easeInOutSine,\n easeInExpo: easeInExpo,\n easeOutExpo: easeOutExpo,\n easeInOutExpo: easeInOutExpo,\n easeInCirc: easeInCirc,\n easeOutCirc: easeOutCirc,\n easeInOutCirc: easeInOutCirc,\n easeInElastic: easeInElastic,\n easeOutElastic: easeOutElastic,\n easeInOutElastic: easeInOutElastic,\n easeInBack: easeInBack,\n easeOutBack: easeOutBack,\n easeInOutBack: easeInOutBack,\n easeInBounce: easeInBounce,\n easeOutBounce: easeOutBounce,\n easeInOutBounce: easeInOutBounce\n };\n\n})();\n\n\n(function(global) {\n\n 'use strict';\n\n /**\n * @name fabric\n * @namespace\n */\n\n var fabric = global.fabric || (global.fabric = { }),\n extend = fabric.util.object.extend,\n clone = fabric.util.object.clone,\n toFixed = fabric.util.toFixed,\n parseUnit = fabric.util.parseUnit,\n multiplyTransformMatrices = fabric.util.multiplyTransformMatrices,\n\n svgValidTagNames = ['path', 'circle', 'polygon', 'polyline', 'ellipse', 'rect', 'line',\n 'image', 'text'],\n svgViewBoxElements = ['symbol', 'image', 'marker', 'pattern', 'view', 'svg'],\n svgInvalidAncestors = ['pattern', 'defs', 'symbol', 'metadata', 'clipPath', 'mask', 'desc'],\n svgValidParents = ['symbol', 'g', 'a', 'svg', 'clipPath', 'defs'],\n\n attributesMap = {\n cx: 'left',\n x: 'left',\n r: 'radius',\n cy: 'top',\n y: 'top',\n display: 'visible',\n visibility: 'visible',\n transform: 'transformMatrix',\n 'fill-opacity': 'fillOpacity',\n 'fill-rule': 'fillRule',\n 'font-family': 'fontFamily',\n 'font-size': 'fontSize',\n 'font-style': 'fontStyle',\n 'font-weight': 'fontWeight',\n 'letter-spacing': 'charSpacing',\n 'paint-order': 'paintFirst',\n 'stroke-dasharray': 'strokeDashArray',\n 'stroke-dashoffset': 'strokeDashOffset',\n 'stroke-linecap': 'strokeLineCap',\n 'stroke-linejoin': 'strokeLineJoin',\n 'stroke-miterlimit': 'strokeMiterLimit',\n 'stroke-opacity': 'strokeOpacity',\n 'stroke-width': 'strokeWidth',\n 'text-decoration': 'textDecoration',\n 'text-anchor': 'textAnchor',\n opacity: 'opacity',\n 'clip-path': 'clipPath',\n 'clip-rule': 'clipRule',\n 'vector-effect': 'strokeUniform'\n },\n\n colorAttributes = {\n stroke: 'strokeOpacity',\n fill: 'fillOpacity'\n },\n\n fSize = 'font-size', cPath = 'clip-path';\n\n fabric.svgValidTagNamesRegEx = getSvgRegex(svgValidTagNames);\n fabric.svgViewBoxElementsRegEx = getSvgRegex(svgViewBoxElements);\n fabric.svgInvalidAncestorsRegEx = getSvgRegex(svgInvalidAncestors);\n fabric.svgValidParentsRegEx = getSvgRegex(svgValidParents);\n\n fabric.cssRules = { };\n fabric.gradientDefs = { };\n fabric.clipPaths = { };\n\n function normalizeAttr(attr) {\n // transform attribute names\n if (attr in attributesMap) {\n return attributesMap[attr];\n }\n return attr;\n }\n\n function normalizeValue(attr, value, parentAttributes, fontSize) {\n var isArray = Object.prototype.toString.call(value) === '[object Array]',\n parsed;\n\n if ((attr === 'fill' || attr === 'stroke') && value === 'none') {\n value = '';\n }\n else if (attr === 'vector-effect') {\n value = value === 'non-scaling-stroke';\n }\n else if (attr === 'strokeDashArray') {\n if (value === 'none') {\n value = null;\n }\n else {\n value = value.replace(/,/g, ' ').split(/\\s+/).map(parseFloat);\n }\n }\n else if (attr === 'transformMatrix') {\n if (parentAttributes && parentAttributes.transformMatrix) {\n value = multiplyTransformMatrices(\n parentAttributes.transformMatrix, fabric.parseTransformAttribute(value));\n }\n else {\n value = fabric.parseTransformAttribute(value);\n }\n }\n else if (attr === 'visible') {\n value = value !== 'none' && value !== 'hidden';\n // display=none on parent element always takes precedence over child element\n if (parentAttributes && parentAttributes.visible === false) {\n value = false;\n }\n }\n else if (attr === 'opacity') {\n value = parseFloat(value);\n if (parentAttributes && typeof parentAttributes.opacity !== 'undefined') {\n value *= parentAttributes.opacity;\n }\n }\n else if (attr === 'textAnchor' /* text-anchor */) {\n value = value === 'start' ? 'left' : value === 'end' ? 'right' : 'center';\n }\n else if (attr === 'charSpacing') {\n // parseUnit returns px and we convert it to em\n parsed = parseUnit(value, fontSize) / fontSize * 1000;\n }\n else if (attr === 'paintFirst') {\n var fillIndex = value.indexOf('fill');\n var strokeIndex = value.indexOf('stroke');\n var value = 'fill';\n if (fillIndex > -1 && strokeIndex > -1 && strokeIndex < fillIndex) {\n value = 'stroke';\n }\n else if (fillIndex === -1 && strokeIndex > -1) {\n value = 'stroke';\n }\n }\n else if (attr === 'href' || attr === 'xlink:href') {\n return value;\n }\n else {\n parsed = isArray ? value.map(parseUnit) : parseUnit(value, fontSize);\n }\n\n return (!isArray && isNaN(parsed) ? value : parsed);\n }\n\n /**\n * @private\n */\n function getSvgRegex(arr) {\n return new RegExp('^(' + arr.join('|') + ')\\\\b', 'i');\n }\n\n /**\n * @private\n * @param {Object} attributes Array of attributes to parse\n */\n function _setStrokeFillOpacity(attributes) {\n for (var attr in colorAttributes) {\n\n if (typeof attributes[colorAttributes[attr]] === 'undefined' || attributes[attr] === '') {\n continue;\n }\n\n if (typeof attributes[attr] === 'undefined') {\n if (!fabric.Object.prototype[attr]) {\n continue;\n }\n attributes[attr] = fabric.Object.prototype[attr];\n }\n\n if (attributes[attr].indexOf('url(') === 0) {\n continue;\n }\n\n var color = new fabric.Color(attributes[attr]);\n attributes[attr] = color.setAlpha(toFixed(color.getAlpha() * attributes[colorAttributes[attr]], 2)).toRgba();\n }\n return attributes;\n }\n\n /**\n * @private\n */\n function _getMultipleNodes(doc, nodeNames) {\n var nodeName, nodeArray = [], nodeList, i, len;\n for (i = 0, len = nodeNames.length; i < len; i++) {\n nodeName = nodeNames[i];\n nodeList = doc.getElementsByTagName(nodeName);\n nodeArray = nodeArray.concat(Array.prototype.slice.call(nodeList));\n }\n return nodeArray;\n }\n\n /**\n * Parses \"transform\" attribute, returning an array of values\n * @static\n * @function\n * @memberOf fabric\n * @param {String} attributeValue String containing attribute value\n * @return {Array} Array of 6 elements representing transformation matrix\n */\n fabric.parseTransformAttribute = (function() {\n function rotateMatrix(matrix, args) {\n var cos = fabric.util.cos(args[0]), sin = fabric.util.sin(args[0]),\n x = 0, y = 0;\n if (args.length === 3) {\n x = args[1];\n y = args[2];\n }\n\n matrix[0] = cos;\n matrix[1] = sin;\n matrix[2] = -sin;\n matrix[3] = cos;\n matrix[4] = x - (cos * x - sin * y);\n matrix[5] = y - (sin * x + cos * y);\n }\n\n function scaleMatrix(matrix, args) {\n var multiplierX = args[0],\n multiplierY = (args.length === 2) ? args[1] : args[0];\n\n matrix[0] = multiplierX;\n matrix[3] = multiplierY;\n }\n\n function skewMatrix(matrix, args, pos) {\n matrix[pos] = Math.tan(fabric.util.degreesToRadians(args[0]));\n }\n\n function translateMatrix(matrix, args) {\n matrix[4] = args[0];\n if (args.length === 2) {\n matrix[5] = args[1];\n }\n }\n\n // identity matrix\n var iMatrix = fabric.iMatrix,\n\n // == begin transform regexp\n number = fabric.reNum,\n\n commaWsp = '(?:\\\\s+,?\\\\s*|,\\\\s*)',\n\n skewX = '(?:(skewX)\\\\s*\\\\(\\\\s*(' + number + ')\\\\s*\\\\))',\n\n skewY = '(?:(skewY)\\\\s*\\\\(\\\\s*(' + number + ')\\\\s*\\\\))',\n\n rotate = '(?:(rotate)\\\\s*\\\\(\\\\s*(' + number + ')(?:' +\n commaWsp + '(' + number + ')' +\n commaWsp + '(' + number + '))?\\\\s*\\\\))',\n\n scale = '(?:(scale)\\\\s*\\\\(\\\\s*(' + number + ')(?:' +\n commaWsp + '(' + number + '))?\\\\s*\\\\))',\n\n translate = '(?:(translate)\\\\s*\\\\(\\\\s*(' + number + ')(?:' +\n commaWsp + '(' + number + '))?\\\\s*\\\\))',\n\n matrix = '(?:(matrix)\\\\s*\\\\(\\\\s*' +\n '(' + number + ')' + commaWsp +\n '(' + number + ')' + commaWsp +\n '(' + number + ')' + commaWsp +\n '(' + number + ')' + commaWsp +\n '(' + number + ')' + commaWsp +\n '(' + number + ')' +\n '\\\\s*\\\\))',\n\n transform = '(?:' +\n matrix + '|' +\n translate + '|' +\n scale + '|' +\n rotate + '|' +\n skewX + '|' +\n skewY +\n ')',\n\n transforms = '(?:' + transform + '(?:' + commaWsp + '*' + transform + ')*' + ')',\n\n transformList = '^\\\\s*(?:' + transforms + '?)\\\\s*$',\n\n // http://www.w3.org/TR/SVG/coords.html#TransformAttribute\n reTransformList = new RegExp(transformList),\n // == end transform regexp\n\n reTransform = new RegExp(transform, 'g');\n\n return function(attributeValue) {\n\n // start with identity matrix\n var matrix = iMatrix.concat(),\n matrices = [];\n\n // return if no argument was given or\n // an argument does not match transform attribute regexp\n if (!attributeValue || (attributeValue && !reTransformList.test(attributeValue))) {\n return matrix;\n }\n\n attributeValue.replace(reTransform, function(match) {\n\n var m = new RegExp(transform).exec(match).filter(function (match) {\n // match !== '' && match != null\n return (!!match);\n }),\n operation = m[1],\n args = m.slice(2).map(parseFloat);\n\n switch (operation) {\n case 'translate':\n translateMatrix(matrix, args);\n break;\n case 'rotate':\n args[0] = fabric.util.degreesToRadians(args[0]);\n rotateMatrix(matrix, args);\n break;\n case 'scale':\n scaleMatrix(matrix, args);\n break;\n case 'skewX':\n skewMatrix(matrix, args, 2);\n break;\n case 'skewY':\n skewMatrix(matrix, args, 1);\n break;\n case 'matrix':\n matrix = args;\n break;\n }\n\n // snapshot current matrix into matrices array\n matrices.push(matrix.concat());\n // reset\n matrix = iMatrix.concat();\n });\n\n var combinedMatrix = matrices[0];\n while (matrices.length > 1) {\n matrices.shift();\n combinedMatrix = fabric.util.multiplyTransformMatrices(combinedMatrix, matrices[0]);\n }\n return combinedMatrix;\n };\n })();\n\n /**\n * @private\n */\n function parseStyleString(style, oStyle) {\n var attr, value;\n style.replace(/;\\s*$/, '').split(';').forEach(function (chunk) {\n var pair = chunk.split(':');\n\n attr = pair[0].trim().toLowerCase();\n value = pair[1].trim();\n\n oStyle[attr] = value;\n });\n }\n\n /**\n * @private\n */\n function parseStyleObject(style, oStyle) {\n var attr, value;\n for (var prop in style) {\n if (typeof style[prop] === 'undefined') {\n continue;\n }\n\n attr = prop.toLowerCase();\n value = style[prop];\n\n oStyle[attr] = value;\n }\n }\n\n /**\n * @private\n */\n function getGlobalStylesForElement(element, svgUid) {\n var styles = { };\n for (var rule in fabric.cssRules[svgUid]) {\n if (elementMatchesRule(element, rule.split(' '))) {\n for (var property in fabric.cssRules[svgUid][rule]) {\n styles[property] = fabric.cssRules[svgUid][rule][property];\n }\n }\n }\n return styles;\n }\n\n /**\n * @private\n */\n function elementMatchesRule(element, selectors) {\n var firstMatching, parentMatching = true;\n //start from rightmost selector.\n firstMatching = selectorMatches(element, selectors.pop());\n if (firstMatching && selectors.length) {\n parentMatching = doesSomeParentMatch(element, selectors);\n }\n return firstMatching && parentMatching && (selectors.length === 0);\n }\n\n function doesSomeParentMatch(element, selectors) {\n var selector, parentMatching = true;\n while (element.parentNode && element.parentNode.nodeType === 1 && selectors.length) {\n if (parentMatching) {\n selector = selectors.pop();\n }\n element = element.parentNode;\n parentMatching = selectorMatches(element, selector);\n }\n return selectors.length === 0;\n }\n\n /**\n * @private\n */\n function selectorMatches(element, selector) {\n var nodeName = element.nodeName,\n classNames = element.getAttribute('class'),\n id = element.getAttribute('id'), matcher, i;\n // i check if a selector matches slicing away part from it.\n // if i get empty string i should match\n matcher = new RegExp('^' + nodeName, 'i');\n selector = selector.replace(matcher, '');\n if (id && selector.length) {\n matcher = new RegExp('#' + id + '(?![a-zA-Z\\\\-]+)', 'i');\n selector = selector.replace(matcher, '');\n }\n if (classNames && selector.length) {\n classNames = classNames.split(' ');\n for (i = classNames.length; i--;) {\n matcher = new RegExp('\\\\.' + classNames[i] + '(?![a-zA-Z\\\\-]+)', 'i');\n selector = selector.replace(matcher, '');\n }\n }\n return selector.length === 0;\n }\n\n /**\n * @private\n * to support IE8 missing getElementById on SVGdocument and on node xmlDOM\n */\n function elementById(doc, id) {\n var el;\n doc.getElementById && (el = doc.getElementById(id));\n if (el) {\n return el;\n }\n var node, i, len, nodelist = doc.getElementsByTagName('*');\n for (i = 0, len = nodelist.length; i < len; i++) {\n node = nodelist[i];\n if (id === node.getAttribute('id')) {\n return node;\n }\n }\n }\n\n /**\n * @private\n */\n function parseUseDirectives(doc) {\n var nodelist = _getMultipleNodes(doc, ['use', 'svg:use']), i = 0;\n while (nodelist.length && i < nodelist.length) {\n var el = nodelist[i],\n xlink = (el.getAttribute('xlink:href') || el.getAttribute('href')).substr(1),\n x = el.getAttribute('x') || 0,\n y = el.getAttribute('y') || 0,\n el2 = elementById(doc, xlink).cloneNode(true),\n currentTrans = (el2.getAttribute('transform') || '') + ' translate(' + x + ', ' + y + ')',\n parentNode, oldLength = nodelist.length, attr, j, attrs, len, namespace = fabric.svgNS;\n\n applyViewboxTransform(el2);\n if (/^svg$/i.test(el2.nodeName)) {\n var el3 = el2.ownerDocument.createElementNS(namespace, 'g');\n for (j = 0, attrs = el2.attributes, len = attrs.length; j < len; j++) {\n attr = attrs.item(j);\n el3.setAttributeNS(namespace, attr.nodeName, attr.nodeValue);\n }\n // el2.firstChild != null\n while (el2.firstChild) {\n el3.appendChild(el2.firstChild);\n }\n el2 = el3;\n }\n\n for (j = 0, attrs = el.attributes, len = attrs.length; j < len; j++) {\n attr = attrs.item(j);\n if (attr.nodeName === 'x' || attr.nodeName === 'y' ||\n attr.nodeName === 'xlink:href' || attr.nodeName === 'href') {\n continue;\n }\n\n if (attr.nodeName === 'transform') {\n currentTrans = attr.nodeValue + ' ' + currentTrans;\n }\n else {\n el2.setAttribute(attr.nodeName, attr.nodeValue);\n }\n }\n\n el2.setAttribute('transform', currentTrans);\n el2.setAttribute('instantiated_by_use', '1');\n el2.removeAttribute('id');\n parentNode = el.parentNode;\n parentNode.replaceChild(el2, el);\n // some browsers do not shorten nodelist after replaceChild (IE8)\n if (nodelist.length === oldLength) {\n i++;\n }\n }\n }\n\n // http://www.w3.org/TR/SVG/coords.html#ViewBoxAttribute\n // matches, e.g.: +14.56e-12, etc.\n var reViewBoxAttrValue = new RegExp(\n '^' +\n '\\\\s*(' + fabric.reNum + '+)\\\\s*,?' +\n '\\\\s*(' + fabric.reNum + '+)\\\\s*,?' +\n '\\\\s*(' + fabric.reNum + '+)\\\\s*,?' +\n '\\\\s*(' + fabric.reNum + '+)\\\\s*' +\n '$'\n );\n\n /**\n * Add a element that envelop all child elements and makes the viewbox transformMatrix descend on all elements\n */\n function applyViewboxTransform(element) {\n\n var viewBoxAttr = element.getAttribute('viewBox'),\n scaleX = 1,\n scaleY = 1,\n minX = 0,\n minY = 0,\n viewBoxWidth, viewBoxHeight, matrix, el,\n widthAttr = element.getAttribute('width'),\n heightAttr = element.getAttribute('height'),\n x = element.getAttribute('x') || 0,\n y = element.getAttribute('y') || 0,\n preserveAspectRatio = element.getAttribute('preserveAspectRatio') || '',\n missingViewBox = (!viewBoxAttr || !fabric.svgViewBoxElementsRegEx.test(element.nodeName)\n || !(viewBoxAttr = viewBoxAttr.match(reViewBoxAttrValue))),\n missingDimAttr = (!widthAttr || !heightAttr || widthAttr === '100%' || heightAttr === '100%'),\n toBeParsed = missingViewBox && missingDimAttr,\n parsedDim = { }, translateMatrix = '', widthDiff = 0, heightDiff = 0;\n\n parsedDim.width = 0;\n parsedDim.height = 0;\n parsedDim.toBeParsed = toBeParsed;\n\n if (toBeParsed) {\n return parsedDim;\n }\n\n if (missingViewBox) {\n parsedDim.width = parseUnit(widthAttr);\n parsedDim.height = parseUnit(heightAttr);\n return parsedDim;\n }\n minX = -parseFloat(viewBoxAttr[1]);\n minY = -parseFloat(viewBoxAttr[2]);\n viewBoxWidth = parseFloat(viewBoxAttr[3]);\n viewBoxHeight = parseFloat(viewBoxAttr[4]);\n parsedDim.minX = minX;\n parsedDim.minY = minY;\n parsedDim.viewBoxWidth = viewBoxWidth;\n parsedDim.viewBoxHeight = viewBoxHeight;\n if (!missingDimAttr) {\n parsedDim.width = parseUnit(widthAttr);\n parsedDim.height = parseUnit(heightAttr);\n scaleX = parsedDim.width / viewBoxWidth;\n scaleY = parsedDim.height / viewBoxHeight;\n }\n else {\n parsedDim.width = viewBoxWidth;\n parsedDim.height = viewBoxHeight;\n }\n\n // default is to preserve aspect ratio\n preserveAspectRatio = fabric.util.parsePreserveAspectRatioAttribute(preserveAspectRatio);\n if (preserveAspectRatio.alignX !== 'none') {\n //translate all container for the effect of Mid, Min, Max\n if (preserveAspectRatio.meetOrSlice === 'meet') {\n scaleY = scaleX = (scaleX > scaleY ? scaleY : scaleX);\n // calculate additional translation to move the viewbox\n }\n if (preserveAspectRatio.meetOrSlice === 'slice') {\n scaleY = scaleX = (scaleX > scaleY ? scaleX : scaleY);\n // calculate additional translation to move the viewbox\n }\n widthDiff = parsedDim.width - viewBoxWidth * scaleX;\n heightDiff = parsedDim.height - viewBoxHeight * scaleX;\n if (preserveAspectRatio.alignX === 'Mid') {\n widthDiff /= 2;\n }\n if (preserveAspectRatio.alignY === 'Mid') {\n heightDiff /= 2;\n }\n if (preserveAspectRatio.alignX === 'Min') {\n widthDiff = 0;\n }\n if (preserveAspectRatio.alignY === 'Min') {\n heightDiff = 0;\n }\n }\n\n if (scaleX === 1 && scaleY === 1 && minX === 0 && minY === 0 && x === 0 && y === 0) {\n return parsedDim;\n }\n\n if (x || y) {\n translateMatrix = ' translate(' + parseUnit(x) + ' ' + parseUnit(y) + ') ';\n }\n\n matrix = translateMatrix + ' matrix(' + scaleX +\n ' 0' +\n ' 0 ' +\n scaleY + ' ' +\n (minX * scaleX + widthDiff) + ' ' +\n (minY * scaleY + heightDiff) + ') ';\n parsedDim.viewboxTransform = fabric.parseTransformAttribute(matrix);\n if (element.nodeName === 'svg') {\n el = element.ownerDocument.createElementNS(fabric.svgNS, 'g');\n // element.firstChild != null\n while (element.firstChild) {\n el.appendChild(element.firstChild);\n }\n element.appendChild(el);\n }\n else {\n el = element;\n matrix = el.getAttribute('transform') + matrix;\n }\n el.setAttribute('transform', matrix);\n return parsedDim;\n }\n\n function hasAncestorWithNodeName(element, nodeName) {\n while (element && (element = element.parentNode)) {\n if (element.nodeName && nodeName.test(element.nodeName.replace('svg:', ''))\n && !element.getAttribute('instantiated_by_use')) {\n return true;\n }\n }\n return false;\n }\n\n /**\n * Parses an SVG document, converts it to an array of corresponding fabric.* instances and passes them to a callback\n * @static\n * @function\n * @memberOf fabric\n * @param {SVGDocument} doc SVG document to parse\n * @param {Function} callback Callback to call when parsing is finished;\n * It's being passed an array of elements (parsed from a document).\n * @param {Function} [reviver] Method for further parsing of SVG elements, called after each fabric object created.\n * @param {Object} [parsingOptions] options for parsing document\n * @param {String} [parsingOptions.crossOrigin] crossOrigin settings\n */\n fabric.parseSVGDocument = function(doc, callback, reviver, parsingOptions) {\n if (!doc) {\n return;\n }\n\n parseUseDirectives(doc);\n\n var svgUid = fabric.Object.__uid++, i, len,\n options = applyViewboxTransform(doc),\n descendants = fabric.util.toArray(doc.getElementsByTagName('*'));\n options.crossOrigin = parsingOptions && parsingOptions.crossOrigin;\n options.svgUid = svgUid;\n\n if (descendants.length === 0 && fabric.isLikelyNode) {\n // we're likely in node, where \"o3-xml\" library fails to gEBTN(\"*\")\n // https://github.com/ajaxorg/node-o3-xml/issues/21\n descendants = doc.selectNodes('//*[name(.)!=\"svg\"]');\n var arr = [];\n for (i = 0, len = descendants.length; i < len; i++) {\n arr[i] = descendants[i];\n }\n descendants = arr;\n }\n\n var elements = descendants.filter(function(el) {\n applyViewboxTransform(el);\n return fabric.svgValidTagNamesRegEx.test(el.nodeName.replace('svg:', '')) &&\n !hasAncestorWithNodeName(el, fabric.svgInvalidAncestorsRegEx); // http://www.w3.org/TR/SVG/struct.html#DefsElement\n });\n\n if (!elements || (elements && !elements.length)) {\n callback && callback([], {});\n return;\n }\n var clipPaths = { };\n descendants.filter(function(el) {\n return el.nodeName.replace('svg:', '') === 'clipPath';\n }).forEach(function(el) {\n var id = el.getAttribute('id');\n clipPaths[id] = fabric.util.toArray(el.getElementsByTagName('*')).filter(function(el) {\n return fabric.svgValidTagNamesRegEx.test(el.nodeName.replace('svg:', ''));\n });\n });\n fabric.gradientDefs[svgUid] = fabric.getGradientDefs(doc);\n fabric.cssRules[svgUid] = fabric.getCSSRules(doc);\n fabric.clipPaths[svgUid] = clipPaths;\n // Precedence of rules: style > class > attribute\n fabric.parseElements(elements, function(instances, elements) {\n if (callback) {\n callback(instances, options, elements, descendants);\n delete fabric.gradientDefs[svgUid];\n delete fabric.cssRules[svgUid];\n delete fabric.clipPaths[svgUid];\n }\n }, clone(options), reviver, parsingOptions);\n };\n\n function recursivelyParseGradientsXlink(doc, gradient) {\n var gradientsAttrs = ['gradientTransform', 'x1', 'x2', 'y1', 'y2', 'gradientUnits', 'cx', 'cy', 'r', 'fx', 'fy'],\n xlinkAttr = 'xlink:href',\n xLink = gradient.getAttribute(xlinkAttr).substr(1),\n referencedGradient = elementById(doc, xLink);\n if (referencedGradient && referencedGradient.getAttribute(xlinkAttr)) {\n recursivelyParseGradientsXlink(doc, referencedGradient);\n }\n gradientsAttrs.forEach(function(attr) {\n if (referencedGradient && !gradient.hasAttribute(attr) && referencedGradient.hasAttribute(attr)) {\n gradient.setAttribute(attr, referencedGradient.getAttribute(attr));\n }\n });\n if (!gradient.children.length) {\n var referenceClone = referencedGradient.cloneNode(true);\n while (referenceClone.firstChild) {\n gradient.appendChild(referenceClone.firstChild);\n }\n }\n gradient.removeAttribute(xlinkAttr);\n }\n\n var reFontDeclaration = new RegExp(\n '(normal|italic)?\\\\s*(normal|small-caps)?\\\\s*' +\n '(normal|bold|bolder|lighter|100|200|300|400|500|600|700|800|900)?\\\\s*(' +\n fabric.reNum +\n '(?:px|cm|mm|em|pt|pc|in)*)(?:\\\\/(normal|' + fabric.reNum + '))?\\\\s+(.*)');\n\n extend(fabric, {\n /**\n * Parses a short font declaration, building adding its properties to a style object\n * @static\n * @function\n * @memberOf fabric\n * @param {String} value font declaration\n * @param {Object} oStyle definition\n */\n parseFontDeclaration: function(value, oStyle) {\n var match = value.match(reFontDeclaration);\n\n if (!match) {\n return;\n }\n var fontStyle = match[1],\n // font variant is not used\n // fontVariant = match[2],\n fontWeight = match[3],\n fontSize = match[4],\n lineHeight = match[5],\n fontFamily = match[6];\n\n if (fontStyle) {\n oStyle.fontStyle = fontStyle;\n }\n if (fontWeight) {\n oStyle.fontWeight = isNaN(parseFloat(fontWeight)) ? fontWeight : parseFloat(fontWeight);\n }\n if (fontSize) {\n oStyle.fontSize = parseUnit(fontSize);\n }\n if (fontFamily) {\n oStyle.fontFamily = fontFamily;\n }\n if (lineHeight) {\n oStyle.lineHeight = lineHeight === 'normal' ? 1 : lineHeight;\n }\n },\n\n /**\n * Parses an SVG document, returning all of the gradient declarations found in it\n * @static\n * @function\n * @memberOf fabric\n * @param {SVGDocument} doc SVG document to parse\n * @return {Object} Gradient definitions; key corresponds to element id, value -- to gradient definition element\n */\n getGradientDefs: function(doc) {\n var tagArray = [\n 'linearGradient',\n 'radialGradient',\n 'svg:linearGradient',\n 'svg:radialGradient'],\n elList = _getMultipleNodes(doc, tagArray),\n el, j = 0, gradientDefs = { };\n j = elList.length;\n while (j--) {\n el = elList[j];\n if (el.getAttribute('xlink:href')) {\n recursivelyParseGradientsXlink(doc, el);\n }\n gradientDefs[el.getAttribute('id')] = el;\n }\n return gradientDefs;\n },\n\n /**\n * Returns an object of attributes' name/value, given element and an array of attribute names;\n * Parses parent \"g\" nodes recursively upwards.\n * @static\n * @memberOf fabric\n * @param {DOMElement} element Element to parse\n * @param {Array} attributes Array of attributes to parse\n * @return {Object} object containing parsed attributes' names/values\n */\n parseAttributes: function(element, attributes, svgUid) {\n\n if (!element) {\n return;\n }\n\n var value,\n parentAttributes = { },\n fontSize, parentFontSize;\n\n if (typeof svgUid === 'undefined') {\n svgUid = element.getAttribute('svgUid');\n }\n // if there's a parent container (`g` or `a` or `symbol` node), parse its attributes recursively upwards\n if (element.parentNode && fabric.svgValidParentsRegEx.test(element.parentNode.nodeName)) {\n parentAttributes = fabric.parseAttributes(element.parentNode, attributes, svgUid);\n }\n\n var ownAttributes = attributes.reduce(function(memo, attr) {\n value = element.getAttribute(attr);\n if (value) { // eslint-disable-line\n memo[attr] = value;\n }\n return memo;\n }, { });\n // add values parsed from style, which take precedence over attributes\n // (see: http://www.w3.org/TR/SVG/styling.html#UsingPresentationAttributes)\n var cssAttrs = extend(\n getGlobalStylesForElement(element, svgUid),\n fabric.parseStyleAttribute(element)\n );\n ownAttributes = extend(\n ownAttributes,\n cssAttrs\n );\n if (cssAttrs[cPath]) {\n element.setAttribute(cPath, cssAttrs[cPath]);\n }\n fontSize = parentFontSize = parentAttributes.fontSize || fabric.Text.DEFAULT_SVG_FONT_SIZE;\n if (ownAttributes[fSize]) {\n // looks like the minimum should be 9px when dealing with ems. this is what looks like in browsers.\n ownAttributes[fSize] = fontSize = parseUnit(ownAttributes[fSize], parentFontSize);\n }\n\n var normalizedAttr, normalizedValue, normalizedStyle = {};\n for (var attr in ownAttributes) {\n normalizedAttr = normalizeAttr(attr);\n normalizedValue = normalizeValue(normalizedAttr, ownAttributes[attr], parentAttributes, fontSize);\n normalizedStyle[normalizedAttr] = normalizedValue;\n }\n if (normalizedStyle && normalizedStyle.font) {\n fabric.parseFontDeclaration(normalizedStyle.font, normalizedStyle);\n }\n var mergedAttrs = extend(parentAttributes, normalizedStyle);\n return fabric.svgValidParentsRegEx.test(element.nodeName) ? mergedAttrs : _setStrokeFillOpacity(mergedAttrs);\n },\n\n /**\n * Transforms an array of svg elements to corresponding fabric.* instances\n * @static\n * @memberOf fabric\n * @param {Array} elements Array of elements to parse\n * @param {Function} callback Being passed an array of fabric instances (transformed from SVG elements)\n * @param {Object} [options] Options object\n * @param {Function} [reviver] Method for further parsing of SVG elements, called after each fabric object created.\n */\n parseElements: function(elements, callback, options, reviver, parsingOptions) {\n new fabric.ElementsParser(elements, callback, options, reviver, parsingOptions).parse();\n },\n\n /**\n * Parses \"style\" attribute, retuning an object with values\n * @static\n * @memberOf fabric\n * @param {SVGElement} element Element to parse\n * @return {Object} Objects with values parsed from style attribute of an element\n */\n parseStyleAttribute: function(element) {\n var oStyle = { },\n style = element.getAttribute('style');\n\n if (!style) {\n return oStyle;\n }\n\n if (typeof style === 'string') {\n parseStyleString(style, oStyle);\n }\n else {\n parseStyleObject(style, oStyle);\n }\n\n return oStyle;\n },\n\n /**\n * Parses \"points\" attribute, returning an array of values\n * @static\n * @memberOf fabric\n * @param {String} points points attribute string\n * @return {Array} array of points\n */\n parsePointsAttribute: function(points) {\n\n // points attribute is required and must not be empty\n if (!points) {\n return null;\n }\n\n // replace commas with whitespace and remove bookending whitespace\n points = points.replace(/,/g, ' ').trim();\n\n points = points.split(/\\s+/);\n var parsedPoints = [], i, len;\n\n for (i = 0, len = points.length; i < len; i += 2) {\n parsedPoints.push({\n x: parseFloat(points[i]),\n y: parseFloat(points[i + 1])\n });\n }\n\n // odd number of points is an error\n // if (parsedPoints.length % 2 !== 0) {\n // return null;\n // }\n\n return parsedPoints;\n },\n\n /**\n * Returns CSS rules for a given SVG document\n * @static\n * @function\n * @memberOf fabric\n * @param {SVGDocument} doc SVG document to parse\n * @return {Object} CSS rules of this document\n */\n getCSSRules: function(doc) {\n var styles = doc.getElementsByTagName('style'), i, len,\n allRules = { }, rules;\n\n // very crude parsing of style contents\n for (i = 0, len = styles.length; i < len; i++) {\n // \\n'\n ].join('');\n }\n\n return markup;\n },\n\n /**\n * @private\n */\n _setSVGObjects: function(markup, reviver) {\n var instance, i, len, objects = this._objects;\n for (i = 0, len = objects.length; i < len; i++) {\n instance = objects[i];\n if (instance.excludeFromExport) {\n continue;\n }\n this._setSVGObject(markup, instance, reviver);\n }\n },\n\n /**\n * @private\n */\n _setSVGObject: function(markup, instance, reviver) {\n markup.push(instance.toSVG(reviver));\n },\n\n /**\n * @private\n */\n _setSVGBgOverlayImage: function(markup, property, reviver) {\n if (this[property] && !this[property].excludeFromExport && this[property].toSVG) {\n markup.push(this[property].toSVG(reviver));\n }\n },\n\n /**\n * @private\n */\n _setSVGBgOverlayColor: function(markup, property) {\n var filler = this[property + 'Color'], vpt = this.viewportTransform, finalWidth = this.width,\n finalHeight = this.height;\n if (!filler) {\n return;\n }\n if (filler.toLive) {\n var repeat = filler.repeat, iVpt = fabric.util.invertTransform(vpt), shouldInvert = this[property + 'Vpt'],\n additionalTransform = shouldInvert ? fabric.util.matrixToSVG(iVpt) : '';\n markup.push(\n '\\n'\n );\n }\n else {\n markup.push(\n '\\n'\n );\n }\n },\n /* _TO_SVG_END_ */\n\n /**\n * Moves an object or the objects of a multiple selection\n * to the bottom of the stack of drawn objects\n * @param {fabric.Object} object Object to send to back\n * @return {fabric.Canvas} thisArg\n * @chainable\n */\n sendToBack: function (object) {\n if (!object) {\n return this;\n }\n var activeSelection = this._activeObject,\n i, obj, objs;\n if (object === activeSelection && object.type === 'activeSelection') {\n objs = activeSelection._objects;\n for (i = objs.length; i--;) {\n obj = objs[i];\n removeFromArray(this._objects, obj);\n this._objects.unshift(obj);\n }\n }\n else {\n removeFromArray(this._objects, object);\n this._objects.unshift(object);\n }\n this.renderOnAddRemove && this.requestRenderAll();\n return this;\n },\n\n /**\n * Moves an object or the objects of a multiple selection\n * to the top of the stack of drawn objects\n * @param {fabric.Object} object Object to send\n * @return {fabric.Canvas} thisArg\n * @chainable\n */\n bringToFront: function (object) {\n if (!object) {\n return this;\n }\n var activeSelection = this._activeObject,\n i, obj, objs;\n if (object === activeSelection && object.type === 'activeSelection') {\n objs = activeSelection._objects;\n for (i = 0; i < objs.length; i++) {\n obj = objs[i];\n removeFromArray(this._objects, obj);\n this._objects.push(obj);\n }\n }\n else {\n removeFromArray(this._objects, object);\n this._objects.push(object);\n }\n this.renderOnAddRemove && this.requestRenderAll();\n return this;\n },\n\n /**\n * Moves an object or a selection down in stack of drawn objects\n * An optional paramter, intersecting allowes to move the object in behind\n * the first intersecting object. Where intersection is calculated with\n * bounding box. If no intersection is found, there will not be change in the\n * stack.\n * @param {fabric.Object} object Object to send\n * @param {Boolean} [intersecting] If `true`, send object behind next lower intersecting object\n * @return {fabric.Canvas} thisArg\n * @chainable\n */\n sendBackwards: function (object, intersecting) {\n if (!object) {\n return this;\n }\n var activeSelection = this._activeObject,\n i, obj, idx, newIdx, objs, objsMoved = 0;\n\n if (object === activeSelection && object.type === 'activeSelection') {\n objs = activeSelection._objects;\n for (i = 0; i < objs.length; i++) {\n obj = objs[i];\n idx = this._objects.indexOf(obj);\n if (idx > 0 + objsMoved) {\n newIdx = idx - 1;\n removeFromArray(this._objects, obj);\n this._objects.splice(newIdx, 0, obj);\n }\n objsMoved++;\n }\n }\n else {\n idx = this._objects.indexOf(object);\n if (idx !== 0) {\n // if object is not on the bottom of stack\n newIdx = this._findNewLowerIndex(object, idx, intersecting);\n removeFromArray(this._objects, object);\n this._objects.splice(newIdx, 0, object);\n }\n }\n this.renderOnAddRemove && this.requestRenderAll();\n return this;\n },\n\n /**\n * @private\n */\n _findNewLowerIndex: function(object, idx, intersecting) {\n var newIdx, i;\n\n if (intersecting) {\n newIdx = idx;\n\n // traverse down the stack looking for the nearest intersecting object\n for (i = idx - 1; i >= 0; --i) {\n\n var isIntersecting = object.intersectsWithObject(this._objects[i]) ||\n object.isContainedWithinObject(this._objects[i]) ||\n this._objects[i].isContainedWithinObject(object);\n\n if (isIntersecting) {\n newIdx = i;\n break;\n }\n }\n }\n else {\n newIdx = idx - 1;\n }\n\n return newIdx;\n },\n\n /**\n * Moves an object or a selection up in stack of drawn objects\n * An optional paramter, intersecting allowes to move the object in front\n * of the first intersecting object. Where intersection is calculated with\n * bounding box. If no intersection is found, there will not be change in the\n * stack.\n * @param {fabric.Object} object Object to send\n * @param {Boolean} [intersecting] If `true`, send object in front of next upper intersecting object\n * @return {fabric.Canvas} thisArg\n * @chainable\n */\n bringForward: function (object, intersecting) {\n if (!object) {\n return this;\n }\n var activeSelection = this._activeObject,\n i, obj, idx, newIdx, objs, objsMoved = 0;\n\n if (object === activeSelection && object.type === 'activeSelection') {\n objs = activeSelection._objects;\n for (i = objs.length; i--;) {\n obj = objs[i];\n idx = this._objects.indexOf(obj);\n if (idx < this._objects.length - 1 - objsMoved) {\n newIdx = idx + 1;\n removeFromArray(this._objects, obj);\n this._objects.splice(newIdx, 0, obj);\n }\n objsMoved++;\n }\n }\n else {\n idx = this._objects.indexOf(object);\n if (idx !== this._objects.length - 1) {\n // if object is not on top of stack (last item in an array)\n newIdx = this._findNewUpperIndex(object, idx, intersecting);\n removeFromArray(this._objects, object);\n this._objects.splice(newIdx, 0, object);\n }\n }\n this.renderOnAddRemove && this.requestRenderAll();\n return this;\n },\n\n /**\n * @private\n */\n _findNewUpperIndex: function(object, idx, intersecting) {\n var newIdx, i, len;\n\n if (intersecting) {\n newIdx = idx;\n\n // traverse up the stack looking for the nearest intersecting object\n for (i = idx + 1, len = this._objects.length; i < len; ++i) {\n\n var isIntersecting = object.intersectsWithObject(this._objects[i]) ||\n object.isContainedWithinObject(this._objects[i]) ||\n this._objects[i].isContainedWithinObject(object);\n\n if (isIntersecting) {\n newIdx = i;\n break;\n }\n }\n }\n else {\n newIdx = idx + 1;\n }\n\n return newIdx;\n },\n\n /**\n * Moves an object to specified level in stack of drawn objects\n * @param {fabric.Object} object Object to send\n * @param {Number} index Position to move to\n * @return {fabric.Canvas} thisArg\n * @chainable\n */\n moveTo: function (object, index) {\n removeFromArray(this._objects, object);\n this._objects.splice(index, 0, object);\n return this.renderOnAddRemove && this.requestRenderAll();\n },\n\n /**\n * Clears a canvas element and dispose objects\n * @return {fabric.Canvas} thisArg\n * @chainable\n */\n dispose: function () {\n // cancel eventually ongoing renders\n if (this.isRendering) {\n fabric.util.cancelAnimFrame(this.isRendering);\n this.isRendering = 0;\n }\n this.forEachObject(function(object) {\n object.dispose && object.dispose();\n });\n this._objects = [];\n if (this.backgroundImage && this.backgroundImage.dispose) {\n this.backgroundImage.dispose();\n }\n this.backgroundImage = null;\n if (this.overlayImage && this.overlayImage.dispose) {\n this.overlayImage.dispose();\n }\n this.overlayImage = null;\n this._iTextInstances = null;\n this.contextContainer = null;\n fabric.util.cleanUpJsdomNode(this.lowerCanvasEl);\n this.lowerCanvasEl = undefined;\n return this;\n },\n\n /**\n * Returns a string representation of an instance\n * @return {String} string representation of an instance\n */\n toString: function () {\n return '#';\n }\n });\n\n extend(fabric.StaticCanvas.prototype, fabric.Observable);\n extend(fabric.StaticCanvas.prototype, fabric.Collection);\n extend(fabric.StaticCanvas.prototype, fabric.DataURLExporter);\n\n extend(fabric.StaticCanvas, /** @lends fabric.StaticCanvas */ {\n\n /**\n * @static\n * @type String\n * @default\n */\n EMPTY_JSON: '{\"objects\": [], \"background\": \"white\"}',\n\n /**\n * Provides a way to check support of some of the canvas methods\n * (either those of HTMLCanvasElement itself, or rendering context)\n *\n * @param {String} methodName Method to check support for;\n * Could be one of \"setLineDash\"\n * @return {Boolean | null} `true` if method is supported (or at least exists),\n * `null` if canvas element or context can not be initialized\n */\n supports: function (methodName) {\n var el = createCanvasElement();\n\n if (!el || !el.getContext) {\n return null;\n }\n\n var ctx = el.getContext('2d');\n if (!ctx) {\n return null;\n }\n\n switch (methodName) {\n\n case 'setLineDash':\n return typeof ctx.setLineDash !== 'undefined';\n\n default:\n return null;\n }\n }\n });\n\n /**\n * Returns JSON representation of canvas\n * @function\n * @param {Array} [propertiesToInclude] Any properties that you might want to additionally include in the output\n * @return {String} JSON string\n * @tutorial {@link http://fabricjs.com/fabric-intro-part-3#serialization}\n * @see {@link http://jsfiddle.net/fabricjs/pec86/|jsFiddle demo}\n * @example JSON without additional properties\n * var json = canvas.toJSON();\n * @example JSON with additional properties included\n * var json = canvas.toJSON(['lockMovementX', 'lockMovementY', 'lockRotation', 'lockScalingX', 'lockScalingY', 'lockUniScaling']);\n * @example JSON without default values\n * canvas.includeDefaultValues = false;\n * var json = canvas.toJSON();\n */\n fabric.StaticCanvas.prototype.toJSON = fabric.StaticCanvas.prototype.toObject;\n\n if (fabric.isLikelyNode) {\n fabric.StaticCanvas.prototype.createPNGStream = function() {\n var impl = getNodeCanvas(this.lowerCanvasEl);\n return impl && impl.createPNGStream();\n };\n fabric.StaticCanvas.prototype.createJPEGStream = function(opts) {\n var impl = getNodeCanvas(this.lowerCanvasEl);\n return impl && impl.createJPEGStream(opts);\n };\n }\n})();\n\n\n/**\n * BaseBrush class\n * @class fabric.BaseBrush\n * @see {@link http://fabricjs.com/freedrawing|Freedrawing demo}\n */\nfabric.BaseBrush = fabric.util.createClass(/** @lends fabric.BaseBrush.prototype */ {\n\n /**\n * Color of a brush\n * @type String\n * @default\n */\n color: 'rgb(0, 0, 0)',\n\n /**\n * Width of a brush, has to be a Number, no string literals\n * @type Number\n * @default\n */\n width: 1,\n\n /**\n * Shadow object representing shadow of this shape.\n * Backwards incompatibility note: This property replaces \"shadowColor\" (String), \"shadowOffsetX\" (Number),\n * \"shadowOffsetY\" (Number) and \"shadowBlur\" (Number) since v1.2.12\n * @type fabric.Shadow\n * @default\n */\n shadow: null,\n\n /**\n * Line endings style of a brush (one of \"butt\", \"round\", \"square\")\n * @type String\n * @default\n */\n strokeLineCap: 'round',\n\n /**\n * Corner style of a brush (one of \"bevel\", \"round\", \"miter\")\n * @type String\n * @default\n */\n strokeLineJoin: 'round',\n\n /**\n * Maximum miter length (used for strokeLineJoin = \"miter\") of a brush's\n * @type Number\n * @default\n */\n strokeMiterLimit: 10,\n\n /**\n * Stroke Dash Array.\n * @type Array\n * @default\n */\n strokeDashArray: null,\n\n /**\n * Sets shadow of an object\n * @param {Object|String} [options] Options object or string (e.g. \"2px 2px 10px rgba(0,0,0,0.2)\")\n * @return {fabric.Object} thisArg\n * @chainable\n */\n setShadow: function(options) {\n this.shadow = new fabric.Shadow(options);\n return this;\n },\n\n /**\n * Sets brush styles\n * @private\n */\n _setBrushStyles: function() {\n var ctx = this.canvas.contextTop;\n ctx.strokeStyle = this.color;\n ctx.lineWidth = this.width;\n ctx.lineCap = this.strokeLineCap;\n ctx.miterLimit = this.strokeMiterLimit;\n ctx.lineJoin = this.strokeLineJoin;\n if (fabric.StaticCanvas.supports('setLineDash')) {\n ctx.setLineDash(this.strokeDashArray || []);\n }\n },\n\n /**\n * Sets the transformation on given context\n * @param {RenderingContext2d} ctx context to render on\n * @private\n */\n _saveAndTransform: function(ctx) {\n var v = this.canvas.viewportTransform;\n ctx.save();\n ctx.transform(v[0], v[1], v[2], v[3], v[4], v[5]);\n },\n\n /**\n * Sets brush shadow styles\n * @private\n */\n _setShadow: function() {\n if (!this.shadow) {\n return;\n }\n\n var canvas = this.canvas,\n shadow = this.shadow,\n ctx = canvas.contextTop,\n zoom = canvas.getZoom();\n if (canvas && canvas._isRetinaScaling()) {\n zoom *= fabric.devicePixelRatio;\n }\n\n ctx.shadowColor = shadow.color;\n ctx.shadowBlur = shadow.blur * zoom;\n ctx.shadowOffsetX = shadow.offsetX * zoom;\n ctx.shadowOffsetY = shadow.offsetY * zoom;\n },\n\n needsFullRender: function() {\n var color = new fabric.Color(this.color);\n return color.getAlpha() < 1 || !!this.shadow;\n },\n\n /**\n * Removes brush shadow styles\n * @private\n */\n _resetShadow: function() {\n var ctx = this.canvas.contextTop;\n\n ctx.shadowColor = '';\n ctx.shadowBlur = ctx.shadowOffsetX = ctx.shadowOffsetY = 0;\n }\n});\n\n\n(function() {\n /**\n * PencilBrush class\n * @class fabric.PencilBrush\n * @extends fabric.BaseBrush\n */\n fabric.PencilBrush = fabric.util.createClass(fabric.BaseBrush, /** @lends fabric.PencilBrush.prototype */ {\n\n /**\n * Discard points that are less than `decimate` pixel distant from each other\n * @type Number\n * @default 0.4\n */\n decimate: 0.4,\n\n /**\n * Constructor\n * @param {fabric.Canvas} canvas\n * @return {fabric.PencilBrush} Instance of a pencil brush\n */\n initialize: function(canvas) {\n this.canvas = canvas;\n this._points = [];\n },\n\n /**\n * Invoked inside on mouse down and mouse move\n * @param {Object} pointer\n */\n _drawSegment: function (ctx, p1, p2) {\n var midPoint = p1.midPointFrom(p2);\n ctx.quadraticCurveTo(p1.x, p1.y, midPoint.x, midPoint.y);\n return midPoint;\n },\n\n /**\n * Inovoked on mouse down\n * @param {Object} pointer\n */\n onMouseDown: function(pointer, options) {\n if (!this.canvas._isMainEvent(options.e)) {\n return;\n }\n this._prepareForDrawing(pointer);\n // capture coordinates immediately\n // this allows to draw dots (when movement never occurs)\n this._captureDrawingPath(pointer);\n this._render();\n },\n\n /**\n * Inovoked on mouse move\n * @param {Object} pointer\n */\n onMouseMove: function(pointer, options) {\n if (!this.canvas._isMainEvent(options.e)) {\n return;\n }\n if (this._captureDrawingPath(pointer) && this._points.length > 1) {\n if (this.needsFullRender()) {\n // redraw curve\n // clear top canvas\n this.canvas.clearContext(this.canvas.contextTop);\n this._render();\n }\n else {\n var points = this._points, length = points.length, ctx = this.canvas.contextTop;\n // draw the curve update\n this._saveAndTransform(ctx);\n if (this.oldEnd) {\n ctx.beginPath();\n ctx.moveTo(this.oldEnd.x, this.oldEnd.y);\n }\n this.oldEnd = this._drawSegment(ctx, points[length - 2], points[length - 1], true);\n ctx.stroke();\n ctx.restore();\n }\n }\n },\n\n /**\n * Invoked on mouse up\n */\n onMouseUp: function(options) {\n if (!this.canvas._isMainEvent(options.e)) {\n return true;\n }\n this.oldEnd = undefined;\n this._finalizeAndAddPath();\n return false;\n },\n\n /**\n * @private\n * @param {Object} pointer Actual mouse position related to the canvas.\n */\n _prepareForDrawing: function(pointer) {\n\n var p = new fabric.Point(pointer.x, pointer.y);\n\n this._reset();\n this._addPoint(p);\n this.canvas.contextTop.moveTo(p.x, p.y);\n },\n\n /**\n * @private\n * @param {fabric.Point} point Point to be added to points array\n */\n _addPoint: function(point) {\n if (this._points.length > 1 && point.eq(this._points[this._points.length - 1])) {\n return false;\n }\n this._points.push(point);\n return true;\n },\n\n /**\n * Clear points array and set contextTop canvas style.\n * @private\n */\n _reset: function() {\n this._points = [];\n this._setBrushStyles();\n this._setShadow();\n },\n\n /**\n * @private\n * @param {Object} pointer Actual mouse position related to the canvas.\n */\n _captureDrawingPath: function(pointer) {\n var pointerPoint = new fabric.Point(pointer.x, pointer.y);\n return this._addPoint(pointerPoint);\n },\n\n /**\n * Draw a smooth path on the topCanvas using quadraticCurveTo\n * @private\n */\n _render: function() {\n var ctx = this.canvas.contextTop, i, len,\n p1 = this._points[0],\n p2 = this._points[1];\n\n this._saveAndTransform(ctx);\n ctx.beginPath();\n //if we only have 2 points in the path and they are the same\n //it means that the user only clicked the canvas without moving the mouse\n //then we should be drawing a dot. A path isn't drawn between two identical dots\n //that's why we set them apart a bit\n if (this._points.length === 2 && p1.x === p2.x && p1.y === p2.y) {\n var width = this.width / 1000;\n p1 = new fabric.Point(p1.x, p1.y);\n p2 = new fabric.Point(p2.x, p2.y);\n p1.x -= width;\n p2.x += width;\n }\n ctx.moveTo(p1.x, p1.y);\n\n for (i = 1, len = this._points.length; i < len; i++) {\n // we pick the point between pi + 1 & pi + 2 as the\n // end point and p1 as our control point.\n this._drawSegment(ctx, p1, p2);\n p1 = this._points[i];\n p2 = this._points[i + 1];\n }\n // Draw last line as a straight line while\n // we wait for the next point to be able to calculate\n // the bezier control point\n ctx.lineTo(p1.x, p1.y);\n ctx.stroke();\n ctx.restore();\n },\n\n /**\n * Converts points to SVG path\n * @param {Array} points Array of points\n * @return {String} SVG path\n */\n convertPointsToSVGPath: function(points) {\n var path = [], i, width = this.width / 1000,\n p1 = new fabric.Point(points[0].x, points[0].y),\n p2 = new fabric.Point(points[1].x, points[1].y),\n len = points.length, multSignX = 1, multSignY = 0, manyPoints = len > 2;\n\n if (manyPoints) {\n multSignX = points[2].x < p2.x ? -1 : points[2].x === p2.x ? 0 : 1;\n multSignY = points[2].y < p2.y ? -1 : points[2].y === p2.y ? 0 : 1;\n }\n path.push('M ', p1.x - multSignX * width, ' ', p1.y - multSignY * width, ' ');\n for (i = 1; i < len; i++) {\n if (!p1.eq(p2)) {\n var midPoint = p1.midPointFrom(p2);\n // p1 is our bezier control point\n // midpoint is our endpoint\n // start point is p(i-1) value.\n path.push('Q ', p1.x, ' ', p1.y, ' ', midPoint.x, ' ', midPoint.y, ' ');\n }\n p1 = points[i];\n if ((i + 1) < points.length) {\n p2 = points[i + 1];\n }\n }\n if (manyPoints) {\n multSignX = p1.x > points[i - 2].x ? 1 : p1.x === points[i - 2].x ? 0 : -1;\n multSignY = p1.y > points[i - 2].y ? 1 : p1.y === points[i - 2].y ? 0 : -1;\n }\n path.push('L ', p1.x + multSignX * width, ' ', p1.y + multSignY * width);\n return path;\n },\n\n /**\n * Creates fabric.Path object to add on canvas\n * @param {String} pathData Path data\n * @return {fabric.Path} Path to add on canvas\n */\n createPath: function(pathData) {\n var path = new fabric.Path(pathData, {\n fill: null,\n stroke: this.color,\n strokeWidth: this.width,\n strokeLineCap: this.strokeLineCap,\n strokeMiterLimit: this.strokeMiterLimit,\n strokeLineJoin: this.strokeLineJoin,\n strokeDashArray: this.strokeDashArray,\n });\n if (this.shadow) {\n this.shadow.affectStroke = true;\n path.setShadow(this.shadow);\n }\n\n return path;\n },\n\n /**\n * Decimate poins array with the decimate value\n */\n decimatePoints: function(points, distance) {\n if (points.length <= 2) {\n return points;\n }\n var zoom = this.canvas.getZoom(), adjustedDistance = Math.pow(distance / zoom, 2),\n i, l = points.length - 1, lastPoint = points[0], newPoints = [lastPoint],\n cDistance;\n for (i = 1; i < l; i++) {\n cDistance = Math.pow(lastPoint.x - points[i].x, 2) + Math.pow(lastPoint.y - points[i].y, 2);\n if (cDistance >= adjustedDistance) {\n lastPoint = points[i];\n newPoints.push(lastPoint);\n }\n }\n if (newPoints.length === 1) {\n newPoints.push(new fabric.Point(newPoints[0].x, newPoints[0].y));\n }\n return newPoints;\n },\n\n /**\n * On mouseup after drawing the path on contextTop canvas\n * we use the points captured to create an new fabric path object\n * and add it to the fabric canvas.\n */\n _finalizeAndAddPath: function() {\n var ctx = this.canvas.contextTop;\n ctx.closePath();\n if (this.decimate) {\n this._points = this.decimatePoints(this._points, this.decimate);\n }\n var pathData = this.convertPointsToSVGPath(this._points).join('');\n if (pathData === 'M 0 0 Q 0 0 0 0 L 0 0') {\n // do not create 0 width/height paths, as they are\n // rendered inconsistently across browsers\n // Firefox 4, for example, renders a dot,\n // whereas Chrome 10 renders nothing\n this.canvas.requestRenderAll();\n return;\n }\n\n var path = this.createPath(pathData);\n this.canvas.clearContext(this.canvas.contextTop);\n this.canvas.add(path);\n this.canvas.requestRenderAll();\n path.setCoords();\n this._resetShadow();\n\n\n // fire event 'path' created\n this.canvas.fire('path:created', { path: path });\n }\n });\n})();\n\n\n/**\n * CircleBrush class\n * @class fabric.CircleBrush\n */\nfabric.CircleBrush = fabric.util.createClass(fabric.BaseBrush, /** @lends fabric.CircleBrush.prototype */ {\n\n /**\n * Width of a brush\n * @type Number\n * @default\n */\n width: 10,\n\n /**\n * Constructor\n * @param {fabric.Canvas} canvas\n * @return {fabric.CircleBrush} Instance of a circle brush\n */\n initialize: function(canvas) {\n this.canvas = canvas;\n this.points = [];\n },\n\n /**\n * Invoked inside on mouse down and mouse move\n * @param {Object} pointer\n */\n drawDot: function(pointer) {\n var point = this.addPoint(pointer),\n ctx = this.canvas.contextTop;\n this._saveAndTransform(ctx);\n this.dot(ctx, point);\n ctx.restore();\n },\n\n dot: function(ctx, point) {\n ctx.fillStyle = point.fill;\n ctx.beginPath();\n ctx.arc(point.x, point.y, point.radius, 0, Math.PI * 2, false);\n ctx.closePath();\n ctx.fill();\n },\n\n /**\n * Invoked on mouse down\n */\n onMouseDown: function(pointer) {\n this.points.length = 0;\n this.canvas.clearContext(this.canvas.contextTop);\n this._setShadow();\n this.drawDot(pointer);\n },\n\n /**\n * Render the full state of the brush\n * @private\n */\n _render: function() {\n var ctx = this.canvas.contextTop, i, len,\n points = this.points;\n this._saveAndTransform(ctx);\n for (i = 0, len = points.length; i < len; i++) {\n this.dot(ctx, points[i]);\n }\n ctx.restore();\n },\n\n /**\n * Invoked on mouse move\n * @param {Object} pointer\n */\n onMouseMove: function(pointer) {\n if (this.needsFullRender()) {\n this.canvas.clearContext(this.canvas.contextTop);\n this.addPoint(pointer);\n this._render();\n }\n else {\n this.drawDot(pointer);\n }\n },\n\n /**\n * Invoked on mouse up\n */\n onMouseUp: function() {\n var originalRenderOnAddRemove = this.canvas.renderOnAddRemove, i, len;\n this.canvas.renderOnAddRemove = false;\n\n var circles = [];\n\n for (i = 0, len = this.points.length; i < len; i++) {\n var point = this.points[i],\n circle = new fabric.Circle({\n radius: point.radius,\n left: point.x,\n top: point.y,\n originX: 'center',\n originY: 'center',\n fill: point.fill\n });\n\n this.shadow && circle.setShadow(this.shadow);\n\n circles.push(circle);\n }\n var group = new fabric.Group(circles);\n group.canvas = this.canvas;\n\n this.canvas.add(group);\n this.canvas.fire('path:created', { path: group });\n\n this.canvas.clearContext(this.canvas.contextTop);\n this._resetShadow();\n this.canvas.renderOnAddRemove = originalRenderOnAddRemove;\n this.canvas.requestRenderAll();\n },\n\n /**\n * @param {Object} pointer\n * @return {fabric.Point} Just added pointer point\n */\n addPoint: function(pointer) {\n var pointerPoint = new fabric.Point(pointer.x, pointer.y),\n\n circleRadius = fabric.util.getRandomInt(\n Math.max(0, this.width - 20), this.width + 20) / 2,\n\n circleColor = new fabric.Color(this.color)\n .setAlpha(fabric.util.getRandomInt(0, 100) / 100)\n .toRgba();\n\n pointerPoint.radius = circleRadius;\n pointerPoint.fill = circleColor;\n\n this.points.push(pointerPoint);\n\n return pointerPoint;\n }\n});\n\n\n/**\n * SprayBrush class\n * @class fabric.SprayBrush\n */\nfabric.SprayBrush = fabric.util.createClass( fabric.BaseBrush, /** @lends fabric.SprayBrush.prototype */ {\n\n /**\n * Width of a spray\n * @type Number\n * @default\n */\n width: 10,\n\n /**\n * Density of a spray (number of dots per chunk)\n * @type Number\n * @default\n */\n density: 20,\n\n /**\n * Width of spray dots\n * @type Number\n * @default\n */\n dotWidth: 1,\n\n /**\n * Width variance of spray dots\n * @type Number\n * @default\n */\n dotWidthVariance: 1,\n\n /**\n * Whether opacity of a dot should be random\n * @type Boolean\n * @default\n */\n randomOpacity: false,\n\n /**\n * Whether overlapping dots (rectangles) should be removed (for performance reasons)\n * @type Boolean\n * @default\n */\n optimizeOverlapping: true,\n\n /**\n * Constructor\n * @param {fabric.Canvas} canvas\n * @return {fabric.SprayBrush} Instance of a spray brush\n */\n initialize: function(canvas) {\n this.canvas = canvas;\n this.sprayChunks = [];\n },\n\n /**\n * Invoked on mouse down\n * @param {Object} pointer\n */\n onMouseDown: function(pointer) {\n this.sprayChunks.length = 0;\n this.canvas.clearContext(this.canvas.contextTop);\n this._setShadow();\n\n this.addSprayChunk(pointer);\n this.render(this.sprayChunkPoints);\n },\n\n /**\n * Invoked on mouse move\n * @param {Object} pointer\n */\n onMouseMove: function(pointer) {\n this.addSprayChunk(pointer);\n this.render(this.sprayChunkPoints);\n },\n\n /**\n * Invoked on mouse up\n */\n onMouseUp: function() {\n var originalRenderOnAddRemove = this.canvas.renderOnAddRemove;\n this.canvas.renderOnAddRemove = false;\n\n var rects = [];\n\n for (var i = 0, ilen = this.sprayChunks.length; i < ilen; i++) {\n var sprayChunk = this.sprayChunks[i];\n\n for (var j = 0, jlen = sprayChunk.length; j < jlen; j++) {\n\n var rect = new fabric.Rect({\n width: sprayChunk[j].width,\n height: sprayChunk[j].width,\n left: sprayChunk[j].x + 1,\n top: sprayChunk[j].y + 1,\n originX: 'center',\n originY: 'center',\n fill: this.color\n });\n rects.push(rect);\n }\n }\n\n if (this.optimizeOverlapping) {\n rects = this._getOptimizedRects(rects);\n }\n\n var group = new fabric.Group(rects);\n this.shadow && group.setShadow(this.shadow);\n this.canvas.add(group);\n this.canvas.fire('path:created', { path: group });\n\n this.canvas.clearContext(this.canvas.contextTop);\n this._resetShadow();\n this.canvas.renderOnAddRemove = originalRenderOnAddRemove;\n this.canvas.requestRenderAll();\n },\n\n /**\n * @private\n * @param {Array} rects\n */\n _getOptimizedRects: function(rects) {\n\n // avoid creating duplicate rects at the same coordinates\n var uniqueRects = { }, key, i, len;\n\n for (i = 0, len = rects.length; i < len; i++) {\n key = rects[i].left + '' + rects[i].top;\n if (!uniqueRects[key]) {\n uniqueRects[key] = rects[i];\n }\n }\n var uniqueRectsArray = [];\n for (key in uniqueRects) {\n uniqueRectsArray.push(uniqueRects[key]);\n }\n\n return uniqueRectsArray;\n },\n\n /**\n * Render new chunk of spray brush\n */\n render: function(sprayChunk) {\n var ctx = this.canvas.contextTop, i, len;\n ctx.fillStyle = this.color;\n\n this._saveAndTransform(ctx);\n\n for (i = 0, len = sprayChunk.length; i < len; i++) {\n var point = sprayChunk[i];\n if (typeof point.opacity !== 'undefined') {\n ctx.globalAlpha = point.opacity;\n }\n ctx.fillRect(point.x, point.y, point.width, point.width);\n }\n ctx.restore();\n },\n\n /**\n * Render all spray chunks\n */\n _render: function() {\n var ctx = this.canvas.contextTop, i, ilen;\n ctx.fillStyle = this.color;\n\n this._saveAndTransform(ctx);\n\n for (i = 0, ilen = this.sprayChunks.length; i < ilen; i++) {\n this.render(this.sprayChunks[i]);\n }\n ctx.restore();\n },\n\n /**\n * @param {Object} pointer\n */\n addSprayChunk: function(pointer) {\n this.sprayChunkPoints = [];\n\n var x, y, width, radius = this.width / 2, i;\n\n for (i = 0; i < this.density; i++) {\n\n x = fabric.util.getRandomInt(pointer.x - radius, pointer.x + radius);\n y = fabric.util.getRandomInt(pointer.y - radius, pointer.y + radius);\n\n if (this.dotWidthVariance) {\n width = fabric.util.getRandomInt(\n // bottom clamp width to 1\n Math.max(1, this.dotWidth - this.dotWidthVariance),\n this.dotWidth + this.dotWidthVariance);\n }\n else {\n width = this.dotWidth;\n }\n\n var point = new fabric.Point(x, y);\n point.width = width;\n\n if (this.randomOpacity) {\n point.opacity = fabric.util.getRandomInt(0, 100) / 100;\n }\n\n this.sprayChunkPoints.push(point);\n }\n\n this.sprayChunks.push(this.sprayChunkPoints);\n }\n});\n\n\n/**\n * PatternBrush class\n * @class fabric.PatternBrush\n * @extends fabric.BaseBrush\n */\nfabric.PatternBrush = fabric.util.createClass(fabric.PencilBrush, /** @lends fabric.PatternBrush.prototype */ {\n\n getPatternSrc: function() {\n\n var dotWidth = 20,\n dotDistance = 5,\n patternCanvas = fabric.util.createCanvasElement(),\n patternCtx = patternCanvas.getContext('2d');\n\n patternCanvas.width = patternCanvas.height = dotWidth + dotDistance;\n\n patternCtx.fillStyle = this.color;\n patternCtx.beginPath();\n patternCtx.arc(dotWidth / 2, dotWidth / 2, dotWidth / 2, 0, Math.PI * 2, false);\n patternCtx.closePath();\n patternCtx.fill();\n\n return patternCanvas;\n },\n\n getPatternSrcFunction: function() {\n return String(this.getPatternSrc).replace('this.color', '\"' + this.color + '\"');\n },\n\n /**\n * Creates \"pattern\" instance property\n */\n getPattern: function() {\n return this.canvas.contextTop.createPattern(this.source || this.getPatternSrc(), 'repeat');\n },\n\n /**\n * Sets brush styles\n */\n _setBrushStyles: function() {\n this.callSuper('_setBrushStyles');\n this.canvas.contextTop.strokeStyle = this.getPattern();\n },\n\n /**\n * Creates path\n */\n createPath: function(pathData) {\n var path = this.callSuper('createPath', pathData),\n topLeft = path._getLeftTopCoords().scalarAdd(path.strokeWidth / 2);\n\n path.stroke = new fabric.Pattern({\n source: this.source || this.getPatternSrcFunction(),\n offsetX: -topLeft.x,\n offsetY: -topLeft.y\n });\n return path;\n }\n});\n\n\n(function() {\n\n var getPointer = fabric.util.getPointer,\n degreesToRadians = fabric.util.degreesToRadians,\n radiansToDegrees = fabric.util.radiansToDegrees,\n atan2 = Math.atan2,\n abs = Math.abs,\n supportLineDash = fabric.StaticCanvas.supports('setLineDash'),\n\n STROKE_OFFSET = 0.5;\n\n /**\n * Canvas class\n * @class fabric.Canvas\n * @extends fabric.StaticCanvas\n * @tutorial {@link http://fabricjs.com/fabric-intro-part-1#canvas}\n * @see {@link fabric.Canvas#initialize} for constructor definition\n *\n * @fires object:modified at the end of a transform or any change when statefull is true\n * @fires object:rotated at the end of a rotation transform\n * @fires object:scaled at the end of a scale transform\n * @fires object:moved at the end of translation transform\n * @fires object:skewed at the end of a skew transform\n * @fires object:rotating while an object is being rotated from the control\n * @fires object:scaling while an object is being scaled by controls\n * @fires object:moving while an object is being dragged\n * @fires object:skewing while an object is being skewed from the controls\n * @fires object:selected this event is deprecated. use selection:created\n *\n * @fires before:transform before a transform is is started\n * @fires before:selection:cleared\n * @fires selection:cleared\n * @fires selection:updated\n * @fires selection:created\n *\n * @fires path:created after a drawing operation ends and the path is added\n * @fires mouse:down\n * @fires mouse:move\n * @fires mouse:up\n * @fires mouse:down:before on mouse down, before the inner fabric logic runs\n * @fires mouse:move:before on mouse move, before the inner fabric logic runs\n * @fires mouse:up:before on mouse up, before the inner fabric logic runs\n * @fires mouse:over\n * @fires mouse:out\n * @fires mouse:dblclick whenever a native dbl click event fires on the canvas.\n *\n * @fires dragover\n * @fires dragenter\n * @fires dragleave\n * @fires drop\n * @fires after:render at the end of the render process, receives the context in the callback\n * @fires before:render at start the render process, receives the context in the callback\n *\n */\n fabric.Canvas = fabric.util.createClass(fabric.StaticCanvas, /** @lends fabric.Canvas.prototype */ {\n\n /**\n * Constructor\n * @param {HTMLElement | String} el <canvas> element to initialize instance on\n * @param {Object} [options] Options object\n * @return {Object} thisArg\n */\n initialize: function(el, options) {\n options || (options = { });\n this.renderAndResetBound = this.renderAndReset.bind(this);\n this.requestRenderAllBound = this.requestRenderAll.bind(this);\n this._initStatic(el, options);\n this._initInteractive();\n this._createCacheCanvas();\n },\n\n /**\n * When true, objects can be transformed by one side (unproportionally)\n * @type Boolean\n * @default\n */\n uniScaleTransform: false,\n\n /**\n * Indicates which key enable unproportional scaling\n * values: 'altKey', 'shiftKey', 'ctrlKey'.\n * If `null` or 'none' or any other string that is not a modifier key\n * feature is disabled feature disabled.\n * @since 1.6.2\n * @type String\n * @default\n */\n uniScaleKey: 'shiftKey',\n\n /**\n * When true, objects use center point as the origin of scale transformation.\n * Backwards incompatibility note: This property replaces \"centerTransform\" (Boolean).\n * @since 1.3.4\n * @type Boolean\n * @default\n */\n centeredScaling: false,\n\n /**\n * When true, objects use center point as the origin of rotate transformation.\n * Backwards incompatibility note: This property replaces \"centerTransform\" (Boolean).\n * @since 1.3.4\n * @type Boolean\n * @default\n */\n centeredRotation: false,\n\n /**\n * Indicates which key enable centered Transform\n * values: 'altKey', 'shiftKey', 'ctrlKey'.\n * If `null` or 'none' or any other string that is not a modifier key\n * feature is disabled feature disabled.\n * @since 1.6.2\n * @type String\n * @default\n */\n centeredKey: 'altKey',\n\n /**\n * Indicates which key enable alternate action on corner\n * values: 'altKey', 'shiftKey', 'ctrlKey'.\n * If `null` or 'none' or any other string that is not a modifier key\n * feature is disabled feature disabled.\n * @since 1.6.2\n * @type String\n * @default\n */\n altActionKey: 'shiftKey',\n\n /**\n * Indicates that canvas is interactive. This property should not be changed.\n * @type Boolean\n * @default\n */\n interactive: true,\n\n /**\n * Indicates whether group selection should be enabled\n * @type Boolean\n * @default\n */\n selection: true,\n\n /**\n * Indicates which key or keys enable multiple click selection\n * Pass value as a string or array of strings\n * values: 'altKey', 'shiftKey', 'ctrlKey'.\n * If `null` or empty or containing any other string that is not a modifier key\n * feature is disabled.\n * @since 1.6.2\n * @type String|Array\n * @default\n */\n selectionKey: 'shiftKey',\n\n /**\n * Indicates which key enable alternative selection\n * in case of target overlapping with active object\n * values: 'altKey', 'shiftKey', 'ctrlKey'.\n * For a series of reason that come from the general expectations on how\n * things should work, this feature works only for preserveObjectStacking true.\n * If `null` or 'none' or any other string that is not a modifier key\n * feature is disabled.\n * @since 1.6.5\n * @type null|String\n * @default\n */\n altSelectionKey: null,\n\n /**\n * Color of selection\n * @type String\n * @default\n */\n selectionColor: 'rgba(100, 100, 255, 0.3)', // blue\n\n /**\n * Default dash array pattern\n * If not empty the selection border is dashed\n * @type Array\n */\n selectionDashArray: [],\n\n /**\n * Color of the border of selection (usually slightly darker than color of selection itself)\n * @type String\n * @default\n */\n selectionBorderColor: 'rgba(255, 255, 255, 0.3)',\n\n /**\n * Width of a line used in object/group selection\n * @type Number\n * @default\n */\n selectionLineWidth: 1,\n\n /**\n * Select only shapes that are fully contained in the dragged selection rectangle.\n * @type Boolean\n * @default\n */\n selectionFullyContained: false,\n\n /**\n * Default cursor value used when hovering over an object on canvas\n * @type String\n * @default\n */\n hoverCursor: 'move',\n\n /**\n * Default cursor value used when moving an object on canvas\n * @type String\n * @default\n */\n moveCursor: 'move',\n\n /**\n * Default cursor value used for the entire canvas\n * @type String\n * @default\n */\n defaultCursor: 'default',\n\n /**\n * Cursor value used during free drawing\n * @type String\n * @default\n */\n freeDrawingCursor: 'crosshair',\n\n /**\n * Cursor value used for rotation point\n * @type String\n * @default\n */\n rotationCursor: 'crosshair',\n\n /**\n * Cursor value used for disabled elements ( corners with disabled action )\n * @type String\n * @since 2.0.0\n * @default\n */\n notAllowedCursor: 'not-allowed',\n\n /**\n * Default element class that's given to wrapper (div) element of canvas\n * @type String\n * @default\n */\n containerClass: 'canvas-container',\n\n /**\n * When true, object detection happens on per-pixel basis rather than on per-bounding-box\n * @type Boolean\n * @default\n */\n perPixelTargetFind: false,\n\n /**\n * Number of pixels around target pixel to tolerate (consider active) during object detection\n * @type Number\n * @default\n */\n targetFindTolerance: 0,\n\n /**\n * When true, target detection is skipped when hovering over canvas. This can be used to improve performance.\n * @type Boolean\n * @default\n */\n skipTargetFind: false,\n\n /**\n * When true, mouse events on canvas (mousedown/mousemove/mouseup) result in free drawing.\n * After mousedown, mousemove creates a shape,\n * and then mouseup finalizes it and adds an instance of `fabric.Path` onto canvas.\n * @tutorial {@link http://fabricjs.com/fabric-intro-part-4#free_drawing}\n * @type Boolean\n * @default\n */\n isDrawingMode: false,\n\n /**\n * Indicates whether objects should remain in current stack position when selected.\n * When false objects are brought to top and rendered as part of the selection group\n * @type Boolean\n * @default\n */\n preserveObjectStacking: false,\n\n /**\n * Indicates the angle that an object will lock to while rotating.\n * @type Number\n * @since 1.6.7\n * @default\n */\n snapAngle: 0,\n\n /**\n * Indicates the distance from the snapAngle the rotation will lock to the snapAngle.\n * When `null`, the snapThreshold will default to the snapAngle.\n * @type null|Number\n * @since 1.6.7\n * @default\n */\n snapThreshold: null,\n\n /**\n * Indicates if the right click on canvas can output the context menu or not\n * @type Boolean\n * @since 1.6.5\n * @default\n */\n stopContextMenu: false,\n\n /**\n * Indicates if the canvas can fire right click events\n * @type Boolean\n * @since 1.6.5\n * @default\n */\n fireRightClick: false,\n\n /**\n * Indicates if the canvas can fire middle click events\n * @type Boolean\n * @since 1.7.8\n * @default\n */\n fireMiddleClick: false,\n\n /**\n * Keep track of the subTargets for Mouse Events\n * @type fabric.Object[]\n */\n targets: [],\n\n /**\n * Keep track of the hovered target\n * @type fabric.Object\n * @private\n */\n _hoveredTarget: null,\n\n /**\n * hold the list of nested targets hovered\n * @type fabric.Object[]\n * @private\n */\n _hoveredTargets: [],\n\n /**\n * @private\n */\n _initInteractive: function() {\n this._currentTransform = null;\n this._groupSelector = null;\n this._initWrapperElement();\n this._createUpperCanvas();\n this._initEventListeners();\n\n this._initRetinaScaling();\n\n this.freeDrawingBrush = fabric.PencilBrush && new fabric.PencilBrush(this);\n\n this.calcOffset();\n },\n\n /**\n * Divides objects in two groups, one to render immediately\n * and one to render as activeGroup.\n * @return {Array} objects to render immediately and pushes the other in the activeGroup.\n */\n _chooseObjectsToRender: function() {\n var activeObjects = this.getActiveObjects(),\n object, objsToRender, activeGroupObjects;\n\n if (activeObjects.length > 0 && !this.preserveObjectStacking) {\n objsToRender = [];\n activeGroupObjects = [];\n for (var i = 0, length = this._objects.length; i < length; i++) {\n object = this._objects[i];\n if (activeObjects.indexOf(object) === -1 ) {\n objsToRender.push(object);\n }\n else {\n activeGroupObjects.push(object);\n }\n }\n if (activeObjects.length > 1) {\n this._activeObject._objects = activeGroupObjects;\n }\n objsToRender.push.apply(objsToRender, activeGroupObjects);\n }\n else {\n objsToRender = this._objects;\n }\n return objsToRender;\n },\n\n /**\n * Renders both the top canvas and the secondary container canvas.\n * @return {fabric.Canvas} instance\n * @chainable\n */\n renderAll: function () {\n if (this.contextTopDirty && !this._groupSelector && !this.isDrawingMode) {\n this.clearContext(this.contextTop);\n this.contextTopDirty = false;\n }\n if (this.hasLostContext) {\n this.renderTopLayer(this.contextTop);\n }\n var canvasToDrawOn = this.contextContainer;\n this.renderCanvas(canvasToDrawOn, this._chooseObjectsToRender());\n return this;\n },\n\n renderTopLayer: function(ctx) {\n ctx.save();\n if (this.isDrawingMode && this._isCurrentlyDrawing) {\n this.freeDrawingBrush && this.freeDrawingBrush._render();\n this.contextTopDirty = true;\n }\n // we render the top context - last object\n if (this.selection && this._groupSelector) {\n this._drawSelection(ctx);\n this.contextTopDirty = true;\n }\n ctx.restore();\n },\n\n /**\n * Method to render only the top canvas.\n * Also used to render the group selection box.\n * @return {fabric.Canvas} thisArg\n * @chainable\n */\n renderTop: function () {\n var ctx = this.contextTop;\n this.clearContext(ctx);\n this.renderTopLayer(ctx);\n this.fire('after:render');\n return this;\n },\n\n /**\n * Resets the current transform to its original values and chooses the type of resizing based on the event\n * @private\n */\n _resetCurrentTransform: function() {\n var t = this._currentTransform;\n\n t.target.set({\n scaleX: t.original.scaleX,\n scaleY: t.original.scaleY,\n skewX: t.original.skewX,\n skewY: t.original.skewY,\n left: t.original.left,\n top: t.original.top\n });\n\n if (this._shouldCenterTransform(t.target)) {\n if (t.originX !== 'center') {\n if (t.originX === 'right') {\n t.mouseXSign = -1;\n }\n else {\n t.mouseXSign = 1;\n }\n }\n if (t.originY !== 'center') {\n if (t.originY === 'bottom') {\n t.mouseYSign = -1;\n }\n else {\n t.mouseYSign = 1;\n }\n }\n\n t.originX = 'center';\n t.originY = 'center';\n }\n else {\n t.originX = t.original.originX;\n t.originY = t.original.originY;\n }\n },\n\n /**\n * Checks if point is contained within an area of given object\n * @param {Event} e Event object\n * @param {fabric.Object} target Object to test against\n * @param {Object} [point] x,y object of point coordinates we want to check.\n * @return {Boolean} true if point is contained within an area of given object\n */\n containsPoint: function (e, target, point) {\n var ignoreZoom = true,\n pointer = point || this.getPointer(e, ignoreZoom),\n xy;\n\n if (target.group && target.group === this._activeObject && target.group.type === 'activeSelection') {\n xy = this._normalizePointer(target.group, pointer);\n }\n else {\n xy = { x: pointer.x, y: pointer.y };\n }\n // http://www.geog.ubc.ca/courses/klink/gis.notes/ncgia/u32.html\n // http://idav.ucdavis.edu/~okreylos/TAship/Spring2000/PointInPolygon.html\n return (target.containsPoint(xy) || target._findTargetCorner(pointer));\n },\n\n /**\n * @private\n */\n _normalizePointer: function (object, pointer) {\n var m = object.calcTransformMatrix(),\n invertedM = fabric.util.invertTransform(m),\n vptPointer = this.restorePointerVpt(pointer);\n return fabric.util.transformPoint(vptPointer, invertedM);\n },\n\n /**\n * Returns true if object is transparent at a certain location\n * @param {fabric.Object} target Object to check\n * @param {Number} x Left coordinate\n * @param {Number} y Top coordinate\n * @return {Boolean}\n */\n isTargetTransparent: function (target, x, y) {\n // in case the target is the activeObject, we cannot execute this optimization\n // because we need to draw controls too.\n if (target.shouldCache() && target._cacheCanvas && target !== this._activeObject) {\n var normalizedPointer = this._normalizePointer(target, {x: x, y: y}),\n targetRelativeX = Math.max(target.cacheTranslationX + (normalizedPointer.x * target.zoomX), 0),\n targetRelativeY = Math.max(target.cacheTranslationY + (normalizedPointer.y * target.zoomY), 0);\n\n var isTransparent = fabric.util.isTransparent(\n target._cacheContext, Math.round(targetRelativeX), Math.round(targetRelativeY), this.targetFindTolerance);\n\n return isTransparent;\n }\n\n var ctx = this.contextCache,\n originalColor = target.selectionBackgroundColor, v = this.viewportTransform;\n\n target.selectionBackgroundColor = '';\n\n this.clearContext(ctx);\n\n ctx.save();\n ctx.transform(v[0], v[1], v[2], v[3], v[4], v[5]);\n target.render(ctx);\n ctx.restore();\n\n target === this._activeObject && target._renderControls(ctx, {\n hasBorders: false,\n transparentCorners: false\n }, {\n hasBorders: false,\n });\n\n target.selectionBackgroundColor = originalColor;\n\n var isTransparent = fabric.util.isTransparent(\n ctx, x, y, this.targetFindTolerance);\n\n return isTransparent;\n },\n\n /**\n * takes an event and determins if selection key has been pressed\n * @private\n * @param {Event} e Event object\n */\n _isSelectionKeyPressed: function(e) {\n var selectionKeyPressed = false;\n\n if (Object.prototype.toString.call(this.selectionKey) === '[object Array]') {\n selectionKeyPressed = !!this.selectionKey.find(function(key) { return e[key] === true; });\n }\n else {\n selectionKeyPressed = e[this.selectionKey];\n }\n\n return selectionKeyPressed;\n },\n\n /**\n * @private\n * @param {Event} e Event object\n * @param {fabric.Object} target\n */\n _shouldClearSelection: function (e, target) {\n var activeObjects = this.getActiveObjects(),\n activeObject = this._activeObject;\n\n return (\n !target\n ||\n (target &&\n activeObject &&\n activeObjects.length > 1 &&\n activeObjects.indexOf(target) === -1 &&\n activeObject !== target &&\n !this._isSelectionKeyPressed(e))\n ||\n (target && !target.evented)\n ||\n (target &&\n !target.selectable &&\n activeObject &&\n activeObject !== target)\n );\n },\n\n /**\n * centeredScaling from object can't override centeredScaling from canvas.\n * this should be fixed, since object setting should take precedence over canvas.\n * @private\n * @param {fabric.Object} target\n */\n _shouldCenterTransform: function (target) {\n if (!target) {\n return;\n }\n\n var t = this._currentTransform,\n centerTransform;\n\n if (t.action === 'scale' || t.action === 'scaleX' || t.action === 'scaleY') {\n centerTransform = this.centeredScaling || target.centeredScaling;\n }\n else if (t.action === 'rotate') {\n centerTransform = this.centeredRotation || target.centeredRotation;\n }\n\n return centerTransform ? !t.altKey : t.altKey;\n },\n\n /**\n * @private\n */\n _getOriginFromCorner: function(target, corner) {\n var origin = {\n x: target.originX,\n y: target.originY\n };\n\n if (corner === 'ml' || corner === 'tl' || corner === 'bl') {\n origin.x = 'right';\n }\n else if (corner === 'mr' || corner === 'tr' || corner === 'br') {\n origin.x = 'left';\n }\n\n if (corner === 'tl' || corner === 'mt' || corner === 'tr') {\n origin.y = 'bottom';\n }\n else if (corner === 'bl' || corner === 'mb' || corner === 'br') {\n origin.y = 'top';\n }\n\n return origin;\n },\n\n /**\n * @private\n * @param {Boolean} alreadySelected true if target is already selected\n * @param {String} corner a string representing the corner ml, mr, tl ...\n * @param {Event} e Event object\n * @param {fabric.Object} [target] inserted back to help overriding. Unused\n */\n _getActionFromCorner: function(alreadySelected, corner, e /* target */) {\n if (!corner || !alreadySelected) {\n return 'drag';\n }\n\n switch (corner) {\n case 'mtr':\n return 'rotate';\n case 'ml':\n case 'mr':\n return e[this.altActionKey] ? 'skewY' : 'scaleX';\n case 'mt':\n case 'mb':\n return e[this.altActionKey] ? 'skewX' : 'scaleY';\n default:\n return 'scale';\n }\n },\n\n /**\n * @private\n * @param {Event} e Event object\n * @param {fabric.Object} target\n */\n _setupCurrentTransform: function (e, target, alreadySelected) {\n if (!target) {\n return;\n }\n\n var pointer = this.getPointer(e),\n corner = target._findTargetCorner(this.getPointer(e, true)),\n action = this._getActionFromCorner(alreadySelected, corner, e, target),\n origin = this._getOriginFromCorner(target, corner);\n\n this._currentTransform = {\n target: target,\n action: action,\n corner: corner,\n scaleX: target.scaleX,\n scaleY: target.scaleY,\n skewX: target.skewX,\n skewY: target.skewY,\n // used by transation\n offsetX: pointer.x - target.left,\n offsetY: pointer.y - target.top,\n originX: origin.x,\n originY: origin.y,\n ex: pointer.x,\n ey: pointer.y,\n lastX: pointer.x,\n lastY: pointer.y,\n // unsure they are usefull anymore.\n // left: target.left,\n // top: target.top,\n theta: degreesToRadians(target.angle),\n // end of unsure\n width: target.width * target.scaleX,\n mouseXSign: 1,\n mouseYSign: 1,\n shiftKey: e.shiftKey,\n altKey: e[this.centeredKey],\n original: fabric.util.saveObjectTransform(target),\n };\n\n this._currentTransform.original.originX = origin.x;\n this._currentTransform.original.originY = origin.y;\n\n this._resetCurrentTransform();\n this._beforeTransform(e);\n },\n\n /**\n * Translates object by \"setting\" its left/top\n * @private\n * @param {Number} x pointer's x coordinate\n * @param {Number} y pointer's y coordinate\n * @return {Boolean} true if the translation occurred\n */\n _translateObject: function (x, y) {\n var transform = this._currentTransform,\n target = transform.target,\n newLeft = x - transform.offsetX,\n newTop = y - transform.offsetY,\n moveX = !target.get('lockMovementX') && target.left !== newLeft,\n moveY = !target.get('lockMovementY') && target.top !== newTop;\n\n moveX && target.set('left', newLeft);\n moveY && target.set('top', newTop);\n return moveX || moveY;\n },\n\n /**\n * Check if we are increasing a positive skew or lower it,\n * checking mouse direction and pressed corner.\n * @private\n */\n _changeSkewTransformOrigin: function(mouseMove, t, by) {\n var property = 'originX', origins = { 0: 'center' },\n skew = t.target.skewX, originA = 'left', originB = 'right',\n corner = t.corner === 'mt' || t.corner === 'ml' ? 1 : -1,\n flipSign = 1;\n\n mouseMove = mouseMove > 0 ? 1 : -1;\n if (by === 'y') {\n skew = t.target.skewY;\n originA = 'top';\n originB = 'bottom';\n property = 'originY';\n }\n origins[-1] = originA;\n origins[1] = originB;\n\n t.target.flipX && (flipSign *= -1);\n t.target.flipY && (flipSign *= -1);\n\n if (skew === 0) {\n t.skewSign = -corner * mouseMove * flipSign;\n t[property] = origins[-mouseMove];\n }\n else {\n skew = skew > 0 ? 1 : -1;\n t.skewSign = skew;\n t[property] = origins[skew * corner * flipSign];\n }\n },\n\n /**\n * Skew object by mouse events\n * @private\n * @param {Number} x pointer's x coordinate\n * @param {Number} y pointer's y coordinate\n * @param {String} by Either 'x' or 'y'\n * @return {Boolean} true if the skewing occurred\n */\n _skewObject: function (x, y, by) {\n var t = this._currentTransform,\n target = t.target, skewed = false,\n lockSkewingX = target.get('lockSkewingX'),\n lockSkewingY = target.get('lockSkewingY');\n\n if ((lockSkewingX && by === 'x') || (lockSkewingY && by === 'y')) {\n return false;\n }\n\n // Get the constraint point\n var center = target.getCenterPoint(),\n actualMouseByCenter = target.toLocalPoint(new fabric.Point(x, y), 'center', 'center')[by],\n lastMouseByCenter = target.toLocalPoint(new fabric.Point(t.lastX, t.lastY), 'center', 'center')[by],\n actualMouseByOrigin, constraintPosition, dim = target._getTransformedDimensions();\n\n this._changeSkewTransformOrigin(actualMouseByCenter - lastMouseByCenter, t, by);\n actualMouseByOrigin = target.toLocalPoint(new fabric.Point(x, y), t.originX, t.originY)[by];\n constraintPosition = target.translateToOriginPoint(center, t.originX, t.originY);\n // Actually skew the object\n skewed = this._setObjectSkew(actualMouseByOrigin, t, by, dim);\n t.lastX = x;\n t.lastY = y;\n // Make sure the constraints apply\n target.setPositionByOrigin(constraintPosition, t.originX, t.originY);\n return skewed;\n },\n\n /**\n * Set object skew\n * @private\n * @return {Boolean} true if the skewing occurred\n */\n _setObjectSkew: function(localMouse, transform, by, _dim) {\n var target = transform.target, newValue, skewed = false,\n skewSign = transform.skewSign, newDim, dimNoSkew,\n otherBy, _otherBy, _by, newDimMouse, skewX, skewY;\n\n if (by === 'x') {\n otherBy = 'y';\n _otherBy = 'Y';\n _by = 'X';\n skewX = 0;\n skewY = target.skewY;\n }\n else {\n otherBy = 'x';\n _otherBy = 'X';\n _by = 'Y';\n skewX = target.skewX;\n skewY = 0;\n }\n\n dimNoSkew = target._getTransformedDimensions(skewX, skewY);\n newDimMouse = 2 * Math.abs(localMouse) - dimNoSkew[by];\n if (newDimMouse <= 2) {\n newValue = 0;\n }\n else {\n newValue = skewSign * Math.atan((newDimMouse / target['scale' + _by]) /\n (dimNoSkew[otherBy] / target['scale' + _otherBy]));\n newValue = fabric.util.radiansToDegrees(newValue);\n }\n skewed = target['skew' + _by] !== newValue;\n target.set('skew' + _by, newValue);\n if (target['skew' + _otherBy] !== 0) {\n newDim = target._getTransformedDimensions();\n newValue = (_dim[otherBy] / newDim[otherBy]) * target['scale' + _otherBy];\n target.set('scale' + _otherBy, newValue);\n }\n return skewed;\n },\n\n /**\n * Scales object by invoking its scaleX/scaleY methods\n * @private\n * @param {Number} x pointer's x coordinate\n * @param {Number} y pointer's y coordinate\n * @param {String} by Either 'x' or 'y' - specifies dimension constraint by which to scale an object.\n * When not provided, an object is scaled by both dimensions equally\n * @return {Boolean} true if the scaling occurred\n */\n _scaleObject: function (x, y, by) {\n var t = this._currentTransform,\n target = t.target,\n lockScalingX = target.lockScalingX,\n lockScalingY = target.lockScalingY,\n lockScalingFlip = target.lockScalingFlip;\n\n if (lockScalingX && lockScalingY) {\n return false;\n }\n\n // Get the constraint point\n var constraintPosition = target.translateToOriginPoint(target.getCenterPoint(), t.originX, t.originY),\n localMouse = target.toLocalPoint(new fabric.Point(x, y), t.originX, t.originY),\n dim = target._getTransformedDimensions(), scaled = false;\n\n this._setLocalMouse(localMouse, t);\n\n // Actually scale the object\n scaled = this._setObjectScale(localMouse, t, lockScalingX, lockScalingY, by, lockScalingFlip, dim);\n\n // Make sure the constraints apply\n target.setPositionByOrigin(constraintPosition, t.originX, t.originY);\n return scaled;\n },\n\n /**\n * @private\n * @return {Boolean} true if the scaling occurred\n */\n _setObjectScale: function(localMouse, transform, lockScalingX, lockScalingY, by, lockScalingFlip, _dim) {\n var target = transform.target, forbidScalingX = false, forbidScalingY = false, scaled = false,\n scaleX = localMouse.x * target.scaleX / _dim.x,\n scaleY = localMouse.y * target.scaleY / _dim.y,\n changeX = target.scaleX !== scaleX,\n changeY = target.scaleY !== scaleY;\n\n transform.newScaleX = scaleX;\n transform.newScaleY = scaleY;\n if (fabric.Textbox && by === 'x' && target instanceof fabric.Textbox) {\n var w = target.width * (localMouse.x / _dim.x);\n if (w >= target.getMinWidth()) {\n scaled = w !== target.width;\n target.set('width', w);\n return scaled;\n }\n return false;\n }\n\n if (lockScalingFlip && scaleX <= 0 && scaleX < target.scaleX) {\n forbidScalingX = true;\n localMouse.x = 0;\n }\n\n if (lockScalingFlip && scaleY <= 0 && scaleY < target.scaleY) {\n forbidScalingY = true;\n localMouse.y = 0;\n }\n\n if (by === 'equally' && !lockScalingX && !lockScalingY) {\n scaled = this._scaleObjectEqually(localMouse, target, transform, _dim);\n }\n else if (!by) {\n forbidScalingX || lockScalingX || (target.set('scaleX', scaleX) && (scaled = scaled || changeX));\n forbidScalingY || lockScalingY || (target.set('scaleY', scaleY) && (scaled = scaled || changeY));\n }\n else if (by === 'x' && !target.get('lockUniScaling')) {\n forbidScalingX || lockScalingX || (target.set('scaleX', scaleX) && (scaled = changeX));\n }\n else if (by === 'y' && !target.get('lockUniScaling')) {\n forbidScalingY || lockScalingY || (target.set('scaleY', scaleY) && (scaled = changeY));\n }\n forbidScalingX || forbidScalingY || this._flipObject(transform, by);\n return scaled;\n },\n\n /**\n * @private\n * @return {Boolean} true if the scaling occurred\n */\n _scaleObjectEqually: function(localMouse, target, transform, _dim) {\n\n var dist = localMouse.y + localMouse.x,\n lastDist = _dim.y * transform.original.scaleY / target.scaleY +\n _dim.x * transform.original.scaleX / target.scaleX,\n scaled, signX = localMouse.x < 0 ? -1 : 1,\n signY = localMouse.y < 0 ? -1 : 1, newScaleX, newScaleY;\n\n // We use transform.scaleX/Y instead of target.scaleX/Y\n // because the object may have a min scale and we'll loose the proportions\n newScaleX = signX * Math.abs(transform.original.scaleX * dist / lastDist);\n newScaleY = signY * Math.abs(transform.original.scaleY * dist / lastDist);\n scaled = newScaleX !== target.scaleX || newScaleY !== target.scaleY;\n target.set('scaleX', newScaleX);\n target.set('scaleY', newScaleY);\n return scaled;\n },\n\n /**\n * @private\n */\n _flipObject: function(transform, by) {\n if (transform.newScaleX < 0 && by !== 'y') {\n if (transform.originX === 'left') {\n transform.originX = 'right';\n }\n else if (transform.originX === 'right') {\n transform.originX = 'left';\n }\n }\n\n if (transform.newScaleY < 0 && by !== 'x') {\n if (transform.originY === 'top') {\n transform.originY = 'bottom';\n }\n else if (transform.originY === 'bottom') {\n transform.originY = 'top';\n }\n }\n },\n\n /**\n * @private\n */\n _setLocalMouse: function(localMouse, t) {\n var target = t.target, zoom = this.getZoom(),\n padding = target.padding / zoom;\n\n if (t.originX === 'right') {\n localMouse.x *= -1;\n }\n else if (t.originX === 'center') {\n localMouse.x *= t.mouseXSign * 2;\n if (localMouse.x < 0) {\n t.mouseXSign = -t.mouseXSign;\n }\n }\n\n if (t.originY === 'bottom') {\n localMouse.y *= -1;\n }\n else if (t.originY === 'center') {\n localMouse.y *= t.mouseYSign * 2;\n if (localMouse.y < 0) {\n t.mouseYSign = -t.mouseYSign;\n }\n }\n\n // adjust the mouse coordinates when dealing with padding\n if (abs(localMouse.x) > padding) {\n if (localMouse.x < 0) {\n localMouse.x += padding;\n }\n else {\n localMouse.x -= padding;\n }\n }\n else { // mouse is within the padding, set to 0\n localMouse.x = 0;\n }\n\n if (abs(localMouse.y) > padding) {\n if (localMouse.y < 0) {\n localMouse.y += padding;\n }\n else {\n localMouse.y -= padding;\n }\n }\n else {\n localMouse.y = 0;\n }\n },\n\n /**\n * Rotates object by invoking its rotate method\n * @private\n * @param {Number} x pointer's x coordinate\n * @param {Number} y pointer's y coordinate\n * @return {Boolean} true if the rotation occurred\n */\n _rotateObject: function (x, y) {\n\n var t = this._currentTransform,\n target = t.target, constraintPosition,\n constraintPosition = target.translateToOriginPoint(target.getCenterPoint(), t.originX, t.originY);\n\n if (target.lockRotation) {\n return false;\n }\n\n var lastAngle = atan2(t.ey - constraintPosition.y, t.ex - constraintPosition.x),\n curAngle = atan2(y - constraintPosition.y, x - constraintPosition.x),\n angle = radiansToDegrees(curAngle - lastAngle + t.theta),\n hasRotated = true;\n\n if (target.snapAngle > 0) {\n var snapAngle = target.snapAngle,\n snapThreshold = target.snapThreshold || snapAngle,\n rightAngleLocked = Math.ceil(angle / snapAngle) * snapAngle,\n leftAngleLocked = Math.floor(angle / snapAngle) * snapAngle;\n\n if (Math.abs(angle - leftAngleLocked) < snapThreshold) {\n angle = leftAngleLocked;\n }\n else if (Math.abs(angle - rightAngleLocked) < snapThreshold) {\n angle = rightAngleLocked;\n }\n }\n\n // normalize angle to positive value\n if (angle < 0) {\n angle = 360 + angle;\n }\n angle %= 360;\n\n if (target.angle === angle) {\n hasRotated = false;\n }\n else {\n // rotation only happen here\n target.angle = angle;\n // Make sure the constraints apply\n target.setPositionByOrigin(constraintPosition, t.originX, t.originY);\n }\n\n return hasRotated;\n },\n\n /**\n * Set the cursor type of the canvas element\n * @param {String} value Cursor type of the canvas element.\n * @see http://www.w3.org/TR/css3-ui/#cursor\n */\n setCursor: function (value) {\n this.upperCanvasEl.style.cursor = value;\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx to draw the selection on\n */\n _drawSelection: function (ctx) {\n var groupSelector = this._groupSelector,\n left = groupSelector.left,\n top = groupSelector.top,\n aleft = abs(left),\n atop = abs(top);\n\n if (this.selectionColor) {\n ctx.fillStyle = this.selectionColor;\n\n ctx.fillRect(\n groupSelector.ex - ((left > 0) ? 0 : -left),\n groupSelector.ey - ((top > 0) ? 0 : -top),\n aleft,\n atop\n );\n }\n\n if (!this.selectionLineWidth || !this.selectionBorderColor) {\n return;\n }\n ctx.lineWidth = this.selectionLineWidth;\n ctx.strokeStyle = this.selectionBorderColor;\n\n // selection border\n if (this.selectionDashArray.length > 1 && !supportLineDash) {\n\n var px = groupSelector.ex + STROKE_OFFSET - ((left > 0) ? 0 : aleft),\n py = groupSelector.ey + STROKE_OFFSET - ((top > 0) ? 0 : atop);\n\n ctx.beginPath();\n\n fabric.util.drawDashedLine(ctx, px, py, px + aleft, py, this.selectionDashArray);\n fabric.util.drawDashedLine(ctx, px, py + atop - 1, px + aleft, py + atop - 1, this.selectionDashArray);\n fabric.util.drawDashedLine(ctx, px, py, px, py + atop, this.selectionDashArray);\n fabric.util.drawDashedLine(ctx, px + aleft - 1, py, px + aleft - 1, py + atop, this.selectionDashArray);\n\n ctx.closePath();\n ctx.stroke();\n }\n else {\n fabric.Object.prototype._setLineDash.call(this, ctx, this.selectionDashArray);\n ctx.strokeRect(\n groupSelector.ex + STROKE_OFFSET - ((left > 0) ? 0 : aleft),\n groupSelector.ey + STROKE_OFFSET - ((top > 0) ? 0 : atop),\n aleft,\n atop\n );\n }\n },\n\n /**\n * Method that determines what object we are clicking on\n * the skipGroup parameter is for internal use, is needed for shift+click action\n * 11/09/2018 TODO: would be cool if findTarget could discern between being a full target\n * or the outside part of the corner.\n * @param {Event} e mouse event\n * @param {Boolean} skipGroup when true, activeGroup is skipped and only objects are traversed through\n * @return {fabric.Object} the target found\n */\n findTarget: function (e, skipGroup) {\n if (this.skipTargetFind) {\n return;\n }\n\n var ignoreZoom = true,\n pointer = this.getPointer(e, ignoreZoom),\n activeObject = this._activeObject,\n aObjects = this.getActiveObjects(),\n activeTarget, activeTargetSubs;\n\n // first check current group (if one exists)\n // active group does not check sub targets like normal groups.\n // if active group just exits.\n this.targets = [];\n\n if (aObjects.length > 1 && !skipGroup && activeObject === this._searchPossibleTargets([activeObject], pointer)) {\n return activeObject;\n }\n // if we hit the corner of an activeObject, let's return that.\n if (aObjects.length === 1 && activeObject._findTargetCorner(pointer)) {\n return activeObject;\n }\n if (aObjects.length === 1 &&\n activeObject === this._searchPossibleTargets([activeObject], pointer)) {\n if (!this.preserveObjectStacking) {\n return activeObject;\n }\n else {\n activeTarget = activeObject;\n activeTargetSubs = this.targets;\n this.targets = [];\n }\n }\n var target = this._searchPossibleTargets(this._objects, pointer);\n if (e[this.altSelectionKey] && target && activeTarget && target !== activeTarget) {\n target = activeTarget;\n this.targets = activeTargetSubs;\n }\n return target;\n },\n\n /**\n * Checks point is inside the object.\n * @param {Object} [pointer] x,y object of point coordinates we want to check.\n * @param {fabric.Object} obj Object to test against\n * @param {Object} [globalPointer] x,y object of point coordinates relative to canvas used to search per pixel target.\n * @return {Boolean} true if point is contained within an area of given object\n * @private\n */\n _checkTarget: function(pointer, obj, globalPointer) {\n if (obj &&\n obj.visible &&\n obj.evented &&\n this.containsPoint(null, obj, pointer)){\n if ((this.perPixelTargetFind || obj.perPixelTargetFind) && !obj.isEditing) {\n var isTransparent = this.isTargetTransparent(obj, globalPointer.x, globalPointer.y);\n if (!isTransparent) {\n return true;\n }\n }\n else {\n return true;\n }\n }\n },\n\n /**\n * Function used to search inside objects an object that contains pointer in bounding box or that contains pointerOnCanvas when painted\n * @param {Array} [objects] objects array to look into\n * @param {Object} [pointer] x,y object of point coordinates we want to check.\n * @return {fabric.Object} object that contains pointer\n * @private\n */\n _searchPossibleTargets: function(objects, pointer) {\n // Cache all targets where their bounding box contains point.\n var target, i = objects.length, subTarget;\n // Do not check for currently grouped objects, since we check the parent group itself.\n // until we call this function specifically to search inside the activeGroup\n while (i--) {\n var objToCheck = objects[i];\n var pointerToUse = objToCheck.group && objToCheck.group.type !== 'activeSelection' ?\n this._normalizePointer(objToCheck.group, pointer) : pointer;\n if (this._checkTarget(pointerToUse, objToCheck, pointer)) {\n target = objects[i];\n if (target.subTargetCheck && target instanceof fabric.Group) {\n subTarget = this._searchPossibleTargets(target._objects, pointer);\n subTarget && this.targets.push(subTarget);\n }\n break;\n }\n }\n return target;\n },\n\n /**\n * Returns pointer coordinates without the effect of the viewport\n * @param {Object} pointer with \"x\" and \"y\" number values\n * @return {Object} object with \"x\" and \"y\" number values\n */\n restorePointerVpt: function(pointer) {\n return fabric.util.transformPoint(\n pointer,\n fabric.util.invertTransform(this.viewportTransform)\n );\n },\n\n /**\n * Returns pointer coordinates relative to canvas.\n * Can return coordinates with or without viewportTransform.\n * ignoreZoom false gives back coordinates that represent\n * the point clicked on canvas element.\n * ignoreZoom true gives back coordinates after being processed\n * by the viewportTransform ( sort of coordinates of what is displayed\n * on the canvas where you are clicking.\n * ignoreZoom true = HTMLElement coordinates relative to top,left\n * ignoreZoom false, default = fabric space coordinates, the same used for shape position\n * To interact with your shapes top and left you want to use ignoreZoom true\n * most of the time, while ignoreZoom false will give you coordinates\n * compatible with the object.oCoords system.\n * of the time.\n * @param {Event} e\n * @param {Boolean} ignoreZoom\n * @return {Object} object with \"x\" and \"y\" number values\n */\n getPointer: function (e, ignoreZoom) {\n // return cached values if we are in the event processing chain\n if (this._absolutePointer && !ignoreZoom) {\n return this._absolutePointer;\n }\n if (this._pointer && ignoreZoom) {\n return this._pointer;\n }\n\n var pointer = getPointer(e),\n upperCanvasEl = this.upperCanvasEl,\n bounds = upperCanvasEl.getBoundingClientRect(),\n boundsWidth = bounds.width || 0,\n boundsHeight = bounds.height || 0,\n cssScale;\n\n if (!boundsWidth || !boundsHeight ) {\n if ('top' in bounds && 'bottom' in bounds) {\n boundsHeight = Math.abs( bounds.top - bounds.bottom );\n }\n if ('right' in bounds && 'left' in bounds) {\n boundsWidth = Math.abs( bounds.right - bounds.left );\n }\n }\n\n this.calcOffset();\n pointer.x = pointer.x - this._offset.left;\n pointer.y = pointer.y - this._offset.top;\n if (!ignoreZoom) {\n pointer = this.restorePointerVpt(pointer);\n }\n\n var retinaScaling = this.getRetinaScaling();\n if (retinaScaling !== 1) {\n pointer.x /= retinaScaling;\n pointer.y /= retinaScaling;\n }\n\n if (boundsWidth === 0 || boundsHeight === 0) {\n // If bounds are not available (i.e. not visible), do not apply scale.\n cssScale = { width: 1, height: 1 };\n }\n else {\n cssScale = {\n width: upperCanvasEl.width / boundsWidth,\n height: upperCanvasEl.height / boundsHeight\n };\n }\n\n return {\n x: pointer.x * cssScale.width,\n y: pointer.y * cssScale.height\n };\n },\n\n /**\n * @private\n * @throws {CANVAS_INIT_ERROR} If canvas can not be initialized\n */\n _createUpperCanvas: function () {\n var lowerCanvasClass = this.lowerCanvasEl.className.replace(/\\s*lower-canvas\\s*/, ''),\n lowerCanvasEl = this.lowerCanvasEl, upperCanvasEl = this.upperCanvasEl;\n\n // there is no need to create a new upperCanvas element if we have already one.\n if (upperCanvasEl) {\n upperCanvasEl.className = '';\n }\n else {\n upperCanvasEl = this._createCanvasElement();\n this.upperCanvasEl = upperCanvasEl;\n }\n fabric.util.addClass(upperCanvasEl, 'upper-canvas ' + lowerCanvasClass);\n\n this.wrapperEl.appendChild(upperCanvasEl);\n\n this._copyCanvasStyle(lowerCanvasEl, upperCanvasEl);\n this._applyCanvasStyle(upperCanvasEl);\n this.contextTop = upperCanvasEl.getContext('2d');\n },\n\n /**\n * @private\n */\n _createCacheCanvas: function () {\n this.cacheCanvasEl = this._createCanvasElement();\n this.cacheCanvasEl.setAttribute('width', this.width);\n this.cacheCanvasEl.setAttribute('height', this.height);\n this.contextCache = this.cacheCanvasEl.getContext('2d');\n },\n\n /**\n * @private\n */\n _initWrapperElement: function () {\n this.wrapperEl = fabric.util.wrapElement(this.lowerCanvasEl, 'div', {\n 'class': this.containerClass\n });\n fabric.util.setStyle(this.wrapperEl, {\n width: this.width + 'px',\n height: this.height + 'px',\n position: 'relative'\n });\n fabric.util.makeElementUnselectable(this.wrapperEl);\n },\n\n /**\n * @private\n * @param {HTMLElement} element canvas element to apply styles on\n */\n _applyCanvasStyle: function (element) {\n var width = this.width || element.width,\n height = this.height || element.height;\n\n fabric.util.setStyle(element, {\n position: 'absolute',\n width: width + 'px',\n height: height + 'px',\n left: 0,\n top: 0,\n 'touch-action': this.allowTouchScrolling ? 'manipulation' : 'none',\n '-ms-touch-action': this.allowTouchScrolling ? 'manipulation' : 'none'\n });\n element.width = width;\n element.height = height;\n fabric.util.makeElementUnselectable(element);\n },\n\n /**\n * Copy the entire inline style from one element (fromEl) to another (toEl)\n * @private\n * @param {Element} fromEl Element style is copied from\n * @param {Element} toEl Element copied style is applied to\n */\n _copyCanvasStyle: function (fromEl, toEl) {\n toEl.style.cssText = fromEl.style.cssText;\n },\n\n /**\n * Returns context of canvas where object selection is drawn\n * @return {CanvasRenderingContext2D}\n */\n getSelectionContext: function() {\n return this.contextTop;\n },\n\n /**\n * Returns <canvas> element on which object selection is drawn\n * @return {HTMLCanvasElement}\n */\n getSelectionElement: function () {\n return this.upperCanvasEl;\n },\n\n /**\n * Returns currently active object\n * @return {fabric.Object} active object\n */\n getActiveObject: function () {\n return this._activeObject;\n },\n\n /**\n * Returns an array with the current selected objects\n * @return {fabric.Object} active object\n */\n getActiveObjects: function () {\n var active = this._activeObject;\n if (active) {\n if (active.type === 'activeSelection' && active._objects) {\n return active._objects.slice(0);\n }\n else {\n return [active];\n }\n }\n return [];\n },\n\n /**\n * @private\n * @param {fabric.Object} obj Object that was removed\n */\n _onObjectRemoved: function(obj) {\n // removing active object should fire \"selection:cleared\" events\n if (obj === this._activeObject) {\n this.fire('before:selection:cleared', { target: obj });\n this._discardActiveObject();\n this.fire('selection:cleared', { target: obj });\n obj.fire('deselected');\n }\n if (obj === this._hoveredTarget){\n this._hoveredTarget = null;\n this._hoveredTargets = [];\n }\n this.callSuper('_onObjectRemoved', obj);\n },\n\n /**\n * @private\n * Compares the old activeObject with the current one and fires correct events\n * @param {fabric.Object} obj old activeObject\n */\n _fireSelectionEvents: function(oldObjects, e) {\n var somethingChanged = false, objects = this.getActiveObjects(),\n added = [], removed = [], opt = { e: e };\n oldObjects.forEach(function(oldObject) {\n if (objects.indexOf(oldObject) === -1) {\n somethingChanged = true;\n oldObject.fire('deselected', opt);\n removed.push(oldObject);\n }\n });\n objects.forEach(function(object) {\n if (oldObjects.indexOf(object) === -1) {\n somethingChanged = true;\n object.fire('selected', opt);\n added.push(object);\n }\n });\n if (oldObjects.length > 0 && objects.length > 0) {\n opt.selected = added;\n opt.deselected = removed;\n // added for backward compatibility\n opt.updated = added[0] || removed[0];\n opt.target = this._activeObject;\n somethingChanged && this.fire('selection:updated', opt);\n }\n else if (objects.length > 0) {\n // deprecated event\n if (objects.length === 1) {\n opt.target = added[0];\n this.fire('object:selected', opt);\n }\n opt.selected = added;\n // added for backward compatibility\n opt.target = this._activeObject;\n this.fire('selection:created', opt);\n }\n else if (oldObjects.length > 0) {\n opt.deselected = removed;\n this.fire('selection:cleared', opt);\n }\n },\n\n /**\n * Sets given object as the only active object on canvas\n * @param {fabric.Object} object Object to set as an active one\n * @param {Event} [e] Event (passed along when firing \"object:selected\")\n * @return {fabric.Canvas} thisArg\n * @chainable\n */\n setActiveObject: function (object, e) {\n var currentActives = this.getActiveObjects();\n this._setActiveObject(object, e);\n this._fireSelectionEvents(currentActives, e);\n return this;\n },\n\n /**\n * @private\n * @param {Object} object to set as active\n * @param {Event} [e] Event (passed along when firing \"object:selected\")\n * @return {Boolean} true if the selection happened\n */\n _setActiveObject: function(object, e) {\n if (this._activeObject === object) {\n return false;\n }\n if (!this._discardActiveObject(e, object)) {\n return false;\n }\n if (object.onSelect({ e: e })) {\n return false;\n }\n this._activeObject = object;\n return true;\n },\n\n /**\n * @private\n */\n _discardActiveObject: function(e, object) {\n var obj = this._activeObject;\n if (obj) {\n // onDeselect return TRUE to cancel selection;\n if (obj.onDeselect({ e: e, object: object })) {\n return false;\n }\n this._activeObject = null;\n }\n return true;\n },\n\n /**\n * Discards currently active object and fire events. If the function is called by fabric\n * as a consequence of a mouse event, the event is passed as a parameter and\n * sent to the fire function for the custom events. When used as a method the\n * e param does not have any application.\n * @param {event} e\n * @return {fabric.Canvas} thisArg\n * @chainable\n */\n discardActiveObject: function (e) {\n var currentActives = this.getActiveObjects(), activeObject = this.getActiveObject();\n if (currentActives.length) {\n this.fire('before:selection:cleared', { target: activeObject, e: e });\n }\n this._discardActiveObject(e);\n this._fireSelectionEvents(currentActives, e);\n return this;\n },\n\n /**\n * Clears a canvas element and removes all event listeners\n * @return {fabric.Canvas} thisArg\n * @chainable\n */\n dispose: function () {\n var wrapper = this.wrapperEl;\n this.removeListeners();\n wrapper.removeChild(this.upperCanvasEl);\n wrapper.removeChild(this.lowerCanvasEl);\n this.contextCache = null;\n this.contextTop = null;\n ['upperCanvasEl', 'cacheCanvasEl'].forEach((function(element) {\n fabric.util.cleanUpJsdomNode(this[element]);\n this[element] = undefined;\n }).bind(this));\n if (wrapper.parentNode) {\n wrapper.parentNode.replaceChild(this.lowerCanvasEl, this.wrapperEl);\n }\n delete this.wrapperEl;\n fabric.StaticCanvas.prototype.dispose.call(this);\n return this;\n },\n\n /**\n * Clears all contexts (background, main, top) of an instance\n * @return {fabric.Canvas} thisArg\n * @chainable\n */\n clear: function () {\n // this.discardActiveGroup();\n this.discardActiveObject();\n this.clearContext(this.contextTop);\n return this.callSuper('clear');\n },\n\n /**\n * Draws objects' controls (borders/controls)\n * @param {CanvasRenderingContext2D} ctx Context to render controls on\n */\n drawControls: function(ctx) {\n var activeObject = this._activeObject;\n\n if (activeObject) {\n activeObject._renderControls(ctx);\n }\n },\n\n /**\n * @private\n */\n _toObject: function(instance, methodName, propertiesToInclude) {\n //If the object is part of the current selection group, it should\n //be transformed appropriately\n //i.e. it should be serialised as it would appear if the selection group\n //were to be destroyed.\n var originalProperties = this._realizeGroupTransformOnObject(instance),\n object = this.callSuper('_toObject', instance, methodName, propertiesToInclude);\n //Undo the damage we did by changing all of its properties\n this._unwindGroupTransformOnObject(instance, originalProperties);\n return object;\n },\n\n /**\n * Realises an object's group transformation on it\n * @private\n * @param {fabric.Object} [instance] the object to transform (gets mutated)\n * @returns the original values of instance which were changed\n */\n _realizeGroupTransformOnObject: function(instance) {\n if (instance.group && instance.group.type === 'activeSelection' && this._activeObject === instance.group) {\n var layoutProps = ['angle', 'flipX', 'flipY', 'left', 'scaleX', 'scaleY', 'skewX', 'skewY', 'top'];\n //Copy all the positionally relevant properties across now\n var originalValues = {};\n layoutProps.forEach(function(prop) {\n originalValues[prop] = instance[prop];\n });\n this._activeObject.realizeTransform(instance);\n return originalValues;\n }\n else {\n return null;\n }\n },\n\n /**\n * Restores the changed properties of instance\n * @private\n * @param {fabric.Object} [instance] the object to un-transform (gets mutated)\n * @param {Object} [originalValues] the original values of instance, as returned by _realizeGroupTransformOnObject\n */\n _unwindGroupTransformOnObject: function(instance, originalValues) {\n if (originalValues) {\n instance.set(originalValues);\n }\n },\n\n /**\n * @private\n */\n _setSVGObject: function(markup, instance, reviver) {\n //If the object is in a selection group, simulate what would happen to that\n //object when the group is deselected\n var originalProperties = this._realizeGroupTransformOnObject(instance);\n this.callSuper('_setSVGObject', markup, instance, reviver);\n this._unwindGroupTransformOnObject(instance, originalProperties);\n },\n\n setViewportTransform: function (vpt) {\n if (this.renderOnAddRemove && this._activeObject && this._activeObject.isEditing) {\n this._activeObject.clearContextTop();\n }\n fabric.StaticCanvas.prototype.setViewportTransform.call(this, vpt);\n }\n });\n\n // copying static properties manually to work around Opera's bug,\n // where \"prototype\" property is enumerable and overrides existing prototype\n for (var prop in fabric.StaticCanvas) {\n if (prop !== 'prototype') {\n fabric.Canvas[prop] = fabric.StaticCanvas[prop];\n }\n }\n})();\n\n\n(function() {\n\n var cursorOffset = {\n mt: 0, // n\n tr: 1, // ne\n mr: 2, // e\n br: 3, // se\n mb: 4, // s\n bl: 5, // sw\n ml: 6, // w\n tl: 7 // nw\n },\n addListener = fabric.util.addListener,\n removeListener = fabric.util.removeListener,\n RIGHT_CLICK = 3, MIDDLE_CLICK = 2, LEFT_CLICK = 1,\n addEventOptions = { passive: false };\n\n function checkClick(e, value) {\n return e.button && (e.button === value - 1);\n }\n\n fabric.util.object.extend(fabric.Canvas.prototype, /** @lends fabric.Canvas.prototype */ {\n\n /**\n * Map of cursor style values for each of the object controls\n * @private\n */\n cursorMap: [\n 'n-resize',\n 'ne-resize',\n 'e-resize',\n 'se-resize',\n 's-resize',\n 'sw-resize',\n 'w-resize',\n 'nw-resize'\n ],\n\n /**\n * Contains the id of the touch event that owns the fabric transform\n * @type Number\n * @private\n */\n mainTouchId: null,\n\n /**\n * Adds mouse listeners to canvas\n * @private\n */\n _initEventListeners: function () {\n // in case we initialized the class twice. This should not happen normally\n // but in some kind of applications where the canvas element may be changed\n // this is a workaround to having double listeners.\n this.removeListeners();\n this._bindEvents();\n this.addOrRemove(addListener, 'add');\n },\n\n /**\n * return an event prefix pointer or mouse.\n * @private\n */\n _getEventPrefix: function () {\n return this.enablePointerEvents ? 'pointer' : 'mouse';\n },\n\n addOrRemove: function(functor, eventjsFunctor) {\n var canvasElement = this.upperCanvasEl,\n eventTypePrefix = this._getEventPrefix();\n functor(fabric.window, 'resize', this._onResize);\n functor(canvasElement, eventTypePrefix + 'down', this._onMouseDown);\n functor(canvasElement, eventTypePrefix + 'move', this._onMouseMove, addEventOptions);\n functor(canvasElement, eventTypePrefix + 'out', this._onMouseOut);\n functor(canvasElement, eventTypePrefix + 'enter', this._onMouseEnter);\n functor(canvasElement, 'wheel', this._onMouseWheel);\n functor(canvasElement, 'contextmenu', this._onContextMenu);\n functor(canvasElement, 'dblclick', this._onDoubleClick);\n functor(canvasElement, 'dragover', this._onDragOver);\n functor(canvasElement, 'dragenter', this._onDragEnter);\n functor(canvasElement, 'dragleave', this._onDragLeave);\n functor(canvasElement, 'drop', this._onDrop);\n if (!this.enablePointerEvents) {\n functor(canvasElement, 'touchstart', this._onTouchStart, addEventOptions);\n }\n if (typeof eventjs !== 'undefined' && eventjsFunctor in eventjs) {\n eventjs[eventjsFunctor](canvasElement, 'gesture', this._onGesture);\n eventjs[eventjsFunctor](canvasElement, 'drag', this._onDrag);\n eventjs[eventjsFunctor](canvasElement, 'orientation', this._onOrientationChange);\n eventjs[eventjsFunctor](canvasElement, 'shake', this._onShake);\n eventjs[eventjsFunctor](canvasElement, 'longpress', this._onLongPress);\n }\n },\n\n /**\n * Removes all event listeners\n */\n removeListeners: function() {\n this.addOrRemove(removeListener, 'remove');\n // if you dispose on a mouseDown, before mouse up, you need to clean document to...\n var eventTypePrefix = this._getEventPrefix();\n removeListener(fabric.document, eventTypePrefix + 'up', this._onMouseUp);\n removeListener(fabric.document, 'touchend', this._onTouchEnd, addEventOptions);\n removeListener(fabric.document, eventTypePrefix + 'move', this._onMouseMove, addEventOptions);\n removeListener(fabric.document, 'touchmove', this._onMouseMove, addEventOptions);\n },\n\n /**\n * @private\n */\n _bindEvents: function() {\n if (this.eventsBound) {\n // for any reason we pass here twice we do not want to bind events twice.\n return;\n }\n this._onMouseDown = this._onMouseDown.bind(this);\n this._onTouchStart = this._onTouchStart.bind(this);\n this._onMouseMove = this._onMouseMove.bind(this);\n this._onMouseUp = this._onMouseUp.bind(this);\n this._onTouchEnd = this._onTouchEnd.bind(this);\n this._onResize = this._onResize.bind(this);\n this._onGesture = this._onGesture.bind(this);\n this._onDrag = this._onDrag.bind(this);\n this._onShake = this._onShake.bind(this);\n this._onLongPress = this._onLongPress.bind(this);\n this._onOrientationChange = this._onOrientationChange.bind(this);\n this._onMouseWheel = this._onMouseWheel.bind(this);\n this._onMouseOut = this._onMouseOut.bind(this);\n this._onMouseEnter = this._onMouseEnter.bind(this);\n this._onContextMenu = this._onContextMenu.bind(this);\n this._onDoubleClick = this._onDoubleClick.bind(this);\n this._onDragOver = this._onDragOver.bind(this);\n this._onDragEnter = this._simpleEventHandler.bind(this, 'dragenter');\n this._onDragLeave = this._simpleEventHandler.bind(this, 'dragleave');\n this._onDrop = this._simpleEventHandler.bind(this, 'drop');\n this.eventsBound = true;\n },\n\n /**\n * @private\n * @param {Event} [e] Event object fired on Event.js gesture\n * @param {Event} [self] Inner Event object\n */\n _onGesture: function(e, self) {\n this.__onTransformGesture && this.__onTransformGesture(e, self);\n },\n\n /**\n * @private\n * @param {Event} [e] Event object fired on Event.js drag\n * @param {Event} [self] Inner Event object\n */\n _onDrag: function(e, self) {\n this.__onDrag && this.__onDrag(e, self);\n },\n\n /**\n * @private\n * @param {Event} [e] Event object fired on wheel event\n */\n _onMouseWheel: function(e) {\n this.__onMouseWheel(e);\n },\n\n /**\n * @private\n * @param {Event} e Event object fired on mousedown\n */\n _onMouseOut: function(e) {\n var target = this._hoveredTarget;\n this.fire('mouse:out', { target: target, e: e });\n this._hoveredTarget = null;\n target && target.fire('mouseout', { e: e });\n\n var _this = this;\n this._hoveredTargets.forEach(function(_target){\n _this.fire('mouse:out', { target: target, e: e });\n _target && target.fire('mouseout', { e: e });\n });\n this._hoveredTargets = [];\n\n if (this._iTextInstances) {\n this._iTextInstances.forEach(function(obj) {\n if (obj.isEditing) {\n obj.hiddenTextarea.focus();\n }\n });\n }\n },\n\n /**\n * @private\n * @param {Event} e Event object fired on mouseenter\n */\n _onMouseEnter: function(e) {\n // This find target and consequent 'mouse:over' is used to\n // clear old instances on hovered target.\n // calling findTarget has the side effect of killing target.__corner.\n // as a short term fix we are not firing this if we are currently transforming.\n // as a long term fix we need to separate the action of finding a target with the\n // side effects we added to it.\n if (!this.currentTransform && !this.findTarget(e)) {\n this.fire('mouse:over', { target: null, e: e });\n this._hoveredTarget = null;\n this._hoveredTargets = [];\n }\n },\n\n /**\n * @private\n * @param {Event} [e] Event object fired on Event.js orientation change\n * @param {Event} [self] Inner Event object\n */\n _onOrientationChange: function(e, self) {\n this.__onOrientationChange && this.__onOrientationChange(e, self);\n },\n\n /**\n * @private\n * @param {Event} [e] Event object fired on Event.js shake\n * @param {Event} [self] Inner Event object\n */\n _onShake: function(e, self) {\n this.__onShake && this.__onShake(e, self);\n },\n\n /**\n * @private\n * @param {Event} [e] Event object fired on Event.js shake\n * @param {Event} [self] Inner Event object\n */\n _onLongPress: function(e, self) {\n this.__onLongPress && this.__onLongPress(e, self);\n },\n\n /**\n * prevent default to allow drop event to be fired\n * @private\n * @param {Event} [e] Event object fired on Event.js shake\n */\n _onDragOver: function(e) {\n e.preventDefault();\n var target = this._simpleEventHandler('dragover', e);\n this._fireEnterLeaveEvents(target, e);\n },\n\n /**\n * @private\n * @param {Event} e Event object fired on mousedown\n */\n _onContextMenu: function (e) {\n if (this.stopContextMenu) {\n e.stopPropagation();\n e.preventDefault();\n }\n return false;\n },\n\n /**\n * @private\n * @param {Event} e Event object fired on mousedown\n */\n _onDoubleClick: function (e) {\n this._cacheTransformEventData(e);\n this._handleEvent(e, 'dblclick');\n this._resetTransformEventData(e);\n },\n\n /**\n * Return a the id of an event.\n * returns either the pointerId or the identifier or 0 for the mouse event\n * @private\n * @param {Event} evt Event object\n */\n getPointerId: function(evt) {\n var changedTouches = evt.changedTouches;\n\n if (changedTouches) {\n return changedTouches[0] && changedTouches[0].identifier;\n }\n\n if (this.enablePointerEvents) {\n return evt.pointerId;\n }\n\n return -1;\n },\n\n /**\n * Determines if an event has the id of the event that is considered main\n * @private\n * @param {evt} event Event object\n */\n _isMainEvent: function(evt) {\n if (evt.isPrimary === true) {\n return true;\n }\n if (evt.isPrimary === false) {\n return false;\n }\n if (evt.type === 'touchend' && evt.touches.length === 0) {\n return true;\n }\n if (evt.changedTouches) {\n return evt.changedTouches[0].identifier === this.mainTouchId;\n }\n return true;\n },\n\n /**\n * @private\n * @param {Event} e Event object fired on mousedown\n */\n _onTouchStart: function(e) {\n e.preventDefault();\n if (this.mainTouchId === null) {\n this.mainTouchId = this.getPointerId(e);\n }\n this.__onMouseDown(e);\n this._resetTransformEventData();\n var canvasElement = this.upperCanvasEl,\n eventTypePrefix = this._getEventPrefix();\n addListener(fabric.document, 'touchend', this._onTouchEnd, addEventOptions);\n addListener(fabric.document, 'touchmove', this._onMouseMove, addEventOptions);\n // Unbind mousedown to prevent double triggers from touch devices\n removeListener(canvasElement, eventTypePrefix + 'down', this._onMouseDown);\n },\n\n /**\n * @private\n * @param {Event} e Event object fired on mousedown\n */\n _onMouseDown: function (e) {\n this.__onMouseDown(e);\n this._resetTransformEventData();\n var canvasElement = this.upperCanvasEl,\n eventTypePrefix = this._getEventPrefix();\n removeListener(canvasElement, eventTypePrefix + 'move', this._onMouseMove, addEventOptions);\n addListener(fabric.document, eventTypePrefix + 'up', this._onMouseUp);\n addListener(fabric.document, eventTypePrefix + 'move', this._onMouseMove, addEventOptions);\n },\n\n /**\n * @private\n * @param {Event} e Event object fired on mousedown\n */\n _onTouchEnd: function(e) {\n if (e.touches.length > 0) {\n // if there are still touches stop here\n return;\n }\n this.__onMouseUp(e);\n this._resetTransformEventData();\n this.mainTouchId = null;\n var eventTypePrefix = this._getEventPrefix();\n removeListener(fabric.document, 'touchend', this._onTouchEnd, addEventOptions);\n removeListener(fabric.document, 'touchmove', this._onMouseMove, addEventOptions);\n var _this = this;\n if (this._willAddMouseDown) {\n clearTimeout(this._willAddMouseDown);\n }\n this._willAddMouseDown = setTimeout(function() {\n // Wait 400ms before rebinding mousedown to prevent double triggers\n // from touch devices\n addListener(_this.upperCanvasEl, eventTypePrefix + 'down', _this._onMouseDown);\n _this._willAddMouseDown = 0;\n }, 400);\n },\n\n /**\n * @private\n * @param {Event} e Event object fired on mouseup\n */\n _onMouseUp: function (e) {\n this.__onMouseUp(e);\n this._resetTransformEventData();\n var canvasElement = this.upperCanvasEl,\n eventTypePrefix = this._getEventPrefix();\n if (this._isMainEvent(e)) {\n removeListener(fabric.document, eventTypePrefix + 'up', this._onMouseUp);\n removeListener(fabric.document, eventTypePrefix + 'move', this._onMouseMove, addEventOptions);\n addListener(canvasElement, eventTypePrefix + 'move', this._onMouseMove, addEventOptions);\n }\n },\n\n /**\n * @private\n * @param {Event} e Event object fired on mousemove\n */\n _onMouseMove: function (e) {\n !this.allowTouchScrolling && e.preventDefault && e.preventDefault();\n this.__onMouseMove(e);\n },\n\n /**\n * @private\n */\n _onResize: function () {\n this.calcOffset();\n },\n\n /**\n * Decides whether the canvas should be redrawn in mouseup and mousedown events.\n * @private\n * @param {Object} target\n */\n _shouldRender: function(target) {\n var activeObject = this._activeObject;\n\n if (\n !!activeObject !== !!target ||\n (activeObject && target && (activeObject !== target))\n ) {\n // this covers: switch of target, from target to no target, selection of target\n // multiSelection with key and mouse\n return true;\n }\n else if (activeObject && activeObject.isEditing) {\n // if we mouse up/down over a editing textbox a cursor change,\n // there is no need to re render\n return false;\n }\n return false;\n },\n\n /**\n * Method that defines the actions when mouse is released on canvas.\n * The method resets the currentTransform parameters, store the image corner\n * position in the image object and render the canvas on top.\n * @private\n * @param {Event} e Event object fired on mouseup\n */\n __onMouseUp: function (e) {\n var target, transform = this._currentTransform,\n groupSelector = this._groupSelector, shouldRender = false,\n isClick = (!groupSelector || (groupSelector.left === 0 && groupSelector.top === 0));\n this._cacheTransformEventData(e);\n target = this._target;\n this._handleEvent(e, 'up:before');\n // if right/middle click just fire events and return\n // target undefined will make the _handleEvent search the target\n if (checkClick(e, RIGHT_CLICK)) {\n if (this.fireRightClick) {\n this._handleEvent(e, 'up', RIGHT_CLICK, isClick);\n }\n return;\n }\n\n if (checkClick(e, MIDDLE_CLICK)) {\n if (this.fireMiddleClick) {\n this._handleEvent(e, 'up', MIDDLE_CLICK, isClick);\n }\n this._resetTransformEventData();\n return;\n }\n\n if (this.isDrawingMode && this._isCurrentlyDrawing) {\n this._onMouseUpInDrawingMode(e);\n return;\n }\n\n if (!this._isMainEvent(e)) {\n return;\n }\n if (transform) {\n this._finalizeCurrentTransform(e);\n shouldRender = transform.actionPerformed;\n }\n\n if (!isClick) {\n this._maybeGroupObjects(e);\n shouldRender || (shouldRender = this._shouldRender(target));\n }\n if (target) {\n target.isMoving = false;\n }\n this._setCursorFromEvent(e, target);\n this._handleEvent(e, 'up', LEFT_CLICK, isClick);\n this._groupSelector = null;\n this._currentTransform = null;\n // reset the target information about which corner is selected\n target && (target.__corner = 0);\n if (shouldRender) {\n this.requestRenderAll();\n }\n else if (!isClick) {\n this.renderTop();\n }\n },\n\n /**\n * @private\n * Handle event firing for target and subtargets\n * @param {Event} e event from mouse\n * @param {String} eventType event to fire (up, down or move)\n * @return {Fabric.Object} target return the the target found, for internal reasons.\n */\n _simpleEventHandler: function(eventType, e) {\n var target = this.findTarget(e),\n targets = this.targets,\n options = {\n e: e,\n target: target,\n subTargets: targets,\n };\n this.fire(eventType, options);\n target && target.fire(eventType, options);\n if (!targets) {\n return target;\n }\n for (var i = 0; i < targets.length; i++) {\n targets[i].fire(eventType, options);\n }\n return target;\n },\n\n /**\n * @private\n * Handle event firing for target and subtargets\n * @param {Event} e event from mouse\n * @param {String} eventType event to fire (up, down or move)\n * @param {fabric.Object} targetObj receiving event\n * @param {Number} [button] button used in the event 1 = left, 2 = middle, 3 = right\n * @param {Boolean} isClick for left button only, indicates that the mouse up happened without move.\n */\n _handleEvent: function(e, eventType, button, isClick) {\n var target = this._target,\n targets = this.targets || [],\n options = {\n e: e,\n target: target,\n subTargets: targets,\n button: button || LEFT_CLICK,\n isClick: isClick || false,\n pointer: this._pointer,\n absolutePointer: this._absolutePointer,\n transform: this._currentTransform\n };\n this.fire('mouse:' + eventType, options);\n target && target.fire('mouse' + eventType, options);\n for (var i = 0; i < targets.length; i++) {\n targets[i].fire('mouse' + eventType, options);\n }\n },\n\n /**\n * @private\n * @param {Event} e send the mouse event that generate the finalize down, so it can be used in the event\n */\n _finalizeCurrentTransform: function(e) {\n\n var transform = this._currentTransform,\n target = transform.target,\n eventName,\n options = {\n e: e,\n target: target,\n transform: transform,\n };\n\n if (target._scaling) {\n target._scaling = false;\n }\n\n target.setCoords();\n\n if (transform.actionPerformed || (this.stateful && target.hasStateChanged())) {\n if (transform.actionPerformed) {\n eventName = this._addEventOptions(options, transform);\n this._fire(eventName, options);\n }\n this._fire('modified', options);\n }\n },\n\n /**\n * Mutate option object in order to add by property and give back the event name.\n * @private\n * @param {Object} options to mutate\n * @param {Object} transform to inspect action from\n */\n _addEventOptions: function(options, transform) {\n // we can probably add more details at low cost\n // scale change, rotation changes, translation changes\n var eventName, by;\n switch (transform.action) {\n case 'scaleX':\n eventName = 'scaled';\n by = 'x';\n break;\n case 'scaleY':\n eventName = 'scaled';\n by = 'y';\n break;\n case 'skewX':\n eventName = 'skewed';\n by = 'x';\n break;\n case 'skewY':\n eventName = 'skewed';\n by = 'y';\n break;\n case 'scale':\n eventName = 'scaled';\n by = 'equally';\n break;\n case 'rotate':\n eventName = 'rotated';\n break;\n case 'drag':\n eventName = 'moved';\n break;\n }\n options.by = by;\n return eventName;\n },\n\n /**\n * @private\n * @param {Event} e Event object fired on mousedown\n */\n _onMouseDownInDrawingMode: function(e) {\n this._isCurrentlyDrawing = true;\n if (this.getActiveObject()) {\n this.discardActiveObject(e).requestRenderAll();\n }\n if (this.clipTo) {\n fabric.util.clipContext(this, this.contextTop);\n }\n var pointer = this.getPointer(e);\n this.freeDrawingBrush.onMouseDown(pointer, { e: e, pointer: pointer });\n this._handleEvent(e, 'down');\n },\n\n /**\n * @private\n * @param {Event} e Event object fired on mousemove\n */\n _onMouseMoveInDrawingMode: function(e) {\n if (this._isCurrentlyDrawing) {\n var pointer = this.getPointer(e);\n this.freeDrawingBrush.onMouseMove(pointer, { e: e, pointer: pointer });\n }\n this.setCursor(this.freeDrawingCursor);\n this._handleEvent(e, 'move');\n },\n\n /**\n * @private\n * @param {Event} e Event object fired on mouseup\n */\n _onMouseUpInDrawingMode: function(e) {\n if (this.clipTo) {\n this.contextTop.restore();\n }\n var pointer = this.getPointer(e);\n this._isCurrentlyDrawing = this.freeDrawingBrush.onMouseUp({ e: e, pointer: pointer });\n this._handleEvent(e, 'up');\n },\n\n /**\n * Method that defines the actions when mouse is clicked on canvas.\n * The method inits the currentTransform parameters and renders all the\n * canvas so the current image can be placed on the top canvas and the rest\n * in on the container one.\n * @private\n * @param {Event} e Event object fired on mousedown\n */\n __onMouseDown: function (e) {\n this._cacheTransformEventData(e);\n this._handleEvent(e, 'down:before');\n var target = this._target;\n // if right click just fire events\n if (checkClick(e, RIGHT_CLICK)) {\n if (this.fireRightClick) {\n this._handleEvent(e, 'down', RIGHT_CLICK);\n }\n return;\n }\n\n if (checkClick(e, MIDDLE_CLICK)) {\n if (this.fireMiddleClick) {\n this._handleEvent(e, 'down', MIDDLE_CLICK);\n }\n return;\n }\n\n if (this.isDrawingMode) {\n this._onMouseDownInDrawingMode(e);\n return;\n }\n\n if (!this._isMainEvent(e)) {\n return;\n }\n\n // ignore if some object is being transformed at this moment\n if (this._currentTransform) {\n return;\n }\n\n var pointer = this._pointer;\n // save pointer for check in __onMouseUp event\n this._previousPointer = pointer;\n var shouldRender = this._shouldRender(target),\n shouldGroup = this._shouldGroup(e, target);\n if (this._shouldClearSelection(e, target)) {\n this.discardActiveObject(e);\n }\n else if (shouldGroup) {\n this._handleGrouping(e, target);\n target = this._activeObject;\n }\n\n if (this.selection && (!target ||\n (!target.selectable && !target.isEditing && target !== this._activeObject))) {\n this._groupSelector = {\n ex: pointer.x,\n ey: pointer.y,\n top: 0,\n left: 0\n };\n }\n\n if (target) {\n var alreadySelected = target === this._activeObject;\n if (target.selectable) {\n this.setActiveObject(target, e);\n }\n if (target === this._activeObject && (target.__corner || !shouldGroup)) {\n this._setupCurrentTransform(e, target, alreadySelected);\n }\n }\n this._handleEvent(e, 'down');\n // we must renderAll so that we update the visuals\n (shouldRender || shouldGroup) && this.requestRenderAll();\n },\n\n /**\n * reset cache form common information needed during event processing\n * @private\n */\n _resetTransformEventData: function() {\n this._target = null;\n this._pointer = null;\n this._absolutePointer = null;\n },\n\n /**\n * Cache common information needed during event processing\n * @private\n * @param {Event} e Event object fired on event\n */\n _cacheTransformEventData: function(e) {\n // reset in order to avoid stale caching\n this._resetTransformEventData();\n this._pointer = this.getPointer(e, true);\n this._absolutePointer = this.restorePointerVpt(this._pointer);\n this._target = this._currentTransform ? this._currentTransform.target : this.findTarget(e) || null;\n },\n\n /**\n * @private\n */\n _beforeTransform: function(e) {\n var t = this._currentTransform;\n this.stateful && t.target.saveState();\n this.fire('before:transform', {\n e: e,\n transform: t,\n });\n // determine if it's a drag or rotate case\n if (t.corner) {\n this.onBeforeScaleRotate(t.target);\n }\n },\n\n /**\n * Method that defines the actions when mouse is hovering the canvas.\n * The currentTransform parameter will define whether the user is rotating/scaling/translating\n * an image or neither of them (only hovering). A group selection is also possible and would cancel\n * all any other type of action.\n * In case of an image transformation only the top canvas will be rendered.\n * @private\n * @param {Event} e Event object fired on mousemove\n */\n __onMouseMove: function (e) {\n this._handleEvent(e, 'move:before');\n this._cacheTransformEventData(e);\n var target, pointer;\n\n if (this.isDrawingMode) {\n this._onMouseMoveInDrawingMode(e);\n return;\n }\n\n if (!this._isMainEvent(e)) {\n return;\n }\n\n var groupSelector = this._groupSelector;\n\n // We initially clicked in an empty area, so we draw a box for multiple selection\n if (groupSelector) {\n pointer = this._pointer;\n\n groupSelector.left = pointer.x - groupSelector.ex;\n groupSelector.top = pointer.y - groupSelector.ey;\n\n this.renderTop();\n }\n else if (!this._currentTransform) {\n target = this.findTarget(e) || null;\n this._setCursorFromEvent(e, target);\n this._fireOverOutEvents(target, e);\n }\n else {\n this._transformObject(e);\n }\n this._handleEvent(e, 'move');\n this._resetTransformEventData();\n },\n\n /**\n * Manage the mouseout, mouseover events for the fabric object on the canvas\n * @param {Fabric.Object} target the target where the target from the mousemove event\n * @param {Event} e Event object fired on mousemove\n * @private\n */\n _fireOverOutEvents: function(target, e) {\n var _hoveredTarget = this._hoveredTarget,\n _hoveredTargets = this._hoveredTargets, targets = this.targets,\n length = Math.max(_hoveredTargets.length, targets.length);\n\n this.fireSyntheticInOutEvents(target, e, {\n oldTarget: _hoveredTarget,\n evtOut: 'mouseout',\n canvasEvtOut: 'mouse:out',\n evtIn: 'mouseover',\n canvasEvtIn: 'mouse:over',\n });\n for (var i = 0; i < length; i++){\n this.fireSyntheticInOutEvents(targets[i], e, {\n oldTarget: _hoveredTargets[i],\n evtOut: 'mouseout',\n evtIn: 'mouseover',\n });\n }\n this._hoveredTarget = target;\n this._hoveredTargets = this.targets.concat();\n },\n\n /**\n * Manage the dragEnter, dragLeave events for the fabric objects on the canvas\n * @param {Fabric.Object} target the target where the target from the onDrag event\n * @param {Event} e Event object fired on ondrag\n * @private\n */\n _fireEnterLeaveEvents: function(target, e) {\n var _draggedoverTarget = this._draggedoverTarget,\n _hoveredTargets = this._hoveredTargets, targets = this.targets,\n length = Math.max(_hoveredTargets.length, targets.length);\n\n this.fireSyntheticInOutEvents(target, e, {\n oldTarget: _draggedoverTarget,\n evtOut: 'dragleave',\n evtIn: 'dragenter',\n });\n for (var i = 0; i < length; i++) {\n this.fireSyntheticInOutEvents(targets[i], e, {\n oldTarget: _hoveredTargets[i],\n evtOut: 'dragleave',\n evtIn: 'dragenter',\n });\n }\n this._draggedoverTarget = target;\n },\n\n /**\n * Manage the synthetic in/out events for the fabric objects on the canvas\n * @param {Fabric.Object} target the target where the target from the supported events\n * @param {Event} e Event object fired\n * @param {Object} config configuration for the function to work\n * @param {String} config.targetName property on the canvas where the old target is stored\n * @param {String} [config.canvasEvtOut] name of the event to fire at canvas level for out\n * @param {String} config.evtOut name of the event to fire for out\n * @param {String} [config.canvasEvtIn] name of the event to fire at canvas level for in\n * @param {String} config.evtIn name of the event to fire for in\n * @private\n */\n fireSyntheticInOutEvents: function(target, e, config) {\n var inOpt, outOpt, oldTarget = config.oldTarget, outFires, inFires,\n targetChanged = oldTarget !== target, canvasEvtIn = config.canvasEvtIn, canvasEvtOut = config.canvasEvtOut;\n if (targetChanged) {\n inOpt = { e: e, target: target, previousTarget: oldTarget };\n outOpt = { e: e, target: oldTarget, nextTarget: target };\n }\n inFires = target && targetChanged;\n outFires = oldTarget && targetChanged;\n if (outFires) {\n canvasEvtOut && this.fire(canvasEvtOut, outOpt);\n oldTarget.fire(config.evtOut, outOpt);\n }\n if (inFires) {\n canvasEvtIn && this.fire(canvasEvtIn, inOpt);\n target.fire(config.evtIn, inOpt);\n }\n },\n\n /**\n * Method that defines actions when an Event Mouse Wheel\n * @param {Event} e Event object fired on mouseup\n */\n __onMouseWheel: function(e) {\n this._cacheTransformEventData(e);\n this._handleEvent(e, 'wheel');\n this._resetTransformEventData();\n },\n\n /**\n * @private\n * @param {Event} e Event fired on mousemove\n */\n _transformObject: function(e) {\n var pointer = this.getPointer(e),\n transform = this._currentTransform;\n\n transform.reset = false;\n transform.target.isMoving = true;\n transform.shiftKey = e.shiftKey;\n transform.altKey = e[this.centeredKey];\n\n this._beforeScaleTransform(e, transform);\n this._performTransformAction(e, transform, pointer);\n\n transform.actionPerformed && this.requestRenderAll();\n },\n\n /**\n * @private\n */\n _performTransformAction: function(e, transform, pointer) {\n var x = pointer.x,\n y = pointer.y,\n action = transform.action,\n actionPerformed = false,\n options = {\n target: transform.target,\n e: e,\n transform: transform,\n pointer: pointer\n };\n\n if (action === 'rotate') {\n (actionPerformed = this._rotateObject(x, y)) && this._fire('rotating', options);\n }\n else if (action === 'scale') {\n (actionPerformed = this._onScale(e, transform, x, y)) && this._fire('scaling', options);\n }\n else if (action === 'scaleX') {\n (actionPerformed = this._scaleObject(x, y, 'x')) && this._fire('scaling', options);\n }\n else if (action === 'scaleY') {\n (actionPerformed = this._scaleObject(x, y, 'y')) && this._fire('scaling', options);\n }\n else if (action === 'skewX') {\n (actionPerformed = this._skewObject(x, y, 'x')) && this._fire('skewing', options);\n }\n else if (action === 'skewY') {\n (actionPerformed = this._skewObject(x, y, 'y')) && this._fire('skewing', options);\n }\n else {\n actionPerformed = this._translateObject(x, y);\n if (actionPerformed) {\n this._fire('moving', options);\n this.setCursor(options.target.moveCursor || this.moveCursor);\n }\n }\n transform.actionPerformed = transform.actionPerformed || actionPerformed;\n },\n\n /**\n * @private\n */\n _fire: function(eventName, options) {\n this.fire('object:' + eventName, options);\n options.target.fire(eventName, options);\n },\n\n /**\n * @private\n */\n _beforeScaleTransform: function(e, transform) {\n if (transform.action === 'scale' || transform.action === 'scaleX' || transform.action === 'scaleY') {\n var centerTransform = this._shouldCenterTransform(transform.target);\n\n // Switch from a normal resize to center-based\n if ((centerTransform && (transform.originX !== 'center' || transform.originY !== 'center')) ||\n // Switch from center-based resize to normal one\n (!centerTransform && transform.originX === 'center' && transform.originY === 'center')\n ) {\n this._resetCurrentTransform();\n transform.reset = true;\n }\n }\n },\n\n /**\n * @private\n * @param {Event} e Event object\n * @param {Object} transform current transform\n * @param {Number} x mouse position x from origin\n * @param {Number} y mouse position y from origin\n * @return {Boolean} true if the scaling occurred\n */\n _onScale: function(e, transform, x, y) {\n if (this._isUniscalePossible(e, transform.target)) {\n transform.currentAction = 'scale';\n return this._scaleObject(x, y);\n }\n else {\n // Switch from a normal resize to proportional\n if (!transform.reset && transform.currentAction === 'scale') {\n this._resetCurrentTransform();\n }\n\n transform.currentAction = 'scaleEqually';\n return this._scaleObject(x, y, 'equally');\n }\n },\n\n /**\n * @private\n * @param {Event} e Event object\n * @param {fabric.Object} target current target\n * @return {Boolean} true if unproportional scaling is possible\n */\n _isUniscalePossible: function(e, target) {\n return (e[this.uniScaleKey] || this.uniScaleTransform) && !target.get('lockUniScaling');\n },\n\n /**\n * Sets the cursor depending on where the canvas is being hovered.\n * Note: very buggy in Opera\n * @param {Event} e Event object\n * @param {Object} target Object that the mouse is hovering, if so.\n */\n _setCursorFromEvent: function (e, target) {\n if (!target) {\n this.setCursor(this.defaultCursor);\n return false;\n }\n var hoverCursor = target.hoverCursor || this.hoverCursor,\n activeSelection = this._activeObject && this._activeObject.type === 'activeSelection' ?\n this._activeObject : null,\n // only show proper corner when group selection is not active\n corner = (!activeSelection || !activeSelection.contains(target))\n && target._findTargetCorner(this.getPointer(e, true));\n\n if (!corner) {\n if (target.subTargetCheck){\n // hoverCursor should come from top-most subTarget,\n // so we walk the array backwards\n this.targets.concat().reverse().map(function(_target){\n hoverCursor = _target.hoverCursor || hoverCursor;\n });\n }\n this.setCursor(hoverCursor);\n }\n else {\n this.setCursor(this.getCornerCursor(corner, target, e));\n }\n },\n\n /**\n * @private\n */\n getCornerCursor: function(corner, target, e) {\n if (this.actionIsDisabled(corner, target, e)) {\n return this.notAllowedCursor;\n }\n else if (corner in cursorOffset) {\n return this._getRotatedCornerCursor(corner, target, e);\n }\n else if (corner === 'mtr' && target.hasRotatingPoint) {\n return this.rotationCursor;\n }\n else {\n return this.defaultCursor;\n }\n },\n\n actionIsDisabled: function(corner, target, e) {\n if (corner === 'mt' || corner === 'mb') {\n return e[this.altActionKey] ? target.lockSkewingX : target.lockScalingY;\n }\n else if (corner === 'ml' || corner === 'mr') {\n return e[this.altActionKey] ? target.lockSkewingY : target.lockScalingX;\n }\n else if (corner === 'mtr') {\n return target.lockRotation;\n }\n else {\n return this._isUniscalePossible(e, target) ?\n target.lockScalingX && target.lockScalingY : target.lockScalingX || target.lockScalingY;\n }\n },\n\n /**\n * @private\n */\n _getRotatedCornerCursor: function(corner, target, e) {\n var n = Math.round((target.angle % 360) / 45);\n\n if (n < 0) {\n n += 8; // full circle ahead\n }\n n += cursorOffset[corner];\n if (e[this.altActionKey] && cursorOffset[corner] % 2 === 0) {\n //if we are holding shift and we are on a mx corner...\n n += 2;\n }\n // normalize n to be from 0 to 7\n n %= 8;\n\n return this.cursorMap[n];\n }\n });\n})();\n\n\n(function() {\n\n var min = Math.min,\n max = Math.max;\n\n fabric.util.object.extend(fabric.Canvas.prototype, /** @lends fabric.Canvas.prototype */ {\n\n /**\n * @private\n * @param {Event} e Event object\n * @param {fabric.Object} target\n * @return {Boolean}\n */\n _shouldGroup: function(e, target) {\n var activeObject = this._activeObject;\n return activeObject && this._isSelectionKeyPressed(e) && target && target.selectable && this.selection &&\n (activeObject !== target || activeObject.type === 'activeSelection') && !target.onSelect({ e: e });\n },\n\n /**\n * @private\n * @param {Event} e Event object\n * @param {fabric.Object} target\n */\n _handleGrouping: function (e, target) {\n var activeObject = this._activeObject;\n // avoid multi select when shift click on a corner\n if (activeObject.__corner) {\n return;\n }\n if (target === activeObject) {\n // if it's a group, find target again, using activeGroup objects\n target = this.findTarget(e, true);\n // if even object is not found or we are on activeObjectCorner, bail out\n if (!target || !target.selectable) {\n return;\n }\n }\n if (activeObject && activeObject.type === 'activeSelection') {\n this._updateActiveSelection(target, e);\n }\n else {\n this._createActiveSelection(target, e);\n }\n },\n\n /**\n * @private\n */\n _updateActiveSelection: function(target, e) {\n var activeSelection = this._activeObject,\n currentActiveObjects = activeSelection._objects.slice(0);\n if (activeSelection.contains(target)) {\n activeSelection.removeWithUpdate(target);\n this._hoveredTarget = target;\n this._hoveredTargets = this.targets.concat();\n if (activeSelection.size() === 1) {\n // activate last remaining object\n this._setActiveObject(activeSelection.item(0), e);\n }\n }\n else {\n activeSelection.addWithUpdate(target);\n this._hoveredTarget = activeSelection;\n this._hoveredTargets = this.targets.concat();\n }\n this._fireSelectionEvents(currentActiveObjects, e);\n },\n\n /**\n * @private\n */\n _createActiveSelection: function(target, e) {\n var currentActives = this.getActiveObjects(), group = this._createGroup(target);\n this._hoveredTarget = group;\n // ISSUE 4115: should we consider subTargets here?\n // this._hoveredTargets = [];\n // this._hoveredTargets = this.targets.concat();\n this._setActiveObject(group, e);\n this._fireSelectionEvents(currentActives, e);\n },\n\n /**\n * @private\n * @param {Object} target\n */\n _createGroup: function(target) {\n var objects = this._objects,\n isActiveLower = objects.indexOf(this._activeObject) < objects.indexOf(target),\n groupObjects = isActiveLower\n ? [this._activeObject, target]\n : [target, this._activeObject];\n this._activeObject.isEditing && this._activeObject.exitEditing();\n return new fabric.ActiveSelection(groupObjects, {\n canvas: this\n });\n },\n\n /**\n * @private\n * @param {Event} e mouse event\n */\n _groupSelectedObjects: function (e) {\n\n var group = this._collectObjects(e),\n aGroup;\n\n // do not create group for 1 element only\n if (group.length === 1) {\n this.setActiveObject(group[0], e);\n }\n else if (group.length > 1) {\n aGroup = new fabric.ActiveSelection(group.reverse(), {\n canvas: this\n });\n this.setActiveObject(aGroup, e);\n }\n },\n\n /**\n * @private\n */\n _collectObjects: function(e) {\n var group = [],\n currentObject,\n x1 = this._groupSelector.ex,\n y1 = this._groupSelector.ey,\n x2 = x1 + this._groupSelector.left,\n y2 = y1 + this._groupSelector.top,\n selectionX1Y1 = new fabric.Point(min(x1, x2), min(y1, y2)),\n selectionX2Y2 = new fabric.Point(max(x1, x2), max(y1, y2)),\n allowIntersect = !this.selectionFullyContained,\n isClick = x1 === x2 && y1 === y2;\n // we iterate reverse order to collect top first in case of click.\n for (var i = this._objects.length; i--; ) {\n currentObject = this._objects[i];\n\n if (!currentObject || !currentObject.selectable || !currentObject.visible) {\n continue;\n }\n\n if ((allowIntersect && currentObject.intersectsWithRect(selectionX1Y1, selectionX2Y2)) ||\n currentObject.isContainedWithinRect(selectionX1Y1, selectionX2Y2) ||\n (allowIntersect && currentObject.containsPoint(selectionX1Y1)) ||\n (allowIntersect && currentObject.containsPoint(selectionX2Y2))\n ) {\n group.push(currentObject);\n // only add one object if it's a click\n if (isClick) {\n break;\n }\n }\n }\n\n if (group.length > 1) {\n group = group.filter(function(object) {\n return !object.onSelect({ e: e });\n });\n }\n\n return group;\n },\n\n /**\n * @private\n */\n _maybeGroupObjects: function(e) {\n if (this.selection && this._groupSelector) {\n this._groupSelectedObjects(e);\n }\n this.setCursor(this.defaultCursor);\n // clear selection and current transformation\n this._groupSelector = null;\n }\n });\n\n})();\n\n\n(function () {\n fabric.util.object.extend(fabric.StaticCanvas.prototype, /** @lends fabric.StaticCanvas.prototype */ {\n\n /**\n * Exports canvas element to a dataurl image. Note that when multiplier is used, cropping is scaled appropriately\n * @param {Object} [options] Options object\n * @param {String} [options.format=png] The format of the output image. Either \"jpeg\" or \"png\"\n * @param {Number} [options.quality=1] Quality level (0..1). Only used for jpeg.\n * @param {Number} [options.multiplier=1] Multiplier to scale by, to have consistent\n * @param {Number} [options.left] Cropping left offset. Introduced in v1.2.14\n * @param {Number} [options.top] Cropping top offset. Introduced in v1.2.14\n * @param {Number} [options.width] Cropping width. Introduced in v1.2.14\n * @param {Number} [options.height] Cropping height. Introduced in v1.2.14\n * @param {Boolean} [options.enableRetinaScaling] Enable retina scaling for clone image. Introduce in 2.0.0\n * @return {String} Returns a data: URL containing a representation of the object in the format specified by options.format\n * @see {@link http://jsfiddle.net/fabricjs/NfZVb/|jsFiddle demo}\n * @example Generate jpeg dataURL with lower quality\n * var dataURL = canvas.toDataURL({\n * format: 'jpeg',\n * quality: 0.8\n * });\n * @example Generate cropped png dataURL (clipping of canvas)\n * var dataURL = canvas.toDataURL({\n * format: 'png',\n * left: 100,\n * top: 100,\n * width: 200,\n * height: 200\n * });\n * @example Generate double scaled png dataURL\n * var dataURL = canvas.toDataURL({\n * format: 'png',\n * multiplier: 2\n * });\n */\n toDataURL: function (options) {\n options || (options = { });\n\n var format = options.format || 'png',\n quality = options.quality || 1,\n multiplier = (options.multiplier || 1) * (options.enableRetinaScaling ? this.getRetinaScaling() : 1),\n canvasEl = this.toCanvasElement(multiplier, options);\n return fabric.util.toDataURL(canvasEl, format, quality);\n },\n\n /**\n * Create a new HTMLCanvas element painted with the current canvas content.\n * No need to resize the actual one or repaint it.\n * Will transfer object ownership to a new canvas, paint it, and set everything back.\n * This is an intermediary step used to get to a dataUrl but also it is useful to\n * create quick image copies of a canvas without passing for the dataUrl string\n * @param {Number} [multiplier] a zoom factor.\n * @param {Object} [cropping] Cropping informations\n * @param {Number} [cropping.left] Cropping left offset.\n * @param {Number} [cropping.top] Cropping top offset.\n * @param {Number} [cropping.width] Cropping width.\n * @param {Number} [cropping.height] Cropping height.\n */\n toCanvasElement: function(multiplier, cropping) {\n multiplier = multiplier || 1;\n cropping = cropping || { };\n var scaledWidth = (cropping.width || this.width) * multiplier,\n scaledHeight = (cropping.height || this.height) * multiplier,\n zoom = this.getZoom(),\n originalWidth = this.width,\n originalHeight = this.height,\n newZoom = zoom * multiplier,\n vp = this.viewportTransform,\n translateX = (vp[4] - (cropping.left || 0)) * multiplier,\n translateY = (vp[5] - (cropping.top || 0)) * multiplier,\n originalInteractive = this.interactive,\n newVp = [newZoom, 0, 0, newZoom, translateX, translateY],\n originalRetina = this.enableRetinaScaling,\n canvasEl = fabric.util.createCanvasElement(),\n originalContextTop = this.contextTop;\n canvasEl.width = scaledWidth;\n canvasEl.height = scaledHeight;\n this.contextTop = null;\n this.enableRetinaScaling = false;\n this.interactive = false;\n this.viewportTransform = newVp;\n this.width = scaledWidth;\n this.height = scaledHeight;\n this.calcViewportBoundaries();\n this.renderCanvas(canvasEl.getContext('2d'), this._objects);\n this.viewportTransform = vp;\n this.width = originalWidth;\n this.height = originalHeight;\n this.calcViewportBoundaries();\n this.interactive = originalInteractive;\n this.enableRetinaScaling = originalRetina;\n this.contextTop = originalContextTop;\n return canvasEl;\n },\n });\n\n})();\n\n\nfabric.util.object.extend(fabric.StaticCanvas.prototype, /** @lends fabric.StaticCanvas.prototype */ {\n\n /**\n * Populates canvas with data from the specified dataless JSON.\n * JSON format must conform to the one of {@link fabric.Canvas#toDatalessJSON}\n * @deprecated since 1.2.2\n * @param {String|Object} json JSON string or object\n * @param {Function} callback Callback, invoked when json is parsed\n * and corresponding objects (e.g: {@link fabric.Image})\n * are initialized\n * @param {Function} [reviver] Method for further parsing of JSON elements, called after each fabric object created.\n * @return {fabric.Canvas} instance\n * @chainable\n * @tutorial {@link http://fabricjs.com/fabric-intro-part-3#deserialization}\n */\n loadFromDatalessJSON: function (json, callback, reviver) {\n return this.loadFromJSON(json, callback, reviver);\n },\n\n /**\n * Populates canvas with data from the specified JSON.\n * JSON format must conform to the one of {@link fabric.Canvas#toJSON}\n * @param {String|Object} json JSON string or object\n * @param {Function} callback Callback, invoked when json is parsed\n * and corresponding objects (e.g: {@link fabric.Image})\n * are initialized\n * @param {Function} [reviver] Method for further parsing of JSON elements, called after each fabric object created.\n * @return {fabric.Canvas} instance\n * @chainable\n * @tutorial {@link http://fabricjs.com/fabric-intro-part-3#deserialization}\n * @see {@link http://jsfiddle.net/fabricjs/fmgXt/|jsFiddle demo}\n * @example loadFromJSON\n * canvas.loadFromJSON(json, canvas.renderAll.bind(canvas));\n * @example loadFromJSON with reviver\n * canvas.loadFromJSON(json, canvas.renderAll.bind(canvas), function(o, object) {\n * // `o` = json object\n * // `object` = fabric.Object instance\n * // ... do some stuff ...\n * });\n */\n loadFromJSON: function (json, callback, reviver) {\n if (!json) {\n return;\n }\n\n // serialize if it wasn't already\n var serialized = (typeof json === 'string')\n ? JSON.parse(json)\n : fabric.util.object.clone(json);\n\n var _this = this,\n clipPath = serialized.clipPath,\n renderOnAddRemove = this.renderOnAddRemove;\n\n this.renderOnAddRemove = false;\n\n delete serialized.clipPath;\n\n this._enlivenObjects(serialized.objects, function (enlivenedObjects) {\n _this.clear();\n _this._setBgOverlay(serialized, function () {\n if (clipPath) {\n _this._enlivenObjects([clipPath], function (enlivenedCanvasClip) {\n _this.clipPath = enlivenedCanvasClip[0];\n _this.__setupCanvas.call(_this, serialized, enlivenedObjects, renderOnAddRemove, callback);\n });\n }\n else {\n _this.__setupCanvas.call(_this, serialized, enlivenedObjects, renderOnAddRemove, callback);\n }\n });\n }, reviver);\n return this;\n },\n\n /**\n * @private\n * @param {Object} serialized Object with background and overlay information\n * @param {Array} restored canvas objects\n * @param {Function} cached renderOnAddRemove callback\n * @param {Function} callback Invoked after all background and overlay images/patterns loaded\n */\n __setupCanvas: function(serialized, enlivenedObjects, renderOnAddRemove, callback) {\n var _this = this;\n enlivenedObjects.forEach(function(obj, index) {\n // we splice the array just in case some custom classes restored from JSON\n // will add more object to canvas at canvas init.\n _this.insertAt(obj, index);\n });\n this.renderOnAddRemove = renderOnAddRemove;\n // remove parts i cannot set as options\n delete serialized.objects;\n delete serialized.backgroundImage;\n delete serialized.overlayImage;\n delete serialized.background;\n delete serialized.overlay;\n // this._initOptions does too many things to just\n // call it. Normally loading an Object from JSON\n // create the Object instance. Here the Canvas is\n // already an instance and we are just loading things over it\n this._setOptions(serialized);\n this.renderAll();\n callback && callback();\n },\n\n /**\n * @private\n * @param {Object} serialized Object with background and overlay information\n * @param {Function} callback Invoked after all background and overlay images/patterns loaded\n */\n _setBgOverlay: function(serialized, callback) {\n var loaded = {\n backgroundColor: false,\n overlayColor: false,\n backgroundImage: false,\n overlayImage: false\n };\n\n if (!serialized.backgroundImage && !serialized.overlayImage && !serialized.background && !serialized.overlay) {\n callback && callback();\n return;\n }\n\n var cbIfLoaded = function () {\n if (loaded.backgroundImage && loaded.overlayImage && loaded.backgroundColor && loaded.overlayColor) {\n callback && callback();\n }\n };\n\n this.__setBgOverlay('backgroundImage', serialized.backgroundImage, loaded, cbIfLoaded);\n this.__setBgOverlay('overlayImage', serialized.overlayImage, loaded, cbIfLoaded);\n this.__setBgOverlay('backgroundColor', serialized.background, loaded, cbIfLoaded);\n this.__setBgOverlay('overlayColor', serialized.overlay, loaded, cbIfLoaded);\n },\n\n /**\n * @private\n * @param {String} property Property to set (backgroundImage, overlayImage, backgroundColor, overlayColor)\n * @param {(Object|String)} value Value to set\n * @param {Object} loaded Set loaded property to true if property is set\n * @param {Object} callback Callback function to invoke after property is set\n */\n __setBgOverlay: function(property, value, loaded, callback) {\n var _this = this;\n\n if (!value) {\n loaded[property] = true;\n callback && callback();\n return;\n }\n\n if (property === 'backgroundImage' || property === 'overlayImage') {\n fabric.util.enlivenObjects([value], function(enlivedObject){\n _this[property] = enlivedObject[0];\n loaded[property] = true;\n callback && callback();\n });\n }\n else {\n this['set' + fabric.util.string.capitalize(property, true)](value, function() {\n loaded[property] = true;\n callback && callback();\n });\n }\n },\n\n /**\n * @private\n * @param {Array} objects\n * @param {Function} callback\n * @param {Function} [reviver]\n */\n _enlivenObjects: function (objects, callback, reviver) {\n if (!objects || objects.length === 0) {\n callback && callback([]);\n return;\n }\n\n fabric.util.enlivenObjects(objects, function(enlivenedObjects) {\n callback && callback(enlivenedObjects);\n }, null, reviver);\n },\n\n /**\n * @private\n * @param {String} format\n * @param {Function} callback\n */\n _toDataURL: function (format, callback) {\n this.clone(function (clone) {\n callback(clone.toDataURL(format));\n });\n },\n\n /**\n * @private\n * @param {String} format\n * @param {Number} multiplier\n * @param {Function} callback\n */\n _toDataURLWithMultiplier: function (format, multiplier, callback) {\n this.clone(function (clone) {\n callback(clone.toDataURLWithMultiplier(format, multiplier));\n });\n },\n\n /**\n * Clones canvas instance\n * @param {Object} [callback] Receives cloned instance as a first argument\n * @param {Array} [properties] Array of properties to include in the cloned canvas and children\n */\n clone: function (callback, properties) {\n var data = JSON.stringify(this.toJSON(properties));\n this.cloneWithoutData(function(clone) {\n clone.loadFromJSON(data, function() {\n callback && callback(clone);\n });\n });\n },\n\n /**\n * Clones canvas instance without cloning existing data.\n * This essentially copies canvas dimensions, clipping properties, etc.\n * but leaves data empty (so that you can populate it with your own)\n * @param {Object} [callback] Receives cloned instance as a first argument\n */\n cloneWithoutData: function(callback) {\n var el = fabric.util.createCanvasElement();\n\n el.width = this.width;\n el.height = this.height;\n\n var clone = new fabric.Canvas(el);\n clone.clipTo = this.clipTo;\n if (this.backgroundImage) {\n clone.setBackgroundImage(this.backgroundImage.src, function() {\n clone.renderAll();\n callback && callback(clone);\n });\n clone.backgroundImageOpacity = this.backgroundImageOpacity;\n clone.backgroundImageStretch = this.backgroundImageStretch;\n }\n else {\n callback && callback(clone);\n }\n }\n});\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { }),\n extend = fabric.util.object.extend,\n clone = fabric.util.object.clone,\n toFixed = fabric.util.toFixed,\n capitalize = fabric.util.string.capitalize,\n degreesToRadians = fabric.util.degreesToRadians,\n supportsLineDash = fabric.StaticCanvas.supports('setLineDash'),\n objectCaching = !fabric.isLikelyNode,\n ALIASING_LIMIT = 2;\n\n if (fabric.Object) {\n return;\n }\n\n /**\n * Root object class from which all 2d shape classes inherit from\n * @class fabric.Object\n * @tutorial {@link http://fabricjs.com/fabric-intro-part-1#objects}\n * @see {@link fabric.Object#initialize} for constructor definition\n *\n * @fires added\n * @fires removed\n *\n * @fires selected\n * @fires deselected\n * @fires modified\n * @fires modified\n * @fires moved\n * @fires scaled\n * @fires rotated\n * @fires skewed\n *\n * @fires rotating\n * @fires scaling\n * @fires moving\n * @fires skewing\n *\n * @fires mousedown\n * @fires mouseup\n * @fires mouseover\n * @fires mouseout\n * @fires mousewheel\n * @fires mousedblclick\n *\n * @fires dragover\n * @fires dragenter\n * @fires dragleave\n * @fires drop\n */\n fabric.Object = fabric.util.createClass(fabric.CommonMethods, /** @lends fabric.Object.prototype */ {\n\n /**\n * Type of an object (rect, circle, path, etc.).\n * Note that this property is meant to be read-only and not meant to be modified.\n * If you modify, certain parts of Fabric (such as JSON loading) won't work correctly.\n * @type String\n * @default\n */\n type: 'object',\n\n /**\n * Horizontal origin of transformation of an object (one of \"left\", \"right\", \"center\")\n * See http://jsfiddle.net/1ow02gea/244/ on how originX/originY affect objects in groups\n * @type String\n * @default\n */\n originX: 'left',\n\n /**\n * Vertical origin of transformation of an object (one of \"top\", \"bottom\", \"center\")\n * See http://jsfiddle.net/1ow02gea/244/ on how originX/originY affect objects in groups\n * @type String\n * @default\n */\n originY: 'top',\n\n /**\n * Top position of an object. Note that by default it's relative to object top. You can change this by setting originY={top/center/bottom}\n * @type Number\n * @default\n */\n top: 0,\n\n /**\n * Left position of an object. Note that by default it's relative to object left. You can change this by setting originX={left/center/right}\n * @type Number\n * @default\n */\n left: 0,\n\n /**\n * Object width\n * @type Number\n * @default\n */\n width: 0,\n\n /**\n * Object height\n * @type Number\n * @default\n */\n height: 0,\n\n /**\n * Object scale factor (horizontal)\n * @type Number\n * @default\n */\n scaleX: 1,\n\n /**\n * Object scale factor (vertical)\n * @type Number\n * @default\n */\n scaleY: 1,\n\n /**\n * When true, an object is rendered as flipped horizontally\n * @type Boolean\n * @default\n */\n flipX: false,\n\n /**\n * When true, an object is rendered as flipped vertically\n * @type Boolean\n * @default\n */\n flipY: false,\n\n /**\n * Opacity of an object\n * @type Number\n * @default\n */\n opacity: 1,\n\n /**\n * Angle of rotation of an object (in degrees)\n * @type Number\n * @default\n */\n angle: 0,\n\n /**\n * Angle of skew on x axes of an object (in degrees)\n * @type Number\n * @default\n */\n skewX: 0,\n\n /**\n * Angle of skew on y axes of an object (in degrees)\n * @type Number\n * @default\n */\n skewY: 0,\n\n /**\n * Size of object's controlling corners (in pixels)\n * @type Number\n * @default\n */\n cornerSize: 13,\n\n /**\n * When true, object's controlling corners are rendered as transparent inside (i.e. stroke instead of fill)\n * @type Boolean\n * @default\n */\n transparentCorners: true,\n\n /**\n * Default cursor value used when hovering over this object on canvas\n * @type String\n * @default\n */\n hoverCursor: null,\n\n /**\n * Default cursor value used when moving this object on canvas\n * @type String\n * @default\n */\n moveCursor: null,\n\n /**\n * Padding between object and its controlling borders (in pixels)\n * @type Number\n * @default\n */\n padding: 0,\n\n /**\n * Color of controlling borders of an object (when it's active)\n * @type String\n * @default\n */\n borderColor: 'rgba(102,153,255,0.75)',\n\n /**\n * Array specifying dash pattern of an object's borders (hasBorder must be true)\n * @since 1.6.2\n * @type Array\n */\n borderDashArray: null,\n\n /**\n * Color of controlling corners of an object (when it's active)\n * @type String\n * @default\n */\n cornerColor: 'rgba(102,153,255,0.5)',\n\n /**\n * Color of controlling corners of an object (when it's active and transparentCorners false)\n * @since 1.6.2\n * @type String\n * @default\n */\n cornerStrokeColor: null,\n\n /**\n * Specify style of control, 'rect' or 'circle'\n * @since 1.6.2\n * @type String\n */\n cornerStyle: 'rect',\n\n /**\n * Array specifying dash pattern of an object's control (hasBorder must be true)\n * @since 1.6.2\n * @type Array\n */\n cornerDashArray: null,\n\n /**\n * When true, this object will use center point as the origin of transformation\n * when being scaled via the controls.\n * Backwards incompatibility note: This property replaces \"centerTransform\" (Boolean).\n * @since 1.3.4\n * @type Boolean\n * @default\n */\n centeredScaling: false,\n\n /**\n * When true, this object will use center point as the origin of transformation\n * when being rotated via the controls.\n * Backwards incompatibility note: This property replaces \"centerTransform\" (Boolean).\n * @since 1.3.4\n * @type Boolean\n * @default\n */\n centeredRotation: true,\n\n /**\n * Color of object's fill\n * takes css colors https://www.w3.org/TR/css-color-3/\n * @type String\n * @default\n */\n fill: 'rgb(0,0,0)',\n\n /**\n * Fill rule used to fill an object\n * accepted values are nonzero, evenodd\n * Backwards incompatibility note: This property was used for setting globalCompositeOperation until v1.4.12 (use `fabric.Object#globalCompositeOperation` instead)\n * @type String\n * @default\n */\n fillRule: 'nonzero',\n\n /**\n * Composite rule used for canvas globalCompositeOperation\n * @type String\n * @default\n */\n globalCompositeOperation: 'source-over',\n\n /**\n * Background color of an object.\n * takes css colors https://www.w3.org/TR/css-color-3/\n * @type String\n * @default\n */\n backgroundColor: '',\n\n /**\n * Selection Background color of an object. colored layer behind the object when it is active.\n * does not mix good with globalCompositeOperation methods.\n * @type String\n * @default\n */\n selectionBackgroundColor: '',\n\n /**\n * When defined, an object is rendered via stroke and this property specifies its color\n * takes css colors https://www.w3.org/TR/css-color-3/\n * @type String\n * @default\n */\n stroke: null,\n\n /**\n * Width of a stroke used to render this object\n * @type Number\n * @default\n */\n strokeWidth: 1,\n\n /**\n * Array specifying dash pattern of an object's stroke (stroke must be defined)\n * @type Array\n */\n strokeDashArray: null,\n\n /**\n * Line offset of an object's stroke\n * @type Number\n * @default\n */\n strokeDashOffset: 0,\n\n /**\n * Line endings style of an object's stroke (one of \"butt\", \"round\", \"square\")\n * @type String\n * @default\n */\n strokeLineCap: 'butt',\n\n /**\n * Corner style of an object's stroke (one of \"bevil\", \"round\", \"miter\")\n * @type String\n * @default\n */\n strokeLineJoin: 'miter',\n\n /**\n * Maximum miter length (used for strokeLineJoin = \"miter\") of an object's stroke\n * @type Number\n * @default\n */\n strokeMiterLimit: 4,\n\n /**\n * Shadow object representing shadow of this shape\n * @type fabric.Shadow\n * @default\n */\n shadow: null,\n\n /**\n * Opacity of object's controlling borders when object is active and moving\n * @type Number\n * @default\n */\n borderOpacityWhenMoving: 0.4,\n\n /**\n * Scale factor of object's controlling borders\n * bigger number will make a thicker border\n * border is 1, so this is basically a border tickness\n * since there is no way to change the border itself.\n * @type Number\n * @default\n */\n borderScaleFactor: 1,\n\n /**\n * Transform matrix (similar to SVG's transform matrix)\n * This property has been depreacted. Since caching and and qrDecompose this\n * property can be handled with the standard top,left,scaleX,scaleY,angle and skewX.\n * A documentation example on how to parse and merge a transformMatrix will be provided before\n * completely removing it in fabric 4.0\n * If you are starting a project now, DO NOT use it.\n * @deprecated since 3.2.0\n * @type Array\n */\n transformMatrix: null,\n\n /**\n * Minimum allowed scale value of an object\n * @type Number\n * @default\n */\n minScaleLimit: 0,\n\n /**\n * When set to `false`, an object can not be selected for modification (using either point-click-based or group-based selection).\n * But events still fire on it.\n * @type Boolean\n * @default\n */\n selectable: true,\n\n /**\n * When set to `false`, an object can not be a target of events. All events propagate through it. Introduced in v1.3.4\n * @type Boolean\n * @default\n */\n evented: true,\n\n /**\n * When set to `false`, an object is not rendered on canvas\n * @type Boolean\n * @default\n */\n visible: true,\n\n /**\n * When set to `false`, object's controls are not displayed and can not be used to manipulate object\n * @type Boolean\n * @default\n */\n hasControls: true,\n\n /**\n * When set to `false`, object's controlling borders are not rendered\n * @type Boolean\n * @default\n */\n hasBorders: true,\n\n /**\n * When set to `false`, object's controlling rotating point will not be visible or selectable\n * @type Boolean\n * @default\n */\n hasRotatingPoint: true,\n\n /**\n * Offset for object's controlling rotating point (when enabled via `hasRotatingPoint`)\n * @type Number\n * @default\n */\n rotatingPointOffset: 40,\n\n /**\n * When set to `true`, objects are \"found\" on canvas on per-pixel basis rather than according to bounding box\n * @type Boolean\n * @default\n */\n perPixelTargetFind: false,\n\n /**\n * When `false`, default object's values are not included in its serialization\n * @type Boolean\n * @default\n */\n includeDefaultValues: true,\n\n /**\n * Function that determines clipping of an object (context is passed as a first argument).\n * If you are using code minification, ctx argument can be minified/manglied you should use\n * as a workaround `var ctx = arguments[0];` in the function;\n * Note that context origin is at the object's center point (not left/top corner)\n * @deprecated since 2.0.0\n * @type Function\n */\n clipTo: null,\n\n /**\n * When `true`, object horizontal movement is locked\n * @type Boolean\n * @default\n */\n lockMovementX: false,\n\n /**\n * When `true`, object vertical movement is locked\n * @type Boolean\n * @default\n */\n lockMovementY: false,\n\n /**\n * When `true`, object rotation is locked\n * @type Boolean\n * @default\n */\n lockRotation: false,\n\n /**\n * When `true`, object horizontal scaling is locked\n * @type Boolean\n * @default\n */\n lockScalingX: false,\n\n /**\n * When `true`, object vertical scaling is locked\n * @type Boolean\n * @default\n */\n lockScalingY: false,\n\n /**\n * When `true`, object non-uniform scaling is locked\n * @type Boolean\n * @default\n */\n lockUniScaling: false,\n\n /**\n * When `true`, object horizontal skewing is locked\n * @type Boolean\n * @default\n */\n lockSkewingX: false,\n\n /**\n * When `true`, object vertical skewing is locked\n * @type Boolean\n * @default\n */\n lockSkewingY: false,\n\n /**\n * When `true`, object cannot be flipped by scaling into negative values\n * @type Boolean\n * @default\n */\n lockScalingFlip: false,\n\n /**\n * When `true`, object is not exported in OBJECT/JSON\n * @since 1.6.3\n * @type Boolean\n * @default\n */\n excludeFromExport: false,\n\n /**\n * When `true`, object is cached on an additional canvas.\n * When `false`, object is not cached unless necessary ( clipPath )\n * default to true\n * @since 1.7.0\n * @type Boolean\n * @default true\n */\n objectCaching: objectCaching,\n\n /**\n * When `true`, object properties are checked for cache invalidation. In some particular\n * situation you may want this to be disabled ( spray brush, very big, groups)\n * or if your application does not allow you to modify properties for groups child you want\n * to disable it for groups.\n * default to false\n * since 1.7.0\n * @type Boolean\n * @default false\n */\n statefullCache: false,\n\n /**\n * When `true`, cache does not get updated during scaling. The picture will get blocky if scaled\n * too much and will be redrawn with correct details at the end of scaling.\n * this setting is performance and application dependant.\n * default to true\n * since 1.7.0\n * @type Boolean\n * @default true\n */\n noScaleCache: true,\n\n /**\n * When `false`, the stoke width will scale with the object.\n * When `true`, the stroke will always match the exact pixel size entered for stroke width.\n * default to false\n * @since 2.6.0\n * @type Boolean\n * @default false\n * @type Boolean\n * @default false\n */\n strokeUniform: false,\n\n /**\n * When set to `true`, object's cache will be rerendered next render call.\n * since 1.7.0\n * @type Boolean\n * @default true\n */\n dirty: true,\n\n /**\n * keeps the value of the last hovered corner during mouse move.\n * 0 is no corner, or 'mt', 'ml', 'mtr' etc..\n * It should be private, but there is no harm in using it as\n * a read-only property.\n * @type number|string|any\n * @default 0\n */\n __corner: 0,\n\n /**\n * Determines if the fill or the stroke is drawn first (one of \"fill\" or \"stroke\")\n * @type String\n * @default\n */\n paintFirst: 'fill',\n\n /**\n * List of properties to consider when checking if state\n * of an object is changed (fabric.Object#hasStateChanged)\n * as well as for history (undo/redo) purposes\n * @type Array\n */\n stateProperties: (\n 'top left width height scaleX scaleY flipX flipY originX originY transformMatrix ' +\n 'stroke strokeWidth strokeDashArray strokeLineCap strokeDashOffset strokeLineJoin strokeMiterLimit ' +\n 'angle opacity fill globalCompositeOperation shadow clipTo visible backgroundColor ' +\n 'skewX skewY fillRule paintFirst clipPath strokeUniform'\n ).split(' '),\n\n /**\n * List of properties to consider when checking if cache needs refresh\n * Those properties are checked by statefullCache ON ( or lazy mode if we want ) or from single\n * calls to Object.set(key, value). If the key is in this list, the object is marked as dirty\n * and refreshed at the next render\n * @type Array\n */\n cacheProperties: (\n 'fill stroke strokeWidth strokeDashArray width height paintFirst strokeUniform' +\n ' strokeLineCap strokeDashOffset strokeLineJoin strokeMiterLimit backgroundColor clipPath'\n ).split(' '),\n\n /**\n * a fabricObject that, without stroke define a clipping area with their shape. filled in black\n * the clipPath object gets used when the object has rendered, and the context is placed in the center\n * of the object cacheCanvas.\n * If you want 0,0 of a clipPath to align with an object center, use clipPath.originX/Y to 'center'\n * @type fabric.Object\n */\n clipPath: undefined,\n\n /**\n * Meaningful ONLY when the object is used as clipPath.\n * if true, the clipPath will make the object clip to the outside of the clipPath\n * since 2.4.0\n * @type boolean\n * @default false\n */\n inverted: false,\n\n /**\n * Meaningful ONLY when the object is used as clipPath.\n * if true, the clipPath will have its top and left relative to canvas, and will\n * not be influenced by the object transform. This will make the clipPath relative\n * to the canvas, but clipping just a particular object.\n * WARNING this is beta, this feature may change or be renamed.\n * since 2.4.0\n * @type boolean\n * @default false\n */\n absolutePositioned: false,\n\n /**\n * Constructor\n * @param {Object} [options] Options object\n */\n initialize: function(options) {\n if (options) {\n this.setOptions(options);\n }\n },\n\n /**\n * Create a the canvas used to keep the cached copy of the object\n * @private\n */\n _createCacheCanvas: function() {\n this._cacheProperties = {};\n this._cacheCanvas = fabric.util.createCanvasElement();\n this._cacheContext = this._cacheCanvas.getContext('2d');\n this._updateCacheCanvas();\n // if canvas gets created, is empty, so dirty.\n this.dirty = true;\n },\n\n /**\n * Limit the cache dimensions so that X * Y do not cross fabric.perfLimitSizeTotal\n * and each side do not cross fabric.cacheSideLimit\n * those numbers are configurable so that you can get as much detail as you want\n * making bargain with performances.\n * @param {Object} dims\n * @param {Object} dims.width width of canvas\n * @param {Object} dims.height height of canvas\n * @param {Object} dims.zoomX zoomX zoom value to unscale the canvas before drawing cache\n * @param {Object} dims.zoomY zoomY zoom value to unscale the canvas before drawing cache\n * @return {Object}.width width of canvas\n * @return {Object}.height height of canvas\n * @return {Object}.zoomX zoomX zoom value to unscale the canvas before drawing cache\n * @return {Object}.zoomY zoomY zoom value to unscale the canvas before drawing cache\n */\n _limitCacheSize: function(dims) {\n var perfLimitSizeTotal = fabric.perfLimitSizeTotal,\n width = dims.width, height = dims.height,\n max = fabric.maxCacheSideLimit, min = fabric.minCacheSideLimit;\n if (width <= max && height <= max && width * height <= perfLimitSizeTotal) {\n if (width < min) {\n dims.width = min;\n }\n if (height < min) {\n dims.height = min;\n }\n return dims;\n }\n var ar = width / height, limitedDims = fabric.util.limitDimsByArea(ar, perfLimitSizeTotal),\n capValue = fabric.util.capValue,\n x = capValue(min, limitedDims.x, max),\n y = capValue(min, limitedDims.y, max);\n if (width > x) {\n dims.zoomX /= width / x;\n dims.width = x;\n dims.capped = true;\n }\n if (height > y) {\n dims.zoomY /= height / y;\n dims.height = y;\n dims.capped = true;\n }\n return dims;\n },\n\n /**\n * Return the dimension and the zoom level needed to create a cache canvas\n * big enough to host the object to be cached.\n * @private\n * @return {Object}.x width of object to be cached\n * @return {Object}.y height of object to be cached\n * @return {Object}.width width of canvas\n * @return {Object}.height height of canvas\n * @return {Object}.zoomX zoomX zoom value to unscale the canvas before drawing cache\n * @return {Object}.zoomY zoomY zoom value to unscale the canvas before drawing cache\n */\n _getCacheCanvasDimensions: function() {\n var objectScale = this.getTotalObjectScaling(),\n // caculate dimensions without skewing\n dim = this._getTransformedDimensions(0, 0),\n neededX = dim.x * objectScale.scaleX / this.scaleX,\n neededY = dim.y * objectScale.scaleY / this.scaleY;\n return {\n // for sure this ALIASING_LIMIT is slightly creating problem\n // in situation in which the cache canvas gets an upper limit\n // also objectScale contains already scaleX and scaleY\n width: neededX + ALIASING_LIMIT,\n height: neededY + ALIASING_LIMIT,\n zoomX: objectScale.scaleX,\n zoomY: objectScale.scaleY,\n x: neededX,\n y: neededY\n };\n },\n\n /**\n * Update width and height of the canvas for cache\n * returns true or false if canvas needed resize.\n * @private\n * @return {Boolean} true if the canvas has been resized\n */\n _updateCacheCanvas: function() {\n var targetCanvas = this.canvas;\n if (this.noScaleCache && targetCanvas && targetCanvas._currentTransform) {\n var target = targetCanvas._currentTransform.target,\n action = targetCanvas._currentTransform.action;\n if (this === target && action.slice && action.slice(0, 5) === 'scale') {\n return false;\n }\n }\n var canvas = this._cacheCanvas,\n dims = this._limitCacheSize(this._getCacheCanvasDimensions()),\n minCacheSize = fabric.minCacheSideLimit,\n width = dims.width, height = dims.height, drawingWidth, drawingHeight,\n zoomX = dims.zoomX, zoomY = dims.zoomY,\n dimensionsChanged = width !== this.cacheWidth || height !== this.cacheHeight,\n zoomChanged = this.zoomX !== zoomX || this.zoomY !== zoomY,\n shouldRedraw = dimensionsChanged || zoomChanged,\n additionalWidth = 0, additionalHeight = 0, shouldResizeCanvas = false;\n if (dimensionsChanged) {\n var canvasWidth = this._cacheCanvas.width,\n canvasHeight = this._cacheCanvas.height,\n sizeGrowing = width > canvasWidth || height > canvasHeight,\n sizeShrinking = (width < canvasWidth * 0.9 || height < canvasHeight * 0.9) &&\n canvasWidth > minCacheSize && canvasHeight > minCacheSize;\n shouldResizeCanvas = sizeGrowing || sizeShrinking;\n if (sizeGrowing && !dims.capped && (width > minCacheSize || height > minCacheSize)) {\n additionalWidth = width * 0.1;\n additionalHeight = height * 0.1;\n }\n }\n if (shouldRedraw) {\n if (shouldResizeCanvas) {\n canvas.width = Math.ceil(width + additionalWidth);\n canvas.height = Math.ceil(height + additionalHeight);\n }\n else {\n this._cacheContext.setTransform(1, 0, 0, 1, 0, 0);\n this._cacheContext.clearRect(0, 0, canvas.width, canvas.height);\n }\n drawingWidth = dims.x / 2;\n drawingHeight = dims.y / 2;\n this.cacheTranslationX = Math.round(canvas.width / 2 - drawingWidth) + drawingWidth;\n this.cacheTranslationY = Math.round(canvas.height / 2 - drawingHeight) + drawingHeight;\n this.cacheWidth = width;\n this.cacheHeight = height;\n this._cacheContext.translate(this.cacheTranslationX, this.cacheTranslationY);\n this._cacheContext.scale(zoomX, zoomY);\n this.zoomX = zoomX;\n this.zoomY = zoomY;\n return true;\n }\n return false;\n },\n\n /**\n * Sets object's properties from options\n * @param {Object} [options] Options object\n */\n setOptions: function(options) {\n this._setOptions(options);\n this._initGradient(options.fill, 'fill');\n this._initGradient(options.stroke, 'stroke');\n this._initClipping(options);\n this._initPattern(options.fill, 'fill');\n this._initPattern(options.stroke, 'stroke');\n },\n\n /**\n * Transforms context when rendering an object\n * @param {CanvasRenderingContext2D} ctx Context\n */\n transform: function(ctx) {\n var m;\n if (this.group && !this.group._transformDone) {\n m = this.calcTransformMatrix();\n }\n else {\n m = this.calcOwnMatrix();\n }\n ctx.transform(m[0], m[1], m[2], m[3], m[4], m[5]);\n },\n\n /**\n * Returns an object representation of an instance\n * @param {Array} [propertiesToInclude] Any properties that you might want to additionally include in the output\n * @return {Object} Object representation of an instance\n */\n toObject: function(propertiesToInclude) {\n var NUM_FRACTION_DIGITS = fabric.Object.NUM_FRACTION_DIGITS,\n\n object = {\n type: this.type,\n version: fabric.version,\n originX: this.originX,\n originY: this.originY,\n left: toFixed(this.left, NUM_FRACTION_DIGITS),\n top: toFixed(this.top, NUM_FRACTION_DIGITS),\n width: toFixed(this.width, NUM_FRACTION_DIGITS),\n height: toFixed(this.height, NUM_FRACTION_DIGITS),\n fill: (this.fill && this.fill.toObject) ? this.fill.toObject() : this.fill,\n stroke: (this.stroke && this.stroke.toObject) ? this.stroke.toObject() : this.stroke,\n strokeWidth: toFixed(this.strokeWidth, NUM_FRACTION_DIGITS),\n strokeDashArray: this.strokeDashArray ? this.strokeDashArray.concat() : this.strokeDashArray,\n strokeLineCap: this.strokeLineCap,\n strokeDashOffset: this.strokeDashOffset,\n strokeLineJoin: this.strokeLineJoin,\n // TODO: add this before release\n // strokeUniform: this.strokeUniform,\n strokeMiterLimit: toFixed(this.strokeMiterLimit, NUM_FRACTION_DIGITS),\n scaleX: toFixed(this.scaleX, NUM_FRACTION_DIGITS),\n scaleY: toFixed(this.scaleY, NUM_FRACTION_DIGITS),\n angle: toFixed(this.angle, NUM_FRACTION_DIGITS),\n flipX: this.flipX,\n flipY: this.flipY,\n opacity: toFixed(this.opacity, NUM_FRACTION_DIGITS),\n shadow: (this.shadow && this.shadow.toObject) ? this.shadow.toObject() : this.shadow,\n visible: this.visible,\n clipTo: this.clipTo && String(this.clipTo),\n backgroundColor: this.backgroundColor,\n fillRule: this.fillRule,\n paintFirst: this.paintFirst,\n globalCompositeOperation: this.globalCompositeOperation,\n transformMatrix: this.transformMatrix ? this.transformMatrix.concat() : null,\n skewX: toFixed(this.skewX, NUM_FRACTION_DIGITS),\n skewY: toFixed(this.skewY, NUM_FRACTION_DIGITS),\n };\n\n if (this.clipPath) {\n object.clipPath = this.clipPath.toObject(propertiesToInclude);\n object.clipPath.inverted = this.clipPath.inverted;\n object.clipPath.absolutePositioned = this.clipPath.absolutePositioned;\n }\n\n fabric.util.populateWithProperties(this, object, propertiesToInclude);\n if (!this.includeDefaultValues) {\n object = this._removeDefaultValues(object);\n }\n\n return object;\n },\n\n /**\n * Returns (dataless) object representation of an instance\n * @param {Array} [propertiesToInclude] Any properties that you might want to additionally include in the output\n * @return {Object} Object representation of an instance\n */\n toDatalessObject: function(propertiesToInclude) {\n // will be overwritten by subclasses\n return this.toObject(propertiesToInclude);\n },\n\n /**\n * @private\n * @param {Object} object\n */\n _removeDefaultValues: function(object) {\n var prototype = fabric.util.getKlass(object.type).prototype,\n stateProperties = prototype.stateProperties;\n stateProperties.forEach(function(prop) {\n if (prop === 'left' || prop === 'top') {\n return;\n }\n if (object[prop] === prototype[prop]) {\n delete object[prop];\n }\n var isArray = Object.prototype.toString.call(object[prop]) === '[object Array]' &&\n Object.prototype.toString.call(prototype[prop]) === '[object Array]';\n\n // basically a check for [] === []\n if (isArray && object[prop].length === 0 && prototype[prop].length === 0) {\n delete object[prop];\n }\n });\n\n return object;\n },\n\n /**\n * Returns a string representation of an instance\n * @return {String}\n */\n toString: function() {\n return '#';\n },\n\n /**\n * Return the object scale factor counting also the group scaling\n * @return {Object} object with scaleX and scaleY properties\n */\n getObjectScaling: function() {\n var options = fabric.util.qrDecompose(this.calcTransformMatrix());\n return { scaleX: Math.abs(options.scaleX), scaleY: Math.abs(options.scaleY) };\n },\n\n /**\n * Return the object scale factor counting also the group scaling, zoom and retina\n * @return {Object} object with scaleX and scaleY properties\n */\n getTotalObjectScaling: function() {\n var scale = this.getObjectScaling(), scaleX = scale.scaleX, scaleY = scale.scaleY;\n if (this.canvas) {\n var zoom = this.canvas.getZoom();\n var retina = this.canvas.getRetinaScaling();\n scaleX *= zoom * retina;\n scaleY *= zoom * retina;\n }\n return { scaleX: scaleX, scaleY: scaleY };\n },\n\n /**\n * Return the object opacity counting also the group property\n * @return {Number}\n */\n getObjectOpacity: function() {\n var opacity = this.opacity;\n if (this.group) {\n opacity *= this.group.getObjectOpacity();\n }\n return opacity;\n },\n\n /**\n * @private\n * @param {String} key\n * @param {*} value\n * @return {fabric.Object} thisArg\n */\n _set: function(key, value) {\n var shouldConstrainValue = (key === 'scaleX' || key === 'scaleY'),\n isChanged = this[key] !== value, groupNeedsUpdate = false;\n\n if (shouldConstrainValue) {\n value = this._constrainScale(value);\n }\n if (key === 'scaleX' && value < 0) {\n this.flipX = !this.flipX;\n value *= -1;\n }\n else if (key === 'scaleY' && value < 0) {\n this.flipY = !this.flipY;\n value *= -1;\n }\n else if (key === 'shadow' && value && !(value instanceof fabric.Shadow)) {\n value = new fabric.Shadow(value);\n }\n else if (key === 'dirty' && this.group) {\n this.group.set('dirty', value);\n }\n\n this[key] = value;\n\n if (isChanged) {\n groupNeedsUpdate = this.group && this.group.isOnACache();\n if (this.cacheProperties.indexOf(key) > -1) {\n this.dirty = true;\n groupNeedsUpdate && this.group.set('dirty', true);\n }\n else if (groupNeedsUpdate && this.stateProperties.indexOf(key) > -1) {\n this.group.set('dirty', true);\n }\n }\n\n return this;\n },\n\n /**\n * This callback function is called by the parent group of an object every\n * time a non-delegated property changes on the group. It is passed the key\n * and value as parameters. Not adding in this function's signature to avoid\n * Travis build error about unused variables.\n */\n setOnGroup: function() {\n // implemented by sub-classes, as needed.\n },\n\n /**\n * Retrieves viewportTransform from Object's canvas if possible\n * @method getViewportTransform\n * @memberOf fabric.Object.prototype\n * @return {Array}\n */\n getViewportTransform: function() {\n if (this.canvas && this.canvas.viewportTransform) {\n return this.canvas.viewportTransform;\n }\n return fabric.iMatrix.concat();\n },\n\n /*\n * @private\n * return if the object would be visible in rendering\n * @memberOf fabric.Object.prototype\n * @return {Boolean}\n */\n isNotVisible: function() {\n return this.opacity === 0 ||\n (this.width === 0 && this.height === 0 && this.strokeWidth === 0) ||\n !this.visible;\n },\n\n /**\n * Renders an object on a specified context\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n render: function(ctx) {\n // do not render if width/height are zeros or object is not visible\n if (this.isNotVisible()) {\n return;\n }\n if (this.canvas && this.canvas.skipOffscreen && !this.group && !this.isOnScreen()) {\n return;\n }\n ctx.save();\n this._setupCompositeOperation(ctx);\n this.drawSelectionBackground(ctx);\n this.transform(ctx);\n this._setOpacity(ctx);\n this._setShadow(ctx, this);\n if (this.transformMatrix) {\n ctx.transform.apply(ctx, this.transformMatrix);\n }\n this.clipTo && fabric.util.clipContext(this, ctx);\n if (this.shouldCache()) {\n this.renderCache();\n this.drawCacheOnCanvas(ctx);\n }\n else {\n this._removeCacheCanvas();\n this.dirty = false;\n this.drawObject(ctx);\n if (this.objectCaching && this.statefullCache) {\n this.saveState({ propertySet: 'cacheProperties' });\n }\n }\n this.clipTo && ctx.restore();\n ctx.restore();\n },\n\n renderCache: function(options) {\n options = options || {};\n if (!this._cacheCanvas) {\n this._createCacheCanvas();\n }\n if (this.isCacheDirty()) {\n this.statefullCache && this.saveState({ propertySet: 'cacheProperties' });\n this.drawObject(this._cacheContext, options.forClipping);\n this.dirty = false;\n }\n },\n\n /**\n * Remove cacheCanvas and its dimensions from the objects\n */\n _removeCacheCanvas: function() {\n this._cacheCanvas = null;\n this.cacheWidth = 0;\n this.cacheHeight = 0;\n },\n\n /**\n * return true if the object will draw a stroke\n * Does not consider text styles. This is just a shortcut used at rendering time\n * We want it to be an aproximation and be fast.\n * wrote to avoid extra caching, it has to return true when stroke happens,\n * can guess when it will not happen at 100% chance, does not matter if it misses\n * some use case where the stroke is invisible.\n * @since 3.0.0\n * @returns Boolean\n */\n hasStroke: function() {\n return this.stroke && this.stroke !== 'transparent' && this.strokeWidth !== 0;\n },\n\n /**\n * return true if the object will draw a fill\n * Does not consider text styles. This is just a shortcut used at rendering time\n * We want it to be an aproximation and be fast.\n * wrote to avoid extra caching, it has to return true when fill happens,\n * can guess when it will not happen at 100% chance, does not matter if it misses\n * some use case where the fill is invisible.\n * @since 3.0.0\n * @returns Boolean\n */\n hasFill: function() {\n return this.fill && this.fill !== 'transparent';\n },\n\n /**\n * When set to `true`, force the object to have its own cache, even if it is inside a group\n * it may be needed when your object behave in a particular way on the cache and always needs\n * its own isolated canvas to render correctly.\n * Created to be overridden\n * since 1.7.12\n * @returns Boolean\n */\n needsItsOwnCache: function() {\n if (this.paintFirst === 'stroke' &&\n this.hasFill() && this.hasStroke() && typeof this.shadow === 'object') {\n return true;\n }\n if (this.clipPath) {\n return true;\n }\n return false;\n },\n\n /**\n * Decide if the object should cache or not. Create its own cache level\n * objectCaching is a global flag, wins over everything\n * needsItsOwnCache should be used when the object drawing method requires\n * a cache step. None of the fabric classes requires it.\n * Generally you do not cache objects in groups because the group outside is cached.\n * Read as: cache if is needed, or if the feature is enabled but we are not already caching.\n * @return {Boolean}\n */\n shouldCache: function() {\n this.ownCaching = this.needsItsOwnCache() || (\n this.objectCaching &&\n (!this.group || !this.group.isOnACache())\n );\n return this.ownCaching;\n },\n\n /**\n * Check if this object or a child object will cast a shadow\n * used by Group.shouldCache to know if child has a shadow recursively\n * @return {Boolean}\n */\n willDrawShadow: function() {\n return !!this.shadow && (this.shadow.offsetX !== 0 || this.shadow.offsetY !== 0);\n },\n\n /**\n * Execute the drawing operation for an object clipPath\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n drawClipPathOnCache: function(ctx) {\n var path = this.clipPath;\n ctx.save();\n // DEBUG: uncomment this line, comment the following\n // ctx.globalAlpha = 0.4\n if (path.inverted) {\n ctx.globalCompositeOperation = 'destination-out';\n }\n else {\n ctx.globalCompositeOperation = 'destination-in';\n }\n //ctx.scale(1 / 2, 1 / 2);\n if (path.absolutePositioned) {\n var m = fabric.util.invertTransform(this.calcTransformMatrix());\n ctx.transform(m[0], m[1], m[2], m[3], m[4], m[5]);\n }\n path.transform(ctx);\n ctx.scale(1 / path.zoomX, 1 / path.zoomY);\n ctx.drawImage(path._cacheCanvas, -path.cacheTranslationX, -path.cacheTranslationY);\n ctx.restore();\n },\n\n /**\n * Execute the drawing operation for an object on a specified context\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n drawObject: function(ctx, forClipping) {\n var originalFill = this.fill, originalStroke = this.stroke;\n if (forClipping) {\n this.fill = 'black';\n this.stroke = '';\n this._setClippingProperties(ctx);\n }\n else {\n this._renderBackground(ctx);\n this._setStrokeStyles(ctx, this);\n this._setFillStyles(ctx, this);\n }\n this._render(ctx);\n this._drawClipPath(ctx);\n this.fill = originalFill;\n this.stroke = originalStroke;\n },\n\n _drawClipPath: function(ctx) {\n var path = this.clipPath;\n if (!path) { return; }\n // needed to setup a couple of variables\n // path canvas gets overridden with this one.\n // TODO find a better solution?\n path.canvas = this.canvas;\n path.shouldCache();\n path._transformDone = true;\n path.renderCache({ forClipping: true });\n this.drawClipPathOnCache(ctx);\n },\n\n /**\n * Paint the cached copy of the object on the target context.\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n drawCacheOnCanvas: function(ctx) {\n ctx.scale(1 / this.zoomX, 1 / this.zoomY);\n ctx.drawImage(this._cacheCanvas, -this.cacheTranslationX, -this.cacheTranslationY);\n },\n\n /**\n * Check if cache is dirty\n * @param {Boolean} skipCanvas skip canvas checks because this object is painted\n * on parent canvas.\n */\n isCacheDirty: function(skipCanvas) {\n if (this.isNotVisible()) {\n return false;\n }\n if (this._cacheCanvas && !skipCanvas && this._updateCacheCanvas()) {\n // in this case the context is already cleared.\n return true;\n }\n else {\n if (this.dirty ||\n (this.clipPath && this.clipPath.absolutePositioned) ||\n (this.statefullCache && this.hasStateChanged('cacheProperties'))\n ) {\n if (this._cacheCanvas && !skipCanvas) {\n var width = this.cacheWidth / this.zoomX;\n var height = this.cacheHeight / this.zoomY;\n this._cacheContext.clearRect(-width / 2, -height / 2, width, height);\n }\n return true;\n }\n }\n return false;\n },\n\n /**\n * Draws a background for the object big as its untransformed dimensions\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _renderBackground: function(ctx) {\n if (!this.backgroundColor) {\n return;\n }\n var dim = this._getNonTransformedDimensions();\n ctx.fillStyle = this.backgroundColor;\n\n ctx.fillRect(\n -dim.x / 2,\n -dim.y / 2,\n dim.x,\n dim.y\n );\n // if there is background color no other shadows\n // should be casted\n this._removeShadow(ctx);\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _setOpacity: function(ctx) {\n if (this.group && !this.group._transformDone) {\n ctx.globalAlpha = this.getObjectOpacity();\n }\n else {\n ctx.globalAlpha *= this.opacity;\n }\n },\n\n _setStrokeStyles: function(ctx, decl) {\n if (decl.stroke) {\n ctx.lineWidth = decl.strokeWidth;\n ctx.lineCap = decl.strokeLineCap;\n ctx.lineDashOffset = decl.strokeDashOffset;\n ctx.lineJoin = decl.strokeLineJoin;\n ctx.miterLimit = decl.strokeMiterLimit;\n ctx.strokeStyle = decl.stroke.toLive\n ? decl.stroke.toLive(ctx, this)\n : decl.stroke;\n }\n },\n\n _setFillStyles: function(ctx, decl) {\n if (decl.fill) {\n ctx.fillStyle = decl.fill.toLive\n ? decl.fill.toLive(ctx, this)\n : decl.fill;\n }\n },\n\n _setClippingProperties: function(ctx) {\n ctx.globalAlpha = 1;\n ctx.strokeStyle = 'transparent';\n ctx.fillStyle = '#000000';\n },\n\n /**\n * @private\n * Sets line dash\n * @param {CanvasRenderingContext2D} ctx Context to set the dash line on\n * @param {Array} dashArray array representing dashes\n * @param {Function} alternative function to call if browser does not support lineDash\n */\n _setLineDash: function(ctx, dashArray, alternative) {\n if (!dashArray || dashArray.length === 0) {\n return;\n }\n // Spec requires the concatenation of two copies the dash list when the number of elements is odd\n if (1 & dashArray.length) {\n dashArray.push.apply(dashArray, dashArray);\n }\n if (supportsLineDash) {\n ctx.setLineDash(dashArray);\n }\n else {\n alternative && alternative(ctx);\n }\n },\n\n /**\n * Renders controls and borders for the object\n * @param {CanvasRenderingContext2D} ctx Context to render on\n * @param {Object} [styleOverride] properties to override the object style\n */\n _renderControls: function(ctx, styleOverride) {\n var vpt = this.getViewportTransform(),\n matrix = this.calcTransformMatrix(),\n options, drawBorders, drawControls;\n styleOverride = styleOverride || { };\n drawBorders = typeof styleOverride.hasBorders !== 'undefined' ? styleOverride.hasBorders : this.hasBorders;\n drawControls = typeof styleOverride.hasControls !== 'undefined' ? styleOverride.hasControls : this.hasControls;\n matrix = fabric.util.multiplyTransformMatrices(vpt, matrix);\n options = fabric.util.qrDecompose(matrix);\n ctx.save();\n ctx.translate(options.translateX, options.translateY);\n ctx.lineWidth = 1 * this.borderScaleFactor;\n if (!this.group) {\n ctx.globalAlpha = this.isMoving ? this.borderOpacityWhenMoving : 1;\n }\n if (styleOverride.forActiveSelection) {\n ctx.rotate(degreesToRadians(options.angle));\n drawBorders && this.drawBordersInGroup(ctx, options, styleOverride);\n }\n else {\n ctx.rotate(degreesToRadians(this.angle));\n drawBorders && this.drawBorders(ctx, styleOverride);\n }\n drawControls && this.drawControls(ctx, styleOverride);\n ctx.restore();\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _setShadow: function(ctx) {\n if (!this.shadow) {\n return;\n }\n\n var shadow = this.shadow, canvas = this.canvas, scaling,\n multX = (canvas && canvas.viewportTransform[0]) || 1,\n multY = (canvas && canvas.viewportTransform[3]) || 1;\n if (shadow.nonScaling) {\n scaling = { scaleX: 1, scaleY: 1 };\n }\n else {\n scaling = this.getObjectScaling();\n }\n if (canvas && canvas._isRetinaScaling()) {\n multX *= fabric.devicePixelRatio;\n multY *= fabric.devicePixelRatio;\n }\n ctx.shadowColor = shadow.color;\n ctx.shadowBlur = shadow.blur * fabric.browserShadowBlurConstant *\n (multX + multY) * (scaling.scaleX + scaling.scaleY) / 4;\n ctx.shadowOffsetX = shadow.offsetX * multX * scaling.scaleX;\n ctx.shadowOffsetY = shadow.offsetY * multY * scaling.scaleY;\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _removeShadow: function(ctx) {\n if (!this.shadow) {\n return;\n }\n\n ctx.shadowColor = '';\n ctx.shadowBlur = ctx.shadowOffsetX = ctx.shadowOffsetY = 0;\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n * @param {Object} filler fabric.Pattern or fabric.Gradient\n * @return {Object} offset.offsetX offset for text rendering\n * @return {Object} offset.offsetY offset for text rendering\n */\n _applyPatternGradientTransform: function(ctx, filler) {\n if (!filler || !filler.toLive) {\n return { offsetX: 0, offsetY: 0 };\n }\n var t = filler.gradientTransform || filler.patternTransform;\n var offsetX = -this.width / 2 + filler.offsetX || 0,\n offsetY = -this.height / 2 + filler.offsetY || 0;\n\n if (filler.gradientUnits === 'percentage') {\n ctx.transform(this.width, 0, 0, this.height, offsetX, offsetY);\n }\n else {\n ctx.transform(1, 0, 0, 1, offsetX, offsetY);\n }\n if (t) {\n ctx.transform(t[0], t[1], t[2], t[3], t[4], t[5]);\n }\n return { offsetX: offsetX, offsetY: offsetY };\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _renderPaintInOrder: function(ctx) {\n if (this.paintFirst === 'stroke') {\n this._renderStroke(ctx);\n this._renderFill(ctx);\n }\n else {\n this._renderFill(ctx);\n this._renderStroke(ctx);\n }\n },\n\n /**\n * @private\n * function that actually render something on the context.\n * empty here to allow Obects to work on tests to benchmark fabric functionalites\n * not related to rendering\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _render: function(/* ctx */) {\n\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _renderFill: function(ctx) {\n if (!this.fill) {\n return;\n }\n\n ctx.save();\n this._applyPatternGradientTransform(ctx, this.fill);\n if (this.fillRule === 'evenodd') {\n ctx.fill('evenodd');\n }\n else {\n ctx.fill();\n }\n ctx.restore();\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _renderStroke: function(ctx) {\n if (!this.stroke || this.strokeWidth === 0) {\n return;\n }\n\n if (this.shadow && !this.shadow.affectStroke) {\n this._removeShadow(ctx);\n }\n\n ctx.save();\n if (this.strokeUniform && this.group) {\n var scaling = this.getObjectScaling();\n ctx.scale(1 / scaling.scaleX, 1 / scaling.scaleY);\n }\n else if (this.strokeUniform) {\n ctx.scale(1 / this.scaleX, 1 / this.scaleY);\n }\n this._setLineDash(ctx, this.strokeDashArray, this._renderDashedStroke);\n if (this.stroke.toLive && this.stroke.gradientUnits === 'percentage') {\n // need to transform gradient in a pattern.\n // this is a slow process. If you are hitting this codepath, and the object\n // is not using caching, you should consider switching it on.\n // we need a canvas as big as the current object caching canvas.\n this._applyPatternForTransformedGradient(ctx, this.stroke);\n }\n else {\n this._applyPatternGradientTransform(ctx, this.stroke);\n }\n ctx.stroke();\n ctx.restore();\n },\n\n /**\n * This function try to patch the missing gradientTransform on canvas gradients.\n * transforming a context to transform the gradient, is going to transform the stroke too.\n * we want to transform the gradient but not the stroke operation, so we create\n * a transformed gradient on a pattern and then we use the pattern instead of the gradient.\n * this method has drwabacks: is slow, is in low resolution, needs a patch for when the size\n * is limited.\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n * @param {fabric.Gradient} filler a fabric gradient instance\n */\n _applyPatternForTransformedGradient: function(ctx, filler) {\n var dims = this._limitCacheSize(this._getCacheCanvasDimensions()),\n pCanvas = fabric.util.createCanvasElement(), pCtx, retinaScaling = this.canvas.getRetinaScaling(),\n width = dims.x / this.scaleX / retinaScaling, height = dims.y / this.scaleY / retinaScaling;\n pCanvas.width = width;\n pCanvas.height = height;\n pCtx = pCanvas.getContext('2d');\n pCtx.beginPath(); pCtx.moveTo(0, 0); pCtx.lineTo(width, 0); pCtx.lineTo(width, height);\n pCtx.lineTo(0, height); pCtx.closePath();\n pCtx.translate(width / 2, height / 2);\n pCtx.scale(\n dims.zoomX / this.scaleX / retinaScaling,\n dims.zoomY / this.scaleY / retinaScaling\n );\n this._applyPatternGradientTransform(pCtx, filler);\n pCtx.fillStyle = filler.toLive(ctx);\n pCtx.fill();\n ctx.translate(-this.width / 2 - this.strokeWidth / 2, -this.height / 2 - this.strokeWidth / 2);\n ctx.scale(\n retinaScaling * this.scaleX / dims.zoomX,\n retinaScaling * this.scaleY / dims.zoomY\n );\n ctx.strokeStyle = pCtx.createPattern(pCanvas, 'no-repeat');\n },\n\n /**\n * This function is an helper for svg import. it returns the center of the object in the svg\n * untransformed coordinates\n * @private\n * @return {Object} center point from element coordinates\n */\n _findCenterFromElement: function() {\n return { x: this.left + this.width / 2, y: this.top + this.height / 2 };\n },\n\n /**\n * This function is an helper for svg import. it decompose the transformMatrix\n * and assign properties to object.\n * untransformed coordinates\n * @private\n * @chainable\n */\n _assignTransformMatrixProps: function() {\n if (this.transformMatrix) {\n var options = fabric.util.qrDecompose(this.transformMatrix);\n this.flipX = false;\n this.flipY = false;\n this.set('scaleX', options.scaleX);\n this.set('scaleY', options.scaleY);\n this.angle = options.angle;\n this.skewX = options.skewX;\n this.skewY = 0;\n }\n },\n\n /**\n * This function is an helper for svg import. it removes the transform matrix\n * and set to object properties that fabricjs can handle\n * @private\n * @param {Object} preserveAspectRatioOptions\n * @return {thisArg}\n */\n _removeTransformMatrix: function(preserveAspectRatioOptions) {\n var center = this._findCenterFromElement();\n if (this.transformMatrix) {\n this._assignTransformMatrixProps();\n center = fabric.util.transformPoint(center, this.transformMatrix);\n }\n this.transformMatrix = null;\n if (preserveAspectRatioOptions) {\n this.scaleX *= preserveAspectRatioOptions.scaleX;\n this.scaleY *= preserveAspectRatioOptions.scaleY;\n this.cropX = preserveAspectRatioOptions.cropX;\n this.cropY = preserveAspectRatioOptions.cropY;\n center.x += preserveAspectRatioOptions.offsetLeft;\n center.y += preserveAspectRatioOptions.offsetTop;\n this.width = preserveAspectRatioOptions.width;\n this.height = preserveAspectRatioOptions.height;\n }\n this.setPositionByOrigin(center, 'center', 'center');\n },\n\n /**\n * Clones an instance, using a callback method will work for every object.\n * @param {Function} callback Callback is invoked with a clone as a first argument\n * @param {Array} [propertiesToInclude] Any properties that you might want to additionally include in the output\n */\n clone: function(callback, propertiesToInclude) {\n var objectForm = this.toObject(propertiesToInclude);\n if (this.constructor.fromObject) {\n this.constructor.fromObject(objectForm, callback);\n }\n else {\n fabric.Object._fromObject('Object', objectForm, callback);\n }\n },\n\n /**\n * Creates an instance of fabric.Image out of an object\n * could make use of both toDataUrl or toCanvasElement.\n * @param {Function} callback callback, invoked with an instance as a first argument\n * @param {Object} [options] for clone as image, passed to toDataURL\n * @param {String} [options.format=png] The format of the output image. Either \"jpeg\" or \"png\"\n * @param {Number} [options.quality=1] Quality level (0..1). Only used for jpeg.\n * @param {Number} [options.multiplier=1] Multiplier to scale by\n * @param {Number} [options.left] Cropping left offset. Introduced in v1.2.14\n * @param {Number} [options.top] Cropping top offset. Introduced in v1.2.14\n * @param {Number} [options.width] Cropping width. Introduced in v1.2.14\n * @param {Number} [options.height] Cropping height. Introduced in v1.2.14\n * @param {Boolean} [options.enableRetinaScaling] Enable retina scaling for clone image. Introduce in 1.6.4\n * @param {Boolean} [options.withoutTransform] Remove current object transform ( no scale , no angle, no flip, no skew ). Introduced in 2.3.4\n * @param {Boolean} [options.withoutShadow] Remove current object shadow. Introduced in 2.4.2\n * @return {fabric.Object} thisArg\n */\n cloneAsImage: function(callback, options) {\n var canvasEl = this.toCanvasElement(options);\n if (callback) {\n callback(new fabric.Image(canvasEl));\n }\n return this;\n },\n\n /**\n * Converts an object into a HTMLCanvas element\n * @param {Object} options Options object\n * @param {Number} [options.multiplier=1] Multiplier to scale by\n * @param {Number} [options.left] Cropping left offset. Introduced in v1.2.14\n * @param {Number} [options.top] Cropping top offset. Introduced in v1.2.14\n * @param {Number} [options.width] Cropping width. Introduced in v1.2.14\n * @param {Number} [options.height] Cropping height. Introduced in v1.2.14\n * @param {Boolean} [options.enableRetinaScaling] Enable retina scaling for clone image. Introduce in 1.6.4\n * @param {Boolean} [options.withoutTransform] Remove current object transform ( no scale , no angle, no flip, no skew ). Introduced in 2.3.4\n * @param {Boolean} [options.withoutShadow] Remove current object shadow. Introduced in 2.4.2\n * @return {HTMLCanvasElement} Returns DOM element with the fabric.Object\n */\n toCanvasElement: function(options) {\n options || (options = { });\n\n var utils = fabric.util, origParams = utils.saveObjectTransform(this),\n originalGroup = this.group,\n originalShadow = this.shadow, abs = Math.abs,\n multiplier = (options.multiplier || 1) * (options.enableRetinaScaling ? fabric.devicePixelRatio : 1);\n delete this.group;\n if (options.withoutTransform) {\n utils.resetObjectTransform(this);\n }\n if (options.withoutShadow) {\n this.shadow = null;\n }\n\n var el = fabric.util.createCanvasElement(),\n // skip canvas zoom and calculate with setCoords now.\n boundingRect = this.getBoundingRect(true, true),\n shadow = this.shadow, scaling,\n shadowOffset = { x: 0, y: 0 }, shadowBlur,\n width, height;\n\n if (shadow) {\n shadowBlur = shadow.blur;\n if (shadow.nonScaling) {\n scaling = { scaleX: 1, scaleY: 1 };\n }\n else {\n scaling = this.getObjectScaling();\n }\n // consider non scaling shadow.\n shadowOffset.x = 2 * Math.round(abs(shadow.offsetX) + shadowBlur) * (abs(scaling.scaleX));\n shadowOffset.y = 2 * Math.round(abs(shadow.offsetY) + shadowBlur) * (abs(scaling.scaleY));\n }\n width = boundingRect.width + shadowOffset.x;\n height = boundingRect.height + shadowOffset.y;\n // if the current width/height is not an integer\n // we need to make it so.\n el.width = Math.ceil(width);\n el.height = Math.ceil(height);\n var canvas = new fabric.StaticCanvas(el, {\n enableRetinaScaling: false,\n renderOnAddRemove: false,\n skipOffscreen: false,\n });\n if (options.format === 'jpeg') {\n canvas.backgroundColor = '#fff';\n }\n this.setPositionByOrigin(new fabric.Point(canvas.width / 2, canvas.height / 2), 'center', 'center');\n\n var originalCanvas = this.canvas;\n canvas.add(this);\n var canvasEl = canvas.toCanvasElement(multiplier || 1, options);\n this.shadow = originalShadow;\n this.set('canvas', originalCanvas);\n if (originalGroup) {\n this.group = originalGroup;\n }\n this.set(origParams).setCoords();\n // canvas.dispose will call image.dispose that will nullify the elements\n // since this canvas is a simple element for the process, we remove references\n // to objects in this way in order to avoid object trashing.\n canvas._objects = [];\n canvas.dispose();\n canvas = null;\n\n return canvasEl;\n },\n\n /**\n * Converts an object into a data-url-like string\n * @param {Object} options Options object\n * @param {String} [options.format=png] The format of the output image. Either \"jpeg\" or \"png\"\n * @param {Number} [options.quality=1] Quality level (0..1). Only used for jpeg.\n * @param {Number} [options.multiplier=1] Multiplier to scale by\n * @param {Number} [options.left] Cropping left offset. Introduced in v1.2.14\n * @param {Number} [options.top] Cropping top offset. Introduced in v1.2.14\n * @param {Number} [options.width] Cropping width. Introduced in v1.2.14\n * @param {Number} [options.height] Cropping height. Introduced in v1.2.14\n * @param {Boolean} [options.enableRetinaScaling] Enable retina scaling for clone image. Introduce in 1.6.4\n * @param {Boolean} [options.withoutTransform] Remove current object transform ( no scale , no angle, no flip, no skew ). Introduced in 2.3.4\n * @param {Boolean} [options.withoutShadow] Remove current object shadow. Introduced in 2.4.2\n * @return {String} Returns a data: URL containing a representation of the object in the format specified by options.format\n */\n toDataURL: function(options) {\n options || (options = { });\n return fabric.util.toDataURL(this.toCanvasElement(options), options.format || 'png', options.quality || 1);\n },\n\n /**\n * Returns true if specified type is identical to the type of an instance\n * @param {String} type Type to check against\n * @return {Boolean}\n */\n isType: function(type) {\n return this.type === type;\n },\n\n /**\n * Returns complexity of an instance\n * @return {Number} complexity of this instance (is 1 unless subclassed)\n */\n complexity: function() {\n return 1;\n },\n\n /**\n * Returns a JSON representation of an instance\n * @param {Array} [propertiesToInclude] Any properties that you might want to additionally include in the output\n * @return {Object} JSON\n */\n toJSON: function(propertiesToInclude) {\n // delegate, not alias\n return this.toObject(propertiesToInclude);\n },\n\n /**\n * Sets gradient (fill or stroke) of an object\n * percentages for x1,x2,y1,y2,r1,r2 together with gradientUnits 'pixels', are not supported.\n * Backwards incompatibility note: This method was named \"setGradientFill\" until v1.1.0\n * @param {String} property Property name 'stroke' or 'fill'\n * @param {Object} [options] Options object\n * @param {String} [options.type] Type of gradient 'radial' or 'linear'\n * @param {Number} [options.x1=0] x-coordinate of start point\n * @param {Number} [options.y1=0] y-coordinate of start point\n * @param {Number} [options.x2=0] x-coordinate of end point\n * @param {Number} [options.y2=0] y-coordinate of end point\n * @param {Number} [options.r1=0] Radius of start point (only for radial gradients)\n * @param {Number} [options.r2=0] Radius of end point (only for radial gradients)\n * @param {Object} [options.colorStops] Color stops object eg. {0: 'ff0000', 1: '000000'}\n * @param {Object} [options.gradientTransform] transformMatrix for gradient\n * @return {fabric.Object} thisArg\n * @chainable\n * @deprecated since 3.4.0\n * @see {@link http://jsfiddle.net/fabricjs/58y8b/|jsFiddle demo}\n * @example Set linear gradient\n * object.setGradient('fill', {\n * type: 'linear',\n * x1: -object.width / 2,\n * y1: 0,\n * x2: object.width / 2,\n * y2: 0,\n * colorStops: {\n * 0: 'red',\n * 0.5: '#005555',\n * 1: 'rgba(0,0,255,0.5)'\n * }\n * });\n * canvas.renderAll();\n * @example Set radial gradient\n * object.setGradient('fill', {\n * type: 'radial',\n * x1: 0,\n * y1: 0,\n * x2: 0,\n * y2: 0,\n * r1: object.width / 2,\n * r2: 10,\n * colorStops: {\n * 0: 'red',\n * 0.5: '#005555',\n * 1: 'rgba(0,0,255,0.5)'\n * }\n * });\n * canvas.renderAll();\n */\n setGradient: function(property, options) {\n options || (options = { });\n\n var gradient = { colorStops: [] };\n\n gradient.type = options.type || (options.r1 || options.r2 ? 'radial' : 'linear');\n gradient.coords = {\n x1: options.x1,\n y1: options.y1,\n x2: options.x2,\n y2: options.y2\n };\n gradient.gradientUnits = options.gradientUnits || 'pixels';\n if (options.r1 || options.r2) {\n gradient.coords.r1 = options.r1;\n gradient.coords.r2 = options.r2;\n }\n\n gradient.gradientTransform = options.gradientTransform;\n fabric.Gradient.prototype.addColorStop.call(gradient, options.colorStops);\n\n return this.set(property, fabric.Gradient.forObject(this, gradient));\n },\n\n /**\n * Sets pattern fill of an object\n * @param {Object} options Options object\n * @param {(String|HTMLImageElement)} options.source Pattern source\n * @param {String} [options.repeat=repeat] Repeat property of a pattern (one of repeat, repeat-x, repeat-y or no-repeat)\n * @param {Number} [options.offsetX=0] Pattern horizontal offset from object's left/top corner\n * @param {Number} [options.offsetY=0] Pattern vertical offset from object's left/top corner\n * @param {Function} [callback] Callback to invoke when image set as a pattern\n * @return {fabric.Object} thisArg\n * @chainable\n * @deprecated since 3.5.0\n * @see {@link http://jsfiddle.net/fabricjs/QT3pa/|jsFiddle demo}\n * @example Set pattern\n * object.setPatternFill({\n * source: 'http://fabricjs.com/assets/escheresque_ste.png',\n * repeat: 'repeat'\n * },canvas.renderAll.bind(canvas));\n */\n setPatternFill: function(options, callback) {\n return this.set('fill', new fabric.Pattern(options, callback));\n },\n\n /**\n * Sets {@link fabric.Object#shadow|shadow} of an object\n * @param {Object|String} [options] Options object or string (e.g. \"2px 2px 10px rgba(0,0,0,0.2)\")\n * @param {String} [options.color=rgb(0,0,0)] Shadow color\n * @param {Number} [options.blur=0] Shadow blur\n * @param {Number} [options.offsetX=0] Shadow horizontal offset\n * @param {Number} [options.offsetY=0] Shadow vertical offset\n * @return {fabric.Object} thisArg\n * @chainable\n * @deprecated since 3.5.0\n * @see {@link http://jsfiddle.net/fabricjs/7gvJG/|jsFiddle demo}\n * @example Set shadow with string notation\n * object.setShadow('2px 2px 10px rgba(0,0,0,0.2)');\n * canvas.renderAll();\n * @example Set shadow with object notation\n * object.setShadow({\n * color: 'red',\n * blur: 10,\n * offsetX: 20,\n * offsetY: 20\n * });\n * canvas.renderAll();\n */\n setShadow: function(options) {\n return this.set('shadow', options ? new fabric.Shadow(options) : null);\n },\n\n /**\n * Sets \"color\" of an instance (alias of `set('fill', …)`)\n * @param {String} color Color value\n * @return {fabric.Object} thisArg\n * @deprecated since 3.5.0\n * @chainable\n */\n setColor: function(color) {\n this.set('fill', color);\n return this;\n },\n\n /**\n * Sets \"angle\" of an instance with centered rotation\n * @param {Number} angle Angle value (in degrees)\n * @return {fabric.Object} thisArg\n * @chainable\n */\n rotate: function(angle) {\n var shouldCenterOrigin = (this.originX !== 'center' || this.originY !== 'center') && this.centeredRotation;\n\n if (shouldCenterOrigin) {\n this._setOriginToCenter();\n }\n\n this.set('angle', angle);\n\n if (shouldCenterOrigin) {\n this._resetOrigin();\n }\n\n return this;\n },\n\n /**\n * Centers object horizontally on canvas to which it was added last.\n * You might need to call `setCoords` on an object after centering, to update controls area.\n * @return {fabric.Object} thisArg\n * @chainable\n */\n centerH: function () {\n this.canvas && this.canvas.centerObjectH(this);\n return this;\n },\n\n /**\n * Centers object horizontally on current viewport of canvas to which it was added last.\n * You might need to call `setCoords` on an object after centering, to update controls area.\n * @return {fabric.Object} thisArg\n * @chainable\n */\n viewportCenterH: function () {\n this.canvas && this.canvas.viewportCenterObjectH(this);\n return this;\n },\n\n /**\n * Centers object vertically on canvas to which it was added last.\n * You might need to call `setCoords` on an object after centering, to update controls area.\n * @return {fabric.Object} thisArg\n * @chainable\n */\n centerV: function () {\n this.canvas && this.canvas.centerObjectV(this);\n return this;\n },\n\n /**\n * Centers object vertically on current viewport of canvas to which it was added last.\n * You might need to call `setCoords` on an object after centering, to update controls area.\n * @return {fabric.Object} thisArg\n * @chainable\n */\n viewportCenterV: function () {\n this.canvas && this.canvas.viewportCenterObjectV(this);\n return this;\n },\n\n /**\n * Centers object vertically and horizontally on canvas to which is was added last\n * You might need to call `setCoords` on an object after centering, to update controls area.\n * @return {fabric.Object} thisArg\n * @chainable\n */\n center: function () {\n this.canvas && this.canvas.centerObject(this);\n return this;\n },\n\n /**\n * Centers object on current viewport of canvas to which it was added last.\n * You might need to call `setCoords` on an object after centering, to update controls area.\n * @return {fabric.Object} thisArg\n * @chainable\n */\n viewportCenter: function () {\n this.canvas && this.canvas.viewportCenterObject(this);\n return this;\n },\n\n /**\n * Returns coordinates of a pointer relative to an object\n * @param {Event} e Event to operate upon\n * @param {Object} [pointer] Pointer to operate upon (instead of event)\n * @return {Object} Coordinates of a pointer (x, y)\n */\n getLocalPointer: function(e, pointer) {\n pointer = pointer || this.canvas.getPointer(e);\n var pClicked = new fabric.Point(pointer.x, pointer.y),\n objectLeftTop = this._getLeftTopCoords();\n if (this.angle) {\n pClicked = fabric.util.rotatePoint(\n pClicked, objectLeftTop, degreesToRadians(-this.angle));\n }\n return {\n x: pClicked.x - objectLeftTop.x,\n y: pClicked.y - objectLeftTop.y\n };\n },\n\n /**\n * Sets canvas globalCompositeOperation for specific object\n * custom composition operation for the particular object can be specified using globalCompositeOperation property\n * @param {CanvasRenderingContext2D} ctx Rendering canvas context\n */\n _setupCompositeOperation: function (ctx) {\n if (this.globalCompositeOperation) {\n ctx.globalCompositeOperation = this.globalCompositeOperation;\n }\n }\n });\n\n fabric.util.createAccessors && fabric.util.createAccessors(fabric.Object);\n\n extend(fabric.Object.prototype, fabric.Observable);\n\n /**\n * Defines the number of fraction digits to use when serializing object values.\n * You can use it to increase/decrease precision of such values like left, top, scaleX, scaleY, etc.\n * @static\n * @memberOf fabric.Object\n * @constant\n * @type Number\n */\n fabric.Object.NUM_FRACTION_DIGITS = 2;\n\n fabric.Object._fromObject = function(className, object, callback, extraParam) {\n var klass = fabric[className];\n object = clone(object, true);\n fabric.util.enlivenPatterns([object.fill, object.stroke], function(patterns) {\n if (typeof patterns[0] !== 'undefined') {\n object.fill = patterns[0];\n }\n if (typeof patterns[1] !== 'undefined') {\n object.stroke = patterns[1];\n }\n fabric.util.enlivenObjects([object.clipPath], function(enlivedProps) {\n object.clipPath = enlivedProps[0];\n var instance = extraParam ? new klass(object[extraParam], object) : new klass(object);\n callback && callback(instance);\n });\n });\n };\n\n /**\n * Unique id used internally when creating SVG elements\n * @static\n * @memberOf fabric.Object\n * @type Number\n */\n fabric.Object.__uid = 0;\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function() {\n\n var degreesToRadians = fabric.util.degreesToRadians,\n originXOffset = {\n left: -0.5,\n center: 0,\n right: 0.5\n },\n originYOffset = {\n top: -0.5,\n center: 0,\n bottom: 0.5\n };\n\n fabric.util.object.extend(fabric.Object.prototype, /** @lends fabric.Object.prototype */ {\n\n /**\n * Translates the coordinates from a set of origin to another (based on the object's dimensions)\n * @param {fabric.Point} point The point which corresponds to the originX and originY params\n * @param {String} fromOriginX Horizontal origin: 'left', 'center' or 'right'\n * @param {String} fromOriginY Vertical origin: 'top', 'center' or 'bottom'\n * @param {String} toOriginX Horizontal origin: 'left', 'center' or 'right'\n * @param {String} toOriginY Vertical origin: 'top', 'center' or 'bottom'\n * @return {fabric.Point}\n */\n translateToGivenOrigin: function(point, fromOriginX, fromOriginY, toOriginX, toOriginY) {\n var x = point.x,\n y = point.y,\n offsetX, offsetY, dim;\n\n if (typeof fromOriginX === 'string') {\n fromOriginX = originXOffset[fromOriginX];\n }\n else {\n fromOriginX -= 0.5;\n }\n\n if (typeof toOriginX === 'string') {\n toOriginX = originXOffset[toOriginX];\n }\n else {\n toOriginX -= 0.5;\n }\n\n offsetX = toOriginX - fromOriginX;\n\n if (typeof fromOriginY === 'string') {\n fromOriginY = originYOffset[fromOriginY];\n }\n else {\n fromOriginY -= 0.5;\n }\n\n if (typeof toOriginY === 'string') {\n toOriginY = originYOffset[toOriginY];\n }\n else {\n toOriginY -= 0.5;\n }\n\n offsetY = toOriginY - fromOriginY;\n\n if (offsetX || offsetY) {\n dim = this._getTransformedDimensions();\n x = point.x + offsetX * dim.x;\n y = point.y + offsetY * dim.y;\n }\n\n return new fabric.Point(x, y);\n },\n\n /**\n * Translates the coordinates from origin to center coordinates (based on the object's dimensions)\n * @param {fabric.Point} point The point which corresponds to the originX and originY params\n * @param {String} originX Horizontal origin: 'left', 'center' or 'right'\n * @param {String} originY Vertical origin: 'top', 'center' or 'bottom'\n * @return {fabric.Point}\n */\n translateToCenterPoint: function(point, originX, originY) {\n var p = this.translateToGivenOrigin(point, originX, originY, 'center', 'center');\n if (this.angle) {\n return fabric.util.rotatePoint(p, point, degreesToRadians(this.angle));\n }\n return p;\n },\n\n /**\n * Translates the coordinates from center to origin coordinates (based on the object's dimensions)\n * @param {fabric.Point} center The point which corresponds to center of the object\n * @param {String} originX Horizontal origin: 'left', 'center' or 'right'\n * @param {String} originY Vertical origin: 'top', 'center' or 'bottom'\n * @return {fabric.Point}\n */\n translateToOriginPoint: function(center, originX, originY) {\n var p = this.translateToGivenOrigin(center, 'center', 'center', originX, originY);\n if (this.angle) {\n return fabric.util.rotatePoint(p, center, degreesToRadians(this.angle));\n }\n return p;\n },\n\n /**\n * Returns the real center coordinates of the object\n * @return {fabric.Point}\n */\n getCenterPoint: function() {\n var leftTop = new fabric.Point(this.left, this.top);\n return this.translateToCenterPoint(leftTop, this.originX, this.originY);\n },\n\n /**\n * Returns the coordinates of the object based on center coordinates\n * @param {fabric.Point} point The point which corresponds to the originX and originY params\n * @return {fabric.Point}\n */\n // getOriginPoint: function(center) {\n // return this.translateToOriginPoint(center, this.originX, this.originY);\n // },\n\n /**\n * Returns the coordinates of the object as if it has a different origin\n * @param {String} originX Horizontal origin: 'left', 'center' or 'right'\n * @param {String} originY Vertical origin: 'top', 'center' or 'bottom'\n * @return {fabric.Point}\n */\n getPointByOrigin: function(originX, originY) {\n var center = this.getCenterPoint();\n return this.translateToOriginPoint(center, originX, originY);\n },\n\n /**\n * Returns the point in local coordinates\n * @param {fabric.Point} point The point relative to the global coordinate system\n * @param {String} originX Horizontal origin: 'left', 'center' or 'right'\n * @param {String} originY Vertical origin: 'top', 'center' or 'bottom'\n * @return {fabric.Point}\n */\n toLocalPoint: function(point, originX, originY) {\n var center = this.getCenterPoint(),\n p, p2;\n\n if (typeof originX !== 'undefined' && typeof originY !== 'undefined' ) {\n p = this.translateToGivenOrigin(center, 'center', 'center', originX, originY);\n }\n else {\n p = new fabric.Point(this.left, this.top);\n }\n\n p2 = new fabric.Point(point.x, point.y);\n if (this.angle) {\n p2 = fabric.util.rotatePoint(p2, center, -degreesToRadians(this.angle));\n }\n return p2.subtractEquals(p);\n },\n\n /**\n * Returns the point in global coordinates\n * @param {fabric.Point} The point relative to the local coordinate system\n * @return {fabric.Point}\n */\n // toGlobalPoint: function(point) {\n // return fabric.util.rotatePoint(point, this.getCenterPoint(), degreesToRadians(this.angle)).addEquals(new fabric.Point(this.left, this.top));\n // },\n\n /**\n * Sets the position of the object taking into consideration the object's origin\n * @param {fabric.Point} pos The new position of the object\n * @param {String} originX Horizontal origin: 'left', 'center' or 'right'\n * @param {String} originY Vertical origin: 'top', 'center' or 'bottom'\n * @return {void}\n */\n setPositionByOrigin: function(pos, originX, originY) {\n var center = this.translateToCenterPoint(pos, originX, originY),\n position = this.translateToOriginPoint(center, this.originX, this.originY);\n this.set('left', position.x);\n this.set('top', position.y);\n },\n\n /**\n * @param {String} to One of 'left', 'center', 'right'\n */\n adjustPosition: function(to) {\n var angle = degreesToRadians(this.angle),\n hypotFull = this.getScaledWidth(),\n xFull = fabric.util.cos(angle) * hypotFull,\n yFull = fabric.util.sin(angle) * hypotFull,\n offsetFrom, offsetTo;\n\n //TODO: this function does not consider mixed situation like top, center.\n if (typeof this.originX === 'string') {\n offsetFrom = originXOffset[this.originX];\n }\n else {\n offsetFrom = this.originX - 0.5;\n }\n if (typeof to === 'string') {\n offsetTo = originXOffset[to];\n }\n else {\n offsetTo = to - 0.5;\n }\n this.left += xFull * (offsetTo - offsetFrom);\n this.top += yFull * (offsetTo - offsetFrom);\n this.setCoords();\n this.originX = to;\n },\n\n /**\n * Sets the origin/position of the object to it's center point\n * @private\n * @return {void}\n */\n _setOriginToCenter: function() {\n this._originalOriginX = this.originX;\n this._originalOriginY = this.originY;\n\n var center = this.getCenterPoint();\n\n this.originX = 'center';\n this.originY = 'center';\n\n this.left = center.x;\n this.top = center.y;\n },\n\n /**\n * Resets the origin/position of the object to it's original origin\n * @private\n * @return {void}\n */\n _resetOrigin: function() {\n var originPoint = this.translateToOriginPoint(\n this.getCenterPoint(),\n this._originalOriginX,\n this._originalOriginY);\n\n this.originX = this._originalOriginX;\n this.originY = this._originalOriginY;\n\n this.left = originPoint.x;\n this.top = originPoint.y;\n\n this._originalOriginX = null;\n this._originalOriginY = null;\n },\n\n /**\n * @private\n */\n _getLeftTopCoords: function() {\n return this.translateToOriginPoint(this.getCenterPoint(), 'left', 'top');\n },\n });\n\n})();\n\n\n(function() {\n\n function getCoords(coords) {\n return [\n new fabric.Point(coords.tl.x, coords.tl.y),\n new fabric.Point(coords.tr.x, coords.tr.y),\n new fabric.Point(coords.br.x, coords.br.y),\n new fabric.Point(coords.bl.x, coords.bl.y)\n ];\n }\n\n var degreesToRadians = fabric.util.degreesToRadians,\n multiplyMatrices = fabric.util.multiplyTransformMatrices,\n transformPoint = fabric.util.transformPoint;\n\n fabric.util.object.extend(fabric.Object.prototype, /** @lends fabric.Object.prototype */ {\n\n /**\n * Describe object's corner position in canvas element coordinates.\n * properties are tl,mt,tr,ml,mr,bl,mb,br,mtr for the main controls.\n * each property is an object with x, y and corner.\n * The `corner` property contains in a similar manner the 4 points of the\n * interactive area of the corner.\n * The coordinates depends from this properties: width, height, scaleX, scaleY\n * skewX, skewY, angle, strokeWidth, viewportTransform, top, left, padding.\n * The coordinates get updated with @method setCoords.\n * You can calculate them without updating with @method calcCoords;\n * @memberOf fabric.Object.prototype\n */\n oCoords: null,\n\n /**\n * Describe object's corner position in canvas object absolute coordinates\n * properties are tl,tr,bl,br and describe the four main corner.\n * each property is an object with x, y, instance of Fabric.Point.\n * The coordinates depends from this properties: width, height, scaleX, scaleY\n * skewX, skewY, angle, strokeWidth, top, left.\n * Those coordinates are useful to understand where an object is. They get updated\n * with oCoords but they do not need to be updated when zoom or panning change.\n * The coordinates get updated with @method setCoords.\n * You can calculate them without updating with @method calcCoords(true);\n * @memberOf fabric.Object.prototype\n */\n aCoords: null,\n\n /**\n * storage for object transform matrix\n */\n ownMatrixCache: null,\n\n /**\n * storage for object full transform matrix\n */\n matrixCache: null,\n\n /**\n * return correct set of coordinates for intersection\n */\n getCoords: function(absolute, calculate) {\n if (!this.oCoords) {\n this.setCoords();\n }\n var coords = absolute ? this.aCoords : this.oCoords;\n return getCoords(calculate ? this.calcCoords(absolute) : coords);\n },\n\n /**\n * Checks if object intersects with an area formed by 2 points\n * @param {Object} pointTL top-left point of area\n * @param {Object} pointBR bottom-right point of area\n * @param {Boolean} [absolute] use coordinates without viewportTransform\n * @param {Boolean} [calculate] use coordinates of current position instead of .oCoords\n * @return {Boolean} true if object intersects with an area formed by 2 points\n */\n intersectsWithRect: function(pointTL, pointBR, absolute, calculate) {\n var coords = this.getCoords(absolute, calculate),\n intersection = fabric.Intersection.intersectPolygonRectangle(\n coords,\n pointTL,\n pointBR\n );\n return intersection.status === 'Intersection';\n },\n\n /**\n * Checks if object intersects with another object\n * @param {Object} other Object to test\n * @param {Boolean} [absolute] use coordinates without viewportTransform\n * @param {Boolean} [calculate] use coordinates of current position instead of .oCoords\n * @return {Boolean} true if object intersects with another object\n */\n intersectsWithObject: function(other, absolute, calculate) {\n var intersection = fabric.Intersection.intersectPolygonPolygon(\n this.getCoords(absolute, calculate),\n other.getCoords(absolute, calculate)\n );\n\n return intersection.status === 'Intersection'\n || other.isContainedWithinObject(this, absolute, calculate)\n || this.isContainedWithinObject(other, absolute, calculate);\n },\n\n /**\n * Checks if object is fully contained within area of another object\n * @param {Object} other Object to test\n * @param {Boolean} [absolute] use coordinates without viewportTransform\n * @param {Boolean} [calculate] use coordinates of current position instead of .oCoords\n * @return {Boolean} true if object is fully contained within area of another object\n */\n isContainedWithinObject: function(other, absolute, calculate) {\n var points = this.getCoords(absolute, calculate),\n i = 0, lines = other._getImageLines(\n calculate ? other.calcCoords(absolute) : absolute ? other.aCoords : other.oCoords\n );\n for (; i < 4; i++) {\n if (!other.containsPoint(points[i], lines)) {\n return false;\n }\n }\n return true;\n },\n\n /**\n * Checks if object is fully contained within area formed by 2 points\n * @param {Object} pointTL top-left point of area\n * @param {Object} pointBR bottom-right point of area\n * @param {Boolean} [absolute] use coordinates without viewportTransform\n * @param {Boolean} [calculate] use coordinates of current position instead of .oCoords\n * @return {Boolean} true if object is fully contained within area formed by 2 points\n */\n isContainedWithinRect: function(pointTL, pointBR, absolute, calculate) {\n var boundingRect = this.getBoundingRect(absolute, calculate);\n\n return (\n boundingRect.left >= pointTL.x &&\n boundingRect.left + boundingRect.width <= pointBR.x &&\n boundingRect.top >= pointTL.y &&\n boundingRect.top + boundingRect.height <= pointBR.y\n );\n },\n\n /**\n * Checks if point is inside the object\n * @param {fabric.Point} point Point to check against\n * @param {Object} [lines] object returned from @method _getImageLines\n * @param {Boolean} [absolute] use coordinates without viewportTransform\n * @param {Boolean} [calculate] use coordinates of current position instead of .oCoords\n * @return {Boolean} true if point is inside the object\n */\n containsPoint: function(point, lines, absolute, calculate) {\n var lines = lines || this._getImageLines(\n calculate ? this.calcCoords(absolute) : absolute ? this.aCoords : this.oCoords\n ),\n xPoints = this._findCrossPoints(point, lines);\n\n // if xPoints is odd then point is inside the object\n return (xPoints !== 0 && xPoints % 2 === 1);\n },\n\n /**\n * Checks if object is contained within the canvas with current viewportTransform\n * the check is done stopping at first point that appears on screen\n * @param {Boolean} [calculate] use coordinates of current position instead of .aCoords\n * @return {Boolean} true if object is fully or partially contained within canvas\n */\n isOnScreen: function(calculate) {\n if (!this.canvas) {\n return false;\n }\n var pointTL = this.canvas.vptCoords.tl, pointBR = this.canvas.vptCoords.br;\n var points = this.getCoords(true, calculate), point;\n for (var i = 0; i < 4; i++) {\n point = points[i];\n if (point.x <= pointBR.x && point.x >= pointTL.x && point.y <= pointBR.y && point.y >= pointTL.y) {\n return true;\n }\n }\n // no points on screen, check intersection with absolute coordinates\n if (this.intersectsWithRect(pointTL, pointBR, true, calculate)) {\n return true;\n }\n return this._containsCenterOfCanvas(pointTL, pointBR, calculate);\n },\n\n /**\n * Checks if the object contains the midpoint between canvas extremities\n * Does not make sense outside the context of isOnScreen and isPartiallyOnScreen\n * @private\n * @param {Fabric.Point} pointTL Top Left point\n * @param {Fabric.Point} pointBR Top Right point\n * @param {Boolean} calculate use coordinates of current position instead of .oCoords\n * @return {Boolean} true if the object contains the point\n */\n _containsCenterOfCanvas: function(pointTL, pointBR, calculate) {\n // worst case scenario the object is so big that contains the screen\n var centerPoint = { x: (pointTL.x + pointBR.x) / 2, y: (pointTL.y + pointBR.y) / 2 };\n if (this.containsPoint(centerPoint, null, true, calculate)) {\n return true;\n }\n return false;\n },\n\n /**\n * Checks if object is partially contained within the canvas with current viewportTransform\n * @param {Boolean} [calculate] use coordinates of current position instead of .oCoords\n * @return {Boolean} true if object is partially contained within canvas\n */\n isPartiallyOnScreen: function(calculate) {\n if (!this.canvas) {\n return false;\n }\n var pointTL = this.canvas.vptCoords.tl, pointBR = this.canvas.vptCoords.br;\n if (this.intersectsWithRect(pointTL, pointBR, true, calculate)) {\n return true;\n }\n return this._containsCenterOfCanvas(pointTL, pointBR, calculate);\n },\n\n /**\n * Method that returns an object with the object edges in it, given the coordinates of the corners\n * @private\n * @param {Object} oCoords Coordinates of the object corners\n */\n _getImageLines: function(oCoords) {\n return {\n topline: {\n o: oCoords.tl,\n d: oCoords.tr\n },\n rightline: {\n o: oCoords.tr,\n d: oCoords.br\n },\n bottomline: {\n o: oCoords.br,\n d: oCoords.bl\n },\n leftline: {\n o: oCoords.bl,\n d: oCoords.tl\n }\n };\n },\n\n /**\n * Helper method to determine how many cross points are between the 4 object edges\n * and the horizontal line determined by a point on canvas\n * @private\n * @param {fabric.Point} point Point to check\n * @param {Object} lines Coordinates of the object being evaluated\n */\n // remove yi, not used but left code here just in case.\n _findCrossPoints: function(point, lines) {\n var b1, b2, a1, a2, xi, // yi,\n xcount = 0,\n iLine;\n\n for (var lineKey in lines) {\n iLine = lines[lineKey];\n // optimisation 1: line below point. no cross\n if ((iLine.o.y < point.y) && (iLine.d.y < point.y)) {\n continue;\n }\n // optimisation 2: line above point. no cross\n if ((iLine.o.y >= point.y) && (iLine.d.y >= point.y)) {\n continue;\n }\n // optimisation 3: vertical line case\n if ((iLine.o.x === iLine.d.x) && (iLine.o.x >= point.x)) {\n xi = iLine.o.x;\n // yi = point.y;\n }\n // calculate the intersection point\n else {\n b1 = 0;\n b2 = (iLine.d.y - iLine.o.y) / (iLine.d.x - iLine.o.x);\n a1 = point.y - b1 * point.x;\n a2 = iLine.o.y - b2 * iLine.o.x;\n\n xi = -(a1 - a2) / (b1 - b2);\n // yi = a1 + b1 * xi;\n }\n // dont count xi < point.x cases\n if (xi >= point.x) {\n xcount += 1;\n }\n // optimisation 4: specific for square images\n if (xcount === 2) {\n break;\n }\n }\n return xcount;\n },\n\n /**\n * Returns coordinates of object's bounding rectangle (left, top, width, height)\n * the box is intended as aligned to axis of canvas.\n * @param {Boolean} [absolute] use coordinates without viewportTransform\n * @param {Boolean} [calculate] use coordinates of current position instead of .oCoords / .aCoords\n * @return {Object} Object with left, top, width, height properties\n */\n getBoundingRect: function(absolute, calculate) {\n var coords = this.getCoords(absolute, calculate);\n return fabric.util.makeBoundingBoxFromPoints(coords);\n },\n\n /**\n * Returns width of an object's bounding box counting transformations\n * before 2.0 it was named getWidth();\n * @return {Number} width value\n */\n getScaledWidth: function() {\n return this._getTransformedDimensions().x;\n },\n\n /**\n * Returns height of an object bounding box counting transformations\n * before 2.0 it was named getHeight();\n * @return {Number} height value\n */\n getScaledHeight: function() {\n return this._getTransformedDimensions().y;\n },\n\n /**\n * Makes sure the scale is valid and modifies it if necessary\n * @private\n * @param {Number} value\n * @return {Number}\n */\n _constrainScale: function(value) {\n if (Math.abs(value) < this.minScaleLimit) {\n if (value < 0) {\n return -this.minScaleLimit;\n }\n else {\n return this.minScaleLimit;\n }\n }\n else if (value === 0) {\n return 0.0001;\n }\n return value;\n },\n\n /**\n * Scales an object (equally by x and y)\n * @param {Number} value Scale factor\n * @return {fabric.Object} thisArg\n * @chainable\n */\n scale: function(value) {\n this._set('scaleX', value);\n this._set('scaleY', value);\n return this.setCoords();\n },\n\n /**\n * Scales an object to a given width, with respect to bounding box (scaling by x/y equally)\n * @param {Number} value New width value\n * @param {Boolean} absolute ignore viewport\n * @return {fabric.Object} thisArg\n * @chainable\n */\n scaleToWidth: function(value, absolute) {\n // adjust to bounding rect factor so that rotated shapes would fit as well\n var boundingRectFactor = this.getBoundingRect(absolute).width / this.getScaledWidth();\n return this.scale(value / this.width / boundingRectFactor);\n },\n\n /**\n * Scales an object to a given height, with respect to bounding box (scaling by x/y equally)\n * @param {Number} value New height value\n * @param {Boolean} absolute ignore viewport\n * @return {fabric.Object} thisArg\n * @chainable\n */\n scaleToHeight: function(value, absolute) {\n // adjust to bounding rect factor so that rotated shapes would fit as well\n var boundingRectFactor = this.getBoundingRect(absolute).height / this.getScaledHeight();\n return this.scale(value / this.height / boundingRectFactor);\n },\n\n /**\n * Calculates and returns the .coords of an object.\n * @return {Object} Object with tl, tr, br, bl ....\n * @chainable\n */\n calcCoords: function(absolute) {\n var rotateMatrix = this._calcRotateMatrix(),\n translateMatrix = this._calcTranslateMatrix(),\n startMatrix = multiplyMatrices(translateMatrix, rotateMatrix),\n vpt = this.getViewportTransform(),\n finalMatrix = absolute ? startMatrix : multiplyMatrices(vpt, startMatrix),\n dim = this._getTransformedDimensions(),\n w = dim.x / 2, h = dim.y / 2,\n tl = transformPoint({ x: -w, y: -h }, finalMatrix),\n tr = transformPoint({ x: w, y: -h }, finalMatrix),\n bl = transformPoint({ x: -w, y: h }, finalMatrix),\n br = transformPoint({ x: w, y: h }, finalMatrix);\n if (!absolute) {\n var padding = this.padding, angle = degreesToRadians(this.angle),\n cos = fabric.util.cos(angle), sin = fabric.util.sin(angle),\n cosP = cos * padding, sinP = sin * padding, cosPSinP = cosP + sinP,\n cosPMinusSinP = cosP - sinP;\n if (padding) {\n tl.x -= cosPMinusSinP;\n tl.y -= cosPSinP;\n tr.x += cosPSinP;\n tr.y -= cosPMinusSinP;\n bl.x -= cosPSinP;\n bl.y += cosPMinusSinP;\n br.x += cosPMinusSinP;\n br.y += cosPSinP;\n }\n var ml = new fabric.Point((tl.x + bl.x) / 2, (tl.y + bl.y) / 2),\n mt = new fabric.Point((tr.x + tl.x) / 2, (tr.y + tl.y) / 2),\n mr = new fabric.Point((br.x + tr.x) / 2, (br.y + tr.y) / 2),\n mb = new fabric.Point((br.x + bl.x) / 2, (br.y + bl.y) / 2),\n mtr = new fabric.Point(mt.x + sin * this.rotatingPointOffset, mt.y - cos * this.rotatingPointOffset);\n }\n\n // if (!absolute) {\n // var canvas = this.canvas;\n // setTimeout(function() {\n // canvas.contextTop.clearRect(0, 0, 700, 700);\n // canvas.contextTop.fillStyle = 'green';\n // canvas.contextTop.fillRect(mb.x, mb.y, 3, 3);\n // canvas.contextTop.fillRect(bl.x, bl.y, 3, 3);\n // canvas.contextTop.fillRect(br.x, br.y, 3, 3);\n // canvas.contextTop.fillRect(tl.x, tl.y, 3, 3);\n // canvas.contextTop.fillRect(tr.x, tr.y, 3, 3);\n // canvas.contextTop.fillRect(ml.x, ml.y, 3, 3);\n // canvas.contextTop.fillRect(mr.x, mr.y, 3, 3);\n // canvas.contextTop.fillRect(mt.x, mt.y, 3, 3);\n // canvas.contextTop.fillRect(mtr.x, mtr.y, 3, 3);\n // }, 50);\n // }\n\n var coords = {\n // corners\n tl: tl, tr: tr, br: br, bl: bl,\n };\n if (!absolute) {\n // middle\n coords.ml = ml;\n coords.mt = mt;\n coords.mr = mr;\n coords.mb = mb;\n // rotating point\n coords.mtr = mtr;\n }\n return coords;\n },\n\n /**\n * Sets corner position coordinates based on current angle, width and height.\n * See {@link https://github.com/kangax/fabric.js/wiki/When-to-call-setCoords|When-to-call-setCoords}\n * @param {Boolean} [ignoreZoom] set oCoords with or without the viewport transform.\n * @param {Boolean} [skipAbsolute] skip calculation of aCoords, useful in setViewportTransform\n * @return {fabric.Object} thisArg\n * @chainable\n */\n setCoords: function(ignoreZoom, skipAbsolute) {\n this.oCoords = this.calcCoords(ignoreZoom);\n if (!skipAbsolute) {\n this.aCoords = this.calcCoords(true);\n }\n\n // set coordinates of the draggable boxes in the corners used to scale/rotate the image\n ignoreZoom || (this._setCornerCoords && this._setCornerCoords());\n\n return this;\n },\n\n /**\n * calculate rotation matrix of an object\n * @return {Array} rotation matrix for the object\n */\n _calcRotateMatrix: function() {\n return fabric.util.calcRotateMatrix(this);\n },\n\n /**\n * calculate the translation matrix for an object transform\n * @return {Array} rotation matrix for the object\n */\n _calcTranslateMatrix: function() {\n var center = this.getCenterPoint();\n return [1, 0, 0, 1, center.x, center.y];\n },\n\n transformMatrixKey: function(skipGroup) {\n var sep = '_', prefix = '';\n if (!skipGroup && this.group) {\n prefix = this.group.transformMatrixKey(skipGroup) + sep;\n };\n return prefix + this.top + sep + this.left + sep + this.scaleX + sep + this.scaleY +\n sep + this.skewX + sep + this.skewY + sep + this.angle + sep + this.originX + sep + this.originY +\n sep + this.width + sep + this.height + sep + this.strokeWidth + this.flipX + this.flipY;\n },\n\n /**\n * calculate transform matrix that represents the current transformations from the\n * object's properties.\n * @param {Boolean} [skipGroup] return transform matrix for object not counting parent transformations\n * @return {Array} transform matrix for the object\n */\n calcTransformMatrix: function(skipGroup) {\n if (skipGroup) {\n return this.calcOwnMatrix();\n }\n var key = this.transformMatrixKey(), cache = this.matrixCache || (this.matrixCache = {});\n if (cache.key === key) {\n return cache.value;\n }\n var matrix = this.calcOwnMatrix();\n if (this.group) {\n matrix = multiplyMatrices(this.group.calcTransformMatrix(), matrix);\n }\n cache.key = key;\n cache.value = matrix;\n return matrix;\n },\n\n /**\n * calculate transform matrix that represents the current transformations from the\n * object's properties, this matrix does not include the group transformation\n * @return {Array} transform matrix for the object\n */\n calcOwnMatrix: function() {\n var key = this.transformMatrixKey(true), cache = this.ownMatrixCache || (this.ownMatrixCache = {});\n if (cache.key === key) {\n return cache.value;\n }\n var tMatrix = this._calcTranslateMatrix();\n this.translateX = tMatrix[4];\n this.translateY = tMatrix[5];\n cache.key = key;\n cache.value = fabric.util.composeMatrix(this);\n return cache.value;\n },\n\n /*\n * Calculate object dimensions from its properties\n * @private\n * @deprecated since 3.4.0, please use fabric.util._calcDimensionsTransformMatrix\n * not including or including flipX, flipY to emulate the flipping boolean\n * @return {Object} .x width dimension\n * @return {Object} .y height dimension\n */\n _calcDimensionsTransformMatrix: function(skewX, skewY, flipping) {\n return fabric.util.calcDimensionsMatrix({\n skewX: skewX,\n skewY: skewY,\n scaleX: this.scaleX * (flipping && this.flipX ? -1 : 1),\n scaleY: this.scaleY * (flipping && this.flipY ? -1 : 1)\n });\n },\n\n /*\n * Calculate object dimensions from its properties\n * @private\n * @return {Object} .x width dimension\n * @return {Object} .y height dimension\n */\n _getNonTransformedDimensions: function() {\n var strokeWidth = this.strokeWidth,\n w = this.width + strokeWidth,\n h = this.height + strokeWidth;\n return { x: w, y: h };\n },\n\n /*\n * Calculate object bounding box dimensions from its properties scale, skew.\n * The skewX and skewY parameters are used in the skewing logic path and\n * do not provide something useful to common use cases.\n * @param {Number} [skewX], a value to override current skewX\n * @param {Number} [skewY], a value to override current skewY\n * @private\n * @return {Object} .x width dimension\n * @return {Object} .y height dimension\n */\n _getTransformedDimensions: function(skewX, skewY) {\n if (typeof skewX === 'undefined') {\n skewX = this.skewX;\n }\n if (typeof skewY === 'undefined') {\n skewY = this.skewY;\n }\n var dimensions = this._getNonTransformedDimensions(), dimX, dimY,\n noSkew = skewX === 0 && skewY === 0;\n\n if (this.strokeUniform) {\n dimX = this.width;\n dimY = this.height;\n }\n else {\n dimX = dimensions.x;\n dimY = dimensions.y;\n }\n if (noSkew) {\n return this._finalizeDimensions(dimX * this.scaleX, dimY * this.scaleY);\n }\n else {\n dimX /= 2;\n dimY /= 2;\n }\n var points = [\n {\n x: -dimX,\n y: -dimY\n },\n {\n x: dimX,\n y: -dimY\n },\n {\n x: -dimX,\n y: dimY\n },\n {\n x: dimX,\n y: dimY\n }],\n transformMatrix = fabric.util.calcDimensionsMatrix({\n scaleX: this.scaleX,\n scaleY: this.scaleY,\n skewX: skewX,\n skewY: skewY,\n }),\n bbox = fabric.util.makeBoundingBoxFromPoints(points, transformMatrix);\n return this._finalizeDimensions(bbox.width, bbox.height);\n },\n\n /*\n * Calculate object bounding box dimensions from its properties scale, skew.\n * @param Number width width of the bbox\n * @param Number height height of the bbox\n * @private\n * @return {Object} .x finalized width dimension\n * @return {Object} .y finalized height dimension\n */\n _finalizeDimensions: function(width, height) {\n return this.strokeUniform ?\n { x: width + this.strokeWidth, y: height + this.strokeWidth }\n :\n { x: width, y: height };\n },\n /*\n * Calculate object dimensions for controls, including padding and canvas zoom.\n * private\n */\n _calculateCurrentDimensions: function() {\n var vpt = this.getViewportTransform(),\n dim = this._getTransformedDimensions(),\n p = fabric.util.transformPoint(dim, vpt, true);\n\n return p.scalarAdd(2 * this.padding);\n },\n });\n})();\n\n\nfabric.util.object.extend(fabric.Object.prototype, /** @lends fabric.Object.prototype */ {\n\n /**\n * Moves an object to the bottom of the stack of drawn objects\n * @return {fabric.Object} thisArg\n * @chainable\n */\n sendToBack: function() {\n if (this.group) {\n fabric.StaticCanvas.prototype.sendToBack.call(this.group, this);\n }\n else if (this.canvas) {\n this.canvas.sendToBack(this);\n }\n return this;\n },\n\n /**\n * Moves an object to the top of the stack of drawn objects\n * @return {fabric.Object} thisArg\n * @chainable\n */\n bringToFront: function() {\n if (this.group) {\n fabric.StaticCanvas.prototype.bringToFront.call(this.group, this);\n }\n else if (this.canvas) {\n this.canvas.bringToFront(this);\n }\n return this;\n },\n\n /**\n * Moves an object down in stack of drawn objects\n * @param {Boolean} [intersecting] If `true`, send object behind next lower intersecting object\n * @return {fabric.Object} thisArg\n * @chainable\n */\n sendBackwards: function(intersecting) {\n if (this.group) {\n fabric.StaticCanvas.prototype.sendBackwards.call(this.group, this, intersecting);\n }\n else if (this.canvas) {\n this.canvas.sendBackwards(this, intersecting);\n }\n return this;\n },\n\n /**\n * Moves an object up in stack of drawn objects\n * @param {Boolean} [intersecting] If `true`, send object in front of next upper intersecting object\n * @return {fabric.Object} thisArg\n * @chainable\n */\n bringForward: function(intersecting) {\n if (this.group) {\n fabric.StaticCanvas.prototype.bringForward.call(this.group, this, intersecting);\n }\n else if (this.canvas) {\n this.canvas.bringForward(this, intersecting);\n }\n return this;\n },\n\n /**\n * Moves an object to specified level in stack of drawn objects\n * @param {Number} index New position of object\n * @return {fabric.Object} thisArg\n * @chainable\n */\n moveTo: function(index) {\n if (this.group && this.group.type !== 'activeSelection') {\n fabric.StaticCanvas.prototype.moveTo.call(this.group, this, index);\n }\n else if (this.canvas) {\n this.canvas.moveTo(this, index);\n }\n return this;\n }\n});\n\n\n/* _TO_SVG_START_ */\n(function() {\n function getSvgColorString(prop, value) {\n if (!value) {\n return prop + ': none; ';\n }\n else if (value.toLive) {\n return prop + ': url(#SVGID_' + value.id + '); ';\n }\n else {\n var color = new fabric.Color(value),\n str = prop + ': ' + color.toRgb() + '; ',\n opacity = color.getAlpha();\n if (opacity !== 1) {\n //change the color in rgb + opacity\n str += prop + '-opacity: ' + opacity.toString() + '; ';\n }\n return str;\n }\n }\n\n var toFixed = fabric.util.toFixed;\n\n fabric.util.object.extend(fabric.Object.prototype, /** @lends fabric.Object.prototype */ {\n /**\n * Returns styles-string for svg-export\n * @param {Boolean} skipShadow a boolean to skip shadow filter output\n * @return {String}\n */\n getSvgStyles: function(skipShadow) {\n\n var fillRule = this.fillRule ? this.fillRule : 'nonzero',\n strokeWidth = this.strokeWidth ? this.strokeWidth : '0',\n strokeDashArray = this.strokeDashArray ? this.strokeDashArray.join(' ') : 'none',\n strokeDashOffset = this.strokeDashOffset ? this.strokeDashOffset : '0',\n strokeLineCap = this.strokeLineCap ? this.strokeLineCap : 'butt',\n strokeLineJoin = this.strokeLineJoin ? this.strokeLineJoin : 'miter',\n strokeMiterLimit = this.strokeMiterLimit ? this.strokeMiterLimit : '4',\n opacity = typeof this.opacity !== 'undefined' ? this.opacity : '1',\n visibility = this.visible ? '' : ' visibility: hidden;',\n filter = skipShadow ? '' : this.getSvgFilter(),\n fill = getSvgColorString('fill', this.fill),\n stroke = getSvgColorString('stroke', this.stroke);\n\n return [\n stroke,\n 'stroke-width: ', strokeWidth, '; ',\n 'stroke-dasharray: ', strokeDashArray, '; ',\n 'stroke-linecap: ', strokeLineCap, '; ',\n 'stroke-dashoffset: ', strokeDashOffset, '; ',\n 'stroke-linejoin: ', strokeLineJoin, '; ',\n 'stroke-miterlimit: ', strokeMiterLimit, '; ',\n fill,\n 'fill-rule: ', fillRule, '; ',\n 'opacity: ', opacity, ';',\n filter,\n visibility\n ].join('');\n },\n\n /**\n * Returns styles-string for svg-export\n * @param {Object} style the object from which to retrieve style properties\n * @param {Boolean} useWhiteSpace a boolean to include an additional attribute in the style.\n * @return {String}\n */\n getSvgSpanStyles: function(style, useWhiteSpace) {\n var term = '; ';\n var fontFamily = style.fontFamily ?\n 'font-family: ' + (((style.fontFamily.indexOf('\\'') === -1 && style.fontFamily.indexOf('\"') === -1) ?\n '\\'' + style.fontFamily + '\\'' : style.fontFamily)) + term : '';\n var strokeWidth = style.strokeWidth ? 'stroke-width: ' + style.strokeWidth + term : '',\n fontFamily = fontFamily,\n fontSize = style.fontSize ? 'font-size: ' + style.fontSize + 'px' + term : '',\n fontStyle = style.fontStyle ? 'font-style: ' + style.fontStyle + term : '',\n fontWeight = style.fontWeight ? 'font-weight: ' + style.fontWeight + term : '',\n fill = style.fill ? getSvgColorString('fill', style.fill) : '',\n stroke = style.stroke ? getSvgColorString('stroke', style.stroke) : '',\n textDecoration = this.getSvgTextDecoration(style),\n deltaY = style.deltaY ? 'baseline-shift: ' + (-style.deltaY) + '; ' : '';\n if (textDecoration) {\n textDecoration = 'text-decoration: ' + textDecoration + term;\n }\n\n return [\n stroke,\n strokeWidth,\n fontFamily,\n fontSize,\n fontStyle,\n fontWeight,\n textDecoration,\n fill,\n deltaY,\n useWhiteSpace ? 'white-space: pre; ' : ''\n ].join('');\n },\n\n /**\n * Returns text-decoration property for svg-export\n * @param {Object} style the object from which to retrieve style properties\n * @return {String}\n */\n getSvgTextDecoration: function(style) {\n return ['overline', 'underline', 'line-through'].filter(function(decoration) {\n return style[decoration.replace('-', '')];\n }).join(' ');\n },\n\n /**\n * Returns filter for svg shadow\n * @return {String}\n */\n getSvgFilter: function() {\n return this.shadow ? 'filter: url(#SVGID_' + this.shadow.id + ');' : '';\n },\n\n /**\n * Returns id attribute for svg output\n * @return {String}\n */\n getSvgCommons: function() {\n return [\n this.id ? 'id=\"' + this.id + '\" ' : '',\n this.clipPath ? 'clip-path=\"url(#' + this.clipPath.clipPathId + ')\" ' : '',\n ].join('');\n },\n\n /**\n * Returns transform-string for svg-export\n * @param {Boolean} use the full transform or the single object one.\n * @return {String}\n */\n getSvgTransform: function(full, additionalTransform) {\n var transform = full ? this.calcTransformMatrix() : this.calcOwnMatrix(),\n svgTransform = 'transform=\"' + fabric.util.matrixToSVG(transform);\n return svgTransform +\n (additionalTransform || '') + this.getSvgTransformMatrix() + '\" ';\n },\n\n /**\n * Returns transform-string for svg-export from the transform matrix of single elements\n * @return {String}\n */\n getSvgTransformMatrix: function() {\n return this.transformMatrix ? ' ' + fabric.util.matrixToSVG(this.transformMatrix) : '';\n },\n\n _setSVGBg: function(textBgRects) {\n if (this.backgroundColor) {\n var NUM_FRACTION_DIGITS = fabric.Object.NUM_FRACTION_DIGITS;\n textBgRects.push(\n '\\t\\t\\n');\n }\n },\n\n /**\n * Returns svg representation of an instance\n * @param {Function} [reviver] Method for further parsing of svg representation.\n * @return {String} svg representation of an instance\n */\n toSVG: function(reviver) {\n return this._createBaseSVGMarkup(this._toSVG(reviver), { reviver: reviver });\n },\n\n /**\n * Returns svg clipPath representation of an instance\n * @param {Function} [reviver] Method for further parsing of svg representation.\n * @return {String} svg representation of an instance\n */\n toClipPathSVG: function(reviver) {\n return '\\t' + this._createBaseClipPathSVGMarkup(this._toSVG(reviver), { reviver: reviver });\n },\n\n /**\n * @private\n */\n _createBaseClipPathSVGMarkup: function(objectMarkup, options) {\n options = options || {};\n var reviver = options.reviver,\n additionalTransform = options.additionalTransform || '',\n commonPieces = [\n this.getSvgTransform(true, additionalTransform),\n this.getSvgCommons(),\n ].join(''),\n // insert commons in the markup, style and svgCommons\n index = objectMarkup.indexOf('COMMON_PARTS');\n objectMarkup[index] = commonPieces;\n return reviver ? reviver(objectMarkup.join('')) : objectMarkup.join('');\n },\n\n /**\n * @private\n */\n _createBaseSVGMarkup: function(objectMarkup, options) {\n options = options || {};\n var noStyle = options.noStyle,\n reviver = options.reviver,\n styleInfo = noStyle ? '' : 'style=\"' + this.getSvgStyles() + '\" ',\n shadowInfo = options.withShadow ? 'style=\"' + this.getSvgFilter() + '\" ' : '',\n clipPath = this.clipPath,\n vectorEffect = this.strokeUniform ? 'vector-effect=\"non-scaling-stroke\" ' : '',\n absoluteClipPath = clipPath && clipPath.absolutePositioned,\n stroke = this.stroke, fill = this.fill, shadow = this.shadow,\n commonPieces, markup = [], clipPathMarkup,\n // insert commons in the markup, style and svgCommons\n index = objectMarkup.indexOf('COMMON_PARTS'),\n additionalTransform = options.additionalTransform;\n if (clipPath) {\n clipPath.clipPathId = 'CLIPPATH_' + fabric.Object.__uid++;\n clipPathMarkup = '\\n' +\n clipPath.toClipPathSVG(reviver) +\n '\\n';\n }\n if (absoluteClipPath) {\n markup.push(\n '\\n'\n );\n }\n markup.push(\n '\\n'\n );\n commonPieces = [\n styleInfo,\n vectorEffect,\n noStyle ? '' : this.addPaintOrder(), ' ',\n additionalTransform ? 'transform=\"' + additionalTransform + '\" ' : '',\n ].join('');\n objectMarkup[index] = commonPieces;\n if (fill && fill.toLive) {\n markup.push(fill.toSVG(this));\n }\n if (stroke && stroke.toLive) {\n markup.push(stroke.toSVG(this));\n }\n if (shadow) {\n markup.push(shadow.toSVG(this));\n }\n if (clipPath) {\n markup.push(clipPathMarkup);\n }\n markup.push(objectMarkup.join(''));\n markup.push('\\n');\n absoluteClipPath && markup.push('\\n');\n return reviver ? reviver(markup.join('')) : markup.join('');\n },\n\n addPaintOrder: function() {\n return this.paintFirst !== 'fill' ? ' paint-order=\"' + this.paintFirst + '\" ' : '';\n }\n });\n})();\n/* _TO_SVG_END_ */\n\n\n(function() {\n\n var extend = fabric.util.object.extend,\n originalSet = 'stateProperties';\n\n /*\n Depends on `stateProperties`\n */\n function saveProps(origin, destination, props) {\n var tmpObj = { }, deep = true;\n props.forEach(function(prop) {\n tmpObj[prop] = origin[prop];\n });\n extend(origin[destination], tmpObj, deep);\n }\n\n function _isEqual(origValue, currentValue, firstPass) {\n if (origValue === currentValue) {\n // if the objects are identical, return\n return true;\n }\n else if (Array.isArray(origValue)) {\n if (!Array.isArray(currentValue) || origValue.length !== currentValue.length) {\n return false;\n }\n for (var i = 0, len = origValue.length; i < len; i++) {\n if (!_isEqual(origValue[i], currentValue[i])) {\n return false;\n }\n }\n return true;\n }\n else if (origValue && typeof origValue === 'object') {\n var keys = Object.keys(origValue), key;\n if (!currentValue ||\n typeof currentValue !== 'object' ||\n (!firstPass && keys.length !== Object.keys(currentValue).length)\n ) {\n return false;\n }\n for (var i = 0, len = keys.length; i < len; i++) {\n key = keys[i];\n // since clipPath is in the statefull cache list and the clipPath objects\n // would be iterated as an object, this would lead to possible infinite recursion\n if (key === 'canvas') {\n continue;\n }\n if (!_isEqual(origValue[key], currentValue[key])) {\n return false;\n }\n }\n return true;\n }\n }\n\n\n fabric.util.object.extend(fabric.Object.prototype, /** @lends fabric.Object.prototype */ {\n\n /**\n * Returns true if object state (one of its state properties) was changed\n * @param {String} [propertySet] optional name for the set of property we want to save\n * @return {Boolean} true if instance' state has changed since `{@link fabric.Object#saveState}` was called\n */\n hasStateChanged: function(propertySet) {\n propertySet = propertySet || originalSet;\n var dashedPropertySet = '_' + propertySet;\n if (Object.keys(this[dashedPropertySet]).length < this[propertySet].length) {\n return true;\n }\n return !_isEqual(this[dashedPropertySet], this, true);\n },\n\n /**\n * Saves state of an object\n * @param {Object} [options] Object with additional `stateProperties` array to include when saving state\n * @return {fabric.Object} thisArg\n */\n saveState: function(options) {\n var propertySet = options && options.propertySet || originalSet,\n destination = '_' + propertySet;\n if (!this[destination]) {\n return this.setupState(options);\n }\n saveProps(this, destination, this[propertySet]);\n if (options && options.stateProperties) {\n saveProps(this, destination, options.stateProperties);\n }\n return this;\n },\n\n /**\n * Setups state of an object\n * @param {Object} [options] Object with additional `stateProperties` array to include when saving state\n * @return {fabric.Object} thisArg\n */\n setupState: function(options) {\n options = options || { };\n var propertySet = options.propertySet || originalSet;\n options.propertySet = propertySet;\n this['_' + propertySet] = { };\n this.saveState(options);\n return this;\n }\n });\n})();\n\n\n(function() {\n\n var degreesToRadians = fabric.util.degreesToRadians;\n\n fabric.util.object.extend(fabric.Object.prototype, /** @lends fabric.Object.prototype */ {\n\n /**\n * The object interactivity controls.\n * @private\n */\n _controlsVisibility: null,\n\n /**\n * Determines which corner has been clicked\n * @private\n * @param {Object} pointer The pointer indicating the mouse position\n * @return {String|Boolean} corner code (tl, tr, bl, br, etc.), or false if nothing is found\n */\n _findTargetCorner: function(pointer) {\n // objects in group, anykind, are not self modificable,\n // must not return an hovered corner.\n if (!this.hasControls || this.group || (!this.canvas || this.canvas._activeObject !== this)) {\n return false;\n }\n\n var ex = pointer.x,\n ey = pointer.y,\n xPoints,\n lines;\n this.__corner = 0;\n for (var i in this.oCoords) {\n\n if (!this.isControlVisible(i)) {\n continue;\n }\n\n if (i === 'mtr' && !this.hasRotatingPoint) {\n continue;\n }\n\n if (this.get('lockUniScaling') &&\n (i === 'mt' || i === 'mr' || i === 'mb' || i === 'ml')) {\n continue;\n }\n\n lines = this._getImageLines(this.oCoords[i].corner);\n\n // debugging\n\n // canvas.contextTop.fillRect(lines.bottomline.d.x, lines.bottomline.d.y, 2, 2);\n // canvas.contextTop.fillRect(lines.bottomline.o.x, lines.bottomline.o.y, 2, 2);\n\n // canvas.contextTop.fillRect(lines.leftline.d.x, lines.leftline.d.y, 2, 2);\n // canvas.contextTop.fillRect(lines.leftline.o.x, lines.leftline.o.y, 2, 2);\n\n // canvas.contextTop.fillRect(lines.topline.d.x, lines.topline.d.y, 2, 2);\n // canvas.contextTop.fillRect(lines.topline.o.x, lines.topline.o.y, 2, 2);\n\n // canvas.contextTop.fillRect(lines.rightline.d.x, lines.rightline.d.y, 2, 2);\n // canvas.contextTop.fillRect(lines.rightline.o.x, lines.rightline.o.y, 2, 2);\n\n xPoints = this._findCrossPoints({ x: ex, y: ey }, lines);\n if (xPoints !== 0 && xPoints % 2 === 1) {\n this.__corner = i;\n return i;\n }\n }\n return false;\n },\n\n /**\n * Sets the coordinates of the draggable boxes in the corners of\n * the image used to scale/rotate it.\n * @private\n */\n _setCornerCoords: function() {\n var coords = this.oCoords,\n newTheta = degreesToRadians(45 - this.angle),\n /* Math.sqrt(2 * Math.pow(this.cornerSize, 2)) / 2, */\n /* 0.707106 stands for sqrt(2)/2 */\n cornerHypotenuse = this.cornerSize * 0.707106,\n cosHalfOffset = cornerHypotenuse * fabric.util.cos(newTheta),\n sinHalfOffset = cornerHypotenuse * fabric.util.sin(newTheta),\n x, y;\n\n for (var point in coords) {\n x = coords[point].x;\n y = coords[point].y;\n coords[point].corner = {\n tl: {\n x: x - sinHalfOffset,\n y: y - cosHalfOffset\n },\n tr: {\n x: x + cosHalfOffset,\n y: y - sinHalfOffset\n },\n bl: {\n x: x - cosHalfOffset,\n y: y + sinHalfOffset\n },\n br: {\n x: x + sinHalfOffset,\n y: y + cosHalfOffset\n }\n };\n }\n },\n\n /**\n * Draws a colored layer behind the object, inside its selection borders.\n * Requires public options: padding, selectionBackgroundColor\n * this function is called when the context is transformed\n * has checks to be skipped when the object is on a staticCanvas\n * @param {CanvasRenderingContext2D} ctx Context to draw on\n * @return {fabric.Object} thisArg\n * @chainable\n */\n drawSelectionBackground: function(ctx) {\n if (!this.selectionBackgroundColor ||\n (this.canvas && !this.canvas.interactive) ||\n (this.canvas && this.canvas._activeObject !== this)\n ) {\n return this;\n }\n ctx.save();\n var center = this.getCenterPoint(), wh = this._calculateCurrentDimensions(),\n vpt = this.canvas.viewportTransform;\n ctx.translate(center.x, center.y);\n ctx.scale(1 / vpt[0], 1 / vpt[3]);\n ctx.rotate(degreesToRadians(this.angle));\n ctx.fillStyle = this.selectionBackgroundColor;\n ctx.fillRect(-wh.x / 2, -wh.y / 2, wh.x, wh.y);\n ctx.restore();\n return this;\n },\n\n /**\n * Draws borders of an object's bounding box.\n * Requires public properties: width, height\n * Requires public options: padding, borderColor\n * @param {CanvasRenderingContext2D} ctx Context to draw on\n * @param {Object} styleOverride object to override the object style\n * @return {fabric.Object} thisArg\n * @chainable\n */\n drawBorders: function(ctx, styleOverride) {\n styleOverride = styleOverride || {};\n var wh = this._calculateCurrentDimensions(),\n strokeWidth = this.borderScaleFactor,\n width = wh.x + strokeWidth,\n height = wh.y + strokeWidth,\n drawRotatingPoint = typeof styleOverride.hasRotatingPoint !== 'undefined' ?\n styleOverride.hasRotatingPoint : this.hasRotatingPoint,\n hasControls = typeof styleOverride.hasControls !== 'undefined' ?\n styleOverride.hasControls : this.hasControls,\n rotatingPointOffset = typeof styleOverride.rotatingPointOffset !== 'undefined' ?\n styleOverride.rotatingPointOffset : this.rotatingPointOffset;\n\n ctx.save();\n ctx.strokeStyle = styleOverride.borderColor || this.borderColor;\n this._setLineDash(ctx, styleOverride.borderDashArray || this.borderDashArray, null);\n\n ctx.strokeRect(\n -width / 2,\n -height / 2,\n width,\n height\n );\n\n if (drawRotatingPoint && this.isControlVisible('mtr') && hasControls) {\n\n var rotateHeight = -height / 2;\n\n ctx.beginPath();\n ctx.moveTo(0, rotateHeight);\n ctx.lineTo(0, rotateHeight - rotatingPointOffset);\n ctx.stroke();\n }\n\n ctx.restore();\n return this;\n },\n\n /**\n * Draws borders of an object's bounding box when it is inside a group.\n * Requires public properties: width, height\n * Requires public options: padding, borderColor\n * @param {CanvasRenderingContext2D} ctx Context to draw on\n * @param {object} options object representing current object parameters\n * @param {Object} styleOverride object to override the object style\n * @return {fabric.Object} thisArg\n * @chainable\n */\n drawBordersInGroup: function(ctx, options, styleOverride) {\n styleOverride = styleOverride || {};\n var p = { x: this.width, y: this.height },\n matrix = fabric.util.composeMatrix({\n scaleX: options.scaleX,\n scaleY: options.scaleY,\n skewX: options.skewX\n }),\n wh = fabric.util.transformPoint(p, matrix),\n strokeWidth = this.strokeWidth,\n borderScaleFactor = this.borderScaleFactor,\n width =\n wh.x + strokeWidth * (this.strokeUniform ? this.canvas.getZoom() : options.scaleX) + borderScaleFactor,\n height =\n wh.y + strokeWidth * (this.strokeUniform ? this.canvas.getZoom() : options.scaleY) + borderScaleFactor;\n ctx.save();\n this._setLineDash(ctx, styleOverride.borderDashArray || this.borderDashArray, null);\n ctx.strokeStyle = styleOverride.borderColor || this.borderColor;\n\n ctx.strokeRect(\n -width / 2,\n -height / 2,\n width,\n height\n );\n\n ctx.restore();\n return this;\n },\n\n /**\n * Draws corners of an object's bounding box.\n * Requires public properties: width, height\n * Requires public options: cornerSize, padding\n * @param {CanvasRenderingContext2D} ctx Context to draw on\n * @param {Object} styleOverride object to override the object style\n * @return {fabric.Object} thisArg\n * @chainable\n */\n drawControls: function(ctx, styleOverride) {\n styleOverride = styleOverride || {};\n var wh = this._calculateCurrentDimensions(),\n width = wh.x,\n height = wh.y,\n scaleOffset = styleOverride.cornerSize || this.cornerSize,\n left = -(width + scaleOffset) / 2,\n top = -(height + scaleOffset) / 2,\n transparentCorners = typeof styleOverride.transparentCorners !== 'undefined' ?\n styleOverride.transparentCorners : this.transparentCorners,\n hasRotatingPoint = typeof styleOverride.hasRotatingPoint !== 'undefined' ?\n styleOverride.hasRotatingPoint : this.hasRotatingPoint,\n methodName = transparentCorners ? 'stroke' : 'fill';\n\n ctx.save();\n ctx.strokeStyle = ctx.fillStyle = styleOverride.cornerColor || this.cornerColor;\n if (!this.transparentCorners) {\n ctx.strokeStyle = styleOverride.cornerStrokeColor || this.cornerStrokeColor;\n }\n this._setLineDash(ctx, styleOverride.cornerDashArray || this.cornerDashArray, null);\n\n // top-left\n this._drawControl('tl', ctx, methodName,\n left,\n top, styleOverride);\n\n // top-right\n this._drawControl('tr', ctx, methodName,\n left + width,\n top, styleOverride);\n\n // bottom-left\n this._drawControl('bl', ctx, methodName,\n left,\n top + height, styleOverride);\n\n // bottom-right\n this._drawControl('br', ctx, methodName,\n left + width,\n top + height, styleOverride);\n\n if (!this.get('lockUniScaling')) {\n\n // middle-top\n this._drawControl('mt', ctx, methodName,\n left + width / 2,\n top, styleOverride);\n\n // middle-bottom\n this._drawControl('mb', ctx, methodName,\n left + width / 2,\n top + height, styleOverride);\n\n // middle-right\n this._drawControl('mr', ctx, methodName,\n left + width,\n top + height / 2, styleOverride);\n\n // middle-left\n this._drawControl('ml', ctx, methodName,\n left,\n top + height / 2, styleOverride);\n }\n\n // middle-top-rotate\n if (hasRotatingPoint) {\n this._drawControl('mtr', ctx, methodName,\n left + width / 2,\n top - this.rotatingPointOffset, styleOverride);\n }\n\n ctx.restore();\n\n return this;\n },\n\n /**\n * @private\n */\n _drawControl: function(control, ctx, methodName, left, top, styleOverride) {\n styleOverride = styleOverride || {};\n if (!this.isControlVisible(control)) {\n return;\n }\n var size = this.cornerSize, stroke = !this.transparentCorners && this.cornerStrokeColor;\n switch (styleOverride.cornerStyle || this.cornerStyle) {\n case 'circle':\n ctx.beginPath();\n ctx.arc(left + size / 2, top + size / 2, size / 2, 0, 2 * Math.PI, false);\n ctx[methodName]();\n if (stroke) {\n ctx.stroke();\n }\n break;\n default:\n this.transparentCorners || ctx.clearRect(left, top, size, size);\n ctx[methodName + 'Rect'](left, top, size, size);\n if (stroke) {\n ctx.strokeRect(left, top, size, size);\n }\n }\n },\n\n /**\n * Returns true if the specified control is visible, false otherwise.\n * @param {String} controlName The name of the control. Possible values are 'tl', 'tr', 'br', 'bl', 'ml', 'mt', 'mr', 'mb', 'mtr'.\n * @returns {Boolean} true if the specified control is visible, false otherwise\n */\n isControlVisible: function(controlName) {\n return this._getControlsVisibility()[controlName];\n },\n\n /**\n * Sets the visibility of the specified control.\n * @param {String} controlName The name of the control. Possible values are 'tl', 'tr', 'br', 'bl', 'ml', 'mt', 'mr', 'mb', 'mtr'.\n * @param {Boolean} visible true to set the specified control visible, false otherwise\n * @return {fabric.Object} thisArg\n * @chainable\n */\n setControlVisible: function(controlName, visible) {\n this._getControlsVisibility()[controlName] = visible;\n return this;\n },\n\n /**\n * Sets the visibility state of object controls.\n * @param {Object} [options] Options object\n * @param {Boolean} [options.bl] true to enable the bottom-left control, false to disable it\n * @param {Boolean} [options.br] true to enable the bottom-right control, false to disable it\n * @param {Boolean} [options.mb] true to enable the middle-bottom control, false to disable it\n * @param {Boolean} [options.ml] true to enable the middle-left control, false to disable it\n * @param {Boolean} [options.mr] true to enable the middle-right control, false to disable it\n * @param {Boolean} [options.mt] true to enable the middle-top control, false to disable it\n * @param {Boolean} [options.tl] true to enable the top-left control, false to disable it\n * @param {Boolean} [options.tr] true to enable the top-right control, false to disable it\n * @param {Boolean} [options.mtr] true to enable the middle-top-rotate control, false to disable it\n * @return {fabric.Object} thisArg\n * @chainable\n */\n setControlsVisibility: function(options) {\n options || (options = { });\n\n for (var p in options) {\n this.setControlVisible(p, options[p]);\n }\n return this;\n },\n\n /**\n * Returns the instance of the control visibility set for this object.\n * @private\n * @returns {Object}\n */\n _getControlsVisibility: function() {\n if (!this._controlsVisibility) {\n this._controlsVisibility = {\n tl: true,\n tr: true,\n br: true,\n bl: true,\n ml: true,\n mt: true,\n mr: true,\n mb: true,\n mtr: true\n };\n }\n return this._controlsVisibility;\n },\n\n /**\n * This callback function is called every time _discardActiveObject or _setActiveObject\n * try to to deselect this object. If the function returns true, the process is cancelled\n * @param {Object} [options] options sent from the upper functions\n * @param {Event} [options.e] event if the process is generated by an event\n */\n onDeselect: function() {\n // implemented by sub-classes, as needed.\n },\n\n\n /**\n * This callback function is called every time _discardActiveObject or _setActiveObject\n * try to to select this object. If the function returns true, the process is cancelled\n * @param {Object} [options] options sent from the upper functions\n * @param {Event} [options.e] event if the process is generated by an event\n */\n onSelect: function() {\n // implemented by sub-classes, as needed.\n }\n });\n})();\n\n\nfabric.util.object.extend(fabric.StaticCanvas.prototype, /** @lends fabric.StaticCanvas.prototype */ {\n\n /**\n * Animation duration (in ms) for fx* methods\n * @type Number\n * @default\n */\n FX_DURATION: 500,\n\n /**\n * Centers object horizontally with animation.\n * @param {fabric.Object} object Object to center\n * @param {Object} [callbacks] Callbacks object with optional \"onComplete\" and/or \"onChange\" properties\n * @param {Function} [callbacks.onComplete] Invoked on completion\n * @param {Function} [callbacks.onChange] Invoked on every step of animation\n * @return {fabric.Canvas} thisArg\n * @chainable\n */\n fxCenterObjectH: function (object, callbacks) {\n callbacks = callbacks || { };\n\n var empty = function() { },\n onComplete = callbacks.onComplete || empty,\n onChange = callbacks.onChange || empty,\n _this = this;\n\n fabric.util.animate({\n startValue: object.left,\n endValue: this.getCenter().left,\n duration: this.FX_DURATION,\n onChange: function(value) {\n object.set('left', value);\n _this.requestRenderAll();\n onChange();\n },\n onComplete: function() {\n object.setCoords();\n onComplete();\n }\n });\n\n return this;\n },\n\n /**\n * Centers object vertically with animation.\n * @param {fabric.Object} object Object to center\n * @param {Object} [callbacks] Callbacks object with optional \"onComplete\" and/or \"onChange\" properties\n * @param {Function} [callbacks.onComplete] Invoked on completion\n * @param {Function} [callbacks.onChange] Invoked on every step of animation\n * @return {fabric.Canvas} thisArg\n * @chainable\n */\n fxCenterObjectV: function (object, callbacks) {\n callbacks = callbacks || { };\n\n var empty = function() { },\n onComplete = callbacks.onComplete || empty,\n onChange = callbacks.onChange || empty,\n _this = this;\n\n fabric.util.animate({\n startValue: object.top,\n endValue: this.getCenter().top,\n duration: this.FX_DURATION,\n onChange: function(value) {\n object.set('top', value);\n _this.requestRenderAll();\n onChange();\n },\n onComplete: function() {\n object.setCoords();\n onComplete();\n }\n });\n\n return this;\n },\n\n /**\n * Same as `fabric.Canvas#remove` but animated\n * @param {fabric.Object} object Object to remove\n * @param {Object} [callbacks] Callbacks object with optional \"onComplete\" and/or \"onChange\" properties\n * @param {Function} [callbacks.onComplete] Invoked on completion\n * @param {Function} [callbacks.onChange] Invoked on every step of animation\n * @return {fabric.Canvas} thisArg\n * @chainable\n */\n fxRemove: function (object, callbacks) {\n callbacks = callbacks || { };\n\n var empty = function() { },\n onComplete = callbacks.onComplete || empty,\n onChange = callbacks.onChange || empty,\n _this = this;\n\n fabric.util.animate({\n startValue: object.opacity,\n endValue: 0,\n duration: this.FX_DURATION,\n onChange: function(value) {\n object.set('opacity', value);\n _this.requestRenderAll();\n onChange();\n },\n onComplete: function () {\n _this.remove(object);\n onComplete();\n }\n });\n\n return this;\n }\n});\n\nfabric.util.object.extend(fabric.Object.prototype, /** @lends fabric.Object.prototype */ {\n /**\n * Animates object's properties\n * @param {String|Object} property Property to animate (if string) or properties to animate (if object)\n * @param {Number|Object} value Value to animate property to (if string was given first) or options object\n * @return {fabric.Object} thisArg\n * @tutorial {@link http://fabricjs.com/fabric-intro-part-2#animation}\n * @chainable\n *\n * As object — multiple properties\n *\n * object.animate({ left: ..., top: ... });\n * object.animate({ left: ..., top: ... }, { duration: ... });\n *\n * As string — one property\n *\n * object.animate('left', ...);\n * object.animate('left', { duration: ... });\n *\n */\n animate: function() {\n if (arguments[0] && typeof arguments[0] === 'object') {\n var propsToAnimate = [], prop, skipCallbacks;\n for (prop in arguments[0]) {\n propsToAnimate.push(prop);\n }\n for (var i = 0, len = propsToAnimate.length; i < len; i++) {\n prop = propsToAnimate[i];\n skipCallbacks = i !== len - 1;\n this._animate(prop, arguments[0][prop], arguments[1], skipCallbacks);\n }\n }\n else {\n this._animate.apply(this, arguments);\n }\n return this;\n },\n\n /**\n * @private\n * @param {String} property Property to animate\n * @param {String} to Value to animate to\n * @param {Object} [options] Options object\n * @param {Boolean} [skipCallbacks] When true, callbacks like onchange and oncomplete are not invoked\n */\n _animate: function(property, to, options, skipCallbacks) {\n var _this = this, propPair;\n\n to = to.toString();\n\n if (!options) {\n options = { };\n }\n else {\n options = fabric.util.object.clone(options);\n }\n\n if (~property.indexOf('.')) {\n propPair = property.split('.');\n }\n\n var currentValue = propPair\n ? this.get(propPair[0])[propPair[1]]\n : this.get(property);\n\n if (!('from' in options)) {\n options.from = currentValue;\n }\n\n if (~to.indexOf('=')) {\n to = currentValue + parseFloat(to.replace('=', ''));\n }\n else {\n to = parseFloat(to);\n }\n\n fabric.util.animate({\n startValue: options.from,\n endValue: to,\n byValue: options.by,\n easing: options.easing,\n duration: options.duration,\n abort: options.abort && function() {\n return options.abort.call(_this);\n },\n onChange: function(value, valueProgress, timeProgress) {\n if (propPair) {\n _this[propPair[0]][propPair[1]] = value;\n }\n else {\n _this.set(property, value);\n }\n if (skipCallbacks) {\n return;\n }\n options.onChange && options.onChange(value, valueProgress, timeProgress);\n },\n onComplete: function(value, valueProgress, timeProgress) {\n if (skipCallbacks) {\n return;\n }\n\n _this.setCoords();\n options.onComplete && options.onComplete(value, valueProgress, timeProgress);\n }\n });\n }\n});\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { }),\n extend = fabric.util.object.extend,\n clone = fabric.util.object.clone,\n coordProps = { x1: 1, x2: 1, y1: 1, y2: 1 },\n supportsLineDash = fabric.StaticCanvas.supports('setLineDash');\n\n if (fabric.Line) {\n fabric.warn('fabric.Line is already defined');\n return;\n }\n\n /**\n * Line class\n * @class fabric.Line\n * @extends fabric.Object\n * @see {@link fabric.Line#initialize} for constructor definition\n */\n fabric.Line = fabric.util.createClass(fabric.Object, /** @lends fabric.Line.prototype */ {\n\n /**\n * Type of an object\n * @type String\n * @default\n */\n type: 'line',\n\n /**\n * x value or first line edge\n * @type Number\n * @default\n */\n x1: 0,\n\n /**\n * y value or first line edge\n * @type Number\n * @default\n */\n y1: 0,\n\n /**\n * x value or second line edge\n * @type Number\n * @default\n */\n x2: 0,\n\n /**\n * y value or second line edge\n * @type Number\n * @default\n */\n y2: 0,\n\n cacheProperties: fabric.Object.prototype.cacheProperties.concat('x1', 'x2', 'y1', 'y2'),\n\n /**\n * Constructor\n * @param {Array} [points] Array of points\n * @param {Object} [options] Options object\n * @return {fabric.Line} thisArg\n */\n initialize: function(points, options) {\n if (!points) {\n points = [0, 0, 0, 0];\n }\n\n this.callSuper('initialize', options);\n\n this.set('x1', points[0]);\n this.set('y1', points[1]);\n this.set('x2', points[2]);\n this.set('y2', points[3]);\n\n this._setWidthHeight(options);\n },\n\n /**\n * @private\n * @param {Object} [options] Options\n */\n _setWidthHeight: function(options) {\n options || (options = { });\n\n this.width = Math.abs(this.x2 - this.x1);\n this.height = Math.abs(this.y2 - this.y1);\n\n this.left = 'left' in options\n ? options.left\n : this._getLeftToOriginX();\n\n this.top = 'top' in options\n ? options.top\n : this._getTopToOriginY();\n },\n\n /**\n * @private\n * @param {String} key\n * @param {*} value\n */\n _set: function(key, value) {\n this.callSuper('_set', key, value);\n if (typeof coordProps[key] !== 'undefined') {\n this._setWidthHeight();\n }\n return this;\n },\n\n /**\n * @private\n * @return {Number} leftToOriginX Distance from left edge of canvas to originX of Line.\n */\n _getLeftToOriginX: makeEdgeToOriginGetter(\n { // property names\n origin: 'originX',\n axis1: 'x1',\n axis2: 'x2',\n dimension: 'width'\n },\n { // possible values of origin\n nearest: 'left',\n center: 'center',\n farthest: 'right'\n }\n ),\n\n /**\n * @private\n * @return {Number} topToOriginY Distance from top edge of canvas to originY of Line.\n */\n _getTopToOriginY: makeEdgeToOriginGetter(\n { // property names\n origin: 'originY',\n axis1: 'y1',\n axis2: 'y2',\n dimension: 'height'\n },\n { // possible values of origin\n nearest: 'top',\n center: 'center',\n farthest: 'bottom'\n }\n ),\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _render: function(ctx) {\n ctx.beginPath();\n\n if (!this.strokeDashArray || this.strokeDashArray && supportsLineDash) {\n // move from center (of virtual box) to its left/top corner\n // we can't assume x1, y1 is top left and x2, y2 is bottom right\n var p = this.calcLinePoints();\n ctx.moveTo(p.x1, p.y1);\n ctx.lineTo(p.x2, p.y2);\n }\n\n ctx.lineWidth = this.strokeWidth;\n\n // TODO: test this\n // make sure setting \"fill\" changes color of a line\n // (by copying fillStyle to strokeStyle, since line is stroked, not filled)\n var origStrokeStyle = ctx.strokeStyle;\n ctx.strokeStyle = this.stroke || ctx.fillStyle;\n this.stroke && this._renderStroke(ctx);\n ctx.strokeStyle = origStrokeStyle;\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _renderDashedStroke: function(ctx) {\n var p = this.calcLinePoints();\n\n ctx.beginPath();\n fabric.util.drawDashedLine(ctx, p.x1, p.y1, p.x2, p.y2, this.strokeDashArray);\n ctx.closePath();\n },\n\n /**\n * This function is an helper for svg import. it returns the center of the object in the svg\n * untransformed coordinates\n * @private\n * @return {Object} center point from element coordinates\n */\n _findCenterFromElement: function() {\n return {\n x: (this.x1 + this.x2) / 2,\n y: (this.y1 + this.y2) / 2,\n };\n },\n\n /**\n * Returns object representation of an instance\n * @methd toObject\n * @param {Array} [propertiesToInclude] Any properties that you might want to additionally include in the output\n * @return {Object} object representation of an instance\n */\n toObject: function(propertiesToInclude) {\n return extend(this.callSuper('toObject', propertiesToInclude), this.calcLinePoints());\n },\n\n /*\n * Calculate object dimensions from its properties\n * @private\n */\n _getNonTransformedDimensions: function() {\n var dim = this.callSuper('_getNonTransformedDimensions');\n if (this.strokeLineCap === 'butt') {\n if (this.width === 0) {\n dim.y -= this.strokeWidth;\n }\n if (this.height === 0) {\n dim.x -= this.strokeWidth;\n }\n }\n return dim;\n },\n\n /**\n * Recalculates line points given width and height\n * @private\n */\n calcLinePoints: function() {\n var xMult = this.x1 <= this.x2 ? -1 : 1,\n yMult = this.y1 <= this.y2 ? -1 : 1,\n x1 = (xMult * this.width * 0.5),\n y1 = (yMult * this.height * 0.5),\n x2 = (xMult * this.width * -0.5),\n y2 = (yMult * this.height * -0.5);\n\n return {\n x1: x1,\n x2: x2,\n y1: y1,\n y2: y2\n };\n },\n\n /* _TO_SVG_START_ */\n /**\n * Returns svg representation of an instance\n * @return {Array} an array of strings with the specific svg representation\n * of the instance\n */\n _toSVG: function() {\n var p = this.calcLinePoints();\n return [\n '\\n'\n ];\n },\n /* _TO_SVG_END_ */\n });\n\n /* _FROM_SVG_START_ */\n /**\n * List of attribute names to account for when parsing SVG element (used by {@link fabric.Line.fromElement})\n * @static\n * @memberOf fabric.Line\n * @see http://www.w3.org/TR/SVG/shapes.html#LineElement\n */\n fabric.Line.ATTRIBUTE_NAMES = fabric.SHARED_ATTRIBUTES.concat('x1 y1 x2 y2'.split(' '));\n\n /**\n * Returns fabric.Line instance from an SVG element\n * @static\n * @memberOf fabric.Line\n * @param {SVGElement} element Element to parse\n * @param {Object} [options] Options object\n * @param {Function} [callback] callback function invoked after parsing\n */\n fabric.Line.fromElement = function(element, callback, options) {\n options = options || { };\n var parsedAttributes = fabric.parseAttributes(element, fabric.Line.ATTRIBUTE_NAMES),\n points = [\n parsedAttributes.x1 || 0,\n parsedAttributes.y1 || 0,\n parsedAttributes.x2 || 0,\n parsedAttributes.y2 || 0\n ];\n callback(new fabric.Line(points, extend(parsedAttributes, options)));\n };\n /* _FROM_SVG_END_ */\n\n /**\n * Returns fabric.Line instance from an object representation\n * @static\n * @memberOf fabric.Line\n * @param {Object} object Object to create an instance from\n * @param {function} [callback] invoked with new instance as first argument\n */\n fabric.Line.fromObject = function(object, callback) {\n function _callback(instance) {\n delete instance.points;\n callback && callback(instance);\n };\n var options = clone(object, true);\n options.points = [object.x1, object.y1, object.x2, object.y2];\n fabric.Object._fromObject('Line', options, _callback, 'points');\n };\n\n /**\n * Produces a function that calculates distance from canvas edge to Line origin.\n */\n function makeEdgeToOriginGetter(propertyNames, originValues) {\n var origin = propertyNames.origin,\n axis1 = propertyNames.axis1,\n axis2 = propertyNames.axis2,\n dimension = propertyNames.dimension,\n nearest = originValues.nearest,\n center = originValues.center,\n farthest = originValues.farthest;\n\n return function() {\n switch (this.get(origin)) {\n case nearest:\n return Math.min(this.get(axis1), this.get(axis2));\n case center:\n return Math.min(this.get(axis1), this.get(axis2)) + (0.5 * this.get(dimension));\n case farthest:\n return Math.max(this.get(axis1), this.get(axis2));\n }\n };\n\n }\n\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { }),\n pi = Math.PI;\n\n if (fabric.Circle) {\n fabric.warn('fabric.Circle is already defined.');\n return;\n }\n\n /**\n * Circle class\n * @class fabric.Circle\n * @extends fabric.Object\n * @see {@link fabric.Circle#initialize} for constructor definition\n */\n fabric.Circle = fabric.util.createClass(fabric.Object, /** @lends fabric.Circle.prototype */ {\n\n /**\n * Type of an object\n * @type String\n * @default\n */\n type: 'circle',\n\n /**\n * Radius of this circle\n * @type Number\n * @default\n */\n radius: 0,\n\n /**\n * Start angle of the circle, moving clockwise\n * deprectated type, this should be in degree, this was an oversight.\n * probably will change to degrees in next major version\n * @type Number\n * @default 0\n */\n startAngle: 0,\n\n /**\n * End angle of the circle\n * deprectated type, this should be in degree, this was an oversight.\n * probably will change to degrees in next major version\n * @type Number\n * @default 2Pi\n */\n endAngle: pi * 2,\n\n cacheProperties: fabric.Object.prototype.cacheProperties.concat('radius', 'startAngle', 'endAngle'),\n\n /**\n * @private\n * @param {String} key\n * @param {*} value\n * @return {fabric.Circle} thisArg\n */\n _set: function(key, value) {\n this.callSuper('_set', key, value);\n\n if (key === 'radius') {\n this.setRadius(value);\n }\n\n return this;\n },\n\n /**\n * Returns object representation of an instance\n * @param {Array} [propertiesToInclude] Any properties that you might want to additionally include in the output\n * @return {Object} object representation of an instance\n */\n toObject: function(propertiesToInclude) {\n return this.callSuper('toObject', ['radius', 'startAngle', 'endAngle'].concat(propertiesToInclude));\n },\n\n /* _TO_SVG_START_ */\n\n /**\n * Returns svg representation of an instance\n * @return {Array} an array of strings with the specific svg representation\n * of the instance\n */\n _toSVG: function() {\n var svgString, x = 0, y = 0,\n angle = (this.endAngle - this.startAngle) % ( 2 * pi);\n\n if (angle === 0) {\n svgString = [\n '\\n'\n ];\n }\n else {\n var startX = fabric.util.cos(this.startAngle) * this.radius,\n startY = fabric.util.sin(this.startAngle) * this.radius,\n endX = fabric.util.cos(this.endAngle) * this.radius,\n endY = fabric.util.sin(this.endAngle) * this.radius,\n largeFlag = angle > pi ? '1' : '0';\n svgString = [\n '\\n'\n ];\n }\n return svgString;\n },\n /* _TO_SVG_END_ */\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx context to render on\n */\n _render: function(ctx) {\n ctx.beginPath();\n ctx.arc(\n 0,\n 0,\n this.radius,\n this.startAngle,\n this.endAngle, false);\n this._renderPaintInOrder(ctx);\n },\n\n /**\n * Returns horizontal radius of an object (according to how an object is scaled)\n * @return {Number}\n */\n getRadiusX: function() {\n return this.get('radius') * this.get('scaleX');\n },\n\n /**\n * Returns vertical radius of an object (according to how an object is scaled)\n * @return {Number}\n */\n getRadiusY: function() {\n return this.get('radius') * this.get('scaleY');\n },\n\n /**\n * Sets radius of an object (and updates width accordingly)\n * @return {fabric.Circle} thisArg\n */\n setRadius: function(value) {\n this.radius = value;\n return this.set('width', value * 2).set('height', value * 2);\n },\n });\n\n /* _FROM_SVG_START_ */\n /**\n * List of attribute names to account for when parsing SVG element (used by {@link fabric.Circle.fromElement})\n * @static\n * @memberOf fabric.Circle\n * @see: http://www.w3.org/TR/SVG/shapes.html#CircleElement\n */\n fabric.Circle.ATTRIBUTE_NAMES = fabric.SHARED_ATTRIBUTES.concat('cx cy r'.split(' '));\n\n /**\n * Returns {@link fabric.Circle} instance from an SVG element\n * @static\n * @memberOf fabric.Circle\n * @param {SVGElement} element Element to parse\n * @param {Function} [callback] Options callback invoked after parsing is finished\n * @param {Object} [options] Options object\n * @throws {Error} If value of `r` attribute is missing or invalid\n */\n fabric.Circle.fromElement = function(element, callback) {\n var parsedAttributes = fabric.parseAttributes(element, fabric.Circle.ATTRIBUTE_NAMES);\n\n if (!isValidRadius(parsedAttributes)) {\n throw new Error('value of `r` attribute is required and can not be negative');\n }\n\n parsedAttributes.left = (parsedAttributes.left || 0) - parsedAttributes.radius;\n parsedAttributes.top = (parsedAttributes.top || 0) - parsedAttributes.radius;\n callback(new fabric.Circle(parsedAttributes));\n };\n\n /**\n * @private\n */\n function isValidRadius(attributes) {\n return (('radius' in attributes) && (attributes.radius >= 0));\n }\n /* _FROM_SVG_END_ */\n\n /**\n * Returns {@link fabric.Circle} instance from an object representation\n * @static\n * @memberOf fabric.Circle\n * @param {Object} object Object to create an instance from\n * @param {function} [callback] invoked with new instance as first argument\n * @return {Object} Instance of fabric.Circle\n */\n fabric.Circle.fromObject = function(object, callback) {\n return fabric.Object._fromObject('Circle', object, callback);\n };\n\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { });\n\n if (fabric.Triangle) {\n fabric.warn('fabric.Triangle is already defined');\n return;\n }\n\n /**\n * Triangle class\n * @class fabric.Triangle\n * @extends fabric.Object\n * @return {fabric.Triangle} thisArg\n * @see {@link fabric.Triangle#initialize} for constructor definition\n */\n fabric.Triangle = fabric.util.createClass(fabric.Object, /** @lends fabric.Triangle.prototype */ {\n\n /**\n * Type of an object\n * @type String\n * @default\n */\n type: 'triangle',\n\n /**\n * Width is set to 100 to compensate the old initialize code that was setting it to 100\n * @type Number\n * @default\n */\n width: 100,\n\n /**\n * Height is set to 100 to compensate the old initialize code that was setting it to 100\n * @type Number\n * @default\n */\n height: 100,\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _render: function(ctx) {\n var widthBy2 = this.width / 2,\n heightBy2 = this.height / 2;\n\n ctx.beginPath();\n ctx.moveTo(-widthBy2, heightBy2);\n ctx.lineTo(0, -heightBy2);\n ctx.lineTo(widthBy2, heightBy2);\n ctx.closePath();\n\n this._renderPaintInOrder(ctx);\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _renderDashedStroke: function(ctx) {\n var widthBy2 = this.width / 2,\n heightBy2 = this.height / 2;\n\n ctx.beginPath();\n fabric.util.drawDashedLine(ctx, -widthBy2, heightBy2, 0, -heightBy2, this.strokeDashArray);\n fabric.util.drawDashedLine(ctx, 0, -heightBy2, widthBy2, heightBy2, this.strokeDashArray);\n fabric.util.drawDashedLine(ctx, widthBy2, heightBy2, -widthBy2, heightBy2, this.strokeDashArray);\n ctx.closePath();\n },\n\n /* _TO_SVG_START_ */\n /**\n * Returns svg representation of an instance\n * @return {Array} an array of strings with the specific svg representation\n * of the instance\n */\n _toSVG: function() {\n var widthBy2 = this.width / 2,\n heightBy2 = this.height / 2,\n points = [\n -widthBy2 + ' ' + heightBy2,\n '0 ' + -heightBy2,\n widthBy2 + ' ' + heightBy2\n ].join(',');\n return [\n ''\n ];\n },\n /* _TO_SVG_END_ */\n });\n\n /**\n * Returns {@link fabric.Triangle} instance from an object representation\n * @static\n * @memberOf fabric.Triangle\n * @param {Object} object Object to create an instance from\n * @param {function} [callback] invoked with new instance as first argument\n */\n fabric.Triangle.fromObject = function(object, callback) {\n return fabric.Object._fromObject('Triangle', object, callback);\n };\n\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { }),\n piBy2 = Math.PI * 2;\n\n if (fabric.Ellipse) {\n fabric.warn('fabric.Ellipse is already defined.');\n return;\n }\n\n /**\n * Ellipse class\n * @class fabric.Ellipse\n * @extends fabric.Object\n * @return {fabric.Ellipse} thisArg\n * @see {@link fabric.Ellipse#initialize} for constructor definition\n */\n fabric.Ellipse = fabric.util.createClass(fabric.Object, /** @lends fabric.Ellipse.prototype */ {\n\n /**\n * Type of an object\n * @type String\n * @default\n */\n type: 'ellipse',\n\n /**\n * Horizontal radius\n * @type Number\n * @default\n */\n rx: 0,\n\n /**\n * Vertical radius\n * @type Number\n * @default\n */\n ry: 0,\n\n cacheProperties: fabric.Object.prototype.cacheProperties.concat('rx', 'ry'),\n\n /**\n * Constructor\n * @param {Object} [options] Options object\n * @return {fabric.Ellipse} thisArg\n */\n initialize: function(options) {\n this.callSuper('initialize', options);\n this.set('rx', options && options.rx || 0);\n this.set('ry', options && options.ry || 0);\n },\n\n /**\n * @private\n * @param {String} key\n * @param {*} value\n * @return {fabric.Ellipse} thisArg\n */\n _set: function(key, value) {\n this.callSuper('_set', key, value);\n switch (key) {\n\n case 'rx':\n this.rx = value;\n this.set('width', value * 2);\n break;\n\n case 'ry':\n this.ry = value;\n this.set('height', value * 2);\n break;\n\n }\n return this;\n },\n\n /**\n * Returns horizontal radius of an object (according to how an object is scaled)\n * @return {Number}\n */\n getRx: function() {\n return this.get('rx') * this.get('scaleX');\n },\n\n /**\n * Returns Vertical radius of an object (according to how an object is scaled)\n * @return {Number}\n */\n getRy: function() {\n return this.get('ry') * this.get('scaleY');\n },\n\n /**\n * Returns object representation of an instance\n * @param {Array} [propertiesToInclude] Any properties that you might want to additionally include in the output\n * @return {Object} object representation of an instance\n */\n toObject: function(propertiesToInclude) {\n return this.callSuper('toObject', ['rx', 'ry'].concat(propertiesToInclude));\n },\n\n /* _TO_SVG_START_ */\n /**\n * Returns svg representation of an instance\n * @return {Array} an array of strings with the specific svg representation\n * of the instance\n */\n _toSVG: function() {\n return [\n '\\n'\n ];\n },\n /* _TO_SVG_END_ */\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx context to render on\n */\n _render: function(ctx) {\n ctx.beginPath();\n ctx.save();\n ctx.transform(1, 0, 0, this.ry / this.rx, 0, 0);\n ctx.arc(\n 0,\n 0,\n this.rx,\n 0,\n piBy2,\n false);\n ctx.restore();\n this._renderPaintInOrder(ctx);\n },\n });\n\n /* _FROM_SVG_START_ */\n /**\n * List of attribute names to account for when parsing SVG element (used by {@link fabric.Ellipse.fromElement})\n * @static\n * @memberOf fabric.Ellipse\n * @see http://www.w3.org/TR/SVG/shapes.html#EllipseElement\n */\n fabric.Ellipse.ATTRIBUTE_NAMES = fabric.SHARED_ATTRIBUTES.concat('cx cy rx ry'.split(' '));\n\n /**\n * Returns {@link fabric.Ellipse} instance from an SVG element\n * @static\n * @memberOf fabric.Ellipse\n * @param {SVGElement} element Element to parse\n * @param {Function} [callback] Options callback invoked after parsing is finished\n * @return {fabric.Ellipse}\n */\n fabric.Ellipse.fromElement = function(element, callback) {\n\n var parsedAttributes = fabric.parseAttributes(element, fabric.Ellipse.ATTRIBUTE_NAMES);\n\n parsedAttributes.left = (parsedAttributes.left || 0) - parsedAttributes.rx;\n parsedAttributes.top = (parsedAttributes.top || 0) - parsedAttributes.ry;\n callback(new fabric.Ellipse(parsedAttributes));\n };\n /* _FROM_SVG_END_ */\n\n /**\n * Returns {@link fabric.Ellipse} instance from an object representation\n * @static\n * @memberOf fabric.Ellipse\n * @param {Object} object Object to create an instance from\n * @param {function} [callback] invoked with new instance as first argument\n * @return {fabric.Ellipse}\n */\n fabric.Ellipse.fromObject = function(object, callback) {\n return fabric.Object._fromObject('Ellipse', object, callback);\n };\n\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { }),\n extend = fabric.util.object.extend;\n\n if (fabric.Rect) {\n fabric.warn('fabric.Rect is already defined');\n return;\n }\n\n /**\n * Rectangle class\n * @class fabric.Rect\n * @extends fabric.Object\n * @return {fabric.Rect} thisArg\n * @see {@link fabric.Rect#initialize} for constructor definition\n */\n fabric.Rect = fabric.util.createClass(fabric.Object, /** @lends fabric.Rect.prototype */ {\n\n /**\n * List of properties to consider when checking if state of an object is changed ({@link fabric.Object#hasStateChanged})\n * as well as for history (undo/redo) purposes\n * @type Array\n */\n stateProperties: fabric.Object.prototype.stateProperties.concat('rx', 'ry'),\n\n /**\n * Type of an object\n * @type String\n * @default\n */\n type: 'rect',\n\n /**\n * Horizontal border radius\n * @type Number\n * @default\n */\n rx: 0,\n\n /**\n * Vertical border radius\n * @type Number\n * @default\n */\n ry: 0,\n\n cacheProperties: fabric.Object.prototype.cacheProperties.concat('rx', 'ry'),\n\n /**\n * Constructor\n * @param {Object} [options] Options object\n * @return {Object} thisArg\n */\n initialize: function(options) {\n this.callSuper('initialize', options);\n this._initRxRy();\n },\n\n /**\n * Initializes rx/ry attributes\n * @private\n */\n _initRxRy: function() {\n if (this.rx && !this.ry) {\n this.ry = this.rx;\n }\n else if (this.ry && !this.rx) {\n this.rx = this.ry;\n }\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _render: function(ctx) {\n\n // 1x1 case (used in spray brush) optimization was removed because\n // with caching and higher zoom level this makes more damage than help\n\n var rx = this.rx ? Math.min(this.rx, this.width / 2) : 0,\n ry = this.ry ? Math.min(this.ry, this.height / 2) : 0,\n w = this.width,\n h = this.height,\n x = -this.width / 2,\n y = -this.height / 2,\n isRounded = rx !== 0 || ry !== 0,\n /* \"magic number\" for bezier approximations of arcs (http://itc.ktu.lt/itc354/Riskus354.pdf) */\n k = 1 - 0.5522847498;\n ctx.beginPath();\n\n ctx.moveTo(x + rx, y);\n\n ctx.lineTo(x + w - rx, y);\n isRounded && ctx.bezierCurveTo(x + w - k * rx, y, x + w, y + k * ry, x + w, y + ry);\n\n ctx.lineTo(x + w, y + h - ry);\n isRounded && ctx.bezierCurveTo(x + w, y + h - k * ry, x + w - k * rx, y + h, x + w - rx, y + h);\n\n ctx.lineTo(x + rx, y + h);\n isRounded && ctx.bezierCurveTo(x + k * rx, y + h, x, y + h - k * ry, x, y + h - ry);\n\n ctx.lineTo(x, y + ry);\n isRounded && ctx.bezierCurveTo(x, y + k * ry, x + k * rx, y, x + rx, y);\n\n ctx.closePath();\n\n this._renderPaintInOrder(ctx);\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _renderDashedStroke: function(ctx) {\n var x = -this.width / 2,\n y = -this.height / 2,\n w = this.width,\n h = this.height;\n\n ctx.beginPath();\n fabric.util.drawDashedLine(ctx, x, y, x + w, y, this.strokeDashArray);\n fabric.util.drawDashedLine(ctx, x + w, y, x + w, y + h, this.strokeDashArray);\n fabric.util.drawDashedLine(ctx, x + w, y + h, x, y + h, this.strokeDashArray);\n fabric.util.drawDashedLine(ctx, x, y + h, x, y, this.strokeDashArray);\n ctx.closePath();\n },\n\n /**\n * Returns object representation of an instance\n * @param {Array} [propertiesToInclude] Any properties that you might want to additionally include in the output\n * @return {Object} object representation of an instance\n */\n toObject: function(propertiesToInclude) {\n return this.callSuper('toObject', ['rx', 'ry'].concat(propertiesToInclude));\n },\n\n /* _TO_SVG_START_ */\n /**\n * Returns svg representation of an instance\n * @return {Array} an array of strings with the specific svg representation\n * of the instance\n */\n _toSVG: function() {\n var x = -this.width / 2, y = -this.height / 2;\n return [\n '\\n'\n ];\n },\n /* _TO_SVG_END_ */\n });\n\n /* _FROM_SVG_START_ */\n /**\n * List of attribute names to account for when parsing SVG element (used by `fabric.Rect.fromElement`)\n * @static\n * @memberOf fabric.Rect\n * @see: http://www.w3.org/TR/SVG/shapes.html#RectElement\n */\n fabric.Rect.ATTRIBUTE_NAMES = fabric.SHARED_ATTRIBUTES.concat('x y rx ry width height'.split(' '));\n\n /**\n * Returns {@link fabric.Rect} instance from an SVG element\n * @static\n * @memberOf fabric.Rect\n * @param {SVGElement} element Element to parse\n * @param {Function} callback callback function invoked after parsing\n * @param {Object} [options] Options object\n */\n fabric.Rect.fromElement = function(element, callback, options) {\n if (!element) {\n return callback(null);\n }\n options = options || { };\n\n var parsedAttributes = fabric.parseAttributes(element, fabric.Rect.ATTRIBUTE_NAMES);\n\n parsedAttributes.left = parsedAttributes.left || 0;\n parsedAttributes.top = parsedAttributes.top || 0;\n parsedAttributes.height = parsedAttributes.height || 0;\n parsedAttributes.width = parsedAttributes.width || 0;\n var rect = new fabric.Rect(extend((options ? fabric.util.object.clone(options) : { }), parsedAttributes));\n rect.visible = rect.visible && rect.width > 0 && rect.height > 0;\n callback(rect);\n };\n /* _FROM_SVG_END_ */\n\n /**\n * Returns {@link fabric.Rect} instance from an object representation\n * @static\n * @memberOf fabric.Rect\n * @param {Object} object Object to create an instance from\n * @param {Function} [callback] Callback to invoke when an fabric.Rect instance is created\n */\n fabric.Rect.fromObject = function(object, callback) {\n return fabric.Object._fromObject('Rect', object, callback);\n };\n\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { }),\n extend = fabric.util.object.extend,\n min = fabric.util.array.min,\n max = fabric.util.array.max,\n toFixed = fabric.util.toFixed;\n\n if (fabric.Polyline) {\n fabric.warn('fabric.Polyline is already defined');\n return;\n }\n\n /**\n * Polyline class\n * @class fabric.Polyline\n * @extends fabric.Object\n * @see {@link fabric.Polyline#initialize} for constructor definition\n */\n fabric.Polyline = fabric.util.createClass(fabric.Object, /** @lends fabric.Polyline.prototype */ {\n\n /**\n * Type of an object\n * @type String\n * @default\n */\n type: 'polyline',\n\n /**\n * Points array\n * @type Array\n * @default\n */\n points: null,\n\n cacheProperties: fabric.Object.prototype.cacheProperties.concat('points'),\n\n /**\n * Constructor\n * @param {Array} points Array of points (where each point is an object with x and y)\n * @param {Object} [options] Options object\n * @return {fabric.Polyline} thisArg\n * @example\n * var poly = new fabric.Polyline([\n * { x: 10, y: 10 },\n * { x: 50, y: 30 },\n * { x: 40, y: 70 },\n * { x: 60, y: 50 },\n * { x: 100, y: 150 },\n * { x: 40, y: 100 }\n * ], {\n * stroke: 'red',\n * left: 100,\n * top: 100\n * });\n */\n initialize: function(points, options) {\n options = options || {};\n this.points = points || [];\n this.callSuper('initialize', options);\n this._setPositionDimensions(options);\n },\n\n _setPositionDimensions: function(options) {\n var calcDim = this._calcDimensions(options), correctLeftTop;\n this.width = calcDim.width;\n this.height = calcDim.height;\n if (!options.fromSVG) {\n correctLeftTop = this.translateToGivenOrigin(\n { x: calcDim.left - this.strokeWidth / 2, y: calcDim.top - this.strokeWidth / 2 },\n 'left',\n 'top',\n this.originX,\n this.originY\n );\n }\n if (typeof options.left === 'undefined') {\n this.left = options.fromSVG ? calcDim.left : correctLeftTop.x;\n }\n if (typeof options.top === 'undefined') {\n this.top = options.fromSVG ? calcDim.top : correctLeftTop.y;\n }\n this.pathOffset = {\n x: calcDim.left + this.width / 2,\n y: calcDim.top + this.height / 2\n };\n },\n\n /**\n * Calculate the polygon min and max point from points array,\n * returning an object with left, top, widht, height to measure the\n * polygon size\n * @return {Object} object.left X coordinate of the polygon leftmost point\n * @return {Object} object.top Y coordinate of the polygon topmost point\n * @return {Object} object.width distance between X coordinates of the polygon leftmost and rightmost point\n * @return {Object} object.height distance between Y coordinates of the polygon topmost and bottommost point\n * @private\n */\n _calcDimensions: function() {\n\n var points = this.points,\n minX = min(points, 'x') || 0,\n minY = min(points, 'y') || 0,\n maxX = max(points, 'x') || 0,\n maxY = max(points, 'y') || 0,\n width = (maxX - minX),\n height = (maxY - minY);\n\n return {\n left: minX,\n top: minY,\n width: width,\n height: height\n };\n },\n\n /**\n * Returns object representation of an instance\n * @param {Array} [propertiesToInclude] Any properties that you might want to additionally include in the output\n * @return {Object} Object representation of an instance\n */\n toObject: function(propertiesToInclude) {\n return extend(this.callSuper('toObject', propertiesToInclude), {\n points: this.points.concat()\n });\n },\n\n /* _TO_SVG_START_ */\n /**\n * Returns svg representation of an instance\n * @return {Array} an array of strings with the specific svg representation\n * of the instance\n */\n _toSVG: function() {\n var points = [], diffX = this.pathOffset.x, diffY = this.pathOffset.y,\n NUM_FRACTION_DIGITS = fabric.Object.NUM_FRACTION_DIGITS;\n\n for (var i = 0, len = this.points.length; i < len; i++) {\n points.push(\n toFixed(this.points[i].x - diffX, NUM_FRACTION_DIGITS), ',',\n toFixed(this.points[i].y - diffY, NUM_FRACTION_DIGITS), ' '\n );\n }\n return [\n '<' + this.type + ' ', 'COMMON_PARTS',\n 'points=\"', points.join(''),\n '\" />\\n'\n ];\n },\n /* _TO_SVG_END_ */\n\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n commonRender: function(ctx) {\n var point, len = this.points.length,\n x = this.pathOffset.x,\n y = this.pathOffset.y;\n\n if (!len || isNaN(this.points[len - 1].y)) {\n // do not draw if no points or odd points\n // NaN comes from parseFloat of a empty string in parser\n return false;\n }\n ctx.beginPath();\n ctx.moveTo(this.points[0].x - x, this.points[0].y - y);\n for (var i = 0; i < len; i++) {\n point = this.points[i];\n ctx.lineTo(point.x - x, point.y - y);\n }\n return true;\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _render: function(ctx) {\n if (!this.commonRender(ctx)) {\n return;\n }\n this._renderPaintInOrder(ctx);\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _renderDashedStroke: function(ctx) {\n var p1, p2;\n\n ctx.beginPath();\n for (var i = 0, len = this.points.length; i < len; i++) {\n p1 = this.points[i];\n p2 = this.points[i + 1] || p1;\n fabric.util.drawDashedLine(ctx, p1.x, p1.y, p2.x, p2.y, this.strokeDashArray);\n }\n },\n\n /**\n * Returns complexity of an instance\n * @return {Number} complexity of this instance\n */\n complexity: function() {\n return this.get('points').length;\n }\n });\n\n /* _FROM_SVG_START_ */\n /**\n * List of attribute names to account for when parsing SVG element (used by {@link fabric.Polyline.fromElement})\n * @static\n * @memberOf fabric.Polyline\n * @see: http://www.w3.org/TR/SVG/shapes.html#PolylineElement\n */\n fabric.Polyline.ATTRIBUTE_NAMES = fabric.SHARED_ATTRIBUTES.concat();\n\n /**\n * Returns fabric.Polyline instance from an SVG element\n * @static\n * @memberOf fabric.Polyline\n * @param {SVGElement} element Element to parser\n * @param {Function} callback callback function invoked after parsing\n * @param {Object} [options] Options object\n */\n fabric.Polyline.fromElementGenerator = function(_class) {\n return function(element, callback, options) {\n if (!element) {\n return callback(null);\n }\n options || (options = { });\n\n var points = fabric.parsePointsAttribute(element.getAttribute('points')),\n parsedAttributes = fabric.parseAttributes(element, fabric[_class].ATTRIBUTE_NAMES);\n parsedAttributes.fromSVG = true;\n callback(new fabric[_class](points, extend(parsedAttributes, options)));\n };\n };\n\n fabric.Polyline.fromElement = fabric.Polyline.fromElementGenerator('Polyline');\n\n /* _FROM_SVG_END_ */\n\n /**\n * Returns fabric.Polyline instance from an object representation\n * @static\n * @memberOf fabric.Polyline\n * @param {Object} object Object to create an instance from\n * @param {Function} [callback] Callback to invoke when an fabric.Path instance is created\n */\n fabric.Polyline.fromObject = function(object, callback) {\n return fabric.Object._fromObject('Polyline', object, callback, 'points');\n };\n\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { });\n\n if (fabric.Polygon) {\n fabric.warn('fabric.Polygon is already defined');\n return;\n }\n\n /**\n * Polygon class\n * @class fabric.Polygon\n * @extends fabric.Polyline\n * @see {@link fabric.Polygon#initialize} for constructor definition\n */\n fabric.Polygon = fabric.util.createClass(fabric.Polyline, /** @lends fabric.Polygon.prototype */ {\n\n /**\n * Type of an object\n * @type String\n * @default\n */\n type: 'polygon',\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _render: function(ctx) {\n if (!this.commonRender(ctx)) {\n return;\n }\n ctx.closePath();\n this._renderPaintInOrder(ctx);\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _renderDashedStroke: function(ctx) {\n this.callSuper('_renderDashedStroke', ctx);\n ctx.closePath();\n },\n });\n\n /* _FROM_SVG_START_ */\n /**\n * List of attribute names to account for when parsing SVG element (used by `fabric.Polygon.fromElement`)\n * @static\n * @memberOf fabric.Polygon\n * @see: http://www.w3.org/TR/SVG/shapes.html#PolygonElement\n */\n fabric.Polygon.ATTRIBUTE_NAMES = fabric.SHARED_ATTRIBUTES.concat();\n\n /**\n * Returns {@link fabric.Polygon} instance from an SVG element\n * @static\n * @memberOf fabric.Polygon\n * @param {SVGElement} element Element to parse\n * @param {Function} callback callback function invoked after parsing\n * @param {Object} [options] Options object\n */\n fabric.Polygon.fromElement = fabric.Polyline.fromElementGenerator('Polygon');\n /* _FROM_SVG_END_ */\n\n /**\n * Returns fabric.Polygon instance from an object representation\n * @static\n * @memberOf fabric.Polygon\n * @param {Object} object Object to create an instance from\n * @param {Function} [callback] Callback to invoke when an fabric.Path instance is created\n */\n fabric.Polygon.fromObject = function(object, callback) {\n return fabric.Object._fromObject('Polygon', object, callback, 'points');\n };\n\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { }),\n min = fabric.util.array.min,\n max = fabric.util.array.max,\n extend = fabric.util.object.extend,\n _toString = Object.prototype.toString,\n drawArc = fabric.util.drawArc,\n toFixed = fabric.util.toFixed,\n commandLengths = {\n m: 2,\n l: 2,\n h: 1,\n v: 1,\n c: 6,\n s: 4,\n q: 4,\n t: 2,\n a: 7\n },\n repeatedCommands = {\n m: 'l',\n M: 'L'\n };\n\n if (fabric.Path) {\n fabric.warn('fabric.Path is already defined');\n return;\n }\n\n /**\n * Path class\n * @class fabric.Path\n * @extends fabric.Object\n * @tutorial {@link http://fabricjs.com/fabric-intro-part-1#path_and_pathgroup}\n * @see {@link fabric.Path#initialize} for constructor definition\n */\n fabric.Path = fabric.util.createClass(fabric.Object, /** @lends fabric.Path.prototype */ {\n\n /**\n * Type of an object\n * @type String\n * @default\n */\n type: 'path',\n\n /**\n * Array of path points\n * @type Array\n * @default\n */\n path: null,\n\n cacheProperties: fabric.Object.prototype.cacheProperties.concat('path', 'fillRule'),\n\n stateProperties: fabric.Object.prototype.stateProperties.concat('path'),\n\n /**\n * Constructor\n * @param {Array|String} path Path data (sequence of coordinates and corresponding \"command\" tokens)\n * @param {Object} [options] Options object\n * @return {fabric.Path} thisArg\n */\n initialize: function(path, options) {\n options = options || { };\n this.callSuper('initialize', options);\n\n if (!path) {\n path = [];\n }\n\n var fromArray = _toString.call(path) === '[object Array]';\n\n this.path = fromArray\n ? path\n // one of commands (m,M,l,L,q,Q,c,C,etc.) followed by non-command characters (i.e. command values)\n : path.match && path.match(/[mzlhvcsqta][^mzlhvcsqta]*/gi);\n\n if (!this.path) {\n return;\n }\n\n if (!fromArray) {\n this.path = this._parsePath();\n }\n\n fabric.Polyline.prototype._setPositionDimensions.call(this, options);\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx context to render path on\n */\n _renderPathCommands: function(ctx) {\n var current, // current instruction\n previous = null,\n subpathStartX = 0,\n subpathStartY = 0,\n x = 0, // current x\n y = 0, // current y\n controlX = 0, // current control point x\n controlY = 0, // current control point y\n tempX,\n tempY,\n l = -this.pathOffset.x,\n t = -this.pathOffset.y;\n\n ctx.beginPath();\n\n for (var i = 0, len = this.path.length; i < len; ++i) {\n\n current = this.path[i];\n\n switch (current[0]) { // first letter\n\n case 'l': // lineto, relative\n x += current[1];\n y += current[2];\n ctx.lineTo(x + l, y + t);\n break;\n\n case 'L': // lineto, absolute\n x = current[1];\n y = current[2];\n ctx.lineTo(x + l, y + t);\n break;\n\n case 'h': // horizontal lineto, relative\n x += current[1];\n ctx.lineTo(x + l, y + t);\n break;\n\n case 'H': // horizontal lineto, absolute\n x = current[1];\n ctx.lineTo(x + l, y + t);\n break;\n\n case 'v': // vertical lineto, relative\n y += current[1];\n ctx.lineTo(x + l, y + t);\n break;\n\n case 'V': // verical lineto, absolute\n y = current[1];\n ctx.lineTo(x + l, y + t);\n break;\n\n case 'm': // moveTo, relative\n x += current[1];\n y += current[2];\n subpathStartX = x;\n subpathStartY = y;\n ctx.moveTo(x + l, y + t);\n break;\n\n case 'M': // moveTo, absolute\n x = current[1];\n y = current[2];\n subpathStartX = x;\n subpathStartY = y;\n ctx.moveTo(x + l, y + t);\n break;\n\n case 'c': // bezierCurveTo, relative\n tempX = x + current[5];\n tempY = y + current[6];\n controlX = x + current[3];\n controlY = y + current[4];\n ctx.bezierCurveTo(\n x + current[1] + l, // x1\n y + current[2] + t, // y1\n controlX + l, // x2\n controlY + t, // y2\n tempX + l,\n tempY + t\n );\n x = tempX;\n y = tempY;\n break;\n\n case 'C': // bezierCurveTo, absolute\n x = current[5];\n y = current[6];\n controlX = current[3];\n controlY = current[4];\n ctx.bezierCurveTo(\n current[1] + l,\n current[2] + t,\n controlX + l,\n controlY + t,\n x + l,\n y + t\n );\n break;\n\n case 's': // shorthand cubic bezierCurveTo, relative\n\n // transform to absolute x,y\n tempX = x + current[3];\n tempY = y + current[4];\n\n if (previous[0].match(/[CcSs]/) === null) {\n // If there is no previous command or if the previous command was not a C, c, S, or s,\n // the control point is coincident with the current point\n controlX = x;\n controlY = y;\n }\n else {\n // calculate reflection of previous control points\n controlX = 2 * x - controlX;\n controlY = 2 * y - controlY;\n }\n\n ctx.bezierCurveTo(\n controlX + l,\n controlY + t,\n x + current[1] + l,\n y + current[2] + t,\n tempX + l,\n tempY + t\n );\n // set control point to 2nd one of this command\n // \"... the first control point is assumed to be\n // the reflection of the second control point on\n // the previous command relative to the current point.\"\n controlX = x + current[1];\n controlY = y + current[2];\n\n x = tempX;\n y = tempY;\n break;\n\n case 'S': // shorthand cubic bezierCurveTo, absolute\n tempX = current[3];\n tempY = current[4];\n if (previous[0].match(/[CcSs]/) === null) {\n // If there is no previous command or if the previous command was not a C, c, S, or s,\n // the control point is coincident with the current point\n controlX = x;\n controlY = y;\n }\n else {\n // calculate reflection of previous control points\n controlX = 2 * x - controlX;\n controlY = 2 * y - controlY;\n }\n ctx.bezierCurveTo(\n controlX + l,\n controlY + t,\n current[1] + l,\n current[2] + t,\n tempX + l,\n tempY + t\n );\n x = tempX;\n y = tempY;\n\n // set control point to 2nd one of this command\n // \"... the first control point is assumed to be\n // the reflection of the second control point on\n // the previous command relative to the current point.\"\n controlX = current[1];\n controlY = current[2];\n\n break;\n\n case 'q': // quadraticCurveTo, relative\n // transform to absolute x,y\n tempX = x + current[3];\n tempY = y + current[4];\n\n controlX = x + current[1];\n controlY = y + current[2];\n\n ctx.quadraticCurveTo(\n controlX + l,\n controlY + t,\n tempX + l,\n tempY + t\n );\n x = tempX;\n y = tempY;\n break;\n\n case 'Q': // quadraticCurveTo, absolute\n tempX = current[3];\n tempY = current[4];\n\n ctx.quadraticCurveTo(\n current[1] + l,\n current[2] + t,\n tempX + l,\n tempY + t\n );\n x = tempX;\n y = tempY;\n controlX = current[1];\n controlY = current[2];\n break;\n\n case 't': // shorthand quadraticCurveTo, relative\n\n // transform to absolute x,y\n tempX = x + current[1];\n tempY = y + current[2];\n\n if (previous[0].match(/[QqTt]/) === null) {\n // If there is no previous command or if the previous command was not a Q, q, T or t,\n // assume the control point is coincident with the current point\n controlX = x;\n controlY = y;\n }\n else {\n // calculate reflection of previous control point\n controlX = 2 * x - controlX;\n controlY = 2 * y - controlY;\n }\n\n ctx.quadraticCurveTo(\n controlX + l,\n controlY + t,\n tempX + l,\n tempY + t\n );\n x = tempX;\n y = tempY;\n\n break;\n\n case 'T':\n tempX = current[1];\n tempY = current[2];\n\n if (previous[0].match(/[QqTt]/) === null) {\n // If there is no previous command or if the previous command was not a Q, q, T or t,\n // assume the control point is coincident with the current point\n controlX = x;\n controlY = y;\n }\n else {\n // calculate reflection of previous control point\n controlX = 2 * x - controlX;\n controlY = 2 * y - controlY;\n }\n ctx.quadraticCurveTo(\n controlX + l,\n controlY + t,\n tempX + l,\n tempY + t\n );\n x = tempX;\n y = tempY;\n break;\n\n case 'a':\n // TODO: optimize this\n drawArc(ctx, x + l, y + t, [\n current[1],\n current[2],\n current[3],\n current[4],\n current[5],\n current[6] + x + l,\n current[7] + y + t\n ]);\n x += current[6];\n y += current[7];\n break;\n\n case 'A':\n // TODO: optimize this\n drawArc(ctx, x + l, y + t, [\n current[1],\n current[2],\n current[3],\n current[4],\n current[5],\n current[6] + l,\n current[7] + t\n ]);\n x = current[6];\n y = current[7];\n break;\n\n case 'z':\n case 'Z':\n x = subpathStartX;\n y = subpathStartY;\n ctx.closePath();\n break;\n }\n previous = current;\n }\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx context to render path on\n */\n _render: function(ctx) {\n this._renderPathCommands(ctx);\n this._renderPaintInOrder(ctx);\n },\n\n /**\n * Returns string representation of an instance\n * @return {String} string representation of an instance\n */\n toString: function() {\n return '#';\n },\n\n /**\n * Returns object representation of an instance\n * @param {Array} [propertiesToInclude] Any properties that you might want to additionally include in the output\n * @return {Object} object representation of an instance\n */\n toObject: function(propertiesToInclude) {\n return extend(this.callSuper('toObject', propertiesToInclude), {\n path: this.path.map(function(item) { return item.slice(); }),\n });\n },\n\n /**\n * Returns dataless object representation of an instance\n * @param {Array} [propertiesToInclude] Any properties that you might want to additionally include in the output\n * @return {Object} object representation of an instance\n */\n toDatalessObject: function(propertiesToInclude) {\n var o = this.toObject(['sourcePath'].concat(propertiesToInclude));\n if (o.sourcePath) {\n delete o.path;\n }\n return o;\n },\n\n /* _TO_SVG_START_ */\n /**\n * Returns svg representation of an instance\n * @return {Array} an array of strings with the specific svg representation\n * of the instance\n */\n _toSVG: function() {\n var path = this.path.map(function(path) {\n return path.join(' ');\n }).join(' ');\n return [\n '\\n'\n ];\n },\n\n _getOffsetTransform: function() {\n var digits = fabric.Object.NUM_FRACTION_DIGITS;\n return ' translate(' + toFixed(-this.pathOffset.x, digits) + ', ' +\n toFixed(-this.pathOffset.y, digits) + ')';\n },\n\n /**\n * Returns svg clipPath representation of an instance\n * @param {Function} [reviver] Method for further parsing of svg representation.\n * @return {String} svg representation of an instance\n */\n toClipPathSVG: function(reviver) {\n var additionalTransform = this._getOffsetTransform();\n return '\\t' + this._createBaseClipPathSVGMarkup(\n this._toSVG(), { reviver: reviver, additionalTransform: additionalTransform }\n );\n },\n\n /**\n * Returns svg representation of an instance\n * @param {Function} [reviver] Method for further parsing of svg representation.\n * @return {String} svg representation of an instance\n */\n toSVG: function(reviver) {\n var additionalTransform = this._getOffsetTransform();\n return this._createBaseSVGMarkup(this._toSVG(), { reviver: reviver, additionalTransform: additionalTransform });\n },\n /* _TO_SVG_END_ */\n\n /**\n * Returns number representation of an instance complexity\n * @return {Number} complexity of this instance\n */\n complexity: function() {\n return this.path.length;\n },\n\n /**\n * @private\n */\n _parsePath: function() {\n var result = [],\n coords = [],\n currentPath,\n parsed,\n re = fabric.rePathCommand,\n match,\n coordsStr;\n\n for (var i = 0, coordsParsed, len = this.path.length; i < len; i++) {\n currentPath = this.path[i];\n\n coordsStr = currentPath.slice(1).trim();\n coords.length = 0;\n\n while ((match = re.exec(coordsStr))) {\n coords.push(match[0]);\n }\n\n coordsParsed = [currentPath.charAt(0)];\n\n for (var j = 0, jlen = coords.length; j < jlen; j++) {\n parsed = parseFloat(coords[j]);\n if (!isNaN(parsed)) {\n coordsParsed.push(parsed);\n }\n }\n\n var command = coordsParsed[0],\n commandLength = commandLengths[command.toLowerCase()],\n repeatedCommand = repeatedCommands[command] || command;\n\n if (coordsParsed.length - 1 > commandLength) {\n for (var k = 1, klen = coordsParsed.length; k < klen; k += commandLength) {\n result.push([command].concat(coordsParsed.slice(k, k + commandLength)));\n command = repeatedCommand;\n }\n }\n else {\n result.push(coordsParsed);\n }\n }\n\n return result;\n },\n\n /**\n * @private\n */\n _calcDimensions: function() {\n\n var aX = [],\n aY = [],\n current, // current instruction\n previous = null,\n subpathStartX = 0,\n subpathStartY = 0,\n x = 0, // current x\n y = 0, // current y\n controlX = 0, // current control point x\n controlY = 0, // current control point y\n tempX,\n tempY,\n bounds;\n\n for (var i = 0, len = this.path.length; i < len; ++i) {\n\n current = this.path[i];\n\n switch (current[0]) { // first letter\n\n case 'l': // lineto, relative\n x += current[1];\n y += current[2];\n bounds = [];\n break;\n\n case 'L': // lineto, absolute\n x = current[1];\n y = current[2];\n bounds = [];\n break;\n\n case 'h': // horizontal lineto, relative\n x += current[1];\n bounds = [];\n break;\n\n case 'H': // horizontal lineto, absolute\n x = current[1];\n bounds = [];\n break;\n\n case 'v': // vertical lineto, relative\n y += current[1];\n bounds = [];\n break;\n\n case 'V': // verical lineto, absolute\n y = current[1];\n bounds = [];\n break;\n\n case 'm': // moveTo, relative\n x += current[1];\n y += current[2];\n subpathStartX = x;\n subpathStartY = y;\n bounds = [];\n break;\n\n case 'M': // moveTo, absolute\n x = current[1];\n y = current[2];\n subpathStartX = x;\n subpathStartY = y;\n bounds = [];\n break;\n\n case 'c': // bezierCurveTo, relative\n tempX = x + current[5];\n tempY = y + current[6];\n controlX = x + current[3];\n controlY = y + current[4];\n bounds = fabric.util.getBoundsOfCurve(x, y,\n x + current[1], // x1\n y + current[2], // y1\n controlX, // x2\n controlY, // y2\n tempX,\n tempY\n );\n x = tempX;\n y = tempY;\n break;\n\n case 'C': // bezierCurveTo, absolute\n controlX = current[3];\n controlY = current[4];\n bounds = fabric.util.getBoundsOfCurve(x, y,\n current[1],\n current[2],\n controlX,\n controlY,\n current[5],\n current[6]\n );\n x = current[5];\n y = current[6];\n break;\n\n case 's': // shorthand cubic bezierCurveTo, relative\n\n // transform to absolute x,y\n tempX = x + current[3];\n tempY = y + current[4];\n\n if (previous[0].match(/[CcSs]/) === null) {\n // If there is no previous command or if the previous command was not a C, c, S, or s,\n // the control point is coincident with the current point\n controlX = x;\n controlY = y;\n }\n else {\n // calculate reflection of previous control points\n controlX = 2 * x - controlX;\n controlY = 2 * y - controlY;\n }\n\n bounds = fabric.util.getBoundsOfCurve(x, y,\n controlX,\n controlY,\n x + current[1],\n y + current[2],\n tempX,\n tempY\n );\n // set control point to 2nd one of this command\n // \"... the first control point is assumed to be\n // the reflection of the second control point on\n // the previous command relative to the current point.\"\n controlX = x + current[1];\n controlY = y + current[2];\n x = tempX;\n y = tempY;\n break;\n\n case 'S': // shorthand cubic bezierCurveTo, absolute\n tempX = current[3];\n tempY = current[4];\n if (previous[0].match(/[CcSs]/) === null) {\n // If there is no previous command or if the previous command was not a C, c, S, or s,\n // the control point is coincident with the current point\n controlX = x;\n controlY = y;\n }\n else {\n // calculate reflection of previous control points\n controlX = 2 * x - controlX;\n controlY = 2 * y - controlY;\n }\n bounds = fabric.util.getBoundsOfCurve(x, y,\n controlX,\n controlY,\n current[1],\n current[2],\n tempX,\n tempY\n );\n x = tempX;\n y = tempY;\n // set control point to 2nd one of this command\n // \"... the first control point is assumed to be\n // the reflection of the second control point on\n // the previous command relative to the current point.\"\n controlX = current[1];\n controlY = current[2];\n break;\n\n case 'q': // quadraticCurveTo, relative\n // transform to absolute x,y\n tempX = x + current[3];\n tempY = y + current[4];\n controlX = x + current[1];\n controlY = y + current[2];\n bounds = fabric.util.getBoundsOfCurve(x, y,\n controlX,\n controlY,\n controlX,\n controlY,\n tempX,\n tempY\n );\n x = tempX;\n y = tempY;\n break;\n\n case 'Q': // quadraticCurveTo, absolute\n controlX = current[1];\n controlY = current[2];\n bounds = fabric.util.getBoundsOfCurve(x, y,\n controlX,\n controlY,\n controlX,\n controlY,\n current[3],\n current[4]\n );\n x = current[3];\n y = current[4];\n break;\n\n case 't': // shorthand quadraticCurveTo, relative\n // transform to absolute x,y\n tempX = x + current[1];\n tempY = y + current[2];\n if (previous[0].match(/[QqTt]/) === null) {\n // If there is no previous command or if the previous command was not a Q, q, T or t,\n // assume the control point is coincident with the current point\n controlX = x;\n controlY = y;\n }\n else {\n // calculate reflection of previous control point\n controlX = 2 * x - controlX;\n controlY = 2 * y - controlY;\n }\n\n bounds = fabric.util.getBoundsOfCurve(x, y,\n controlX,\n controlY,\n controlX,\n controlY,\n tempX,\n tempY\n );\n x = tempX;\n y = tempY;\n\n break;\n\n case 'T':\n tempX = current[1];\n tempY = current[2];\n\n if (previous[0].match(/[QqTt]/) === null) {\n // If there is no previous command or if the previous command was not a Q, q, T or t,\n // assume the control point is coincident with the current point\n controlX = x;\n controlY = y;\n }\n else {\n // calculate reflection of previous control point\n controlX = 2 * x - controlX;\n controlY = 2 * y - controlY;\n }\n bounds = fabric.util.getBoundsOfCurve(x, y,\n controlX,\n controlY,\n controlX,\n controlY,\n tempX,\n tempY\n );\n x = tempX;\n y = tempY;\n break;\n\n case 'a':\n // TODO: optimize this\n bounds = fabric.util.getBoundsOfArc(x, y,\n current[1],\n current[2],\n current[3],\n current[4],\n current[5],\n current[6] + x,\n current[7] + y\n );\n x += current[6];\n y += current[7];\n break;\n\n case 'A':\n // TODO: optimize this\n bounds = fabric.util.getBoundsOfArc(x, y,\n current[1],\n current[2],\n current[3],\n current[4],\n current[5],\n current[6],\n current[7]\n );\n x = current[6];\n y = current[7];\n break;\n\n case 'z':\n case 'Z':\n x = subpathStartX;\n y = subpathStartY;\n break;\n }\n previous = current;\n bounds.forEach(function (point) {\n aX.push(point.x);\n aY.push(point.y);\n });\n aX.push(x);\n aY.push(y);\n }\n\n var minX = min(aX) || 0,\n minY = min(aY) || 0,\n maxX = max(aX) || 0,\n maxY = max(aY) || 0,\n deltaX = maxX - minX,\n deltaY = maxY - minY;\n\n return {\n left: minX,\n top: minY,\n width: deltaX,\n height: deltaY\n };\n }\n });\n\n /**\n * Creates an instance of fabric.Path from an object\n * @static\n * @memberOf fabric.Path\n * @param {Object} object\n * @param {Function} [callback] Callback to invoke when an fabric.Path instance is created\n */\n fabric.Path.fromObject = function(object, callback) {\n if (typeof object.sourcePath === 'string') {\n var pathUrl = object.sourcePath;\n fabric.loadSVGFromURL(pathUrl, function (elements) {\n var path = elements[0];\n path.setOptions(object);\n callback && callback(path);\n });\n }\n else {\n fabric.Object._fromObject('Path', object, callback, 'path');\n }\n };\n\n /* _FROM_SVG_START_ */\n /**\n * List of attribute names to account for when parsing SVG element (used by `fabric.Path.fromElement`)\n * @static\n * @memberOf fabric.Path\n * @see http://www.w3.org/TR/SVG/paths.html#PathElement\n */\n fabric.Path.ATTRIBUTE_NAMES = fabric.SHARED_ATTRIBUTES.concat(['d']);\n\n /**\n * Creates an instance of fabric.Path from an SVG element\n * @static\n * @memberOf fabric.Path\n * @param {SVGElement} element to parse\n * @param {Function} callback Callback to invoke when an fabric.Path instance is created\n * @param {Object} [options] Options object\n * @param {Function} [callback] Options callback invoked after parsing is finished\n */\n fabric.Path.fromElement = function(element, callback, options) {\n var parsedAttributes = fabric.parseAttributes(element, fabric.Path.ATTRIBUTE_NAMES);\n parsedAttributes.fromSVG = true;\n callback(new fabric.Path(parsedAttributes.d, extend(parsedAttributes, options)));\n };\n /* _FROM_SVG_END_ */\n\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { }),\n min = fabric.util.array.min,\n max = fabric.util.array.max;\n\n if (fabric.Group) {\n return;\n }\n\n /**\n * Group class\n * @class fabric.Group\n * @extends fabric.Object\n * @mixes fabric.Collection\n * @tutorial {@link http://fabricjs.com/fabric-intro-part-3#groups}\n * @see {@link fabric.Group#initialize} for constructor definition\n */\n fabric.Group = fabric.util.createClass(fabric.Object, fabric.Collection, /** @lends fabric.Group.prototype */ {\n\n /**\n * Type of an object\n * @type String\n * @default\n */\n type: 'group',\n\n /**\n * Width of stroke\n * @type Number\n * @default\n */\n strokeWidth: 0,\n\n /**\n * Indicates if click, mouseover, mouseout events & hoverCursor should also check for subtargets\n * @type Boolean\n * @default\n */\n subTargetCheck: false,\n\n /**\n * Groups are container, do not render anything on theyr own, ence no cache properties\n * @type Array\n * @default\n */\n cacheProperties: [],\n\n /**\n * setOnGroup is a method used for TextBox that is no more used since 2.0.0 The behavior is still\n * available setting this boolean to true.\n * @type Boolean\n * @since 2.0.0\n * @default\n */\n useSetOnGroup: false,\n\n /**\n * Constructor\n * @param {Object} objects Group objects\n * @param {Object} [options] Options object\n * @param {Boolean} [isAlreadyGrouped] if true, objects have been grouped already.\n * @return {Object} thisArg\n */\n initialize: function(objects, options, isAlreadyGrouped) {\n options = options || {};\n this._objects = [];\n // if objects enclosed in a group have been grouped already,\n // we cannot change properties of objects.\n // Thus we need to set options to group without objects,\n isAlreadyGrouped && this.callSuper('initialize', options);\n this._objects = objects || [];\n for (var i = this._objects.length; i--; ) {\n this._objects[i].group = this;\n }\n\n if (!isAlreadyGrouped) {\n var center = options && options.centerPoint;\n // we want to set origins before calculating the bounding box.\n // so that the topleft can be set with that in mind.\n // if specific top and left are passed, are overwritten later\n // with the callSuper('initialize', options)\n if (options.originX !== undefined) {\n this.originX = options.originX;\n }\n if (options.originY !== undefined) {\n this.originY = options.originY;\n }\n // if coming from svg i do not want to calc bounds.\n // i assume width and height are passed along options\n center || this._calcBounds();\n this._updateObjectsCoords(center);\n delete options.centerPoint;\n this.callSuper('initialize', options);\n }\n else {\n this._updateObjectsACoords();\n }\n\n this.setCoords();\n },\n\n /**\n * @private\n * @param {Boolean} [skipCoordsChange] if true, coordinates of objects enclosed in a group do not change\n */\n _updateObjectsACoords: function() {\n var ignoreZoom = true, skipAbsolute = true;\n for (var i = this._objects.length; i--; ){\n this._objects[i].setCoords(ignoreZoom, skipAbsolute);\n }\n },\n\n /**\n * @private\n * @param {Boolean} [skipCoordsChange] if true, coordinates of objects enclosed in a group do not change\n */\n _updateObjectsCoords: function(center) {\n var center = center || this.getCenterPoint();\n for (var i = this._objects.length; i--; ){\n this._updateObjectCoords(this._objects[i], center);\n }\n },\n\n /**\n * @private\n * @param {Object} object\n * @param {fabric.Point} center, current center of group.\n */\n _updateObjectCoords: function(object, center) {\n var objectLeft = object.left,\n objectTop = object.top,\n ignoreZoom = true, skipAbsolute = true;\n\n object.set({\n left: objectLeft - center.x,\n top: objectTop - center.y\n });\n object.group = this;\n object.setCoords(ignoreZoom, skipAbsolute);\n },\n\n /**\n * Returns string represenation of a group\n * @return {String}\n */\n toString: function() {\n return '#';\n },\n\n /**\n * Adds an object to a group; Then recalculates group's dimension, position.\n * @param {Object} object\n * @return {fabric.Group} thisArg\n * @chainable\n */\n addWithUpdate: function(object) {\n this._restoreObjectsState();\n fabric.util.resetObjectTransform(this);\n if (object) {\n this._objects.push(object);\n object.group = this;\n object._set('canvas', this.canvas);\n }\n this._calcBounds();\n this._updateObjectsCoords();\n this.setCoords();\n this.dirty = true;\n return this;\n },\n\n /**\n * Removes an object from a group; Then recalculates group's dimension, position.\n * @param {Object} object\n * @return {fabric.Group} thisArg\n * @chainable\n */\n removeWithUpdate: function(object) {\n this._restoreObjectsState();\n fabric.util.resetObjectTransform(this);\n\n this.remove(object);\n this._calcBounds();\n this._updateObjectsCoords();\n this.setCoords();\n this.dirty = true;\n return this;\n },\n\n /**\n * @private\n */\n _onObjectAdded: function(object) {\n this.dirty = true;\n object.group = this;\n object._set('canvas', this.canvas);\n },\n\n /**\n * @private\n */\n _onObjectRemoved: function(object) {\n this.dirty = true;\n delete object.group;\n },\n\n /**\n * @private\n */\n _set: function(key, value) {\n var i = this._objects.length;\n if (this.useSetOnGroup) {\n while (i--) {\n this._objects[i].setOnGroup(key, value);\n }\n }\n if (key === 'canvas') {\n while (i--) {\n this._objects[i]._set(key, value);\n }\n }\n fabric.Object.prototype._set.call(this, key, value);\n },\n\n /**\n * Returns object representation of an instance\n * @param {Array} [propertiesToInclude] Any properties that you might want to additionally include in the output\n * @return {Object} object representation of an instance\n */\n toObject: function(propertiesToInclude) {\n var _includeDefaultValues = this.includeDefaultValues;\n var objsToObject = this._objects.map(function(obj) {\n var originalDefaults = obj.includeDefaultValues;\n obj.includeDefaultValues = _includeDefaultValues;\n var _obj = obj.toObject(propertiesToInclude);\n obj.includeDefaultValues = originalDefaults;\n return _obj;\n });\n var obj = fabric.Object.prototype.toObject.call(this, propertiesToInclude);\n obj.objects = objsToObject;\n return obj;\n },\n\n /**\n * Returns object representation of an instance, in dataless mode.\n * @param {Array} [propertiesToInclude] Any properties that you might want to additionally include in the output\n * @return {Object} object representation of an instance\n */\n toDatalessObject: function(propertiesToInclude) {\n var objsToObject, sourcePath = this.sourcePath;\n if (sourcePath) {\n objsToObject = sourcePath;\n }\n else {\n var _includeDefaultValues = this.includeDefaultValues;\n objsToObject = this._objects.map(function(obj) {\n var originalDefaults = obj.includeDefaultValues;\n obj.includeDefaultValues = _includeDefaultValues;\n var _obj = obj.toDatalessObject(propertiesToInclude);\n obj.includeDefaultValues = originalDefaults;\n return _obj;\n });\n }\n var obj = fabric.Object.prototype.toDatalessObject.call(this, propertiesToInclude);\n obj.objects = objsToObject;\n return obj;\n },\n\n /**\n * Renders instance on a given context\n * @param {CanvasRenderingContext2D} ctx context to render instance on\n */\n render: function(ctx) {\n this._transformDone = true;\n this.callSuper('render', ctx);\n this._transformDone = false;\n },\n\n /**\n * Decide if the object should cache or not. Create its own cache level\n * needsItsOwnCache should be used when the object drawing method requires\n * a cache step. None of the fabric classes requires it.\n * Generally you do not cache objects in groups because the group is already cached.\n * @return {Boolean}\n */\n shouldCache: function() {\n var ownCache = fabric.Object.prototype.shouldCache.call(this);\n if (ownCache) {\n for (var i = 0, len = this._objects.length; i < len; i++) {\n if (this._objects[i].willDrawShadow()) {\n this.ownCaching = false;\n return false;\n }\n }\n }\n return ownCache;\n },\n\n /**\n * Check if this object or a child object will cast a shadow\n * @return {Boolean}\n */\n willDrawShadow: function() {\n if (fabric.Object.prototype.willDrawShadow.call(this)) {\n return true;\n }\n for (var i = 0, len = this._objects.length; i < len; i++) {\n if (this._objects[i].willDrawShadow()) {\n return true;\n }\n }\n return false;\n },\n\n /**\n * Check if this group or its parent group are caching, recursively up\n * @return {Boolean}\n */\n isOnACache: function() {\n return this.ownCaching || (this.group && this.group.isOnACache());\n },\n\n /**\n * Execute the drawing operation for an object on a specified context\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n drawObject: function(ctx) {\n for (var i = 0, len = this._objects.length; i < len; i++) {\n this._objects[i].render(ctx);\n }\n this._drawClipPath(ctx);\n },\n\n /**\n * Check if cache is dirty\n */\n isCacheDirty: function(skipCanvas) {\n if (this.callSuper('isCacheDirty', skipCanvas)) {\n return true;\n }\n if (!this.statefullCache) {\n return false;\n }\n for (var i = 0, len = this._objects.length; i < len; i++) {\n if (this._objects[i].isCacheDirty(true)) {\n if (this._cacheCanvas) {\n // if this group has not a cache canvas there is nothing to clean\n var x = this.cacheWidth / this.zoomX, y = this.cacheHeight / this.zoomY;\n this._cacheContext.clearRect(-x / 2, -y / 2, x, y);\n }\n return true;\n }\n }\n return false;\n },\n\n /**\n * Retores original state of each of group objects (original state is that which was before group was created).\n * @private\n * @return {fabric.Group} thisArg\n * @chainable\n */\n _restoreObjectsState: function() {\n this._objects.forEach(this._restoreObjectState, this);\n return this;\n },\n\n /**\n * Realises the transform from this group onto the supplied object\n * i.e. it tells you what would happen if the supplied object was in\n * the group, and then the group was destroyed. It mutates the supplied\n * object.\n * @param {fabric.Object} object\n * @return {fabric.Object} transformedObject\n */\n realizeTransform: function(object) {\n var matrix = object.calcTransformMatrix(),\n options = fabric.util.qrDecompose(matrix),\n center = new fabric.Point(options.translateX, options.translateY);\n object.flipX = false;\n object.flipY = false;\n object.set('scaleX', options.scaleX);\n object.set('scaleY', options.scaleY);\n object.skewX = options.skewX;\n object.skewY = options.skewY;\n object.angle = options.angle;\n object.setPositionByOrigin(center, 'center', 'center');\n return object;\n },\n\n /**\n * Restores original state of a specified object in group\n * @private\n * @param {fabric.Object} object\n * @return {fabric.Group} thisArg\n */\n _restoreObjectState: function(object) {\n this.realizeTransform(object);\n object.setCoords();\n delete object.group;\n return this;\n },\n\n /**\n * Destroys a group (restoring state of its objects)\n * @return {fabric.Group} thisArg\n * @chainable\n */\n destroy: function() {\n // when group is destroyed objects needs to get a repaint to be eventually\n // displayed on canvas.\n this._objects.forEach(function(object) {\n object.set('dirty', true);\n });\n return this._restoreObjectsState();\n },\n\n /**\n * make a group an active selection, remove the group from canvas\n * the group has to be on canvas for this to work.\n * @return {fabric.ActiveSelection} thisArg\n * @chainable\n */\n toActiveSelection: function() {\n if (!this.canvas) {\n return;\n }\n var objects = this._objects, canvas = this.canvas;\n this._objects = [];\n var options = this.toObject();\n delete options.objects;\n var activeSelection = new fabric.ActiveSelection([]);\n activeSelection.set(options);\n activeSelection.type = 'activeSelection';\n canvas.remove(this);\n objects.forEach(function(object) {\n object.group = activeSelection;\n object.dirty = true;\n canvas.add(object);\n });\n activeSelection.canvas = canvas;\n activeSelection._objects = objects;\n canvas._activeObject = activeSelection;\n activeSelection.setCoords();\n return activeSelection;\n },\n\n /**\n * Destroys a group (restoring state of its objects)\n * @return {fabric.Group} thisArg\n * @chainable\n */\n ungroupOnCanvas: function() {\n return this._restoreObjectsState();\n },\n\n /**\n * Sets coordinates of all objects inside group\n * @return {fabric.Group} thisArg\n * @chainable\n */\n setObjectsCoords: function() {\n var ignoreZoom = true, skipAbsolute = true;\n this.forEachObject(function(object) {\n object.setCoords(ignoreZoom, skipAbsolute);\n });\n return this;\n },\n\n /**\n * @private\n */\n _calcBounds: function(onlyWidthHeight) {\n var aX = [],\n aY = [],\n o, prop,\n props = ['tr', 'br', 'bl', 'tl'],\n i = 0, iLen = this._objects.length,\n j, jLen = props.length,\n ignoreZoom = true;\n\n for ( ; i < iLen; ++i) {\n o = this._objects[i];\n o.setCoords(ignoreZoom);\n for (j = 0; j < jLen; j++) {\n prop = props[j];\n aX.push(o.oCoords[prop].x);\n aY.push(o.oCoords[prop].y);\n }\n }\n\n this._getBounds(aX, aY, onlyWidthHeight);\n },\n\n /**\n * @private\n */\n _getBounds: function(aX, aY, onlyWidthHeight) {\n var minXY = new fabric.Point(min(aX), min(aY)),\n maxXY = new fabric.Point(max(aX), max(aY)),\n top = minXY.y || 0, left = minXY.x || 0,\n width = (maxXY.x - minXY.x) || 0,\n height = (maxXY.y - minXY.y) || 0;\n this.width = width;\n this.height = height;\n if (!onlyWidthHeight) {\n // the bounding box always finds the topleft most corner.\n // whatever is the group origin, we set up here the left/top position.\n this.setPositionByOrigin({ x: left, y: top }, 'left', 'top');\n }\n },\n\n /* _TO_SVG_START_ */\n /**\n * Returns svg representation of an instance\n * @param {Function} [reviver] Method for further parsing of svg representation.\n * @return {String} svg representation of an instance\n */\n _toSVG: function(reviver) {\n var svgString = ['\\n'];\n\n for (var i = 0, len = this._objects.length; i < len; i++) {\n svgString.push('\\t\\t', this._objects[i].toSVG(reviver));\n }\n svgString.push('\\n');\n return svgString;\n },\n\n /**\n * Returns styles-string for svg-export, specific version for group\n * @return {String}\n */\n getSvgStyles: function() {\n var opacity = typeof this.opacity !== 'undefined' && this.opacity !== 1 ?\n 'opacity: ' + this.opacity + ';' : '',\n visibility = this.visible ? '' : ' visibility: hidden;';\n return [\n opacity,\n this.getSvgFilter(),\n visibility\n ].join('');\n },\n\n /**\n * Returns svg clipPath representation of an instance\n * @param {Function} [reviver] Method for further parsing of svg representation.\n * @return {String} svg representation of an instance\n */\n toClipPathSVG: function(reviver) {\n var svgString = [];\n\n for (var i = 0, len = this._objects.length; i < len; i++) {\n svgString.push('\\t', this._objects[i].toClipPathSVG(reviver));\n }\n\n return this._createBaseClipPathSVGMarkup(svgString, { reviver: reviver });\n },\n /* _TO_SVG_END_ */\n });\n\n /**\n * Returns {@link fabric.Group} instance from an object representation\n * @static\n * @memberOf fabric.Group\n * @param {Object} object Object to create a group from\n * @param {Function} [callback] Callback to invoke when an group instance is created\n */\n fabric.Group.fromObject = function(object, callback) {\n var objects = object.objects,\n options = fabric.util.object.clone(object, true);\n delete options.objects;\n if (typeof objects === 'string') {\n // it has to be an url or something went wrong.\n fabric.loadSVGFromURL(objects, function (elements) {\n var group = fabric.util.groupSVGElements(elements, object, objects);\n group.set(options);\n callback && callback(group);\n });\n return;\n }\n fabric.util.enlivenObjects(objects, function(enlivenedObjects) {\n fabric.util.enlivenObjects([object.clipPath], function(enlivedClipPath) {\n var options = fabric.util.object.clone(object, true);\n options.clipPath = enlivedClipPath[0];\n delete options.objects;\n callback && callback(new fabric.Group(enlivenedObjects, options, true));\n });\n });\n };\n\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { });\n\n if (fabric.ActiveSelection) {\n return;\n }\n\n /**\n * Group class\n * @class fabric.ActiveSelection\n * @extends fabric.Group\n * @tutorial {@link http://fabricjs.com/fabric-intro-part-3#groups}\n * @see {@link fabric.ActiveSelection#initialize} for constructor definition\n */\n fabric.ActiveSelection = fabric.util.createClass(fabric.Group, /** @lends fabric.ActiveSelection.prototype */ {\n\n /**\n * Type of an object\n * @type String\n * @default\n */\n type: 'activeSelection',\n\n /**\n * Constructor\n * @param {Object} objects ActiveSelection objects\n * @param {Object} [options] Options object\n * @return {Object} thisArg\n */\n initialize: function(objects, options) {\n options = options || {};\n this._objects = objects || [];\n for (var i = this._objects.length; i--; ) {\n this._objects[i].group = this;\n }\n\n if (options.originX) {\n this.originX = options.originX;\n }\n if (options.originY) {\n this.originY = options.originY;\n }\n this._calcBounds();\n this._updateObjectsCoords();\n fabric.Object.prototype.initialize.call(this, options);\n this.setCoords();\n },\n\n /**\n * Change te activeSelection to a normal group,\n * High level function that automatically adds it to canvas as\n * active object. no events fired.\n * @since 2.0.0\n * @return {fabric.Group}\n */\n toGroup: function() {\n var objects = this._objects.concat();\n this._objects = [];\n var options = fabric.Object.prototype.toObject.call(this);\n var newGroup = new fabric.Group([]);\n delete options.type;\n newGroup.set(options);\n objects.forEach(function(object) {\n object.canvas.remove(object);\n object.group = newGroup;\n });\n newGroup._objects = objects;\n if (!this.canvas) {\n return newGroup;\n }\n var canvas = this.canvas;\n canvas.add(newGroup);\n canvas._activeObject = newGroup;\n newGroup.setCoords();\n return newGroup;\n },\n\n /**\n * If returns true, deselection is cancelled.\n * @since 2.0.0\n * @return {Boolean} [cancel]\n */\n onDeselect: function() {\n this.destroy();\n return false;\n },\n\n /**\n * Returns string representation of a group\n * @return {String}\n */\n toString: function() {\n return '#';\n },\n\n /**\n * Decide if the object should cache or not. Create its own cache level\n * objectCaching is a global flag, wins over everything\n * needsItsOwnCache should be used when the object drawing method requires\n * a cache step. None of the fabric classes requires it.\n * Generally you do not cache objects in groups because the group outside is cached.\n * @return {Boolean}\n */\n shouldCache: function() {\n return false;\n },\n\n /**\n * Check if this group or its parent group are caching, recursively up\n * @return {Boolean}\n */\n isOnACache: function() {\n return false;\n },\n\n /**\n * Renders controls and borders for the object\n * @param {CanvasRenderingContext2D} ctx Context to render on\n * @param {Object} [styleOverride] properties to override the object style\n * @param {Object} [childrenOverride] properties to override the children overrides\n */\n _renderControls: function(ctx, styleOverride, childrenOverride) {\n ctx.save();\n ctx.globalAlpha = this.isMoving ? this.borderOpacityWhenMoving : 1;\n this.callSuper('_renderControls', ctx, styleOverride);\n childrenOverride = childrenOverride || { };\n if (typeof childrenOverride.hasControls === 'undefined') {\n childrenOverride.hasControls = false;\n }\n if (typeof childrenOverride.hasRotatingPoint === 'undefined') {\n childrenOverride.hasRotatingPoint = false;\n }\n childrenOverride.forActiveSelection = true;\n for (var i = 0, len = this._objects.length; i < len; i++) {\n this._objects[i]._renderControls(ctx, childrenOverride);\n }\n ctx.restore();\n },\n });\n\n /**\n * Returns {@link fabric.ActiveSelection} instance from an object representation\n * @static\n * @memberOf fabric.ActiveSelection\n * @param {Object} object Object to create a group from\n * @param {Function} [callback] Callback to invoke when an ActiveSelection instance is created\n */\n fabric.ActiveSelection.fromObject = function(object, callback) {\n fabric.util.enlivenObjects(object.objects, function(enlivenedObjects) {\n delete object.objects;\n callback && callback(new fabric.ActiveSelection(enlivenedObjects, object, true));\n });\n };\n\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n\n 'use strict';\n\n var extend = fabric.util.object.extend;\n\n if (!global.fabric) {\n global.fabric = { };\n }\n\n if (global.fabric.Image) {\n fabric.warn('fabric.Image is already defined.');\n return;\n }\n\n /**\n * Image class\n * @class fabric.Image\n * @extends fabric.Object\n * @tutorial {@link http://fabricjs.com/fabric-intro-part-1#images}\n * @see {@link fabric.Image#initialize} for constructor definition\n */\n fabric.Image = fabric.util.createClass(fabric.Object, /** @lends fabric.Image.prototype */ {\n\n /**\n * Type of an object\n * @type String\n * @default\n */\n type: 'image',\n\n /**\n * crossOrigin value (one of \"\", \"anonymous\", \"use-credentials\")\n * @see https://developer.mozilla.org/en-US/docs/HTML/CORS_settings_attributes\n * @type String\n * @default\n */\n crossOrigin: '',\n\n /**\n * Width of a stroke.\n * For image quality a stroke multiple of 2 gives better results.\n * @type Number\n * @default\n */\n strokeWidth: 0,\n\n /**\n * When calling {@link fabric.Image.getSrc}, return value from element src with `element.getAttribute('src')`.\n * This allows for relative urls as image src.\n * @since 2.7.0\n * @type Boolean\n * @default\n */\n srcFromAttribute: false,\n\n /**\n * private\n * contains last value of scaleX to detect\n * if the Image got resized after the last Render\n * @type Number\n */\n _lastScaleX: 1,\n\n /**\n * private\n * contains last value of scaleY to detect\n * if the Image got resized after the last Render\n * @type Number\n */\n _lastScaleY: 1,\n\n /**\n * private\n * contains last value of scaling applied by the apply filter chain\n * @type Number\n */\n _filterScalingX: 1,\n\n /**\n * private\n * contains last value of scaling applied by the apply filter chain\n * @type Number\n */\n _filterScalingY: 1,\n\n /**\n * minimum scale factor under which any resizeFilter is triggered to resize the image\n * 0 will disable the automatic resize. 1 will trigger automatically always.\n * number bigger than 1 are not implemented yet.\n * @type Number\n */\n minimumScaleTrigger: 0.5,\n\n /**\n * List of properties to consider when checking if\n * state of an object is changed ({@link fabric.Object#hasStateChanged})\n * as well as for history (undo/redo) purposes\n * @type Array\n */\n stateProperties: fabric.Object.prototype.stateProperties.concat('cropX', 'cropY'),\n\n /**\n * key used to retrieve the texture representing this image\n * @since 2.0.0\n * @type String\n * @default\n */\n cacheKey: '',\n\n /**\n * Image crop in pixels from original image size.\n * @since 2.0.0\n * @type Number\n * @default\n */\n cropX: 0,\n\n /**\n * Image crop in pixels from original image size.\n * @since 2.0.0\n * @type Number\n * @default\n */\n cropY: 0,\n\n /**\n * Constructor\n * @param {HTMLImageElement | String} element Image element\n * @param {Object} [options] Options object\n * @param {function} [callback] callback function to call after eventual filters applied.\n * @return {fabric.Image} thisArg\n */\n initialize: function(element, options) {\n options || (options = { });\n this.filters = [];\n this.cacheKey = 'texture' + fabric.Object.__uid++;\n this.callSuper('initialize', options);\n this._initElement(element, options);\n },\n\n /**\n * Returns image element which this instance if based on\n * @return {HTMLImageElement} Image element\n */\n getElement: function() {\n return this._element || {};\n },\n\n /**\n * Sets image element for this instance to a specified one.\n * If filters defined they are applied to new image.\n * You might need to call `canvas.renderAll` and `object.setCoords` after replacing, to render new image and update controls area.\n * @param {HTMLImageElement} element\n * @param {Object} [options] Options object\n * @return {fabric.Image} thisArg\n * @chainable\n */\n setElement: function(element, options) {\n this.removeTexture(this.cacheKey);\n this.removeTexture(this.cacheKey + '_filtered');\n this._element = element;\n this._originalElement = element;\n this._initConfig(options);\n if (this.filters.length !== 0) {\n this.applyFilters();\n }\n // resizeFilters work on the already filtered copy.\n // we need to apply resizeFilters AFTER normal filters.\n // applyResizeFilters is run more often than normal fiters\n // and is triggered by user interactions rather than dev code\n if (this.resizeFilter) {\n this.applyResizeFilters();\n }\n return this;\n },\n\n /**\n * Delete a single texture if in webgl mode\n */\n removeTexture: function(key) {\n var backend = fabric.filterBackend;\n if (backend && backend.evictCachesForKey) {\n backend.evictCachesForKey(key);\n }\n },\n\n /**\n * Delete textures, reference to elements and eventually JSDOM cleanup\n */\n dispose: function() {\n this.removeTexture(this.cacheKey);\n this.removeTexture(this.cacheKey + '_filtered');\n this._cacheContext = undefined;\n ['_originalElement', '_element', '_filteredEl', '_cacheCanvas'].forEach((function(element) {\n fabric.util.cleanUpJsdomNode(this[element]);\n this[element] = undefined;\n }).bind(this));\n },\n\n /**\n * Sets crossOrigin value (on an instance and corresponding image element)\n * @return {fabric.Image} thisArg\n * @chainable\n */\n setCrossOrigin: function(value) {\n this.crossOrigin = value;\n this._element.crossOrigin = value;\n\n return this;\n },\n\n /**\n * Returns original size of an image\n * @return {Object} Object with \"width\" and \"height\" properties\n */\n getOriginalSize: function() {\n var element = this.getElement();\n return {\n width: element.naturalWidth || element.width,\n height: element.naturalHeight || element.height\n };\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _stroke: function(ctx) {\n if (!this.stroke || this.strokeWidth === 0) {\n return;\n }\n var w = this.width / 2, h = this.height / 2;\n ctx.beginPath();\n ctx.moveTo(-w, -h);\n ctx.lineTo(w, -h);\n ctx.lineTo(w, h);\n ctx.lineTo(-w, h);\n ctx.lineTo(-w, -h);\n ctx.closePath();\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _renderDashedStroke: function(ctx) {\n var x = -this.width / 2,\n y = -this.height / 2,\n w = this.width,\n h = this.height;\n\n ctx.save();\n this._setStrokeStyles(ctx, this);\n\n ctx.beginPath();\n fabric.util.drawDashedLine(ctx, x, y, x + w, y, this.strokeDashArray);\n fabric.util.drawDashedLine(ctx, x + w, y, x + w, y + h, this.strokeDashArray);\n fabric.util.drawDashedLine(ctx, x + w, y + h, x, y + h, this.strokeDashArray);\n fabric.util.drawDashedLine(ctx, x, y + h, x, y, this.strokeDashArray);\n ctx.closePath();\n ctx.restore();\n },\n\n /**\n * Returns object representation of an instance\n * @param {Array} [propertiesToInclude] Any properties that you might want to additionally include in the output\n * @return {Object} Object representation of an instance\n */\n toObject: function(propertiesToInclude) {\n var filters = [];\n\n this.filters.forEach(function(filterObj) {\n if (filterObj) {\n filters.push(filterObj.toObject());\n }\n });\n var object = extend(\n this.callSuper(\n 'toObject',\n ['crossOrigin', 'cropX', 'cropY'].concat(propertiesToInclude)\n ), {\n src: this.getSrc(),\n filters: filters,\n });\n if (this.resizeFilter) {\n object.resizeFilter = this.resizeFilter.toObject();\n }\n return object;\n },\n\n /**\n * Returns true if an image has crop applied, inspecting values of cropX,cropY,width,hight.\n * @return {Boolean}\n */\n hasCrop: function() {\n return this.cropX || this.cropY || this.width < this._element.width || this.height < this._element.height;\n },\n\n /* _TO_SVG_START_ */\n /**\n * Returns svg representation of an instance\n * @return {Array} an array of strings with the specific svg representation\n * of the instance\n */\n _toSVG: function() {\n var svgString = [], imageMarkup = [], strokeSvg,\n x = -this.width / 2, y = -this.height / 2, clipPath = '';\n if (this.hasCrop()) {\n var clipPathId = fabric.Object.__uid++;\n svgString.push(\n '\\n',\n '\\t\\n',\n '\\n'\n );\n clipPath = ' clip-path=\"url(#imageCrop_' + clipPathId + ')\" ';\n }\n imageMarkup.push('\\t element with actual transformation, then offsetting object to the top/left\n // so that object's center aligns with container's left/top\n '\" width=\"', this._element.width || this._element.naturalWidth,\n '\" height=\"', this._element.height || this._element.height,\n '\"', clipPath,\n '>\\n');\n\n if (this.stroke || this.strokeDashArray) {\n var origFill = this.fill;\n this.fill = null;\n strokeSvg = [\n '\\t\\n'\n ];\n this.fill = origFill;\n }\n if (this.paintFirst !== 'fill') {\n svgString = svgString.concat(strokeSvg, imageMarkup);\n }\n else {\n svgString = svgString.concat(imageMarkup, strokeSvg);\n }\n return svgString;\n },\n /* _TO_SVG_END_ */\n\n /**\n * Returns source of an image\n * @param {Boolean} filtered indicates if the src is needed for svg\n * @return {String} Source of an image\n */\n getSrc: function(filtered) {\n var element = filtered ? this._element : this._originalElement;\n if (element) {\n if (element.toDataURL) {\n return element.toDataURL();\n }\n\n if (this.srcFromAttribute) {\n return element.getAttribute('src');\n }\n else {\n return element.src;\n }\n }\n else {\n return this.src || '';\n }\n },\n\n /**\n * Sets source of an image\n * @param {String} src Source string (URL)\n * @param {Function} [callback] Callback is invoked when image has been loaded (and all filters have been applied)\n * @param {Object} [options] Options object\n * @return {fabric.Image} thisArg\n * @chainable\n */\n setSrc: function(src, callback, options) {\n fabric.util.loadImage(src, function(img) {\n this.setElement(img, options);\n this._setWidthHeight();\n callback && callback(this);\n }, this, options && options.crossOrigin);\n return this;\n },\n\n /**\n * Returns string representation of an instance\n * @return {String} String representation of an instance\n */\n toString: function() {\n return '#';\n },\n\n applyResizeFilters: function() {\n var filter = this.resizeFilter,\n minimumScale = this.minimumScaleTrigger,\n objectScale = this.getTotalObjectScaling(),\n scaleX = objectScale.scaleX,\n scaleY = objectScale.scaleY,\n elementToFilter = this._filteredEl || this._originalElement;\n if (this.group) {\n this.set('dirty', true);\n }\n if (!filter || (scaleX > minimumScale && scaleY > minimumScale)) {\n this._element = elementToFilter;\n this._filterScalingX = 1;\n this._filterScalingY = 1;\n this._lastScaleX = scaleX;\n this._lastScaleY = scaleY;\n return;\n }\n if (!fabric.filterBackend) {\n fabric.filterBackend = fabric.initFilterBackend();\n }\n var canvasEl = fabric.util.createCanvasElement(),\n cacheKey = this._filteredEl ? (this.cacheKey + '_filtered') : this.cacheKey,\n sourceWidth = elementToFilter.width, sourceHeight = elementToFilter.height;\n canvasEl.width = sourceWidth;\n canvasEl.height = sourceHeight;\n this._element = canvasEl;\n this._lastScaleX = filter.scaleX = scaleX;\n this._lastScaleY = filter.scaleY = scaleY;\n fabric.filterBackend.applyFilters(\n [filter], elementToFilter, sourceWidth, sourceHeight, this._element, cacheKey);\n this._filterScalingX = canvasEl.width / this._originalElement.width;\n this._filterScalingY = canvasEl.height / this._originalElement.height;\n },\n\n /**\n * Applies filters assigned to this image (from \"filters\" array) or from filter param\n * @method applyFilters\n * @param {Array} filters to be applied\n * @param {Boolean} forResizing specify if the filter operation is a resize operation\n * @return {thisArg} return the fabric.Image object\n * @chainable\n */\n applyFilters: function(filters) {\n\n filters = filters || this.filters || [];\n filters = filters.filter(function(filter) { return filter && !filter.isNeutralState(); });\n this.set('dirty', true);\n\n // needs to clear out or WEBGL will not resize correctly\n this.removeTexture(this.cacheKey + '_filtered');\n\n if (filters.length === 0) {\n this._element = this._originalElement;\n this._filteredEl = null;\n this._filterScalingX = 1;\n this._filterScalingY = 1;\n return this;\n }\n\n var imgElement = this._originalElement,\n sourceWidth = imgElement.naturalWidth || imgElement.width,\n sourceHeight = imgElement.naturalHeight || imgElement.height;\n\n if (this._element === this._originalElement) {\n // if the element is the same we need to create a new element\n var canvasEl = fabric.util.createCanvasElement();\n canvasEl.width = sourceWidth;\n canvasEl.height = sourceHeight;\n this._element = canvasEl;\n this._filteredEl = canvasEl;\n }\n else {\n // clear the existing element to get new filter data\n // also dereference the eventual resized _element\n this._element = this._filteredEl;\n this._filteredEl.getContext('2d').clearRect(0, 0, sourceWidth, sourceHeight);\n // we also need to resize again at next renderAll, so remove saved _lastScaleX/Y\n this._lastScaleX = 1;\n this._lastScaleY = 1;\n }\n if (!fabric.filterBackend) {\n fabric.filterBackend = fabric.initFilterBackend();\n }\n fabric.filterBackend.applyFilters(\n filters, this._originalElement, sourceWidth, sourceHeight, this._element, this.cacheKey);\n if (this._originalElement.width !== this._element.width ||\n this._originalElement.height !== this._element.height) {\n this._filterScalingX = this._element.width / this._originalElement.width;\n this._filterScalingY = this._element.height / this._originalElement.height;\n }\n return this;\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _render: function(ctx) {\n if (this.isMoving !== true && this.resizeFilter && this._needsResize()) {\n this.applyResizeFilters();\n }\n this._stroke(ctx);\n this._renderPaintInOrder(ctx);\n },\n\n /**\n * Decide if the object should cache or not. Create its own cache level\n * needsItsOwnCache should be used when the object drawing method requires\n * a cache step. None of the fabric classes requires it.\n * Generally you do not cache objects in groups because the group outside is cached.\n * This is the special image version where we would like to avoid caching where possible.\n * Essentially images do not benefit from caching. They may require caching, and in that\n * case we do it. Also caching an image usually ends in a loss of details.\n * A full performance audit should be done.\n * @return {Boolean}\n */\n shouldCache: function() {\n return this.needsItsOwnCache();\n },\n\n _renderFill: function(ctx) {\n var elementToDraw = this._element;\n if (!elementToDraw) {\n return;\n }\n var scaleX = this._filterScalingX, scaleY = this._filterScalingY,\n w = this.width, h = this.height, min = Math.min, max = Math.max,\n // crop values cannot be lesser than 0.\n cropX = max(this.cropX, 0), cropY = max(this.cropY, 0),\n elWidth = elementToDraw.naturalWidth || elementToDraw.width,\n elHeight = elementToDraw.naturalHeight || elementToDraw.height,\n sX = cropX * scaleX,\n sY = cropY * scaleY,\n // the width height cannot exceed element width/height, starting from the crop offset.\n sW = min(w * scaleX, elWidth - sX),\n sH = min(h * scaleY, elHeight - sY),\n x = -w / 2, y = -h / 2,\n maxDestW = min(w, elWidth / scaleX - cropX),\n maxDestH = min(h, elHeight / scaleX - cropY);\n\n elementToDraw && ctx.drawImage(elementToDraw, sX, sY, sW, sH, x, y, maxDestW, maxDestH);\n },\n\n /**\n * needed to check if image needs resize\n * @private\n */\n _needsResize: function() {\n var scale = this.getTotalObjectScaling();\n return (scale.scaleX !== this._lastScaleX || scale.scaleY !== this._lastScaleY);\n },\n\n /**\n * @private\n */\n _resetWidthHeight: function() {\n this.set(this.getOriginalSize());\n },\n\n /**\n * The Image class's initialization method. This method is automatically\n * called by the constructor.\n * @private\n * @param {HTMLImageElement|String} element The element representing the image\n * @param {Object} [options] Options object\n */\n _initElement: function(element, options) {\n this.setElement(fabric.util.getById(element), options);\n fabric.util.addClass(this.getElement(), fabric.Image.CSS_CANVAS);\n },\n\n /**\n * @private\n * @param {Object} [options] Options object\n */\n _initConfig: function(options) {\n options || (options = { });\n this.setOptions(options);\n this._setWidthHeight(options);\n if (this._element && this.crossOrigin) {\n this._element.crossOrigin = this.crossOrigin;\n }\n },\n\n /**\n * @private\n * @param {Array} filters to be initialized\n * @param {Function} callback Callback to invoke when all fabric.Image.filters instances are created\n */\n _initFilters: function(filters, callback) {\n if (filters && filters.length) {\n fabric.util.enlivenObjects(filters, function(enlivenedObjects) {\n callback && callback(enlivenedObjects);\n }, 'fabric.Image.filters');\n }\n else {\n callback && callback();\n }\n },\n\n /**\n * @private\n * Set the width and the height of the image object, using the element or the\n * options.\n * @param {Object} [options] Object with width/height properties\n */\n _setWidthHeight: function(options) {\n options || (options = { });\n var el = this.getElement();\n this.width = options.width || el.naturalWidth || el.width || 0;\n this.height = options.height || el.naturalHeight || el.height || 0;\n },\n\n /**\n * Calculate offset for center and scale factor for the image in order to respect\n * the preserveAspectRatio attribute\n * @private\n * @return {Object}\n */\n parsePreserveAspectRatioAttribute: function() {\n var pAR = fabric.util.parsePreserveAspectRatioAttribute(this.preserveAspectRatio || ''),\n rWidth = this._element.width, rHeight = this._element.height,\n scaleX = 1, scaleY = 1, offsetLeft = 0, offsetTop = 0, cropX = 0, cropY = 0,\n offset, pWidth = this.width, pHeight = this.height, parsedAttributes = { width: pWidth, height: pHeight };\n if (pAR && (pAR.alignX !== 'none' || pAR.alignY !== 'none')) {\n if (pAR.meetOrSlice === 'meet') {\n scaleX = scaleY = fabric.util.findScaleToFit(this._element, parsedAttributes);\n offset = (pWidth - rWidth * scaleX) / 2;\n if (pAR.alignX === 'Min') {\n offsetLeft = -offset;\n }\n if (pAR.alignX === 'Max') {\n offsetLeft = offset;\n }\n offset = (pHeight - rHeight * scaleY) / 2;\n if (pAR.alignY === 'Min') {\n offsetTop = -offset;\n }\n if (pAR.alignY === 'Max') {\n offsetTop = offset;\n }\n }\n if (pAR.meetOrSlice === 'slice') {\n scaleX = scaleY = fabric.util.findScaleToCover(this._element, parsedAttributes);\n offset = rWidth - pWidth / scaleX;\n if (pAR.alignX === 'Mid') {\n cropX = offset / 2;\n }\n if (pAR.alignX === 'Max') {\n cropX = offset;\n }\n offset = rHeight - pHeight / scaleY;\n if (pAR.alignY === 'Mid') {\n cropY = offset / 2;\n }\n if (pAR.alignY === 'Max') {\n cropY = offset;\n }\n rWidth = pWidth / scaleX;\n rHeight = pHeight / scaleY;\n }\n }\n else {\n scaleX = pWidth / rWidth;\n scaleY = pHeight / rHeight;\n }\n return {\n width: rWidth,\n height: rHeight,\n scaleX: scaleX,\n scaleY: scaleY,\n offsetLeft: offsetLeft,\n offsetTop: offsetTop,\n cropX: cropX,\n cropY: cropY\n };\n }\n });\n\n /**\n * Default CSS class name for canvas\n * @static\n * @type String\n * @default\n */\n fabric.Image.CSS_CANVAS = 'canvas-img';\n\n /**\n * Alias for getSrc\n * @static\n */\n fabric.Image.prototype.getSvgSrc = fabric.Image.prototype.getSrc;\n\n /**\n * Creates an instance of fabric.Image from its object representation\n * @static\n * @param {Object} object Object to create an instance from\n * @param {Function} callback Callback to invoke when an image instance is created\n */\n fabric.Image.fromObject = function(_object, callback) {\n var object = fabric.util.object.clone(_object);\n fabric.util.loadImage(object.src, function(img, error) {\n if (error) {\n callback && callback(null, error);\n return;\n }\n fabric.Image.prototype._initFilters.call(object, object.filters, function(filters) {\n object.filters = filters || [];\n fabric.Image.prototype._initFilters.call(object, [object.resizeFilter], function(resizeFilters) {\n object.resizeFilter = resizeFilters[0];\n fabric.util.enlivenObjects([object.clipPath], function(enlivedProps) {\n object.clipPath = enlivedProps[0];\n var image = new fabric.Image(img, object);\n callback(image);\n });\n });\n });\n }, null, object.crossOrigin);\n };\n\n /**\n * Creates an instance of fabric.Image from an URL string\n * @static\n * @param {String} url URL to create an image from\n * @param {Function} [callback] Callback to invoke when image is created (newly created image is passed as a first argument)\n * @param {Object} [imgOptions] Options object\n */\n fabric.Image.fromURL = function(url, callback, imgOptions) {\n fabric.util.loadImage(url, function(img) {\n callback && callback(new fabric.Image(img, imgOptions));\n }, null, imgOptions && imgOptions.crossOrigin);\n };\n\n /* _FROM_SVG_START_ */\n /**\n * List of attribute names to account for when parsing SVG element (used by {@link fabric.Image.fromElement})\n * @static\n * @see {@link http://www.w3.org/TR/SVG/struct.html#ImageElement}\n */\n fabric.Image.ATTRIBUTE_NAMES =\n fabric.SHARED_ATTRIBUTES.concat('x y width height preserveAspectRatio xlink:href crossOrigin'.split(' '));\n\n /**\n * Returns {@link fabric.Image} instance from an SVG element\n * @static\n * @param {SVGElement} element Element to parse\n * @param {Object} [options] Options object\n * @param {Function} callback Callback to execute when fabric.Image object is created\n * @return {fabric.Image} Instance of fabric.Image\n */\n fabric.Image.fromElement = function(element, callback, options) {\n var parsedAttributes = fabric.parseAttributes(element, fabric.Image.ATTRIBUTE_NAMES);\n fabric.Image.fromURL(parsedAttributes['xlink:href'], callback,\n extend((options ? fabric.util.object.clone(options) : { }), parsedAttributes));\n };\n /* _FROM_SVG_END_ */\n\n})(typeof exports !== 'undefined' ? exports : this);\n\n\nfabric.util.object.extend(fabric.Object.prototype, /** @lends fabric.Object.prototype */ {\n\n /**\n * @private\n * @return {Number} angle value\n */\n _getAngleValueForStraighten: function() {\n var angle = this.angle % 360;\n if (angle > 0) {\n return Math.round((angle - 1) / 90) * 90;\n }\n return Math.round(angle / 90) * 90;\n },\n\n /**\n * Straightens an object (rotating it from current angle to one of 0, 90, 180, 270, etc. depending on which is closer)\n * @return {fabric.Object} thisArg\n * @chainable\n */\n straighten: function() {\n this.rotate(this._getAngleValueForStraighten());\n return this;\n },\n\n /**\n * Same as {@link fabric.Object.prototype.straighten} but with animation\n * @param {Object} callbacks Object with callback functions\n * @param {Function} [callbacks.onComplete] Invoked on completion\n * @param {Function} [callbacks.onChange] Invoked on every step of animation\n * @return {fabric.Object} thisArg\n * @chainable\n */\n fxStraighten: function(callbacks) {\n callbacks = callbacks || { };\n\n var empty = function() { },\n onComplete = callbacks.onComplete || empty,\n onChange = callbacks.onChange || empty,\n _this = this;\n\n fabric.util.animate({\n startValue: this.get('angle'),\n endValue: this._getAngleValueForStraighten(),\n duration: this.FX_DURATION,\n onChange: function(value) {\n _this.rotate(value);\n onChange();\n },\n onComplete: function() {\n _this.setCoords();\n onComplete();\n },\n });\n\n return this;\n }\n});\n\nfabric.util.object.extend(fabric.StaticCanvas.prototype, /** @lends fabric.StaticCanvas.prototype */ {\n\n /**\n * Straightens object, then rerenders canvas\n * @param {fabric.Object} object Object to straighten\n * @return {fabric.Canvas} thisArg\n * @chainable\n */\n straightenObject: function (object) {\n object.straighten();\n this.requestRenderAll();\n return this;\n },\n\n /**\n * Same as {@link fabric.Canvas.prototype.straightenObject}, but animated\n * @param {fabric.Object} object Object to straighten\n * @return {fabric.Canvas} thisArg\n * @chainable\n */\n fxStraightenObject: function (object) {\n object.fxStraighten({\n onChange: this.requestRenderAllBound\n });\n return this;\n }\n});\n\n\n(function() {\n\n 'use strict';\n\n /**\n * Tests if webgl supports certain precision\n * @param {WebGL} Canvas WebGL context to test on\n * @param {String} Precision to test can be any of following: 'lowp', 'mediump', 'highp'\n * @returns {Boolean} Whether the user's browser WebGL supports given precision.\n */\n function testPrecision(gl, precision){\n var fragmentSource = 'precision ' + precision + ' float;\\nvoid main(){}';\n var fragmentShader = gl.createShader(gl.FRAGMENT_SHADER);\n gl.shaderSource(fragmentShader, fragmentSource);\n gl.compileShader(fragmentShader);\n if (!gl.getShaderParameter(fragmentShader, gl.COMPILE_STATUS)) {\n return false;\n }\n return true;\n }\n\n /**\n * Indicate whether this filtering backend is supported by the user's browser.\n * @param {Number} tileSize check if the tileSize is supported\n * @returns {Boolean} Whether the user's browser supports WebGL.\n */\n fabric.isWebglSupported = function(tileSize) {\n if (fabric.isLikelyNode) {\n return false;\n }\n tileSize = tileSize || fabric.WebglFilterBackend.prototype.tileSize;\n var canvas = document.createElement('canvas');\n var gl = canvas.getContext('webgl') || canvas.getContext('experimental-webgl');\n var isSupported = false;\n // eslint-disable-next-line\n if (gl) {\n fabric.maxTextureSize = gl.getParameter(gl.MAX_TEXTURE_SIZE);\n isSupported = fabric.maxTextureSize >= tileSize;\n var precisions = ['highp', 'mediump', 'lowp'];\n for (var i = 0; i < 3; i++){\n if (testPrecision(gl, precisions[i])){\n fabric.webGlPrecision = precisions[i];\n break;\n };\n }\n }\n this.isSupported = isSupported;\n return isSupported;\n };\n\n fabric.WebglFilterBackend = WebglFilterBackend;\n\n /**\n * WebGL filter backend.\n */\n function WebglFilterBackend(options) {\n if (options && options.tileSize) {\n this.tileSize = options.tileSize;\n }\n this.setupGLContext(this.tileSize, this.tileSize);\n this.captureGPUInfo();\n };\n\n WebglFilterBackend.prototype = /** @lends fabric.WebglFilterBackend.prototype */ {\n\n tileSize: 2048,\n\n /**\n * Experimental. This object is a sort of repository of help layers used to avoid\n * of recreating them during frequent filtering. If you are previewing a filter with\n * a slider you problably do not want to create help layers every filter step.\n * in this object there will be appended some canvases, created once, resized sometimes\n * cleared never. Clearing is left to the developer.\n **/\n resources: {\n\n },\n\n /**\n * Setup a WebGL context suitable for filtering, and bind any needed event handlers.\n */\n setupGLContext: function(width, height) {\n this.dispose();\n this.createWebGLCanvas(width, height);\n // eslint-disable-next-line\n this.aPosition = new Float32Array([0, 0, 0, 1, 1, 0, 1, 1]);\n this.chooseFastestCopyGLTo2DMethod(width, height);\n },\n\n /**\n * Pick a method to copy data from GL context to 2d canvas. In some browsers using\n * putImageData is faster than drawImage for that specific operation.\n */\n chooseFastestCopyGLTo2DMethod: function(width, height) {\n var canMeasurePerf = typeof window.performance !== 'undefined', canUseImageData;\n try {\n new ImageData(1, 1);\n canUseImageData = true;\n }\n catch (e) {\n canUseImageData = false;\n }\n // eslint-disable-next-line no-undef\n var canUseArrayBuffer = typeof ArrayBuffer !== 'undefined';\n // eslint-disable-next-line no-undef\n var canUseUint8Clamped = typeof Uint8ClampedArray !== 'undefined';\n\n if (!(canMeasurePerf && canUseImageData && canUseArrayBuffer && canUseUint8Clamped)) {\n return;\n }\n\n var targetCanvas = fabric.util.createCanvasElement();\n // eslint-disable-next-line no-undef\n var imageBuffer = new ArrayBuffer(width * height * 4);\n if (fabric.forceGLPutImageData) {\n this.imageBuffer = imageBuffer;\n this.copyGLTo2D = copyGLTo2DPutImageData;\n return;\n }\n var testContext = {\n imageBuffer: imageBuffer,\n destinationWidth: width,\n destinationHeight: height,\n targetCanvas: targetCanvas\n };\n var startTime, drawImageTime, putImageDataTime;\n targetCanvas.width = width;\n targetCanvas.height = height;\n\n startTime = window.performance.now();\n copyGLTo2DDrawImage.call(testContext, this.gl, testContext);\n drawImageTime = window.performance.now() - startTime;\n\n startTime = window.performance.now();\n copyGLTo2DPutImageData.call(testContext, this.gl, testContext);\n putImageDataTime = window.performance.now() - startTime;\n\n if (drawImageTime > putImageDataTime) {\n this.imageBuffer = imageBuffer;\n this.copyGLTo2D = copyGLTo2DPutImageData;\n }\n else {\n this.copyGLTo2D = copyGLTo2DDrawImage;\n }\n },\n\n /**\n * Create a canvas element and associated WebGL context and attaches them as\n * class properties to the GLFilterBackend class.\n */\n createWebGLCanvas: function(width, height) {\n var canvas = fabric.util.createCanvasElement();\n canvas.width = width;\n canvas.height = height;\n var glOptions = {\n alpha: true,\n premultipliedAlpha: false,\n depth: false,\n stencil: false,\n antialias: false\n },\n gl = canvas.getContext('webgl', glOptions);\n if (!gl) {\n gl = canvas.getContext('experimental-webgl', glOptions);\n }\n if (!gl) {\n return;\n }\n gl.clearColor(0, 0, 0, 0);\n // this canvas can fire webglcontextlost and webglcontextrestored\n this.canvas = canvas;\n this.gl = gl;\n },\n\n /**\n * Attempts to apply the requested filters to the source provided, drawing the filtered output\n * to the provided target canvas.\n *\n * @param {Array} filters The filters to apply.\n * @param {HTMLImageElement|HTMLCanvasElement} source The source to be filtered.\n * @param {Number} width The width of the source input.\n * @param {Number} height The height of the source input.\n * @param {HTMLCanvasElement} targetCanvas The destination for filtered output to be drawn.\n * @param {String|undefined} cacheKey A key used to cache resources related to the source. If\n * omitted, caching will be skipped.\n */\n applyFilters: function(filters, source, width, height, targetCanvas, cacheKey) {\n var gl = this.gl;\n var cachedTexture;\n if (cacheKey) {\n cachedTexture = this.getCachedTexture(cacheKey, source);\n }\n var pipelineState = {\n originalWidth: source.width || source.originalWidth,\n originalHeight: source.height || source.originalHeight,\n sourceWidth: width,\n sourceHeight: height,\n destinationWidth: width,\n destinationHeight: height,\n context: gl,\n sourceTexture: this.createTexture(gl, width, height, !cachedTexture && source),\n targetTexture: this.createTexture(gl, width, height),\n originalTexture: cachedTexture ||\n this.createTexture(gl, width, height, !cachedTexture && source),\n passes: filters.length,\n webgl: true,\n aPosition: this.aPosition,\n programCache: this.programCache,\n pass: 0,\n filterBackend: this,\n targetCanvas: targetCanvas\n };\n var tempFbo = gl.createFramebuffer();\n gl.bindFramebuffer(gl.FRAMEBUFFER, tempFbo);\n filters.forEach(function(filter) { filter && filter.applyTo(pipelineState); });\n resizeCanvasIfNeeded(pipelineState);\n this.copyGLTo2D(gl, pipelineState);\n gl.bindTexture(gl.TEXTURE_2D, null);\n gl.deleteTexture(pipelineState.sourceTexture);\n gl.deleteTexture(pipelineState.targetTexture);\n gl.deleteFramebuffer(tempFbo);\n targetCanvas.getContext('2d').setTransform(1, 0, 0, 1, 0, 0);\n return pipelineState;\n },\n\n /**\n * Detach event listeners, remove references, and clean up caches.\n */\n dispose: function() {\n if (this.canvas) {\n this.canvas = null;\n this.gl = null;\n }\n this.clearWebGLCaches();\n },\n\n /**\n * Wipe out WebGL-related caches.\n */\n clearWebGLCaches: function() {\n this.programCache = {};\n this.textureCache = {};\n },\n\n /**\n * Create a WebGL texture object.\n *\n * Accepts specific dimensions to initialize the textuer to or a source image.\n *\n * @param {WebGLRenderingContext} gl The GL context to use for creating the texture.\n * @param {Number} width The width to initialize the texture at.\n * @param {Number} height The height to initialize the texture.\n * @param {HTMLImageElement|HTMLCanvasElement} textureImageSource A source for the texture data.\n * @returns {WebGLTexture}\n */\n createTexture: function(gl, width, height, textureImageSource) {\n var texture = gl.createTexture();\n gl.bindTexture(gl.TEXTURE_2D, texture);\n gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MAG_FILTER, gl.NEAREST);\n gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.NEAREST);\n gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_WRAP_S, gl.CLAMP_TO_EDGE);\n gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_WRAP_T, gl.CLAMP_TO_EDGE);\n if (textureImageSource) {\n gl.texImage2D(gl.TEXTURE_2D, 0, gl.RGBA, gl.RGBA, gl.UNSIGNED_BYTE, textureImageSource);\n }\n else {\n gl.texImage2D(gl.TEXTURE_2D, 0, gl.RGBA, width, height, 0, gl.RGBA, gl.UNSIGNED_BYTE, null);\n }\n return texture;\n },\n\n /**\n * Can be optionally used to get a texture from the cache array\n *\n * If an existing texture is not found, a new texture is created and cached.\n *\n * @param {String} uniqueId A cache key to use to find an existing texture.\n * @param {HTMLImageElement|HTMLCanvasElement} textureImageSource A source to use to create the\n * texture cache entry if one does not already exist.\n */\n getCachedTexture: function(uniqueId, textureImageSource) {\n if (this.textureCache[uniqueId]) {\n return this.textureCache[uniqueId];\n }\n else {\n var texture = this.createTexture(\n this.gl, textureImageSource.width, textureImageSource.height, textureImageSource);\n this.textureCache[uniqueId] = texture;\n return texture;\n }\n },\n\n /**\n * Clear out cached resources related to a source image that has been\n * filtered previously.\n *\n * @param {String} cacheKey The cache key provided when the source image was filtered.\n */\n evictCachesForKey: function(cacheKey) {\n if (this.textureCache[cacheKey]) {\n this.gl.deleteTexture(this.textureCache[cacheKey]);\n delete this.textureCache[cacheKey];\n }\n },\n\n copyGLTo2D: copyGLTo2DDrawImage,\n\n /**\n * Attempt to extract GPU information strings from a WebGL context.\n *\n * Useful information when debugging or blacklisting specific GPUs.\n *\n * @returns {Object} A GPU info object with renderer and vendor strings.\n */\n captureGPUInfo: function() {\n if (this.gpuInfo) {\n return this.gpuInfo;\n }\n var gl = this.gl, gpuInfo = { renderer: '', vendor: '' };\n if (!gl) {\n return gpuInfo;\n }\n var ext = gl.getExtension('WEBGL_debug_renderer_info');\n if (ext) {\n var renderer = gl.getParameter(ext.UNMASKED_RENDERER_WEBGL);\n var vendor = gl.getParameter(ext.UNMASKED_VENDOR_WEBGL);\n if (renderer) {\n gpuInfo.renderer = renderer.toLowerCase();\n }\n if (vendor) {\n gpuInfo.vendor = vendor.toLowerCase();\n }\n }\n this.gpuInfo = gpuInfo;\n return gpuInfo;\n },\n };\n})();\n\nfunction resizeCanvasIfNeeded(pipelineState) {\n var targetCanvas = pipelineState.targetCanvas,\n width = targetCanvas.width, height = targetCanvas.height,\n dWidth = pipelineState.destinationWidth,\n dHeight = pipelineState.destinationHeight;\n\n if (width !== dWidth || height !== dHeight) {\n targetCanvas.width = dWidth;\n targetCanvas.height = dHeight;\n }\n}\n\n/**\n * Copy an input WebGL canvas on to an output 2D canvas.\n *\n * The WebGL canvas is assumed to be upside down, with the top-left pixel of the\n * desired output image appearing in the bottom-left corner of the WebGL canvas.\n *\n * @param {WebGLRenderingContext} sourceContext The WebGL context to copy from.\n * @param {HTMLCanvasElement} targetCanvas The 2D target canvas to copy on to.\n * @param {Object} pipelineState The 2D target canvas to copy on to.\n */\nfunction copyGLTo2DDrawImage(gl, pipelineState) {\n var glCanvas = gl.canvas, targetCanvas = pipelineState.targetCanvas,\n ctx = targetCanvas.getContext('2d');\n ctx.translate(0, targetCanvas.height); // move it down again\n ctx.scale(1, -1); // vertical flip\n // where is my image on the big glcanvas?\n var sourceY = glCanvas.height - targetCanvas.height;\n ctx.drawImage(glCanvas, 0, sourceY, targetCanvas.width, targetCanvas.height, 0, 0,\n targetCanvas.width, targetCanvas.height);\n}\n\n/**\n * Copy an input WebGL canvas on to an output 2D canvas using 2d canvas' putImageData\n * API. Measurably faster than using ctx.drawImage in Firefox (version 54 on OSX Sierra).\n *\n * @param {WebGLRenderingContext} sourceContext The WebGL context to copy from.\n * @param {HTMLCanvasElement} targetCanvas The 2D target canvas to copy on to.\n * @param {Object} pipelineState The 2D target canvas to copy on to.\n */\nfunction copyGLTo2DPutImageData(gl, pipelineState) {\n var targetCanvas = pipelineState.targetCanvas, ctx = targetCanvas.getContext('2d'),\n dWidth = pipelineState.destinationWidth,\n dHeight = pipelineState.destinationHeight,\n numBytes = dWidth * dHeight * 4;\n\n // eslint-disable-next-line no-undef\n var u8 = new Uint8Array(this.imageBuffer, 0, numBytes);\n // eslint-disable-next-line no-undef\n var u8Clamped = new Uint8ClampedArray(this.imageBuffer, 0, numBytes);\n\n gl.readPixels(0, 0, dWidth, dHeight, gl.RGBA, gl.UNSIGNED_BYTE, u8);\n var imgData = new ImageData(u8Clamped, dWidth, dHeight);\n ctx.putImageData(imgData, 0, 0);\n}\n\n\n(function() {\n\n 'use strict';\n\n var noop = function() {};\n\n fabric.Canvas2dFilterBackend = Canvas2dFilterBackend;\n\n /**\n * Canvas 2D filter backend.\n */\n function Canvas2dFilterBackend() {};\n\n Canvas2dFilterBackend.prototype = /** @lends fabric.Canvas2dFilterBackend.prototype */ {\n evictCachesForKey: noop,\n dispose: noop,\n clearWebGLCaches: noop,\n\n /**\n * Experimental. This object is a sort of repository of help layers used to avoid\n * of recreating them during frequent filtering. If you are previewing a filter with\n * a slider you probably do not want to create help layers every filter step.\n * in this object there will be appended some canvases, created once, resized sometimes\n * cleared never. Clearing is left to the developer.\n **/\n resources: {\n\n },\n\n /**\n * Apply a set of filters against a source image and draw the filtered output\n * to the provided destination canvas.\n *\n * @param {EnhancedFilter} filters The filter to apply.\n * @param {HTMLImageElement|HTMLCanvasElement} sourceElement The source to be filtered.\n * @param {Number} sourceWidth The width of the source input.\n * @param {Number} sourceHeight The height of the source input.\n * @param {HTMLCanvasElement} targetCanvas The destination for filtered output to be drawn.\n */\n applyFilters: function(filters, sourceElement, sourceWidth, sourceHeight, targetCanvas) {\n var ctx = targetCanvas.getContext('2d');\n ctx.drawImage(sourceElement, 0, 0, sourceWidth, sourceHeight);\n var imageData = ctx.getImageData(0, 0, sourceWidth, sourceHeight);\n var originalImageData = ctx.getImageData(0, 0, sourceWidth, sourceHeight);\n var pipelineState = {\n sourceWidth: sourceWidth,\n sourceHeight: sourceHeight,\n imageData: imageData,\n originalEl: sourceElement,\n originalImageData: originalImageData,\n canvasEl: targetCanvas,\n ctx: ctx,\n filterBackend: this,\n };\n filters.forEach(function(filter) { filter.applyTo(pipelineState); });\n if (pipelineState.imageData.width !== sourceWidth || pipelineState.imageData.height !== sourceHeight) {\n targetCanvas.width = pipelineState.imageData.width;\n targetCanvas.height = pipelineState.imageData.height;\n }\n ctx.putImageData(pipelineState.imageData, 0, 0);\n return pipelineState;\n },\n\n };\n})();\n\n\n/**\n * @namespace fabric.Image.filters\n * @memberOf fabric.Image\n * @tutorial {@link http://fabricjs.com/fabric-intro-part-2#image_filters}\n * @see {@link http://fabricjs.com/image-filters|ImageFilters demo}\n */\nfabric.Image = fabric.Image || { };\nfabric.Image.filters = fabric.Image.filters || { };\n\n/**\n * Root filter class from which all filter classes inherit from\n * @class fabric.Image.filters.BaseFilter\n * @memberOf fabric.Image.filters\n */\nfabric.Image.filters.BaseFilter = fabric.util.createClass(/** @lends fabric.Image.filters.BaseFilter.prototype */ {\n\n /**\n * Filter type\n * @param {String} type\n * @default\n */\n type: 'BaseFilter',\n\n /**\n * Array of attributes to send with buffers. do not modify\n * @private\n */\n\n vertexSource: 'attribute vec2 aPosition;\\n' +\n 'varying vec2 vTexCoord;\\n' +\n 'void main() {\\n' +\n 'vTexCoord = aPosition;\\n' +\n 'gl_Position = vec4(aPosition * 2.0 - 1.0, 0.0, 1.0);\\n' +\n '}',\n\n fragmentSource: 'precision highp float;\\n' +\n 'varying vec2 vTexCoord;\\n' +\n 'uniform sampler2D uTexture;\\n' +\n 'void main() {\\n' +\n 'gl_FragColor = texture2D(uTexture, vTexCoord);\\n' +\n '}',\n\n /**\n * Constructor\n * @param {Object} [options] Options object\n */\n initialize: function(options) {\n if (options) {\n this.setOptions(options);\n }\n },\n\n /**\n * Sets filter's properties from options\n * @param {Object} [options] Options object\n */\n setOptions: function(options) {\n for (var prop in options) {\n this[prop] = options[prop];\n }\n },\n\n /**\n * Compile this filter's shader program.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context to use for shader compilation.\n * @param {String} fragmentSource fragmentShader source for compilation\n * @param {String} vertexSource vertexShader source for compilation\n */\n createProgram: function(gl, fragmentSource, vertexSource) {\n fragmentSource = fragmentSource || this.fragmentSource;\n vertexSource = vertexSource || this.vertexSource;\n if (fabric.webGlPrecision !== 'highp'){\n fragmentSource = fragmentSource.replace(\n /precision highp float/g,\n 'precision ' + fabric.webGlPrecision + ' float'\n );\n }\n var vertexShader = gl.createShader(gl.VERTEX_SHADER);\n gl.shaderSource(vertexShader, vertexSource);\n gl.compileShader(vertexShader);\n if (!gl.getShaderParameter(vertexShader, gl.COMPILE_STATUS)) {\n throw new Error(\n // eslint-disable-next-line prefer-template\n 'Vertex shader compile error for ' + this.type + ': ' +\n gl.getShaderInfoLog(vertexShader)\n );\n }\n\n var fragmentShader = gl.createShader(gl.FRAGMENT_SHADER);\n gl.shaderSource(fragmentShader, fragmentSource);\n gl.compileShader(fragmentShader);\n if (!gl.getShaderParameter(fragmentShader, gl.COMPILE_STATUS)) {\n throw new Error(\n // eslint-disable-next-line prefer-template\n 'Fragment shader compile error for ' + this.type + ': ' +\n gl.getShaderInfoLog(fragmentShader)\n );\n }\n\n var program = gl.createProgram();\n gl.attachShader(program, vertexShader);\n gl.attachShader(program, fragmentShader);\n gl.linkProgram(program);\n if (!gl.getProgramParameter(program, gl.LINK_STATUS)) {\n throw new Error(\n // eslint-disable-next-line prefer-template\n 'Shader link error for \"${this.type}\" ' +\n gl.getProgramInfoLog(program)\n );\n }\n\n var attributeLocations = this.getAttributeLocations(gl, program);\n var uniformLocations = this.getUniformLocations(gl, program) || { };\n uniformLocations.uStepW = gl.getUniformLocation(program, 'uStepW');\n uniformLocations.uStepH = gl.getUniformLocation(program, 'uStepH');\n return {\n program: program,\n attributeLocations: attributeLocations,\n uniformLocations: uniformLocations\n };\n },\n\n /**\n * Return a map of attribute names to WebGLAttributeLocation objects.\n *\n * @param {WebGLRenderingContext} gl The canvas context used to compile the shader program.\n * @param {WebGLShaderProgram} program The shader program from which to take attribute locations.\n * @returns {Object} A map of attribute names to attribute locations.\n */\n getAttributeLocations: function(gl, program) {\n return {\n aPosition: gl.getAttribLocation(program, 'aPosition'),\n };\n },\n\n /**\n * Return a map of uniform names to WebGLUniformLocation objects.\n *\n * Intended to be overridden by subclasses.\n *\n * @param {WebGLRenderingContext} gl The canvas context used to compile the shader program.\n * @param {WebGLShaderProgram} program The shader program from which to take uniform locations.\n * @returns {Object} A map of uniform names to uniform locations.\n */\n getUniformLocations: function (/* gl, program */) {\n // in case i do not need any special uniform i need to return an empty object\n return { };\n },\n\n /**\n * Send attribute data from this filter to its shader program on the GPU.\n *\n * @param {WebGLRenderingContext} gl The canvas context used to compile the shader program.\n * @param {Object} attributeLocations A map of shader attribute names to their locations.\n */\n sendAttributeData: function(gl, attributeLocations, aPositionData) {\n var attributeLocation = attributeLocations.aPosition;\n var buffer = gl.createBuffer();\n gl.bindBuffer(gl.ARRAY_BUFFER, buffer);\n gl.enableVertexAttribArray(attributeLocation);\n gl.vertexAttribPointer(attributeLocation, 2, gl.FLOAT, false, 0, 0);\n gl.bufferData(gl.ARRAY_BUFFER, aPositionData, gl.STATIC_DRAW);\n },\n\n _setupFrameBuffer: function(options) {\n var gl = options.context, width, height;\n if (options.passes > 1) {\n width = options.destinationWidth;\n height = options.destinationHeight;\n if (options.sourceWidth !== width || options.sourceHeight !== height) {\n gl.deleteTexture(options.targetTexture);\n options.targetTexture = options.filterBackend.createTexture(gl, width, height);\n }\n gl.framebufferTexture2D(gl.FRAMEBUFFER, gl.COLOR_ATTACHMENT0, gl.TEXTURE_2D,\n options.targetTexture, 0);\n }\n else {\n // draw last filter on canvas and not to framebuffer.\n gl.bindFramebuffer(gl.FRAMEBUFFER, null);\n gl.finish();\n }\n },\n\n _swapTextures: function(options) {\n options.passes--;\n options.pass++;\n var temp = options.targetTexture;\n options.targetTexture = options.sourceTexture;\n options.sourceTexture = temp;\n },\n\n /**\n * Generic isNeutral implementation for one parameter based filters.\n * Used only in image applyFilters to discard filters that will not have an effect\n * on the image\n * Other filters may need their own verison ( ColorMatrix, HueRotation, gamma, ComposedFilter )\n * @param {Object} options\n **/\n isNeutralState: function(/* options */) {\n var main = this.mainParameter,\n _class = fabric.Image.filters[this.type].prototype;\n if (main) {\n if (Array.isArray(_class[main])) {\n for (var i = _class[main].length; i--;) {\n if (this[main][i] !== _class[main][i]) {\n return false;\n }\n }\n return true;\n }\n else {\n return _class[main] === this[main];\n }\n }\n else {\n return false;\n }\n },\n\n /**\n * Apply this filter to the input image data provided.\n *\n * Determines whether to use WebGL or Canvas2D based on the options.webgl flag.\n *\n * @param {Object} options\n * @param {Number} options.passes The number of filters remaining to be executed\n * @param {Boolean} options.webgl Whether to use webgl to render the filter.\n * @param {WebGLTexture} options.sourceTexture The texture setup as the source to be filtered.\n * @param {WebGLTexture} options.targetTexture The texture where filtered output should be drawn.\n * @param {WebGLRenderingContext} options.context The GL context used for rendering.\n * @param {Object} options.programCache A map of compiled shader programs, keyed by filter type.\n */\n applyTo: function(options) {\n if (options.webgl) {\n this._setupFrameBuffer(options);\n this.applyToWebGL(options);\n this._swapTextures(options);\n }\n else {\n this.applyTo2d(options);\n }\n },\n\n /**\n * Retrieves the cached shader.\n * @param {Object} options\n * @param {WebGLRenderingContext} options.context The GL context used for rendering.\n * @param {Object} options.programCache A map of compiled shader programs, keyed by filter type.\n */\n retrieveShader: function(options) {\n if (!options.programCache.hasOwnProperty(this.type)) {\n options.programCache[this.type] = this.createProgram(options.context);\n }\n return options.programCache[this.type];\n },\n\n /**\n * Apply this filter using webgl.\n *\n * @param {Object} options\n * @param {Number} options.passes The number of filters remaining to be executed\n * @param {Boolean} options.webgl Whether to use webgl to render the filter.\n * @param {WebGLTexture} options.originalTexture The texture of the original input image.\n * @param {WebGLTexture} options.sourceTexture The texture setup as the source to be filtered.\n * @param {WebGLTexture} options.targetTexture The texture where filtered output should be drawn.\n * @param {WebGLRenderingContext} options.context The GL context used for rendering.\n * @param {Object} options.programCache A map of compiled shader programs, keyed by filter type.\n */\n applyToWebGL: function(options) {\n var gl = options.context;\n var shader = this.retrieveShader(options);\n if (options.pass === 0 && options.originalTexture) {\n gl.bindTexture(gl.TEXTURE_2D, options.originalTexture);\n }\n else {\n gl.bindTexture(gl.TEXTURE_2D, options.sourceTexture);\n }\n gl.useProgram(shader.program);\n this.sendAttributeData(gl, shader.attributeLocations, options.aPosition);\n\n gl.uniform1f(shader.uniformLocations.uStepW, 1 / options.sourceWidth);\n gl.uniform1f(shader.uniformLocations.uStepH, 1 / options.sourceHeight);\n\n this.sendUniformData(gl, shader.uniformLocations);\n gl.viewport(0, 0, options.destinationWidth, options.destinationHeight);\n gl.drawArrays(gl.TRIANGLE_STRIP, 0, 4);\n },\n\n bindAdditionalTexture: function(gl, texture, textureUnit) {\n gl.activeTexture(textureUnit);\n gl.bindTexture(gl.TEXTURE_2D, texture);\n // reset active texture to 0 as usual\n gl.activeTexture(gl.TEXTURE0);\n },\n\n unbindAdditionalTexture: function(gl, textureUnit) {\n gl.activeTexture(textureUnit);\n gl.bindTexture(gl.TEXTURE_2D, null);\n gl.activeTexture(gl.TEXTURE0);\n },\n\n getMainParameter: function() {\n return this[this.mainParameter];\n },\n\n setMainParameter: function(value) {\n this[this.mainParameter] = value;\n },\n\n /**\n * Send uniform data from this filter to its shader program on the GPU.\n *\n * Intended to be overridden by subclasses.\n *\n * @param {WebGLRenderingContext} gl The canvas context used to compile the shader program.\n * @param {Object} uniformLocations A map of shader uniform names to their locations.\n */\n sendUniformData: function(/* gl, uniformLocations */) {\n // Intentionally left blank. Override me in subclasses.\n },\n\n /**\n * If needed by a 2d filter, this functions can create an helper canvas to be used\n * remember that options.targetCanvas is available for use till end of chain.\n */\n createHelpLayer: function(options) {\n if (!options.helpLayer) {\n var helpLayer = document.createElement('canvas');\n helpLayer.width = options.sourceWidth;\n helpLayer.height = options.sourceHeight;\n options.helpLayer = helpLayer;\n }\n },\n\n /**\n * Returns object representation of an instance\n * @return {Object} Object representation of an instance\n */\n toObject: function() {\n var object = { type: this.type }, mainP = this.mainParameter;\n if (mainP) {\n object[mainP] = this[mainP];\n }\n return object;\n },\n\n /**\n * Returns a JSON representation of an instance\n * @return {Object} JSON\n */\n toJSON: function() {\n // delegate, not alias\n return this.toObject();\n }\n});\n\nfabric.Image.filters.BaseFilter.fromObject = function(object, callback) {\n var filter = new fabric.Image.filters[object.type](object);\n callback && callback(filter);\n return filter;\n};\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { }),\n filters = fabric.Image.filters,\n createClass = fabric.util.createClass;\n\n /**\n * Color Matrix filter class\n * @class fabric.Image.filters.ColorMatrix\n * @memberOf fabric.Image.filters\n * @extends fabric.Image.filters.BaseFilter\n * @see {@link fabric.Image.filters.ColorMatrix#initialize} for constructor definition\n * @see {@link http://fabricjs.com/image-filters|ImageFilters demo}\n * @see {@Link http://www.webwasp.co.uk/tutorials/219/Color_Matrix_Filter.php}\n * @see {@Link http://phoboslab.org/log/2013/11/fast-image-filters-with-webgl}\n * @example Kodachrome filter\n * var filter = new fabric.Image.filters.ColorMatrix({\n * matrix: [\n 1.1285582396593525, -0.3967382283601348, -0.03992559172921793, 0, 63.72958762196502,\n -0.16404339962244616, 1.0835251566291304, -0.05498805115633132, 0, 24.732407896706203,\n -0.16786010706155763, -0.5603416277695248, 1.6014850761964943, 0, 35.62982807460946,\n 0, 0, 0, 1, 0\n ]\n * });\n * object.filters.push(filter);\n * object.applyFilters();\n */\n filters.ColorMatrix = createClass(filters.BaseFilter, /** @lends fabric.Image.filters.ColorMatrix.prototype */ {\n\n /**\n * Filter type\n * @param {String} type\n * @default\n */\n type: 'ColorMatrix',\n\n fragmentSource: 'precision highp float;\\n' +\n 'uniform sampler2D uTexture;\\n' +\n 'varying vec2 vTexCoord;\\n' +\n 'uniform mat4 uColorMatrix;\\n' +\n 'uniform vec4 uConstants;\\n' +\n 'void main() {\\n' +\n 'vec4 color = texture2D(uTexture, vTexCoord);\\n' +\n 'color *= uColorMatrix;\\n' +\n 'color += uConstants;\\n' +\n 'gl_FragColor = color;\\n' +\n '}',\n\n /**\n * Colormatrix for pixels.\n * array of 20 floats. Numbers in positions 4, 9, 14, 19 loose meaning\n * outside the -1, 1 range.\n * 0.0039215686 is the part of 1 that get translated to 1 in 2d\n * @param {Array} matrix array of 20 numbers.\n * @default\n */\n matrix: [\n 1, 0, 0, 0, 0,\n 0, 1, 0, 0, 0,\n 0, 0, 1, 0, 0,\n 0, 0, 0, 1, 0\n ],\n\n mainParameter: 'matrix',\n\n /**\n * Lock the colormatrix on the color part, skipping alpha, manly for non webgl scenario\n * to save some calculation\n */\n colorsOnly: true,\n\n /**\n * Constructor\n * @param {Object} [options] Options object\n */\n initialize: function(options) {\n this.callSuper('initialize', options);\n // create a new array instead mutating the prototype with push\n this.matrix = this.matrix.slice(0);\n },\n\n /**\n * Apply the ColorMatrix operation to a Uint8Array representing the pixels of an image.\n *\n * @param {Object} options\n * @param {ImageData} options.imageData The Uint8Array to be filtered.\n */\n applyTo2d: function(options) {\n var imageData = options.imageData,\n data = imageData.data,\n iLen = data.length,\n m = this.matrix,\n r, g, b, a, i, colorsOnly = this.colorsOnly;\n\n for (i = 0; i < iLen; i += 4) {\n r = data[i];\n g = data[i + 1];\n b = data[i + 2];\n if (colorsOnly) {\n data[i] = r * m[0] + g * m[1] + b * m[2] + m[4] * 255;\n data[i + 1] = r * m[5] + g * m[6] + b * m[7] + m[9] * 255;\n data[i + 2] = r * m[10] + g * m[11] + b * m[12] + m[14] * 255;\n }\n else {\n a = data[i + 3];\n data[i] = r * m[0] + g * m[1] + b * m[2] + a * m[3] + m[4] * 255;\n data[i + 1] = r * m[5] + g * m[6] + b * m[7] + a * m[8] + m[9] * 255;\n data[i + 2] = r * m[10] + g * m[11] + b * m[12] + a * m[13] + m[14] * 255;\n data[i + 3] = r * m[15] + g * m[16] + b * m[17] + a * m[18] + m[19] * 255;\n }\n }\n },\n\n /**\n * Return WebGL uniform locations for this filter's shader.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {WebGLShaderProgram} program This filter's compiled shader program.\n */\n getUniformLocations: function(gl, program) {\n return {\n uColorMatrix: gl.getUniformLocation(program, 'uColorMatrix'),\n uConstants: gl.getUniformLocation(program, 'uConstants'),\n };\n },\n\n /**\n * Send data from this filter to its shader program's uniforms.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {Object} uniformLocations A map of string uniform names to WebGLUniformLocation objects\n */\n sendUniformData: function(gl, uniformLocations) {\n var m = this.matrix,\n matrix = [\n m[0], m[1], m[2], m[3],\n m[5], m[6], m[7], m[8],\n m[10], m[11], m[12], m[13],\n m[15], m[16], m[17], m[18]\n ],\n constants = [m[4], m[9], m[14], m[19]];\n gl.uniformMatrix4fv(uniformLocations.uColorMatrix, false, matrix);\n gl.uniform4fv(uniformLocations.uConstants, constants);\n },\n });\n\n /**\n * Returns filter instance from an object representation\n * @static\n * @param {Object} object Object to create an instance from\n * @param {function} [callback] function to invoke after filter creation\n * @return {fabric.Image.filters.ColorMatrix} Instance of fabric.Image.filters.ColorMatrix\n */\n fabric.Image.filters.ColorMatrix.fromObject = fabric.Image.filters.BaseFilter.fromObject;\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { }),\n filters = fabric.Image.filters,\n createClass = fabric.util.createClass;\n\n /**\n * Brightness filter class\n * @class fabric.Image.filters.Brightness\n * @memberOf fabric.Image.filters\n * @extends fabric.Image.filters.BaseFilter\n * @see {@link fabric.Image.filters.Brightness#initialize} for constructor definition\n * @see {@link http://fabricjs.com/image-filters|ImageFilters demo}\n * @example\n * var filter = new fabric.Image.filters.Brightness({\n * brightness: 0.05\n * });\n * object.filters.push(filter);\n * object.applyFilters();\n */\n filters.Brightness = createClass(filters.BaseFilter, /** @lends fabric.Image.filters.Brightness.prototype */ {\n\n /**\n * Filter type\n * @param {String} type\n * @default\n */\n type: 'Brightness',\n\n /**\n * Fragment source for the brightness program\n */\n fragmentSource: 'precision highp float;\\n' +\n 'uniform sampler2D uTexture;\\n' +\n 'uniform float uBrightness;\\n' +\n 'varying vec2 vTexCoord;\\n' +\n 'void main() {\\n' +\n 'vec4 color = texture2D(uTexture, vTexCoord);\\n' +\n 'color.rgb += uBrightness;\\n' +\n 'gl_FragColor = color;\\n' +\n '}',\n\n /**\n * Brightness value, from -1 to 1.\n * translated to -255 to 255 for 2d\n * 0.0039215686 is the part of 1 that get translated to 1 in 2d\n * @param {Number} brightness\n * @default\n */\n brightness: 0,\n\n /**\n * Describe the property that is the filter parameter\n * @param {String} m\n * @default\n */\n mainParameter: 'brightness',\n\n /**\n * Apply the Brightness operation to a Uint8ClampedArray representing the pixels of an image.\n *\n * @param {Object} options\n * @param {ImageData} options.imageData The Uint8ClampedArray to be filtered.\n */\n applyTo2d: function(options) {\n if (this.brightness === 0) {\n return;\n }\n var imageData = options.imageData,\n data = imageData.data, i, len = data.length,\n brightness = Math.round(this.brightness * 255);\n for (i = 0; i < len; i += 4) {\n data[i] = data[i] + brightness;\n data[i + 1] = data[i + 1] + brightness;\n data[i + 2] = data[i + 2] + brightness;\n }\n },\n\n /**\n * Return WebGL uniform locations for this filter's shader.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {WebGLShaderProgram} program This filter's compiled shader program.\n */\n getUniformLocations: function(gl, program) {\n return {\n uBrightness: gl.getUniformLocation(program, 'uBrightness'),\n };\n },\n\n /**\n * Send data from this filter to its shader program's uniforms.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {Object} uniformLocations A map of string uniform names to WebGLUniformLocation objects\n */\n sendUniformData: function(gl, uniformLocations) {\n gl.uniform1f(uniformLocations.uBrightness, this.brightness);\n },\n });\n\n /**\n * Returns filter instance from an object representation\n * @static\n * @param {Object} object Object to create an instance from\n * @param {function} [callback] to be invoked after filter creation\n * @return {fabric.Image.filters.Brightness} Instance of fabric.Image.filters.Brightness\n */\n fabric.Image.filters.Brightness.fromObject = fabric.Image.filters.BaseFilter.fromObject;\n\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { }),\n extend = fabric.util.object.extend,\n filters = fabric.Image.filters,\n createClass = fabric.util.createClass;\n\n /**\n * Adapted from html5rocks article\n * @class fabric.Image.filters.Convolute\n * @memberOf fabric.Image.filters\n * @extends fabric.Image.filters.BaseFilter\n * @see {@link fabric.Image.filters.Convolute#initialize} for constructor definition\n * @see {@link http://fabricjs.com/image-filters|ImageFilters demo}\n * @example Sharpen filter\n * var filter = new fabric.Image.filters.Convolute({\n * matrix: [ 0, -1, 0,\n * -1, 5, -1,\n * 0, -1, 0 ]\n * });\n * object.filters.push(filter);\n * object.applyFilters();\n * canvas.renderAll();\n * @example Blur filter\n * var filter = new fabric.Image.filters.Convolute({\n * matrix: [ 1/9, 1/9, 1/9,\n * 1/9, 1/9, 1/9,\n * 1/9, 1/9, 1/9 ]\n * });\n * object.filters.push(filter);\n * object.applyFilters();\n * canvas.renderAll();\n * @example Emboss filter\n * var filter = new fabric.Image.filters.Convolute({\n * matrix: [ 1, 1, 1,\n * 1, 0.7, -1,\n * -1, -1, -1 ]\n * });\n * object.filters.push(filter);\n * object.applyFilters();\n * canvas.renderAll();\n * @example Emboss filter with opaqueness\n * var filter = new fabric.Image.filters.Convolute({\n * opaque: true,\n * matrix: [ 1, 1, 1,\n * 1, 0.7, -1,\n * -1, -1, -1 ]\n * });\n * object.filters.push(filter);\n * object.applyFilters();\n * canvas.renderAll();\n */\n filters.Convolute = createClass(filters.BaseFilter, /** @lends fabric.Image.filters.Convolute.prototype */ {\n\n /**\n * Filter type\n * @param {String} type\n * @default\n */\n type: 'Convolute',\n\n /*\n * Opaque value (true/false)\n */\n opaque: false,\n\n /*\n * matrix for the filter, max 9x9\n */\n matrix: [0, 0, 0, 0, 1, 0, 0, 0, 0],\n\n /**\n * Fragment source for the brightness program\n */\n fragmentSource: {\n Convolute_3_1: 'precision highp float;\\n' +\n 'uniform sampler2D uTexture;\\n' +\n 'uniform float uMatrix[9];\\n' +\n 'uniform float uStepW;\\n' +\n 'uniform float uStepH;\\n' +\n 'varying vec2 vTexCoord;\\n' +\n 'void main() {\\n' +\n 'vec4 color = vec4(0, 0, 0, 0);\\n' +\n 'for (float h = 0.0; h < 3.0; h+=1.0) {\\n' +\n 'for (float w = 0.0; w < 3.0; w+=1.0) {\\n' +\n 'vec2 matrixPos = vec2(uStepW * (w - 1), uStepH * (h - 1));\\n' +\n 'color += texture2D(uTexture, vTexCoord + matrixPos) * uMatrix[int(h * 3.0 + w)];\\n' +\n '}\\n' +\n '}\\n' +\n 'gl_FragColor = color;\\n' +\n '}',\n Convolute_3_0: 'precision highp float;\\n' +\n 'uniform sampler2D uTexture;\\n' +\n 'uniform float uMatrix[9];\\n' +\n 'uniform float uStepW;\\n' +\n 'uniform float uStepH;\\n' +\n 'varying vec2 vTexCoord;\\n' +\n 'void main() {\\n' +\n 'vec4 color = vec4(0, 0, 0, 1);\\n' +\n 'for (float h = 0.0; h < 3.0; h+=1.0) {\\n' +\n 'for (float w = 0.0; w < 3.0; w+=1.0) {\\n' +\n 'vec2 matrixPos = vec2(uStepW * (w - 1.0), uStepH * (h - 1.0));\\n' +\n 'color.rgb += texture2D(uTexture, vTexCoord + matrixPos).rgb * uMatrix[int(h * 3.0 + w)];\\n' +\n '}\\n' +\n '}\\n' +\n 'float alpha = texture2D(uTexture, vTexCoord).a;\\n' +\n 'gl_FragColor = color;\\n' +\n 'gl_FragColor.a = alpha;\\n' +\n '}',\n Convolute_5_1: 'precision highp float;\\n' +\n 'uniform sampler2D uTexture;\\n' +\n 'uniform float uMatrix[25];\\n' +\n 'uniform float uStepW;\\n' +\n 'uniform float uStepH;\\n' +\n 'varying vec2 vTexCoord;\\n' +\n 'void main() {\\n' +\n 'vec4 color = vec4(0, 0, 0, 0);\\n' +\n 'for (float h = 0.0; h < 5.0; h+=1.0) {\\n' +\n 'for (float w = 0.0; w < 5.0; w+=1.0) {\\n' +\n 'vec2 matrixPos = vec2(uStepW * (w - 2.0), uStepH * (h - 2.0));\\n' +\n 'color += texture2D(uTexture, vTexCoord + matrixPos) * uMatrix[int(h * 5.0 + w)];\\n' +\n '}\\n' +\n '}\\n' +\n 'gl_FragColor = color;\\n' +\n '}',\n Convolute_5_0: 'precision highp float;\\n' +\n 'uniform sampler2D uTexture;\\n' +\n 'uniform float uMatrix[25];\\n' +\n 'uniform float uStepW;\\n' +\n 'uniform float uStepH;\\n' +\n 'varying vec2 vTexCoord;\\n' +\n 'void main() {\\n' +\n 'vec4 color = vec4(0, 0, 0, 1);\\n' +\n 'for (float h = 0.0; h < 5.0; h+=1.0) {\\n' +\n 'for (float w = 0.0; w < 5.0; w+=1.0) {\\n' +\n 'vec2 matrixPos = vec2(uStepW * (w - 2.0), uStepH * (h - 2.0));\\n' +\n 'color.rgb += texture2D(uTexture, vTexCoord + matrixPos).rgb * uMatrix[int(h * 5.0 + w)];\\n' +\n '}\\n' +\n '}\\n' +\n 'float alpha = texture2D(uTexture, vTexCoord).a;\\n' +\n 'gl_FragColor = color;\\n' +\n 'gl_FragColor.a = alpha;\\n' +\n '}',\n Convolute_7_1: 'precision highp float;\\n' +\n 'uniform sampler2D uTexture;\\n' +\n 'uniform float uMatrix[49];\\n' +\n 'uniform float uStepW;\\n' +\n 'uniform float uStepH;\\n' +\n 'varying vec2 vTexCoord;\\n' +\n 'void main() {\\n' +\n 'vec4 color = vec4(0, 0, 0, 0);\\n' +\n 'for (float h = 0.0; h < 7.0; h+=1.0) {\\n' +\n 'for (float w = 0.0; w < 7.0; w+=1.0) {\\n' +\n 'vec2 matrixPos = vec2(uStepW * (w - 3.0), uStepH * (h - 3.0));\\n' +\n 'color += texture2D(uTexture, vTexCoord + matrixPos) * uMatrix[int(h * 7.0 + w)];\\n' +\n '}\\n' +\n '}\\n' +\n 'gl_FragColor = color;\\n' +\n '}',\n Convolute_7_0: 'precision highp float;\\n' +\n 'uniform sampler2D uTexture;\\n' +\n 'uniform float uMatrix[49];\\n' +\n 'uniform float uStepW;\\n' +\n 'uniform float uStepH;\\n' +\n 'varying vec2 vTexCoord;\\n' +\n 'void main() {\\n' +\n 'vec4 color = vec4(0, 0, 0, 1);\\n' +\n 'for (float h = 0.0; h < 7.0; h+=1.0) {\\n' +\n 'for (float w = 0.0; w < 7.0; w+=1.0) {\\n' +\n 'vec2 matrixPos = vec2(uStepW * (w - 3.0), uStepH * (h - 3.0));\\n' +\n 'color.rgb += texture2D(uTexture, vTexCoord + matrixPos).rgb * uMatrix[int(h * 7.0 + w)];\\n' +\n '}\\n' +\n '}\\n' +\n 'float alpha = texture2D(uTexture, vTexCoord).a;\\n' +\n 'gl_FragColor = color;\\n' +\n 'gl_FragColor.a = alpha;\\n' +\n '}',\n Convolute_9_1: 'precision highp float;\\n' +\n 'uniform sampler2D uTexture;\\n' +\n 'uniform float uMatrix[81];\\n' +\n 'uniform float uStepW;\\n' +\n 'uniform float uStepH;\\n' +\n 'varying vec2 vTexCoord;\\n' +\n 'void main() {\\n' +\n 'vec4 color = vec4(0, 0, 0, 0);\\n' +\n 'for (float h = 0.0; h < 9.0; h+=1.0) {\\n' +\n 'for (float w = 0.0; w < 9.0; w+=1.0) {\\n' +\n 'vec2 matrixPos = vec2(uStepW * (w - 4.0), uStepH * (h - 4.0));\\n' +\n 'color += texture2D(uTexture, vTexCoord + matrixPos) * uMatrix[int(h * 9.0 + w)];\\n' +\n '}\\n' +\n '}\\n' +\n 'gl_FragColor = color;\\n' +\n '}',\n Convolute_9_0: 'precision highp float;\\n' +\n 'uniform sampler2D uTexture;\\n' +\n 'uniform float uMatrix[81];\\n' +\n 'uniform float uStepW;\\n' +\n 'uniform float uStepH;\\n' +\n 'varying vec2 vTexCoord;\\n' +\n 'void main() {\\n' +\n 'vec4 color = vec4(0, 0, 0, 1);\\n' +\n 'for (float h = 0.0; h < 9.0; h+=1.0) {\\n' +\n 'for (float w = 0.0; w < 9.0; w+=1.0) {\\n' +\n 'vec2 matrixPos = vec2(uStepW * (w - 4.0), uStepH * (h - 4.0));\\n' +\n 'color.rgb += texture2D(uTexture, vTexCoord + matrixPos).rgb * uMatrix[int(h * 9.0 + w)];\\n' +\n '}\\n' +\n '}\\n' +\n 'float alpha = texture2D(uTexture, vTexCoord).a;\\n' +\n 'gl_FragColor = color;\\n' +\n 'gl_FragColor.a = alpha;\\n' +\n '}',\n },\n\n /**\n * Constructor\n * @memberOf fabric.Image.filters.Convolute.prototype\n * @param {Object} [options] Options object\n * @param {Boolean} [options.opaque=false] Opaque value (true/false)\n * @param {Array} [options.matrix] Filter matrix\n */\n\n\n /**\n * Retrieves the cached shader.\n * @param {Object} options\n * @param {WebGLRenderingContext} options.context The GL context used for rendering.\n * @param {Object} options.programCache A map of compiled shader programs, keyed by filter type.\n */\n retrieveShader: function(options) {\n var size = Math.sqrt(this.matrix.length);\n var cacheKey = this.type + '_' + size + '_' + (this.opaque ? 1 : 0);\n var shaderSource = this.fragmentSource[cacheKey];\n if (!options.programCache.hasOwnProperty(cacheKey)) {\n options.programCache[cacheKey] = this.createProgram(options.context, shaderSource);\n }\n return options.programCache[cacheKey];\n },\n\n /**\n * Apply the Brightness operation to a Uint8ClampedArray representing the pixels of an image.\n *\n * @param {Object} options\n * @param {ImageData} options.imageData The Uint8ClampedArray to be filtered.\n */\n applyTo2d: function(options) {\n var imageData = options.imageData,\n data = imageData.data,\n weights = this.matrix,\n side = Math.round(Math.sqrt(weights.length)),\n halfSide = Math.floor(side / 2),\n sw = imageData.width,\n sh = imageData.height,\n output = options.ctx.createImageData(sw, sh),\n dst = output.data,\n // go through the destination image pixels\n alphaFac = this.opaque ? 1 : 0,\n r, g, b, a, dstOff,\n scx, scy, srcOff, wt,\n x, y, cx, cy;\n\n for (y = 0; y < sh; y++) {\n for (x = 0; x < sw; x++) {\n dstOff = (y * sw + x) * 4;\n // calculate the weighed sum of the source image pixels that\n // fall under the convolution matrix\n r = 0; g = 0; b = 0; a = 0;\n\n for (cy = 0; cy < side; cy++) {\n for (cx = 0; cx < side; cx++) {\n scy = y + cy - halfSide;\n scx = x + cx - halfSide;\n\n // eslint-disable-next-line max-depth\n if (scy < 0 || scy >= sh || scx < 0 || scx >= sw) {\n continue;\n }\n\n srcOff = (scy * sw + scx) * 4;\n wt = weights[cy * side + cx];\n\n r += data[srcOff] * wt;\n g += data[srcOff + 1] * wt;\n b += data[srcOff + 2] * wt;\n // eslint-disable-next-line max-depth\n if (!alphaFac) {\n a += data[srcOff + 3] * wt;\n }\n }\n }\n dst[dstOff] = r;\n dst[dstOff + 1] = g;\n dst[dstOff + 2] = b;\n if (!alphaFac) {\n dst[dstOff + 3] = a;\n }\n else {\n dst[dstOff + 3] = data[dstOff + 3];\n }\n }\n }\n options.imageData = output;\n },\n\n /**\n * Return WebGL uniform locations for this filter's shader.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {WebGLShaderProgram} program This filter's compiled shader program.\n */\n getUniformLocations: function(gl, program) {\n return {\n uMatrix: gl.getUniformLocation(program, 'uMatrix'),\n uOpaque: gl.getUniformLocation(program, 'uOpaque'),\n uHalfSize: gl.getUniformLocation(program, 'uHalfSize'),\n uSize: gl.getUniformLocation(program, 'uSize'),\n };\n },\n\n /**\n * Send data from this filter to its shader program's uniforms.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {Object} uniformLocations A map of string uniform names to WebGLUniformLocation objects\n */\n sendUniformData: function(gl, uniformLocations) {\n gl.uniform1fv(uniformLocations.uMatrix, this.matrix);\n },\n\n /**\n * Returns object representation of an instance\n * @return {Object} Object representation of an instance\n */\n toObject: function() {\n return extend(this.callSuper('toObject'), {\n opaque: this.opaque,\n matrix: this.matrix\n });\n }\n });\n\n /**\n * Returns filter instance from an object representation\n * @static\n * @param {Object} object Object to create an instance from\n * @param {function} [callback] to be invoked after filter creation\n * @return {fabric.Image.filters.Convolute} Instance of fabric.Image.filters.Convolute\n */\n fabric.Image.filters.Convolute.fromObject = fabric.Image.filters.BaseFilter.fromObject;\n\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { }),\n filters = fabric.Image.filters,\n createClass = fabric.util.createClass;\n\n /**\n * Grayscale image filter class\n * @class fabric.Image.filters.Grayscale\n * @memberOf fabric.Image.filters\n * @extends fabric.Image.filters.BaseFilter\n * @see {@link http://fabricjs.com/image-filters|ImageFilters demo}\n * @example\n * var filter = new fabric.Image.filters.Grayscale();\n * object.filters.push(filter);\n * object.applyFilters();\n */\n filters.Grayscale = createClass(filters.BaseFilter, /** @lends fabric.Image.filters.Grayscale.prototype */ {\n\n /**\n * Filter type\n * @param {String} type\n * @default\n */\n type: 'Grayscale',\n\n fragmentSource: {\n average: 'precision highp float;\\n' +\n 'uniform sampler2D uTexture;\\n' +\n 'varying vec2 vTexCoord;\\n' +\n 'void main() {\\n' +\n 'vec4 color = texture2D(uTexture, vTexCoord);\\n' +\n 'float average = (color.r + color.b + color.g) / 3.0;\\n' +\n 'gl_FragColor = vec4(average, average, average, color.a);\\n' +\n '}',\n lightness: 'precision highp float;\\n' +\n 'uniform sampler2D uTexture;\\n' +\n 'uniform int uMode;\\n' +\n 'varying vec2 vTexCoord;\\n' +\n 'void main() {\\n' +\n 'vec4 col = texture2D(uTexture, vTexCoord);\\n' +\n 'float average = (max(max(col.r, col.g),col.b) + min(min(col.r, col.g),col.b)) / 2.0;\\n' +\n 'gl_FragColor = vec4(average, average, average, col.a);\\n' +\n '}',\n luminosity: 'precision highp float;\\n' +\n 'uniform sampler2D uTexture;\\n' +\n 'uniform int uMode;\\n' +\n 'varying vec2 vTexCoord;\\n' +\n 'void main() {\\n' +\n 'vec4 col = texture2D(uTexture, vTexCoord);\\n' +\n 'float average = 0.21 * col.r + 0.72 * col.g + 0.07 * col.b;\\n' +\n 'gl_FragColor = vec4(average, average, average, col.a);\\n' +\n '}',\n },\n\n\n /**\n * Grayscale mode, between 'average', 'lightness', 'luminosity'\n * @param {String} type\n * @default\n */\n mode: 'average',\n\n mainParameter: 'mode',\n\n /**\n * Apply the Grayscale operation to a Uint8Array representing the pixels of an image.\n *\n * @param {Object} options\n * @param {ImageData} options.imageData The Uint8Array to be filtered.\n */\n applyTo2d: function(options) {\n var imageData = options.imageData,\n data = imageData.data, i,\n len = data.length, value,\n mode = this.mode;\n for (i = 0; i < len; i += 4) {\n if (mode === 'average') {\n value = (data[i] + data[i + 1] + data[i + 2]) / 3;\n }\n else if (mode === 'lightness') {\n value = (Math.min(data[i], data[i + 1], data[i + 2]) +\n Math.max(data[i], data[i + 1], data[i + 2])) / 2;\n }\n else if (mode === 'luminosity') {\n value = 0.21 * data[i] + 0.72 * data[i + 1] + 0.07 * data[i + 2];\n }\n data[i] = value;\n data[i + 1] = value;\n data[i + 2] = value;\n }\n },\n\n /**\n * Retrieves the cached shader.\n * @param {Object} options\n * @param {WebGLRenderingContext} options.context The GL context used for rendering.\n * @param {Object} options.programCache A map of compiled shader programs, keyed by filter type.\n */\n retrieveShader: function(options) {\n var cacheKey = this.type + '_' + this.mode;\n if (!options.programCache.hasOwnProperty(cacheKey)) {\n var shaderSource = this.fragmentSource[this.mode];\n options.programCache[cacheKey] = this.createProgram(options.context, shaderSource);\n }\n return options.programCache[cacheKey];\n },\n\n /**\n * Return WebGL uniform locations for this filter's shader.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {WebGLShaderProgram} program This filter's compiled shader program.\n */\n getUniformLocations: function(gl, program) {\n return {\n uMode: gl.getUniformLocation(program, 'uMode'),\n };\n },\n\n /**\n * Send data from this filter to its shader program's uniforms.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {Object} uniformLocations A map of string uniform names to WebGLUniformLocation objects\n */\n sendUniformData: function(gl, uniformLocations) {\n // default average mode.\n var mode = 1;\n gl.uniform1i(uniformLocations.uMode, mode);\n },\n\n /**\n * Grayscale filter isNeutralState implementation\n * The filter is never neutral\n * on the image\n **/\n isNeutralState: function() {\n return false;\n },\n });\n\n /**\n * Returns filter instance from an object representation\n * @static\n * @param {Object} object Object to create an instance from\n * @param {function} [callback] to be invoked after filter creation\n * @return {fabric.Image.filters.Grayscale} Instance of fabric.Image.filters.Grayscale\n */\n fabric.Image.filters.Grayscale.fromObject = fabric.Image.filters.BaseFilter.fromObject;\n\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { }),\n filters = fabric.Image.filters,\n createClass = fabric.util.createClass;\n\n /**\n * Invert filter class\n * @class fabric.Image.filters.Invert\n * @memberOf fabric.Image.filters\n * @extends fabric.Image.filters.BaseFilter\n * @see {@link http://fabricjs.com/image-filters|ImageFilters demo}\n * @example\n * var filter = new fabric.Image.filters.Invert();\n * object.filters.push(filter);\n * object.applyFilters(canvas.renderAll.bind(canvas));\n */\n filters.Invert = createClass(filters.BaseFilter, /** @lends fabric.Image.filters.Invert.prototype */ {\n\n /**\n * Filter type\n * @param {String} type\n * @default\n */\n type: 'Invert',\n\n fragmentSource: 'precision highp float;\\n' +\n 'uniform sampler2D uTexture;\\n' +\n 'uniform int uInvert;\\n' +\n 'varying vec2 vTexCoord;\\n' +\n 'void main() {\\n' +\n 'vec4 color = texture2D(uTexture, vTexCoord);\\n' +\n 'if (uInvert == 1) {\\n' +\n 'gl_FragColor = vec4(1.0 - color.r,1.0 -color.g,1.0 -color.b,color.a);\\n' +\n '} else {\\n' +\n 'gl_FragColor = color;\\n' +\n '}\\n' +\n '}',\n\n /**\n * Filter invert. if false, does nothing\n * @param {Boolean} invert\n * @default\n */\n invert: true,\n\n mainParameter: 'invert',\n\n /**\n * Apply the Invert operation to a Uint8Array representing the pixels of an image.\n *\n * @param {Object} options\n * @param {ImageData} options.imageData The Uint8Array to be filtered.\n */\n applyTo2d: function(options) {\n var imageData = options.imageData,\n data = imageData.data, i,\n len = data.length;\n for (i = 0; i < len; i += 4) {\n data[i] = 255 - data[i];\n data[i + 1] = 255 - data[i + 1];\n data[i + 2] = 255 - data[i + 2];\n }\n },\n\n /**\n * Invert filter isNeutralState implementation\n * Used only in image applyFilters to discard filters that will not have an effect\n * on the image\n * @param {Object} options\n **/\n isNeutralState: function() {\n return !this.invert;\n },\n\n /**\n * Return WebGL uniform locations for this filter's shader.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {WebGLShaderProgram} program This filter's compiled shader program.\n */\n getUniformLocations: function(gl, program) {\n return {\n uInvert: gl.getUniformLocation(program, 'uInvert'),\n };\n },\n\n /**\n * Send data from this filter to its shader program's uniforms.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {Object} uniformLocations A map of string uniform names to WebGLUniformLocation objects\n */\n sendUniformData: function(gl, uniformLocations) {\n gl.uniform1i(uniformLocations.uInvert, this.invert);\n },\n });\n\n /**\n * Returns filter instance from an object representation\n * @static\n * @param {Object} object Object to create an instance from\n * @param {function} [callback] to be invoked after filter creation\n * @return {fabric.Image.filters.Invert} Instance of fabric.Image.filters.Invert\n */\n fabric.Image.filters.Invert.fromObject = fabric.Image.filters.BaseFilter.fromObject;\n\n\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { }),\n extend = fabric.util.object.extend,\n filters = fabric.Image.filters,\n createClass = fabric.util.createClass;\n\n /**\n * Noise filter class\n * @class fabric.Image.filters.Noise\n * @memberOf fabric.Image.filters\n * @extends fabric.Image.filters.BaseFilter\n * @see {@link fabric.Image.filters.Noise#initialize} for constructor definition\n * @see {@link http://fabricjs.com/image-filters|ImageFilters demo}\n * @example\n * var filter = new fabric.Image.filters.Noise({\n * noise: 700\n * });\n * object.filters.push(filter);\n * object.applyFilters();\n * canvas.renderAll();\n */\n filters.Noise = createClass(filters.BaseFilter, /** @lends fabric.Image.filters.Noise.prototype */ {\n\n /**\n * Filter type\n * @param {String} type\n * @default\n */\n type: 'Noise',\n\n /**\n * Fragment source for the noise program\n */\n fragmentSource: 'precision highp float;\\n' +\n 'uniform sampler2D uTexture;\\n' +\n 'uniform float uStepH;\\n' +\n 'uniform float uNoise;\\n' +\n 'uniform float uSeed;\\n' +\n 'varying vec2 vTexCoord;\\n' +\n 'float rand(vec2 co, float seed, float vScale) {\\n' +\n 'return fract(sin(dot(co.xy * vScale ,vec2(12.9898 , 78.233))) * 43758.5453 * (seed + 0.01) / 2.0);\\n' +\n '}\\n' +\n 'void main() {\\n' +\n 'vec4 color = texture2D(uTexture, vTexCoord);\\n' +\n 'color.rgb += (0.5 - rand(vTexCoord, uSeed, 0.1 / uStepH)) * uNoise;\\n' +\n 'gl_FragColor = color;\\n' +\n '}',\n\n /**\n * Describe the property that is the filter parameter\n * @param {String} m\n * @default\n */\n mainParameter: 'noise',\n\n /**\n * Noise value, from\n * @param {Number} noise\n * @default\n */\n noise: 0,\n\n /**\n * Apply the Brightness operation to a Uint8ClampedArray representing the pixels of an image.\n *\n * @param {Object} options\n * @param {ImageData} options.imageData The Uint8ClampedArray to be filtered.\n */\n applyTo2d: function(options) {\n if (this.noise === 0) {\n return;\n }\n var imageData = options.imageData,\n data = imageData.data, i, len = data.length,\n noise = this.noise, rand;\n\n for (i = 0, len = data.length; i < len; i += 4) {\n\n rand = (0.5 - Math.random()) * noise;\n\n data[i] += rand;\n data[i + 1] += rand;\n data[i + 2] += rand;\n }\n },\n\n /**\n * Return WebGL uniform locations for this filter's shader.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {WebGLShaderProgram} program This filter's compiled shader program.\n */\n getUniformLocations: function(gl, program) {\n return {\n uNoise: gl.getUniformLocation(program, 'uNoise'),\n uSeed: gl.getUniformLocation(program, 'uSeed'),\n };\n },\n\n /**\n * Send data from this filter to its shader program's uniforms.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {Object} uniformLocations A map of string uniform names to WebGLUniformLocation objects\n */\n sendUniformData: function(gl, uniformLocations) {\n gl.uniform1f(uniformLocations.uNoise, this.noise / 255);\n gl.uniform1f(uniformLocations.uSeed, Math.random());\n },\n\n /**\n * Returns object representation of an instance\n * @return {Object} Object representation of an instance\n */\n toObject: function() {\n return extend(this.callSuper('toObject'), {\n noise: this.noise\n });\n }\n });\n\n /**\n * Returns filter instance from an object representation\n * @static\n * @param {Object} object Object to create an instance from\n * @param {Function} [callback] to be invoked after filter creation\n * @return {fabric.Image.filters.Noise} Instance of fabric.Image.filters.Noise\n */\n fabric.Image.filters.Noise.fromObject = fabric.Image.filters.BaseFilter.fromObject;\n\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { }),\n filters = fabric.Image.filters,\n createClass = fabric.util.createClass;\n\n /**\n * Pixelate filter class\n * @class fabric.Image.filters.Pixelate\n * @memberOf fabric.Image.filters\n * @extends fabric.Image.filters.BaseFilter\n * @see {@link fabric.Image.filters.Pixelate#initialize} for constructor definition\n * @see {@link http://fabricjs.com/image-filters|ImageFilters demo}\n * @example\n * var filter = new fabric.Image.filters.Pixelate({\n * blocksize: 8\n * });\n * object.filters.push(filter);\n * object.applyFilters();\n */\n filters.Pixelate = createClass(filters.BaseFilter, /** @lends fabric.Image.filters.Pixelate.prototype */ {\n\n /**\n * Filter type\n * @param {String} type\n * @default\n */\n type: 'Pixelate',\n\n blocksize: 4,\n\n mainParameter: 'blocksize',\n\n /**\n * Fragment source for the Pixelate program\n */\n fragmentSource: 'precision highp float;\\n' +\n 'uniform sampler2D uTexture;\\n' +\n 'uniform float uBlocksize;\\n' +\n 'uniform float uStepW;\\n' +\n 'uniform float uStepH;\\n' +\n 'varying vec2 vTexCoord;\\n' +\n 'void main() {\\n' +\n 'float blockW = uBlocksize * uStepW;\\n' +\n 'float blockH = uBlocksize * uStepW;\\n' +\n 'int posX = int(vTexCoord.x / blockW);\\n' +\n 'int posY = int(vTexCoord.y / blockH);\\n' +\n 'float fposX = float(posX);\\n' +\n 'float fposY = float(posY);\\n' +\n 'vec2 squareCoords = vec2(fposX * blockW, fposY * blockH);\\n' +\n 'vec4 color = texture2D(uTexture, squareCoords);\\n' +\n 'gl_FragColor = color;\\n' +\n '}',\n\n /**\n * Apply the Pixelate operation to a Uint8ClampedArray representing the pixels of an image.\n *\n * @param {Object} options\n * @param {ImageData} options.imageData The Uint8ClampedArray to be filtered.\n */\n applyTo2d: function(options) {\n var imageData = options.imageData,\n data = imageData.data,\n iLen = imageData.height,\n jLen = imageData.width,\n index, i, j, r, g, b, a,\n _i, _j, _iLen, _jLen;\n\n for (i = 0; i < iLen; i += this.blocksize) {\n for (j = 0; j < jLen; j += this.blocksize) {\n\n index = (i * 4) * jLen + (j * 4);\n\n r = data[index];\n g = data[index + 1];\n b = data[index + 2];\n a = data[index + 3];\n\n _iLen = Math.min(i + this.blocksize, iLen);\n _jLen = Math.min(j + this.blocksize, jLen);\n for (_i = i; _i < _iLen; _i++) {\n for (_j = j; _j < _jLen; _j++) {\n index = (_i * 4) * jLen + (_j * 4);\n data[index] = r;\n data[index + 1] = g;\n data[index + 2] = b;\n data[index + 3] = a;\n }\n }\n }\n }\n },\n\n /**\n * Indicate when the filter is not gonna apply changes to the image\n **/\n isNeutralState: function() {\n return this.blocksize === 1;\n },\n\n /**\n * Return WebGL uniform locations for this filter's shader.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {WebGLShaderProgram} program This filter's compiled shader program.\n */\n getUniformLocations: function(gl, program) {\n return {\n uBlocksize: gl.getUniformLocation(program, 'uBlocksize'),\n uStepW: gl.getUniformLocation(program, 'uStepW'),\n uStepH: gl.getUniformLocation(program, 'uStepH'),\n };\n },\n\n /**\n * Send data from this filter to its shader program's uniforms.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {Object} uniformLocations A map of string uniform names to WebGLUniformLocation objects\n */\n sendUniformData: function(gl, uniformLocations) {\n gl.uniform1f(uniformLocations.uBlocksize, this.blocksize);\n },\n });\n\n /**\n * Returns filter instance from an object representation\n * @static\n * @param {Object} object Object to create an instance from\n * @param {Function} [callback] to be invoked after filter creation\n * @return {fabric.Image.filters.Pixelate} Instance of fabric.Image.filters.Pixelate\n */\n fabric.Image.filters.Pixelate.fromObject = fabric.Image.filters.BaseFilter.fromObject;\n\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { }),\n extend = fabric.util.object.extend,\n filters = fabric.Image.filters,\n createClass = fabric.util.createClass;\n\n /**\n * Remove white filter class\n * @class fabric.Image.filters.RemoveColor\n * @memberOf fabric.Image.filters\n * @extends fabric.Image.filters.BaseFilter\n * @see {@link fabric.Image.filters.RemoveColor#initialize} for constructor definition\n * @see {@link http://fabricjs.com/image-filters|ImageFilters demo}\n * @example\n * var filter = new fabric.Image.filters.RemoveColor({\n * threshold: 0.2,\n * });\n * object.filters.push(filter);\n * object.applyFilters();\n * canvas.renderAll();\n */\n filters.RemoveColor = createClass(filters.BaseFilter, /** @lends fabric.Image.filters.RemoveColor.prototype */ {\n\n /**\n * Filter type\n * @param {String} type\n * @default\n */\n type: 'RemoveColor',\n\n /**\n * Color to remove, in any format understood by fabric.Color.\n * @param {String} type\n * @default\n */\n color: '#FFFFFF',\n\n /**\n * Fragment source for the brightness program\n */\n fragmentSource: 'precision highp float;\\n' +\n 'uniform sampler2D uTexture;\\n' +\n 'uniform vec4 uLow;\\n' +\n 'uniform vec4 uHigh;\\n' +\n 'varying vec2 vTexCoord;\\n' +\n 'void main() {\\n' +\n 'gl_FragColor = texture2D(uTexture, vTexCoord);\\n' +\n 'if(all(greaterThan(gl_FragColor.rgb,uLow.rgb)) && all(greaterThan(uHigh.rgb,gl_FragColor.rgb))) {\\n' +\n 'gl_FragColor.a = 0.0;\\n' +\n '}\\n' +\n '}',\n\n /**\n * distance to actual color, as value up or down from each r,g,b\n * between 0 and 1\n **/\n distance: 0.02,\n\n /**\n * For color to remove inside distance, use alpha channel for a smoother deletion\n * NOT IMPLEMENTED YET\n **/\n useAlpha: false,\n\n /**\n * Constructor\n * @memberOf fabric.Image.filters.RemoveWhite.prototype\n * @param {Object} [options] Options object\n * @param {Number} [options.color=#RRGGBB] Threshold value\n * @param {Number} [options.distance=10] Distance value\n */\n\n /**\n * Applies filter to canvas element\n * @param {Object} canvasEl Canvas element to apply filter to\n */\n applyTo2d: function(options) {\n var imageData = options.imageData,\n data = imageData.data, i,\n distance = this.distance * 255,\n r, g, b,\n source = new fabric.Color(this.color).getSource(),\n lowC = [\n source[0] - distance,\n source[1] - distance,\n source[2] - distance,\n ],\n highC = [\n source[0] + distance,\n source[1] + distance,\n source[2] + distance,\n ];\n\n\n for (i = 0; i < data.length; i += 4) {\n r = data[i];\n g = data[i + 1];\n b = data[i + 2];\n\n if (r > lowC[0] &&\n g > lowC[1] &&\n b > lowC[2] &&\n r < highC[0] &&\n g < highC[1] &&\n b < highC[2]) {\n data[i + 3] = 0;\n }\n }\n },\n\n /**\n * Return WebGL uniform locations for this filter's shader.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {WebGLShaderProgram} program This filter's compiled shader program.\n */\n getUniformLocations: function(gl, program) {\n return {\n uLow: gl.getUniformLocation(program, 'uLow'),\n uHigh: gl.getUniformLocation(program, 'uHigh'),\n };\n },\n\n /**\n * Send data from this filter to its shader program's uniforms.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {Object} uniformLocations A map of string uniform names to WebGLUniformLocation objects\n */\n sendUniformData: function(gl, uniformLocations) {\n var source = new fabric.Color(this.color).getSource(),\n distance = parseFloat(this.distance),\n lowC = [\n 0 + source[0] / 255 - distance,\n 0 + source[1] / 255 - distance,\n 0 + source[2] / 255 - distance,\n 1\n ],\n highC = [\n source[0] / 255 + distance,\n source[1] / 255 + distance,\n source[2] / 255 + distance,\n 1\n ];\n gl.uniform4fv(uniformLocations.uLow, lowC);\n gl.uniform4fv(uniformLocations.uHigh, highC);\n },\n\n /**\n * Returns object representation of an instance\n * @return {Object} Object representation of an instance\n */\n toObject: function() {\n return extend(this.callSuper('toObject'), {\n color: this.color,\n distance: this.distance\n });\n }\n });\n\n /**\n * Returns filter instance from an object representation\n * @static\n * @param {Object} object Object to create an instance from\n * @param {Function} [callback] to be invoked after filter creation\n * @return {fabric.Image.filters.RemoveColor} Instance of fabric.Image.filters.RemoveWhite\n */\n fabric.Image.filters.RemoveColor.fromObject = fabric.Image.filters.BaseFilter.fromObject;\n\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { }),\n filters = fabric.Image.filters,\n createClass = fabric.util.createClass;\n\n var matrices = {\n Brownie: [\n 0.59970,0.34553,-0.27082,0,0.186,\n -0.03770,0.86095,0.15059,0,-0.1449,\n 0.24113,-0.07441,0.44972,0,-0.02965,\n 0,0,0,1,0\n ],\n Vintage: [\n 0.62793,0.32021,-0.03965,0,0.03784,\n 0.02578,0.64411,0.03259,0,0.02926,\n 0.04660,-0.08512,0.52416,0,0.02023,\n 0,0,0,1,0\n ],\n Kodachrome: [\n 1.12855,-0.39673,-0.03992,0,0.24991,\n -0.16404,1.08352,-0.05498,0,0.09698,\n -0.16786,-0.56034,1.60148,0,0.13972,\n 0,0,0,1,0\n ],\n Technicolor: [\n 1.91252,-0.85453,-0.09155,0,0.04624,\n -0.30878,1.76589,-0.10601,0,-0.27589,\n -0.23110,-0.75018,1.84759,0,0.12137,\n 0,0,0,1,0\n ],\n Polaroid: [\n 1.438,-0.062,-0.062,0,0,\n -0.122,1.378,-0.122,0,0,\n -0.016,-0.016,1.483,0,0,\n 0,0,0,1,0\n ],\n Sepia: [\n 0.393, 0.769, 0.189, 0, 0,\n 0.349, 0.686, 0.168, 0, 0,\n 0.272, 0.534, 0.131, 0, 0,\n 0, 0, 0, 1, 0\n ],\n BlackWhite: [\n 1.5, 1.5, 1.5, 0, -1,\n 1.5, 1.5, 1.5, 0, -1,\n 1.5, 1.5, 1.5, 0, -1,\n 0, 0, 0, 1, 0,\n ]\n };\n\n for (var key in matrices) {\n filters[key] = createClass(filters.ColorMatrix, /** @lends fabric.Image.filters.Sepia.prototype */ {\n\n /**\n * Filter type\n * @param {String} type\n * @default\n */\n type: key,\n\n /**\n * Colormatrix for the effect\n * array of 20 floats. Numbers in positions 4, 9, 14, 19 loose meaning\n * outside the -1, 1 range.\n * @param {Array} matrix array of 20 numbers.\n * @default\n */\n matrix: matrices[key],\n\n /**\n * Lock the matrix export for this kind of static, parameter less filters.\n */\n mainParameter: false,\n /**\n * Lock the colormatrix on the color part, skipping alpha\n */\n colorsOnly: true,\n\n });\n fabric.Image.filters[key].fromObject = fabric.Image.filters.BaseFilter.fromObject;\n }\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n 'use strict';\n\n var fabric = global.fabric,\n filters = fabric.Image.filters,\n createClass = fabric.util.createClass;\n\n /**\n * Color Blend filter class\n * @class fabric.Image.filter.BlendColor\n * @memberOf fabric.Image.filters\n * @extends fabric.Image.filters.BaseFilter\n * @example\n * var filter = new fabric.Image.filters.BlendColor({\n * color: '#000',\n * mode: 'multiply'\n * });\n *\n * var filter = new fabric.Image.filters.BlendImage({\n * image: fabricImageObject,\n * mode: 'multiply',\n * alpha: 0.5\n * });\n * object.filters.push(filter);\n * object.applyFilters();\n * canvas.renderAll();\n */\n\n filters.BlendColor = createClass(filters.BaseFilter, /** @lends fabric.Image.filters.Blend.prototype */ {\n type: 'BlendColor',\n\n /**\n * Color to make the blend operation with. default to a reddish color since black or white\n * gives always strong result.\n **/\n color: '#F95C63',\n\n /**\n * Blend mode for the filter: one of multiply, add, diff, screen, subtract,\n * darken, lighten, overlay, exclusion, tint.\n **/\n mode: 'multiply',\n\n /**\n * alpha value. represent the strength of the blend color operation.\n **/\n alpha: 1,\n\n /**\n * Fragment source for the Multiply program\n */\n fragmentSource: {\n multiply: 'gl_FragColor.rgb *= uColor.rgb;\\n',\n screen: 'gl_FragColor.rgb = 1.0 - (1.0 - gl_FragColor.rgb) * (1.0 - uColor.rgb);\\n',\n add: 'gl_FragColor.rgb += uColor.rgb;\\n',\n diff: 'gl_FragColor.rgb = abs(gl_FragColor.rgb - uColor.rgb);\\n',\n subtract: 'gl_FragColor.rgb -= uColor.rgb;\\n',\n lighten: 'gl_FragColor.rgb = max(gl_FragColor.rgb, uColor.rgb);\\n',\n darken: 'gl_FragColor.rgb = min(gl_FragColor.rgb, uColor.rgb);\\n',\n exclusion: 'gl_FragColor.rgb += uColor.rgb - 2.0 * (uColor.rgb * gl_FragColor.rgb);\\n',\n overlay: 'if (uColor.r < 0.5) {\\n' +\n 'gl_FragColor.r *= 2.0 * uColor.r;\\n' +\n '} else {\\n' +\n 'gl_FragColor.r = 1.0 - 2.0 * (1.0 - gl_FragColor.r) * (1.0 - uColor.r);\\n' +\n '}\\n' +\n 'if (uColor.g < 0.5) {\\n' +\n 'gl_FragColor.g *= 2.0 * uColor.g;\\n' +\n '} else {\\n' +\n 'gl_FragColor.g = 1.0 - 2.0 * (1.0 - gl_FragColor.g) * (1.0 - uColor.g);\\n' +\n '}\\n' +\n 'if (uColor.b < 0.5) {\\n' +\n 'gl_FragColor.b *= 2.0 * uColor.b;\\n' +\n '} else {\\n' +\n 'gl_FragColor.b = 1.0 - 2.0 * (1.0 - gl_FragColor.b) * (1.0 - uColor.b);\\n' +\n '}\\n',\n tint: 'gl_FragColor.rgb *= (1.0 - uColor.a);\\n' +\n 'gl_FragColor.rgb += uColor.rgb;\\n',\n },\n\n /**\n * build the fragment source for the filters, joining the common part with\n * the specific one.\n * @param {String} mode the mode of the filter, a key of this.fragmentSource\n * @return {String} the source to be compiled\n * @private\n */\n buildSource: function(mode) {\n return 'precision highp float;\\n' +\n 'uniform sampler2D uTexture;\\n' +\n 'uniform vec4 uColor;\\n' +\n 'varying vec2 vTexCoord;\\n' +\n 'void main() {\\n' +\n 'vec4 color = texture2D(uTexture, vTexCoord);\\n' +\n 'gl_FragColor = color;\\n' +\n 'if (color.a > 0.0) {\\n' +\n this.fragmentSource[mode] +\n '}\\n' +\n '}';\n },\n\n /**\n * Retrieves the cached shader.\n * @param {Object} options\n * @param {WebGLRenderingContext} options.context The GL context used for rendering.\n * @param {Object} options.programCache A map of compiled shader programs, keyed by filter type.\n */\n retrieveShader: function(options) {\n var cacheKey = this.type + '_' + this.mode, shaderSource;\n if (!options.programCache.hasOwnProperty(cacheKey)) {\n shaderSource = this.buildSource(this.mode);\n options.programCache[cacheKey] = this.createProgram(options.context, shaderSource);\n }\n return options.programCache[cacheKey];\n },\n\n /**\n * Apply the Blend operation to a Uint8ClampedArray representing the pixels of an image.\n *\n * @param {Object} options\n * @param {ImageData} options.imageData The Uint8ClampedArray to be filtered.\n */\n applyTo2d: function(options) {\n var imageData = options.imageData,\n data = imageData.data, iLen = data.length,\n tr, tg, tb,\n r, g, b,\n source, alpha1 = 1 - this.alpha;\n\n source = new fabric.Color(this.color).getSource();\n tr = source[0] * this.alpha;\n tg = source[1] * this.alpha;\n tb = source[2] * this.alpha;\n\n for (var i = 0; i < iLen; i += 4) {\n\n r = data[i];\n g = data[i + 1];\n b = data[i + 2];\n\n switch (this.mode) {\n case 'multiply':\n data[i] = r * tr / 255;\n data[i + 1] = g * tg / 255;\n data[i + 2] = b * tb / 255;\n break;\n case 'screen':\n data[i] = 255 - (255 - r) * (255 - tr) / 255;\n data[i + 1] = 255 - (255 - g) * (255 - tg) / 255;\n data[i + 2] = 255 - (255 - b) * (255 - tb) / 255;\n break;\n case 'add':\n data[i] = r + tr;\n data[i + 1] = g + tg;\n data[i + 2] = b + tb;\n break;\n case 'diff':\n case 'difference':\n data[i] = Math.abs(r - tr);\n data[i + 1] = Math.abs(g - tg);\n data[i + 2] = Math.abs(b - tb);\n break;\n case 'subtract':\n data[i] = r - tr;\n data[i + 1] = g - tg;\n data[i + 2] = b - tb;\n break;\n case 'darken':\n data[i] = Math.min(r, tr);\n data[i + 1] = Math.min(g, tg);\n data[i + 2] = Math.min(b, tb);\n break;\n case 'lighten':\n data[i] = Math.max(r, tr);\n data[i + 1] = Math.max(g, tg);\n data[i + 2] = Math.max(b, tb);\n break;\n case 'overlay':\n data[i] = tr < 128 ? (2 * r * tr / 255) : (255 - 2 * (255 - r) * (255 - tr) / 255);\n data[i + 1] = tg < 128 ? (2 * g * tg / 255) : (255 - 2 * (255 - g) * (255 - tg) / 255);\n data[i + 2] = tb < 128 ? (2 * b * tb / 255) : (255 - 2 * (255 - b) * (255 - tb) / 255);\n break;\n case 'exclusion':\n data[i] = tr + r - ((2 * tr * r) / 255);\n data[i + 1] = tg + g - ((2 * tg * g) / 255);\n data[i + 2] = tb + b - ((2 * tb * b) / 255);\n break;\n case 'tint':\n data[i] = tr + r * alpha1;\n data[i + 1] = tg + g * alpha1;\n data[i + 2] = tb + b * alpha1;\n }\n }\n },\n\n /**\n * Return WebGL uniform locations for this filter's shader.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {WebGLShaderProgram} program This filter's compiled shader program.\n */\n getUniformLocations: function(gl, program) {\n return {\n uColor: gl.getUniformLocation(program, 'uColor'),\n };\n },\n\n /**\n * Send data from this filter to its shader program's uniforms.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {Object} uniformLocations A map of string uniform names to WebGLUniformLocation objects\n */\n sendUniformData: function(gl, uniformLocations) {\n var source = new fabric.Color(this.color).getSource();\n source[0] = this.alpha * source[0] / 255;\n source[1] = this.alpha * source[1] / 255;\n source[2] = this.alpha * source[2] / 255;\n source[3] = this.alpha;\n gl.uniform4fv(uniformLocations.uColor, source);\n },\n\n /**\n * Returns object representation of an instance\n * @return {Object} Object representation of an instance\n */\n toObject: function() {\n return {\n type: this.type,\n color: this.color,\n mode: this.mode,\n alpha: this.alpha\n };\n }\n });\n\n /**\n * Returns filter instance from an object representation\n * @static\n * @param {Object} object Object to create an instance from\n * @param {function} [callback] to be invoked after filter creation\n * @return {fabric.Image.filters.BlendColor} Instance of fabric.Image.filters.BlendColor\n */\n fabric.Image.filters.BlendColor.fromObject = fabric.Image.filters.BaseFilter.fromObject;\n\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n 'use strict';\n\n var fabric = global.fabric,\n filters = fabric.Image.filters,\n createClass = fabric.util.createClass;\n\n /**\n * Image Blend filter class\n * @class fabric.Image.filter.BlendImage\n * @memberOf fabric.Image.filters\n * @extends fabric.Image.filters.BaseFilter\n * @example\n * var filter = new fabric.Image.filters.BlendColor({\n * color: '#000',\n * mode: 'multiply'\n * });\n *\n * var filter = new fabric.Image.filters.BlendImage({\n * image: fabricImageObject,\n * mode: 'multiply',\n * alpha: 0.5\n * });\n * object.filters.push(filter);\n * object.applyFilters();\n * canvas.renderAll();\n */\n\n filters.BlendImage = createClass(filters.BaseFilter, /** @lends fabric.Image.filters.BlendImage.prototype */ {\n type: 'BlendImage',\n\n /**\n * Color to make the blend operation with. default to a reddish color since black or white\n * gives always strong result.\n **/\n image: null,\n\n /**\n * Blend mode for the filter: one of multiply, add, diff, screen, subtract,\n * darken, lighten, overlay, exclusion, tint.\n **/\n mode: 'multiply',\n\n /**\n * alpha value. represent the strength of the blend image operation.\n * not implemented.\n **/\n alpha: 1,\n\n vertexSource: 'attribute vec2 aPosition;\\n' +\n 'varying vec2 vTexCoord;\\n' +\n 'varying vec2 vTexCoord2;\\n' +\n 'uniform mat3 uTransformMatrix;\\n' +\n 'void main() {\\n' +\n 'vTexCoord = aPosition;\\n' +\n 'vTexCoord2 = (uTransformMatrix * vec3(aPosition, 1.0)).xy;\\n' +\n 'gl_Position = vec4(aPosition * 2.0 - 1.0, 0.0, 1.0);\\n' +\n '}',\n\n /**\n * Fragment source for the Multiply program\n */\n fragmentSource: {\n multiply: 'precision highp float;\\n' +\n 'uniform sampler2D uTexture;\\n' +\n 'uniform sampler2D uImage;\\n' +\n 'uniform vec4 uColor;\\n' +\n 'varying vec2 vTexCoord;\\n' +\n 'varying vec2 vTexCoord2;\\n' +\n 'void main() {\\n' +\n 'vec4 color = texture2D(uTexture, vTexCoord);\\n' +\n 'vec4 color2 = texture2D(uImage, vTexCoord2);\\n' +\n 'color.rgba *= color2.rgba;\\n' +\n 'gl_FragColor = color;\\n' +\n '}',\n mask: 'precision highp float;\\n' +\n 'uniform sampler2D uTexture;\\n' +\n 'uniform sampler2D uImage;\\n' +\n 'uniform vec4 uColor;\\n' +\n 'varying vec2 vTexCoord;\\n' +\n 'varying vec2 vTexCoord2;\\n' +\n 'void main() {\\n' +\n 'vec4 color = texture2D(uTexture, vTexCoord);\\n' +\n 'vec4 color2 = texture2D(uImage, vTexCoord2);\\n' +\n 'color.a = color2.a;\\n' +\n 'gl_FragColor = color;\\n' +\n '}',\n },\n\n /**\n * Retrieves the cached shader.\n * @param {Object} options\n * @param {WebGLRenderingContext} options.context The GL context used for rendering.\n * @param {Object} options.programCache A map of compiled shader programs, keyed by filter type.\n */\n retrieveShader: function(options) {\n var cacheKey = this.type + '_' + this.mode;\n var shaderSource = this.fragmentSource[this.mode];\n if (!options.programCache.hasOwnProperty(cacheKey)) {\n options.programCache[cacheKey] = this.createProgram(options.context, shaderSource);\n }\n return options.programCache[cacheKey];\n },\n\n applyToWebGL: function(options) {\n // load texture to blend.\n var gl = options.context,\n texture = this.createTexture(options.filterBackend, this.image);\n this.bindAdditionalTexture(gl, texture, gl.TEXTURE1);\n this.callSuper('applyToWebGL', options);\n this.unbindAdditionalTexture(gl, gl.TEXTURE1);\n },\n\n createTexture: function(backend, image) {\n return backend.getCachedTexture(image.cacheKey, image._element);\n },\n\n /**\n * Calculate a transformMatrix to adapt the image to blend over\n * @param {Object} options\n * @param {WebGLRenderingContext} options.context The GL context used for rendering.\n * @param {Object} options.programCache A map of compiled shader programs, keyed by filter type.\n */\n calculateMatrix: function() {\n var image = this.image,\n width = image._element.width,\n height = image._element.height;\n return [\n 1 / image.scaleX, 0, 0,\n 0, 1 / image.scaleY, 0,\n -image.left / width, -image.top / height, 1\n ];\n },\n\n /**\n * Apply the Blend operation to a Uint8ClampedArray representing the pixels of an image.\n *\n * @param {Object} options\n * @param {ImageData} options.imageData The Uint8ClampedArray to be filtered.\n */\n applyTo2d: function(options) {\n var imageData = options.imageData,\n resources = options.filterBackend.resources,\n data = imageData.data, iLen = data.length,\n width = imageData.width,\n height = imageData.height,\n tr, tg, tb, ta,\n r, g, b, a,\n canvas1, context, image = this.image, blendData;\n\n if (!resources.blendImage) {\n resources.blendImage = fabric.util.createCanvasElement();\n }\n canvas1 = resources.blendImage;\n context = canvas1.getContext('2d');\n if (canvas1.width !== width || canvas1.height !== height) {\n canvas1.width = width;\n canvas1.height = height;\n }\n else {\n context.clearRect(0, 0, width, height);\n }\n context.setTransform(image.scaleX, 0, 0, image.scaleY, image.left, image.top);\n context.drawImage(image._element, 0, 0, width, height);\n blendData = context.getImageData(0, 0, width, height).data;\n for (var i = 0; i < iLen; i += 4) {\n\n r = data[i];\n g = data[i + 1];\n b = data[i + 2];\n a = data[i + 3];\n\n tr = blendData[i];\n tg = blendData[i + 1];\n tb = blendData[i + 2];\n ta = blendData[i + 3];\n\n switch (this.mode) {\n case 'multiply':\n data[i] = r * tr / 255;\n data[i + 1] = g * tg / 255;\n data[i + 2] = b * tb / 255;\n data[i + 3] = a * ta / 255;\n break;\n case 'mask':\n data[i + 3] = ta;\n break;\n }\n }\n },\n\n /**\n * Return WebGL uniform locations for this filter's shader.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {WebGLShaderProgram} program This filter's compiled shader program.\n */\n getUniformLocations: function(gl, program) {\n return {\n uTransformMatrix: gl.getUniformLocation(program, 'uTransformMatrix'),\n uImage: gl.getUniformLocation(program, 'uImage'),\n };\n },\n\n /**\n * Send data from this filter to its shader program's uniforms.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {Object} uniformLocations A map of string uniform names to WebGLUniformLocation objects\n */\n sendUniformData: function(gl, uniformLocations) {\n var matrix = this.calculateMatrix();\n gl.uniform1i(uniformLocations.uImage, 1); // texture unit 1.\n gl.uniformMatrix3fv(uniformLocations.uTransformMatrix, false, matrix);\n },\n\n /**\n * Returns object representation of an instance\n * @return {Object} Object representation of an instance\n */\n toObject: function() {\n return {\n type: this.type,\n image: this.image && this.image.toObject(),\n mode: this.mode,\n alpha: this.alpha\n };\n }\n });\n\n /**\n * Returns filter instance from an object representation\n * @static\n * @param {Object} object Object to create an instance from\n * @param {function} callback to be invoked after filter creation\n * @return {fabric.Image.filters.BlendImage} Instance of fabric.Image.filters.BlendImage\n */\n fabric.Image.filters.BlendImage.fromObject = function(object, callback) {\n fabric.Image.fromObject(object.image, function(image) {\n var options = fabric.util.object.clone(object);\n options.image = image;\n callback(new fabric.Image.filters.BlendImage(options));\n });\n };\n\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { }), pow = Math.pow, floor = Math.floor,\n sqrt = Math.sqrt, abs = Math.abs, round = Math.round, sin = Math.sin,\n ceil = Math.ceil,\n filters = fabric.Image.filters,\n createClass = fabric.util.createClass;\n\n /**\n * Resize image filter class\n * @class fabric.Image.filters.Resize\n * @memberOf fabric.Image.filters\n * @extends fabric.Image.filters.BaseFilter\n * @see {@link http://fabricjs.com/image-filters|ImageFilters demo}\n * @example\n * var filter = new fabric.Image.filters.Resize();\n * object.filters.push(filter);\n * object.applyFilters(canvas.renderAll.bind(canvas));\n */\n filters.Resize = createClass(filters.BaseFilter, /** @lends fabric.Image.filters.Resize.prototype */ {\n\n /**\n * Filter type\n * @param {String} type\n * @default\n */\n type: 'Resize',\n\n /**\n * Resize type\n * for webgl resizeType is just lanczos, for canvas2d can be:\n * bilinear, hermite, sliceHack, lanczos.\n * @param {String} resizeType\n * @default\n */\n resizeType: 'hermite',\n\n /**\n * Scale factor for resizing, x axis\n * @param {Number} scaleX\n * @default\n */\n scaleX: 1,\n\n /**\n * Scale factor for resizing, y axis\n * @param {Number} scaleY\n * @default\n */\n scaleY: 1,\n\n /**\n * LanczosLobes parameter for lanczos filter, valid for resizeType lanczos\n * @param {Number} lanczosLobes\n * @default\n */\n lanczosLobes: 3,\n\n\n /**\n * Return WebGL uniform locations for this filter's shader.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {WebGLShaderProgram} program This filter's compiled shader program.\n */\n getUniformLocations: function(gl, program) {\n return {\n uDelta: gl.getUniformLocation(program, 'uDelta'),\n uTaps: gl.getUniformLocation(program, 'uTaps'),\n };\n },\n\n /**\n * Send data from this filter to its shader program's uniforms.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {Object} uniformLocations A map of string uniform names to WebGLUniformLocation objects\n */\n sendUniformData: function(gl, uniformLocations) {\n gl.uniform2fv(uniformLocations.uDelta, this.horizontal ? [1 / this.width, 0] : [0, 1 / this.height]);\n gl.uniform1fv(uniformLocations.uTaps, this.taps);\n },\n\n /**\n * Retrieves the cached shader.\n * @param {Object} options\n * @param {WebGLRenderingContext} options.context The GL context used for rendering.\n * @param {Object} options.programCache A map of compiled shader programs, keyed by filter type.\n */\n retrieveShader: function(options) {\n var filterWindow = this.getFilterWindow(), cacheKey = this.type + '_' + filterWindow;\n if (!options.programCache.hasOwnProperty(cacheKey)) {\n var fragmentShader = this.generateShader(filterWindow);\n options.programCache[cacheKey] = this.createProgram(options.context, fragmentShader);\n }\n return options.programCache[cacheKey];\n },\n\n getFilterWindow: function() {\n var scale = this.tempScale;\n return Math.ceil(this.lanczosLobes / scale);\n },\n\n getTaps: function() {\n var lobeFunction = this.lanczosCreate(this.lanczosLobes), scale = this.tempScale,\n filterWindow = this.getFilterWindow(), taps = new Array(filterWindow);\n for (var i = 1; i <= filterWindow; i++) {\n taps[i - 1] = lobeFunction(i * scale);\n }\n return taps;\n },\n\n /**\n * Generate vertex and shader sources from the necessary steps numbers\n * @param {Number} filterWindow\n */\n generateShader: function(filterWindow) {\n var offsets = new Array(filterWindow),\n fragmentShader = this.fragmentSourceTOP, filterWindow;\n\n for (var i = 1; i <= filterWindow; i++) {\n offsets[i - 1] = i + '.0 * uDelta';\n }\n\n fragmentShader += 'uniform float uTaps[' + filterWindow + '];\\n';\n fragmentShader += 'void main() {\\n';\n fragmentShader += ' vec4 color = texture2D(uTexture, vTexCoord);\\n';\n fragmentShader += ' float sum = 1.0;\\n';\n\n offsets.forEach(function(offset, i) {\n fragmentShader += ' color += texture2D(uTexture, vTexCoord + ' + offset + ') * uTaps[' + i + '];\\n';\n fragmentShader += ' color += texture2D(uTexture, vTexCoord - ' + offset + ') * uTaps[' + i + '];\\n';\n fragmentShader += ' sum += 2.0 * uTaps[' + i + '];\\n';\n });\n fragmentShader += ' gl_FragColor = color / sum;\\n';\n fragmentShader += '}';\n return fragmentShader;\n },\n\n fragmentSourceTOP: 'precision highp float;\\n' +\n 'uniform sampler2D uTexture;\\n' +\n 'uniform vec2 uDelta;\\n' +\n 'varying vec2 vTexCoord;\\n',\n\n /**\n * Apply the resize filter to the image\n * Determines whether to use WebGL or Canvas2D based on the options.webgl flag.\n *\n * @param {Object} options\n * @param {Number} options.passes The number of filters remaining to be executed\n * @param {Boolean} options.webgl Whether to use webgl to render the filter.\n * @param {WebGLTexture} options.sourceTexture The texture setup as the source to be filtered.\n * @param {WebGLTexture} options.targetTexture The texture where filtered output should be drawn.\n * @param {WebGLRenderingContext} options.context The GL context used for rendering.\n * @param {Object} options.programCache A map of compiled shader programs, keyed by filter type.\n */\n applyTo: function(options) {\n if (options.webgl) {\n options.passes++;\n this.width = options.sourceWidth;\n this.horizontal = true;\n this.dW = Math.round(this.width * this.scaleX);\n this.dH = options.sourceHeight;\n this.tempScale = this.dW / this.width;\n this.taps = this.getTaps();\n options.destinationWidth = this.dW;\n this._setupFrameBuffer(options);\n this.applyToWebGL(options);\n this._swapTextures(options);\n options.sourceWidth = options.destinationWidth;\n\n this.height = options.sourceHeight;\n this.horizontal = false;\n this.dH = Math.round(this.height * this.scaleY);\n this.tempScale = this.dH / this.height;\n this.taps = this.getTaps();\n options.destinationHeight = this.dH;\n this._setupFrameBuffer(options);\n this.applyToWebGL(options);\n this._swapTextures(options);\n options.sourceHeight = options.destinationHeight;\n }\n else {\n this.applyTo2d(options);\n }\n },\n\n isNeutralState: function() {\n return this.scaleX === 1 && this.scaleY === 1;\n },\n\n lanczosCreate: function(lobes) {\n return function(x) {\n if (x >= lobes || x <= -lobes) {\n return 0.0;\n }\n if (x < 1.19209290E-07 && x > -1.19209290E-07) {\n return 1.0;\n }\n x *= Math.PI;\n var xx = x / lobes;\n return (sin(x) / x) * sin(xx) / xx;\n };\n },\n\n /**\n * Applies filter to canvas element\n * @memberOf fabric.Image.filters.Resize.prototype\n * @param {Object} canvasEl Canvas element to apply filter to\n * @param {Number} scaleX\n * @param {Number} scaleY\n */\n applyTo2d: function(options) {\n var imageData = options.imageData,\n scaleX = this.scaleX,\n scaleY = this.scaleY;\n\n this.rcpScaleX = 1 / scaleX;\n this.rcpScaleY = 1 / scaleY;\n\n var oW = imageData.width, oH = imageData.height,\n dW = round(oW * scaleX), dH = round(oH * scaleY),\n newData;\n\n if (this.resizeType === 'sliceHack') {\n newData = this.sliceByTwo(options, oW, oH, dW, dH);\n }\n else if (this.resizeType === 'hermite') {\n newData = this.hermiteFastResize(options, oW, oH, dW, dH);\n }\n else if (this.resizeType === 'bilinear') {\n newData = this.bilinearFiltering(options, oW, oH, dW, dH);\n }\n else if (this.resizeType === 'lanczos') {\n newData = this.lanczosResize(options, oW, oH, dW, dH);\n }\n options.imageData = newData;\n },\n\n /**\n * Filter sliceByTwo\n * @param {Object} canvasEl Canvas element to apply filter to\n * @param {Number} oW Original Width\n * @param {Number} oH Original Height\n * @param {Number} dW Destination Width\n * @param {Number} dH Destination Height\n * @returns {ImageData}\n */\n sliceByTwo: function(options, oW, oH, dW, dH) {\n var imageData = options.imageData,\n mult = 0.5, doneW = false, doneH = false, stepW = oW * mult,\n stepH = oH * mult, resources = fabric.filterBackend.resources,\n tmpCanvas, ctx, sX = 0, sY = 0, dX = oW, dY = 0;\n if (!resources.sliceByTwo) {\n resources.sliceByTwo = document.createElement('canvas');\n }\n tmpCanvas = resources.sliceByTwo;\n if (tmpCanvas.width < oW * 1.5 || tmpCanvas.height < oH) {\n tmpCanvas.width = oW * 1.5;\n tmpCanvas.height = oH;\n }\n ctx = tmpCanvas.getContext('2d');\n ctx.clearRect(0, 0, oW * 1.5, oH);\n ctx.putImageData(imageData, 0, 0);\n\n dW = floor(dW);\n dH = floor(dH);\n\n while (!doneW || !doneH) {\n oW = stepW;\n oH = stepH;\n if (dW < floor(stepW * mult)) {\n stepW = floor(stepW * mult);\n }\n else {\n stepW = dW;\n doneW = true;\n }\n if (dH < floor(stepH * mult)) {\n stepH = floor(stepH * mult);\n }\n else {\n stepH = dH;\n doneH = true;\n }\n ctx.drawImage(tmpCanvas, sX, sY, oW, oH, dX, dY, stepW, stepH);\n sX = dX;\n sY = dY;\n dY += stepH;\n }\n return ctx.getImageData(sX, sY, dW, dH);\n },\n\n /**\n * Filter lanczosResize\n * @param {Object} canvasEl Canvas element to apply filter to\n * @param {Number} oW Original Width\n * @param {Number} oH Original Height\n * @param {Number} dW Destination Width\n * @param {Number} dH Destination Height\n * @returns {ImageData}\n */\n lanczosResize: function(options, oW, oH, dW, dH) {\n\n function process(u) {\n var v, i, weight, idx, a, red, green,\n blue, alpha, fX, fY;\n center.x = (u + 0.5) * ratioX;\n icenter.x = floor(center.x);\n for (v = 0; v < dH; v++) {\n center.y = (v + 0.5) * ratioY;\n icenter.y = floor(center.y);\n a = 0; red = 0; green = 0; blue = 0; alpha = 0;\n for (i = icenter.x - range2X; i <= icenter.x + range2X; i++) {\n if (i < 0 || i >= oW) {\n continue;\n }\n fX = floor(1000 * abs(i - center.x));\n if (!cacheLanc[fX]) {\n cacheLanc[fX] = { };\n }\n for (var j = icenter.y - range2Y; j <= icenter.y + range2Y; j++) {\n if (j < 0 || j >= oH) {\n continue;\n }\n fY = floor(1000 * abs(j - center.y));\n if (!cacheLanc[fX][fY]) {\n cacheLanc[fX][fY] = lanczos(sqrt(pow(fX * rcpRatioX, 2) + pow(fY * rcpRatioY, 2)) / 1000);\n }\n weight = cacheLanc[fX][fY];\n if (weight > 0) {\n idx = (j * oW + i) * 4;\n a += weight;\n red += weight * srcData[idx];\n green += weight * srcData[idx + 1];\n blue += weight * srcData[idx + 2];\n alpha += weight * srcData[idx + 3];\n }\n }\n }\n idx = (v * dW + u) * 4;\n destData[idx] = red / a;\n destData[idx + 1] = green / a;\n destData[idx + 2] = blue / a;\n destData[idx + 3] = alpha / a;\n }\n\n if (++u < dW) {\n return process(u);\n }\n else {\n return destImg;\n }\n }\n\n var srcData = options.imageData.data,\n destImg = options.ctx.createImageData(dW, dH),\n destData = destImg.data,\n lanczos = this.lanczosCreate(this.lanczosLobes),\n ratioX = this.rcpScaleX, ratioY = this.rcpScaleY,\n rcpRatioX = 2 / this.rcpScaleX, rcpRatioY = 2 / this.rcpScaleY,\n range2X = ceil(ratioX * this.lanczosLobes / 2),\n range2Y = ceil(ratioY * this.lanczosLobes / 2),\n cacheLanc = { }, center = { }, icenter = { };\n\n return process(0);\n },\n\n /**\n * bilinearFiltering\n * @param {Object} canvasEl Canvas element to apply filter to\n * @param {Number} oW Original Width\n * @param {Number} oH Original Height\n * @param {Number} dW Destination Width\n * @param {Number} dH Destination Height\n * @returns {ImageData}\n */\n bilinearFiltering: function(options, oW, oH, dW, dH) {\n var a, b, c, d, x, y, i, j, xDiff, yDiff, chnl,\n color, offset = 0, origPix, ratioX = this.rcpScaleX,\n ratioY = this.rcpScaleY,\n w4 = 4 * (oW - 1), img = options.imageData,\n pixels = img.data, destImage = options.ctx.createImageData(dW, dH),\n destPixels = destImage.data;\n for (i = 0; i < dH; i++) {\n for (j = 0; j < dW; j++) {\n x = floor(ratioX * j);\n y = floor(ratioY * i);\n xDiff = ratioX * j - x;\n yDiff = ratioY * i - y;\n origPix = 4 * (y * oW + x);\n\n for (chnl = 0; chnl < 4; chnl++) {\n a = pixels[origPix + chnl];\n b = pixels[origPix + 4 + chnl];\n c = pixels[origPix + w4 + chnl];\n d = pixels[origPix + w4 + 4 + chnl];\n color = a * (1 - xDiff) * (1 - yDiff) + b * xDiff * (1 - yDiff) +\n c * yDiff * (1 - xDiff) + d * xDiff * yDiff;\n destPixels[offset++] = color;\n }\n }\n }\n return destImage;\n },\n\n /**\n * hermiteFastResize\n * @param {Object} canvasEl Canvas element to apply filter to\n * @param {Number} oW Original Width\n * @param {Number} oH Original Height\n * @param {Number} dW Destination Width\n * @param {Number} dH Destination Height\n * @returns {ImageData}\n */\n hermiteFastResize: function(options, oW, oH, dW, dH) {\n var ratioW = this.rcpScaleX, ratioH = this.rcpScaleY,\n ratioWHalf = ceil(ratioW / 2),\n ratioHHalf = ceil(ratioH / 2),\n img = options.imageData, data = img.data,\n img2 = options.ctx.createImageData(dW, dH), data2 = img2.data;\n for (var j = 0; j < dH; j++) {\n for (var i = 0; i < dW; i++) {\n var x2 = (i + j * dW) * 4, weight = 0, weights = 0, weightsAlpha = 0,\n gxR = 0, gxG = 0, gxB = 0, gxA = 0, centerY = (j + 0.5) * ratioH;\n for (var yy = floor(j * ratioH); yy < (j + 1) * ratioH; yy++) {\n var dy = abs(centerY - (yy + 0.5)) / ratioHHalf,\n centerX = (i + 0.5) * ratioW, w0 = dy * dy;\n for (var xx = floor(i * ratioW); xx < (i + 1) * ratioW; xx++) {\n var dx = abs(centerX - (xx + 0.5)) / ratioWHalf,\n w = sqrt(w0 + dx * dx);\n /* eslint-disable max-depth */\n if (w > 1 && w < -1) {\n continue;\n }\n //hermite filter\n weight = 2 * w * w * w - 3 * w * w + 1;\n if (weight > 0) {\n dx = 4 * (xx + yy * oW);\n //alpha\n gxA += weight * data[dx + 3];\n weightsAlpha += weight;\n //colors\n if (data[dx + 3] < 255) {\n weight = weight * data[dx + 3] / 250;\n }\n gxR += weight * data[dx];\n gxG += weight * data[dx + 1];\n gxB += weight * data[dx + 2];\n weights += weight;\n }\n /* eslint-enable max-depth */\n }\n }\n data2[x2] = gxR / weights;\n data2[x2 + 1] = gxG / weights;\n data2[x2 + 2] = gxB / weights;\n data2[x2 + 3] = gxA / weightsAlpha;\n }\n }\n return img2;\n },\n\n /**\n * Returns object representation of an instance\n * @return {Object} Object representation of an instance\n */\n toObject: function() {\n return {\n type: this.type,\n scaleX: this.scaleX,\n scaleY: this.scaleY,\n resizeType: this.resizeType,\n lanczosLobes: this.lanczosLobes\n };\n }\n });\n\n /**\n * Returns filter instance from an object representation\n * @static\n * @param {Object} object Object to create an instance from\n * @param {Function} [callback] to be invoked after filter creation\n * @return {fabric.Image.filters.Resize} Instance of fabric.Image.filters.Resize\n */\n fabric.Image.filters.Resize.fromObject = fabric.Image.filters.BaseFilter.fromObject;\n\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { }),\n filters = fabric.Image.filters,\n createClass = fabric.util.createClass;\n\n /**\n * Contrast filter class\n * @class fabric.Image.filters.Contrast\n * @memberOf fabric.Image.filters\n * @extends fabric.Image.filters.BaseFilter\n * @see {@link fabric.Image.filters.Contrast#initialize} for constructor definition\n * @see {@link http://fabricjs.com/image-filters|ImageFilters demo}\n * @example\n * var filter = new fabric.Image.filters.Contrast({\n * contrast: 0.25\n * });\n * object.filters.push(filter);\n * object.applyFilters();\n */\n filters.Contrast = createClass(filters.BaseFilter, /** @lends fabric.Image.filters.Contrast.prototype */ {\n\n /**\n * Filter type\n * @param {String} type\n * @default\n */\n type: 'Contrast',\n\n fragmentSource: 'precision highp float;\\n' +\n 'uniform sampler2D uTexture;\\n' +\n 'uniform float uContrast;\\n' +\n 'varying vec2 vTexCoord;\\n' +\n 'void main() {\\n' +\n 'vec4 color = texture2D(uTexture, vTexCoord);\\n' +\n 'float contrastF = 1.015 * (uContrast + 1.0) / (1.0 * (1.015 - uContrast));\\n' +\n 'color.rgb = contrastF * (color.rgb - 0.5) + 0.5;\\n' +\n 'gl_FragColor = color;\\n' +\n '}',\n\n /**\n * contrast value, range from -1 to 1.\n * @param {Number} contrast\n * @default 0\n */\n contrast: 0,\n\n mainParameter: 'contrast',\n\n /**\n * Constructor\n * @memberOf fabric.Image.filters.Contrast.prototype\n * @param {Object} [options] Options object\n * @param {Number} [options.contrast=0] Value to contrast the image up (-1...1)\n */\n\n /**\n * Apply the Contrast operation to a Uint8Array representing the pixels of an image.\n *\n * @param {Object} options\n * @param {ImageData} options.imageData The Uint8Array to be filtered.\n */\n applyTo2d: function(options) {\n if (this.contrast === 0) {\n return;\n }\n var imageData = options.imageData, i, len,\n data = imageData.data, len = data.length,\n contrast = Math.floor(this.contrast * 255),\n contrastF = 259 * (contrast + 255) / (255 * (259 - contrast));\n\n for (i = 0; i < len; i += 4) {\n data[i] = contrastF * (data[i] - 128) + 128;\n data[i + 1] = contrastF * (data[i + 1] - 128) + 128;\n data[i + 2] = contrastF * (data[i + 2] - 128) + 128;\n }\n },\n\n /**\n * Return WebGL uniform locations for this filter's shader.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {WebGLShaderProgram} program This filter's compiled shader program.\n */\n getUniformLocations: function(gl, program) {\n return {\n uContrast: gl.getUniformLocation(program, 'uContrast'),\n };\n },\n\n /**\n * Send data from this filter to its shader program's uniforms.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {Object} uniformLocations A map of string uniform names to WebGLUniformLocation objects\n */\n sendUniformData: function(gl, uniformLocations) {\n gl.uniform1f(uniformLocations.uContrast, this.contrast);\n },\n });\n\n /**\n * Returns filter instance from an object representation\n * @static\n * @param {Object} object Object to create an instance from\n * @param {function} [callback] to be invoked after filter creation\n * @return {fabric.Image.filters.Contrast} Instance of fabric.Image.filters.Contrast\n */\n fabric.Image.filters.Contrast.fromObject = fabric.Image.filters.BaseFilter.fromObject;\n\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { }),\n filters = fabric.Image.filters,\n createClass = fabric.util.createClass;\n\n /**\n * Saturate filter class\n * @class fabric.Image.filters.Saturation\n * @memberOf fabric.Image.filters\n * @extends fabric.Image.filters.BaseFilter\n * @see {@link fabric.Image.filters.Saturation#initialize} for constructor definition\n * @see {@link http://fabricjs.com/image-filters|ImageFilters demo}\n * @example\n * var filter = new fabric.Image.filters.Saturation({\n * saturation: 100\n * });\n * object.filters.push(filter);\n * object.applyFilters();\n */\n filters.Saturation = createClass(filters.BaseFilter, /** @lends fabric.Image.filters.Saturation.prototype */ {\n\n /**\n * Filter type\n * @param {String} type\n * @default\n */\n type: 'Saturation',\n\n fragmentSource: 'precision highp float;\\n' +\n 'uniform sampler2D uTexture;\\n' +\n 'uniform float uSaturation;\\n' +\n 'varying vec2 vTexCoord;\\n' +\n 'void main() {\\n' +\n 'vec4 color = texture2D(uTexture, vTexCoord);\\n' +\n 'float rgMax = max(color.r, color.g);\\n' +\n 'float rgbMax = max(rgMax, color.b);\\n' +\n 'color.r += rgbMax != color.r ? (rgbMax - color.r) * uSaturation : 0.00;\\n' +\n 'color.g += rgbMax != color.g ? (rgbMax - color.g) * uSaturation : 0.00;\\n' +\n 'color.b += rgbMax != color.b ? (rgbMax - color.b) * uSaturation : 0.00;\\n' +\n 'gl_FragColor = color;\\n' +\n '}',\n\n saturation: 0,\n\n mainParameter: 'saturation',\n\n /**\n * Constructor\n * @memberOf fabric.Image.filters.Saturate.prototype\n * @param {Object} [options] Options object\n * @param {Number} [options.saturate=0] Value to saturate the image (-1...1)\n */\n\n /**\n * Apply the Saturation operation to a Uint8ClampedArray representing the pixels of an image.\n *\n * @param {Object} options\n * @param {ImageData} options.imageData The Uint8ClampedArray to be filtered.\n */\n applyTo2d: function(options) {\n if (this.saturation === 0) {\n return;\n }\n var imageData = options.imageData,\n data = imageData.data, len = data.length,\n adjust = -this.saturation, i, max;\n\n for (i = 0; i < len; i += 4) {\n max = Math.max(data[i], data[i + 1], data[i + 2]);\n data[i] += max !== data[i] ? (max - data[i]) * adjust : 0;\n data[i + 1] += max !== data[i + 1] ? (max - data[i + 1]) * adjust : 0;\n data[i + 2] += max !== data[i + 2] ? (max - data[i + 2]) * adjust : 0;\n }\n },\n\n /**\n * Return WebGL uniform locations for this filter's shader.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {WebGLShaderProgram} program This filter's compiled shader program.\n */\n getUniformLocations: function(gl, program) {\n return {\n uSaturation: gl.getUniformLocation(program, 'uSaturation'),\n };\n },\n\n /**\n * Send data from this filter to its shader program's uniforms.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {Object} uniformLocations A map of string uniform names to WebGLUniformLocation objects\n */\n sendUniformData: function(gl, uniformLocations) {\n gl.uniform1f(uniformLocations.uSaturation, -this.saturation);\n },\n });\n\n /**\n * Returns filter instance from an object representation\n * @static\n * @param {Object} object Object to create an instance from\n * @param {Function} [callback] to be invoked after filter creation\n * @return {fabric.Image.filters.Saturation} Instance of fabric.Image.filters.Saturate\n */\n fabric.Image.filters.Saturation.fromObject = fabric.Image.filters.BaseFilter.fromObject;\n\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { }),\n filters = fabric.Image.filters,\n createClass = fabric.util.createClass;\n\n /**\n * Blur filter class\n * @class fabric.Image.filters.Blur\n * @memberOf fabric.Image.filters\n * @extends fabric.Image.filters.BaseFilter\n * @see {@link fabric.Image.filters.Blur#initialize} for constructor definition\n * @see {@link http://fabricjs.com/image-filters|ImageFilters demo}\n * @example\n * var filter = new fabric.Image.filters.Blur({\n * blur: 0.5\n * });\n * object.filters.push(filter);\n * object.applyFilters();\n * canvas.renderAll();\n */\n filters.Blur = createClass(filters.BaseFilter, /** @lends fabric.Image.filters.Blur.prototype */ {\n\n type: 'Blur',\n\n /*\n'gl_FragColor = vec4(0.0);',\n'gl_FragColor += texture2D(texture, vTexCoord + -7 * uDelta)*0.0044299121055113265;',\n'gl_FragColor += texture2D(texture, vTexCoord + -6 * uDelta)*0.00895781211794;',\n'gl_FragColor += texture2D(texture, vTexCoord + -5 * uDelta)*0.0215963866053;',\n'gl_FragColor += texture2D(texture, vTexCoord + -4 * uDelta)*0.0443683338718;',\n'gl_FragColor += texture2D(texture, vTexCoord + -3 * uDelta)*0.0776744219933;',\n'gl_FragColor += texture2D(texture, vTexCoord + -2 * uDelta)*0.115876621105;',\n'gl_FragColor += texture2D(texture, vTexCoord + -1 * uDelta)*0.147308056121;',\n'gl_FragColor += texture2D(texture, vTexCoord )*0.159576912161;',\n'gl_FragColor += texture2D(texture, vTexCoord + 1 * uDelta)*0.147308056121;',\n'gl_FragColor += texture2D(texture, vTexCoord + 2 * uDelta)*0.115876621105;',\n'gl_FragColor += texture2D(texture, vTexCoord + 3 * uDelta)*0.0776744219933;',\n'gl_FragColor += texture2D(texture, vTexCoord + 4 * uDelta)*0.0443683338718;',\n'gl_FragColor += texture2D(texture, vTexCoord + 5 * uDelta)*0.0215963866053;',\n'gl_FragColor += texture2D(texture, vTexCoord + 6 * uDelta)*0.00895781211794;',\n'gl_FragColor += texture2D(texture, vTexCoord + 7 * uDelta)*0.0044299121055113265;',\n*/\n\n /* eslint-disable max-len */\n fragmentSource: 'precision highp float;\\n' +\n 'uniform sampler2D uTexture;\\n' +\n 'uniform vec2 uDelta;\\n' +\n 'varying vec2 vTexCoord;\\n' +\n 'const float nSamples = 15.0;\\n' +\n 'vec3 v3offset = vec3(12.9898, 78.233, 151.7182);\\n' +\n 'float random(vec3 scale) {\\n' +\n /* use the fragment position for a different seed per-pixel */\n 'return fract(sin(dot(gl_FragCoord.xyz, scale)) * 43758.5453);\\n' +\n '}\\n' +\n 'void main() {\\n' +\n 'vec4 color = vec4(0.0);\\n' +\n 'float total = 0.0;\\n' +\n 'float offset = random(v3offset);\\n' +\n 'for (float t = -nSamples; t <= nSamples; t++) {\\n' +\n 'float percent = (t + offset - 0.5) / nSamples;\\n' +\n 'float weight = 1.0 - abs(percent);\\n' +\n 'color += texture2D(uTexture, vTexCoord + uDelta * percent) * weight;\\n' +\n 'total += weight;\\n' +\n '}\\n' +\n 'gl_FragColor = color / total;\\n' +\n '}',\n /* eslint-enable max-len */\n\n /**\n * blur value, in percentage of image dimensions.\n * specific to keep the image blur constant at different resolutions\n * range bewteen 0 and 1.\n */\n blur: 0,\n\n mainParameter: 'blur',\n\n applyTo: function(options) {\n if (options.webgl) {\n // this aspectRatio is used to give the same blur to vertical and horizontal\n this.aspectRatio = options.sourceWidth / options.sourceHeight;\n options.passes++;\n this._setupFrameBuffer(options);\n this.horizontal = true;\n this.applyToWebGL(options);\n this._swapTextures(options);\n this._setupFrameBuffer(options);\n this.horizontal = false;\n this.applyToWebGL(options);\n this._swapTextures(options);\n }\n else {\n this.applyTo2d(options);\n }\n },\n\n applyTo2d: function(options) {\n // paint canvasEl with current image data.\n //options.ctx.putImageData(options.imageData, 0, 0);\n options.imageData = this.simpleBlur(options);\n },\n\n simpleBlur: function(options) {\n var resources = options.filterBackend.resources, canvas1, canvas2,\n width = options.imageData.width,\n height = options.imageData.height;\n\n if (!resources.blurLayer1) {\n resources.blurLayer1 = fabric.util.createCanvasElement();\n resources.blurLayer2 = fabric.util.createCanvasElement();\n }\n canvas1 = resources.blurLayer1;\n canvas2 = resources.blurLayer2;\n if (canvas1.width !== width || canvas1.height !== height) {\n canvas2.width = canvas1.width = width;\n canvas2.height = canvas1.height = height;\n }\n var ctx1 = canvas1.getContext('2d'),\n ctx2 = canvas2.getContext('2d'),\n nSamples = 15,\n random, percent, j, i,\n blur = this.blur * 0.06 * 0.5;\n\n // load first canvas\n ctx1.putImageData(options.imageData, 0, 0);\n ctx2.clearRect(0, 0, width, height);\n\n for (i = -nSamples; i <= nSamples; i++) {\n random = (Math.random() - 0.5) / 4;\n percent = i / nSamples;\n j = blur * percent * width + random;\n ctx2.globalAlpha = 1 - Math.abs(percent);\n ctx2.drawImage(canvas1, j, random);\n ctx1.drawImage(canvas2, 0, 0);\n ctx2.globalAlpha = 1;\n ctx2.clearRect(0, 0, canvas2.width, canvas2.height);\n }\n for (i = -nSamples; i <= nSamples; i++) {\n random = (Math.random() - 0.5) / 4;\n percent = i / nSamples;\n j = blur * percent * height + random;\n ctx2.globalAlpha = 1 - Math.abs(percent);\n ctx2.drawImage(canvas1, random, j);\n ctx1.drawImage(canvas2, 0, 0);\n ctx2.globalAlpha = 1;\n ctx2.clearRect(0, 0, canvas2.width, canvas2.height);\n }\n options.ctx.drawImage(canvas1, 0, 0);\n var newImageData = options.ctx.getImageData(0, 0, canvas1.width, canvas1.height);\n ctx1.globalAlpha = 1;\n ctx1.clearRect(0, 0, canvas1.width, canvas1.height);\n return newImageData;\n },\n\n /**\n * Return WebGL uniform locations for this filter's shader.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {WebGLShaderProgram} program This filter's compiled shader program.\n */\n getUniformLocations: function(gl, program) {\n return {\n delta: gl.getUniformLocation(program, 'uDelta'),\n };\n },\n\n /**\n * Send data from this filter to its shader program's uniforms.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {Object} uniformLocations A map of string uniform names to WebGLUniformLocation objects\n */\n sendUniformData: function(gl, uniformLocations) {\n var delta = this.chooseRightDelta();\n gl.uniform2fv(uniformLocations.delta, delta);\n },\n\n /**\n * choose right value of image percentage to blur with\n * @returns {Array} a numeric array with delta values\n */\n chooseRightDelta: function() {\n var blurScale = 1, delta = [0, 0], blur;\n if (this.horizontal) {\n if (this.aspectRatio > 1) {\n // image is wide, i want to shrink radius horizontal\n blurScale = 1 / this.aspectRatio;\n }\n }\n else {\n if (this.aspectRatio < 1) {\n // image is tall, i want to shrink radius vertical\n blurScale = this.aspectRatio;\n }\n }\n blur = blurScale * this.blur * 0.12;\n if (this.horizontal) {\n delta[0] = blur;\n }\n else {\n delta[1] = blur;\n }\n return delta;\n },\n });\n\n /**\n * Deserialize a JSON definition of a BlurFilter into a concrete instance.\n */\n filters.Blur.fromObject = fabric.Image.filters.BaseFilter.fromObject;\n\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { }),\n filters = fabric.Image.filters,\n createClass = fabric.util.createClass;\n\n /**\n * Gamma filter class\n * @class fabric.Image.filters.Gamma\n * @memberOf fabric.Image.filters\n * @extends fabric.Image.filters.BaseFilter\n * @see {@link fabric.Image.filters.Gamma#initialize} for constructor definition\n * @see {@link http://fabricjs.com/image-filters|ImageFilters demo}\n * @example\n * var filter = new fabric.Image.filters.Gamma({\n * brightness: 200\n * });\n * object.filters.push(filter);\n * object.applyFilters();\n */\n filters.Gamma = createClass(filters.BaseFilter, /** @lends fabric.Image.filters.Gamma.prototype */ {\n\n /**\n * Filter type\n * @param {String} type\n * @default\n */\n type: 'Gamma',\n\n fragmentSource: 'precision highp float;\\n' +\n 'uniform sampler2D uTexture;\\n' +\n 'uniform vec3 uGamma;\\n' +\n 'varying vec2 vTexCoord;\\n' +\n 'void main() {\\n' +\n 'vec4 color = texture2D(uTexture, vTexCoord);\\n' +\n 'vec3 correction = (1.0 / uGamma);\\n' +\n 'color.r = pow(color.r, correction.r);\\n' +\n 'color.g = pow(color.g, correction.g);\\n' +\n 'color.b = pow(color.b, correction.b);\\n' +\n 'gl_FragColor = color;\\n' +\n 'gl_FragColor.rgb *= color.a;\\n' +\n '}',\n\n /**\n * Gamma array value, from 0.01 to 2.2.\n * @param {Array} gamma\n * @default\n */\n gamma: [1, 1, 1],\n\n /**\n * Describe the property that is the filter parameter\n * @param {String} m\n * @default\n */\n mainParameter: 'gamma',\n\n /**\n * Constructor\n * @param {Object} [options] Options object\n */\n initialize: function(options) {\n this.gamma = [1, 1, 1];\n filters.BaseFilter.prototype.initialize.call(this, options);\n },\n\n /**\n * Apply the Gamma operation to a Uint8Array representing the pixels of an image.\n *\n * @param {Object} options\n * @param {ImageData} options.imageData The Uint8Array to be filtered.\n */\n applyTo2d: function(options) {\n var imageData = options.imageData, data = imageData.data,\n gamma = this.gamma, len = data.length,\n rInv = 1 / gamma[0], gInv = 1 / gamma[1],\n bInv = 1 / gamma[2], i;\n\n if (!this.rVals) {\n // eslint-disable-next-line\n this.rVals = new Uint8Array(256);\n // eslint-disable-next-line\n this.gVals = new Uint8Array(256);\n // eslint-disable-next-line\n this.bVals = new Uint8Array(256);\n }\n\n // This is an optimization - pre-compute a look-up table for each color channel\n // instead of performing these pow calls for each pixel in the image.\n for (i = 0, len = 256; i < len; i++) {\n this.rVals[i] = Math.pow(i / 255, rInv) * 255;\n this.gVals[i] = Math.pow(i / 255, gInv) * 255;\n this.bVals[i] = Math.pow(i / 255, bInv) * 255;\n }\n for (i = 0, len = data.length; i < len; i += 4) {\n data[i] = this.rVals[data[i]];\n data[i + 1] = this.gVals[data[i + 1]];\n data[i + 2] = this.bVals[data[i + 2]];\n }\n },\n\n /**\n * Return WebGL uniform locations for this filter's shader.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {WebGLShaderProgram} program This filter's compiled shader program.\n */\n getUniformLocations: function(gl, program) {\n return {\n uGamma: gl.getUniformLocation(program, 'uGamma'),\n };\n },\n\n /**\n * Send data from this filter to its shader program's uniforms.\n *\n * @param {WebGLRenderingContext} gl The GL canvas context used to compile this filter's shader.\n * @param {Object} uniformLocations A map of string uniform names to WebGLUniformLocation objects\n */\n sendUniformData: function(gl, uniformLocations) {\n gl.uniform3fv(uniformLocations.uGamma, this.gamma);\n },\n });\n\n /**\n * Returns filter instance from an object representation\n * @static\n * @param {Object} object Object to create an instance from\n * @param {function} [callback] to be invoked after filter creation\n * @return {fabric.Image.filters.Gamma} Instance of fabric.Image.filters.Gamma\n */\n fabric.Image.filters.Gamma.fromObject = fabric.Image.filters.BaseFilter.fromObject;\n\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { }),\n filters = fabric.Image.filters,\n createClass = fabric.util.createClass;\n\n /**\n * A container class that knows how to apply a sequence of filters to an input image.\n */\n filters.Composed = createClass(filters.BaseFilter, /** @lends fabric.Image.filters.Composed.prototype */ {\n\n type: 'Composed',\n\n /**\n * A non sparse array of filters to apply\n */\n subFilters: [],\n\n /**\n * Constructor\n * @param {Object} [options] Options object\n */\n initialize: function(options) {\n this.callSuper('initialize', options);\n // create a new array instead mutating the prototype with push\n this.subFilters = this.subFilters.slice(0);\n },\n\n /**\n * Apply this container's filters to the input image provided.\n *\n * @param {Object} options\n * @param {Number} options.passes The number of filters remaining to be applied.\n */\n applyTo: function(options) {\n options.passes += this.subFilters.length - 1;\n this.subFilters.forEach(function(filter) {\n filter.applyTo(options);\n });\n },\n\n /**\n * Serialize this filter into JSON.\n *\n * @returns {Object} A JSON representation of this filter.\n */\n toObject: function() {\n return fabric.util.object.extend(this.callSuper('toObject'), {\n subFilters: this.subFilters.map(function(filter) { return filter.toObject(); }),\n });\n },\n\n isNeutralState: function() {\n return !this.subFilters.some(function(filter) { return !filter.isNeutralState(); });\n }\n });\n\n /**\n * Deserialize a JSON definition of a ComposedFilter into a concrete instance.\n */\n fabric.Image.filters.Composed.fromObject = function(object, callback) {\n var filters = object.subFilters || [],\n subFilters = filters.map(function(filter) {\n return new fabric.Image.filters[filter.type](filter);\n }),\n instance = new fabric.Image.filters.Composed({ subFilters: subFilters });\n callback && callback(instance);\n return instance;\n };\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { }),\n filters = fabric.Image.filters,\n createClass = fabric.util.createClass;\n\n /**\n * HueRotation filter class\n * @class fabric.Image.filters.HueRotation\n * @memberOf fabric.Image.filters\n * @extends fabric.Image.filters.BaseFilter\n * @see {@link fabric.Image.filters.HueRotation#initialize} for constructor definition\n * @see {@link http://fabricjs.com/image-filters|ImageFilters demo}\n * @example\n * var filter = new fabric.Image.filters.HueRotation({\n * rotation: -0.5\n * });\n * object.filters.push(filter);\n * object.applyFilters();\n */\n filters.HueRotation = createClass(filters.ColorMatrix, /** @lends fabric.Image.filters.HueRotation.prototype */ {\n\n /**\n * Filter type\n * @param {String} type\n * @default\n */\n type: 'HueRotation',\n\n /**\n * HueRotation value, from -1 to 1.\n * the unit is radians\n * @param {Number} myParameter\n * @default\n */\n rotation: 0,\n\n /**\n * Describe the property that is the filter parameter\n * @param {String} m\n * @default\n */\n mainParameter: 'rotation',\n\n calculateMatrix: function() {\n var rad = this.rotation * Math.PI, cos = fabric.util.cos(rad), sin = fabric.util.sin(rad),\n aThird = 1 / 3, aThirdSqtSin = Math.sqrt(aThird) * sin, OneMinusCos = 1 - cos;\n this.matrix = [\n 1, 0, 0, 0, 0,\n 0, 1, 0, 0, 0,\n 0, 0, 1, 0, 0,\n 0, 0, 0, 1, 0\n ];\n this.matrix[0] = cos + OneMinusCos / 3;\n this.matrix[1] = aThird * OneMinusCos - aThirdSqtSin;\n this.matrix[2] = aThird * OneMinusCos + aThirdSqtSin;\n this.matrix[5] = aThird * OneMinusCos + aThirdSqtSin;\n this.matrix[6] = cos + aThird * OneMinusCos;\n this.matrix[7] = aThird * OneMinusCos - aThirdSqtSin;\n this.matrix[10] = aThird * OneMinusCos - aThirdSqtSin;\n this.matrix[11] = aThird * OneMinusCos + aThirdSqtSin;\n this.matrix[12] = cos + aThird * OneMinusCos;\n },\n\n /**\n * HueRotation isNeutralState implementation\n * Used only in image applyFilters to discard filters that will not have an effect\n * on the image\n * @param {Object} options\n **/\n isNeutralState: function(options) {\n this.calculateMatrix();\n return filters.BaseFilter.prototype.isNeutralState.call(this, options);\n },\n\n /**\n * Apply this filter to the input image data provided.\n *\n * Determines whether to use WebGL or Canvas2D based on the options.webgl flag.\n *\n * @param {Object} options\n * @param {Number} options.passes The number of filters remaining to be executed\n * @param {Boolean} options.webgl Whether to use webgl to render the filter.\n * @param {WebGLTexture} options.sourceTexture The texture setup as the source to be filtered.\n * @param {WebGLTexture} options.targetTexture The texture where filtered output should be drawn.\n * @param {WebGLRenderingContext} options.context The GL context used for rendering.\n * @param {Object} options.programCache A map of compiled shader programs, keyed by filter type.\n */\n applyTo: function(options) {\n this.calculateMatrix();\n filters.BaseFilter.prototype.applyTo.call(this, options);\n },\n\n });\n\n /**\n * Returns filter instance from an object representation\n * @static\n * @param {Object} object Object to create an instance from\n * @param {function} [callback] to be invoked after filter creation\n * @return {fabric.Image.filters.HueRotation} Instance of fabric.Image.filters.HueRotation\n */\n fabric.Image.filters.HueRotation.fromObject = fabric.Image.filters.BaseFilter.fromObject;\n\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = { }),\n clone = fabric.util.object.clone;\n\n if (fabric.Text) {\n fabric.warn('fabric.Text is already defined');\n return;\n }\n\n /**\n * Text class\n * @class fabric.Text\n * @extends fabric.Object\n * @return {fabric.Text} thisArg\n * @tutorial {@link http://fabricjs.com/fabric-intro-part-2#text}\n * @see {@link fabric.Text#initialize} for constructor definition\n */\n fabric.Text = fabric.util.createClass(fabric.Object, /** @lends fabric.Text.prototype */ {\n\n /**\n * Properties which when set cause object to change dimensions\n * @type Array\n * @private\n */\n _dimensionAffectingProps: [\n 'fontSize',\n 'fontWeight',\n 'fontFamily',\n 'fontStyle',\n 'lineHeight',\n 'text',\n 'charSpacing',\n 'textAlign',\n 'styles',\n ],\n\n /**\n * @private\n */\n _reNewline: /\\r?\\n/,\n\n /**\n * Use this regular expression to filter for whitespaces that is not a new line.\n * Mostly used when text is 'justify' aligned.\n * @private\n */\n _reSpacesAndTabs: /[ \\t\\r]/g,\n\n /**\n * Use this regular expression to filter for whitespace that is not a new line.\n * Mostly used when text is 'justify' aligned.\n * @private\n */\n _reSpaceAndTab: /[ \\t\\r]/,\n\n /**\n * Use this regular expression to filter consecutive groups of non spaces.\n * Mostly used when text is 'justify' aligned.\n * @private\n */\n _reWords: /\\S+/g,\n\n /**\n * Type of an object\n * @type String\n * @default\n */\n type: 'text',\n\n /**\n * Font size (in pixels)\n * @type Number\n * @default\n */\n fontSize: 40,\n\n /**\n * Font weight (e.g. bold, normal, 400, 600, 800)\n * @type {(Number|String)}\n * @default\n */\n fontWeight: 'normal',\n\n /**\n * Font family\n * @type String\n * @default\n */\n fontFamily: 'Times New Roman',\n\n /**\n * Text decoration underline.\n * @type Boolean\n * @default\n */\n underline: false,\n\n /**\n * Text decoration overline.\n * @type Boolean\n * @default\n */\n overline: false,\n\n /**\n * Text decoration linethrough.\n * @type Boolean\n * @default\n */\n linethrough: false,\n\n /**\n * Text alignment. Possible values: \"left\", \"center\", \"right\", \"justify\",\n * \"justify-left\", \"justify-center\" or \"justify-right\".\n * @type String\n * @default\n */\n textAlign: 'left',\n\n /**\n * Font style . Possible values: \"\", \"normal\", \"italic\" or \"oblique\".\n * @type String\n * @default\n */\n fontStyle: 'normal',\n\n /**\n * Line height\n * @type Number\n * @default\n */\n lineHeight: 1.16,\n\n /**\n * Superscript schema object (minimum overlap)\n * @type {Object}\n * @default\n */\n superscript: {\n size: 0.60, // fontSize factor\n baseline: -0.35 // baseline-shift factor (upwards)\n },\n\n /**\n * Subscript schema object (minimum overlap)\n * @type {Object}\n * @default\n */\n subscript: {\n size: 0.60, // fontSize factor\n baseline: 0.11 // baseline-shift factor (downwards)\n },\n\n /**\n * Background color of text lines\n * @type String\n * @default\n */\n textBackgroundColor: '',\n\n /**\n * List of properties to consider when checking if\n * state of an object is changed ({@link fabric.Object#hasStateChanged})\n * as well as for history (undo/redo) purposes\n * @type Array\n */\n stateProperties: fabric.Object.prototype.stateProperties.concat('fontFamily',\n 'fontWeight',\n 'fontSize',\n 'text',\n 'underline',\n 'overline',\n 'linethrough',\n 'textAlign',\n 'fontStyle',\n 'lineHeight',\n 'textBackgroundColor',\n 'charSpacing',\n 'styles'),\n\n /**\n * List of properties to consider when checking if cache needs refresh\n * @type Array\n */\n cacheProperties: fabric.Object.prototype.cacheProperties.concat('fontFamily',\n 'fontWeight',\n 'fontSize',\n 'text',\n 'underline',\n 'overline',\n 'linethrough',\n 'textAlign',\n 'fontStyle',\n 'lineHeight',\n 'textBackgroundColor',\n 'charSpacing',\n 'styles'),\n\n /**\n * When defined, an object is rendered via stroke and this property specifies its color.\n * Backwards incompatibility note: This property was named \"strokeStyle\" until v1.1.6\n * @type String\n * @default\n */\n stroke: null,\n\n /**\n * Shadow object representing shadow of this shape.\n * Backwards incompatibility note: This property was named \"textShadow\" (String) until v1.2.11\n * @type fabric.Shadow\n * @default\n */\n shadow: null,\n\n /**\n * @private\n */\n _fontSizeFraction: 0.222,\n\n /**\n * @private\n */\n offsets: {\n underline: 0.10,\n linethrough: -0.315,\n overline: -0.88\n },\n\n /**\n * Text Line proportion to font Size (in pixels)\n * @type Number\n * @default\n */\n _fontSizeMult: 1.13,\n\n /**\n * additional space between characters\n * expressed in thousands of em unit\n * @type Number\n * @default\n */\n charSpacing: 0,\n\n /**\n * Object containing character styles - top-level properties -> line numbers,\n * 2nd-level properties - charater numbers\n * @type Object\n * @default\n */\n styles: null,\n\n /**\n * Reference to a context to measure text char or couple of chars\n * the cacheContext of the canvas will be used or a freshly created one if the object is not on canvas\n * once created it will be referenced on fabric._measuringContext to avoide creating a canvas for every\n * text object created.\n * @type {CanvasRenderingContext2D}\n * @default\n */\n _measuringContext: null,\n\n /**\n * Baseline shift, stlyes only, keep at 0 for the main text object\n * @type {Number}\n * @default\n */\n deltaY: 0,\n\n /**\n * Array of properties that define a style unit (of 'styles').\n * @type {Array}\n * @default\n */\n _styleProperties: [\n 'stroke',\n 'strokeWidth',\n 'fill',\n 'fontFamily',\n 'fontSize',\n 'fontWeight',\n 'fontStyle',\n 'underline',\n 'overline',\n 'linethrough',\n 'deltaY',\n 'textBackgroundColor',\n ],\n\n /**\n * contains characters bounding boxes\n */\n __charBounds: [],\n\n /**\n * use this size when measuring text. To avoid IE11 rounding errors\n * @type {Number}\n * @default\n * @readonly\n * @private\n */\n CACHE_FONT_SIZE: 400,\n\n /**\n * contains the min text width to avoid getting 0\n * @type {Number}\n * @default\n */\n MIN_TEXT_WIDTH: 2,\n\n /**\n * Constructor\n * @param {String} text Text string\n * @param {Object} [options] Options object\n * @return {fabric.Text} thisArg\n */\n initialize: function(text, options) {\n this.styles = options ? (options.styles || { }) : { };\n this.text = text;\n this.__skipDimension = true;\n this.callSuper('initialize', options);\n this.__skipDimension = false;\n this.initDimensions();\n this.setCoords();\n this.setupState({ propertySet: '_dimensionAffectingProps' });\n },\n\n /**\n * Return a contex for measurement of text string.\n * if created it gets stored for reuse\n * @param {String} text Text string\n * @param {Object} [options] Options object\n * @return {fabric.Text} thisArg\n */\n getMeasuringContext: function() {\n // if we did not return we have to measure something.\n if (!fabric._measuringContext) {\n fabric._measuringContext = this.canvas && this.canvas.contextCache ||\n fabric.util.createCanvasElement().getContext('2d');\n }\n return fabric._measuringContext;\n },\n\n /**\n * @private\n * Divides text into lines of text and lines of graphemes.\n */\n _splitText: function() {\n var newLines = this._splitTextIntoLines(this.text);\n this.textLines = newLines.lines;\n this._textLines = newLines.graphemeLines;\n this._unwrappedTextLines = newLines._unwrappedLines;\n this._text = newLines.graphemeText;\n return newLines;\n },\n\n /**\n * Initialize or update text dimensions.\n * Updates this.width and this.height with the proper values.\n * Does not return dimensions.\n */\n initDimensions: function() {\n if (this.__skipDimension) {\n return;\n }\n this._splitText();\n this._clearCache();\n this.width = this.calcTextWidth() || this.cursorWidth || this.MIN_TEXT_WIDTH;\n if (this.textAlign.indexOf('justify') !== -1) {\n // once text is measured we need to make space fatter to make justified text.\n this.enlargeSpaces();\n }\n this.height = this.calcTextHeight();\n this.saveState({ propertySet: '_dimensionAffectingProps' });\n },\n\n /**\n * Enlarge space boxes and shift the others\n */\n enlargeSpaces: function() {\n var diffSpace, currentLineWidth, numberOfSpaces, accumulatedSpace, line, charBound, spaces;\n for (var i = 0, len = this._textLines.length; i < len; i++) {\n if (this.textAlign !== 'justify' && (i === len - 1 || this.isEndOfWrapping(i))) {\n continue;\n }\n accumulatedSpace = 0;\n line = this._textLines[i];\n currentLineWidth = this.getLineWidth(i);\n if (currentLineWidth < this.width && (spaces = this.textLines[i].match(this._reSpacesAndTabs))) {\n numberOfSpaces = spaces.length;\n diffSpace = (this.width - currentLineWidth) / numberOfSpaces;\n for (var j = 0, jlen = line.length; j <= jlen; j++) {\n charBound = this.__charBounds[i][j];\n if (this._reSpaceAndTab.test(line[j])) {\n charBound.width += diffSpace;\n charBound.kernedWidth += diffSpace;\n charBound.left += accumulatedSpace;\n accumulatedSpace += diffSpace;\n }\n else {\n charBound.left += accumulatedSpace;\n }\n }\n }\n }\n },\n\n /**\n * Detect if the text line is ended with an hard break\n * text and itext do not have wrapping, return false\n * @return {Boolean}\n */\n isEndOfWrapping: function(lineIndex) {\n return lineIndex === this._textLines.length - 1;\n },\n\n /**\n * Detect if a line has a linebreak and so we need to account for it when moving\n * and counting style.\n * It return always for text and Itext.\n * @return Number\n */\n missingNewlineOffset: function() {\n return 1;\n },\n\n /**\n * Returns string representation of an instance\n * @return {String} String representation of text object\n */\n toString: function() {\n return '#';\n },\n\n /**\n * Return the dimension and the zoom level needed to create a cache canvas\n * big enough to host the object to be cached.\n * @private\n * @param {Object} dim.x width of object to be cached\n * @param {Object} dim.y height of object to be cached\n * @return {Object}.width width of canvas\n * @return {Object}.height height of canvas\n * @return {Object}.zoomX zoomX zoom value to unscale the canvas before drawing cache\n * @return {Object}.zoomY zoomY zoom value to unscale the canvas before drawing cache\n */\n _getCacheCanvasDimensions: function() {\n var dims = this.callSuper('_getCacheCanvasDimensions');\n var fontSize = this.fontSize;\n dims.width += fontSize * dims.zoomX;\n dims.height += fontSize * dims.zoomY;\n return dims;\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _render: function(ctx) {\n this._setTextStyles(ctx);\n this._renderTextLinesBackground(ctx);\n this._renderTextDecoration(ctx, 'underline');\n this._renderText(ctx);\n this._renderTextDecoration(ctx, 'overline');\n this._renderTextDecoration(ctx, 'linethrough');\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _renderText: function(ctx) {\n if (this.paintFirst === 'stroke') {\n this._renderTextStroke(ctx);\n this._renderTextFill(ctx);\n }\n else {\n this._renderTextFill(ctx);\n this._renderTextStroke(ctx);\n }\n },\n\n /**\n * Set the font parameter of the context with the object properties or with charStyle\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n * @param {Object} [charStyle] object with font style properties\n * @param {String} [charStyle.fontFamily] Font Family\n * @param {Number} [charStyle.fontSize] Font size in pixels. ( without px suffix )\n * @param {String} [charStyle.fontWeight] Font weight\n * @param {String} [charStyle.fontStyle] Font style (italic|normal)\n */\n _setTextStyles: function(ctx, charStyle, forMeasuring) {\n ctx.textBaseline = 'alphabetic';\n ctx.font = this._getFontDeclaration(charStyle, forMeasuring);\n },\n\n /**\n * calculate and return the text Width measuring each line.\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n * @return {Number} Maximum width of fabric.Text object\n */\n calcTextWidth: function() {\n var maxWidth = this.getLineWidth(0);\n\n for (var i = 1, len = this._textLines.length; i < len; i++) {\n var currentLineWidth = this.getLineWidth(i);\n if (currentLineWidth > maxWidth) {\n maxWidth = currentLineWidth;\n }\n }\n return maxWidth;\n },\n\n /**\n * @private\n * @param {String} method Method name (\"fillText\" or \"strokeText\")\n * @param {CanvasRenderingContext2D} ctx Context to render on\n * @param {String} line Text to render\n * @param {Number} left Left position of text\n * @param {Number} top Top position of text\n * @param {Number} lineIndex Index of a line in a text\n */\n _renderTextLine: function(method, ctx, line, left, top, lineIndex) {\n this._renderChars(method, ctx, line, left, top, lineIndex);\n },\n\n /**\n * Renders the text background for lines, taking care of style\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _renderTextLinesBackground: function(ctx) {\n if (!this.textBackgroundColor && !this.styleHas('textBackgroundColor')) {\n return;\n }\n var lineTopOffset = 0, heightOfLine,\n lineLeftOffset, originalFill = ctx.fillStyle,\n line, lastColor,\n leftOffset = this._getLeftOffset(),\n topOffset = this._getTopOffset(),\n boxStart = 0, boxWidth = 0, charBox, currentColor;\n\n for (var i = 0, len = this._textLines.length; i < len; i++) {\n heightOfLine = this.getHeightOfLine(i);\n if (!this.textBackgroundColor && !this.styleHas('textBackgroundColor', i)) {\n lineTopOffset += heightOfLine;\n continue;\n }\n line = this._textLines[i];\n lineLeftOffset = this._getLineLeftOffset(i);\n boxWidth = 0;\n boxStart = 0;\n lastColor = this.getValueOfPropertyAt(i, 0, 'textBackgroundColor');\n for (var j = 0, jlen = line.length; j < jlen; j++) {\n charBox = this.__charBounds[i][j];\n currentColor = this.getValueOfPropertyAt(i, j, 'textBackgroundColor');\n if (currentColor !== lastColor) {\n ctx.fillStyle = lastColor;\n lastColor && ctx.fillRect(\n leftOffset + lineLeftOffset + boxStart,\n topOffset + lineTopOffset,\n boxWidth,\n heightOfLine / this.lineHeight\n );\n boxStart = charBox.left;\n boxWidth = charBox.width;\n lastColor = currentColor;\n }\n else {\n boxWidth += charBox.kernedWidth;\n }\n }\n if (currentColor) {\n ctx.fillStyle = currentColor;\n ctx.fillRect(\n leftOffset + lineLeftOffset + boxStart,\n topOffset + lineTopOffset,\n boxWidth,\n heightOfLine / this.lineHeight\n );\n }\n lineTopOffset += heightOfLine;\n }\n ctx.fillStyle = originalFill;\n // if there is text background color no\n // other shadows should be casted\n this._removeShadow(ctx);\n },\n\n /**\n * @private\n * @param {Object} decl style declaration for cache\n * @param {String} decl.fontFamily fontFamily\n * @param {String} decl.fontStyle fontStyle\n * @param {String} decl.fontWeight fontWeight\n * @return {Object} reference to cache\n */\n getFontCache: function(decl) {\n var fontFamily = decl.fontFamily.toLowerCase();\n if (!fabric.charWidthsCache[fontFamily]) {\n fabric.charWidthsCache[fontFamily] = { };\n }\n var cache = fabric.charWidthsCache[fontFamily],\n cacheProp = decl.fontStyle.toLowerCase() + '_' + (decl.fontWeight + '').toLowerCase();\n if (!cache[cacheProp]) {\n cache[cacheProp] = { };\n }\n return cache[cacheProp];\n },\n\n /**\n * apply all the character style to canvas for rendering\n * @private\n * @param {String} _char\n * @param {Number} lineIndex\n * @param {Number} charIndex\n * @param {Object} [decl]\n */\n _applyCharStyles: function(method, ctx, lineIndex, charIndex, styleDeclaration) {\n\n this._setFillStyles(ctx, styleDeclaration);\n this._setStrokeStyles(ctx, styleDeclaration);\n\n ctx.font = this._getFontDeclaration(styleDeclaration);\n },\n\n /**\n * measure and return the width of a single character.\n * possibly overridden to accommodate different measure logic or\n * to hook some external lib for character measurement\n * @private\n * @param {String} _char, char to be measured\n * @param {Object} charStyle style of char to be measured\n * @param {String} [previousChar] previous char\n * @param {Object} [prevCharStyle] style of previous char\n */\n _measureChar: function(_char, charStyle, previousChar, prevCharStyle) {\n // first i try to return from cache\n var fontCache = this.getFontCache(charStyle), fontDeclaration = this._getFontDeclaration(charStyle),\n previousFontDeclaration = this._getFontDeclaration(prevCharStyle), couple = previousChar + _char,\n stylesAreEqual = fontDeclaration === previousFontDeclaration, width, coupleWidth, previousWidth,\n fontMultiplier = charStyle.fontSize / this.CACHE_FONT_SIZE, kernedWidth;\n\n if (previousChar && fontCache[previousChar] !== undefined) {\n previousWidth = fontCache[previousChar];\n }\n if (fontCache[_char] !== undefined) {\n kernedWidth = width = fontCache[_char];\n }\n if (stylesAreEqual && fontCache[couple] !== undefined) {\n coupleWidth = fontCache[couple];\n kernedWidth = coupleWidth - previousWidth;\n }\n if (width === undefined || previousWidth === undefined || coupleWidth === undefined) {\n var ctx = this.getMeasuringContext();\n // send a TRUE to specify measuring font size CACHE_FONT_SIZE\n this._setTextStyles(ctx, charStyle, true);\n }\n if (width === undefined) {\n kernedWidth = width = ctx.measureText(_char).width;\n fontCache[_char] = width;\n }\n if (previousWidth === undefined && stylesAreEqual && previousChar) {\n previousWidth = ctx.measureText(previousChar).width;\n fontCache[previousChar] = previousWidth;\n }\n if (stylesAreEqual && coupleWidth === undefined) {\n // we can measure the kerning couple and subtract the width of the previous character\n coupleWidth = ctx.measureText(couple).width;\n fontCache[couple] = coupleWidth;\n kernedWidth = coupleWidth - previousWidth;\n }\n return { width: width * fontMultiplier, kernedWidth: kernedWidth * fontMultiplier };\n },\n\n /**\n * Computes height of character at given position\n * @param {Number} line the line index number\n * @param {Number} _char the character index number\n * @return {Number} fontSize of the character\n */\n getHeightOfChar: function(line, _char) {\n return this.getValueOfPropertyAt(line, _char, 'fontSize');\n },\n\n /**\n * measure a text line measuring all characters.\n * @param {Number} lineIndex line number\n * @return {Number} Line width\n */\n measureLine: function(lineIndex) {\n var lineInfo = this._measureLine(lineIndex);\n if (this.charSpacing !== 0) {\n lineInfo.width -= this._getWidthOfCharSpacing();\n }\n if (lineInfo.width < 0) {\n lineInfo.width = 0;\n }\n return lineInfo;\n },\n\n /**\n * measure every grapheme of a line, populating __charBounds\n * @param {Number} lineIndex\n * @return {Object} object.width total width of characters\n * @return {Object} object.widthOfSpaces length of chars that match this._reSpacesAndTabs\n */\n _measureLine: function(lineIndex) {\n var width = 0, i, grapheme, line = this._textLines[lineIndex], prevGrapheme,\n graphemeInfo, numOfSpaces = 0, lineBounds = new Array(line.length);\n\n this.__charBounds[lineIndex] = lineBounds;\n for (i = 0; i < line.length; i++) {\n grapheme = line[i];\n graphemeInfo = this._getGraphemeBox(grapheme, lineIndex, i, prevGrapheme);\n lineBounds[i] = graphemeInfo;\n width += graphemeInfo.kernedWidth;\n prevGrapheme = grapheme;\n }\n // this latest bound box represent the last character of the line\n // to simplify cursor handling in interactive mode.\n lineBounds[i] = {\n left: graphemeInfo ? graphemeInfo.left + graphemeInfo.width : 0,\n width: 0,\n kernedWidth: 0,\n height: this.fontSize\n };\n return { width: width, numOfSpaces: numOfSpaces };\n },\n\n /**\n * Measure and return the info of a single grapheme.\n * needs the the info of previous graphemes already filled\n * @private\n * @param {String} grapheme to be measured\n * @param {Number} lineIndex index of the line where the char is\n * @param {Number} charIndex position in the line\n * @param {String} [prevGrapheme] character preceding the one to be measured\n */\n _getGraphemeBox: function(grapheme, lineIndex, charIndex, prevGrapheme, skipLeft) {\n var style = this.getCompleteStyleDeclaration(lineIndex, charIndex),\n prevStyle = prevGrapheme ? this.getCompleteStyleDeclaration(lineIndex, charIndex - 1) : { },\n info = this._measureChar(grapheme, style, prevGrapheme, prevStyle),\n kernedWidth = info.kernedWidth,\n width = info.width, charSpacing;\n\n if (this.charSpacing !== 0) {\n charSpacing = this._getWidthOfCharSpacing();\n width += charSpacing;\n kernedWidth += charSpacing;\n }\n\n var box = {\n width: width,\n left: 0,\n height: style.fontSize,\n kernedWidth: kernedWidth,\n deltaY: style.deltaY,\n };\n if (charIndex > 0 && !skipLeft) {\n var previousBox = this.__charBounds[lineIndex][charIndex - 1];\n box.left = previousBox.left + previousBox.width + info.kernedWidth - info.width;\n }\n return box;\n },\n\n /**\n * Calculate height of line at 'lineIndex'\n * @param {Number} lineIndex index of line to calculate\n * @return {Number}\n */\n getHeightOfLine: function(lineIndex) {\n if (this.__lineHeights[lineIndex]) {\n return this.__lineHeights[lineIndex];\n }\n\n var line = this._textLines[lineIndex],\n // char 0 is measured before the line cycle because it nneds to char\n // emptylines\n maxHeight = this.getHeightOfChar(lineIndex, 0);\n for (var i = 1, len = line.length; i < len; i++) {\n maxHeight = Math.max(this.getHeightOfChar(lineIndex, i), maxHeight);\n }\n\n return this.__lineHeights[lineIndex] = maxHeight * this.lineHeight * this._fontSizeMult;\n },\n\n /**\n * Calculate text box height\n */\n calcTextHeight: function() {\n var lineHeight, height = 0;\n for (var i = 0, len = this._textLines.length; i < len; i++) {\n lineHeight = this.getHeightOfLine(i);\n height += (i === len - 1 ? lineHeight / this.lineHeight : lineHeight);\n }\n return height;\n },\n\n /**\n * @private\n * @return {Number} Left offset\n */\n _getLeftOffset: function() {\n return -this.width / 2;\n },\n\n /**\n * @private\n * @return {Number} Top offset\n */\n _getTopOffset: function() {\n return -this.height / 2;\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n * @param {Object} filler fabric.Pattern or fabric.Gradient\n * @return {Object} offset.offsetX offset for text rendering\n * @return {Object} offset.offsetY offset for text rendering\n */\n _applyPatternGradientTransform: function(ctx, filler) {\n if (!filler || !filler.toLive) {\n return { offsetX: 0, offsetY: 0 };\n }\n var offsetX = -this.width / 2 + filler.offsetX || 0,\n offsetY = -this.height / 2 + filler.offsetY || 0;\n\n ctx.transform(1, 0, 0, 1, offsetX, offsetY);\n return { offsetX: offsetX, offsetY: offsetY };\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n * @param {String} method Method name (\"fillText\" or \"strokeText\")\n */\n _renderTextCommon: function(ctx, method) {\n ctx.save();\n var lineHeights = 0, left = this._getLeftOffset(), top = this._getTopOffset(),\n offsets = this._applyPatternGradientTransform(ctx, method === 'fillText' ? this.fill : this.stroke);\n for (var i = 0, len = this._textLines.length; i < len; i++) {\n var heightOfLine = this.getHeightOfLine(i),\n maxHeight = heightOfLine / this.lineHeight,\n leftOffset = this._getLineLeftOffset(i);\n this._renderTextLine(\n method,\n ctx,\n this._textLines[i],\n left + leftOffset - offsets.offsetX,\n top + lineHeights + maxHeight - offsets.offsetY,\n i\n );\n lineHeights += heightOfLine;\n }\n ctx.restore();\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _renderTextFill: function(ctx) {\n if (!this.fill && !this.styleHas('fill')) {\n return;\n }\n\n this._renderTextCommon(ctx, 'fillText');\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _renderTextStroke: function(ctx) {\n if ((!this.stroke || this.strokeWidth === 0) && this.isEmptyStyles()) {\n return;\n }\n\n if (this.shadow && !this.shadow.affectStroke) {\n this._removeShadow(ctx);\n }\n\n ctx.save();\n this._setLineDash(ctx, this.strokeDashArray);\n ctx.beginPath();\n this._renderTextCommon(ctx, 'strokeText');\n ctx.closePath();\n ctx.restore();\n },\n\n /**\n * @private\n * @param {String} method\n * @param {CanvasRenderingContext2D} ctx Context to render on\n * @param {String} line Content of the line\n * @param {Number} left\n * @param {Number} top\n * @param {Number} lineIndex\n * @param {Number} charOffset\n */\n _renderChars: function(method, ctx, line, left, top, lineIndex) {\n // set proper line offset\n var lineHeight = this.getHeightOfLine(lineIndex),\n isJustify = this.textAlign.indexOf('justify') !== -1,\n actualStyle,\n nextStyle,\n charsToRender = '',\n charBox,\n boxWidth = 0,\n timeToRender,\n shortCut = !isJustify && this.charSpacing === 0 && this.isEmptyStyles(lineIndex);\n\n ctx.save();\n top -= lineHeight * this._fontSizeFraction / this.lineHeight;\n if (shortCut) {\n // render all the line in one pass without checking\n this._renderChar(method, ctx, lineIndex, 0, this.textLines[lineIndex], left, top, lineHeight);\n ctx.restore();\n return;\n }\n for (var i = 0, len = line.length - 1; i <= len; i++) {\n timeToRender = i === len || this.charSpacing;\n charsToRender += line[i];\n charBox = this.__charBounds[lineIndex][i];\n if (boxWidth === 0) {\n left += charBox.kernedWidth - charBox.width;\n boxWidth += charBox.width;\n }\n else {\n boxWidth += charBox.kernedWidth;\n }\n if (isJustify && !timeToRender) {\n if (this._reSpaceAndTab.test(line[i])) {\n timeToRender = true;\n }\n }\n if (!timeToRender) {\n // if we have charSpacing, we render char by char\n actualStyle = actualStyle || this.getCompleteStyleDeclaration(lineIndex, i);\n nextStyle = this.getCompleteStyleDeclaration(lineIndex, i + 1);\n timeToRender = this._hasStyleChanged(actualStyle, nextStyle);\n }\n if (timeToRender) {\n this._renderChar(method, ctx, lineIndex, i, charsToRender, left, top, lineHeight);\n charsToRender = '';\n actualStyle = nextStyle;\n left += boxWidth;\n boxWidth = 0;\n }\n }\n ctx.restore();\n },\n\n /**\n * @private\n * @param {String} method\n * @param {CanvasRenderingContext2D} ctx Context to render on\n * @param {Number} lineIndex\n * @param {Number} charIndex\n * @param {String} _char\n * @param {Number} left Left coordinate\n * @param {Number} top Top coordinate\n * @param {Number} lineHeight Height of the line\n */\n _renderChar: function(method, ctx, lineIndex, charIndex, _char, left, top) {\n var decl = this._getStyleDeclaration(lineIndex, charIndex),\n fullDecl = this.getCompleteStyleDeclaration(lineIndex, charIndex),\n shouldFill = method === 'fillText' && fullDecl.fill,\n shouldStroke = method === 'strokeText' && fullDecl.stroke && fullDecl.strokeWidth;\n\n if (!shouldStroke && !shouldFill) {\n return;\n }\n decl && ctx.save();\n\n this._applyCharStyles(method, ctx, lineIndex, charIndex, fullDecl);\n\n if (decl && decl.textBackgroundColor) {\n this._removeShadow(ctx);\n }\n if (decl && decl.deltaY) {\n top += decl.deltaY;\n }\n\n shouldFill && ctx.fillText(_char, left, top);\n shouldStroke && ctx.strokeText(_char, left, top);\n decl && ctx.restore();\n },\n\n /**\n * Turns the character into a 'superior figure' (i.e. 'superscript')\n * @param {Number} start selection start\n * @param {Number} end selection end\n * @returns {fabric.Text} thisArg\n * @chainable\n */\n setSuperscript: function(start, end) {\n return this._setScript(start, end, this.superscript);\n },\n\n /**\n * Turns the character into an 'inferior figure' (i.e. 'subscript')\n * @param {Number} start selection start\n * @param {Number} end selection end\n * @returns {fabric.Text} thisArg\n * @chainable\n */\n setSubscript: function(start, end) {\n return this._setScript(start, end, this.subscript);\n },\n\n /**\n * Applies 'schema' at given position\n * @private\n * @param {Number} start selection start\n * @param {Number} end selection end\n * @param {Number} schema\n * @returns {fabric.Text} thisArg\n * @chainable\n */\n _setScript: function(start, end, schema) {\n var loc = this.get2DCursorLocation(start, true),\n fontSize = this.getValueOfPropertyAt(loc.lineIndex, loc.charIndex, 'fontSize'),\n dy = this.getValueOfPropertyAt(loc.lineIndex, loc.charIndex, 'deltaY'),\n style = { fontSize: fontSize * schema.size, deltaY: dy + fontSize * schema.baseline };\n this.setSelectionStyles(style, start, end);\n return this;\n },\n\n /**\n * @private\n * @param {Object} prevStyle\n * @param {Object} thisStyle\n */\n _hasStyleChanged: function(prevStyle, thisStyle) {\n return prevStyle.fill !== thisStyle.fill ||\n prevStyle.stroke !== thisStyle.stroke ||\n prevStyle.strokeWidth !== thisStyle.strokeWidth ||\n prevStyle.fontSize !== thisStyle.fontSize ||\n prevStyle.fontFamily !== thisStyle.fontFamily ||\n prevStyle.fontWeight !== thisStyle.fontWeight ||\n prevStyle.fontStyle !== thisStyle.fontStyle ||\n prevStyle.deltaY !== thisStyle.deltaY;\n },\n\n /**\n * @private\n * @param {Object} prevStyle\n * @param {Object} thisStyle\n */\n _hasStyleChangedForSvg: function(prevStyle, thisStyle) {\n return this._hasStyleChanged(prevStyle, thisStyle) ||\n prevStyle.overline !== thisStyle.overline ||\n prevStyle.underline !== thisStyle.underline ||\n prevStyle.linethrough !== thisStyle.linethrough;\n },\n\n /**\n * @private\n * @param {Number} lineIndex index text line\n * @return {Number} Line left offset\n */\n _getLineLeftOffset: function(lineIndex) {\n var lineWidth = this.getLineWidth(lineIndex);\n if (this.textAlign === 'center') {\n return (this.width - lineWidth) / 2;\n }\n if (this.textAlign === 'right') {\n return this.width - lineWidth;\n }\n if (this.textAlign === 'justify-center' && this.isEndOfWrapping(lineIndex)) {\n return (this.width - lineWidth) / 2;\n }\n if (this.textAlign === 'justify-right' && this.isEndOfWrapping(lineIndex)) {\n return this.width - lineWidth;\n }\n return 0;\n },\n\n /**\n * @private\n */\n _clearCache: function() {\n this.__lineWidths = [];\n this.__lineHeights = [];\n this.__charBounds = [];\n },\n\n /**\n * @private\n */\n _shouldClearDimensionCache: function() {\n var shouldClear = this._forceClearCache;\n shouldClear || (shouldClear = this.hasStateChanged('_dimensionAffectingProps'));\n if (shouldClear) {\n this.dirty = true;\n this._forceClearCache = false;\n }\n return shouldClear;\n },\n\n /**\n * Measure a single line given its index. Used to calculate the initial\n * text bounding box. The values are calculated and stored in __lineWidths cache.\n * @private\n * @param {Number} lineIndex line number\n * @return {Number} Line width\n */\n getLineWidth: function(lineIndex) {\n if (this.__lineWidths[lineIndex]) {\n return this.__lineWidths[lineIndex];\n }\n\n var width, line = this._textLines[lineIndex], lineInfo;\n\n if (line === '') {\n width = 0;\n }\n else {\n lineInfo = this.measureLine(lineIndex);\n width = lineInfo.width;\n }\n this.__lineWidths[lineIndex] = width;\n return width;\n },\n\n _getWidthOfCharSpacing: function() {\n if (this.charSpacing !== 0) {\n return this.fontSize * this.charSpacing / 1000;\n }\n return 0;\n },\n\n /**\n * Retrieves the value of property at given character position\n * @param {Number} lineIndex the line number\n * @param {Number} charIndex the charater number\n * @param {String} property the property name\n * @returns the value of 'property'\n */\n getValueOfPropertyAt: function(lineIndex, charIndex, property) {\n var charStyle = this._getStyleDeclaration(lineIndex, charIndex);\n if (charStyle && typeof charStyle[property] !== 'undefined') {\n return charStyle[property];\n }\n return this[property];\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _renderTextDecoration: function(ctx, type) {\n if (!this[type] && !this.styleHas(type)) {\n return;\n }\n var heightOfLine, size, _size,\n lineLeftOffset, dy, _dy,\n line, lastDecoration,\n leftOffset = this._getLeftOffset(),\n topOffset = this._getTopOffset(), top,\n boxStart, boxWidth, charBox, currentDecoration,\n maxHeight, currentFill, lastFill,\n charSpacing = this._getWidthOfCharSpacing();\n\n for (var i = 0, len = this._textLines.length; i < len; i++) {\n heightOfLine = this.getHeightOfLine(i);\n if (!this[type] && !this.styleHas(type, i)) {\n topOffset += heightOfLine;\n continue;\n }\n line = this._textLines[i];\n maxHeight = heightOfLine / this.lineHeight;\n lineLeftOffset = this._getLineLeftOffset(i);\n boxStart = 0;\n boxWidth = 0;\n lastDecoration = this.getValueOfPropertyAt(i, 0, type);\n lastFill = this.getValueOfPropertyAt(i, 0, 'fill');\n top = topOffset + maxHeight * (1 - this._fontSizeFraction);\n size = this.getHeightOfChar(i, 0);\n dy = this.getValueOfPropertyAt(i, 0, 'deltaY');\n for (var j = 0, jlen = line.length; j < jlen; j++) {\n charBox = this.__charBounds[i][j];\n currentDecoration = this.getValueOfPropertyAt(i, j, type);\n currentFill = this.getValueOfPropertyAt(i, j, 'fill');\n _size = this.getHeightOfChar(i, j);\n _dy = this.getValueOfPropertyAt(i, j, 'deltaY');\n if ((currentDecoration !== lastDecoration || currentFill !== lastFill || _size !== size || _dy !== dy) &&\n boxWidth > 0) {\n ctx.fillStyle = lastFill;\n lastDecoration && lastFill && ctx.fillRect(\n leftOffset + lineLeftOffset + boxStart,\n top + this.offsets[type] * size + dy,\n boxWidth,\n this.fontSize / 15\n );\n boxStart = charBox.left;\n boxWidth = charBox.width;\n lastDecoration = currentDecoration;\n lastFill = currentFill;\n size = _size;\n dy = _dy;\n }\n else {\n boxWidth += charBox.kernedWidth;\n }\n }\n ctx.fillStyle = currentFill;\n currentDecoration && currentFill && ctx.fillRect(\n leftOffset + lineLeftOffset + boxStart,\n top + this.offsets[type] * size + dy,\n boxWidth - charSpacing,\n this.fontSize / 15\n );\n topOffset += heightOfLine;\n }\n // if there is text background color no\n // other shadows should be casted\n this._removeShadow(ctx);\n },\n\n /**\n * return font declaration string for canvas context\n * @param {Object} [styleObject] object\n * @returns {String} font declaration formatted for canvas context.\n */\n _getFontDeclaration: function(styleObject, forMeasuring) {\n var style = styleObject || this, family = this.fontFamily,\n fontIsGeneric = fabric.Text.genericFonts.indexOf(family.toLowerCase()) > -1;\n var fontFamily = family === undefined ||\n family.indexOf('\\'') > -1 || family.indexOf(',') > -1 ||\n family.indexOf('\"') > -1 || fontIsGeneric\n ? style.fontFamily : '\"' + style.fontFamily + '\"';\n return [\n // node-canvas needs \"weight style\", while browsers need \"style weight\"\n // verify if this can be fixed in JSDOM\n (fabric.isLikelyNode ? style.fontWeight : style.fontStyle),\n (fabric.isLikelyNode ? style.fontStyle : style.fontWeight),\n forMeasuring ? this.CACHE_FONT_SIZE + 'px' : style.fontSize + 'px',\n fontFamily\n ].join(' ');\n },\n\n /**\n * Renders text instance on a specified context\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n render: function(ctx) {\n // do not render if object is not visible\n if (!this.visible) {\n return;\n }\n if (this.canvas && this.canvas.skipOffscreen && !this.group && !this.isOnScreen()) {\n return;\n }\n if (this._shouldClearDimensionCache()) {\n this.initDimensions();\n }\n this.callSuper('render', ctx);\n },\n\n /**\n * Returns the text as an array of lines.\n * @param {String} text text to split\n * @returns {Array} Lines in the text\n */\n _splitTextIntoLines: function(text) {\n var lines = text.split(this._reNewline),\n newLines = new Array(lines.length),\n newLine = ['\\n'],\n newText = [];\n for (var i = 0; i < lines.length; i++) {\n newLines[i] = fabric.util.string.graphemeSplit(lines[i]);\n newText = newText.concat(newLines[i], newLine);\n }\n newText.pop();\n return { _unwrappedLines: newLines, lines: lines, graphemeText: newText, graphemeLines: newLines };\n },\n\n /**\n * Returns object representation of an instance\n * @param {Array} [propertiesToInclude] Any properties that you might want to additionally include in the output\n * @return {Object} Object representation of an instance\n */\n toObject: function(propertiesToInclude) {\n var additionalProperties = [\n 'text',\n 'fontSize',\n 'fontWeight',\n 'fontFamily',\n 'fontStyle',\n 'lineHeight',\n 'underline',\n 'overline',\n 'linethrough',\n 'textAlign',\n 'textBackgroundColor',\n 'charSpacing',\n ].concat(propertiesToInclude);\n var obj = this.callSuper('toObject', additionalProperties);\n obj.styles = clone(this.styles, true);\n return obj;\n },\n\n /**\n * Sets property to a given value. When changing position/dimension -related properties (left, top, scale, angle, etc.) `set` does not update position of object's borders/controls. If you need to update those, call `setCoords()`.\n * @param {String|Object} key Property name or object (if object, iterate over the object properties)\n * @param {Object|Function} value Property value (if function, the value is passed into it and its return value is used as a new one)\n * @return {fabric.Object} thisArg\n * @chainable\n */\n set: function(key, value) {\n this.callSuper('set', key, value);\n var needsDims = false;\n if (typeof key === 'object') {\n for (var _key in key) {\n needsDims = needsDims || this._dimensionAffectingProps.indexOf(_key) !== -1;\n }\n }\n else {\n needsDims = this._dimensionAffectingProps.indexOf(key) !== -1;\n }\n if (needsDims) {\n this.initDimensions();\n this.setCoords();\n }\n return this;\n },\n\n /**\n * Returns complexity of an instance\n * @return {Number} complexity\n */\n complexity: function() {\n return 1;\n }\n });\n\n /* _FROM_SVG_START_ */\n /**\n * List of attribute names to account for when parsing SVG element (used by {@link fabric.Text.fromElement})\n * @static\n * @memberOf fabric.Text\n * @see: http://www.w3.org/TR/SVG/text.html#TextElement\n */\n fabric.Text.ATTRIBUTE_NAMES = fabric.SHARED_ATTRIBUTES.concat(\n 'x y dx dy font-family font-style font-weight font-size letter-spacing text-decoration text-anchor'.split(' '));\n\n /**\n * Default SVG font size\n * @static\n * @memberOf fabric.Text\n */\n fabric.Text.DEFAULT_SVG_FONT_SIZE = 16;\n\n /**\n * Returns fabric.Text instance from an SVG element (not yet implemented)\n * @static\n * @memberOf fabric.Text\n * @param {SVGElement} element Element to parse\n * @param {Function} callback callback function invoked after parsing\n * @param {Object} [options] Options object\n */\n fabric.Text.fromElement = function(element, callback, options) {\n if (!element) {\n return callback(null);\n }\n\n var parsedAttributes = fabric.parseAttributes(element, fabric.Text.ATTRIBUTE_NAMES),\n parsedAnchor = parsedAttributes.textAnchor || 'left';\n options = fabric.util.object.extend((options ? clone(options) : { }), parsedAttributes);\n\n options.top = options.top || 0;\n options.left = options.left || 0;\n if (parsedAttributes.textDecoration) {\n var textDecoration = parsedAttributes.textDecoration;\n if (textDecoration.indexOf('underline') !== -1) {\n options.underline = true;\n }\n if (textDecoration.indexOf('overline') !== -1) {\n options.overline = true;\n }\n if (textDecoration.indexOf('line-through') !== -1) {\n options.linethrough = true;\n }\n delete options.textDecoration;\n }\n if ('dx' in parsedAttributes) {\n options.left += parsedAttributes.dx;\n }\n if ('dy' in parsedAttributes) {\n options.top += parsedAttributes.dy;\n }\n if (!('fontSize' in options)) {\n options.fontSize = fabric.Text.DEFAULT_SVG_FONT_SIZE;\n }\n\n var textContent = '';\n\n // The XML is not properly parsed in IE9 so a workaround to get\n // textContent is through firstChild.data. Another workaround would be\n // to convert XML loaded from a file to be converted using DOMParser (same way loadSVGFromString() does)\n if (!('textContent' in element)) {\n if ('firstChild' in element && element.firstChild !== null) {\n if ('data' in element.firstChild && element.firstChild.data !== null) {\n textContent = element.firstChild.data;\n }\n }\n }\n else {\n textContent = element.textContent;\n }\n\n textContent = textContent.replace(/^\\s+|\\s+$|\\n+/g, '').replace(/\\s+/g, ' ');\n var originalStrokeWidth = options.strokeWidth;\n options.strokeWidth = 0;\n\n var text = new fabric.Text(textContent, options),\n textHeightScaleFactor = text.getScaledHeight() / text.height,\n lineHeightDiff = (text.height + text.strokeWidth) * text.lineHeight - text.height,\n scaledDiff = lineHeightDiff * textHeightScaleFactor,\n textHeight = text.getScaledHeight() + scaledDiff,\n offX = 0;\n /*\n Adjust positioning:\n x/y attributes in SVG correspond to the bottom-left corner of text bounding box\n fabric output by default at top, left.\n */\n if (parsedAnchor === 'center') {\n offX = text.getScaledWidth() / 2;\n }\n if (parsedAnchor === 'right') {\n offX = text.getScaledWidth();\n }\n text.set({\n left: text.left - offX,\n top: text.top - (textHeight - text.fontSize * (0.07 + text._fontSizeFraction)) / text.lineHeight,\n strokeWidth: typeof originalStrokeWidth !== 'undefined' ? originalStrokeWidth : 1,\n });\n callback(text);\n };\n /* _FROM_SVG_END_ */\n\n /**\n * Returns fabric.Text instance from an object representation\n * @static\n * @memberOf fabric.Text\n * @param {Object} object Object to create an instance from\n * @param {Function} [callback] Callback to invoke when an fabric.Text instance is created\n */\n fabric.Text.fromObject = function(object, callback) {\n return fabric.Object._fromObject('Text', object, callback, 'text');\n };\n\n fabric.Text.genericFonts = ['sans-serif', 'serif', 'cursive', 'fantasy', 'monospace'];\n\n fabric.util.createAccessors && fabric.util.createAccessors(fabric.Text);\n\n})(typeof exports !== 'undefined' ? exports : this);\n\n\n(function() {\n fabric.util.object.extend(fabric.Text.prototype, /** @lends fabric.Text.prototype */ {\n /**\n * Returns true if object has no styling or no styling in a line\n * @param {Number} lineIndex , lineIndex is on wrapped lines.\n * @return {Boolean}\n */\n isEmptyStyles: function(lineIndex) {\n if (!this.styles) {\n return true;\n }\n if (typeof lineIndex !== 'undefined' && !this.styles[lineIndex]) {\n return true;\n }\n var obj = typeof lineIndex === 'undefined' ? this.styles : { line: this.styles[lineIndex] };\n for (var p1 in obj) {\n for (var p2 in obj[p1]) {\n // eslint-disable-next-line no-unused-vars\n for (var p3 in obj[p1][p2]) {\n return false;\n }\n }\n }\n return true;\n },\n\n /**\n * Returns true if object has a style property or has it ina specified line\n * This function is used to detect if a text will use a particular property or not.\n * @param {String} property to check for\n * @param {Number} lineIndex to check the style on\n * @return {Boolean}\n */\n styleHas: function(property, lineIndex) {\n if (!this.styles || !property || property === '') {\n return false;\n }\n if (typeof lineIndex !== 'undefined' && !this.styles[lineIndex]) {\n return false;\n }\n var obj = typeof lineIndex === 'undefined' ? this.styles : { 0: this.styles[lineIndex] };\n // eslint-disable-next-line\n for (var p1 in obj) {\n // eslint-disable-next-line\n for (var p2 in obj[p1]) {\n if (typeof obj[p1][p2][property] !== 'undefined') {\n return true;\n }\n }\n }\n return false;\n },\n\n /**\n * Check if characters in a text have a value for a property\n * whose value matches the textbox's value for that property. If so,\n * the character-level property is deleted. If the character\n * has no other properties, then it is also deleted. Finally,\n * if the line containing that character has no other characters\n * then it also is deleted.\n *\n * @param {string} property The property to compare between characters and text.\n */\n cleanStyle: function(property) {\n if (!this.styles || !property || property === '') {\n return false;\n }\n var obj = this.styles, stylesCount = 0, letterCount, stylePropertyValue,\n allStyleObjectPropertiesMatch = true, graphemeCount = 0, styleObject;\n // eslint-disable-next-line\n for (var p1 in obj) {\n letterCount = 0;\n // eslint-disable-next-line\n for (var p2 in obj[p1]) {\n var styleObject = obj[p1][p2],\n stylePropertyHasBeenSet = styleObject.hasOwnProperty(property);\n\n stylesCount++;\n\n if (stylePropertyHasBeenSet) {\n if (!stylePropertyValue) {\n stylePropertyValue = styleObject[property];\n }\n else if (styleObject[property] !== stylePropertyValue) {\n allStyleObjectPropertiesMatch = false;\n }\n\n if (styleObject[property] === this[property]) {\n delete styleObject[property];\n }\n }\n else {\n allStyleObjectPropertiesMatch = false;\n }\n\n if (Object.keys(styleObject).length !== 0) {\n letterCount++;\n }\n else {\n delete obj[p1][p2];\n }\n }\n\n if (letterCount === 0) {\n delete obj[p1];\n }\n }\n // if every grapheme has the same style set then\n // delete those styles and set it on the parent\n for (var i = 0; i < this._textLines.length; i++) {\n graphemeCount += this._textLines[i].length;\n }\n if (allStyleObjectPropertiesMatch && stylesCount === graphemeCount) {\n this[property] = stylePropertyValue;\n this.removeStyle(property);\n }\n },\n\n /**\n * Remove a style property or properties from all individual character styles\n * in a text object. Deletes the character style object if it contains no other style\n * props. Deletes a line style object if it contains no other character styles.\n *\n * @param {String} props The property to remove from character styles.\n */\n removeStyle: function(property) {\n if (!this.styles || !property || property === '') {\n return;\n }\n var obj = this.styles, line, lineNum, charNum;\n for (lineNum in obj) {\n line = obj[lineNum];\n for (charNum in line) {\n delete line[charNum][property];\n if (Object.keys(line[charNum]).length === 0) {\n delete line[charNum];\n }\n }\n if (Object.keys(line).length === 0) {\n delete obj[lineNum];\n }\n }\n },\n\n /**\n * @private\n */\n _extendStyles: function(index, styles) {\n var loc = this.get2DCursorLocation(index);\n\n if (!this._getLineStyle(loc.lineIndex)) {\n this._setLineStyle(loc.lineIndex);\n }\n\n if (!this._getStyleDeclaration(loc.lineIndex, loc.charIndex)) {\n this._setStyleDeclaration(loc.lineIndex, loc.charIndex, {});\n }\n\n fabric.util.object.extend(this._getStyleDeclaration(loc.lineIndex, loc.charIndex), styles);\n },\n\n /**\n * Returns 2d representation (lineIndex and charIndex) of cursor (or selection start)\n * @param {Number} [selectionStart] Optional index. When not given, current selectionStart is used.\n * @param {Boolean} [skipWrapping] consider the location for unwrapped lines. usefull to manage styles.\n */\n get2DCursorLocation: function(selectionStart, skipWrapping) {\n if (typeof selectionStart === 'undefined') {\n selectionStart = this.selectionStart;\n }\n var lines = skipWrapping ? this._unwrappedTextLines : this._textLines,\n len = lines.length;\n for (var i = 0; i < len; i++) {\n if (selectionStart <= lines[i].length) {\n return {\n lineIndex: i,\n charIndex: selectionStart\n };\n }\n selectionStart -= lines[i].length + this.missingNewlineOffset(i);\n }\n return {\n lineIndex: i - 1,\n charIndex: lines[i - 1].length < selectionStart ? lines[i - 1].length : selectionStart\n };\n },\n\n /**\n * Gets style of a current selection/cursor (at the start position)\n * if startIndex or endIndex are not provided, slectionStart or selectionEnd will be used.\n * @param {Number} [startIndex] Start index to get styles at\n * @param {Number} [endIndex] End index to get styles at, if not specified selectionEnd or startIndex + 1\n * @param {Boolean} [complete] get full style or not\n * @return {Array} styles an array with one, zero or more Style objects\n */\n getSelectionStyles: function(startIndex, endIndex, complete) {\n if (typeof startIndex === 'undefined') {\n startIndex = this.selectionStart || 0;\n }\n if (typeof endIndex === 'undefined') {\n endIndex = this.selectionEnd || startIndex;\n }\n var styles = [];\n for (var i = startIndex; i < endIndex; i++) {\n styles.push(this.getStyleAtPosition(i, complete));\n }\n return styles;\n },\n\n /**\n * Gets style of a current selection/cursor position\n * @param {Number} position to get styles at\n * @param {Boolean} [complete] full style if true\n * @return {Object} style Style object at a specified index\n * @private\n */\n getStyleAtPosition: function(position, complete) {\n var loc = this.get2DCursorLocation(position),\n style = complete ? this.getCompleteStyleDeclaration(loc.lineIndex, loc.charIndex) :\n this._getStyleDeclaration(loc.lineIndex, loc.charIndex);\n return style || {};\n },\n\n /**\n * Sets style of a current selection, if no selection exist, do not set anything.\n * @param {Object} [styles] Styles object\n * @param {Number} [startIndex] Start index to get styles at\n * @param {Number} [endIndex] End index to get styles at, if not specified selectionEnd or startIndex + 1\n * @return {fabric.IText} thisArg\n * @chainable\n */\n setSelectionStyles: function(styles, startIndex, endIndex) {\n if (typeof startIndex === 'undefined') {\n startIndex = this.selectionStart || 0;\n }\n if (typeof endIndex === 'undefined') {\n endIndex = this.selectionEnd || startIndex;\n }\n for (var i = startIndex; i < endIndex; i++) {\n this._extendStyles(i, styles);\n }\n /* not included in _extendStyles to avoid clearing cache more than once */\n this._forceClearCache = true;\n return this;\n },\n\n /**\n * get the reference, not a clone, of the style object for a given character\n * @param {Number} lineIndex\n * @param {Number} charIndex\n * @return {Object} style object\n */\n _getStyleDeclaration: function(lineIndex, charIndex) {\n var lineStyle = this.styles && this.styles[lineIndex];\n if (!lineStyle) {\n return null;\n }\n return lineStyle[charIndex];\n },\n\n /**\n * return a new object that contains all the style property for a character\n * the object returned is newly created\n * @param {Number} lineIndex of the line where the character is\n * @param {Number} charIndex position of the character on the line\n * @return {Object} style object\n */\n getCompleteStyleDeclaration: function(lineIndex, charIndex) {\n var style = this._getStyleDeclaration(lineIndex, charIndex) || { },\n styleObject = { }, prop;\n for (var i = 0; i < this._styleProperties.length; i++) {\n prop = this._styleProperties[i];\n styleObject[prop] = typeof style[prop] === 'undefined' ? this[prop] : style[prop];\n }\n return styleObject;\n },\n\n /**\n * @param {Number} lineIndex\n * @param {Number} charIndex\n * @param {Object} style\n * @private\n */\n _setStyleDeclaration: function(lineIndex, charIndex, style) {\n this.styles[lineIndex][charIndex] = style;\n },\n\n /**\n *\n * @param {Number} lineIndex\n * @param {Number} charIndex\n * @private\n */\n _deleteStyleDeclaration: function(lineIndex, charIndex) {\n delete this.styles[lineIndex][charIndex];\n },\n\n /**\n * @param {Number} lineIndex\n * @return {Boolean} if the line exists or not\n * @private\n */\n _getLineStyle: function(lineIndex) {\n return !!this.styles[lineIndex];\n },\n\n /**\n * Set the line style to an empty object so that is initialized\n * @param {Number} lineIndex\n * @private\n */\n _setLineStyle: function(lineIndex) {\n this.styles[lineIndex] = {};\n },\n\n /**\n * @param {Number} lineIndex\n * @private\n */\n _deleteLineStyle: function(lineIndex) {\n delete this.styles[lineIndex];\n }\n });\n})();\n\n\n(function() {\n\n function parseDecoration(object) {\n if (object.textDecoration) {\n object.textDecoration.indexOf('underline') > -1 && (object.underline = true);\n object.textDecoration.indexOf('line-through') > -1 && (object.linethrough = true);\n object.textDecoration.indexOf('overline') > -1 && (object.overline = true);\n delete object.textDecoration;\n }\n }\n\n /**\n * IText class (introduced in v1.4) Events are also fired with \"text:\"\n * prefix when observing canvas.\n * @class fabric.IText\n * @extends fabric.Text\n * @mixes fabric.Observable\n *\n * @fires changed\n * @fires selection:changed\n * @fires editing:entered\n * @fires editing:exited\n *\n * @return {fabric.IText} thisArg\n * @see {@link fabric.IText#initialize} for constructor definition\n *\n *

Supported key combinations:

\n *
\n   *   Move cursor:                    left, right, up, down\n   *   Select character:               shift + left, shift + right\n   *   Select text vertically:         shift + up, shift + down\n   *   Move cursor by word:            alt + left, alt + right\n   *   Select words:                   shift + alt + left, shift + alt + right\n   *   Move cursor to line start/end:  cmd + left, cmd + right or home, end\n   *   Select till start/end of line:  cmd + shift + left, cmd + shift + right or shift + home, shift + end\n   *   Jump to start/end of text:      cmd + up, cmd + down\n   *   Select till start/end of text:  cmd + shift + up, cmd + shift + down or shift + pgUp, shift + pgDown\n   *   Delete character:               backspace\n   *   Delete word:                    alt + backspace\n   *   Delete line:                    cmd + backspace\n   *   Forward delete:                 delete\n   *   Copy text:                      ctrl/cmd + c\n   *   Paste text:                     ctrl/cmd + v\n   *   Cut text:                       ctrl/cmd + x\n   *   Select entire text:             ctrl/cmd + a\n   *   Quit editing                    tab or esc\n   * 
\n *\n *

Supported mouse/touch combination

\n *
\n   *   Position cursor:                click/touch\n   *   Create selection:               click/touch & drag\n   *   Create selection:               click & shift + click\n   *   Select word:                    double click\n   *   Select line:                    triple click\n   * 
\n */\n fabric.IText = fabric.util.createClass(fabric.Text, fabric.Observable, /** @lends fabric.IText.prototype */ {\n\n /**\n * Type of an object\n * @type String\n * @default\n */\n type: 'i-text',\n\n /**\n * Index where text selection starts (or where cursor is when there is no selection)\n * @type Number\n * @default\n */\n selectionStart: 0,\n\n /**\n * Index where text selection ends\n * @type Number\n * @default\n */\n selectionEnd: 0,\n\n /**\n * Color of text selection\n * @type String\n * @default\n */\n selectionColor: 'rgba(17,119,255,0.3)',\n\n /**\n * Indicates whether text is in editing mode\n * @type Boolean\n * @default\n */\n isEditing: false,\n\n /**\n * Indicates whether a text can be edited\n * @type Boolean\n * @default\n */\n editable: true,\n\n /**\n * Border color of text object while it's in editing mode\n * @type String\n * @default\n */\n editingBorderColor: 'rgba(102,153,255,0.25)',\n\n /**\n * Width of cursor (in px)\n * @type Number\n * @default\n */\n cursorWidth: 2,\n\n /**\n * Color of default cursor (when not overwritten by character style)\n * @type String\n * @default\n */\n cursorColor: '#333',\n\n /**\n * Delay between cursor blink (in ms)\n * @type Number\n * @default\n */\n cursorDelay: 1000,\n\n /**\n * Duration of cursor fadein (in ms)\n * @type Number\n * @default\n */\n cursorDuration: 600,\n\n /**\n * Indicates whether internal text char widths can be cached\n * @type Boolean\n * @default\n */\n caching: true,\n\n /**\n * @private\n */\n _reSpace: /\\s|\\n/,\n\n /**\n * @private\n */\n _currentCursorOpacity: 0,\n\n /**\n * @private\n */\n _selectionDirection: null,\n\n /**\n * @private\n */\n _abortCursorAnimation: false,\n\n /**\n * @private\n */\n __widthOfSpace: [],\n\n /**\n * Helps determining when the text is in composition, so that the cursor\n * rendering is altered.\n */\n inCompositionMode: false,\n\n /**\n * Constructor\n * @param {String} text Text string\n * @param {Object} [options] Options object\n * @return {fabric.IText} thisArg\n */\n initialize: function(text, options) {\n this.callSuper('initialize', text, options);\n this.initBehavior();\n },\n\n /**\n * Sets selection start (left boundary of a selection)\n * @param {Number} index Index to set selection start to\n */\n setSelectionStart: function(index) {\n index = Math.max(index, 0);\n this._updateAndFire('selectionStart', index);\n },\n\n /**\n * Sets selection end (right boundary of a selection)\n * @param {Number} index Index to set selection end to\n */\n setSelectionEnd: function(index) {\n index = Math.min(index, this.text.length);\n this._updateAndFire('selectionEnd', index);\n },\n\n /**\n * @private\n * @param {String} property 'selectionStart' or 'selectionEnd'\n * @param {Number} index new position of property\n */\n _updateAndFire: function(property, index) {\n if (this[property] !== index) {\n this._fireSelectionChanged();\n this[property] = index;\n }\n this._updateTextarea();\n },\n\n /**\n * Fires the even of selection changed\n * @private\n */\n _fireSelectionChanged: function() {\n this.fire('selection:changed');\n this.canvas && this.canvas.fire('text:selection:changed', { target: this });\n },\n\n /**\n * Initialize text dimensions. Render all text on given context\n * or on a offscreen canvas to get the text width with measureText.\n * Updates this.width and this.height with the proper values.\n * Does not return dimensions.\n * @private\n */\n initDimensions: function() {\n this.isEditing && this.initDelayedCursor();\n this.clearContextTop();\n this.callSuper('initDimensions');\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n render: function(ctx) {\n this.clearContextTop();\n this.callSuper('render', ctx);\n // clear the cursorOffsetCache, so we ensure to calculate once per renderCursor\n // the correct position but not at every cursor animation.\n this.cursorOffsetCache = { };\n this.renderCursorOrSelection();\n },\n\n /**\n * @private\n * @param {CanvasRenderingContext2D} ctx Context to render on\n */\n _render: function(ctx) {\n this.callSuper('_render', ctx);\n },\n\n /**\n * Prepare and clean the contextTop\n */\n clearContextTop: function(skipRestore) {\n if (!this.isEditing || !this.canvas || !this.canvas.contextTop) {\n return;\n }\n var ctx = this.canvas.contextTop, v = this.canvas.viewportTransform;\n ctx.save();\n ctx.transform(v[0], v[1], v[2], v[3], v[4], v[5]);\n this.transform(ctx);\n this.transformMatrix && ctx.transform.apply(ctx, this.transformMatrix);\n this._clearTextArea(ctx);\n skipRestore || ctx.restore();\n },\n\n /**\n * Renders cursor or selection (depending on what exists)\n * it does on the contextTop. If contextTop is not available, do nothing.\n */\n renderCursorOrSelection: function() {\n if (!this.isEditing || !this.canvas || !this.canvas.contextTop) {\n return;\n }\n var boundaries = this._getCursorBoundaries(),\n ctx = this.canvas.contextTop;\n this.clearContextTop(true);\n if (this.selectionStart === this.selectionEnd) {\n this.renderCursor(boundaries, ctx);\n }\n else {\n this.renderSelection(boundaries, ctx);\n }\n ctx.restore();\n },\n\n _clearTextArea: function(ctx) {\n // we add 4 pixel, to be sure to do not leave any pixel out\n var width = this.width + 4, height = this.height + 4;\n ctx.clearRect(-width / 2, -height / 2, width, height);\n },\n\n /**\n * Returns cursor boundaries (left, top, leftOffset, topOffset)\n * @private\n * @param {Array} chars Array of characters\n * @param {String} typeOfBoundaries\n */\n _getCursorBoundaries: function(position) {\n\n // left/top are left/top of entire text box\n // leftOffset/topOffset are offset from that left/top point of a text box\n\n if (typeof position === 'undefined') {\n position = this.selectionStart;\n }\n\n var left = this._getLeftOffset(),\n top = this._getTopOffset(),\n offsets = this._getCursorBoundariesOffsets(position);\n\n return {\n left: left,\n top: top,\n leftOffset: offsets.left,\n topOffset: offsets.top\n };\n },\n\n /**\n * @private\n */\n _getCursorBoundariesOffsets: function(position) {\n if (this.cursorOffsetCache && 'top' in this.cursorOffsetCache) {\n return this.cursorOffsetCache;\n }\n var lineLeftOffset,\n lineIndex,\n charIndex,\n topOffset = 0,\n leftOffset = 0,\n boundaries,\n cursorPosition = this.get2DCursorLocation(position);\n charIndex = cursorPosition.charIndex;\n lineIndex = cursorPosition.lineIndex;\n for (var i = 0; i < lineIndex; i++) {\n topOffset += this.getHeightOfLine(i);\n }\n lineLeftOffset = this._getLineLeftOffset(lineIndex);\n var bound = this.__charBounds[lineIndex][charIndex];\n bound && (leftOffset = bound.left);\n if (this.charSpacing !== 0 && charIndex === this._textLines[lineIndex].length) {\n leftOffset -= this._getWidthOfCharSpacing();\n }\n boundaries = {\n top: topOffset,\n left: lineLeftOffset + (leftOffset > 0 ? leftOffset : 0),\n };\n this.cursorOffsetCache = boundaries;\n return this.cursorOffsetCache;\n },\n\n /**\n * Renders cursor\n * @param {Object} boundaries\n * @param {CanvasRenderingContext2D} ctx transformed context to draw on\n */\n renderCursor: function(boundaries, ctx) {\n var cursorLocation = this.get2DCursorLocation(),\n lineIndex = cursorLocation.lineIndex,\n charIndex = cursorLocation.charIndex > 0 ? cursorLocation.charIndex - 1 : 0,\n charHeight = this.getValueOfPropertyAt(lineIndex, charIndex, 'fontSize'),\n multiplier = this.scaleX * this.canvas.getZoom(),\n cursorWidth = this.cursorWidth / multiplier,\n topOffset = boundaries.topOffset,\n dy = this.getValueOfPropertyAt(lineIndex, charIndex, 'deltaY');\n\n topOffset += (1 - this._fontSizeFraction) * this.getHeightOfLine(lineIndex) / this.lineHeight\n - charHeight * (1 - this._fontSizeFraction);\n\n if (this.inCompositionMode) {\n this.renderSelection(boundaries, ctx);\n }\n\n ctx.fillStyle = this.getValueOfPropertyAt(lineIndex, charIndex, 'fill');\n ctx.globalAlpha = this.__isMousedown ? 1 : this._currentCursorOpacity;\n ctx.fillRect(\n boundaries.left + boundaries.leftOffset - cursorWidth / 2,\n topOffset + boundaries.top + dy,\n cursorWidth,\n charHeight);\n },\n\n /**\n * Renders text selection\n * @param {Object} boundaries Object with left/top/leftOffset/topOffset\n * @param {CanvasRenderingContext2D} ctx transformed context to draw on\n */\n renderSelection: function(boundaries, ctx) {\n\n var selectionStart = this.inCompositionMode ? this.hiddenTextarea.selectionStart : this.selectionStart,\n selectionEnd = this.inCompositionMode ? this.hiddenTextarea.selectionEnd : this.selectionEnd,\n isJustify = this.textAlign.indexOf('justify') !== -1,\n start = this.get2DCursorLocation(selectionStart),\n end = this.get2DCursorLocation(selectionEnd),\n startLine = start.lineIndex,\n endLine = end.lineIndex,\n startChar = start.charIndex < 0 ? 0 : start.charIndex,\n endChar = end.charIndex < 0 ? 0 : end.charIndex;\n\n for (var i = startLine; i <= endLine; i++) {\n var lineOffset = this._getLineLeftOffset(i) || 0,\n lineHeight = this.getHeightOfLine(i),\n realLineHeight = 0, boxStart = 0, boxEnd = 0;\n\n if (i === startLine) {\n boxStart = this.__charBounds[startLine][startChar].left;\n }\n if (i >= startLine && i < endLine) {\n boxEnd = isJustify && !this.isEndOfWrapping(i) ? this.width : this.getLineWidth(i) || 5; // WTF is this 5?\n }\n else if (i === endLine) {\n if (endChar === 0) {\n boxEnd = this.__charBounds[endLine][endChar].left;\n }\n else {\n var charSpacing = this._getWidthOfCharSpacing();\n boxEnd = this.__charBounds[endLine][endChar - 1].left\n + this.__charBounds[endLine][endChar - 1].width - charSpacing;\n }\n }\n realLineHeight = lineHeight;\n if (this.lineHeight < 1 || (i === endLine && this.lineHeight > 1)) {\n lineHeight /= this.lineHeight;\n }\n if (this.inCompositionMode) {\n ctx.fillStyle = this.compositionColor || 'black';\n ctx.fillRect(\n boundaries.left + lineOffset + boxStart,\n boundaries.top + boundaries.topOffset + lineHeight,\n boxEnd - boxStart,\n 1);\n }\n else {\n ctx.fillStyle = this.selectionColor;\n ctx.fillRect(\n boundaries.left + lineOffset + boxStart,\n boundaries.top + boundaries.topOffset,\n boxEnd - boxStart,\n lineHeight);\n }\n\n\n boundaries.topOffset += realLineHeight;\n }\n },\n\n /**\n * High level function to know the height of the cursor.\n * the currentChar is the one that precedes the cursor\n * Returns fontSize of char at the current cursor\n * Unused from the library, is for the end user\n * @return {Number} Character font size\n */\n getCurrentCharFontSize: function() {\n var cp = this._getCurrentCharIndex();\n return this.getValueOfPropertyAt(cp.l, cp.c, 'fontSize');\n },\n\n /**\n * High level function to know the color of the cursor.\n * the currentChar is the one that precedes the cursor\n * Returns color (fill) of char at the current cursor\n * Unused from the library, is for the end user\n * @return {String} Character color (fill)\n */\n getCurrentCharColor: function() {\n var cp = this._getCurrentCharIndex();\n return this.getValueOfPropertyAt(cp.l, cp.c, 'fill');\n },\n\n /**\n * Returns the cursor position for the getCurrent.. functions\n * @private\n */\n _getCurrentCharIndex: function() {\n var cursorPosition = this.get2DCursorLocation(this.selectionStart, true),\n charIndex = cursorPosition.charIndex > 0 ? cursorPosition.charIndex - 1 : 0;\n return { l: cursorPosition.lineIndex, c: charIndex };\n }\n });\n\n /**\n * Returns fabric.IText instance from an object representation\n * @static\n * @memberOf fabric.IText\n * @param {Object} object Object to create an instance from\n * @param {function} [callback] invoked with new instance as argument\n */\n fabric.IText.fromObject = function(object, callback) {\n parseDecoration(object);\n if (object.styles) {\n for (var i in object.styles) {\n for (var j in object.styles[i]) {\n parseDecoration(object.styles[i][j]);\n }\n }\n }\n fabric.Object._fromObject('IText', object, callback, 'text');\n };\n})();\n\n\n(function() {\n\n var clone = fabric.util.object.clone;\n\n fabric.util.object.extend(fabric.IText.prototype, /** @lends fabric.IText.prototype */ {\n\n /**\n * Initializes all the interactive behavior of IText\n */\n initBehavior: function() {\n this.initAddedHandler();\n this.initRemovedHandler();\n this.initCursorSelectionHandlers();\n this.initDoubleClickSimulation();\n this.mouseMoveHandler = this.mouseMoveHandler.bind(this);\n },\n\n onDeselect: function() {\n this.isEditing && this.exitEditing();\n this.selected = false;\n },\n\n /**\n * Initializes \"added\" event handler\n */\n initAddedHandler: function() {\n var _this = this;\n this.on('added', function() {\n var canvas = _this.canvas;\n if (canvas) {\n if (!canvas._hasITextHandlers) {\n canvas._hasITextHandlers = true;\n _this._initCanvasHandlers(canvas);\n }\n canvas._iTextInstances = canvas._iTextInstances || [];\n canvas._iTextInstances.push(_this);\n }\n });\n },\n\n initRemovedHandler: function() {\n var _this = this;\n this.on('removed', function() {\n var canvas = _this.canvas;\n if (canvas) {\n canvas._iTextInstances = canvas._iTextInstances || [];\n fabric.util.removeFromArray(canvas._iTextInstances, _this);\n if (canvas._iTextInstances.length === 0) {\n canvas._hasITextHandlers = false;\n _this._removeCanvasHandlers(canvas);\n }\n }\n });\n },\n\n /**\n * register canvas event to manage exiting on other instances\n * @private\n */\n _initCanvasHandlers: function(canvas) {\n canvas._mouseUpITextHandler = function() {\n if (canvas._iTextInstances) {\n canvas._iTextInstances.forEach(function(obj) {\n obj.__isMousedown = false;\n });\n }\n };\n canvas.on('mouse:up', canvas._mouseUpITextHandler);\n },\n\n /**\n * remove canvas event to manage exiting on other instances\n * @private\n */\n _removeCanvasHandlers: function(canvas) {\n canvas.off('mouse:up', canvas._mouseUpITextHandler);\n },\n\n /**\n * @private\n */\n _tick: function() {\n this._currentTickState = this._animateCursor(this, 1, this.cursorDuration, '_onTickComplete');\n },\n\n /**\n * @private\n */\n _animateCursor: function(obj, targetOpacity, duration, completeMethod) {\n\n var tickState;\n\n tickState = {\n isAborted: false,\n abort: function() {\n this.isAborted = true;\n },\n };\n\n obj.animate('_currentCursorOpacity', targetOpacity, {\n duration: duration,\n onComplete: function() {\n if (!tickState.isAborted) {\n obj[completeMethod]();\n }\n },\n onChange: function() {\n // we do not want to animate a selection, only cursor\n if (obj.canvas && obj.selectionStart === obj.selectionEnd) {\n obj.renderCursorOrSelection();\n }\n },\n abort: function() {\n return tickState.isAborted;\n }\n });\n return tickState;\n },\n\n /**\n * @private\n */\n _onTickComplete: function() {\n\n var _this = this;\n\n if (this._cursorTimeout1) {\n clearTimeout(this._cursorTimeout1);\n }\n this._cursorTimeout1 = setTimeout(function() {\n _this._currentTickCompleteState = _this._animateCursor(_this, 0, this.cursorDuration / 2, '_tick');\n }, 100);\n },\n\n /**\n * Initializes delayed cursor\n */\n initDelayedCursor: function(restart) {\n var _this = this,\n delay = restart ? 0 : this.cursorDelay;\n\n this.abortCursorAnimation();\n this._currentCursorOpacity = 1;\n this._cursorTimeout2 = setTimeout(function() {\n _this._tick();\n }, delay);\n },\n\n /**\n * Aborts cursor animation and clears all timeouts\n */\n abortCursorAnimation: function() {\n var shouldClear = this._currentTickState || this._currentTickCompleteState,\n canvas = this.canvas;\n this._currentTickState && this._currentTickState.abort();\n this._currentTickCompleteState && this._currentTickCompleteState.abort();\n\n clearTimeout(this._cursorTimeout1);\n clearTimeout(this._cursorTimeout2);\n\n this._currentCursorOpacity = 0;\n // to clear just itext area we need to transform the context\n // it may not be worth it\n if (shouldClear && canvas) {\n canvas.clearContext(canvas.contextTop || canvas.contextContainer);\n }\n\n },\n\n /**\n * Selects entire text\n * @return {fabric.IText} thisArg\n * @chainable\n */\n selectAll: function() {\n this.selectionStart = 0;\n this.selectionEnd = this._text.length;\n this._fireSelectionChanged();\n this._updateTextarea();\n return this;\n },\n\n /**\n * Returns selected text\n * @return {String}\n */\n getSelectedText: function() {\n return this._text.slice(this.selectionStart, this.selectionEnd).join('');\n },\n\n /**\n * Find new selection index representing start of current word according to current selection index\n * @param {Number} startFrom Current selection index\n * @return {Number} New selection index\n */\n findWordBoundaryLeft: function(startFrom) {\n var offset = 0, index = startFrom - 1;\n\n // remove space before cursor first\n if (this._reSpace.test(this._text[index])) {\n while (this._reSpace.test(this._text[index])) {\n offset++;\n index--;\n }\n }\n while (/\\S/.test(this._text[index]) && index > -1) {\n offset++;\n index--;\n }\n\n return startFrom - offset;\n },\n\n /**\n * Find new selection index representing end of current word according to current selection index\n * @param {Number} startFrom Current selection index\n * @return {Number} New selection index\n */\n findWordBoundaryRight: function(startFrom) {\n var offset = 0, index = startFrom;\n\n // remove space after cursor first\n if (this._reSpace.test(this._text[index])) {\n while (this._reSpace.test(this._text[index])) {\n offset++;\n index++;\n }\n }\n while (/\\S/.test(this._text[index]) && index < this._text.length) {\n offset++;\n index++;\n }\n\n return startFrom + offset;\n },\n\n /**\n * Find new selection index representing start of current line according to current selection index\n * @param {Number} startFrom Current selection index\n * @return {Number} New selection index\n */\n findLineBoundaryLeft: function(startFrom) {\n var offset = 0, index = startFrom - 1;\n\n while (!/\\n/.test(this._text[index]) && index > -1) {\n offset++;\n index--;\n }\n\n return startFrom - offset;\n },\n\n /**\n * Find new selection index representing end of current line according to current selection index\n * @param {Number} startFrom Current selection index\n * @return {Number} New selection index\n */\n findLineBoundaryRight: function(startFrom) {\n var offset = 0, index = startFrom;\n\n while (!/\\n/.test(this._text[index]) && index < this._text.length) {\n offset++;\n index++;\n }\n\n return startFrom + offset;\n },\n\n /**\n * Finds index corresponding to beginning or end of a word\n * @param {Number} selectionStart Index of a character\n * @param {Number} direction 1 or -1\n * @return {Number} Index of the beginning or end of a word\n */\n searchWordBoundary: function(selectionStart, direction) {\n var text = this._text,\n index = this._reSpace.test(text[selectionStart]) ? selectionStart - 1 : selectionStart,\n _char = text[index],\n // wrong\n reNonWord = fabric.reNonWord;\n\n while (!reNonWord.test(_char) && index > 0 && index < text.length) {\n index += direction;\n _char = text[index];\n }\n if (reNonWord.test(_char)) {\n index += direction === 1 ? 0 : 1;\n }\n return index;\n },\n\n /**\n * Selects a word based on the index\n * @param {Number} selectionStart Index of a character\n */\n selectWord: function(selectionStart) {\n selectionStart = selectionStart || this.selectionStart;\n var newSelectionStart = this.searchWordBoundary(selectionStart, -1), /* search backwards */\n newSelectionEnd = this.searchWordBoundary(selectionStart, 1); /* search forward */\n\n this.selectionStart = newSelectionStart;\n this.selectionEnd = newSelectionEnd;\n this._fireSelectionChanged();\n this._updateTextarea();\n this.renderCursorOrSelection();\n },\n\n /**\n * Selects a line based on the index\n * @param {Number} selectionStart Index of a character\n * @return {fabric.IText} thisArg\n * @chainable\n */\n selectLine: function(selectionStart) {\n selectionStart = selectionStart || this.selectionStart;\n var newSelectionStart = this.findLineBoundaryLeft(selectionStart),\n newSelectionEnd = this.findLineBoundaryRight(selectionStart);\n\n this.selectionStart = newSelectionStart;\n this.selectionEnd = newSelectionEnd;\n this._fireSelectionChanged();\n this._updateTextarea();\n return this;\n },\n\n /**\n * Enters editing state\n * @return {fabric.IText} thisArg\n * @chainable\n */\n enterEditing: function(e) {\n if (this.isEditing || !this.editable) {\n return;\n }\n\n if (this.canvas) {\n this.canvas.calcOffset();\n this.exitEditingOnOthers(this.canvas);\n }\n\n this.isEditing = true;\n\n this.initHiddenTextarea(e);\n this.hiddenTextarea.focus();\n this.hiddenTextarea.value = this.text;\n this._updateTextarea();\n this._saveEditingProps();\n this._setEditingProps();\n this._textBeforeEdit = this.text;\n\n this._tick();\n this.fire('editing:entered');\n this._fireSelectionChanged();\n if (!this.canvas) {\n return this;\n }\n this.canvas.fire('text:editing:entered', { target: this });\n this.initMouseMoveHandler();\n this.canvas.requestRenderAll();\n return this;\n },\n\n exitEditingOnOthers: function(canvas) {\n if (canvas._iTextInstances) {\n canvas._iTextInstances.forEach(function(obj) {\n obj.selected = false;\n if (obj.isEditing) {\n obj.exitEditing();\n }\n });\n }\n },\n\n /**\n * Initializes \"mousemove\" event handler\n */\n initMouseMoveHandler: function() {\n this.canvas.on('mouse:move', this.mouseMoveHandler);\n },\n\n /**\n * @private\n */\n mouseMoveHandler: function(options) {\n if (!this.__isMousedown || !this.isEditing) {\n return;\n }\n\n var newSelectionStart = this.getSelectionStartFromPointer(options.e),\n currentStart = this.selectionStart,\n currentEnd = this.selectionEnd;\n if (\n (newSelectionStart !== this.__selectionStartOnMouseDown || currentStart === currentEnd)\n &&\n (currentStart === newSelectionStart || currentEnd === newSelectionStart)\n ) {\n return;\n }\n if (newSelectionStart > this.__selectionStartOnMouseDown) {\n this.selectionStart = this.__selectionStartOnMouseDown;\n this.selectionEnd = newSelectionStart;\n }\n else {\n this.selectionStart = newSelectionStart;\n this.selectionEnd = this.__selectionStartOnMouseDown;\n }\n if (this.selectionStart !== currentStart || this.selectionEnd !== currentEnd) {\n this.restartCursorIfNeeded();\n this._fireSelectionChanged();\n this._updateTextarea();\n this.renderCursorOrSelection();\n }\n },\n\n /**\n * @private\n */\n _setEditingProps: function() {\n this.hoverCursor = 'text';\n\n if (this.canvas) {\n this.canvas.defaultCursor = this.canvas.moveCursor = 'text';\n }\n\n this.borderColor = this.editingBorderColor;\n this.hasControls = this.selectable = false;\n this.lockMovementX = this.lockMovementY = true;\n },\n\n /**\n * convert from textarea to grapheme indexes\n */\n fromStringToGraphemeSelection: function(start, end, text) {\n var smallerTextStart = text.slice(0, start),\n graphemeStart = fabric.util.string.graphemeSplit(smallerTextStart).length;\n if (start === end) {\n return { selectionStart: graphemeStart, selectionEnd: graphemeStart };\n }\n var smallerTextEnd = text.slice(start, end),\n graphemeEnd = fabric.util.string.graphemeSplit(smallerTextEnd).length;\n return { selectionStart: graphemeStart, selectionEnd: graphemeStart + graphemeEnd };\n },\n\n /**\n * convert from fabric to textarea values\n */\n fromGraphemeToStringSelection: function(start, end, _text) {\n var smallerTextStart = _text.slice(0, start),\n graphemeStart = smallerTextStart.join('').length;\n if (start === end) {\n return { selectionStart: graphemeStart, selectionEnd: graphemeStart };\n }\n var smallerTextEnd = _text.slice(start, end),\n graphemeEnd = smallerTextEnd.join('').length;\n return { selectionStart: graphemeStart, selectionEnd: graphemeStart + graphemeEnd };\n },\n\n /**\n * @private\n */\n _updateTextarea: function() {\n this.cursorOffsetCache = { };\n if (!this.hiddenTextarea) {\n return;\n }\n if (!this.inCompositionMode) {\n var newSelection = this.fromGraphemeToStringSelection(this.selectionStart, this.selectionEnd, this._text);\n this.hiddenTextarea.selectionStart = newSelection.selectionStart;\n this.hiddenTextarea.selectionEnd = newSelection.selectionEnd;\n }\n this.updateTextareaPosition();\n },\n\n /**\n * @private\n */\n updateFromTextArea: function() {\n if (!this.hiddenTextarea) {\n return;\n }\n this.cursorOffsetCache = { };\n this.text = this.hiddenTextarea.value;\n if (this._shouldClearDimensionCache()) {\n this.initDimensions();\n this.setCoords();\n }\n var newSelection = this.fromStringToGraphemeSelection(\n this.hiddenTextarea.selectionStart, this.hiddenTextarea.selectionEnd, this.hiddenTextarea.value);\n this.selectionEnd = this.selectionStart = newSelection.selectionEnd;\n if (!this.inCompositionMode) {\n this.selectionStart = newSelection.selectionStart;\n }\n this.updateTextareaPosition();\n },\n\n /**\n * @private\n */\n updateTextareaPosition: function() {\n if (this.selectionStart === this.selectionEnd) {\n var style = this._calcTextareaPosition();\n this.hiddenTextarea.style.left = style.left;\n this.hiddenTextarea.style.top = style.top;\n }\n },\n\n /**\n * @private\n * @return {Object} style contains style for hiddenTextarea\n */\n _calcTextareaPosition: function() {\n if (!this.canvas) {\n return { x: 1, y: 1 };\n }\n var desiredPosition = this.inCompositionMode ? this.compositionStart : this.selectionStart,\n boundaries = this._getCursorBoundaries(desiredPosition),\n cursorLocation = this.get2DCursorLocation(desiredPosition),\n lineIndex = cursorLocation.lineIndex,\n charIndex = cursorLocation.charIndex,\n charHeight = this.getValueOfPropertyAt(lineIndex, charIndex, 'fontSize') * this.lineHeight,\n leftOffset = boundaries.leftOffset,\n m = this.calcTransformMatrix(),\n p = {\n x: boundaries.left + leftOffset,\n y: boundaries.top + boundaries.topOffset + charHeight\n },\n retinaScaling = this.canvas.getRetinaScaling(),\n upperCanvas = this.canvas.upperCanvasEl,\n upperCanvasWidth = upperCanvas.width / retinaScaling,\n upperCanvasHeight = upperCanvas.height / retinaScaling,\n maxWidth = upperCanvasWidth - charHeight,\n maxHeight = upperCanvasHeight - charHeight,\n scaleX = upperCanvas.clientWidth / upperCanvasWidth,\n scaleY = upperCanvas.clientHeight / upperCanvasHeight;\n\n p = fabric.util.transformPoint(p, m);\n p = fabric.util.transformPoint(p, this.canvas.viewportTransform);\n p.x *= scaleX;\n p.y *= scaleY;\n if (p.x < 0) {\n p.x = 0;\n }\n if (p.x > maxWidth) {\n p.x = maxWidth;\n }\n if (p.y < 0) {\n p.y = 0;\n }\n if (p.y > maxHeight) {\n p.y = maxHeight;\n }\n\n // add canvas offset on document\n p.x += this.canvas._offset.left;\n p.y += this.canvas._offset.top;\n\n return { left: p.x + 'px', top: p.y + 'px', fontSize: charHeight + 'px', charHeight: charHeight };\n },\n\n /**\n * @private\n */\n _saveEditingProps: function() {\n this._savedProps = {\n hasControls: this.hasControls,\n borderColor: this.borderColor,\n lockMovementX: this.lockMovementX,\n lockMovementY: this.lockMovementY,\n hoverCursor: this.hoverCursor,\n selectable: this.selectable,\n defaultCursor: this.canvas && this.canvas.defaultCursor,\n moveCursor: this.canvas && this.canvas.moveCursor\n };\n },\n\n /**\n * @private\n */\n _restoreEditingProps: function() {\n if (!this._savedProps) {\n return;\n }\n\n this.hoverCursor = this._savedProps.hoverCursor;\n this.hasControls = this._savedProps.hasControls;\n this.borderColor = this._savedProps.borderColor;\n this.selectable = this._savedProps.selectable;\n this.lockMovementX = this._savedProps.lockMovementX;\n this.lockMovementY = this._savedProps.lockMovementY;\n\n if (this.canvas) {\n this.canvas.defaultCursor = this._savedProps.defaultCursor;\n this.canvas.moveCursor = this._savedProps.moveCursor;\n }\n },\n\n /**\n * Exits from editing state\n * @return {fabric.IText} thisArg\n * @chainable\n */\n exitEditing: function() {\n var isTextChanged = (this._textBeforeEdit !== this.text);\n var hiddenTextarea = this.hiddenTextarea;\n this.selected = false;\n this.isEditing = false;\n\n this.selectionEnd = this.selectionStart;\n\n if (hiddenTextarea) {\n hiddenTextarea.blur && hiddenTextarea.blur();\n hiddenTextarea.parentNode && hiddenTextarea.parentNode.removeChild(hiddenTextarea);\n }\n this.hiddenTextarea = null;\n this.abortCursorAnimation();\n this._restoreEditingProps();\n this._currentCursorOpacity = 0;\n if (this._shouldClearDimensionCache()) {\n this.initDimensions();\n this.setCoords();\n }\n this.fire('editing:exited');\n isTextChanged && this.fire('modified');\n if (this.canvas) {\n this.canvas.off('mouse:move', this.mouseMoveHandler);\n this.canvas.fire('text:editing:exited', { target: this });\n isTextChanged && this.canvas.fire('object:modified', { target: this });\n }\n return this;\n },\n\n /**\n * @private\n */\n _removeExtraneousStyles: function() {\n for (var prop in this.styles) {\n if (!this._textLines[prop]) {\n delete this.styles[prop];\n }\n }\n },\n\n /**\n * remove and reflow a style block from start to end.\n * @param {Number} start linear start position for removal (included in removal)\n * @param {Number} end linear end position for removal ( excluded from removal )\n */\n removeStyleFromTo: function(start, end) {\n var cursorStart = this.get2DCursorLocation(start, true),\n cursorEnd = this.get2DCursorLocation(end, true),\n lineStart = cursorStart.lineIndex,\n charStart = cursorStart.charIndex,\n lineEnd = cursorEnd.lineIndex,\n charEnd = cursorEnd.charIndex,\n i, styleObj;\n if (lineStart !== lineEnd) {\n // step1 remove the trailing of lineStart\n if (this.styles[lineStart]) {\n for (i = charStart; i < this._unwrappedTextLines[lineStart].length; i++) {\n delete this.styles[lineStart][i];\n }\n }\n // step2 move the trailing of lineEnd to lineStart if needed\n if (this.styles[lineEnd]) {\n for (i = charEnd; i < this._unwrappedTextLines[lineEnd].length; i++) {\n styleObj = this.styles[lineEnd][i];\n if (styleObj) {\n this.styles[lineStart] || (this.styles[lineStart] = { });\n this.styles[lineStart][charStart + i - charEnd] = styleObj;\n }\n }\n }\n // step3 detects lines will be completely removed.\n for (i = lineStart + 1; i <= lineEnd; i++) {\n delete this.styles[i];\n }\n // step4 shift remaining lines.\n this.shiftLineStyles(lineEnd, lineStart - lineEnd);\n }\n else {\n // remove and shift left on the same line\n if (this.styles[lineStart]) {\n styleObj = this.styles[lineStart];\n var diff = charEnd - charStart, numericChar, _char;\n for (i = charStart; i < charEnd; i++) {\n delete styleObj[i];\n }\n for (_char in this.styles[lineStart]) {\n numericChar = parseInt(_char, 10);\n if (numericChar >= charEnd) {\n styleObj[numericChar - diff] = styleObj[_char];\n delete styleObj[_char];\n }\n }\n }\n }\n },\n\n /**\n * Shifts line styles up or down\n * @param {Number} lineIndex Index of a line\n * @param {Number} offset Can any number?\n */\n shiftLineStyles: function(lineIndex, offset) {\n // shift all line styles by offset upward or downward\n // do not clone deep. we need new array, not new style objects\n var clonedStyles = clone(this.styles);\n for (var line in this.styles) {\n var numericLine = parseInt(line, 10);\n if (numericLine > lineIndex) {\n this.styles[numericLine + offset] = clonedStyles[numericLine];\n if (!clonedStyles[numericLine - offset]) {\n delete this.styles[numericLine];\n }\n }\n }\n },\n\n restartCursorIfNeeded: function() {\n if (!this._currentTickState || this._currentTickState.isAborted\n || !this._currentTickCompleteState || this._currentTickCompleteState.isAborted\n ) {\n this.initDelayedCursor();\n }\n },\n\n /**\n * Handle insertion of more consecutive style lines for when one or more\n * newlines gets added to the text. Since current style needs to be shifted\n * first we shift the current style of the number lines needed, then we add\n * new lines from the last to the first.\n * @param {Number} lineIndex Index of a line\n * @param {Number} charIndex Index of a char\n * @param {Number} qty number of lines to add\n * @param {Array} copiedStyle Array of objects styles\n */\n insertNewlineStyleObject: function(lineIndex, charIndex, qty, copiedStyle) {\n var currentCharStyle,\n newLineStyles = {},\n somethingAdded = false,\n isEndOfLine = this._unwrappedTextLines[lineIndex].length === charIndex;\n\n qty || (qty = 1);\n this.shiftLineStyles(lineIndex, qty);\n if (this.styles[lineIndex]) {\n currentCharStyle = this.styles[lineIndex][charIndex === 0 ? charIndex : charIndex - 1];\n }\n // we clone styles of all chars\n // after cursor onto the current line\n for (var index in this.styles[lineIndex]) {\n var numIndex = parseInt(index, 10);\n if (numIndex >= charIndex) {\n somethingAdded = true;\n newLineStyles[numIndex - charIndex] = this.styles[lineIndex][index];\n // remove lines from the previous line since they're on a new line now\n if (!(isEndOfLine && charIndex === 0)) {\n delete this.styles[lineIndex][index];\n }\n }\n }\n var styleCarriedOver = false;\n if (somethingAdded && !isEndOfLine) {\n // if is end of line, the extra style we copied\n // is probably not something we want\n this.styles[lineIndex + qty] = newLineStyles;\n styleCarriedOver = true;\n }\n if (styleCarriedOver) {\n // skip the last line of since we already prepared it.\n qty--;\n }\n // for the all the lines or all the other lines\n // we clone current char style onto the next (otherwise empty) line\n while (qty > 0) {\n if (copiedStyle && copiedStyle[qty - 1]) {\n this.styles[lineIndex + qty] = { 0: clone(copiedStyle[qty - 1]) };\n }\n else if (currentCharStyle) {\n this.styles[lineIndex + qty] = { 0: clone(currentCharStyle) };\n }\n else {\n delete this.styles[lineIndex + qty];\n }\n qty--;\n }\n this._forceClearCache = true;\n },\n\n /**\n * Inserts style object for a given line/char index\n * @param {Number} lineIndex Index of a line\n * @param {Number} charIndex Index of a char\n * @param {Number} quantity number Style object to insert, if given\n * @param {Array} copiedStyle array of style objects\n */\n insertCharStyleObject: function(lineIndex, charIndex, quantity, copiedStyle) {\n if (!this.styles) {\n this.styles = {};\n }\n var currentLineStyles = this.styles[lineIndex],\n currentLineStylesCloned = currentLineStyles ? clone(currentLineStyles) : {};\n\n quantity || (quantity = 1);\n // shift all char styles by quantity forward\n // 0,1,2,3 -> (charIndex=2) -> 0,1,3,4 -> (insert 2) -> 0,1,2,3,4\n for (var index in currentLineStylesCloned) {\n var numericIndex = parseInt(index, 10);\n if (numericIndex >= charIndex) {\n currentLineStyles[numericIndex + quantity] = currentLineStylesCloned[numericIndex];\n // only delete the style if there was nothing moved there\n if (!currentLineStylesCloned[numericIndex - quantity]) {\n delete currentLineStyles[numericIndex];\n }\n }\n }\n this._forceClearCache = true;\n if (copiedStyle) {\n while (quantity--) {\n if (!Object.keys(copiedStyle[quantity]).length) {\n continue;\n }\n if (!this.styles[lineIndex]) {\n this.styles[lineIndex] = {};\n }\n this.styles[lineIndex][charIndex + quantity] = clone(copiedStyle[quantity]);\n }\n return;\n }\n if (!currentLineStyles) {\n return;\n }\n var newStyle = currentLineStyles[charIndex ? charIndex - 1 : 1];\n while (newStyle && quantity--) {\n this.styles[lineIndex][charIndex + quantity] = clone(newStyle);\n }\n },\n\n /**\n * Inserts style object(s)\n * @param {Array} insertedText Characters at the location where style is inserted\n * @param {Number} start cursor index for inserting style\n * @param {Array} [copiedStyle] array of style objects to insert.\n */\n insertNewStyleBlock: function(insertedText, start, copiedStyle) {\n var cursorLoc = this.get2DCursorLocation(start, true),\n addedLines = [0], linesLength = 0;\n // get an array of how many char per lines are being added.\n for (var i = 0; i < insertedText.length; i++) {\n if (insertedText[i] === '\\n') {\n linesLength++;\n addedLines[linesLength] = 0;\n }\n else {\n addedLines[linesLength]++;\n }\n }\n // for the first line copy the style from the current char position.\n if (addedLines[0] > 0) {\n this.insertCharStyleObject(cursorLoc.lineIndex, cursorLoc.charIndex, addedLines[0], copiedStyle);\n copiedStyle = copiedStyle && copiedStyle.slice(addedLines[0] + 1);\n }\n linesLength && this.insertNewlineStyleObject(\n cursorLoc.lineIndex, cursorLoc.charIndex + addedLines[0], linesLength);\n for (var i = 1; i < linesLength; i++) {\n if (addedLines[i] > 0) {\n this.insertCharStyleObject(cursorLoc.lineIndex + i, 0, addedLines[i], copiedStyle);\n }\n else if (copiedStyle) {\n this.styles[cursorLoc.lineIndex + i][0] = copiedStyle[0];\n }\n copiedStyle = copiedStyle && copiedStyle.slice(addedLines[i] + 1);\n }\n // we use i outside the loop to get it like linesLength\n if (addedLines[i] > 0) {\n this.insertCharStyleObject(cursorLoc.lineIndex + i, 0, addedLines[i], copiedStyle);\n }\n },\n\n /**\n * Set the selectionStart and selectionEnd according to the new position of cursor\n * mimic the key - mouse navigation when shift is pressed.\n */\n setSelectionStartEndWithShift: function(start, end, newSelection) {\n if (newSelection <= start) {\n if (end === start) {\n this._selectionDirection = 'left';\n }\n else if (this._selectionDirection === 'right') {\n this._selectionDirection = 'left';\n this.selectionEnd = start;\n }\n this.selectionStart = newSelection;\n }\n else if (newSelection > start && newSelection < end) {\n if (this._selectionDirection === 'right') {\n this.selectionEnd = newSelection;\n }\n else {\n this.selectionStart = newSelection;\n }\n }\n else {\n // newSelection is > selection start and end\n if (end === start) {\n this._selectionDirection = 'right';\n }\n else if (this._selectionDirection === 'left') {\n this._selectionDirection = 'right';\n this.selectionStart = end;\n }\n this.selectionEnd = newSelection;\n }\n },\n\n setSelectionInBoundaries: function() {\n var length = this.text.length;\n if (this.selectionStart > length) {\n this.selectionStart = length;\n }\n else if (this.selectionStart < 0) {\n this.selectionStart = 0;\n }\n if (this.selectionEnd > length) {\n this.selectionEnd = length;\n }\n else if (this.selectionEnd < 0) {\n this.selectionEnd = 0;\n }\n }\n });\n})();\n\n\nfabric.util.object.extend(fabric.IText.prototype, /** @lends fabric.IText.prototype */ {\n /**\n * Initializes \"dbclick\" event handler\n */\n initDoubleClickSimulation: function() {\n\n // for double click\n this.__lastClickTime = +new Date();\n\n // for triple click\n this.__lastLastClickTime = +new Date();\n\n this.__lastPointer = { };\n\n this.on('mousedown', this.onMouseDown);\n },\n\n /**\n * Default event handler to simulate triple click\n * @private\n */\n onMouseDown: function(options) {\n if (!this.canvas) {\n return;\n }\n this.__newClickTime = +new Date();\n var newPointer = options.pointer;\n if (this.isTripleClick(newPointer)) {\n this.fire('tripleclick', options);\n this._stopEvent(options.e);\n }\n this.__lastLastClickTime = this.__lastClickTime;\n this.__lastClickTime = this.__newClickTime;\n this.__lastPointer = newPointer;\n this.__lastIsEditing = this.isEditing;\n this.__lastSelected = this.selected;\n },\n\n isTripleClick: function(newPointer) {\n return this.__newClickTime - this.__lastClickTime < 500 &&\n this.__lastClickTime - this.__lastLastClickTime < 500 &&\n this.__lastPointer.x === newPointer.x &&\n this.__lastPointer.y === newPointer.y;\n },\n\n /**\n * @private\n */\n _stopEvent: function(e) {\n e.preventDefault && e.preventDefault();\n e.stopPropagation && e.stopPropagation();\n },\n\n /**\n * Initializes event handlers related to cursor or selection\n */\n initCursorSelectionHandlers: function() {\n this.initMousedownHandler();\n this.initMouseupHandler();\n this.initClicks();\n },\n\n /**\n * Default handler for double click, select a word\n */\n doubleClickHandler: function(options) {\n if (!this.isEditing) {\n return;\n }\n this.selectWord(this.getSelectionStartFromPointer(options.e));\n },\n\n /**\n * Default handler for triple click, select a line\n */\n tripleClickHandler: function(options) {\n if (!this.isEditing) {\n return;\n }\n this.selectLine(this.getSelectionStartFromPointer(options.e));\n },\n\n /**\n * Initializes double and triple click event handlers\n */\n initClicks: function() {\n this.on('mousedblclick', this.doubleClickHandler);\n this.on('tripleclick', this.tripleClickHandler);\n },\n\n /**\n * Default event handler for the basic functionalities needed on _mouseDown\n * can be overridden to do something different.\n * Scope of this implementation is: find the click position, set selectionStart\n * find selectionEnd, initialize the drawing of either cursor or selection area\n */\n _mouseDownHandler: function(options) {\n if (!this.canvas || !this.editable || (options.e.button && options.e.button !== 1)) {\n return;\n }\n\n this.__isMousedown = true;\n\n if (this.selected) {\n this.setCursorByClick(options.e);\n }\n\n if (this.isEditing) {\n this.__selectionStartOnMouseDown = this.selectionStart;\n if (this.selectionStart === this.selectionEnd) {\n this.abortCursorAnimation();\n }\n this.renderCursorOrSelection();\n }\n },\n\n /**\n * Default event handler for the basic functionalities needed on mousedown:before\n * can be overridden to do something different.\n * Scope of this implementation is: verify the object is already selected when mousing down\n */\n _mouseDownHandlerBefore: function(options) {\n if (!this.canvas || !this.editable || (options.e.button && options.e.button !== 1)) {\n return;\n }\n // we want to avoid that an object that was selected and then becomes unselectable,\n // may trigger editing mode in some way.\n this.selected = this === this.canvas._activeObject;\n },\n\n /**\n * Initializes \"mousedown\" event handler\n */\n initMousedownHandler: function() {\n this.on('mousedown', this._mouseDownHandler);\n this.on('mousedown:before', this._mouseDownHandlerBefore);\n },\n\n /**\n * Initializes \"mouseup\" event handler\n */\n initMouseupHandler: function() {\n this.on('mouseup', this.mouseUpHandler);\n },\n\n /**\n * standard hander for mouse up, overridable\n * @private\n */\n mouseUpHandler: function(options) {\n this.__isMousedown = false;\n if (!this.editable || this.group ||\n (options.transform && options.transform.actionPerformed) ||\n (options.e.button && options.e.button !== 1)) {\n return;\n }\n\n if (this.canvas) {\n var currentActive = this.canvas._activeObject;\n if (currentActive && currentActive !== this) {\n // avoid running this logic when there is an active object\n // this because is possible with shift click and fast clicks,\n // to rapidly deselect and reselect this object and trigger an enterEdit\n return;\n }\n }\n\n if (this.__lastSelected && !this.__corner) {\n this.selected = false;\n this.__lastSelected = false;\n this.enterEditing(options.e);\n if (this.selectionStart === this.selectionEnd) {\n this.initDelayedCursor(true);\n }\n else {\n this.renderCursorOrSelection();\n }\n }\n else {\n this.selected = true;\n }\n },\n\n /**\n * Changes cursor location in a text depending on passed pointer (x/y) object\n * @param {Event} e Event object\n */\n setCursorByClick: function(e) {\n var newSelection = this.getSelectionStartFromPointer(e),\n start = this.selectionStart, end = this.selectionEnd;\n if (e.shiftKey) {\n this.setSelectionStartEndWithShift(start, end, newSelection);\n }\n else {\n this.selectionStart = newSelection;\n this.selectionEnd = newSelection;\n }\n if (this.isEditing) {\n this._fireSelectionChanged();\n this._updateTextarea();\n }\n },\n\n /**\n * Returns index of a character corresponding to where an object was clicked\n * @param {Event} e Event object\n * @return {Number} Index of a character\n */\n getSelectionStartFromPointer: function(e) {\n var mouseOffset = this.getLocalPointer(e),\n prevWidth = 0,\n width = 0,\n height = 0,\n charIndex = 0,\n lineIndex = 0,\n lineLeftOffset,\n line;\n\n for (var i = 0, len = this._textLines.length; i < len; i++) {\n if (height <= mouseOffset.y) {\n height += this.getHeightOfLine(i) * this.scaleY;\n lineIndex = i;\n if (i > 0) {\n charIndex += this._textLines[i - 1].length + this.missingNewlineOffset(i - 1);\n }\n }\n else {\n break;\n }\n }\n lineLeftOffset = this._getLineLeftOffset(lineIndex);\n width = lineLeftOffset * this.scaleX;\n line = this._textLines[lineIndex];\n for (var j = 0, jlen = line.length; j < jlen; j++) {\n prevWidth = width;\n // i removed something about flipX here, check.\n width += this.__charBounds[lineIndex][j].kernedWidth * this.scaleX;\n if (width <= mouseOffset.x) {\n charIndex++;\n }\n else {\n break;\n }\n }\n return this._getNewSelectionStartFromOffset(mouseOffset, prevWidth, width, charIndex, jlen);\n },\n\n /**\n * @private\n */\n _getNewSelectionStartFromOffset: function(mouseOffset, prevWidth, width, index, jlen) {\n // we need Math.abs because when width is after the last char, the offset is given as 1, while is 0\n var distanceBtwLastCharAndCursor = mouseOffset.x - prevWidth,\n distanceBtwNextCharAndCursor = width - mouseOffset.x,\n offset = distanceBtwNextCharAndCursor > distanceBtwLastCharAndCursor ||\n distanceBtwNextCharAndCursor < 0 ? 0 : 1,\n newSelectionStart = index + offset;\n // if object is horizontally flipped, mirror cursor location from the end\n if (this.flipX) {\n newSelectionStart = jlen - newSelectionStart;\n }\n\n if (newSelectionStart > this._text.length) {\n newSelectionStart = this._text.length;\n }\n\n return newSelectionStart;\n }\n});\n\n\nfabric.util.object.extend(fabric.IText.prototype, /** @lends fabric.IText.prototype */ {\n\n /**\n * Initializes hidden textarea (needed to bring up keyboard in iOS)\n */\n initHiddenTextarea: function() {\n this.hiddenTextarea = fabric.document.createElement('textarea');\n this.hiddenTextarea.setAttribute('autocapitalize', 'off');\n this.hiddenTextarea.setAttribute('autocorrect', 'off');\n this.hiddenTextarea.setAttribute('autocomplete', 'off');\n this.hiddenTextarea.setAttribute('spellcheck', 'false');\n this.hiddenTextarea.setAttribute('data-fabric-hiddentextarea', '');\n this.hiddenTextarea.setAttribute('wrap', 'off');\n var style = this._calcTextareaPosition();\n // line-height: 1px; was removed from the style to fix this:\n // https://bugs.chromium.org/p/chromium/issues/detail?id=870966\n this.hiddenTextarea.style.cssText = 'position: absolute; top: ' + style.top +\n '; left: ' + style.left + '; z-index: -999; opacity: 0; width: 1px; height: 1px; font-size: 1px;' +\n ' paddingーtop: ' + style.fontSize + ';';\n fabric.document.body.appendChild(this.hiddenTextarea);\n\n fabric.util.addListener(this.hiddenTextarea, 'keydown', this.onKeyDown.bind(this));\n fabric.util.addListener(this.hiddenTextarea, 'keyup', this.onKeyUp.bind(this));\n fabric.util.addListener(this.hiddenTextarea, 'input', this.onInput.bind(this));\n fabric.util.addListener(this.hiddenTextarea, 'copy', this.copy.bind(this));\n fabric.util.addListener(this.hiddenTextarea, 'cut', this.copy.bind(this));\n fabric.util.addListener(this.hiddenTextarea, 'paste', this.paste.bind(this));\n fabric.util.addListener(this.hiddenTextarea, 'compositionstart', this.onCompositionStart.bind(this));\n fabric.util.addListener(this.hiddenTextarea, 'compositionupdate', this.onCompositionUpdate.bind(this));\n fabric.util.addListener(this.hiddenTextarea, 'compositionend', this.onCompositionEnd.bind(this));\n\n if (!this._clickHandlerInitialized && this.canvas) {\n fabric.util.addListener(this.canvas.upperCanvasEl, 'click', this.onClick.bind(this));\n this._clickHandlerInitialized = true;\n }\n },\n\n /**\n * For functionalities on keyDown\n * Map a special key to a function of the instance/prototype\n * If you need different behaviour for ESC or TAB or arrows, you have to change\n * this map setting the name of a function that you build on the fabric.Itext or\n * your prototype.\n * the map change will affect all Instances unless you need for only some text Instances\n * in that case you have to clone this object and assign your Instance.\n * this.keysMap = fabric.util.object.clone(this.keysMap);\n * The function must be in fabric.Itext.prototype.myFunction And will receive event as args[0]\n */\n keysMap: {\n 9: 'exitEditing',\n 27: 'exitEditing',\n 33: 'moveCursorUp',\n 34: 'moveCursorDown',\n 35: 'moveCursorRight',\n 36: 'moveCursorLeft',\n 37: 'moveCursorLeft',\n 38: 'moveCursorUp',\n 39: 'moveCursorRight',\n 40: 'moveCursorDown',\n },\n\n /**\n * For functionalities on keyUp + ctrl || cmd\n */\n ctrlKeysMapUp: {\n 67: 'copy',\n 88: 'cut'\n },\n\n /**\n * For functionalities on keyDown + ctrl || cmd\n */\n ctrlKeysMapDown: {\n 65: 'selectAll'\n },\n\n onClick: function() {\n // No need to trigger click event here, focus is enough to have the keyboard appear on Android\n this.hiddenTextarea && this.hiddenTextarea.focus();\n },\n\n /**\n * Handles keyup event\n * @param {Event} e Event object\n */\n onKeyDown: function(e) {\n if (!this.isEditing || this.inCompositionMode) {\n return;\n }\n if (e.keyCode in this.keysMap) {\n this[this.keysMap[e.keyCode]](e);\n }\n else if ((e.keyCode in this.ctrlKeysMapDown) && (e.ctrlKey || e.metaKey)) {\n this[this.ctrlKeysMapDown[e.keyCode]](e);\n }\n else {\n return;\n }\n e.stopImmediatePropagation();\n e.preventDefault();\n if (e.keyCode >= 33 && e.keyCode <= 40) {\n // if i press an arrow key just update selection\n this.clearContextTop();\n this.renderCursorOrSelection();\n }\n else {\n this.canvas && this.canvas.requestRenderAll();\n }\n },\n\n /**\n * Handles keyup event\n * We handle KeyUp because ie11 and edge have difficulties copy/pasting\n * if a copy/cut event fired, keyup is dismissed\n * @param {Event} e Event object\n */\n onKeyUp: function(e) {\n if (!this.isEditing || this._copyDone || this.inCompositionMode) {\n this._copyDone = false;\n return;\n }\n if ((e.keyCode in this.ctrlKeysMapUp) && (e.ctrlKey || e.metaKey)) {\n this[this.ctrlKeysMapUp[e.keyCode]](e);\n }\n else {\n return;\n }\n e.stopImmediatePropagation();\n e.preventDefault();\n this.canvas && this.canvas.requestRenderAll();\n },\n\n /**\n * Handles onInput event\n * @param {Event} e Event object\n */\n onInput: function(e) {\n var fromPaste = this.fromPaste;\n this.fromPaste = false;\n e && e.stopPropagation();\n if (!this.isEditing) {\n return;\n }\n // decisions about style changes.\n var nextText = this._splitTextIntoLines(this.hiddenTextarea.value).graphemeText,\n charCount = this._text.length,\n nextCharCount = nextText.length,\n removedText, insertedText,\n charDiff = nextCharCount - charCount,\n selectionStart = this.selectionStart, selectionEnd = this.selectionEnd,\n selection = selectionStart !== selectionEnd,\n copiedStyle, removeFrom, removeTo;\n if (this.hiddenTextarea.value === '') {\n this.styles = { };\n this.updateFromTextArea();\n this.fire('changed');\n if (this.canvas) {\n this.canvas.fire('text:changed', { target: this });\n this.canvas.requestRenderAll();\n }\n return;\n }\n\n var textareaSelection = this.fromStringToGraphemeSelection(\n this.hiddenTextarea.selectionStart,\n this.hiddenTextarea.selectionEnd,\n this.hiddenTextarea.value\n );\n var backDelete = selectionStart > textareaSelection.selectionStart;\n\n if (selection) {\n removedText = this._text.slice(selectionStart, selectionEnd);\n charDiff += selectionEnd - selectionStart;\n }\n else if (nextCharCount < charCount) {\n if (backDelete) {\n removedText = this._text.slice(selectionEnd + charDiff, selectionEnd);\n }\n else {\n removedText = this._text.slice(selectionStart, selectionStart - charDiff);\n }\n }\n var copiedStyle;\n insertedText = nextText.slice(textareaSelection.selectionEnd - charDiff, textareaSelection.selectionEnd);\n if (removedText && removedText.length) {\n if (insertedText.length) {\n // let's copy some style before deleting.\n // we want to copy the style before the cursor OR the style at the cursor if selection\n // is bigger than 0.\n copiedStyle = this.getSelectionStyles(selectionStart, selectionStart + 1, true);\n // now duplicate the style one for each inserted text.\n copiedStyle = insertedText.map(function() {\n // this return an array of references, but that is fine since we are\n // copying the style later.\n return copiedStyle[0];\n });\n }\n if (selection) {\n removeFrom = selectionStart;\n removeTo = selectionEnd;\n }\n else if (backDelete) {\n // detect differencies between forwardDelete and backDelete\n removeFrom = selectionEnd - removedText.length;\n removeTo = selectionEnd;\n }\n else {\n removeFrom = selectionEnd;\n removeTo = selectionEnd + removedText.length;\n }\n this.removeStyleFromTo(removeFrom, removeTo);\n }\n if (insertedText.length) {\n if (fromPaste && insertedText.join('') === fabric.copiedText && !fabric.disableStyleCopyPaste) {\n copiedStyle = fabric.copiedTextStyle;\n }\n this.insertNewStyleBlock(insertedText, selectionStart, copiedStyle);\n }\n this.updateFromTextArea();\n this.fire('changed');\n if (this.canvas) {\n this.canvas.fire('text:changed', { target: this });\n this.canvas.requestRenderAll();\n }\n },\n /**\n * Composition start\n */\n onCompositionStart: function() {\n this.inCompositionMode = true;\n },\n\n /**\n * Composition end\n */\n onCompositionEnd: function() {\n this.inCompositionMode = false;\n },\n\n // /**\n // * Composition update\n // */\n onCompositionUpdate: function(e) {\n this.compositionStart = e.target.selectionStart;\n this.compositionEnd = e.target.selectionEnd;\n this.updateTextareaPosition();\n },\n\n /**\n * Copies selected text\n * @param {Event} e Event object\n */\n copy: function() {\n if (this.selectionStart === this.selectionEnd) {\n //do not cut-copy if no selection\n return;\n }\n\n fabric.copiedText = this.getSelectedText();\n if (!fabric.disableStyleCopyPaste) {\n fabric.copiedTextStyle = this.getSelectionStyles(this.selectionStart, this.selectionEnd, true);\n }\n else {\n fabric.copiedTextStyle = null;\n }\n this._copyDone = true;\n },\n\n /**\n * Pastes text\n * @param {Event} e Event object\n */\n paste: function() {\n this.fromPaste = true;\n },\n\n /**\n * @private\n * @param {Event} e Event object\n * @return {Object} Clipboard data object\n */\n _getClipboardData: function(e) {\n return (e && e.clipboardData) || fabric.window.clipboardData;\n },\n\n /**\n * Finds the width in pixels before the cursor on the same line\n * @private\n * @param {Number} lineIndex\n * @param {Number} charIndex\n * @return {Number} widthBeforeCursor width before cursor\n */\n _getWidthBeforeCursor: function(lineIndex, charIndex) {\n var widthBeforeCursor = this._getLineLeftOffset(lineIndex), bound;\n\n if (charIndex > 0) {\n bound = this.__charBounds[lineIndex][charIndex - 1];\n widthBeforeCursor += bound.left + bound.width;\n }\n return widthBeforeCursor;\n },\n\n /**\n * Gets start offset of a selection\n * @param {Event} e Event object\n * @param {Boolean} isRight\n * @return {Number}\n */\n getDownCursorOffset: function(e, isRight) {\n var selectionProp = this._getSelectionForOffset(e, isRight),\n cursorLocation = this.get2DCursorLocation(selectionProp),\n lineIndex = cursorLocation.lineIndex;\n // if on last line, down cursor goes to end of line\n if (lineIndex === this._textLines.length - 1 || e.metaKey || e.keyCode === 34) {\n // move to the end of a text\n return this._text.length - selectionProp;\n }\n var charIndex = cursorLocation.charIndex,\n widthBeforeCursor = this._getWidthBeforeCursor(lineIndex, charIndex),\n indexOnOtherLine = this._getIndexOnLine(lineIndex + 1, widthBeforeCursor),\n textAfterCursor = this._textLines[lineIndex].slice(charIndex);\n return textAfterCursor.length + indexOnOtherLine + 1 + this.missingNewlineOffset(lineIndex);\n },\n\n /**\n * private\n * Helps finding if the offset should be counted from Start or End\n * @param {Event} e Event object\n * @param {Boolean} isRight\n * @return {Number}\n */\n _getSelectionForOffset: function(e, isRight) {\n if (e.shiftKey && this.selectionStart !== this.selectionEnd && isRight) {\n return this.selectionEnd;\n }\n else {\n return this.selectionStart;\n }\n },\n\n /**\n * @param {Event} e Event object\n * @param {Boolean} isRight\n * @return {Number}\n */\n getUpCursorOffset: function(e, isRight) {\n var selectionProp = this._getSelectionForOffset(e, isRight),\n cursorLocation = this.get2DCursorLocation(selectionProp),\n lineIndex = cursorLocation.lineIndex;\n if (lineIndex === 0 || e.metaKey || e.keyCode === 33) {\n // if on first line, up cursor goes to start of line\n return -selectionProp;\n }\n var charIndex = cursorLocation.charIndex,\n widthBeforeCursor = this._getWidthBeforeCursor(lineIndex, charIndex),\n indexOnOtherLine = this._getIndexOnLine(lineIndex - 1, widthBeforeCursor),\n textBeforeCursor = this._textLines[lineIndex].slice(0, charIndex),\n missingNewlineOffset = this.missingNewlineOffset(lineIndex - 1);\n // return a negative offset\n return -this._textLines[lineIndex - 1].length\n + indexOnOtherLine - textBeforeCursor.length + (1 - missingNewlineOffset);\n },\n\n /**\n * for a given width it founds the matching character.\n * @private\n */\n _getIndexOnLine: function(lineIndex, width) {\n\n var line = this._textLines[lineIndex],\n lineLeftOffset = this._getLineLeftOffset(lineIndex),\n widthOfCharsOnLine = lineLeftOffset,\n indexOnLine = 0, charWidth, foundMatch;\n\n for (var j = 0, jlen = line.length; j < jlen; j++) {\n charWidth = this.__charBounds[lineIndex][j].width;\n widthOfCharsOnLine += charWidth;\n if (widthOfCharsOnLine > width) {\n foundMatch = true;\n var leftEdge = widthOfCharsOnLine - charWidth,\n rightEdge = widthOfCharsOnLine,\n offsetFromLeftEdge = Math.abs(leftEdge - width),\n offsetFromRightEdge = Math.abs(rightEdge - width);\n\n indexOnLine = offsetFromRightEdge < offsetFromLeftEdge ? j : (j - 1);\n break;\n }\n }\n\n // reached end\n if (!foundMatch) {\n indexOnLine = line.length - 1;\n }\n\n return indexOnLine;\n },\n\n\n /**\n * Moves cursor down\n * @param {Event} e Event object\n */\n moveCursorDown: function(e) {\n if (this.selectionStart >= this._text.length && this.selectionEnd >= this._text.length) {\n return;\n }\n this._moveCursorUpOrDown('Down', e);\n },\n\n /**\n * Moves cursor up\n * @param {Event} e Event object\n */\n moveCursorUp: function(e) {\n if (this.selectionStart === 0 && this.selectionEnd === 0) {\n return;\n }\n this._moveCursorUpOrDown('Up', e);\n },\n\n /**\n * Moves cursor up or down, fires the events\n * @param {String} direction 'Up' or 'Down'\n * @param {Event} e Event object\n */\n _moveCursorUpOrDown: function(direction, e) {\n // getUpCursorOffset\n // getDownCursorOffset\n var action = 'get' + direction + 'CursorOffset',\n offset = this[action](e, this._selectionDirection === 'right');\n if (e.shiftKey) {\n this.moveCursorWithShift(offset);\n }\n else {\n this.moveCursorWithoutShift(offset);\n }\n if (offset !== 0) {\n this.setSelectionInBoundaries();\n this.abortCursorAnimation();\n this._currentCursorOpacity = 1;\n this.initDelayedCursor();\n this._fireSelectionChanged();\n this._updateTextarea();\n }\n },\n\n /**\n * Moves cursor with shift\n * @param {Number} offset\n */\n moveCursorWithShift: function(offset) {\n var newSelection = this._selectionDirection === 'left'\n ? this.selectionStart + offset\n : this.selectionEnd + offset;\n this.setSelectionStartEndWithShift(this.selectionStart, this.selectionEnd, newSelection);\n return offset !== 0;\n },\n\n /**\n * Moves cursor up without shift\n * @param {Number} offset\n */\n moveCursorWithoutShift: function(offset) {\n if (offset < 0) {\n this.selectionStart += offset;\n this.selectionEnd = this.selectionStart;\n }\n else {\n this.selectionEnd += offset;\n this.selectionStart = this.selectionEnd;\n }\n return offset !== 0;\n },\n\n /**\n * Moves cursor left\n * @param {Event} e Event object\n */\n moveCursorLeft: function(e) {\n if (this.selectionStart === 0 && this.selectionEnd === 0) {\n return;\n }\n this._moveCursorLeftOrRight('Left', e);\n },\n\n /**\n * @private\n * @return {Boolean} true if a change happened\n */\n _move: function(e, prop, direction) {\n var newValue;\n if (e.altKey) {\n newValue = this['findWordBoundary' + direction](this[prop]);\n }\n else if (e.metaKey || e.keyCode === 35 || e.keyCode === 36 ) {\n newValue = this['findLineBoundary' + direction](this[prop]);\n }\n else {\n this[prop] += direction === 'Left' ? -1 : 1;\n return true;\n }\n if (typeof newValue !== undefined && this[prop] !== newValue) {\n this[prop] = newValue;\n return true;\n }\n },\n\n /**\n * @private\n */\n _moveLeft: function(e, prop) {\n return this._move(e, prop, 'Left');\n },\n\n /**\n * @private\n */\n _moveRight: function(e, prop) {\n return this._move(e, prop, 'Right');\n },\n\n /**\n * Moves cursor left without keeping selection\n * @param {Event} e\n */\n moveCursorLeftWithoutShift: function(e) {\n var change = true;\n this._selectionDirection = 'left';\n\n // only move cursor when there is no selection,\n // otherwise we discard it, and leave cursor on same place\n if (this.selectionEnd === this.selectionStart && this.selectionStart !== 0) {\n change = this._moveLeft(e, 'selectionStart');\n\n }\n this.selectionEnd = this.selectionStart;\n return change;\n },\n\n /**\n * Moves cursor left while keeping selection\n * @param {Event} e\n */\n moveCursorLeftWithShift: function(e) {\n if (this._selectionDirection === 'right' && this.selectionStart !== this.selectionEnd) {\n return this._moveLeft(e, 'selectionEnd');\n }\n else if (this.selectionStart !== 0){\n this._selectionDirection = 'left';\n return this._moveLeft(e, 'selectionStart');\n }\n },\n\n /**\n * Moves cursor right\n * @param {Event} e Event object\n */\n moveCursorRight: function(e) {\n if (this.selectionStart >= this._text.length && this.selectionEnd >= this._text.length) {\n return;\n }\n this._moveCursorLeftOrRight('Right', e);\n },\n\n /**\n * Moves cursor right or Left, fires event\n * @param {String} direction 'Left', 'Right'\n * @param {Event} e Event object\n */\n _moveCursorLeftOrRight: function(direction, e) {\n var actionName = 'moveCursor' + direction + 'With';\n this._currentCursorOpacity = 1;\n\n if (e.shiftKey) {\n actionName += 'Shift';\n }\n else {\n actionName += 'outShift';\n }\n if (this[actionName](e)) {\n this.abortCursorAnimation();\n this.initDelayedCursor();\n this._fireSelectionChanged();\n this._updateTextarea();\n }\n },\n\n /**\n * Moves cursor right while keeping selection\n * @param {Event} e\n */\n moveCursorRightWithShift: function(e) {\n if (this._selectionDirection === 'left' && this.selectionStart !== this.selectionEnd) {\n return this._moveRight(e, 'selectionStart');\n }\n else if (this.selectionEnd !== this._text.length) {\n this._selectionDirection = 'right';\n return this._moveRight(e, 'selectionEnd');\n }\n },\n\n /**\n * Moves cursor right without keeping selection\n * @param {Event} e Event object\n */\n moveCursorRightWithoutShift: function(e) {\n var changed = true;\n this._selectionDirection = 'right';\n\n if (this.selectionStart === this.selectionEnd) {\n changed = this._moveRight(e, 'selectionStart');\n this.selectionEnd = this.selectionStart;\n }\n else {\n this.selectionStart = this.selectionEnd;\n }\n return changed;\n },\n\n /**\n * Removes characters from start/end\n * start/end ar per grapheme position in _text array.\n *\n * @param {Number} start\n * @param {Number} end default to start + 1\n */\n removeChars: function(start, end) {\n if (typeof end === 'undefined') {\n end = start + 1;\n }\n this.removeStyleFromTo(start, end);\n this._text.splice(start, end - start);\n this.text = this._text.join('');\n this.set('dirty', true);\n if (this._shouldClearDimensionCache()) {\n this.initDimensions();\n this.setCoords();\n }\n this._removeExtraneousStyles();\n },\n\n /**\n * insert characters at start position, before start position.\n * start equal 1 it means the text get inserted between actual grapheme 0 and 1\n * if style array is provided, it must be as the same length of text in graphemes\n * if end is provided and is bigger than start, old text is replaced.\n * start/end ar per grapheme position in _text array.\n *\n * @param {String} text text to insert\n * @param {Array} style array of style objects\n * @param {Number} start\n * @param {Number} end default to start + 1\n */\n insertChars: function(text, style, start, end) {\n if (typeof end === 'undefined') {\n end = start;\n }\n if (end > start) {\n this.removeStyleFromTo(start, end);\n }\n var graphemes = fabric.util.string.graphemeSplit(text);\n this.insertNewStyleBlock(graphemes, start, style);\n this._text = [].concat(this._text.slice(0, start), graphemes, this._text.slice(end));\n this.text = this._text.join('');\n this.set('dirty', true);\n if (this._shouldClearDimensionCache()) {\n this.initDimensions();\n this.setCoords();\n }\n this._removeExtraneousStyles();\n },\n\n});\n\n\n/* _TO_SVG_START_ */\n(function() {\n var toFixed = fabric.util.toFixed,\n multipleSpacesRegex = / +/g;\n\n fabric.util.object.extend(fabric.Text.prototype, /** @lends fabric.Text.prototype */ {\n\n /**\n * Returns SVG representation of an instance\n * @param {Function} [reviver] Method for further parsing of svg representation.\n * @return {String} svg representation of an instance\n */\n _toSVG: function() {\n var offsets = this._getSVGLeftTopOffsets(),\n textAndBg = this._getSVGTextAndBg(offsets.textTop, offsets.textLeft);\n return this._wrapSVGTextAndBg(textAndBg);\n },\n\n /**\n * Returns svg representation of an instance\n * @param {Function} [reviver] Method for further parsing of svg representation.\n * @return {String} svg representation of an instance\n */\n toSVG: function(reviver) {\n return this._createBaseSVGMarkup(\n this._toSVG(),\n { reviver: reviver, noStyle: true, withShadow: true }\n );\n },\n\n /**\n * @private\n */\n _getSVGLeftTopOffsets: function() {\n return {\n textLeft: -this.width / 2,\n textTop: -this.height / 2,\n lineTop: this.getHeightOfLine(0)\n };\n },\n\n /**\n * @private\n */\n _wrapSVGTextAndBg: function(textAndBg) {\n var noShadow = true,\n textDecoration = this.getSvgTextDecoration(this);\n return [\n textAndBg.textBgRects.join(''),\n '\\t\\t',\n textAndBg.textSpans.join(''),\n '\\n'\n ];\n },\n\n /**\n * @private\n * @param {Number} textTopOffset Text top offset\n * @param {Number} textLeftOffset Text left offset\n * @return {Object}\n */\n _getSVGTextAndBg: function(textTopOffset, textLeftOffset) {\n var textSpans = [],\n textBgRects = [],\n height = textTopOffset, lineOffset;\n // bounding-box background\n this._setSVGBg(textBgRects);\n\n // text and text-background\n for (var i = 0, len = this._textLines.length; i < len; i++) {\n lineOffset = this._getLineLeftOffset(i);\n if (this.textBackgroundColor || this.styleHas('textBackgroundColor', i)) {\n this._setSVGTextLineBg(textBgRects, i, textLeftOffset + lineOffset, height);\n }\n this._setSVGTextLineText(textSpans, i, textLeftOffset + lineOffset, height);\n height += this.getHeightOfLine(i);\n }\n\n return {\n textSpans: textSpans,\n textBgRects: textBgRects\n };\n },\n\n /**\n * @private\n */\n _createTextCharSpan: function(_char, styleDecl, left, top) {\n var shouldUseWhitespace = _char !== _char.trim() || _char.match(multipleSpacesRegex),\n styleProps = this.getSvgSpanStyles(styleDecl, shouldUseWhitespace),\n fillStyles = styleProps ? 'style=\"' + styleProps + '\"' : '',\n dy = styleDecl.deltaY, dySpan = '',\n NUM_FRACTION_DIGITS = fabric.Object.NUM_FRACTION_DIGITS;\n if (dy) {\n dySpan = ' dy=\"' + toFixed(dy, NUM_FRACTION_DIGITS) + '\" ';\n }\n return [\n '',\n fabric.util.string.escapeXml(_char),\n ''\n ].join('');\n },\n\n _setSVGTextLineText: function(textSpans, lineIndex, textLeftOffset, textTopOffset) {\n // set proper line offset\n var lineHeight = this.getHeightOfLine(lineIndex),\n isJustify = this.textAlign.indexOf('justify') !== -1,\n actualStyle,\n nextStyle,\n charsToRender = '',\n charBox, style,\n boxWidth = 0,\n line = this._textLines[lineIndex],\n timeToRender;\n\n textTopOffset += lineHeight * (1 - this._fontSizeFraction) / this.lineHeight;\n for (var i = 0, len = line.length - 1; i <= len; i++) {\n timeToRender = i === len || this.charSpacing;\n charsToRender += line[i];\n charBox = this.__charBounds[lineIndex][i];\n if (boxWidth === 0) {\n textLeftOffset += charBox.kernedWidth - charBox.width;\n boxWidth += charBox.width;\n }\n else {\n boxWidth += charBox.kernedWidth;\n }\n if (isJustify && !timeToRender) {\n if (this._reSpaceAndTab.test(line[i])) {\n timeToRender = true;\n }\n }\n if (!timeToRender) {\n // if we have charSpacing, we render char by char\n actualStyle = actualStyle || this.getCompleteStyleDeclaration(lineIndex, i);\n nextStyle = this.getCompleteStyleDeclaration(lineIndex, i + 1);\n timeToRender = this._hasStyleChangedForSvg(actualStyle, nextStyle);\n }\n if (timeToRender) {\n style = this._getStyleDeclaration(lineIndex, i) || { };\n textSpans.push(this._createTextCharSpan(charsToRender, style, textLeftOffset, textTopOffset));\n charsToRender = '';\n actualStyle = nextStyle;\n textLeftOffset += boxWidth;\n boxWidth = 0;\n }\n }\n },\n\n _pushTextBgRect: function(textBgRects, color, left, top, width, height) {\n var NUM_FRACTION_DIGITS = fabric.Object.NUM_FRACTION_DIGITS;\n textBgRects.push(\n '\\t\\t\\n');\n },\n\n _setSVGTextLineBg: function(textBgRects, i, leftOffset, textTopOffset) {\n var line = this._textLines[i],\n heightOfLine = this.getHeightOfLine(i) / this.lineHeight,\n boxWidth = 0,\n boxStart = 0,\n charBox, currentColor,\n lastColor = this.getValueOfPropertyAt(i, 0, 'textBackgroundColor');\n for (var j = 0, jlen = line.length; j < jlen; j++) {\n charBox = this.__charBounds[i][j];\n currentColor = this.getValueOfPropertyAt(i, j, 'textBackgroundColor');\n if (currentColor !== lastColor) {\n lastColor && this._pushTextBgRect(textBgRects, lastColor, leftOffset + boxStart,\n textTopOffset, boxWidth, heightOfLine);\n boxStart = charBox.left;\n boxWidth = charBox.width;\n lastColor = currentColor;\n }\n else {\n boxWidth += charBox.kernedWidth;\n }\n }\n currentColor && this._pushTextBgRect(textBgRects, currentColor, leftOffset + boxStart,\n textTopOffset, boxWidth, heightOfLine);\n },\n\n /**\n * Adobe Illustrator (at least CS5) is unable to render rgba()-based fill values\n * we work around it by \"moving\" alpha channel into opacity attribute and setting fill's alpha to 1\n *\n * @private\n * @param {*} value\n * @return {String}\n */\n _getFillAttributes: function(value) {\n var fillColor = (value && typeof value === 'string') ? new fabric.Color(value) : '';\n if (!fillColor || !fillColor.getSource() || fillColor.getAlpha() === 1) {\n return 'fill=\"' + value + '\"';\n }\n return 'opacity=\"' + fillColor.getAlpha() + '\" fill=\"' + fillColor.setAlpha(1).toRgb() + '\"';\n },\n\n /**\n * @private\n */\n _getSVGLineTopOffset: function(lineIndex) {\n var lineTopOffset = 0, lastHeight = 0;\n for (var j = 0; j < lineIndex; j++) {\n lineTopOffset += this.getHeightOfLine(j);\n }\n lastHeight = this.getHeightOfLine(j);\n return {\n lineTop: lineTopOffset,\n offset: (this._fontSizeMult - this._fontSizeFraction) * lastHeight / (this.lineHeight * this._fontSizeMult)\n };\n },\n\n /**\n * Returns styles-string for svg-export\n * @param {Boolean} skipShadow a boolean to skip shadow filter output\n * @return {String}\n */\n getSvgStyles: function(skipShadow) {\n var svgStyle = fabric.Object.prototype.getSvgStyles.call(this, skipShadow);\n return svgStyle + ' white-space: pre;';\n },\n });\n})();\n/* _TO_SVG_END_ */\n\n\n(function(global) {\n\n 'use strict';\n\n var fabric = global.fabric || (global.fabric = {});\n\n /**\n * Textbox class, based on IText, allows the user to resize the text rectangle\n * and wraps lines automatically. Textboxes have their Y scaling locked, the\n * user can only change width. Height is adjusted automatically based on the\n * wrapping of lines.\n * @class fabric.Textbox\n * @extends fabric.IText\n * @mixes fabric.Observable\n * @return {fabric.Textbox} thisArg\n * @see {@link fabric.Textbox#initialize} for constructor definition\n */\n fabric.Textbox = fabric.util.createClass(fabric.IText, fabric.Observable, {\n\n /**\n * Type of an object\n * @type String\n * @default\n */\n type: 'textbox',\n\n /**\n * Minimum width of textbox, in pixels.\n * @type Number\n * @default\n */\n minWidth: 20,\n\n /**\n * Minimum calculated width of a textbox, in pixels.\n * fixed to 2 so that an empty textbox cannot go to 0\n * and is still selectable without text.\n * @type Number\n * @default\n */\n dynamicMinWidth: 2,\n\n /**\n * Cached array of text wrapping.\n * @type Array\n */\n __cachedLines: null,\n\n /**\n * Override standard Object class values\n */\n lockScalingFlip: true,\n\n /**\n * Override standard Object class values\n * Textbox needs this on false\n */\n noScaleCache: false,\n\n /**\n * Properties which when set cause object to change dimensions\n * @type Object\n * @private\n */\n _dimensionAffectingProps: fabric.Text.prototype._dimensionAffectingProps.concat('width'),\n\n /**\n * Use this regular expression to split strings in breakable lines\n * @private\n */\n _wordJoiners: /[ \\t\\r]/,\n\n /**\n * Use this boolean property in order to split strings that have no white space concept.\n * this is a cheap way to help with chinese/japaense\n * @type Boolean\n * @since 2.6.0\n */\n splitByGrapheme: false,\n\n /**\n * Unlike superclass's version of this function, Textbox does not update\n * its width.\n * @private\n * @override\n */\n initDimensions: function() {\n if (this.__skipDimension) {\n return;\n }\n this.isEditing && this.initDelayedCursor();\n this.clearContextTop();\n this._clearCache();\n // clear dynamicMinWidth as it will be different after we re-wrap line\n this.dynamicMinWidth = 0;\n // wrap lines\n this._styleMap = this._generateStyleMap(this._splitText());\n // if after wrapping, the width is smaller than dynamicMinWidth, change the width and re-wrap\n if (this.dynamicMinWidth > this.width) {\n this._set('width', this.dynamicMinWidth);\n }\n if (this.textAlign.indexOf('justify') !== -1) {\n // once text is measured we need to make space fatter to make justified text.\n this.enlargeSpaces();\n }\n // clear cache and re-calculate height\n this.height = this.calcTextHeight();\n this.saveState({ propertySet: '_dimensionAffectingProps' });\n },\n\n /**\n * Generate an object that translates the style object so that it is\n * broken up by visual lines (new lines and automatic wrapping).\n * The original text styles object is broken up by actual lines (new lines only),\n * which is only sufficient for Text / IText\n * @private\n */\n _generateStyleMap: function(textInfo) {\n var realLineCount = 0,\n realLineCharCount = 0,\n charCount = 0,\n map = {};\n\n for (var i = 0; i < textInfo.graphemeLines.length; i++) {\n if (textInfo.graphemeText[charCount] === '\\n' && i > 0) {\n realLineCharCount = 0;\n charCount++;\n realLineCount++;\n }\n else if (!this.splitByGrapheme && this._reSpaceAndTab.test(textInfo.graphemeText[charCount]) && i > 0) {\n // this case deals with space's that are removed from end of lines when wrapping\n realLineCharCount++;\n charCount++;\n }\n\n map[i] = { line: realLineCount, offset: realLineCharCount };\n\n charCount += textInfo.graphemeLines[i].length;\n realLineCharCount += textInfo.graphemeLines[i].length;\n }\n\n return map;\n },\n\n /**\n * Returns true if object has a style property or has it on a specified line\n * @param {Number} lineIndex\n * @return {Boolean}\n */\n styleHas: function(property, lineIndex) {\n if (this._styleMap && !this.isWrapping) {\n var map = this._styleMap[lineIndex];\n if (map) {\n lineIndex = map.line;\n }\n }\n return fabric.Text.prototype.styleHas.call(this, property, lineIndex);\n },\n\n /**\n * Returns true if object has no styling or no styling in a line\n * @param {Number} lineIndex , lineIndex is on wrapped lines.\n * @return {Boolean}\n */\n isEmptyStyles: function(lineIndex) {\n if (!this.styles) {\n return true;\n }\n var offset = 0, nextLineIndex = lineIndex + 1, nextOffset, obj, shouldLimit = false,\n map = this._styleMap[lineIndex], mapNextLine = this._styleMap[lineIndex + 1];\n if (map) {\n lineIndex = map.line;\n offset = map.offset;\n }\n if (mapNextLine) {\n nextLineIndex = mapNextLine.line;\n shouldLimit = nextLineIndex === lineIndex;\n nextOffset = mapNextLine.offset;\n }\n obj = typeof lineIndex === 'undefined' ? this.styles : { line: this.styles[lineIndex] };\n for (var p1 in obj) {\n for (var p2 in obj[p1]) {\n if (p2 >= offset && (!shouldLimit || p2 < nextOffset)) {\n // eslint-disable-next-line no-unused-vars\n for (var p3 in obj[p1][p2]) {\n return false;\n }\n }\n }\n }\n return true;\n },\n\n /**\n * @param {Number} lineIndex\n * @param {Number} charIndex\n * @private\n */\n _getStyleDeclaration: function(lineIndex, charIndex) {\n if (this._styleMap && !this.isWrapping) {\n var map = this._styleMap[lineIndex];\n if (!map) {\n return null;\n }\n lineIndex = map.line;\n charIndex = map.offset + charIndex;\n }\n return this.callSuper('_getStyleDeclaration', lineIndex, charIndex);\n },\n\n /**\n * @param {Number} lineIndex\n * @param {Number} charIndex\n * @param {Object} style\n * @private\n */\n _setStyleDeclaration: function(lineIndex, charIndex, style) {\n var map = this._styleMap[lineIndex];\n lineIndex = map.line;\n charIndex = map.offset + charIndex;\n\n this.styles[lineIndex][charIndex] = style;\n },\n\n /**\n * @param {Number} lineIndex\n * @param {Number} charIndex\n * @private\n */\n _deleteStyleDeclaration: function(lineIndex, charIndex) {\n var map = this._styleMap[lineIndex];\n lineIndex = map.line;\n charIndex = map.offset + charIndex;\n delete this.styles[lineIndex][charIndex];\n },\n\n /**\n * probably broken need a fix\n * Returns the real style line that correspond to the wrapped lineIndex line\n * Used just to verify if the line does exist or not.\n * @param {Number} lineIndex\n * @returns {Boolean} if the line exists or not\n * @private\n */\n _getLineStyle: function(lineIndex) {\n var map = this._styleMap[lineIndex];\n return !!this.styles[map.line];\n },\n\n /**\n * Set the line style to an empty object so that is initialized\n * @param {Number} lineIndex\n * @param {Object} style\n * @private\n */\n _setLineStyle: function(lineIndex) {\n var map = this._styleMap[lineIndex];\n this.styles[map.line] = {};\n },\n\n /**\n * Wraps text using the 'width' property of Textbox. First this function\n * splits text on newlines, so we preserve newlines entered by the user.\n * Then it wraps each line using the width of the Textbox by calling\n * _wrapLine().\n * @param {Array} lines The string array of text that is split into lines\n * @param {Number} desiredWidth width you want to wrap to\n * @returns {Array} Array of lines\n */\n _wrapText: function(lines, desiredWidth) {\n var wrapped = [], i;\n this.isWrapping = true;\n for (i = 0; i < lines.length; i++) {\n wrapped = wrapped.concat(this._wrapLine(lines[i], i, desiredWidth));\n }\n this.isWrapping = false;\n return wrapped;\n },\n\n /**\n * Helper function to measure a string of text, given its lineIndex and charIndex offset\n * it gets called when charBounds are not available yet.\n * @param {CanvasRenderingContext2D} ctx\n * @param {String} text\n * @param {number} lineIndex\n * @param {number} charOffset\n * @returns {number}\n * @private\n */\n _measureWord: function(word, lineIndex, charOffset) {\n var width = 0, prevGrapheme, skipLeft = true;\n charOffset = charOffset || 0;\n for (var i = 0, len = word.length; i < len; i++) {\n var box = this._getGraphemeBox(word[i], lineIndex, i + charOffset, prevGrapheme, skipLeft);\n width += box.kernedWidth;\n prevGrapheme = word[i];\n }\n return width;\n },\n\n /**\n * Wraps a line of text using the width of the Textbox and a context.\n * @param {Array} line The grapheme array that represent the line\n * @param {Number} lineIndex\n * @param {Number} desiredWidth width you want to wrap the line to\n * @param {Number} reservedSpace space to remove from wrapping for custom functionalities\n * @returns {Array} Array of line(s) into which the given text is wrapped\n * to.\n */\n _wrapLine: function(_line, lineIndex, desiredWidth, reservedSpace) {\n var lineWidth = 0,\n splitByGrapheme = this.splitByGrapheme,\n graphemeLines = [],\n line = [],\n // spaces in different languges?\n words = splitByGrapheme ? fabric.util.string.graphemeSplit(_line) : _line.split(this._wordJoiners),\n word = '',\n offset = 0,\n infix = splitByGrapheme ? '' : ' ',\n wordWidth = 0,\n infixWidth = 0,\n largestWordWidth = 0,\n lineJustStarted = true,\n additionalSpace = splitByGrapheme ? 0 : this._getWidthOfCharSpacing(),\n reservedSpace = reservedSpace || 0;\n // fix a difference between split and graphemeSplit\n if (words.length === 0) {\n words.push([]);\n }\n desiredWidth -= reservedSpace;\n for (var i = 0; i < words.length; i++) {\n // if using splitByGrapheme words are already in graphemes.\n word = splitByGrapheme ? words[i] : fabric.util.string.graphemeSplit(words[i]);\n wordWidth = this._measureWord(word, lineIndex, offset);\n offset += word.length;\n\n lineWidth += infixWidth + wordWidth - additionalSpace;\n\n if (lineWidth >= desiredWidth && !lineJustStarted) {\n graphemeLines.push(line);\n line = [];\n lineWidth = wordWidth;\n lineJustStarted = true;\n }\n else {\n lineWidth += additionalSpace;\n }\n\n if (!lineJustStarted && !splitByGrapheme) {\n line.push(infix);\n }\n line = line.concat(word);\n\n infixWidth = this._measureWord([infix], lineIndex, offset);\n offset++;\n lineJustStarted = false;\n // keep track of largest word\n if (wordWidth > largestWordWidth) {\n largestWordWidth = wordWidth;\n }\n }\n\n i && graphemeLines.push(line);\n\n if (largestWordWidth + reservedSpace > this.dynamicMinWidth) {\n this.dynamicMinWidth = largestWordWidth - additionalSpace + reservedSpace;\n }\n\n return graphemeLines;\n },\n\n /**\n * Detect if the text line is ended with an hard break\n * text and itext do not have wrapping, return false\n * @param {Number} lineIndex text to split\n * @return {Boolean}\n */\n isEndOfWrapping: function(lineIndex) {\n if (!this._styleMap[lineIndex + 1]) {\n // is last line, return true;\n return true;\n }\n if (this._styleMap[lineIndex + 1].line !== this._styleMap[lineIndex].line) {\n // this is last line before a line break, return true;\n return true;\n }\n return false;\n },\n\n /**\n * Detect if a line has a linebreak and so we need to account for it when moving\n * and counting style.\n * @return Number\n */\n missingNewlineOffset: function(lineIndex) {\n if (this.splitByGrapheme) {\n return this.isEndOfWrapping(lineIndex) ? 1 : 0;\n }\n return 1;\n },\n\n /**\n * Gets lines of text to render in the Textbox. This function calculates\n * text wrapping on the fly every time it is called.\n * @param {String} text text to split\n * @returns {Array} Array of lines in the Textbox.\n * @override\n */\n _splitTextIntoLines: function(text) {\n var newText = fabric.Text.prototype._splitTextIntoLines.call(this, text),\n graphemeLines = this._wrapText(newText.lines, this.width),\n lines = new Array(graphemeLines.length);\n for (var i = 0; i < graphemeLines.length; i++) {\n lines[i] = graphemeLines[i].join('');\n }\n newText.lines = lines;\n newText.graphemeLines = graphemeLines;\n return newText;\n },\n\n getMinWidth: function() {\n return Math.max(this.minWidth, this.dynamicMinWidth);\n },\n\n _removeExtraneousStyles: function() {\n var linesToKeep = {};\n for (var prop in this._styleMap) {\n if (this._textLines[prop]) {\n linesToKeep[this._styleMap[prop].line] = 1;\n }\n }\n for (var prop in this.styles) {\n if (!linesToKeep[prop]) {\n delete this.styles[prop];\n }\n }\n },\n\n /**\n * Returns object representation of an instance\n * @method toObject\n * @param {Array} [propertiesToInclude] Any properties that you might want to additionally include in the output\n * @return {Object} object representation of an instance\n */\n toObject: function(propertiesToInclude) {\n return this.callSuper('toObject', ['minWidth', 'splitByGrapheme'].concat(propertiesToInclude));\n }\n });\n\n /**\n * Returns fabric.Textbox instance from an object representation\n * @static\n * @memberOf fabric.Textbox\n * @param {Object} object Object to create an instance from\n * @param {Function} [callback] Callback to invoke when an fabric.Textbox instance is created\n */\n fabric.Textbox.fromObject = function(object, callback) {\n return fabric.Object._fromObject('Textbox', object, callback, 'text');\n };\n})(typeof exports !== 'undefined' ? exports : this);\n\n","import {initProdTileCarousel} from './productTileCarousel';\nimport {forceLockScroll, forceUnlockScroll, preventDefault, genericAjaxCall} from '../util/common';\nexport {initProductTile, initSlotCarousel, closeAllQuickAdd};\n\n// SELECTOR ELEMENT CLASS USED LIST\nconst PREVENT_DEFAULT = '.js-prevent-link';\nconst PRODUCT_GRID_PLP = '.js-plp-productGrid';\nconst PRODUCT_TILE = '.js-prodTile';\nconst QUICKADD_BUTTON = '.js-prodTile-quickAdd-button';\nconst QUICKADD_CLOSE = '.js-prodTile-quickAdd-modal-closeQuickAdd';\nconst QUICKADD_MODAL = '.js-prodTile-quickAdd-modal';\nconst QUICKADD_MODAL_OVERFLOW = '.js-prodTile-quickAdd-modal-overflow';\nconst QUICKADD_MODAL_SLIDER = '.js-quickAdd-modal-container';\nconst QUICKADD_PROCEEDBUTTON = '.js-prodTile-quickAdd-modal-confirmButton';\nconst QUICKADD_SIZEBUTTON = '.js-prodTile-quickAdd-modal-sizes-button';\nconst QUICKADD_SIZEBUTTON_SELECTED = '.js-prodTile-quickAdd-modal-size_selected';\nconst QUICKADD_SIZESELECTED_LABEL = '.js-prodTile-quickAdd-modal-sizeSelected';\n\nlet isOpened = false;\n\n// LIST OF STYLE CLASS USED\nconst STYLE_QUICKADD_SIZEBUTTON_SELECTED =\n 'cc-prodTile-quickAdd-modal-sizes-button_selected js-prodTile-quickAdd-modal-size_selected';\nconst QUICKADD_MODAL_OPEN = 'js-prodTile-quickAdd-modal_open';\n\nfunction initProductTile() {\n if ($('.page').data('action') === 'Search-Show') {\n initOnlyPLP();\n } else {\n initProdTileCarousel();\n $(QUICKADD_BUTTON).off('click').on('click', openQuickAdd);\n $(PRODUCT_TILE).off('click').on('click', PREVENT_DEFAULT, preventDefault);\n }\n\n if ($('.js-suggestedProducts-container').length) {\n initSlotCarousel('.js-suggestedProducts-container');\n }\n\n if ($('.js-completeLook').length) {\n initSlotCarousel('.js-completeLook');\n }\n\n if ($('.js-completePromo').length) {\n initSlotCarousel('.js-completePromo');\n }\n\n $(window).on('resize', onResizeFunction);\n}\n\nfunction initSlotCarousel(containerClassName) {\n $(containerClassName)\n .off('click')\n .on('click', QUICKADD_BUTTON, openQuickAdd)\n .on('click', PREVENT_DEFAULT, preventDefault);\n\n if ($('.js-site-search').hasClass('cc-site-search_open') && !Foundation.MediaQuery.atLeast('large')) {\n $('.js-prodTile-quickAdd-modal').addClass('js-quickAdd-modal-container');\n }\n}\n\nfunction initOnlyPLP() {\n if ($(PRODUCT_GRID_PLP).length > 0) {\n initProdTileCarousel(PRODUCT_GRID_PLP);\n initSlotCarousel(PRODUCT_GRID_PLP);\n removeGridFullBanner();\n }\n}\n\nfunction removeGridFullBanner () {\n $('.cc-gridFullBanner-wrp').each(function (i, element) {\n if ($(element).children().length <= 0) {\n $(element).remove();\n }\n });\n}\n\nfunction openQuickAdd(e) {\n if (e.currentTarget.classList.contains('analytics-sizeBox') &&\n e.currentTarget.classList.contains('js-prodTile-quickAdd-button')) {\n $('body').trigger('product:selectSize', e.currentTarget);\n }\n e.preventDefault();\n e.stopPropagation();\n\n let $this = $(this);\n let url = $(this).data('url');\n let $modal = $(this).siblings(QUICKADD_MODAL);\n let $modalForSlider = $(QUICKADD_MODAL_SLIDER);\n let isCompletePromo = false;\n\n // Needed because we have two modals in position fixed one inside the other\n if ($('.js-site-search').hasClass('cc-site-search_open') && !Foundation.MediaQuery.atLeast('large')) {\n $('.js-site-search').after($modalForSlider);\n }\n\n if ($(this).closest('.js-hpShoppable').length > 0) {\n if (Foundation.MediaQuery.atLeast('large')) {\n openQuickAddShoppable($this, url, $modal);\n return;\n } else {\n $modal = $modalForSlider.first();\n }\n } else if (\n $(this).closest('.cc-emCarouselEditProd').length > 0 &&\n !Foundation.MediaQuery.atLeast('large')\n ) {\n $modal = $modalForSlider.first();\n } else {\n if (\n $(this).closest('.slick-track').length &&\n $modalForSlider.length &&\n !Foundation.MediaQuery.atLeast('large')\n ) {\n $modal = $modalForSlider.first();\n } else if (\n $(this).closest('.cc-completeYourPromo-productCards, .cc-productCarousel-coreMedia').length > 0 &&\n !Foundation.MediaQuery.atLeast('large')\n ) {\n let $quickAddOutsideModal = $('.js-quickAdd-modal-container').eq(0).clone();\n if ($('body > .js-quickAdd-modal-container').length === 0) {\n $('body').prepend($quickAddOutsideModal);\n }\n\n if ($(this).closest('.cc-completeYourPromo-productCards').length > 0) {\n isCompletePromo = true;\n }\n\n $modal = $('body > .js-quickAdd-modal-container');\n }\n }\n\n const analytics = $this.closest('.js-prodTile').find('.analytics.productListingItem').data();\n $modal.data('item_list_id', analytics.item_list_id);\n $modal.data('item_list_name', analytics.item_list_name);\n $modal.data('index', analytics.index);\n\n genericAjaxCall(url, null, null, false).then(function (data) {\n var newDOMModal = $(data).clone();\n $modal.empty().html(newDOMModal);\n\n $modal.slideDown({\n start: function () {\n $modal.css({display: 'flex'}).addClass(QUICKADD_MODAL_OPEN);\n $('body').addClass('veiled-for-small-only');\n if (isCompletePromo) {\n $('body').addClass('veiled-for-small-only_higher');\n }\n },\n complete: function () {\n $modal.on('click', QUICKADD_CLOSE, {modal: $modal}, closeQuickAdd);\n $modal.on('click', QUICKADD_SIZEBUTTON, {modal: $modal}, prepareAddToCart);\n searchSelectedSize($modal);\n if (!Foundation.MediaQuery.atLeast('large')) {\n forceLockScroll();\n // closeDrawerWithGesture($modal); comment for the moment\n }\n },\n });\n });\n}\n\nfunction openQuickAddShoppable($this, url, $modal) {\n if (!isOpened || !$modal.hasClass('quickAdd-opened')) {\n isOpened = true;\n // Handle the button rotation when opens in shoppable image banner\n $this.addClass('cm-rotateQuickAddButton');\n genericAjaxCall(url, null, null, true).then(function (data) {\n var newDOMModal = $(data).clone();\n $modal.empty().html(newDOMModal);\n $modal\n .closest('.cc-emShoppable__productCard')\n .addClass('cc-emShoppable__productCard--opened quickAdd-opened');\n $modal.addClass('cc-customModalOpened');\n $('.cc-emShoppableVideo__productCard:not(.cc-active)').removeClass('cc-emShoppable__productCard--opened quickAdd-opened');\n $('.cc-emShoppableVideo__productCard:not(.cc-active)').find('.js-prodTile-quickAdd-modal').removeClass('cc-customModalOpened');\n $this.on('click', {modal: $modal}, closeQuickAddShoppable);\n $modal.on('click', QUICKADD_SIZEBUTTON, {modal: $modal}, prepareAddToCart);\n searchSelectedSize($modal);\n });\n }\n}\n\nfunction closeQuickAdd(e, $modal) {\n try {\n e.preventDefault();\n } catch (exc) {}\n\n if (!Foundation.MediaQuery.atLeast('large')) {\n forceUnlockScroll();\n }\n\n var modal = $modal ? $modal : e.data.modal;\n\n modal.slideUp({\n complete: function () {\n modal.removeClass(QUICKADD_MODAL_OPEN);\n $('body').removeClass('veiled-for-small-only veiled-for-small-only_higher');\n },\n });\n modal.off('click', QUICKADD_CLOSE).off('click', QUICKADD_SIZEBUTTON);\n modal.find(QUICKADD_PROCEEDBUTTON).off('click');\n}\n\nfunction closeQuickAddShoppable(e) {\n try {\n e.preventDefault();\n e.stopPropagation();\n } catch (exc) {}\n\n let $modal = e.data.modal;\n isOpened = false;\n // Handle the button rotation when closes in shoppable image banner\n const closeQuickButton = $(e.currentTarget);\n if (closeQuickButton.hasClass('cm-rotateQuickAddButton')) {\n closeQuickButton.removeClass('cm-rotateQuickAddButton');\n }\n\n $modal\n .closest('.cc-emShoppable__productCard')\n .removeClass('cc-emShoppable__productCard--opened quickAdd-opened');\n $modal.removeClass('cc-customModalOpened');\n $(QUICKADD_BUTTON).off('click');\n $modal.off('click', QUICKADD_CLOSE).off('click', QUICKADD_SIZEBUTTON);\n $modal.find(QUICKADD_PROCEEDBUTTON).off('click');\n}\n\nfunction closeDrawerWithGesture(modal) {\n var modalContainer = modal;\n\n const scrollElement = modalContainer.find(QUICKADD_MODAL_OVERFLOW)[0];\n\n var hammertime = new Hammer(modalContainer[0]);\n hammertime.get('swipe').set({direction: Hammer.DIRECTION_VERTICAL});\n hammertime.get('pan').set({direction: Hammer.DIRECTION_VERTICAL});\n\n const isScrollable = scrollElement.scrollHeight > scrollElement.clientHeight;\n\n var startY,\n scrollTop = 0;\n\n if (isScrollable) {\n let actionStart = false;\n hammertime.on('panstart', function (e) {\n actionStart = true;\n startY = e.deltaY - scrollElement.offsetTop;\n scrollTop = scrollElement.scrollTop;\n });\n hammertime.on('panend', function (e) {\n actionStart = false;\n });\n hammertime.on('panmove', function (e) {\n if (!actionStart) {\n return;\n }\n const y = e.deltaY - scrollElement.offsetTop;\n const scroll = y - startY;\n scrollElement.scrollTop = scrollTop - scroll;\n });\n }\n\n hammertime.on('swipedown', function (e) {\n if (isScrollable && (scrollElement.scrollTop !== 0 || scrollTop > 30)) {\n return;\n }\n\n closeQuickAdd(e, modal);\n hammertime.off('swipedown panmove panend panstart').destroy();\n });\n}\n\n/**\n * function for close all the quickadd open with screen device is in large breakpoint\n */\nfunction closeAllQuickAdd() {\n let allQAopen = $('.' + QUICKADD_MODAL_OPEN);\n if (allQAopen.length > 0) {\n allQAopen.each(function () {\n closeQuickAdd(null, $(this));\n });\n }\n}\n\nfunction searchSelectedSize($modal) {\n var selectSize = $modal.find(QUICKADD_SIZEBUTTON_SELECTED);\n if (selectSize.length) {\n $modal.find(QUICKADD_SIZESELECTED_LABEL).empty().html(selectSize.data('name'));\n }\n}\n\nfunction prepareAddToCart(e) {\n var sizeButton = $(this);\n if (sizeButton.hasClass('notifyMe')) {\n return;\n }\n e.data.modal.find(QUICKADD_SIZEBUTTON).removeClass(STYLE_QUICKADD_SIZEBUTTON_SELECTED);\n sizeButton.addClass(STYLE_QUICKADD_SIZEBUTTON_SELECTED);\n\n const prepareData = {\n form: {\n pid: sizeButton.data('pid'),\n quantity: 1,\n GTMItemListName: e.data.modal.data('item_list_name'),\n GTMItemListId: e.data.modal.data('item_list_id'),\n GTMIndex: e.data.modal.data('index')\n },\n addToCartUrl: sizeButton.data('url'),\n modal: e.data.modal,\n $productContainer: sizeButton.closest('.js-prodTile')\n };\n\n searchSelectedSize(e.data.modal);\n\n if (Foundation.MediaQuery.atLeast('large')) {\n // desktop version\n makeAddToCart({data: prepareData});\n } else {\n // mobile version\n e.data.modal\n .find(QUICKADD_PROCEEDBUTTON)\n .attr('disabled', false)\n .on('click', prepareData, makeAddToCart);\n }\n}\n\nfunction makeAddToCart(e) {\n let $modal = e.data.modal;\n var dataValue = e.data;\n genericAjaxCall(dataValue.addToCartUrl, 'POST', dataValue.form).then(function (data) {\n if (data.error === false) {\n $('body').trigger('product:didChangeSizeQuickAddToCart', {\n ...data,\n form: dataValue.form,\n $productContainer: dataValue.$productContainer\n });\n\n $('body').trigger('product:afterAddToCart', {\n ...data,\n form: dataValue.form,\n $productContainer: dataValue.$productContainer,\n });\n handlePostCartAdd(data);\n\n if ($modal.closest('.js-hpShoppable').length > 0) {\n if (Foundation.MediaQuery.atLeast('large')) {\n closeQuickAddShoppable(e);\n return;\n }\n }\n\n closeAllQuickAdd();\n }\n });\n}\n\nfunction handlePostCartAdd(response) {\n $('body').trigger('count:update', response);\n // show add to cart toast\n if (response.error) {\n return;\n }\n if ($('.add-to-cart-messages').length === 0) {\n $('body').append('
');\n }\n if ($('.page[data-action=\"Cart-Show\"]').length > 0) {\n if (history.scrollRestoration) {\n history.scrollRestoration = 'manual';\n }\n $('html').animate({scrollTop: 0}, 500);\n }\n}\n\nfunction onResizeFunction() {\n closeAllQuickAdd();\n forceUnlockScroll();\n}\n","export default function () {\n // QuickView\n $('.js-carousel-select-color-quickview').slick({\n slidesToShow: 6,\n slidesToScroll: 2,\n infinite: false,\n variableWidth: true,\n responsive: [\n {\n breakpoint: 769,\n settings: {\n slidesToShow: 10,\n slidesToScroll: 2\n }\n },\n {\n breakpoint: 640,\n settings: {\n slidesToShow: 6,\n slidesToScroll: 2\n }\n }\n ]\n\n });\n}\n","var g;\n\n// This works in non-strict mode\ng = (function() {\n\treturn this;\n})();\n\ntry {\n\t// This works if eval is allowed (see CSP)\n\tg = g || new Function(\"return this\")();\n} catch (e) {\n\t// This works if the window reference is available\n\tif (typeof window === \"object\") g = window;\n}\n\n// g can still be undefined, but nothing to do about it...\n// We return undefined, instead of nothing here, so it's\n// easier to handle this case. if(!global) { ...}\n\nmodule.exports = g;\n","export {initProdTileCarousel, unslickProdTileCarousel};\n\nconst IMAGE_CONTAINER_CAROUSEL_CLASS = '.js-prodTile-imageContainer-carousel';\n\nfunction initProdTileCarousel (containerClass) {\n const $tileCarousel = containerClass\n ? $(containerClass + ' ' + IMAGE_CONTAINER_CAROUSEL_CLASS)\n : $(IMAGE_CONTAINER_CAROUSEL_CLASS);\n\n if ($tileCarousel) {\n loadLazyVideo();\n $tileCarousel.on('init', function () {\n $(this).find('.slick-arrow').addClass('js-prevent-link');\n $(this).find('.slick-dots').addClass('js-prevent-link');\n\n var previousLabel = $('.js-fetch-slick-previous-label').data('label');\n $(this).find('.slick-arrow.slick-prev').attr('aria-label', previousLabel);\n var nextLabel = $('.js-fetch-slick-next-label').data('label');\n $(this).find('.slick-arrow.slick-next').attr('aria-label', nextLabel);\n });\n $tileCarousel.slick({\n lazyLoad: 'ondemand',\n draggable: true,\n dots: true,\n accessibility: false,\n arrows: true,\n responsive: [\n {\n breakpoint: 1023,\n settings: {\n arrows: false,\n },\n },\n ],\n });\n }\n}\n\nfunction unslickProdTileCarousel (containerClass) {\n const $tileCarousel = containerClass\n ? $(containerClass + ' ' + IMAGE_CONTAINER_CAROUSEL_CLASS + '.slick-initialized')\n : $(IMAGE_CONTAINER_CAROUSEL_CLASS + '.slick-initialized');\n\n if ($tileCarousel) {\n $tileCarousel.slick('unslick');\n }\n}\n\nfunction loadLazyVideo () {\n const lazyloadclass = 'js-customLazyload';\n let lazyVideos = [].slice.call(document.querySelectorAll('.' + lazyloadclass));\n\n let lazyVideoObserver = new IntersectionObserver(function (entries) {\n entries.forEach(function (video) {\n if (video.isIntersecting) {\n for (let source in video.target.children) {\n let videoSource = video.target.children[source];\n if (\n typeof videoSource.tagName === 'string' &&\n videoSource.tagName === 'SOURCE'\n ) {\n videoSource.src = videoSource.dataset.src;\n }\n }\n\n video.target.load();\n video.target.classList.remove(lazyloadclass);\n lazyVideoObserver.unobserve(video.target);\n }\n });\n });\n\n lazyVideos.forEach(function (lazyVideo) {\n lazyVideoObserver.observe(lazyVideo);\n });\n}\n","// import tingle from 'tingle.js';\n// import ProductHelpers from './base';\nimport { newModal } from '../components/modal';\nimport productSlider from '../components/productSlider';\n// let wishlist = require('./wishlistHeart');\n\n/**\n * replaces the content in the modal window on for the selected product variation.\n * @param {string} productUrl - url to be used for going to the product details page\n * @param {string} selectedValueUrl - url to be used to retrieve a new product model\n */\nconst fillModalElement = (productUrl, selectedValueUrl, modal) => {\n $.ajax({\n url: selectedValueUrl,\n method: 'GET',\n dataType: 'json',\n success: html => {\n modal.setContent(html.renderedTemplate);\n $('.product-quickview .carousel-inner').slick({\n arrows: true,\n dots: false\n });\n productSlider();\n // wishlist.highlightIconsForAllItemsInWishlist();\n modal.open();\n\n localStorage.setItem('prevlisttype', localStorage.getItem('listtype'));\n localStorage.setItem('listtype', 'landing');\n localStorage.setItem('prevlisttypeforcart', localStorage.getItem('listtypeforcart'));\n localStorage.setItem('listtypeforcart', 'landing');\n $('body').trigger('product:productLanding');\n\n if (document.getElementById('TU')) {\n document.getElementById('TU').click();\n }\n $(modal.modalBox)\n .find('.close-custom')\n .on('click', function (e) {\n modal.close();\n modal.destroy();\n });\n\n const destroyModal = () => {\n try {\n modal.close();\n modal.destroy();\n } catch (e) {};\n // remove the event listener to manage cases where the modal\n // is opened two or more times, (removes console error)\n $(document).off('product:afterAddToCart', destroyModal);\n };\n\n $(document).on('product:afterAddToCart', destroyModal);\n },\n error: err => {\n console.log('Error:', err);\n }\n });\n};\n\nconst addToCartFromListing = (pid, promoId, $productContainer) => {\n $.spinner().start();\n var form = {\n pid: pid,\n quantity: 1,\n options: [],\n promoId: promoId\n };\n var url = $('#tileAddToCartUrl').data('url');\n $.ajax({\n url: url,\n type: 'post',\n dataType: 'json',\n data: form,\n success: function (response) {\n if (response) {\n $('.js-mainHeader-minicart').trigger('count:update', response);\n localStorage.setItem('lastClickedPosition', '');\n localStorage.setItem('listtype', 'listing');\n // $(\"body, html\").animate({ scrollTop: 0 }, 500, 'swing');\n $('body').trigger('product:afterAddToCart', {\n ...response,\n form,\n $productContainer\n });\n $('body').trigger('product:afterQuickBuyListing', response);\n } else {\n console.error('Ajax: Empty Response');\n }\n $.spinner().stop();\n },\n error: function (err) {\n console.error('ErrorCase: ' + err.message);\n $.spinner().stop();\n }\n });\n};\n\nclass QuickView {\n run () {\n this.showQuickview();\n this.observeQuickBuy();\n }\n\n showQuickview () {\n $('body').on('click', '.quickview', function (e) {\n e.stopPropagation();\n e.preventDefault();\n const selectedValueUrl = $(this).attr('href');\n const productUrl = selectedValueUrl.replace('Product-ShowQuickView', 'Product-Show');\n const modal = newModal(false, ['quickview-modal']);\n fillModalElement(productUrl, selectedValueUrl, modal);\n\n // trigger for analytics product detail event\n const target = $(this).closest('.product');\n if (target.length > 0) {\n $('body').trigger('product:analyticsProductDetails', target);\n }\n });\n }\n\n observeQuickBuy () {\n $('body').on('click', '.js-quick-buy-sizes-item-select', function (e) {\n e.preventDefault();\n if ($(this).hasClass('disable') || !$(this).data('variant')) {\n return false;\n }\n var url = $(this).data('variant');\n\n var pid = $(e.currentTarget).data('pid');\n $(`.js-quick-buy-sizes-item[data-pid=\"${pid}\"]`).attr('variant', url);\n });\n $('body').on('click', '.js-quick-buy-sizes-item', function (e) {\n e.preventDefault();\n\n var url = $(this).attr('variant');\n $.spinner().start();\n $.ajax({\n url: url,\n type: 'GET',\n dataType: 'json',\n success: function (response) {\n $.spinner().stop();\n const $productContainer = $(e.target);\n if (response.product.available && !response.product.comingSoon) {\n addToCartFromListing(response.product.id, false, $productContainer);\n } else {\n $('body').trigger('product:afterAddToCartFailed', {\n ...response,\n $productContainer\n });\n }\n },\n error: function (err) {\n console.error('ErrorCase: ' + err.message);\n $.spinner().stop();\n }\n });\n });\n }\n}\n// const quickView = new QuickView();\nexport default QuickView;\nexport { addToCartFromListing };\n","'use strict';\n\nimport { newModalFromString } from '../components/modal';\nimport FormHelpers, { addInputClearIcon } from '../util/form';\n\n/**\n * Checks if the email value entered is correct format\n * @param {string} email - email string to check if valid\n * @returns {boolean} Whether email is valid\n */\nfunction validateEmail (email) {\n var regex = /^[\\w.%+-]+@[\\w.-]+\\.[\\w]{2,6}$/;\n return regex.test(email);\n}\n\nclass NotifyHelper {\n notifyMeModal () {\n $('body').on('click', '.js-intProductDetail-size-item', (e) => {\n if (!$(e.currentTarget).find('.notifyMe').length) {\n return;\n }\n e.preventDefault();\n let actualDiv = $(e.currentTarget).find('.notifyMe');\n this.notifyMeAction(actualDiv);\n });\n\n $('body').on('click', '.notifyMe', (e) => {\n e.preventDefault();\n this.notifyMeAction(e.currentTarget);\n });\n }\n\n notifyMeAction (notifyMeDiv) {\n var paramUrl = $(notifyMeDiv).siblings().attr('data-variation-url');\n if (!paramUrl) {\n paramUrl = $(notifyMeDiv).siblings().attr('data-url');\n }\n if ($('.js-notifyMeModal').length > 0 || $(notifyMeDiv).hasClass('js-size-personalizable')) {\n return;\n }\n if ($(notifyMeDiv).hasClass('notifyPopup')) {\n $('.js-prod-select-size-modal').remove();\n paramUrl = $(notifyMeDiv).attr('data-url');\n }\n $('.js-notifyMeModal-titleNotComingSoon').removeClass('hidden');\n $('.js-notifyMeModal-subTitleNotComingSoon').removeClass('hidden');\n $('.js-notifyMeModal-titleComingSoon').addClass('hidden');\n $('.js-notifyMeModal-subTitleComingSoon').addClass('hidden');\n let isComingSoon = $(notifyMeDiv).siblings().attr('data-iscomingsoon') == 'true';\n if (isComingSoon) {\n $('.js-notifyMeModal-titleNotComingSoon').addClass('hidden');\n $('.js-notifyMeModal-subTitleNotComingSoon').addClass('hidden');\n $('.js-notifyMeModal-titleComingSoon').removeClass('hidden');\n $('.js-notifyMeModal-subTitleComingSoon').removeClass('hidden');\n }\n $('.js-notifyMeModal-toHide').removeClass('hidden');\n $('.js-notifyMeModal-toShow').addClass('hidden');\n $('.js-notifyMeModal-notifyBtn').parent().removeClass('hidden');\n $('.continueShopping').addClass('hidden');\n $('.js-notifyMeModal-emailError').addClass('hidden');\n $('.js-notifyMeModal-duplicateError').addClass('hidden');\n const htmlContent = $($(this).data('target')).html();\n // create and open confirmation modal\n const modal = newModalFromString(htmlContent, false, [\n 'cc-notifyMeModal',\n 'js-notifyMeModal',\n ]);\n if ($('.page').data('action') !== 'Product-Show') {\n $(modal.modalBox).addClass(\n 'cc-hide-findInStoreButton'\n );\n }\n $(modal.modalBox).addClass(\n 'rightModalAttribute cc-notifyMeModal-modalBox rightModalAttribute_sizeMedium'\n );\n let size = $(notifyMeDiv).innerText;\n $('.sizeNotify').html(size);\n\n let quickAddFlow = $(notifyMeDiv).hasClass('notifyMeQuickAdd');\n // Retrieve images from correct SKU (e.g: big cup models)\n var url = $('#notifyMeModalImageUrl').val();\n var pid;\n var selectedColor;\n var selectedSize;\n\n if (quickAddFlow) {\n pid = $(notifyMeDiv).data('pid');\n selectedColor = $(notifyMeDiv).data('color').split(' - ')[1]\n ? $(notifyMeDiv).data('color').split(' - ')[1].trim()\n : '';\n selectedSize = $(notifyMeDiv).data('value');\n } else {\n pid = decodeURIComponent($('.product-detail').attr('data-variant-pid'));\n selectedColor = $('[data-attr=\"color\"] .swatch-value.selected').data('attr-value');\n selectedSize =\n $(notifyMeDiv).closest('label').find('input').data('size-id') + '';\n selectedSize = selectedSize.replaceAll('/', '\\\\/');\n $('[data-attr=\"size\"] #' + selectedSize).prop('checked', true);\n }\n\n $.ajax({\n url: url,\n type: 'GET',\n data: {\n pid: pid,\n color: selectedColor,\n size: selectedSize,\n },\n }).then(function (rsp) {\n modal.setContent(rsp.renderedTemplate);\n\n if ($('.quickview-modal').hasClass('tingle-modal--visible') && !$('.quickview-modal').hasClass('js-notifyMe-modal')) {\n $('.quickview-modal').remove();\n }\n\n modal.open();\n if ($('.js-complete-your-promo-quick-view').length > 0) {\n $(modal.modalBox).find('#findInStore-modal').addClass('hide');\n }\n // Enable addInputClearIcon inside class FormHelpers\n FormHelpers.init($('.js-notifyMeModal'));\n // Call addInputClearIcon for the current or every future input in this modal.\n $('input[type=text],input[type=email]').each(function (index, inputItem) {\n addInputClearIcon(inputItem);\n });\n });\n\n $(modal.modalBox).on('click', '.js-notifyMeModal-close', (e) => {\n modal.close();\n modal.destroy();\n });\n\n $(modal.modalBox).on('click', '.continue-shopping-link', (e) => {\n e.preventDefault();\n let sku = $('div.notifyMeModal').data('master-pid') || '';\n let productName = $('.analytics.product').data('name') || '';\n productName = productName.replace(/\\s\\s+/g, ' ').split(' ').join('_');\n $('body').trigger('soldout:popupActions', {\n cta: $(e.currentTarget).data('analytics-action'),\n productName: productName,\n size: $('.sizeNotify').text().trim(),\n sku,\n });\n modal.close();\n modal.destroy();\n });\n\n $(modal.modalBox).on('click', '.analytics-notify-popup-actions', (e) => {\n e.preventDefault();\n let sku = $('div.notifyMeModal').data('master-pid') || '';\n let productName = $('.analytics.product').data('name') || '';\n productName = productName.replace(/\\s\\s+/g, ' ').split(' ').join('_');\n $('body').trigger('soldout:popupActions', {\n cta: $(e.currentTarget).data('analytics-action'),\n productName: productName,\n size: $('.sizeNotify').text().trim(),\n sku,\n });\n });\n\n $(modal.modalBox).on('click', '.js-notifyMeModal-notifyBtn', (e) => {\n let email = $('#emailNotify').val();\n let isValid = validateEmail(email);\n let type = !isComingSoon ? 'back-in-stock' : 'coming-soon';\n let queryString = paramUrl.split('Product-Variation')[1];\n let productName = $('.analytics.product.hidden').attr('data-item_name') || '';\n let analyticsSku = $('div.notifyMeModal').data('master-pid') || '';\n productName = productName.replace(/\\s\\s+/g, ' ').split(' ').join('_');\n\n if (isValid) {\n let dataForm = {\n sku: $('#skuNotify').val(),\n owner: email,\n type: type,\n };\n let url = $('.notify-url').val();\n $.spinner().start();\n $.ajax({\n url: url + queryString,\n method: 'POST',\n dataType: 'json',\n data: dataForm,\n success: (data) => {\n $.spinner().stop();\n if (data.success) {\n $('.js-notifyMeModal-toHide').addClass('hidden');\n if (isComingSoon) {\n $('#messageGreen').addClass('hidden');\n $('#comingSoonGreen').removeClass('hidden');\n }\n $('#comingSoonGreen').text(data.messageComingSoon);\n $('#messageGreen').text(data.message);\n $('.js-notifyMeModal-toShow').removeClass('hidden');\n $('.js-notifyMeModal-notifyBtn').addClass('hidden');\n $(\n '.js-notifyMeModal-titleNotComingSoon,.js-notifyMeModal-titleComingSoon'\n ).addClass('hidden');\n $(\n '.js-notifyMeModal-subTitleNotComingSoon, .js-notifyMeModal-subTitleComingSoon'\n ).addClass('hidden');\n $('.continueShopping').removeClass('hidden');\n $('.js-notifyMeModal-emailError').addClass('hidden');\n $('.js-notifyMeModal-duplicateError').addClass('hidden');\n if (!Foundation.MediaQuery.atLeast('medium')) {\n $('.subtitleHide').addClass('hidden');\n }\n $('body').trigger('soldout:notify', {\n size: $('.sizeNotify').text().trim(),\n productName: productName,\n sku: analyticsSku,\n availability: 'product_notify_me',\n });\n } else {\n if (data.duplicate) {\n $('.js-notifyMeModal-duplicateError').removeClass('hidden');\n }\n }\n },\n error: () => {\n $.spinner().stop();\n },\n });\n } else {\n $('.js-notifyMeModal-emailError').removeClass('hidden');\n }\n });\n }\n}\n\nconst notifyHelper = new NotifyHelper();\nexport default notifyHelper;\n","export const startCarouselTileImageFunction = (element) => {\n var carousel = element ? $(element) : $('.js-tileImageCarousel');\n carousel.on('init', function (event, slick) {\n $(this).find('.tile-image').removeClass('hide');\n $(this).find('.slick-arrow').addClass('js-prevent-link');\n });\n carousel.slick({\n responsive: [\n {\n settings: {\n draggable: false,\n swipe: false,\n swipeToSlide: false,\n touchMove: false,\n accessibility: false,\n arrows: false\n }\n }\n ]\n });\n};\n\nclass ProductBox {\n run () {\n this.gotoPDP();\n this.startCarouselTileImage();\n this.afterAttributesSelectionEvent();\n }\n\n gotoPDP () {\n $(document).on('click', '.product-tile', function (evt) {\n if (evt.target.classList.contains('js-prevent-link')) {\n evt.preventDefault();\n }\n });\n }\n\n startCarouselTileImage () {\n startCarouselTileImageFunction();\n\n $('body').on('click', '.product .js-tileImageCarousel .slick-arrow', function (e) {\n e.preventDefault();\n e.stopPropagation();\n });\n }\n\n afterAttributesSelectionEvent () {\n $(document).on('product:afterAttributeSelect', (evt, additionalData) => {\n const $container = additionalData.container;\n var newPriceData = additionalData.data.product.price.html;\n if (additionalData.data.product.doubleCurrency && additionalData.data.product.doubleCurrency.html) {\n newPriceData += additionalData.data.product.doubleCurrency.html;\n }\n $container.find('.price-container').html(newPriceData);\n });\n }\n}\n\n// const productBox = new ProductBox();\nexport default ProductBox;\n","'use strict';\n\nconst checkCarouselLength = (carouselContainer) => {\n if ($(carouselContainer).length > 0) {\n $(carouselContainer).each(function () {\n const carousel = $(this);\n let carouselWidth = parseInt($(carousel).outerWidth());\n let carouselItemsNumber = $(carousel).children().length;\n let carouselItemsWidth = parseInt($(carousel).children().outerWidth());\n let carouselItemsWidthSum = carouselItemsWidth * carouselItemsNumber;\n if ((carouselItemsWidthSum + 16) <= carouselWidth) {\n $(this).closest('.cc-em').find('.cc-em__carouselCustom__arrows').hide();\n $(this).addClass('cc-em__carouselCustom_center');\n } else {\n $(this).closest('.cc-em').find('.cc-em__carouselCustom__arrows').show();\n $(this).removeClass('cc-em__carouselCustom_center');\n }\n\n $(this).scroll(function () {\n carouselWidth = parseInt($(carousel).outerWidth());\n carouselItemsNumber = $(carousel).children().length;\n carouselItemsWidth = parseInt($(carousel).children().outerWidth());\n carouselItemsWidthSum = carouselItemsWidth * carouselItemsNumber;\n let carouselScrolled = $(carousel).scrollLeft();\n\n if (carouselScrolled < 1) {\n $(carousel).closest('.cc-em').find('.js-carouselCustom__arrowLeft').addClass('cc-disabled');\n } else if (carouselScrolled >= (carouselItemsWidthSum - carouselWidth + 16)) {\n $(carousel).closest('.cc-em').find('.js-carouselCustom__arrowRight').addClass('cc-disabled');\n } else {\n $(carousel).closest('.cc-em').find('.js-carouselCustom__arrowLeft').removeClass('cc-disabled');\n $(carousel).closest('.cc-em').find('.js-carouselCustom__arrowRight').removeClass('cc-disabled');\n }\n });\n });\n }\n};\n$(document).ready(function () {\n // Custom Carousel\n function carouselScroll (el, dir) {\n const carousel = $(el).closest('.cc-em').find('.cc-em__carouselCustom');\n const carouselItemsWidth = parseInt($(carousel).children().outerWidth());\n let carouselScrolled = $(carousel).scrollLeft();\n\n if (dir === 'right') {\n $(carousel).scrollLeft(carouselScrolled + carouselItemsWidth);\n } else {\n $(carousel).scrollLeft(carouselScrolled - carouselItemsWidth);\n }\n }\n\n $(document).on('click', '.js-carouselCustom__arrowLeft', function () {\n carouselScroll(this, 'left');\n });\n\n $(document).on('click', '.js-carouselCustom__arrowRight', function () {\n carouselScroll(this, 'right');\n });\n $('body').on('common:checkCarouselLength', function (e, data) {\n checkCarouselLength(data.name);\n });\n});\n\nexport {\n checkCarouselLength,\n};\n","import { fabric } from 'fabric';\nimport { generateSvgForOTP } from './personalization/generateSvgForOTP';\nimport {\n newModalFromString\n} from './components/modal';\nimport sizePanel from './product/sizePanel';\nimport SELECTORS from './personalization/selectors';\nimport CLASSES from './personalization/classes';\n\nlet customizePosition, customizeSide, customizeText, customizeFont, customizePattern, customizeColor, allowedCharactersRegex, canvas, canvasText, canvasRect, canvasGroup, canvasImage, top, left, topBack, leftBack, badWords, loadingTime, isStepTwo, rectColor, switchDisable;\n\nfunction initText () {\n const { textInput, fontsButtons, colorsButtons } = SELECTORS;\n $(textInput).val('');\n $(fontsButtons).removeClass('active');\n $(fontsButtons).first().addClass('active');\n $(colorsButtons).removeClass('active');\n $(colorsButtons).first().addClass('active');\n\n customizePosition = '0';\n customizeText = '';\n customizeFont = '\"Didot\",Times,serif';\n customizePattern = '1';\n customizeColor = '#000000';\n allowedCharactersRegex = $(textInput).data('regex-pattern');\n}\n\nfunction initVariables () {\n customizeSide = '0';\n top = parseInt($(SELECTORS.pixelText).attr('top-desktop'));\n left = parseInt($(SELECTORS.pixelText).attr('left-desktop'));\n topBack = parseInt($(SELECTORS.pixelText).attr('top-desktop-back'));\n leftBack = parseInt($(SELECTORS.pixelText).attr('left-desktop-back'));\n switchDisable = $(SELECTORS.pixelText).attr('switch-disable') === 'true';\n badWords = [];\n loadingTime = 300;\n isStepTwo = false;\n rectColor = '#3C3738';\n\n initText();\n}\n\n/**\n * @function initCanvas - Init the canvas\n * @returns {void}\n */\nfunction initCanvas (imageToLoad = SELECTORS.imgFront) {\n canvas = new fabric.StaticCanvas('personalization-canvas', {\n width: 2000,\n height: 3000,\n enableRetinaScaling: false\n });\n\n let transformX = left / canvas.width * 100;\n let transformY = top / canvas.height * 100;\n let translateY = transformY < 25 ? 0 : transformY > 75 ? -50 : 25 - transformY;\n\n $(SELECTORS.personalizationCanvas).css({\n transformOrigin: transformX + '% ' + transformY + '%',\n transform: 'scale(1)',\n top: isStepTwo ? translateY + '%' : '0'\n });\n\n $(SELECTORS.zoomButton).removeClass('active');\n\n const canvasRatio = 7.125; // canvas ratio calculated based on the design dimensions of the image (2000/355)\n canvasText = new fabric.Textbox(customizeText, {\n top: top,\n left: left,\n originX: 'center',\n originY: 'center',\n width: canvasRatio * 48,\n fontSize: canvasRatio * 10,\n lineHeight: canvasRatio * 15,\n fontFamily: customizeFont,\n textAlign: 'center',\n fill: customizeColor,\n });\n\n if (isStepTwo) {\n canvasRect = new fabric.Rect({\n strokeDashArray: [canvasRatio * 5, canvasRatio * 5],\n top: top,\n left: left,\n originX: 'center',\n originY: 'center',\n width: canvasRatio * 48,\n height: canvasRatio * 26,\n fill: '',\n stroke: rectColor,\n strokeWidth: canvasRatio * 1\n });\n }\n\n let imageUrl = $(imageToLoad).attr('src');\n fabric.Image.fromURL(imageUrl, function (img) {\n canvasImage = img.set({\n top: 0,\n selectable: false,\n hasRotatingPoint: true,\n width: canvas.width,\n height: canvas.height\n });\n canvasImage.scaleToWidth(canvas.width);\n\n if (isStepTwo) {\n canvasGroup = new fabric.Group([canvasImage, canvasText, canvasRect], {});\n } else {\n canvasGroup = new fabric.Group([canvasImage, canvasText], {});\n }\n canvas.add(canvasGroup);\n\n setTimeout(() => {\n canvas.renderAll();\n }, loadingTime);\n });\n}\n\n/**\n * @function initForm - Saves customization values inside the submit form inputs\n */\nfunction initForm () {\n $('.form-position').val(customizePosition);\n $('.form-text').val(customizeText);\n $('.form-font').val(customizeFont);\n $('.form-pattern').val(customizePattern);\n $('.form-color').val(customizeColor);\n $('.form-color-selected-circle-src').val($('#imageColor').attr('src'));\n}\n\n/**\n * @function updateCanvasElem - Update the canvas element based on a property and value\n * @param {Object} elem - Canvas element\n * @param {String} property - Property to update\n * @param {*} value - Value to set\n */\nfunction updateCanvasElem (elem, property, value) {\n if (elem) {\n elem.set(property, value);\n\n setTimeout(() => {\n canvas.renderAll();\n }, loadingTime);\n }\n};\n\n/**\n * @function waitToLoadAllImages - Wait for all images to load\n * @returns {Promise} - Promise that resolves when all images are loaded\n */\nfunction waitToLoadAllImages () {\n let defer = jQuery.Deferred();\n let imagesNumber = $('.js-personalization-image').length;\n let loadComplete = 0;\n $('.js-personalization-image').one('load', function () {\n loadComplete++;\n if (loadComplete === imagesNumber) {\n defer.resolve(true);\n }\n }).on('error', function () {\n loadComplete++;\n if (loadComplete === imagesNumber) {\n defer.resolve(true);\n }\n }).each(function () {\n if (this.complete) {\n $(this).trigger('load');\n } else if (this.error) {\n $(this).error();\n }\n });\n return defer.promise();\n};\n\n/**\n * @function runPersonalizationListener - Init the canvas, add event listeners on the modal elements and init the form\n */\nfunction runPersonalizationListener () {\n initVariables();\n sizePanel.init('#size-panel-mobile-pers');\n $('#size').attr('size-attribute', $('[data-attr=\"size\"] input:checked').attr('id'));\n\n waitToLoadAllImages().then(function () {\n initCanvas();\n positionChoice();\n });\n\n initForm();\n\n $('#input-type1').on('input', function () {\n editTextOnCanvas();\n });\n\n /**\n * Change the color of the text on the canvas\n */\n $(document).on('click', '.js-choice-editor .cc-choice-pattern_item', function (e) {\n customizePattern = $(this).find('img').attr('src');\n customizeColor = $(this).find('img').attr('alt');\n let colorName = $(this).find('img').data('name');\n $('.js-color-value').text(colorName);\n $('.js-customizePage').find('.js-choice-editor .cc-choice-pattern_item.active').removeClass('active');\n $(this).addClass('active');\n\n updateCanvasElem(canvasText, 'fill', customizeColor);\n\n e.stopPropagation();\n });\n\n /**\n * Select one of the 2 available hotspost\n */\n $(document).off('click', '.js-customizePage .js-positionChoice-1, .js-customizePage .js-positionChoice-2');\n $(document).on('click', '.js-customizePage .js-positionChoice-1, .js-customizePage .js-positionChoice-2', function (e) {\n isStepTwo = true;\n if ($(this).hasClass('js-positionChoice-1')) {\n selectPosition(1);\n } else if ($(this).hasClass('js-positionChoice-2')) {\n selectPosition(2);\n }\n choicePosition();\n $('.js-customizePage .js-positionChoice-1, .js-customizePage .js-positionChoice-2').hide();\n e.stopPropagation();\n });\n\n onZoomButtonClick();\n}\n\n/**\n * @function onZoomButtonClick - Add event listener on the zoom button, to zoom in/out the canvas\n */\nfunction onZoomButtonClick () {\n $(SELECTORS.zoomButton).on('click', function (e) {\n const $this = $(this);\n const scaleValue = $this.hasClass('active') ? 1 : 1.9;\n\n $(SELECTORS.personalizationCanvas).css({\n transform: 'scale(' + scaleValue + ')'\n });\n\n $this.toggleClass('active');\n e.stopPropagation();\n });\n}\n\n/**\n * @function editTextOnCanvas - Update the text on the canvas\n */\nfunction editTextOnCanvas () {\n customizeText = $('#input-type1').val();\n let badWordsFlag = false;\n\n if (badWords.includes(customizeText.toLowerCase())) {\n badWordsFlag = true;\n customizeText = '';\n $('.js-personalizeButtonModal').attr('disabled', true);\n $('.content-input-err').removeClass('hidden');\n } else {\n $('.js-personalizeButtonModal').attr('disabled', false);\n $('.content-input-err').addClass('hidden');\n }\n if (customizeText === undefined || customizeText === '') {\n $('.js-personalizeButtonModal').attr('disabled', true);\n $('.content-input-err-cyrillic').addClass('hidden');\n } else {\n $('.js-personalizeButtonModal').attr('disabled', false);\n\n if (!badWordsFlag) {\n const isRegexValid = customizeText.toLowerCase().match(allowedCharactersRegex);\n if (!isRegexValid) {\n $('.js-personalizeButtonModal').attr('disabled', true);\n $('.content-input-err-cyrillic').removeClass('hidden');\n } else {\n $('.js-personalizeButtonModal').attr('disabled', false);\n $('.content-input-err-cyrillic').addClass('hidden');\n }\n }\n }\n\n updateCanvasElem(canvasText, 'text', customizeText);\n\n if (customizeText !== '') {\n updateCanvasElem(canvasRect, 'stroke', '');\n } else {\n updateCanvasElem(canvasRect, 'stroke', rectColor);\n }\n}\n\n/**\n * @function updateCanvas - Re-load the canvas with a new image\n * @param {String} imageToLoad - Selector of the image tag to use for the canvas\n */\nfunction updateCanvas (imageToLoad) {\n canvas.clear();\n initCanvas(imageToLoad);\n}\n\n/**\n * @function choicePosition - Go to step 2, function is called after clicking on the hotspot\n */\nlet choicePosition = function () {\n const { page, mainChoice, showOtherSide, stepOne, stepTwo, termsBottomDesktop, footer, zoomButton } = SELECTORS;\n\n if (customizePosition !== '0') {\n $(mainChoice).addClass('visible');\n $(stepOne + ', ' + termsBottomDesktop).removeClass('cc-visible');\n $(stepTwo + ', ' + footer).addClass('cc-visible');\n $(showOtherSide).removeClass('back').addClass('hide');\n $(zoomButton).removeClass('hide');\n $(page).removeClass(CLASSES.pageStepOne).addClass(CLASSES.pageStepTwo);\n }\n};\n\n/**\n * @function backChoicePosition - Go back to step 1, function is called after clicking on the back button\n */\nlet backChoicePosition = function () {\n const { page, mainChoice, hotspotOne, hotspotTwo, stepOne, stepTwo, termsBottomDesktop, footer, showOtherSide, zoomButton } = SELECTORS;\n isStepTwo = false;\n if (customizeSide !== '0') {\n $(showOtherSide).removeClass('hide');\n\n if (customizeSide === '1') {\n $(showOtherSide).addClass('back').removeClass('front');\n } else {\n $(showOtherSide).addClass('front').removeClass('back');\n }\n } else {\n $(hotspotOne).removeClass('hide');\n $(hotspotTwo).removeClass('hide');\n }\n const imageToLoad = customizeSide === '1' || customizeSide === '0' ? $(SELECTORS.imgFront) : $(SELECTORS.imgBack);\n\n canvas.clear();\n initText();\n initCanvas(imageToLoad);\n\n $(mainChoice).removeClass('visible');\n $(stepOne + ', ' + termsBottomDesktop).addClass('cc-visible');\n $(stepTwo + ', ' + footer).removeClass('cc-visible');\n $(page).addClass(CLASSES.pageStepOne).removeClass(CLASSES.pageStepTwo);\n $(hotspotOne + ', ' + hotspotTwo).show();\n $(zoomButton).removeClass('active').addClass('hide');\n};\n\n/**\n * @function selectPosition - Select if we are using the image front or back\n * @param {Number} pos - 1: front, 2: back\n */\nfunction selectPosition (pos) {\n const { imgFront, imgBack, pixelText, hotspotOne, hotspotTwo, showOtherSide } = SELECTORS;\n let imageToLoad = $(imgFront);\n if (pos === 1 || pos === 0) {\n top = parseInt($(pixelText).attr('top-desktop'));\n left = parseInt($(pixelText).attr('left-desktop'));\n customizePosition = pos;\n $(showOtherSide).addClass('back').removeClass('front');\n $(hotspotOne).removeClass('hide');\n if (pos !== 0) {\n $(hotspotTwo).addClass('hide');\n }\n } else {\n top = parseInt($(pixelText).attr('top-desktop-back'));\n left = parseInt($(pixelText).attr('left-desktop-back'));\n imageToLoad = $(imgBack);\n customizePosition = '2';\n $(showOtherSide).addClass('front').removeClass('back');\n $(hotspotOne).addClass('hide');\n $(hotspotTwo).removeClass('hide');\n }\n\n updateCanvas(imageToLoad);\n}\n\n/**\n * @function positionChoice - Add event listeners on the position buttons\n */\nfunction positionChoice () {\n const imageFront = $('#img-url-front').attr('data-url').replace(/&/g, '&');\n const imageBack = $('#img-url-back').attr('data-url').replace(/&/g, '&');\n const topPercentage = (top / canvas.height) * 100;\n const leftPercentage = (left / canvas.width) * 100;\n const topBackPercentage = (topBack / canvas.height) * 100;\n const leftBackPercentage = (leftBack / canvas.width) * 100;\n\n if (imageBack !== '') {\n let $position1 = $('').html($('.cordinates-spot-icon i').html()).addClass('js-pers-hotspotBtn js-positionChoice-1 cc-pers-hotspotBtn');\n let $position2 = $('').html($('.cordinates-spot-icon i').html()).addClass('js-pers-hotspotBtn js-positionChoice-2 cc-pers-hotspotBtn');\n $position1.css({'position': 'absolute', 'top': topPercentage + '%', 'left': leftPercentage + '%', 'display': 'flex'}).appendTo('.js-section-module_result_image');\n $position2.css({'position': 'absolute', 'top': topBackPercentage + '%', 'left': leftBackPercentage + '%', 'display': 'flex'}).appendTo('.js-section-module_result_image');\n $position1.data('position', '1');\n $position2.data('position', '2');\n\n if (imageFront !== imageBack && !switchDisable) {\n $('.js-show-other-side').removeClass('hide').addClass('back');\n selectPosition(1);\n customizeSide = '1';\n } else {\n $('.js-show-other-side').addClass('hide');\n selectPosition(0);\n customizeSide = '0';\n }\n } else {\n let $position1 = $('').html($('.cordinates-spot-icon i').html()).addClass('js-pers-hotspotBtn js-positionChoice-1 cc-pers-hotspotBtn');\n $position1.css({'position': 'absolute', 'top': topPercentage + '%', 'left': leftPercentage + '%', 'display': 'flex'}).appendTo('.js-section-module_result_image');\n selectPosition(0);\n customizeSide = '0';\n $position1.data('position', '1');\n }\n\n /**\n * Add event listener on go back button (return to step 1);\n */\n $(document).off('click', '.cc-customizePage-topbar .js-page-back');\n $(document).on('click', '.cc-customizePage-topbar .js-page-back', function (e) {\n backChoicePosition();\n e.stopPropagation();\n $('body').trigger('customize:actions', {\n action: 'back',\n pid: $('.js-customizePage').data('pid')\n });\n });\n\n // Cambio Fronte/Retro\n $(document).off('click', '.js-show-other-side .js-other-side-btn');\n $(document).on('click', '.js-show-other-side .js-other-side-btn', function (e) {\n if ($(this).closest('.js-show-other-side').hasClass('front')) {\n $(this).closest('.js-show-other-side').removeClass('front').addClass('back');\n selectPosition(1);\n customizeSide = '1';\n } else {\n $(this).closest('.js-show-other-side').removeClass('back').addClass('front');\n selectPosition(2);\n customizeSide = '2';\n }\n });\n\n $(document).on('click', '.js-choice-editor .cc-choice-item', function (e) {\n customizeFont = $(this).data('font');\n $('.form-font').val(customizeFont);\n\n $('.js-choice-editor .cc-choice-item.active').removeClass('active');\n $(this).addClass('active');\n $('#input-type1').css('font-family', customizeFont);\n\n updateCanvasElem(canvasText, 'fontFamily', customizeFont);\n e.stopPropagation();\n });\n\n /**\n * Creates new canvas for the export and populates data for add to cart\n */\n $(document).on('click', SELECTORS.personalizeAddToCart, function (e) {\n initForm();\n\n $.spinner().start();\n\n let canvasOptions = {\n top: top,\n left: left,\n customizeText: customizeText,\n customizeFont: customizeFont,\n customizeColor: customizeColor,\n imageToLoad: customizeSide === '1' || customizeSide === '0' ? $(SELECTORS.imgFront) : $(SELECTORS.imgBack)\n };\n let svgAllFormat = generateSvgForOTP(canvasOptions);\n let base64FullSVG = svgAllFormat.personalizationFullSVG;\n $('#base64').attr('data-fullSVG', base64FullSVG);\n let base64TextFullSVG = svgAllFormat.personalizationTextSVG;\n $('#base64').attr('data-fullTextSVG', base64TextFullSVG);\n let base64TextSmallSVG = svgAllFormat.personalizationSmallSVG;\n $('#base64').attr('data-smallSVG', base64TextSmallSVG);\n $.spinner().stop();\n\n let size = $('#size').attr('size-attribute').replace('/', '~');\n if (size !== '') {\n $('#' + size).attr('checked', true);\n }\n\n // Update modal add-to-cart\n $('body').on('product:updateAddToCart', (e, response) => {\n if (!response.product.readyToOrder || !response.product.available || response.product.comingSoon) {\n if (this.sizeModal && this.sizeModal.modal) {\n $(this.sizeModal.modalBox).find('button.js-add-to-cart').attr('disabled', true);\n }\n } else if (this.sizeModal && this.sizeModal.modal) {\n $(this.sizeModal.modalBox).find('button.js-add-to-cart').attr('disabled', false);\n }\n });\n\n // Close the modal when a product is added to the cart\n $('body').on('product:afterAddToCart', (e) => {\n if (this.sizeModal && this.sizeModal.modal) {\n this.sizeModal.close();\n this.sizeModal.destroy();\n }\n });\n\n $('.js-personalizeButtonCheckout.js-add-to-cart').trigger('click');\n });\n\n // Modal Customize Terms\n $(SELECTORS.termsAndConditionsModal).on('click', function (e) {\n e.preventDefault();\n const htmlContent = $($(this).data('target')).html();\n // create and open confirmation modal\n const modal = newModalFromString(htmlContent, false);\n $('.tingle-modal:not(.jsPersonalizationToolModal)').addClass('cc-modalCustomizeTerms');\n $('.cc-modalCustomizeTerms .tingle-modal-box').addClass('cc-modalCustomizeTerms-container rightModalAttribute');\n $('.cc-modalCustomizeTerms .tingle-modal-box__content').addClass('cc-modalCustomizeTerms-container-modal');\n modal.open();\n modal.setContent(document.querySelector('.js-ModalCustomizeTerms').innerHTML);\n $(modal.modalBox)\n .find('.close')\n .on('click', function (e) {\n modal.close();\n });\n\n $('.js-inside-close-modal, [data-dismiss=\"modalBigContent\"]').on('click', function (e) {\n e.preventDefault();\n modal.close();\n });\n });\n\n $(SELECTORS.analyticsCustomizeAction).on('click', function (e) {\n let pid = $('.js-customizePage').data('pid');\n let action = $(e.currentTarget).data('action');\n $('body').trigger('customize:actions', {action: action, pid: pid});\n });\n\n $(SELECTORS.pageClose).on('click', function (e) {\n $('body').trigger('customize:actions', {\n action: 'close', \n pid: $('.js-customizePage').data('pid')\n });\n $('.jsPersonalizationToolModal .tingle-modal__close').trigger('click');\n initVariables();\n sizePanel.init();\n });\n\n // Hot spot selection - define \"position\" attribute\n $('body').on('click', '.js-pers-hotspotBtn', e => {\n customizePosition = $(e.currentTarget).data('position');\n $('.form-position').val(customizePosition);\n });\n};\n\nmodule.exports = {\n runPersonalizationListener: runPersonalizationListener,\n};\n","/*!\n * The buffer module from node.js, for the browser.\n *\n * @author Feross Aboukhadijeh \n * @license MIT\n */\n/* eslint-disable no-proto */\n\n'use strict'\n\nvar base64 = require('base64-js')\nvar ieee754 = require('ieee754')\nvar isArray = require('isarray')\n\nexports.Buffer = Buffer\nexports.SlowBuffer = SlowBuffer\nexports.INSPECT_MAX_BYTES = 50\n\n/**\n * If `Buffer.TYPED_ARRAY_SUPPORT`:\n * === true Use Uint8Array implementation (fastest)\n * === false Use Object implementation (most compatible, even IE6)\n *\n * Browsers that support typed arrays are IE 10+, Firefox 4+, Chrome 7+, Safari 5.1+,\n * Opera 11.6+, iOS 4.2+.\n *\n * Due to various browser bugs, sometimes the Object implementation will be used even\n * when the browser supports typed arrays.\n *\n * Note:\n *\n * - Firefox 4-29 lacks support for adding new properties to `Uint8Array` instances,\n * See: https://bugzilla.mozilla.org/show_bug.cgi?id=695438.\n *\n * - Chrome 9-10 is missing the `TypedArray.prototype.subarray` function.\n *\n * - IE10 has a broken `TypedArray.prototype.subarray` function which returns arrays of\n * incorrect length in some situations.\n\n * We detect these buggy browsers and set `Buffer.TYPED_ARRAY_SUPPORT` to `false` so they\n * get the Object implementation, which is slower but behaves correctly.\n */\nBuffer.TYPED_ARRAY_SUPPORT = global.TYPED_ARRAY_SUPPORT !== undefined\n ? global.TYPED_ARRAY_SUPPORT\n : typedArraySupport()\n\n/*\n * Export kMaxLength after typed array support is determined.\n */\nexports.kMaxLength = kMaxLength()\n\nfunction typedArraySupport () {\n try {\n var arr = new Uint8Array(1)\n arr.__proto__ = {__proto__: Uint8Array.prototype, foo: function () { return 42 }}\n return arr.foo() === 42 && // typed array instances can be augmented\n typeof arr.subarray === 'function' && // chrome 9-10 lack `subarray`\n arr.subarray(1, 1).byteLength === 0 // ie10 has broken `subarray`\n } catch (e) {\n return false\n }\n}\n\nfunction kMaxLength () {\n return Buffer.TYPED_ARRAY_SUPPORT\n ? 0x7fffffff\n : 0x3fffffff\n}\n\nfunction createBuffer (that, length) {\n if (kMaxLength() < length) {\n throw new RangeError('Invalid typed array length')\n }\n if (Buffer.TYPED_ARRAY_SUPPORT) {\n // Return an augmented `Uint8Array` instance, for best performance\n that = new Uint8Array(length)\n that.__proto__ = Buffer.prototype\n } else {\n // Fallback: Return an object instance of the Buffer class\n if (that === null) {\n that = new Buffer(length)\n }\n that.length = length\n }\n\n return that\n}\n\n/**\n * The Buffer constructor returns instances of `Uint8Array` that have their\n * prototype changed to `Buffer.prototype`. Furthermore, `Buffer` is a subclass of\n * `Uint8Array`, so the returned instances will have all the node `Buffer` methods\n * and the `Uint8Array` methods. Square bracket notation works as expected -- it\n * returns a single octet.\n *\n * The `Uint8Array` prototype remains unmodified.\n */\n\nfunction Buffer (arg, encodingOrOffset, length) {\n if (!Buffer.TYPED_ARRAY_SUPPORT && !(this instanceof Buffer)) {\n return new Buffer(arg, encodingOrOffset, length)\n }\n\n // Common case.\n if (typeof arg === 'number') {\n if (typeof encodingOrOffset === 'string') {\n throw new Error(\n 'If encoding is specified then the first argument must be a string'\n )\n }\n return allocUnsafe(this, arg)\n }\n return from(this, arg, encodingOrOffset, length)\n}\n\nBuffer.poolSize = 8192 // not used by this implementation\n\n// TODO: Legacy, not needed anymore. Remove in next major version.\nBuffer._augment = function (arr) {\n arr.__proto__ = Buffer.prototype\n return arr\n}\n\nfunction from (that, value, encodingOrOffset, length) {\n if (typeof value === 'number') {\n throw new TypeError('\"value\" argument must not be a number')\n }\n\n if (typeof ArrayBuffer !== 'undefined' && value instanceof ArrayBuffer) {\n return fromArrayBuffer(that, value, encodingOrOffset, length)\n }\n\n if (typeof value === 'string') {\n return fromString(that, value, encodingOrOffset)\n }\n\n return fromObject(that, value)\n}\n\n/**\n * Functionally equivalent to Buffer(arg, encoding) but throws a TypeError\n * if value is a number.\n * Buffer.from(str[, encoding])\n * Buffer.from(array)\n * Buffer.from(buffer)\n * Buffer.from(arrayBuffer[, byteOffset[, length]])\n **/\nBuffer.from = function (value, encodingOrOffset, length) {\n return from(null, value, encodingOrOffset, length)\n}\n\nif (Buffer.TYPED_ARRAY_SUPPORT) {\n Buffer.prototype.__proto__ = Uint8Array.prototype\n Buffer.__proto__ = Uint8Array\n if (typeof Symbol !== 'undefined' && Symbol.species &&\n Buffer[Symbol.species] === Buffer) {\n // Fix subarray() in ES2016. See: https://github.com/feross/buffer/pull/97\n Object.defineProperty(Buffer, Symbol.species, {\n value: null,\n configurable: true\n })\n }\n}\n\nfunction assertSize (size) {\n if (typeof size !== 'number') {\n throw new TypeError('\"size\" argument must be a number')\n } else if (size < 0) {\n throw new RangeError('\"size\" argument must not be negative')\n }\n}\n\nfunction alloc (that, size, fill, encoding) {\n assertSize(size)\n if (size <= 0) {\n return createBuffer(that, size)\n }\n if (fill !== undefined) {\n // Only pay attention to encoding if it's a string. This\n // prevents accidentally sending in a number that would\n // be interpretted as a start offset.\n return typeof encoding === 'string'\n ? createBuffer(that, size).fill(fill, encoding)\n : createBuffer(that, size).fill(fill)\n }\n return createBuffer(that, size)\n}\n\n/**\n * Creates a new filled Buffer instance.\n * alloc(size[, fill[, encoding]])\n **/\nBuffer.alloc = function (size, fill, encoding) {\n return alloc(null, size, fill, encoding)\n}\n\nfunction allocUnsafe (that, size) {\n assertSize(size)\n that = createBuffer(that, size < 0 ? 0 : checked(size) | 0)\n if (!Buffer.TYPED_ARRAY_SUPPORT) {\n for (var i = 0; i < size; ++i) {\n that[i] = 0\n }\n }\n return that\n}\n\n/**\n * Equivalent to Buffer(num), by default creates a non-zero-filled Buffer instance.\n * */\nBuffer.allocUnsafe = function (size) {\n return allocUnsafe(null, size)\n}\n/**\n * Equivalent to SlowBuffer(num), by default creates a non-zero-filled Buffer instance.\n */\nBuffer.allocUnsafeSlow = function (size) {\n return allocUnsafe(null, size)\n}\n\nfunction fromString (that, string, encoding) {\n if (typeof encoding !== 'string' || encoding === '') {\n encoding = 'utf8'\n }\n\n if (!Buffer.isEncoding(encoding)) {\n throw new TypeError('\"encoding\" must be a valid string encoding')\n }\n\n var length = byteLength(string, encoding) | 0\n that = createBuffer(that, length)\n\n var actual = that.write(string, encoding)\n\n if (actual !== length) {\n // Writing a hex string, for example, that contains invalid characters will\n // cause everything after the first invalid character to be ignored. (e.g.\n // 'abxxcd' will be treated as 'ab')\n that = that.slice(0, actual)\n }\n\n return that\n}\n\nfunction fromArrayLike (that, array) {\n var length = array.length < 0 ? 0 : checked(array.length) | 0\n that = createBuffer(that, length)\n for (var i = 0; i < length; i += 1) {\n that[i] = array[i] & 255\n }\n return that\n}\n\nfunction fromArrayBuffer (that, array, byteOffset, length) {\n array.byteLength // this throws if `array` is not a valid ArrayBuffer\n\n if (byteOffset < 0 || array.byteLength < byteOffset) {\n throw new RangeError('\\'offset\\' is out of bounds')\n }\n\n if (array.byteLength < byteOffset + (length || 0)) {\n throw new RangeError('\\'length\\' is out of bounds')\n }\n\n if (byteOffset === undefined && length === undefined) {\n array = new Uint8Array(array)\n } else if (length === undefined) {\n array = new Uint8Array(array, byteOffset)\n } else {\n array = new Uint8Array(array, byteOffset, length)\n }\n\n if (Buffer.TYPED_ARRAY_SUPPORT) {\n // Return an augmented `Uint8Array` instance, for best performance\n that = array\n that.__proto__ = Buffer.prototype\n } else {\n // Fallback: Return an object instance of the Buffer class\n that = fromArrayLike(that, array)\n }\n return that\n}\n\nfunction fromObject (that, obj) {\n if (Buffer.isBuffer(obj)) {\n var len = checked(obj.length) | 0\n that = createBuffer(that, len)\n\n if (that.length === 0) {\n return that\n }\n\n obj.copy(that, 0, 0, len)\n return that\n }\n\n if (obj) {\n if ((typeof ArrayBuffer !== 'undefined' &&\n obj.buffer instanceof ArrayBuffer) || 'length' in obj) {\n if (typeof obj.length !== 'number' || isnan(obj.length)) {\n return createBuffer(that, 0)\n }\n return fromArrayLike(that, obj)\n }\n\n if (obj.type === 'Buffer' && isArray(obj.data)) {\n return fromArrayLike(that, obj.data)\n }\n }\n\n throw new TypeError('First argument must be a string, Buffer, ArrayBuffer, Array, or array-like object.')\n}\n\nfunction checked (length) {\n // Note: cannot use `length < kMaxLength()` here because that fails when\n // length is NaN (which is otherwise coerced to zero.)\n if (length >= kMaxLength()) {\n throw new RangeError('Attempt to allocate Buffer larger than maximum ' +\n 'size: 0x' + kMaxLength().toString(16) + ' bytes')\n }\n return length | 0\n}\n\nfunction SlowBuffer (length) {\n if (+length != length) { // eslint-disable-line eqeqeq\n length = 0\n }\n return Buffer.alloc(+length)\n}\n\nBuffer.isBuffer = function isBuffer (b) {\n return !!(b != null && b._isBuffer)\n}\n\nBuffer.compare = function compare (a, b) {\n if (!Buffer.isBuffer(a) || !Buffer.isBuffer(b)) {\n throw new TypeError('Arguments must be Buffers')\n }\n\n if (a === b) return 0\n\n var x = a.length\n var y = b.length\n\n for (var i = 0, len = Math.min(x, y); i < len; ++i) {\n if (a[i] !== b[i]) {\n x = a[i]\n y = b[i]\n break\n }\n }\n\n if (x < y) return -1\n if (y < x) return 1\n return 0\n}\n\nBuffer.isEncoding = function isEncoding (encoding) {\n switch (String(encoding).toLowerCase()) {\n case 'hex':\n case 'utf8':\n case 'utf-8':\n case 'ascii':\n case 'latin1':\n case 'binary':\n case 'base64':\n case 'ucs2':\n case 'ucs-2':\n case 'utf16le':\n case 'utf-16le':\n return true\n default:\n return false\n }\n}\n\nBuffer.concat = function concat (list, length) {\n if (!isArray(list)) {\n throw new TypeError('\"list\" argument must be an Array of Buffers')\n }\n\n if (list.length === 0) {\n return Buffer.alloc(0)\n }\n\n var i\n if (length === undefined) {\n length = 0\n for (i = 0; i < list.length; ++i) {\n length += list[i].length\n }\n }\n\n var buffer = Buffer.allocUnsafe(length)\n var pos = 0\n for (i = 0; i < list.length; ++i) {\n var buf = list[i]\n if (!Buffer.isBuffer(buf)) {\n throw new TypeError('\"list\" argument must be an Array of Buffers')\n }\n buf.copy(buffer, pos)\n pos += buf.length\n }\n return buffer\n}\n\nfunction byteLength (string, encoding) {\n if (Buffer.isBuffer(string)) {\n return string.length\n }\n if (typeof ArrayBuffer !== 'undefined' && typeof ArrayBuffer.isView === 'function' &&\n (ArrayBuffer.isView(string) || string instanceof ArrayBuffer)) {\n return string.byteLength\n }\n if (typeof string !== 'string') {\n string = '' + string\n }\n\n var len = string.length\n if (len === 0) return 0\n\n // Use a for loop to avoid recursion\n var loweredCase = false\n for (;;) {\n switch (encoding) {\n case 'ascii':\n case 'latin1':\n case 'binary':\n return len\n case 'utf8':\n case 'utf-8':\n case undefined:\n return utf8ToBytes(string).length\n case 'ucs2':\n case 'ucs-2':\n case 'utf16le':\n case 'utf-16le':\n return len * 2\n case 'hex':\n return len >>> 1\n case 'base64':\n return base64ToBytes(string).length\n default:\n if (loweredCase) return utf8ToBytes(string).length // assume utf8\n encoding = ('' + encoding).toLowerCase()\n loweredCase = true\n }\n }\n}\nBuffer.byteLength = byteLength\n\nfunction slowToString (encoding, start, end) {\n var loweredCase = false\n\n // No need to verify that \"this.length <= MAX_UINT32\" since it's a read-only\n // property of a typed array.\n\n // This behaves neither like String nor Uint8Array in that we set start/end\n // to their upper/lower bounds if the value passed is out of range.\n // undefined is handled specially as per ECMA-262 6th Edition,\n // Section 13.3.3.7 Runtime Semantics: KeyedBindingInitialization.\n if (start === undefined || start < 0) {\n start = 0\n }\n // Return early if start > this.length. Done here to prevent potential uint32\n // coercion fail below.\n if (start > this.length) {\n return ''\n }\n\n if (end === undefined || end > this.length) {\n end = this.length\n }\n\n if (end <= 0) {\n return ''\n }\n\n // Force coersion to uint32. This will also coerce falsey/NaN values to 0.\n end >>>= 0\n start >>>= 0\n\n if (end <= start) {\n return ''\n }\n\n if (!encoding) encoding = 'utf8'\n\n while (true) {\n switch (encoding) {\n case 'hex':\n return hexSlice(this, start, end)\n\n case 'utf8':\n case 'utf-8':\n return utf8Slice(this, start, end)\n\n case 'ascii':\n return asciiSlice(this, start, end)\n\n case 'latin1':\n case 'binary':\n return latin1Slice(this, start, end)\n\n case 'base64':\n return base64Slice(this, start, end)\n\n case 'ucs2':\n case 'ucs-2':\n case 'utf16le':\n case 'utf-16le':\n return utf16leSlice(this, start, end)\n\n default:\n if (loweredCase) throw new TypeError('Unknown encoding: ' + encoding)\n encoding = (encoding + '').toLowerCase()\n loweredCase = true\n }\n }\n}\n\n// The property is used by `Buffer.isBuffer` and `is-buffer` (in Safari 5-7) to detect\n// Buffer instances.\nBuffer.prototype._isBuffer = true\n\nfunction swap (b, n, m) {\n var i = b[n]\n b[n] = b[m]\n b[m] = i\n}\n\nBuffer.prototype.swap16 = function swap16 () {\n var len = this.length\n if (len % 2 !== 0) {\n throw new RangeError('Buffer size must be a multiple of 16-bits')\n }\n for (var i = 0; i < len; i += 2) {\n swap(this, i, i + 1)\n }\n return this\n}\n\nBuffer.prototype.swap32 = function swap32 () {\n var len = this.length\n if (len % 4 !== 0) {\n throw new RangeError('Buffer size must be a multiple of 32-bits')\n }\n for (var i = 0; i < len; i += 4) {\n swap(this, i, i + 3)\n swap(this, i + 1, i + 2)\n }\n return this\n}\n\nBuffer.prototype.swap64 = function swap64 () {\n var len = this.length\n if (len % 8 !== 0) {\n throw new RangeError('Buffer size must be a multiple of 64-bits')\n }\n for (var i = 0; i < len; i += 8) {\n swap(this, i, i + 7)\n swap(this, i + 1, i + 6)\n swap(this, i + 2, i + 5)\n swap(this, i + 3, i + 4)\n }\n return this\n}\n\nBuffer.prototype.toString = function toString () {\n var length = this.length | 0\n if (length === 0) return ''\n if (arguments.length === 0) return utf8Slice(this, 0, length)\n return slowToString.apply(this, arguments)\n}\n\nBuffer.prototype.equals = function equals (b) {\n if (!Buffer.isBuffer(b)) throw new TypeError('Argument must be a Buffer')\n if (this === b) return true\n return Buffer.compare(this, b) === 0\n}\n\nBuffer.prototype.inspect = function inspect () {\n var str = ''\n var max = exports.INSPECT_MAX_BYTES\n if (this.length > 0) {\n str = this.toString('hex', 0, max).match(/.{2}/g).join(' ')\n if (this.length > max) str += ' ... '\n }\n return ''\n}\n\nBuffer.prototype.compare = function compare (target, start, end, thisStart, thisEnd) {\n if (!Buffer.isBuffer(target)) {\n throw new TypeError('Argument must be a Buffer')\n }\n\n if (start === undefined) {\n start = 0\n }\n if (end === undefined) {\n end = target ? target.length : 0\n }\n if (thisStart === undefined) {\n thisStart = 0\n }\n if (thisEnd === undefined) {\n thisEnd = this.length\n }\n\n if (start < 0 || end > target.length || thisStart < 0 || thisEnd > this.length) {\n throw new RangeError('out of range index')\n }\n\n if (thisStart >= thisEnd && start >= end) {\n return 0\n }\n if (thisStart >= thisEnd) {\n return -1\n }\n if (start >= end) {\n return 1\n }\n\n start >>>= 0\n end >>>= 0\n thisStart >>>= 0\n thisEnd >>>= 0\n\n if (this === target) return 0\n\n var x = thisEnd - thisStart\n var y = end - start\n var len = Math.min(x, y)\n\n var thisCopy = this.slice(thisStart, thisEnd)\n var targetCopy = target.slice(start, end)\n\n for (var i = 0; i < len; ++i) {\n if (thisCopy[i] !== targetCopy[i]) {\n x = thisCopy[i]\n y = targetCopy[i]\n break\n }\n }\n\n if (x < y) return -1\n if (y < x) return 1\n return 0\n}\n\n// Finds either the first index of `val` in `buffer` at offset >= `byteOffset`,\n// OR the last index of `val` in `buffer` at offset <= `byteOffset`.\n//\n// Arguments:\n// - buffer - a Buffer to search\n// - val - a string, Buffer, or number\n// - byteOffset - an index into `buffer`; will be clamped to an int32\n// - encoding - an optional encoding, relevant is val is a string\n// - dir - true for indexOf, false for lastIndexOf\nfunction bidirectionalIndexOf (buffer, val, byteOffset, encoding, dir) {\n // Empty buffer means no match\n if (buffer.length === 0) return -1\n\n // Normalize byteOffset\n if (typeof byteOffset === 'string') {\n encoding = byteOffset\n byteOffset = 0\n } else if (byteOffset > 0x7fffffff) {\n byteOffset = 0x7fffffff\n } else if (byteOffset < -0x80000000) {\n byteOffset = -0x80000000\n }\n byteOffset = +byteOffset // Coerce to Number.\n if (isNaN(byteOffset)) {\n // byteOffset: it it's undefined, null, NaN, \"foo\", etc, search whole buffer\n byteOffset = dir ? 0 : (buffer.length - 1)\n }\n\n // Normalize byteOffset: negative offsets start from the end of the buffer\n if (byteOffset < 0) byteOffset = buffer.length + byteOffset\n if (byteOffset >= buffer.length) {\n if (dir) return -1\n else byteOffset = buffer.length - 1\n } else if (byteOffset < 0) {\n if (dir) byteOffset = 0\n else return -1\n }\n\n // Normalize val\n if (typeof val === 'string') {\n val = Buffer.from(val, encoding)\n }\n\n // Finally, search either indexOf (if dir is true) or lastIndexOf\n if (Buffer.isBuffer(val)) {\n // Special case: looking for empty string/buffer always fails\n if (val.length === 0) {\n return -1\n }\n return arrayIndexOf(buffer, val, byteOffset, encoding, dir)\n } else if (typeof val === 'number') {\n val = val & 0xFF // Search for a byte value [0-255]\n if (Buffer.TYPED_ARRAY_SUPPORT &&\n typeof Uint8Array.prototype.indexOf === 'function') {\n if (dir) {\n return Uint8Array.prototype.indexOf.call(buffer, val, byteOffset)\n } else {\n return Uint8Array.prototype.lastIndexOf.call(buffer, val, byteOffset)\n }\n }\n return arrayIndexOf(buffer, [ val ], byteOffset, encoding, dir)\n }\n\n throw new TypeError('val must be string, number or Buffer')\n}\n\nfunction arrayIndexOf (arr, val, byteOffset, encoding, dir) {\n var indexSize = 1\n var arrLength = arr.length\n var valLength = val.length\n\n if (encoding !== undefined) {\n encoding = String(encoding).toLowerCase()\n if (encoding === 'ucs2' || encoding === 'ucs-2' ||\n encoding === 'utf16le' || encoding === 'utf-16le') {\n if (arr.length < 2 || val.length < 2) {\n return -1\n }\n indexSize = 2\n arrLength /= 2\n valLength /= 2\n byteOffset /= 2\n }\n }\n\n function read (buf, i) {\n if (indexSize === 1) {\n return buf[i]\n } else {\n return buf.readUInt16BE(i * indexSize)\n }\n }\n\n var i\n if (dir) {\n var foundIndex = -1\n for (i = byteOffset; i < arrLength; i++) {\n if (read(arr, i) === read(val, foundIndex === -1 ? 0 : i - foundIndex)) {\n if (foundIndex === -1) foundIndex = i\n if (i - foundIndex + 1 === valLength) return foundIndex * indexSize\n } else {\n if (foundIndex !== -1) i -= i - foundIndex\n foundIndex = -1\n }\n }\n } else {\n if (byteOffset + valLength > arrLength) byteOffset = arrLength - valLength\n for (i = byteOffset; i >= 0; i--) {\n var found = true\n for (var j = 0; j < valLength; j++) {\n if (read(arr, i + j) !== read(val, j)) {\n found = false\n break\n }\n }\n if (found) return i\n }\n }\n\n return -1\n}\n\nBuffer.prototype.includes = function includes (val, byteOffset, encoding) {\n return this.indexOf(val, byteOffset, encoding) !== -1\n}\n\nBuffer.prototype.indexOf = function indexOf (val, byteOffset, encoding) {\n return bidirectionalIndexOf(this, val, byteOffset, encoding, true)\n}\n\nBuffer.prototype.lastIndexOf = function lastIndexOf (val, byteOffset, encoding) {\n return bidirectionalIndexOf(this, val, byteOffset, encoding, false)\n}\n\nfunction hexWrite (buf, string, offset, length) {\n offset = Number(offset) || 0\n var remaining = buf.length - offset\n if (!length) {\n length = remaining\n } else {\n length = Number(length)\n if (length > remaining) {\n length = remaining\n }\n }\n\n // must be an even number of digits\n var strLen = string.length\n if (strLen % 2 !== 0) throw new TypeError('Invalid hex string')\n\n if (length > strLen / 2) {\n length = strLen / 2\n }\n for (var i = 0; i < length; ++i) {\n var parsed = parseInt(string.substr(i * 2, 2), 16)\n if (isNaN(parsed)) return i\n buf[offset + i] = parsed\n }\n return i\n}\n\nfunction utf8Write (buf, string, offset, length) {\n return blitBuffer(utf8ToBytes(string, buf.length - offset), buf, offset, length)\n}\n\nfunction asciiWrite (buf, string, offset, length) {\n return blitBuffer(asciiToBytes(string), buf, offset, length)\n}\n\nfunction latin1Write (buf, string, offset, length) {\n return asciiWrite(buf, string, offset, length)\n}\n\nfunction base64Write (buf, string, offset, length) {\n return blitBuffer(base64ToBytes(string), buf, offset, length)\n}\n\nfunction ucs2Write (buf, string, offset, length) {\n return blitBuffer(utf16leToBytes(string, buf.length - offset), buf, offset, length)\n}\n\nBuffer.prototype.write = function write (string, offset, length, encoding) {\n // Buffer#write(string)\n if (offset === undefined) {\n encoding = 'utf8'\n length = this.length\n offset = 0\n // Buffer#write(string, encoding)\n } else if (length === undefined && typeof offset === 'string') {\n encoding = offset\n length = this.length\n offset = 0\n // Buffer#write(string, offset[, length][, encoding])\n } else if (isFinite(offset)) {\n offset = offset | 0\n if (isFinite(length)) {\n length = length | 0\n if (encoding === undefined) encoding = 'utf8'\n } else {\n encoding = length\n length = undefined\n }\n // legacy write(string, encoding, offset, length) - remove in v0.13\n } else {\n throw new Error(\n 'Buffer.write(string, encoding, offset[, length]) is no longer supported'\n )\n }\n\n var remaining = this.length - offset\n if (length === undefined || length > remaining) length = remaining\n\n if ((string.length > 0 && (length < 0 || offset < 0)) || offset > this.length) {\n throw new RangeError('Attempt to write outside buffer bounds')\n }\n\n if (!encoding) encoding = 'utf8'\n\n var loweredCase = false\n for (;;) {\n switch (encoding) {\n case 'hex':\n return hexWrite(this, string, offset, length)\n\n case 'utf8':\n case 'utf-8':\n return utf8Write(this, string, offset, length)\n\n case 'ascii':\n return asciiWrite(this, string, offset, length)\n\n case 'latin1':\n case 'binary':\n return latin1Write(this, string, offset, length)\n\n case 'base64':\n // Warning: maxLength not taken into account in base64Write\n return base64Write(this, string, offset, length)\n\n case 'ucs2':\n case 'ucs-2':\n case 'utf16le':\n case 'utf-16le':\n return ucs2Write(this, string, offset, length)\n\n default:\n if (loweredCase) throw new TypeError('Unknown encoding: ' + encoding)\n encoding = ('' + encoding).toLowerCase()\n loweredCase = true\n }\n }\n}\n\nBuffer.prototype.toJSON = function toJSON () {\n return {\n type: 'Buffer',\n data: Array.prototype.slice.call(this._arr || this, 0)\n }\n}\n\nfunction base64Slice (buf, start, end) {\n if (start === 0 && end === buf.length) {\n return base64.fromByteArray(buf)\n } else {\n return base64.fromByteArray(buf.slice(start, end))\n }\n}\n\nfunction utf8Slice (buf, start, end) {\n end = Math.min(buf.length, end)\n var res = []\n\n var i = start\n while (i < end) {\n var firstByte = buf[i]\n var codePoint = null\n var bytesPerSequence = (firstByte > 0xEF) ? 4\n : (firstByte > 0xDF) ? 3\n : (firstByte > 0xBF) ? 2\n : 1\n\n if (i + bytesPerSequence <= end) {\n var secondByte, thirdByte, fourthByte, tempCodePoint\n\n switch (bytesPerSequence) {\n case 1:\n if (firstByte < 0x80) {\n codePoint = firstByte\n }\n break\n case 2:\n secondByte = buf[i + 1]\n if ((secondByte & 0xC0) === 0x80) {\n tempCodePoint = (firstByte & 0x1F) << 0x6 | (secondByte & 0x3F)\n if (tempCodePoint > 0x7F) {\n codePoint = tempCodePoint\n }\n }\n break\n case 3:\n secondByte = buf[i + 1]\n thirdByte = buf[i + 2]\n if ((secondByte & 0xC0) === 0x80 && (thirdByte & 0xC0) === 0x80) {\n tempCodePoint = (firstByte & 0xF) << 0xC | (secondByte & 0x3F) << 0x6 | (thirdByte & 0x3F)\n if (tempCodePoint > 0x7FF && (tempCodePoint < 0xD800 || tempCodePoint > 0xDFFF)) {\n codePoint = tempCodePoint\n }\n }\n break\n case 4:\n secondByte = buf[i + 1]\n thirdByte = buf[i + 2]\n fourthByte = buf[i + 3]\n if ((secondByte & 0xC0) === 0x80 && (thirdByte & 0xC0) === 0x80 && (fourthByte & 0xC0) === 0x80) {\n tempCodePoint = (firstByte & 0xF) << 0x12 | (secondByte & 0x3F) << 0xC | (thirdByte & 0x3F) << 0x6 | (fourthByte & 0x3F)\n if (tempCodePoint > 0xFFFF && tempCodePoint < 0x110000) {\n codePoint = tempCodePoint\n }\n }\n }\n }\n\n if (codePoint === null) {\n // we did not generate a valid codePoint so insert a\n // replacement char (U+FFFD) and advance only 1 byte\n codePoint = 0xFFFD\n bytesPerSequence = 1\n } else if (codePoint > 0xFFFF) {\n // encode to utf16 (surrogate pair dance)\n codePoint -= 0x10000\n res.push(codePoint >>> 10 & 0x3FF | 0xD800)\n codePoint = 0xDC00 | codePoint & 0x3FF\n }\n\n res.push(codePoint)\n i += bytesPerSequence\n }\n\n return decodeCodePointsArray(res)\n}\n\n// Based on http://stackoverflow.com/a/22747272/680742, the browser with\n// the lowest limit is Chrome, with 0x10000 args.\n// We go 1 magnitude less, for safety\nvar MAX_ARGUMENTS_LENGTH = 0x1000\n\nfunction decodeCodePointsArray (codePoints) {\n var len = codePoints.length\n if (len <= MAX_ARGUMENTS_LENGTH) {\n return String.fromCharCode.apply(String, codePoints) // avoid extra slice()\n }\n\n // Decode in chunks to avoid \"call stack size exceeded\".\n var res = ''\n var i = 0\n while (i < len) {\n res += String.fromCharCode.apply(\n String,\n codePoints.slice(i, i += MAX_ARGUMENTS_LENGTH)\n )\n }\n return res\n}\n\nfunction asciiSlice (buf, start, end) {\n var ret = ''\n end = Math.min(buf.length, end)\n\n for (var i = start; i < end; ++i) {\n ret += String.fromCharCode(buf[i] & 0x7F)\n }\n return ret\n}\n\nfunction latin1Slice (buf, start, end) {\n var ret = ''\n end = Math.min(buf.length, end)\n\n for (var i = start; i < end; ++i) {\n ret += String.fromCharCode(buf[i])\n }\n return ret\n}\n\nfunction hexSlice (buf, start, end) {\n var len = buf.length\n\n if (!start || start < 0) start = 0\n if (!end || end < 0 || end > len) end = len\n\n var out = ''\n for (var i = start; i < end; ++i) {\n out += toHex(buf[i])\n }\n return out\n}\n\nfunction utf16leSlice (buf, start, end) {\n var bytes = buf.slice(start, end)\n var res = ''\n for (var i = 0; i < bytes.length; i += 2) {\n res += String.fromCharCode(bytes[i] + bytes[i + 1] * 256)\n }\n return res\n}\n\nBuffer.prototype.slice = function slice (start, end) {\n var len = this.length\n start = ~~start\n end = end === undefined ? len : ~~end\n\n if (start < 0) {\n start += len\n if (start < 0) start = 0\n } else if (start > len) {\n start = len\n }\n\n if (end < 0) {\n end += len\n if (end < 0) end = 0\n } else if (end > len) {\n end = len\n }\n\n if (end < start) end = start\n\n var newBuf\n if (Buffer.TYPED_ARRAY_SUPPORT) {\n newBuf = this.subarray(start, end)\n newBuf.__proto__ = Buffer.prototype\n } else {\n var sliceLen = end - start\n newBuf = new Buffer(sliceLen, undefined)\n for (var i = 0; i < sliceLen; ++i) {\n newBuf[i] = this[i + start]\n }\n }\n\n return newBuf\n}\n\n/*\n * Need to make sure that buffer isn't trying to write out of bounds.\n */\nfunction checkOffset (offset, ext, length) {\n if ((offset % 1) !== 0 || offset < 0) throw new RangeError('offset is not uint')\n if (offset + ext > length) throw new RangeError('Trying to access beyond buffer length')\n}\n\nBuffer.prototype.readUIntLE = function readUIntLE (offset, byteLength, noAssert) {\n offset = offset | 0\n byteLength = byteLength | 0\n if (!noAssert) checkOffset(offset, byteLength, this.length)\n\n var val = this[offset]\n var mul = 1\n var i = 0\n while (++i < byteLength && (mul *= 0x100)) {\n val += this[offset + i] * mul\n }\n\n return val\n}\n\nBuffer.prototype.readUIntBE = function readUIntBE (offset, byteLength, noAssert) {\n offset = offset | 0\n byteLength = byteLength | 0\n if (!noAssert) {\n checkOffset(offset, byteLength, this.length)\n }\n\n var val = this[offset + --byteLength]\n var mul = 1\n while (byteLength > 0 && (mul *= 0x100)) {\n val += this[offset + --byteLength] * mul\n }\n\n return val\n}\n\nBuffer.prototype.readUInt8 = function readUInt8 (offset, noAssert) {\n if (!noAssert) checkOffset(offset, 1, this.length)\n return this[offset]\n}\n\nBuffer.prototype.readUInt16LE = function readUInt16LE (offset, noAssert) {\n if (!noAssert) checkOffset(offset, 2, this.length)\n return this[offset] | (this[offset + 1] << 8)\n}\n\nBuffer.prototype.readUInt16BE = function readUInt16BE (offset, noAssert) {\n if (!noAssert) checkOffset(offset, 2, this.length)\n return (this[offset] << 8) | this[offset + 1]\n}\n\nBuffer.prototype.readUInt32LE = function readUInt32LE (offset, noAssert) {\n if (!noAssert) checkOffset(offset, 4, this.length)\n\n return ((this[offset]) |\n (this[offset + 1] << 8) |\n (this[offset + 2] << 16)) +\n (this[offset + 3] * 0x1000000)\n}\n\nBuffer.prototype.readUInt32BE = function readUInt32BE (offset, noAssert) {\n if (!noAssert) checkOffset(offset, 4, this.length)\n\n return (this[offset] * 0x1000000) +\n ((this[offset + 1] << 16) |\n (this[offset + 2] << 8) |\n this[offset + 3])\n}\n\nBuffer.prototype.readIntLE = function readIntLE (offset, byteLength, noAssert) {\n offset = offset | 0\n byteLength = byteLength | 0\n if (!noAssert) checkOffset(offset, byteLength, this.length)\n\n var val = this[offset]\n var mul = 1\n var i = 0\n while (++i < byteLength && (mul *= 0x100)) {\n val += this[offset + i] * mul\n }\n mul *= 0x80\n\n if (val >= mul) val -= Math.pow(2, 8 * byteLength)\n\n return val\n}\n\nBuffer.prototype.readIntBE = function readIntBE (offset, byteLength, noAssert) {\n offset = offset | 0\n byteLength = byteLength | 0\n if (!noAssert) checkOffset(offset, byteLength, this.length)\n\n var i = byteLength\n var mul = 1\n var val = this[offset + --i]\n while (i > 0 && (mul *= 0x100)) {\n val += this[offset + --i] * mul\n }\n mul *= 0x80\n\n if (val >= mul) val -= Math.pow(2, 8 * byteLength)\n\n return val\n}\n\nBuffer.prototype.readInt8 = function readInt8 (offset, noAssert) {\n if (!noAssert) checkOffset(offset, 1, this.length)\n if (!(this[offset] & 0x80)) return (this[offset])\n return ((0xff - this[offset] + 1) * -1)\n}\n\nBuffer.prototype.readInt16LE = function readInt16LE (offset, noAssert) {\n if (!noAssert) checkOffset(offset, 2, this.length)\n var val = this[offset] | (this[offset + 1] << 8)\n return (val & 0x8000) ? val | 0xFFFF0000 : val\n}\n\nBuffer.prototype.readInt16BE = function readInt16BE (offset, noAssert) {\n if (!noAssert) checkOffset(offset, 2, this.length)\n var val = this[offset + 1] | (this[offset] << 8)\n return (val & 0x8000) ? val | 0xFFFF0000 : val\n}\n\nBuffer.prototype.readInt32LE = function readInt32LE (offset, noAssert) {\n if (!noAssert) checkOffset(offset, 4, this.length)\n\n return (this[offset]) |\n (this[offset + 1] << 8) |\n (this[offset + 2] << 16) |\n (this[offset + 3] << 24)\n}\n\nBuffer.prototype.readInt32BE = function readInt32BE (offset, noAssert) {\n if (!noAssert) checkOffset(offset, 4, this.length)\n\n return (this[offset] << 24) |\n (this[offset + 1] << 16) |\n (this[offset + 2] << 8) |\n (this[offset + 3])\n}\n\nBuffer.prototype.readFloatLE = function readFloatLE (offset, noAssert) {\n if (!noAssert) checkOffset(offset, 4, this.length)\n return ieee754.read(this, offset, true, 23, 4)\n}\n\nBuffer.prototype.readFloatBE = function readFloatBE (offset, noAssert) {\n if (!noAssert) checkOffset(offset, 4, this.length)\n return ieee754.read(this, offset, false, 23, 4)\n}\n\nBuffer.prototype.readDoubleLE = function readDoubleLE (offset, noAssert) {\n if (!noAssert) checkOffset(offset, 8, this.length)\n return ieee754.read(this, offset, true, 52, 8)\n}\n\nBuffer.prototype.readDoubleBE = function readDoubleBE (offset, noAssert) {\n if (!noAssert) checkOffset(offset, 8, this.length)\n return ieee754.read(this, offset, false, 52, 8)\n}\n\nfunction checkInt (buf, value, offset, ext, max, min) {\n if (!Buffer.isBuffer(buf)) throw new TypeError('\"buffer\" argument must be a Buffer instance')\n if (value > max || value < min) throw new RangeError('\"value\" argument is out of bounds')\n if (offset + ext > buf.length) throw new RangeError('Index out of range')\n}\n\nBuffer.prototype.writeUIntLE = function writeUIntLE (value, offset, byteLength, noAssert) {\n value = +value\n offset = offset | 0\n byteLength = byteLength | 0\n if (!noAssert) {\n var maxBytes = Math.pow(2, 8 * byteLength) - 1\n checkInt(this, value, offset, byteLength, maxBytes, 0)\n }\n\n var mul = 1\n var i = 0\n this[offset] = value & 0xFF\n while (++i < byteLength && (mul *= 0x100)) {\n this[offset + i] = (value / mul) & 0xFF\n }\n\n return offset + byteLength\n}\n\nBuffer.prototype.writeUIntBE = function writeUIntBE (value, offset, byteLength, noAssert) {\n value = +value\n offset = offset | 0\n byteLength = byteLength | 0\n if (!noAssert) {\n var maxBytes = Math.pow(2, 8 * byteLength) - 1\n checkInt(this, value, offset, byteLength, maxBytes, 0)\n }\n\n var i = byteLength - 1\n var mul = 1\n this[offset + i] = value & 0xFF\n while (--i >= 0 && (mul *= 0x100)) {\n this[offset + i] = (value / mul) & 0xFF\n }\n\n return offset + byteLength\n}\n\nBuffer.prototype.writeUInt8 = function writeUInt8 (value, offset, noAssert) {\n value = +value\n offset = offset | 0\n if (!noAssert) checkInt(this, value, offset, 1, 0xff, 0)\n if (!Buffer.TYPED_ARRAY_SUPPORT) value = Math.floor(value)\n this[offset] = (value & 0xff)\n return offset + 1\n}\n\nfunction objectWriteUInt16 (buf, value, offset, littleEndian) {\n if (value < 0) value = 0xffff + value + 1\n for (var i = 0, j = Math.min(buf.length - offset, 2); i < j; ++i) {\n buf[offset + i] = (value & (0xff << (8 * (littleEndian ? i : 1 - i)))) >>>\n (littleEndian ? i : 1 - i) * 8\n }\n}\n\nBuffer.prototype.writeUInt16LE = function writeUInt16LE (value, offset, noAssert) {\n value = +value\n offset = offset | 0\n if (!noAssert) checkInt(this, value, offset, 2, 0xffff, 0)\n if (Buffer.TYPED_ARRAY_SUPPORT) {\n this[offset] = (value & 0xff)\n this[offset + 1] = (value >>> 8)\n } else {\n objectWriteUInt16(this, value, offset, true)\n }\n return offset + 2\n}\n\nBuffer.prototype.writeUInt16BE = function writeUInt16BE (value, offset, noAssert) {\n value = +value\n offset = offset | 0\n if (!noAssert) checkInt(this, value, offset, 2, 0xffff, 0)\n if (Buffer.TYPED_ARRAY_SUPPORT) {\n this[offset] = (value >>> 8)\n this[offset + 1] = (value & 0xff)\n } else {\n objectWriteUInt16(this, value, offset, false)\n }\n return offset + 2\n}\n\nfunction objectWriteUInt32 (buf, value, offset, littleEndian) {\n if (value < 0) value = 0xffffffff + value + 1\n for (var i = 0, j = Math.min(buf.length - offset, 4); i < j; ++i) {\n buf[offset + i] = (value >>> (littleEndian ? i : 3 - i) * 8) & 0xff\n }\n}\n\nBuffer.prototype.writeUInt32LE = function writeUInt32LE (value, offset, noAssert) {\n value = +value\n offset = offset | 0\n if (!noAssert) checkInt(this, value, offset, 4, 0xffffffff, 0)\n if (Buffer.TYPED_ARRAY_SUPPORT) {\n this[offset + 3] = (value >>> 24)\n this[offset + 2] = (value >>> 16)\n this[offset + 1] = (value >>> 8)\n this[offset] = (value & 0xff)\n } else {\n objectWriteUInt32(this, value, offset, true)\n }\n return offset + 4\n}\n\nBuffer.prototype.writeUInt32BE = function writeUInt32BE (value, offset, noAssert) {\n value = +value\n offset = offset | 0\n if (!noAssert) checkInt(this, value, offset, 4, 0xffffffff, 0)\n if (Buffer.TYPED_ARRAY_SUPPORT) {\n this[offset] = (value >>> 24)\n this[offset + 1] = (value >>> 16)\n this[offset + 2] = (value >>> 8)\n this[offset + 3] = (value & 0xff)\n } else {\n objectWriteUInt32(this, value, offset, false)\n }\n return offset + 4\n}\n\nBuffer.prototype.writeIntLE = function writeIntLE (value, offset, byteLength, noAssert) {\n value = +value\n offset = offset | 0\n if (!noAssert) {\n var limit = Math.pow(2, 8 * byteLength - 1)\n\n checkInt(this, value, offset, byteLength, limit - 1, -limit)\n }\n\n var i = 0\n var mul = 1\n var sub = 0\n this[offset] = value & 0xFF\n while (++i < byteLength && (mul *= 0x100)) {\n if (value < 0 && sub === 0 && this[offset + i - 1] !== 0) {\n sub = 1\n }\n this[offset + i] = ((value / mul) >> 0) - sub & 0xFF\n }\n\n return offset + byteLength\n}\n\nBuffer.prototype.writeIntBE = function writeIntBE (value, offset, byteLength, noAssert) {\n value = +value\n offset = offset | 0\n if (!noAssert) {\n var limit = Math.pow(2, 8 * byteLength - 1)\n\n checkInt(this, value, offset, byteLength, limit - 1, -limit)\n }\n\n var i = byteLength - 1\n var mul = 1\n var sub = 0\n this[offset + i] = value & 0xFF\n while (--i >= 0 && (mul *= 0x100)) {\n if (value < 0 && sub === 0 && this[offset + i + 1] !== 0) {\n sub = 1\n }\n this[offset + i] = ((value / mul) >> 0) - sub & 0xFF\n }\n\n return offset + byteLength\n}\n\nBuffer.prototype.writeInt8 = function writeInt8 (value, offset, noAssert) {\n value = +value\n offset = offset | 0\n if (!noAssert) checkInt(this, value, offset, 1, 0x7f, -0x80)\n if (!Buffer.TYPED_ARRAY_SUPPORT) value = Math.floor(value)\n if (value < 0) value = 0xff + value + 1\n this[offset] = (value & 0xff)\n return offset + 1\n}\n\nBuffer.prototype.writeInt16LE = function writeInt16LE (value, offset, noAssert) {\n value = +value\n offset = offset | 0\n if (!noAssert) checkInt(this, value, offset, 2, 0x7fff, -0x8000)\n if (Buffer.TYPED_ARRAY_SUPPORT) {\n this[offset] = (value & 0xff)\n this[offset + 1] = (value >>> 8)\n } else {\n objectWriteUInt16(this, value, offset, true)\n }\n return offset + 2\n}\n\nBuffer.prototype.writeInt16BE = function writeInt16BE (value, offset, noAssert) {\n value = +value\n offset = offset | 0\n if (!noAssert) checkInt(this, value, offset, 2, 0x7fff, -0x8000)\n if (Buffer.TYPED_ARRAY_SUPPORT) {\n this[offset] = (value >>> 8)\n this[offset + 1] = (value & 0xff)\n } else {\n objectWriteUInt16(this, value, offset, false)\n }\n return offset + 2\n}\n\nBuffer.prototype.writeInt32LE = function writeInt32LE (value, offset, noAssert) {\n value = +value\n offset = offset | 0\n if (!noAssert) checkInt(this, value, offset, 4, 0x7fffffff, -0x80000000)\n if (Buffer.TYPED_ARRAY_SUPPORT) {\n this[offset] = (value & 0xff)\n this[offset + 1] = (value >>> 8)\n this[offset + 2] = (value >>> 16)\n this[offset + 3] = (value >>> 24)\n } else {\n objectWriteUInt32(this, value, offset, true)\n }\n return offset + 4\n}\n\nBuffer.prototype.writeInt32BE = function writeInt32BE (value, offset, noAssert) {\n value = +value\n offset = offset | 0\n if (!noAssert) checkInt(this, value, offset, 4, 0x7fffffff, -0x80000000)\n if (value < 0) value = 0xffffffff + value + 1\n if (Buffer.TYPED_ARRAY_SUPPORT) {\n this[offset] = (value >>> 24)\n this[offset + 1] = (value >>> 16)\n this[offset + 2] = (value >>> 8)\n this[offset + 3] = (value & 0xff)\n } else {\n objectWriteUInt32(this, value, offset, false)\n }\n return offset + 4\n}\n\nfunction checkIEEE754 (buf, value, offset, ext, max, min) {\n if (offset + ext > buf.length) throw new RangeError('Index out of range')\n if (offset < 0) throw new RangeError('Index out of range')\n}\n\nfunction writeFloat (buf, value, offset, littleEndian, noAssert) {\n if (!noAssert) {\n checkIEEE754(buf, value, offset, 4, 3.4028234663852886e+38, -3.4028234663852886e+38)\n }\n ieee754.write(buf, value, offset, littleEndian, 23, 4)\n return offset + 4\n}\n\nBuffer.prototype.writeFloatLE = function writeFloatLE (value, offset, noAssert) {\n return writeFloat(this, value, offset, true, noAssert)\n}\n\nBuffer.prototype.writeFloatBE = function writeFloatBE (value, offset, noAssert) {\n return writeFloat(this, value, offset, false, noAssert)\n}\n\nfunction writeDouble (buf, value, offset, littleEndian, noAssert) {\n if (!noAssert) {\n checkIEEE754(buf, value, offset, 8, 1.7976931348623157E+308, -1.7976931348623157E+308)\n }\n ieee754.write(buf, value, offset, littleEndian, 52, 8)\n return offset + 8\n}\n\nBuffer.prototype.writeDoubleLE = function writeDoubleLE (value, offset, noAssert) {\n return writeDouble(this, value, offset, true, noAssert)\n}\n\nBuffer.prototype.writeDoubleBE = function writeDoubleBE (value, offset, noAssert) {\n return writeDouble(this, value, offset, false, noAssert)\n}\n\n// copy(targetBuffer, targetStart=0, sourceStart=0, sourceEnd=buffer.length)\nBuffer.prototype.copy = function copy (target, targetStart, start, end) {\n if (!start) start = 0\n if (!end && end !== 0) end = this.length\n if (targetStart >= target.length) targetStart = target.length\n if (!targetStart) targetStart = 0\n if (end > 0 && end < start) end = start\n\n // Copy 0 bytes; we're done\n if (end === start) return 0\n if (target.length === 0 || this.length === 0) return 0\n\n // Fatal error conditions\n if (targetStart < 0) {\n throw new RangeError('targetStart out of bounds')\n }\n if (start < 0 || start >= this.length) throw new RangeError('sourceStart out of bounds')\n if (end < 0) throw new RangeError('sourceEnd out of bounds')\n\n // Are we oob?\n if (end > this.length) end = this.length\n if (target.length - targetStart < end - start) {\n end = target.length - targetStart + start\n }\n\n var len = end - start\n var i\n\n if (this === target && start < targetStart && targetStart < end) {\n // descending copy from end\n for (i = len - 1; i >= 0; --i) {\n target[i + targetStart] = this[i + start]\n }\n } else if (len < 1000 || !Buffer.TYPED_ARRAY_SUPPORT) {\n // ascending copy from start\n for (i = 0; i < len; ++i) {\n target[i + targetStart] = this[i + start]\n }\n } else {\n Uint8Array.prototype.set.call(\n target,\n this.subarray(start, start + len),\n targetStart\n )\n }\n\n return len\n}\n\n// Usage:\n// buffer.fill(number[, offset[, end]])\n// buffer.fill(buffer[, offset[, end]])\n// buffer.fill(string[, offset[, end]][, encoding])\nBuffer.prototype.fill = function fill (val, start, end, encoding) {\n // Handle string cases:\n if (typeof val === 'string') {\n if (typeof start === 'string') {\n encoding = start\n start = 0\n end = this.length\n } else if (typeof end === 'string') {\n encoding = end\n end = this.length\n }\n if (val.length === 1) {\n var code = val.charCodeAt(0)\n if (code < 256) {\n val = code\n }\n }\n if (encoding !== undefined && typeof encoding !== 'string') {\n throw new TypeError('encoding must be a string')\n }\n if (typeof encoding === 'string' && !Buffer.isEncoding(encoding)) {\n throw new TypeError('Unknown encoding: ' + encoding)\n }\n } else if (typeof val === 'number') {\n val = val & 255\n }\n\n // Invalid ranges are not set to a default, so can range check early.\n if (start < 0 || this.length < start || this.length < end) {\n throw new RangeError('Out of range index')\n }\n\n if (end <= start) {\n return this\n }\n\n start = start >>> 0\n end = end === undefined ? this.length : end >>> 0\n\n if (!val) val = 0\n\n var i\n if (typeof val === 'number') {\n for (i = start; i < end; ++i) {\n this[i] = val\n }\n } else {\n var bytes = Buffer.isBuffer(val)\n ? val\n : utf8ToBytes(new Buffer(val, encoding).toString())\n var len = bytes.length\n for (i = 0; i < end - start; ++i) {\n this[i + start] = bytes[i % len]\n }\n }\n\n return this\n}\n\n// HELPER FUNCTIONS\n// ================\n\nvar INVALID_BASE64_RE = /[^+\\/0-9A-Za-z-_]/g\n\nfunction base64clean (str) {\n // Node strips out invalid characters like \\n and \\t from the string, base64-js does not\n str = stringtrim(str).replace(INVALID_BASE64_RE, '')\n // Node converts strings with length < 2 to ''\n if (str.length < 2) return ''\n // Node allows for non-padded base64 strings (missing trailing ===), base64-js does not\n while (str.length % 4 !== 0) {\n str = str + '='\n }\n return str\n}\n\nfunction stringtrim (str) {\n if (str.trim) return str.trim()\n return str.replace(/^\\s+|\\s+$/g, '')\n}\n\nfunction toHex (n) {\n if (n < 16) return '0' + n.toString(16)\n return n.toString(16)\n}\n\nfunction utf8ToBytes (string, units) {\n units = units || Infinity\n var codePoint\n var length = string.length\n var leadSurrogate = null\n var bytes = []\n\n for (var i = 0; i < length; ++i) {\n codePoint = string.charCodeAt(i)\n\n // is surrogate component\n if (codePoint > 0xD7FF && codePoint < 0xE000) {\n // last char was a lead\n if (!leadSurrogate) {\n // no lead yet\n if (codePoint > 0xDBFF) {\n // unexpected trail\n if ((units -= 3) > -1) bytes.push(0xEF, 0xBF, 0xBD)\n continue\n } else if (i + 1 === length) {\n // unpaired lead\n if ((units -= 3) > -1) bytes.push(0xEF, 0xBF, 0xBD)\n continue\n }\n\n // valid lead\n leadSurrogate = codePoint\n\n continue\n }\n\n // 2 leads in a row\n if (codePoint < 0xDC00) {\n if ((units -= 3) > -1) bytes.push(0xEF, 0xBF, 0xBD)\n leadSurrogate = codePoint\n continue\n }\n\n // valid surrogate pair\n codePoint = (leadSurrogate - 0xD800 << 10 | codePoint - 0xDC00) + 0x10000\n } else if (leadSurrogate) {\n // valid bmp char, but last char was a lead\n if ((units -= 3) > -1) bytes.push(0xEF, 0xBF, 0xBD)\n }\n\n leadSurrogate = null\n\n // encode utf8\n if (codePoint < 0x80) {\n if ((units -= 1) < 0) break\n bytes.push(codePoint)\n } else if (codePoint < 0x800) {\n if ((units -= 2) < 0) break\n bytes.push(\n codePoint >> 0x6 | 0xC0,\n codePoint & 0x3F | 0x80\n )\n } else if (codePoint < 0x10000) {\n if ((units -= 3) < 0) break\n bytes.push(\n codePoint >> 0xC | 0xE0,\n codePoint >> 0x6 & 0x3F | 0x80,\n codePoint & 0x3F | 0x80\n )\n } else if (codePoint < 0x110000) {\n if ((units -= 4) < 0) break\n bytes.push(\n codePoint >> 0x12 | 0xF0,\n codePoint >> 0xC & 0x3F | 0x80,\n codePoint >> 0x6 & 0x3F | 0x80,\n codePoint & 0x3F | 0x80\n )\n } else {\n throw new Error('Invalid code point')\n }\n }\n\n return bytes\n}\n\nfunction asciiToBytes (str) {\n var byteArray = []\n for (var i = 0; i < str.length; ++i) {\n // Node's code seems to be doing this and not & 0x7F..\n byteArray.push(str.charCodeAt(i) & 0xFF)\n }\n return byteArray\n}\n\nfunction utf16leToBytes (str, units) {\n var c, hi, lo\n var byteArray = []\n for (var i = 0; i < str.length; ++i) {\n if ((units -= 2) < 0) break\n\n c = str.charCodeAt(i)\n hi = c >> 8\n lo = c % 256\n byteArray.push(lo)\n byteArray.push(hi)\n }\n\n return byteArray\n}\n\nfunction base64ToBytes (str) {\n return base64.toByteArray(base64clean(str))\n}\n\nfunction blitBuffer (src, dst, offset, length) {\n for (var i = 0; i < length; ++i) {\n if ((i + offset >= dst.length) || (i >= src.length)) break\n dst[i + offset] = src[i]\n }\n return i\n}\n\nfunction isnan (val) {\n return val !== val // eslint-disable-line no-self-compare\n}\n","'use strict'\n\nexports.byteLength = byteLength\nexports.toByteArray = toByteArray\nexports.fromByteArray = fromByteArray\n\nvar lookup = []\nvar revLookup = []\nvar Arr = typeof Uint8Array !== 'undefined' ? Uint8Array : Array\n\nvar code = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/'\nfor (var i = 0, len = code.length; i < len; ++i) {\n lookup[i] = code[i]\n revLookup[code.charCodeAt(i)] = i\n}\n\n// Support decoding URL-safe base64 strings, as Node.js does.\n// See: https://en.wikipedia.org/wiki/Base64#URL_applications\nrevLookup['-'.charCodeAt(0)] = 62\nrevLookup['_'.charCodeAt(0)] = 63\n\nfunction getLens (b64) {\n var len = b64.length\n\n if (len % 4 > 0) {\n throw new Error('Invalid string. Length must be a multiple of 4')\n }\n\n // Trim off extra bytes after placeholder bytes are found\n // See: https://github.com/beatgammit/base64-js/issues/42\n var validLen = b64.indexOf('=')\n if (validLen === -1) validLen = len\n\n var placeHoldersLen = validLen === len\n ? 0\n : 4 - (validLen % 4)\n\n return [validLen, placeHoldersLen]\n}\n\n// base64 is 4/3 + up to two characters of the original data\nfunction byteLength (b64) {\n var lens = getLens(b64)\n var validLen = lens[0]\n var placeHoldersLen = lens[1]\n return ((validLen + placeHoldersLen) * 3 / 4) - placeHoldersLen\n}\n\nfunction _byteLength (b64, validLen, placeHoldersLen) {\n return ((validLen + placeHoldersLen) * 3 / 4) - placeHoldersLen\n}\n\nfunction toByteArray (b64) {\n var tmp\n var lens = getLens(b64)\n var validLen = lens[0]\n var placeHoldersLen = lens[1]\n\n var arr = new Arr(_byteLength(b64, validLen, placeHoldersLen))\n\n var curByte = 0\n\n // if there are placeholders, only get up to the last complete 4 chars\n var len = placeHoldersLen > 0\n ? validLen - 4\n : validLen\n\n var i\n for (i = 0; i < len; i += 4) {\n tmp =\n (revLookup[b64.charCodeAt(i)] << 18) |\n (revLookup[b64.charCodeAt(i + 1)] << 12) |\n (revLookup[b64.charCodeAt(i + 2)] << 6) |\n revLookup[b64.charCodeAt(i + 3)]\n arr[curByte++] = (tmp >> 16) & 0xFF\n arr[curByte++] = (tmp >> 8) & 0xFF\n arr[curByte++] = tmp & 0xFF\n }\n\n if (placeHoldersLen === 2) {\n tmp =\n (revLookup[b64.charCodeAt(i)] << 2) |\n (revLookup[b64.charCodeAt(i + 1)] >> 4)\n arr[curByte++] = tmp & 0xFF\n }\n\n if (placeHoldersLen === 1) {\n tmp =\n (revLookup[b64.charCodeAt(i)] << 10) |\n (revLookup[b64.charCodeAt(i + 1)] << 4) |\n (revLookup[b64.charCodeAt(i + 2)] >> 2)\n arr[curByte++] = (tmp >> 8) & 0xFF\n arr[curByte++] = tmp & 0xFF\n }\n\n return arr\n}\n\nfunction tripletToBase64 (num) {\n return lookup[num >> 18 & 0x3F] +\n lookup[num >> 12 & 0x3F] +\n lookup[num >> 6 & 0x3F] +\n lookup[num & 0x3F]\n}\n\nfunction encodeChunk (uint8, start, end) {\n var tmp\n var output = []\n for (var i = start; i < end; i += 3) {\n tmp =\n ((uint8[i] << 16) & 0xFF0000) +\n ((uint8[i + 1] << 8) & 0xFF00) +\n (uint8[i + 2] & 0xFF)\n output.push(tripletToBase64(tmp))\n }\n return output.join('')\n}\n\nfunction fromByteArray (uint8) {\n var tmp\n var len = uint8.length\n var extraBytes = len % 3 // if we have 1 byte left, pad 2 bytes\n var parts = []\n var maxChunkLength = 16383 // must be multiple of 3\n\n // go through the array every three bytes, we'll deal with trailing stuff later\n for (var i = 0, len2 = len - extraBytes; i < len2; i += maxChunkLength) {\n parts.push(encodeChunk(\n uint8, i, (i + maxChunkLength) > len2 ? len2 : (i + maxChunkLength)\n ))\n }\n\n // pad the end with zeros, but make sure to not forget the extra bytes\n if (extraBytes === 1) {\n tmp = uint8[len - 1]\n parts.push(\n lookup[tmp >> 2] +\n lookup[(tmp << 4) & 0x3F] +\n '=='\n )\n } else if (extraBytes === 2) {\n tmp = (uint8[len - 2] << 8) + uint8[len - 1]\n parts.push(\n lookup[tmp >> 10] +\n lookup[(tmp >> 4) & 0x3F] +\n lookup[(tmp << 2) & 0x3F] +\n '='\n )\n }\n\n return parts.join('')\n}\n","exports.read = function (buffer, offset, isLE, mLen, nBytes) {\n var e, m\n var eLen = (nBytes * 8) - mLen - 1\n var eMax = (1 << eLen) - 1\n var eBias = eMax >> 1\n var nBits = -7\n var i = isLE ? (nBytes - 1) : 0\n var d = isLE ? -1 : 1\n var s = buffer[offset + i]\n\n i += d\n\n e = s & ((1 << (-nBits)) - 1)\n s >>= (-nBits)\n nBits += eLen\n for (; nBits > 0; e = (e * 256) + buffer[offset + i], i += d, nBits -= 8) {}\n\n m = e & ((1 << (-nBits)) - 1)\n e >>= (-nBits)\n nBits += mLen\n for (; nBits > 0; m = (m * 256) + buffer[offset + i], i += d, nBits -= 8) {}\n\n if (e === 0) {\n e = 1 - eBias\n } else if (e === eMax) {\n return m ? NaN : ((s ? -1 : 1) * Infinity)\n } else {\n m = m + Math.pow(2, mLen)\n e = e - eBias\n }\n return (s ? -1 : 1) * m * Math.pow(2, e - mLen)\n}\n\nexports.write = function (buffer, value, offset, isLE, mLen, nBytes) {\n var e, m, c\n var eLen = (nBytes * 8) - mLen - 1\n var eMax = (1 << eLen) - 1\n var eBias = eMax >> 1\n var rt = (mLen === 23 ? Math.pow(2, -24) - Math.pow(2, -77) : 0)\n var i = isLE ? 0 : (nBytes - 1)\n var d = isLE ? 1 : -1\n var s = value < 0 || (value === 0 && 1 / value < 0) ? 1 : 0\n\n value = Math.abs(value)\n\n if (isNaN(value) || value === Infinity) {\n m = isNaN(value) ? 1 : 0\n e = eMax\n } else {\n e = Math.floor(Math.log(value) / Math.LN2)\n if (value * (c = Math.pow(2, -e)) < 1) {\n e--\n c *= 2\n }\n if (e + eBias >= 1) {\n value += rt / c\n } else {\n value += rt * Math.pow(2, 1 - eBias)\n }\n if (value * c >= 2) {\n e++\n c /= 2\n }\n\n if (e + eBias >= eMax) {\n m = 0\n e = eMax\n } else if (e + eBias >= 1) {\n m = ((value * c) - 1) * Math.pow(2, mLen)\n e = e + eBias\n } else {\n m = value * Math.pow(2, eBias - 1) * Math.pow(2, mLen)\n e = 0\n }\n }\n\n for (; mLen >= 8; buffer[offset + i] = m & 0xff, i += d, m /= 256, mLen -= 8) {}\n\n e = (e << mLen) | m\n eLen += mLen\n for (; eLen > 0; buffer[offset + i] = e & 0xff, i += d, e /= 256, eLen -= 8) {}\n\n buffer[offset + i - d] |= s * 128\n}\n","var toString = {}.toString;\n\nmodule.exports = Array.isArray || function (arr) {\n return toString.call(arr) == '[object Array]';\n};\n","import { fabric } from 'fabric';\n\n/**\n * @function createSvgFromCanvas - create svg from canvas\n * @param {Object} canvasToConvert - fabric canvas object\n * @returns {String} encodeSVG\n */\nfunction createSvgFromCanvas (canvasToConvert) {\n let svg = canvasToConvert.toSVG().toString().replace(/&(?!amp;)/g, '&').replace(/https:\\/\\//g, 'http://');\n let encodeSVG = encodeURIComponent(svg);\n return encodeSVG;\n}\n\n/**\n * @function generateSvgForOTP - generate svg for otp and return svgAllFormat\n * @param {Object} canvasOptions - canvas options to create canvas elements\n * @returns {Object} svgAllFormat\n */\nexport function generateSvgForOTP (canvasOptions) {\n let svgAllFormat = {};\n let top = canvasOptions.top;\n let left = canvasOptions.left;\n let customizeText = canvasOptions.customizeText;\n let customizeFont = canvasOptions.customizeFont;\n let customizeColor = canvasOptions.customizeColor;\n let imageToLoad = canvasOptions.imageToLoad;\n\n let newCanvas = new fabric.StaticCanvas('rebuildCanvas', {\n width: 2000,\n height: 3000,\n });\n\n const canvasRatio = 7.125; // canvas ratio calculated based on the design dimensions of the image (2000/355)\n let canvasText = new fabric.Textbox(customizeText, {\n top: top,\n left: left,\n originX: 'center',\n originY: 'center',\n width: canvasRatio * 48,\n fontSize: canvasRatio * 10,\n lineHeight: canvasRatio * 15,\n fontFamily: customizeFont,\n textAlign: 'center',\n fill: customizeColor,\n });\n\n let img = $(imageToLoad)[0];\n let canvasImage = new fabric.Image(img, {\n top: 0,\n selectable: false,\n hasRotatingPoint: true,\n width: 2000,\n height: 3000\n });\n canvasImage.scaleToWidth(2000);\n\n let canvasGroup = new fabric.Group([canvasImage, canvasText], {});\n newCanvas.add(canvasGroup);\n\n // FULL TEXT SVG\n svgAllFormat.personalizationFullSVG = createSvgFromCanvas(newCanvas);\n\n // HALF SIZE SVG\n let scaleRatio = Math.min(0.5);\n newCanvas.setDimensions({ width: newCanvas.getWidth() * scaleRatio, height: newCanvas.getHeight() * scaleRatio });\n newCanvas.setZoom(scaleRatio);\n svgAllFormat.personalizationSmallSVG = createSvgFromCanvas(newCanvas);\n\n // ONLY TEXT SVG\n canvasGroup.remove(canvasImage);\n newCanvas.clear();\n newCanvas.add(canvasGroup);\n let personalizationTextSVG = createSvgFromCanvas(newCanvas);\n svgAllFormat.personalizationTextSVG = personalizationTextSVG;\n\n return svgAllFormat;\n}\n","const SELECTORS = {\n page: '.js-customizePage',\n personalizationCanvas: '#personalization-canvas',\n mainChoice: '.js-sectionMainChoice',\n imgFront: '#img-object-front',\n imgBack: '#img-object-back',\n pixelText: '#pixel-text',\n canvasNode: '.js-customize-canvas',\n textInput: '.js-input-type1',\n fontsButtons: '.js-choice-editor .cc-choice-item',\n colorsButtons: '.js-choice-editor .cc-choice-pattern_item',\n showOtherSide: '.js-show-other-side',\n hotspotOne: '.js-customizePage .js-positionChoice-1',\n hotspotTwo: '.js-customizePage .js-positionChoice-2',\n stepOne: '.js-customize-step1',\n stepTwo: '.js-customize-step2',\n termsBottomDesktop: 'js-termsCondition--bottom-desktop',\n footer: '.js-customize-footer',\n zoomButton: '.js-zoom-button',\n termsAndConditionsModal: '.js-linkModalCustomizeTerms',\n analyticsCustomizeAction: '.js-analyticsCustomizeAction',\n pageClose: '.js-customizePage-icon_pageClose',\n personalizeAddToCart: '.js-personalizeButtonModal',\n};\n\nexport default SELECTORS;\n","const CLASSES = {\n active: 'active',\n pageStepOne: 'cc-customizePage--step-one',\n pageStepTwo: 'cc-customizePage--step-two',\n};\n\nexport default CLASSES;\n","import ProductHelpers, {activatePromoAnimationMessage} from './base';\nimport {newModal, newModalFromString} from '../components/modal';\nimport {initSlotCarousel, initProductTile} from '../productTileComponent/productTile';\nimport {checkCarouselLength} from '../customCarousel';\n\nfunction isPortionOfElementInContainer(el, container) {\n const rect = el.getBoundingClientRect();\n const containerRect = container.getBoundingClientRect();\n // DOMRect { x: 8, y: 8, width: 100, height: 100, top: 8, right: 108, bottom: 108, left: 8 }\n const windowHeight =\n (window.innerHeight || document.documentElement.clientHeight) - containerRect.top;\n // http://stackoverflow.com/questions/325933/determine-whether-two-date-ranges-overlap\n const vertInView = rect.top <= windowHeight && rect.top + 0.66 * rect.height >= 0;\n return vertInView;\n}\n\nfunction computeCurrentlyVisibleImage() {}\n\nconst handleDetailsTabs = (clickedTab) => {\n $('.js-detailsPopup-tabContent, .js-detailsPopup-tabLink').removeClass('cc-currentTab');\n $(\n '.js-detailsPopup-tabContent#' +\n clickedTab +\n ', .js-detailsPopup-tabLink[data-tab=' +\n clickedTab +\n ']'\n ).addClass('cc-currentTab');\n};\n\nconst openQuickView = (url, modalClass) => {\n const modal = newModal(false, ['quickview-modal']);\n $.ajax({\n url: url,\n method: 'GET',\n dataType: 'json',\n success: (html) => {\n modal.setContent(html.renderedTemplate);\n if (Foundation.MediaQuery.atLeast('large')) {\n $('.product-quickview .carousel-inner').slick({\n arrows: true,\n dots: false,\n slidesToShow: 1,\n });\n }\n\n // QuickView\n $('.product-quickview .js-carousel-select-color-quickview')\n .slick({\n slidesToShow: 6,\n slidesToScroll: 2,\n infinite: false,\n responsive: [\n {\n breakpoint: 769,\n settings: {\n slidesToShow: 10,\n slidesToScroll: 2,\n },\n },\n {\n breakpoint: 640,\n settings: {\n slidesToShow: 6,\n slidesToScroll: 2,\n },\n },\n ],\n })\n .slick('setPosition');\n\n $('body').trigger('product:crossSellLoaded', true);\n\n $('.product-quickview .js-carousel-select-size')\n .slick({\n slidesToShow: 1.2,\n slidesToScroll: 1,\n infinite: false,\n })\n .slick('setPosition');\n\n if (modalClass) {\n $(modal.modalBox).find('.product-quickview').addClass(modalClass);\n }\n\n modal.open();\n $(modal.modalBox)\n .find('.close-custom')\n .on('click', function (e) {\n modal.close();\n modal.destroy();\n });\n $('body').on('product:afterAddToCart', function (data) {\n modal.close();\n modal.destroy();\n });\n },\n error: (err) => {\n console.log('Error:', err);\n },\n });\n};\n\nconst setMinHeightPromoPanel = (container) => {\n var _array = [];\n $(container)\n .find('div.promo-message.js-promo-container')\n .each(function () {\n _array.push($(this).innerHeight());\n });\n var maxHeight = Math.max.apply(Math, _array);\n $(container)\n .find('div.promo-message.js-promo-container')\n .each(function () {\n $(this).css('min-height', maxHeight);\n });\n\n var _array2 = [];\n $(container)\n .find('.product-tile__name')\n .each(function () {\n _array2.push($(this).innerHeight());\n });\n var maxHeightTitle = Math.max.apply(Math, _array2);\n $(container)\n .find('.product-tile__name')\n .each(function () {\n $(this).css('min-height', maxHeightTitle);\n });\n};\n\nconst getProductVariationGroup = (product, type) => {\n if (typeof product === 'string') {\n return product.trim();\n }\n\n if (type === 'size') {\n return product.id;\n }\n\n // size and color have already been selected. In this case, the variation\n // group is built with the style of the product, 'color' and the selected\n // color variation\n let pid = '';\n if (product.productType === 'variant') {\n pid = product.id.split(' ')[0].trim();\n } else if (product.productType === 'variationGroup') {\n // in this case the user only chose the color, and not the size\n pid = product.id.split('_')[0].trim();\n }\n let selectedVariation;\n\n for (let k in product.variationAttributes) {\n const variationAttribute = product.variationAttributes[k];\n if (variationAttribute.attributeId === 'color') {\n for (let j in variationAttribute.values) {\n if (variationAttribute.values[j].selected === true) {\n selectedVariation = variationAttribute.values[j].value;\n break;\n }\n }\n }\n // If a size is selected and selectable, retrieve its recommendation instead of variant color's one\n if (variationAttribute.attributeId === 'size') {\n for (let j in variationAttribute.values) {\n if (\n variationAttribute.values[j].selected === true &&\n variationAttribute.values[j].selectable === true\n ) {\n return product.id;\n }\n }\n }\n }\n\n return pid + '_color_' + selectedVariation;\n};\n\nconst crossSellItems = (product, type) => {\n if (!document.getElementById('crossSellItemsBaseUrl')) {\n return;\n }\n const pid = getProductVariationGroup(product, type);\n let requestUrl = document.getElementById('crossSellItemsBaseUrl').value;\n let isSizeChange = type === 'size';\n const promotionId = $('.marketing-messages.pdp .marketing-budge').data('promotion-id');\n $.ajax({\n url: requestUrl,\n method: 'GET',\n data: {\n pid: pid,\n promotionId: promotionId,\n },\n success: (data) => {\n const $result = $(data);\n\n const $completePromoData = $result.find('#completePromoProducts');\n const $completePromoSection = $('.js-completePromo');\n const $completePromoProducts = $completePromoSection.find('.crossSellContainer');\n $completePromoProducts.empty();\n if ($completePromoData.length) {\n $completePromoProducts.empty().append($completePromoData.html());\n $completePromoSection\n .find('.promo-budge-container')\n .empty()\n .append($('.marketing-messages.pdp .marketing-budge:first').text().trim());\n const $completePromoContainer = $result.find('#completePromoContainer');\n if ($completePromoContainer.length) {\n $completePromoSection\n .find('.js-completePromo-grid-info-description')\n .removeClass('hidden')\n .html($completePromoContainer.find('.js-promoDetails-description').html());\n $completePromoSection\n .find('.js-completePromo-grid-info-budge')\n .removeClass('hidden')\n .html($completePromoContainer.find('.js-promoDetails-calloutMsg').html());\n } else {\n $completePromoSection.find('.promo-more-info').addClass('hidden');\n }\n $completePromoSection.removeClass('hidden');\n checkCarouselLength('.js-promoCarousel');\n } else {\n $completePromoSection.addClass('hidden');\n }\n\n const $completeLookData = $result.find('#completeLookProducts');\n const $completeLookSection = $('.js-completeLook');\n const $completeLookProducts = $completeLookSection.find('.crossSellContainer');\n $completeLookProducts.empty();\n if ($completeLookData.length) {\n $completeLookProducts.empty().append($completeLookData.html());\n $completeLookSection.removeClass('hidden');\n checkCarouselLength('.js-lookCarousel');\n } else {\n $completeLookSection.addClass('hidden');\n }\n\n if ($completePromoData.length && $completeLookData.length) {\n $('.recommended-products-pdp').addClass('hidden');\n } else {\n $('.recommended-products-pdp').removeClass('hidden');\n }\n\n $('body').on(\n 'click',\n '.js-completePromo .crossSellContainer .js-pdp-link, .js-completeLook .crossSellContainer .js-pdp-link',\n (evt) => {\n // Open QuickView only not mobile\n\n evt.preventDefault();\n const url = evt.currentTarget.dataset.quickview;\n // Completa il tuo look\n let modalClass;\n if ($(evt.currentTarget).closest('.js-completeLook').length) {\n modalClass = 'complete-look-quick-view';\n }\n openQuickView(url, modalClass);\n\n /*\n else {\n if ($(evt.currentTarget).closest('.product').find('.add-to-cart-quick-add').attr('data-size-available') !== 'true') {\n evt.preventDefault();\n evt.stopPropagation();\n $(evt.currentTarget).closest('.product').find('.product-detail-quick-add').find('.js-panel-opener-size-quick-add').trigger('click', { mustAdd: true });\n }\n }\n */\n }\n );\n\n $('.js-completeLook .product-detail-quick-add .add-to-cart-quick-add').on(\n 'click',\n (e) => {\n if (\n $(e.currentTarget).attr('data-size-available') !== 'true' &&\n Foundation.MediaQuery.is('large')\n ) {\n e.preventDefault();\n e.stopPropagation();\n $(e.currentTarget)\n .closest('.product-detail-quick-add')\n .find('.js-panel-opener-size-quick-add')\n .trigger('click', {mustAdd: true});\n } else if (!Foundation.MediaQuery.is('large')) {\n e.preventDefault();\n e.stopPropagation();\n openQuickView(\n $(e.currentTarget)\n .closest('.product')\n .find('.js-pdp-link')\n .data('quickview'),\n 'complete-look-quick-view'\n );\n }\n }\n );\n\n setTimeout(function () {\n setMinHeightPromoPanel('.js-completePromo');\n setMinHeightPromoPanel('.js-completeLook');\n }, 300);\n $('body').trigger('product:crossSellLoaded', isSizeChange);\n },\n error: () => {\n $.spinner().stop();\n $('body').trigger('product:crossSellError');\n },\n });\n};\n\nconst openCurtain = () => {\n $('.overlay-pdp-mobile').show();\n $('#esw-fab').addClass('ui-eswback');\n};\n\nconst closeCurtain = () => {\n $('.overlay-pdp-mobile').hide();\n $('#esw-fab').removeClass('ui-eswback');\n};\n\nfunction closeAllOpenMenus() {\n if (Foundation.MediaQuery.atLeast('medium')) {\n return;\n }\n // Close open menus\n $('.js-select-size-for-mobile').addClass('hidden').removeClass('open');\n $('.js-select-color-for-mobile').addClass('hidden').removeClass('open');\n $('.js-panel-opener-color').removeClass('on');\n $('.js-panel-opener-size').removeClass('on');\n closeCurtain();\n}\n\nfunction removeNulls(el) {\n var price = el.find('.analytics').data('price');\n if (\n !price ||\n price == null ||\n price === 'null' ||\n price === '' ||\n price === 0 ||\n price == '0.00'\n ) {\n el.css('display', 'none');\n return true;\n }\n return false;\n}\n\nconst updatePrimaryImagesSlide = () => {\n let height = $('.primary-images .slick-active').outerHeight();\n $('.primary-images .slick-list').outerHeight(height);\n $('#miniatureVerticalImg .slide').removeClass('active');\n let index = $('.primary-images .slick-active').data('index');\n $(`#miniatureVerticalImg .slide[data-index=\"${index}\"]`).addClass('active');\n};\n\nconst enableImageSlideHeightObservers = () => {\n let imgNode = $('.primary-images .slick-list .carousel-item:first-child img');\n if (imgNode.length) {\n let config = {attributes: true, childList: true, subtree: true};\n let callback = function (mutationsList, observer) {\n for (let index = 0; index < mutationsList.length; index++) {\n let mutation = mutationsList[index];\n if (\n mutation.type === 'attributes' &&\n mutation.attributeName === 'class' &&\n mutation.target.classList.contains('lazyloaded')\n ) {\n updatePrimaryImagesSlide();\n }\n }\n };\n let observer = new MutationObserver(callback);\n observer.observe(imgNode[0], config);\n }\n let slickNode = $('.primary-images .slick-track');\n if (slickNode.length) {\n let config = {attributes: true, childList: true, subtree: true};\n let callback = function (mutationsList, observer) {\n for (let index = 0; index < mutationsList.length; index++) {\n let mutation = mutationsList[index];\n if (mutation.type === 'attributes' && mutation.attributeName === 'style') {\n updatePrimaryImagesSlide();\n }\n }\n };\n let observer = new MutationObserver(callback);\n observer.observe(slickNode[0], config);\n }\n};\n\nconst destroyPrimaryImagesSlider = () => {\n if (\n Foundation.MediaQuery.is('medium') &&\n $('.product-detail-keeper').length &&\n !$('.product-quickview.product-detail').length &&\n $('.primary-images').hasClass('slick-initialized')\n ) {\n $('.primary-images')\n .off('afterChange', updatePrimaryImagesSlide)\n .off('init', enableImageSlideHeightObservers)\n .slick('unslick');\n }\n};\n\nconst initializePrimaryImagesSlider = () => {\n if (\n $('.product-detail-keeper').length &&\n !$('.product-quickview.product-detail').length &&\n !$('.primary-images').hasClass('slick-initialized')\n ) {\n $('.primary-images').slick({\n arrows: false,\n dots: true,\n infinite: false,\n draggable: true,\n slidesToShow: 1,\n slidesToScroll: 1,\n responsive: [\n {\n breakpoint: 1023,\n settings: {\n slidesToShow: 1.4,\n slidesToScroll: 1,\n },\n },\n {\n breakpoint: 765,\n settings: {\n slidesToShow: 1.07,\n slidesToScroll: 1,\n },\n },\n ],\n });\n }\n\n const disableAutoScroll = () => {\n $('.primary-images').slick('slickPause');\n $('body').off('touchstart', this);\n };\n $('body').on('touchstart', disableAutoScroll);\n};\n\nconst updatePrimaryImagesSlider = (primaryImages) => {\n if (\n Foundation.MediaQuery.is('medium') &&\n $('.product-detail-keeper').length &&\n !$('.product-quickview.product-detail').length\n ) {\n initializePrimaryImagesSlider();\n let carouselItems = $('.primary-images .carousel-item');\n if (carouselItems.length) {\n for (let i = primaryImages.length; i < carouselItems.length; i++) {\n $('.primary-images').slick('slickRemove', primaryImages.length);\n }\n }\n }\n};\n\nclass Product {\n run() {\n ProductHelpers.run();\n // this.updateAttributesAndDetails();\n this.showSpinner();\n this.updateAttribute();\n this.updateAddToCart();\n this.updateAvailability();\n // this.sizeChart();\n this.getCrossSellItems();\n this.afterUpdateImages();\n this.recentlyViewedItems();\n this.buyNowQuichview();\n this.suggedtedProductsPDP();\n this.observeCurtainTap();\n this.removeNullCrossSell();\n this.pdpCrossSell();\n this.handleAccordionsInPDP();\n this.changeAddToBagButton();\n initializePrimaryImagesSlider();\n }\n\n changeAddToBagButton() {\n $('body').on('click', '.js-add-to-cart', function (e) {\n var button = $(this);\n\n $('body').on('product:afterAddToCart', function () {\n button.addClass('clicked');\n setTimeout(() => {\n button.removeClass('clicked');\n }, 3000);\n });\n });\n }\n\n removeNullCrossSell() {\n $('body').on('product:crossSellLoaded', function (e) {\n let $container = $('.js-completePromo .crossSellContainer');\n let index = 0;\n let items = $container.find('.js-cross-product').length;\n $container.find('.js-cross-product').each(function () {\n if (removeNulls($(this))) {\n index++;\n }\n });\n if (index == items) {\n $('.js-completePromo').addClass('hidden');\n }\n\n $container = $('.js-completeLook .crossSellContainer');\n index = 0;\n items = $container.find('.js-cross-product').length;\n $container.find('.js-cross-product').each(function () {\n if (removeNulls($(this))) {\n index++;\n }\n });\n if (index == items) {\n $('.js-completeLook').addClass('hidden');\n }\n });\n $('body').on(\n 'listing:einsteinloadedSuggestedProducts listing:einsteinloaded',\n function (e) {\n let $container = $('.js-em__carouselCustom');\n let index = 0;\n $container.find('.cc-emCarouselEditProd__item').each(function () {\n if (removeNulls($(this))) {\n index++;\n }\n });\n if (index > 0) {\n localStorage.setItem('suggestedProductsWithNullPrice', index);\n }\n setMinHeightPromoPanel('.recommended-products-pdp');\n }\n );\n $('body').on('listing:einsteinloadedSuggestedProducts', function (e) {\n let $container = $('.js-em__carouselCustom');\n let index = 0;\n $container.find('.cc-emCarouselEditProd__item').each(function () {\n if (removeNulls($(this))) {\n index++;\n }\n });\n if (index > 0) {\n localStorage.setItem('suggestedProductsWithNullPrice', index);\n }\n setMinHeightPromoPanel('.recommended-products-pdp');\n });\n if ($('.suggested-products-slider.slick-initialized').length) {\n $('body').trigger('listing:einsteinloadedSuggestedProducts', {\n container: '.suggested-products-slider',\n type: 'suggested-products',\n });\n }\n }\n\n observeCurtainTap() {\n $('.overlay-pdp-mobile').on('click', function (e) {\n if ($(this).css('display') !== 'none' && !Foundation.MediaQuery.atLeast('medium')) {\n closeAllOpenMenus();\n }\n });\n }\n\n recentlyViewedItems() {\n $('body').on('click', '.recentlyviewed .js-pdp-link', (evt) => {\n if (Foundation.MediaQuery.is('medium')) {\n evt.preventDefault();\n const url = evt.currentTarget.dataset.quickview;\n openQuickView(url);\n\n // trigger for analytics product detail event\n const target = $(evt.currentTarget).closest('.product');\n if (target.length > 0) {\n $('body').trigger('product:analyticsProductDetails', target);\n }\n }\n });\n }\n\n buyNowQuichview() {\n $('body').on('click', 'button.add-to-cart-quick-view', (e) => {\n e.preventDefault();\n openQuickView($(e.currentTarget).data('url'));\n });\n }\n\n suggedtedProductsPDP() {\n $('body').on('click', '.pdp-recommendations .js-pdp-link', (e) => {\n const $buyNowCta = $(e.currentTarget)\n .closest('.product')\n .find('.add-to-cart-quick-view');\n if ($buyNowCta.length) {\n e.preventDefault();\n e.stopPropagation();\n $buyNowCta.trigger('click');\n }\n });\n }\n\n getCrossSellItems() {\n $('body').on('product:afterAttributeSelect', (e, data) => {\n if (data.container.hasClass('product-quickview')) {\n return;\n }\n if (data.type === 'color' || data.type === 'size') {\n crossSellItems(data.data.product, data.type);\n }\n });\n }\n\n afterUpdateImages() {\n $('body').on('product:afterAttributeSelect', (e) => {\n computeCurrentlyVisibleImage(e);\n });\n }\n\n showSpinner() {\n $('body').on('product:beforeAddToCart product:beforeAttributeSelect', () => {\n $.spinner().start();\n });\n }\n\n updateAttribute() {\n $('body').on('product:afterAttributeSelect', (e, response) => {\n if ($('.product-detail>.bundle-items').length) {\n response.container.data('pid', response.data.product.id);\n response.container.find('.product-id').text(response.data.product.id);\n } else if ($('.product-set-detail').eq(0)) {\n response.container.data('pid', response.data.product.id);\n response.container.find('.product-id').text(response.data.product.id);\n } else {\n $('.product-id').text(response.data.product.id);\n $('.product-detail:not(\".bundle-item\")').data('pid', response.data.product.id);\n }\n });\n }\n\n updateAddToCart() {\n $('body').on('product:updateAddToCart', function (e, response) {\n if (\n $('.page').data('action') === 'Product-Show' &&\n !response.product.comingSoon &&\n !response.product.availability.orderable &&\n !response.product.availability.available\n ) {\n $('button.js-add-to-cart', '#fis-select-size').prop('disabled', true);\n $('button.js-add-to-cart', '#fis-select-size').data('disabled', true);\n return;\n }\n $('button.js-add-to-cart, button.add-to-cart-global').prop(\n 'disabled',\n !response.product.available || response.product.comingSoon\n );\n $('button.js-add-to-cart, button.add-to-cart-global').data(\n 'disabled',\n !response.product.readyToOrder\n );\n });\n }\n\n pdpCrossSell() {\n $('.js-shopTheLook-button').on('click', (e) => {\n e.preventDefault();\n e.stopPropagation();\n let htmlContent = $('.pdp-buy-look-container').html();\n const modal = newModalFromString(htmlContent, false, [\n 'cc-pdpCrossSell',\n 'js-pdpCrossSell',\n ]);\n $(modal.modalBox).addClass(\n 'rightModalAttribute cc-pdpCrossSell-modalBox rightModalAttribute_sizeLarge'\n );\n modal.open();\n initProductTile();\n\n $(modal.modalBox).on('click', '.js-pdpCrossSell-close', (e) => {\n e.preventDefault();\n modal.close();\n modal.destroy();\n });\n $(modal.modalBox).on('click', '.color-variation', (e) => {\n e.preventDefault();\n modal.close();\n modal.destroy();\n });\n\n $('body').trigger('product:buyLookBtnAnalytics', true);\n });\n\n $('.pdp-buy-look-container').on('click', (e) => {\n e.preventDefault();\n e.stopPropagation();\n $('.js-shopTheLook-button').removeClass('hidden');\n $('.embedded-service').removeClass('hide-for-STL');\n $('.img-wrapper .cell.hide-for-large > .icon-container').css('opacity', '1');\n $('.pdp-buy-look-container').addClass('hidden');\n });\n\n $('.pdp-buy-look-container').on('click', '.cross-sell-item', (e) => {\n e.preventDefault();\n e.stopPropagation();\n openQuickView($(e.currentTarget).data('url'));\n });\n\n $('body').on('product:afterAttributeSelect', (e, d) => {\n if (d.type !== 'color' || d.container.hasClass('product-quickview')) {\n return;\n }\n $('.js-shopTheLook-button').addClass('hidden');\n $('.pdp-buy-look-container').addClass('hidden');\n var pdpCrossSell = d.data.product.pdpCrossSell;\n if (!pdpCrossSell) {\n return;\n }\n\n $('.cross-sell-item').addClass('hidden');\n pdpCrossSell.forEach((cs, i) => {\n const $csItem = $(`.cross-sell-item[data-index=\"${i}\"]`);\n $csItem.data('url', cs.url);\n $csItem.find('.image').attr('src', cs.image);\n $csItem.find('.name').text(cs.name);\n $csItem.removeClass('hidden');\n });\n $('.js-shopTheLook-button').removeClass('hidden');\n });\n }\n\n updateAvailability() {}\n\n handleAccordionsInPDP() {\n if ($('.js-intProductDetail-details').length > 0) {\n if (!Foundation.MediaQuery.atLeast('large')) {\n /* Shipping accordion */\n if ($('.js-details-accordion_shipping').length > 0) {\n var $detailsAccordionShipping = $('.js-details-accordion_shipping');\n $('.js-details-shipping-content', $detailsAccordionShipping)\n .removeClass('accordion-content-visible')\n .addClass('accordion-content');\n $('.js-details-title', $detailsAccordionShipping).addClass('accordion-title');\n }\n /* Description accordion */\n if ($('.js-details-accordion_description').length > 0) {\n var $detailsAccordionDescription = $('.js-details-accordion_description');\n $('.js-details-description-content', $detailsAccordionDescription)\n .removeClass('accordion-content-visible')\n .addClass('accordion-content');\n $('.js-details-title', $detailsAccordionDescription).addClass(\n 'accordion-title'\n );\n }\n } else {\n $('.js-accordionDetails')\n .removeClass('accordion-title')\n .on('click', function (e) {\n const htmlContent = $('.js-detailsPopup').html();\n const modal = newModalFromString(htmlContent, false, ['cc-detailsPopup']);\n $(modal.modalBox).addClass(\n 'rightModalAttribute cc-detailsPopup-modalBox rightModalAttribute_sizeMedium'\n );\n\n handleDetailsTabs($(e.currentTarget).data('tab'));\n\n modal.open();\n\n if ($('.pdp-size-box').hasClass('size-selected')) {\n $('#main-and-care-label').addClass('hidden');\n }\n\n $('.js-detailsPopup-tabLink').on('click', function (e) {\n handleDetailsTabs($(e.currentTarget).data('tab'));\n });\n\n $(modal.modalBox)\n .find('.js-detailsPopup-close')\n .on('click', function () {\n $(modal.modalBox)\n .addClass('cc-modalClosing')\n .on(\n 'transitionend webkitTransitionEnd oTransitionEnd MSTransitionEnd',\n function () {\n modal.close();\n }\n );\n });\n });\n }\n }\n }\n}\n\nconst product = new Product();\nexport default product;\nexport {\n crossSellItems,\n computeCurrentlyVisibleImage,\n activatePromoAnimationMessage,\n closeAllOpenMenus,\n initializePrimaryImagesSlider,\n updatePrimaryImagesSlider,\n destroyPrimaryImagesSlider,\n};\n","/**\n * Core SFRA function for run everything everywhere\n * @param {Function || Object} include - stuff to run\n */\nconst processInclude = include => {\n if (typeof include === 'function') {\n include();\n } else if (typeof include === 'object') {\n Object.keys(include).forEach(function (key) {\n if (typeof include[key] === 'function') {\n include[key]();\n }\n });\n }\n};\n\n// Enqueues tasks to be executed afterwards\nfunction enqueueTask (task) {\n window.requestAnimationFrame(task);\n}\n\n/**\n * Parses the html for a modal window\n * @param {string} html - representing the body and footer of the modal window\n *\n * @return {Object} - Object with properties body and footer.\n */\nconst parseHtml = (html, map) => {\n const el = document.createElement('div');\n el.innerHTML = html;\n\n let htmlMap = {};\n for (var key in map) {\n if (map.hasOwnProperty(key)) {\n htmlMap[key] = el.querySelector(map[key]);\n }\n }\n\n return htmlMap;\n};\n\n/**\n * appends params to a url\n * @param {string} url - Original url\n * @param {Object} params - Parameters to append\n * @returns {string} result url with appended parameters\n */\nconst appendToUrl = (url, params) => {\n var newUrl = url;\n newUrl += (newUrl.indexOf('?') !== -1 ? '&' : '?') + Object.keys(params).map(function (key) {\n return key + '=' + encodeURIComponent(params[key]);\n }).join('&');\n\n return newUrl;\n};\n\nconst lockScroll = () => {\n $('body, html').css('overflow-y', 'hidden');\n $('body, html').css('position', 'fixed'); // iOS issue\n};\n\nconst unlockScroll = () => {\n $('body, html').css('overflow-y', '');\n $('body, html').css('position', ''); // iOS issue\n};\n\nconst cookieExists = (name) => {\n return document.cookie.split(';').filter((item) => {\n return item.trim().indexOf(`${name}=`) === 0;\n }).length;\n};\n\nconst createCookie = (name, value = false, days = 0) => {\n var expires;\n if (days) {\n var date = new Date();\n date.setTime(date.getTime() + (days * 24 * 60 * 60 * 1000));\n expires = '; expires=' + date.toGMTString();\n } else {\n expires = '';\n }\n document.cookie = name + '=' + value + expires + '; path=/';\n};\n\nexport {\n appendToUrl,\n cookieExists,\n createCookie,\n enqueueTask,\n processInclude,\n parseHtml,\n lockScroll,\n unlockScroll\n};\n","'use strict';\nimport {\n newModalFromString,\n newModalFromSelector\n} from '../components/modal';\nimport ProductHelpers from './base';\nimport sizePanel from './sizePanel';\n\nclass SmartGiftHelper {\n constructor () {\n this.basketBeforeRemovedProduct = [];\n this.basketObserverEnabled = false;\n this.basketAlreadyFetched = false;\n }\n\n run () {\n $('body').on('click', '.js-smart-gift', (e) => {\n let pid = ProductHelpers.methods.getPidValue($(e.currentTarget));\n if (!ProductHelpers.isSizeSelected()) {\n sizePanel.openSizePanel(sizePanel.Types.SMARTGIFT);\n } else {\n this.addSmartGift(pid);\n this.enableAnalyticsBasketObserver();\n }\n });\n\n let analyticsDataButton = {\n action: '',\n skus: '',\n quantity: ''\n };\n let basketButtonsSelector = '.sidebar-widget .sidebar-continue-shopping-button,';\n basketButtonsSelector += '.sidebar-widget .widget-summary-button';\n $('body').on('click', basketButtonsSelector, (event) => {\n if (SGBasket) {\n if ($(event.currentTarget).hasClass('sidebar-continue-shopping-button')) {\n analyticsDataButton.action = 'continue_shopping';\n } else if ($(event.currentTarget).hasClass('widget-summary-button')) {\n analyticsDataButton.action = 'prepare_my_gift';\n }\n analyticsDataButton.skus = this.getSkus();\n analyticsDataButton.quantity = this.getSkusQuantity();\n $('body').trigger('analytics:smartGiftBasketButtons', analyticsDataButton);\n }\n });\n\n $('body').on('click', '.sidebar-widget .SGBasketButton', () => {\n if (SGBasket) {\n $('body').trigger('analytics:smartGiftBasketIcon');\n }\n });\n\n $('body').on('click', '.smart-gift-rules-label, .js-smart-gift-rules', () => {\n $('body').trigger('analytics:smartGiftMoreInfo');\n });\n };\n\n addRecommendedItems(data){\n var eachSuggestion = $('.box-complete-yourlook .product');\n let dataSuggestion = [];\n var suggestionLength = eachSuggestion.length > 3 ? 3 : eachSuggestion.length;\n for (var i = 0; i < suggestionLength; i++){\n let suggestionItem = {};\n let infoSuggestion = eachSuggestion[i].querySelector('.productListingItem');\n let imgSuggestion = eachSuggestion[i].querySelector('.tile-image');\n let hrefSuggestion = eachSuggestion[i].querySelector('.product-tile');\n suggestionItem.skuCode = eachSuggestion[i].dataset.pid.replace('~', '/');\n suggestionItem.name = imgSuggestion.title;\n suggestionItem.price = infoSuggestion.dataset.price;\n suggestionItem.skuUrl = hrefSuggestion.href;\n suggestionItem.image = imgSuggestion.src || imgSuggestion.dataset.src;\n dataSuggestion.push(suggestionItem);\n }\n data.recommendedItems = dataSuggestion;\n };\n\n addSmartGift(pid){\n let data = {};\n data.skuCode = pid.replace('~', '/');\n data.name = $('h1[itemprop=\"name\"]').text();\n data.price = $('.product.analytics').data('price');\n data.skuUrl = window.location.href;\n data.image = $('.still-life-img').data('still-life');\n let nameEng = $('.product.analytics').data('name');\n data.nameEng = nameEng;\n\n this.addRecommendedItems(data);\n\n SGBasket.addItem(data);\n console.log(data);\n $('body').trigger('analytics:addSmartGift', { sku: data.skuCode, name: nameEng });\n };\n\n getSkus () {\n let skus = [];\n SGBasket.state.basket.forEach((element) => {\n skus.push(element.skuCode);\n });\n return skus;\n };\n\n getSkusQuantity () {\n return SGBasket.state.basket.length;\n };\n\n getBasket () {\n let basket = [];\n if (SGBasket) {\n SGBasket.state.basket.forEach((element) => {\n basket.push(element);\n });\n return basket;\n }\n };\n\n setAnalyticsProductIndex () {\n $('.product-list .sc-bxivhb .product-item-text-rmv').each(function (index) {\n $(this).attr('data-analytics-product-index', index);\n });\n };\n\n triggerRemoveProduct (removedProduct) {\n let productUrl = $('.product-detail.product-wrapper').data('variationInfo').replace('PID_PLACEHOLDER', removedProduct.skuCode);\n let nameEng = '';\n $.get({\n url: productUrl,\n success: data => {\n if (data.product && data.product.nameEng) {\n nameEng = data.product.nameEng;\n }\n $('body').trigger('analytics:smartGiftBasketRemoveProduct', {productName: nameEng, sku: removedProduct.skuCode});\n },\n error: function () {\n $.spinner().stop();\n }\n });\n };\n\n enableAnalyticsBasketObserver() {\n if (SGBasket && !this.basketObserverEnabled) {\n this.basketObserverEnabled = true;\n let targetWidgetNode = $('.SGBasket-widget')[0];\n if (targetWidgetNode) {\n let config = { attributes: true, childList: true, subtree: true };\n let _self = this;\n let callback = function (mutationsList, observer) {\n for (let index = 0; index < mutationsList.length; index++) {\n let mutation = mutationsList[index];\n if (mutation.type === 'attributes' &&\n mutation.target.nodeName === 'DIV' &&\n $(mutation.target).hasClass('showOverview') &&\n $(mutation.target).hasClass('show') &&\n !_self.basketAlreadyFetched) {\n _self.basketAlreadyFetched = true;\n _self.setAnalyticsProductIndex();\n _self.basketBeforeRemovedProduct = _self.getBasket();\n const clickedProduct = function (event) {\n event.stopImmediatePropagation();\n let productIndex = $(this).data('analyticsProductIndex');\n let removedProduct = _self.basketBeforeRemovedProduct.splice(productIndex, 1)[0];\n _self.triggerRemoveProduct(removedProduct);\n };\n $('.product-list .product-item-text-rmv').on('click', clickedProduct);\n } else if (mutation.type === 'attributes' &&\n mutation.target.nodeName === 'DIV' &&\n $(mutation.target).hasClass('showOverview') &&\n $(mutation.target).hasClass('hide')) {\n _self.basketAlreadyFetched = false;\n }\n }\n };\n let observer = new MutationObserver(callback);\n observer.observe(targetWidgetNode, config);\n }\n }\n };\n}\n\nconst smartGiftHelper = new SmartGiftHelper();\nexport default smartGiftHelper;\n","'use strict';\n\n/**\n * Replace the URL query string color during color selection update in PDP.\n * @param {string} needle parameter to detect the key, e.g. \"_COL_\", \"_COLORI_\", etc.\n * @param {string} color new color to be submitted\n */\nconst updateProductDetailUrl = (needle, color) => {\n // Build url object\n var urlObject = new URL(window.location.href);\n var queryString = urlObject.searchParams;\n\n // Retrieve exact key name to be replaced\n var qsKeyToUpdate;\n for (var qsKey of queryString.keys()) {\n var qsValue = queryString.get(qsKey);\n if (qsKey.toLowerCase().indexOf(needle) !== -1 && qsValue) {\n qsKeyToUpdate = qsKey;\n break;\n }\n }\n\n // Cancel action if key is not found\n if (!qsKeyToUpdate) {\n return;\n }\n\n // Push new value to querystring key obtained above\n urlObject.searchParams.set(qsKeyToUpdate, color);\n // Replace current URL with new\n window.history.replaceState(null, document.title, urlObject.href);\n};\n\nexport {\n updateProductDetailUrl\n};\n","/**\n * Renders the template within the given environment\n * @param {string} tmpl The template to render\n * @param {Object.} environment The environment to evaluate the expressions in\n */\nfunction renderTemplate (tmpl, environment) {\n return tmpl.replace(/\\{([a-z0-9]+)\\}/gi, function (_completeMatch, varName) {\n if (environment[varName]) {\n return environment[varName];\n } else {\n return '';\n }\n });\n}\n\n/**\n * Renders the template within the given environment\n * @param {string} id The ID of the HTML element containing the template to render\n * @param {Object.} environment The environment to evaluate the expressions in\n */\nfunction applyRendering (id, environment) {\n return renderTemplate(document.getElementById(id).innerHTML, environment);\n}\n\nexport {\n applyRendering\n};\n","'use strict';\n\n/* globals grecaptcha */\n\nvar processBalanceAjaxCall = function (ajaxUrl, giftCardType, giftCardNumber, giftCardPin, captcha, target) {\n var gcType;\n if (giftCardType === 'Physical') {\n gcType = 'card';\n } else if (giftCardType === 'Electronic') {\n gcType = 'electronic';\n }\n if (target) {\n let inModal = $(target).parents('.tingle-modal').length > 0;\n if (inModal) {\n captcha = $(target).parents('.tingle-modal').find('[name=\"g-recaptcha-response\"]')[0].value;\n } else {\n captcha = $(target).parents('.gift-card-number').find('[name=\"g-recaptcha-response\"]')[0].value;\n }\n } else {\n if (document.querySelector('#g-recaptcha-response') != null) {\n captcha = document.querySelector('#g-recaptcha-response').value;\n }\n }\n if (!captcha && captcha != null) {\n $('.no-robot').removeClass('hidden');\n $.spinner().stop();\n return;\n }\n\n $.ajax({\n url: ajaxUrl,\n method: 'POST',\n dataType: 'json',\n data: {\n giftCardType: giftCardType,\n giftCardNumber: giftCardNumber,\n giftCardPin: giftCardPin,\n captcha: captcha || ''\n },\n success: responseData => {\n $('.giftcard-checkbalance-error').addClass('hidden');\n $('.resocard-checkbalance-balance-error').addClass('hidden');\n $('.giftcard-checkbalance-balance-error').addClass('hidden');\n $('.giftcard-checkbalance-error-expired').addClass('hidden');\n $('.giftcard-checkbalance-success').addClass('hidden');\n $('.resocard-checkbalance-success').addClass('hidden');\n $('.resocard-checkbalance-error').addClass('hidden');\n $('.resocard-checkbalance-error-expired').addClass('hidden');\n $('.wrapper-content-slot').removeClass('hiddenGiftCard');\n $('body').trigger('einsteinGiftCardRecommendation');\n\n if (responseData.amount === 0) {\n $('.giftcard-checkbalance-success').addClass('hidden');\n $('.resocard-checkbalance-success').addClass('hidden');\n $('.giftcard-checkbalance-balance-error').removeClass('hidden');\n\n return;\n }\n\n if (!responseData.success) {\n if (responseData.isResocard) {\n if (responseData.isExpired) {\n // Display error expired reso card\n $('.resocard-checkbalance-error-expired').removeClass('hidden');\n } else {\n $('.resocard-checkbalance-error').removeClass('hidden');\n }\n } else {\n if (responseData.isExpired) {\n // Display error gift card expired\n $('.giftcard-checkbalance-error-expired').removeClass('hidden');\n } else {\n // Display not enough balance error\n $('.giftcard-checkbalance-error').removeClass('hidden');\n }\n }\n } else {\n $('body').trigger('checkout:giftcardCheckBalance', { 'gcCode': giftCardNumber, 'gcType': gcType });\n // Display success message\n if (responseData.isResocard) {\n $('.resocard-checkbalance-success').removeClass('hidden');\n $('.resocard-checkbalance-balance').removeClass('hidden');\n $('.resocard-checkbalance-balance').text(`${responseData.currency} ${responseData.amount}`);\n $('.resocard-checkbalance-expired').text(`${responseData.expiryDate}`);\n $('.js-check-balance').addClass('hidden');\n $('.js-check-yourbalance-button').addClass('hidden');\n } else {\n $('.giftcard-checkbalance-success').removeClass('hidden');\n $('.giftcard-checkbalance-balance').removeClass('hidden');\n $('.giftcard-checkbalance-balance').text(`${responseData.currency} ${responseData.amount}`);\n $('.giftcard-checkbalance-expired').text(`${responseData.expiryDate}`);\n $('.js-check-balance').addClass('hidden');\n $('.js-check-yourbalance-button').addClass('hidden');\n }\n if (responseData.firstName) {\n $('.js-giftcardNameToStamp').text('' + responseData.firstName);\n } else {\n $('.js-giftcardNameToStamp').text('');\n }\n }\n },\n error: () => {\n // Display error with not enough balance\n $('.resocard-checkbalance-balance-error').addClass('hidden');\n $('.giftcard-checkbalance-balance-error').addClass('hidden');\n $('.resocard-checkbalance-success').addClass('hidden');\n $('.resocard-checkbalance-error').addClass('hidden');\n $('.resocard-checkbalance-error-expired').addClass('hidden');\n $('.giftcard-checkbalance-error').removeClass('hidden');\n $('.giftcard-checkbalance-error-expired').addClass('hidden');\n $('.giftcard-checkbalance-success').addClass('hidden');\n $('#giftCardPane input[type=\"text\"]').removeClass('valid-data');\n },\n complete: () => {\n $.spinner().stop();\n try {\n grecaptcha.reset();\n } catch (e) {\n console.error(e);\n }\n }\n });\n};\n\n// Disabled CTA if inputs are empty\nconst checkGiftCardInputFields = () => {\n var isGiftCardCodeEmpty = !$('.input-code').val();\n var isGiftCardPinEmpty = $('.input-pin').is(':visible') && !$('.input-pin').val();\n $('.js-giftcard-check-balance').prop('disabled', isGiftCardCodeEmpty || isGiftCardPinEmpty);\n};\n\nconst processBalance = () => {\n $('body').trigger('einsteinGiftCardRecommendation');\n $.spinner().start();\n var giftCardType = $('form#form-gift-card input[type=\"radio\"]#card-fisica:checked').length > $('input[type=\"radio\"]#e-card:checked').length ? 'Physical' : 'Electronic';\n var giftCardNumber = $('form#form-gift-card input[name=\"inputCode\"]').val();\n var giftCardPin = $('form#form-gift-card input[name=\"inputPin\"]').val();\n var captcha = document.querySelector('#g-recaptcha-response').value;\n processBalanceAjaxCall($('form#form-gift-card').data('url'), giftCardType, giftCardNumber, giftCardPin, captcha);\n};\n\nmodule.exports = {\n retriveGiftCardBalanceFooter: function () {\n $('body').on('change', '[id=\"card-fisica\"]', () => {\n $('.wrapper-content-slot').addClass('hiddenGiftCard');\n $('.input-code').removeClass('is-invalid-input');\n $('#errorInputCode').addClass('hiddenErrorsGiftCard');\n $('.input-pin').removeClass('is-invalid-input');\n $('#errorInputPin').addClass('hiddenErrorsGiftCard');\n $('#e-card-label').removeClass('selected');\n $('#card-fisica-label').addClass('selected');\n grecaptcha.reset();\n });\n $('body').on('change', '[id=\"e-card\"]', () => {\n $('.wrapper-content-slot').addClass('hiddenGiftCard');\n $('.input-code').removeClass('is-invalid-input');\n $('#errorInputCode').addClass('hiddenErrorsGiftCard');\n $('.input-pin').removeClass('is-invalid-input');\n $('#errorInputPin').addClass('hiddenErrorsGiftCard');\n grecaptcha.reset();\n });\n\n $('body').on('input', '.input-code', function (e) {\n e.preventDefault();\n $('.input-code').removeClass('is-invalid-input');\n $('#errorInputCode').removeClass('hiddenErrorsGiftCard');\n });\n\n $('body').on('input', '.input-pin', function (e) {\n e.preventDefault();\n $('.input-pin').removeClass('is-invalid-input');\n $('#errorInputPin').addClass('hiddenErrorsGiftCard');\n });\n\n // Disabled CTA if inputs are empty on input\n $('body').on('input', '.input-code, .input-pin', checkGiftCardInputFields);\n // Disabled CTA if inputs are empty on type switch\n $('body').on('change', '[name=\"input-radio-1\"]', checkGiftCardInputFields);\n\n $('body').on('click', 'form#form-gift-card .button', function (e) {\n e.preventDefault();\n\n if ($('#card-fisica').is(':checked')) {\n if ($('.input-code').val() !== undefined && $('.input-code').val() !== '' && $('.input-pin').val() !== undefined && $('.input-pin').val() !== '') {\n processBalance();\n } else {\n if ($('.input-code').val() == undefined || $('.input-code').val() == '') {\n $('#errorInputCode').removeClass('hiddenErrorsGiftCard');\n $('.input-code').addClass('is-invalid-input');\n }\n if ($('.input-pin').val() == undefined || $('.input-pin').val() == '') {\n $('#errorInputPin').removeClass('hiddenErrorsGiftCard');\n $('.input-pin').addClass('is-invalid-input');\n }\n $('.wrapper-content-slot').addClass('hiddenGiftCard');\n }\n } else {\n if ($('.input-code').val() !== undefined && $('.input-code').val() !== '') {\n processBalance();\n } else {\n $('#errorInputCode').removeClass('hiddenErrorsGiftCard');\n $('.input-code').addClass('is-invalid-input');\n $('.wrapper-content-slot').addClass('hiddenGiftCard');\n }\n }\n });\n },\n retriveGiftCardBalance: function () {\n $('body').on('click', 'form.giftCardBalanceModalForm .js-check-balance', function () {\n var giftCardType = $('form.giftCardBalanceModalForm input[type=\"radio\"]#giftCardPhysical:checked').length > $('input[type=\"radio\"]#giftCardElectronic:checked').length ? 'Physical' : 'Electronic';\n var giftCardNumber = $('form.giftCardBalanceModalForm #giftCardNumber').val();\n var giftCardPin = $('form.giftCardBalanceModalForm #giftCardPin').val();\n $('#giftCardFormGroup #giftCardNumber').val(giftCardNumber);\n $('#giftCardFormGroup #giftCardPin').val(giftCardPin);\n if (giftCardType === 'Physical') {\n if ($('#giftCardPane input[type=\"radio\"]#giftCardElectronic:checked').length) {\n $('##giftCardPane input[type=\"radio\"]#giftCardPhysical').trigger('click');\n }\n } else {\n if ($('#giftCardPane input[type=\"radio\"]#giftCardPhysical:checked').length) {\n $('#giftCardPane input[type=\"radio\"]#giftCardElectronic').trigger('click');\n }\n }\n\n processBalanceAjaxCall($('form.giftCardBalanceModalForm').data('url'), giftCardType, giftCardNumber, giftCardPin, undefined, $(this));\n });\n },\n\n applyGiftcard: function () {\n $('body').on('click', '.apply-giftcard', function (e) {\n var captcha;\n let target = $(this);\n if (target) {\n let inModal = $(target).parents('.tingle-modal').length > 0;\n if (inModal) {\n captcha = $(target).parents('.tingle-modal').find('[name=\"g-recaptcha-response\"]')[0].value;\n } else {\n captcha = $(target).parents('.gift-card-number').find('[name=\"g-recaptcha-response\"]')[0].value;\n }\n } else {\n if (document.querySelector('#g-recaptcha-response') != null) {\n captcha = document.querySelector('#g-recaptcha-response').value;\n }\n }\n\n if (!captcha && !$(e.target).hasClass('remove-applied-giftcard')) {\n $('.no-robot').removeClass('hidden');\n return;\n }\n var giftCardType = $('input[type=\"radio\"]#giftCardPhysical:checked').length > $('input[type=\"radio\"]#giftCardElectronic:checked').length ? 'Physical' : 'Electronic';\n var giftCardNumber = $('#giftCardNumber').val();\n var giftCardPin = $('#giftCardPin').val();\n\n $.ajax({\n url: $('#giftCardFormGroup').data('url'),\n method: 'POST',\n dataType: 'json',\n data: {\n giftCardType: giftCardType,\n giftCardNumber: giftCardNumber,\n giftCardPin: giftCardPin\n },\n success: responseData => {\n $('.giftcard-amount-feedback').removeClass('hidden');\n $('.giftcard-amount-feedback').removeClass('error');\n $('.gift-card-error').addClass('hidden');\n if (!responseData.success) {\n $('.giftcard-amount-feedback').addClass('error');\n $('.gift-card-error').removeClass('hidden').text(responseData.message);\n $('.giftcard-applied').addClass('hidden');\n $('.giftCardRemainedAmount').addClass('hidden').text('');\n $('.giftcard-applied').removeClass('multipaymentToSelect');\n } else {\n $('body').trigger('checkout:applyGiftCard', {'gcCode': giftCardNumber, 'gcType': giftCardType.toLowerCase()});\n $('.giftcard-modal-block').addClass('hidden');\n $('.gift-card-error').addClass('hidden');\n $('.item-giftcard').removeClass('hidden');\n $('.giftcard-total').text(responseData.amountText);\n $('.giftcard-applied').removeClass('hidden').html(responseData.message);\n $('#giftCardFormGroup .buttonApplyGiftcard').addClass('hide');\n $('#giftCardFormGroup .buttonRemoveGiftcard').removeClass('hide');\n $('.giftCardNumberField, .giftCardPinField').addClass('giftcardSubmitted');\n $('.giftCardRemainedAmount').removeClass('hidden').html(responseData.messageRemainedAmount);\n if (responseData.coversTotalAmount) {\n $('#GIFT_CARD').click();\n $('.drawer input[name$=\"paymentMethod\"]:not(#GIFT_CARD, #RESO_CARD)').attr('disabled', true);\n $('.giftCardDrawer .giftcard-submit-payment').removeClass('hidden');\n $('.giftCardRemainedAmount').removeClass('giftcardMultiPaymentAmount');\n } else {\n $('.giftCardRemainedAmount').addClass('giftcardMultiPaymentAmount');\n $('.js-express-button').removeClass('disableExpressButton');\n $('.giftcard-applied').addClass('multipaymentToSelect');\n if ($('input#DW_APPLE_PAY:checked').length > 0 && $('#apple-pay-btn').length > 0) {\n $('.applepay-tab-header input').trigger('change');\n }\n }\n // For multipayment\n $('body').trigger('checkout:updateCheckoutView', {\n order: responseData.order,\n customer: responseData.customer,\n coversTotalAmount: responseData.coversTotalAmount,\n action: 'addGiftcard'\n });\n $('.tingle-modal .close').trigger('click');\n }\n },\n error: () => {\n $('.giftcard-modal-block').addClass('hidden');\n $('.giftcard-amount-feedback').addClass('error');\n $('.gift-card-error').removeClass('hidden');\n },\n complete: () => {\n $.spinner().stop();\n try {\n grecaptcha.reset();\n $('.no-robot').addClass('hidden');\n } catch (e) {\n console.error(e);\n }\n }\n });\n });\n },\n\n getGiftCardBalance: function () {\n $('#giftCardPane .buttonApplyGiftcard').on('click', function (e) {\n var captcha;\n if (document.querySelector('#g-recaptcha-response') != null) {\n captcha = document.querySelector('#g-recaptcha-response').value;\n }\n if (!captcha && !$(e.target).hasClass('remove-applied-giftcard')) {\n $('.no-robot').removeClass('hidden');\n return;\n }\n var giftCardType = $('input[type=\"radio\"]#giftCardPhysical:checked').length > $('input[type=\"radio\"]#giftCardElectronic:checked').length ? 'Physical' : 'Electronic';\n var giftCardNumber = $('#giftCardNumber').val();\n var giftCardPin = $('#giftCardPin').val();\n\n var gcType;\n if (giftCardType === 'Physical') {\n gcType = 'card';\n } else if (giftCardType === 'Electronic') {\n gcType = 'electronic';\n }\n\n // Reset coupon section state\n $('.card.coupon-code, .loyalty-coupons-container').removeClass('disabled');\n $('.checkout-applied-giftcard-message').addClass('hide');\n\n $.ajax({\n url: $('#giftCardFormGroup').data('url'),\n method: 'POST',\n dataType: 'json',\n data: {\n giftCardType: giftCardType,\n giftCardNumber: giftCardNumber,\n giftCardPin: giftCardPin\n },\n success: responseData => {\n $('.giftcard-amount-feedback').removeClass('hidden');\n $('.giftcard-amount-feedback').removeClass('error');\n $('.gift-card-error').addClass('hidden');\n $('#giftCardFormGroup .buttonRemoveGiftcard').removeClass('hide');\n if (!responseData.success) {\n $('.giftcard-amount-feedback').addClass('error');\n $('.gift-card-error').removeClass('hidden');\n $('.giftcard-applied').addClass('hidden');\n $('.giftCardRemainedAmount').addClass('hidden').text('');\n $('.giftcard-applied').removeClass('multipaymentToSelect');\n } else {\n $('body').trigger('checkout:applyGiftCard', {'gcCode': giftCardNumber, 'gcType': gcType});\n $('.giftcard-modal-block').addClass('hidden');\n if (responseData.isResocard) {\n $('.display-resocard').removeClass('hidden');\n } else {\n $('.display-giftcard').removeClass('hidden');\n }\n $('.gift-card-error').addClass('hidden');\n $('.item-giftcard').removeClass('hidden');\n $('.giftcard-applied').removeClass('hidden').html(responseData.message);\n $('.giftcard-total').text(responseData.amountText);\n $('#giftCardFormGroup .js-recaptcha').addClass('hide');\n $('#giftCardFormGroup .js-controlCardButtons').addClass('hide');\n $('.giftCardNumberField, .giftCardPinField').addClass('giftcardSubmitted');\n if (giftCardType === 'Electronic') {\n $('.green-check-mark').addClass('eCard');\n } else if (giftCardType === 'Physical') {\n $('.green-check-mark').addClass('physicalCard');\n }\n\n if (responseData.coversTotalAmount) {\n $('#GIFT_CARD').click();\n $('.drawer input[name$=\"paymentMethod\"]:not(#GIFT_CARD, #RESO_CARD)').attr('disabled', true);\n $('.giftCardDrawer .giftcard-submit-payment').removeClass('hidden');\n $('.giftCardRemainedAmount').removeClass('giftcardMultiPaymentAmount');\n } else {\n $('.giftCardRemainedAmount').addClass('giftcardMultiPaymentAmount');\n $('.js-express-button').removeClass('disableExpressButton');\n $('.giftcard-applied').addClass('multipaymentToSelect');\n if ($('input#DW_APPLE_PAY:checked').length > 0 && $('#apple-pay-btn').length > 0) {\n $('.applepay-tab-header input').trigger('change');\n }\n }\n $('.giftCardRemainedAmount').removeClass('hidden').html(responseData.messageRemainedAmount);\n\n // Disable coupon application (code and loyalty) when EGC is applied\n $('.card.coupon-code, .loyalty-coupons-container').addClass('disabled');\n $('.checkout-applied-giftcard-message').removeClass('hide');\n\n // For multipayment\n $('body').trigger('checkout:updateCheckoutView', {\n order: responseData.order,\n customer: responseData.customer,\n coversTotalAmount: responseData.coversTotalAmount,\n action: 'addGiftcard'\n });\n }\n },\n error: () => {\n $('.giftcard-modal-block').addClass('hidden');\n $('.gift-card-error').removeClass('hidden');\n $('.giftcard-amount-feedback').addClass('error');\n },\n complete: () => {\n $.spinner().stop();\n try {\n grecaptcha.reset();\n $('.no-robot').addClass('hidden');\n } catch (e) {\n console.error(e);\n }\n }\n });\n });\n },\n\n handleGiftcardInput: function () {\n $('body').on('input', '#giftCardFormGroup .giftCardNumberField,#giftCardFormGroup .giftCardPinField', function (e) {\n $('.giftcard-amount-feedback').addClass('hidden');\n $('.giftcard-amount-feedback').removeClass('error');\n $('.gift-card-error').addClass('hidden');\n });\n },\n checkingGiftCardType: function () {\n $('.gift-card-number').addClass('physicalCard');\n $('#giftCardPhysical').on('click', function () {\n $('.gift-card-number').addClass('physicalCard');\n $('.gift-card-number').removeClass('eCard');\n });\n $('#giftCardElectronic').on('click', function () {\n $('.gift-card-number').addClass('eCard');\n $('.gift-card-number').removeClass('physicalCard');\n });\n }\n};\n","'use strict';\n\nimport { processInclude } from 'util/common';\nimport { newModalFromString } from './components/modal';\nimport { applyRendering } from './util/render';\nimport GiftcardHelper from './giftcard/giftcardAddToCart';\nimport productHelpers from './product/base';\n\nconst formatDate = (date, formatPattern) => {\n if (formatPattern === 'dd-mm-yyyy') {\n return ('0' + date.getDate()).slice(-2) + '-' + ('0' + (date.getMonth() + 1)).slice(-2) + '-' + date.getFullYear();\n } else if (formatPattern === 'mm-dd-yyyy') {\n return ('0' + (date.getMonth() + 1)).slice(-2) + '-' + ('0' + date.getDate()).slice(-2) + '-' + date.getFullYear();\n } else if (formatPattern === 'yyyy年mm月dd日') {\n var dateParsed = (date.getFullYear() + '年' + ('0' + (date.getMonth() + 1)).slice(-2) + '月' + ('0' + date.getDate()).slice(-2) + '日');\n return dateParsed;\n }\n};\n\nclass GiftCard {\n init () {\n // Gift card selection variables\n this.selectedOccasion = null;\n this.selectedSwatchIndex = null;\n this.selectedColor = null;\n\n // Class variables\n this.occasionElement = '.js-occasion-tab';\n this.swatchesContainer = '.js-giftcard-slider-nav';\n this.carousel = '.js-giftcard-carousel';\n this.swatchesElement = '.js-giftcard-swatch';\n this.colorsSection = '.js-giftCardPage-colorSwatches';\n this.colorsContainer = '.js-giftcard-color-list';\n this.colorsElement = '.js-giftcard-select-color';\n this.colorName = '.js-giftcard-color-name';\n this.giftCardImage = '.js-giftcard-image';\n this.giftCardPriceBanner = '.js-giftCardPage-price-banner';\n this.amounts = '.js-giftcard-amount-option';\n this.manualAmount = '.js-giftcard-amount-manual';\n this.sliderConfig = {\n slidesToShow: 1,\n slidesToScroll: 1,\n centerMode: false,\n infinite: false,\n dots: false,\n focusOnSelect: true,\n accessibility: false,\n arrows: false,\n speed: 0\n };\n\n // Initialize selection of first elements\n var firstOccasionName = $(this.occasionElement).first().data('occasion');\n var firstSwatchIndex = 0;\n var firstColorId = $(`${this.colorsContainer}[data-occasion=\"${firstOccasionName}\"]`).find(this.colorsElement).first().data('color-id');\n this._selectOccasion(firstOccasionName, firstSwatchIndex, firstColorId);\n\n // Initialize colors\n const _self = this;\n $(this.colorsElement).each(function (index, element) {\n let colorName = $(element).data('display-value');\n let colorCode = $(element).data('code');\n $(element).css('background-color', colorCode);\n if (index === 0) {\n $(_self.colorName).text(colorName);\n }\n });\n\n // Class methods\n this.giftCardEventListeners();\n this.formListeners();\n this.initializeDateSelector();\n this.initParsleyValidator();\n this.initSwatches();\n this.initModalPreview();\n\n // Legacy imports\n processInclude(require('./giftcard/giftcardBalance'));\n processInclude(require('./checkout/giftcard'));\n GiftcardHelper.addToCart();\n\n productHelpers.run();\n }\n\n _selectOccasion (occasionName, swatchIndex, colorId) {\n // Reset all occasions\n $(this.occasionElement).removeClass('selected');\n\n // Select occasion based on name\n const $selectedOccasion = $(`${this.occasionElement}[data-occasion=\"${occasionName}\"]`);\n $selectedOccasion.addClass('selected');\n this.selectedOccasion = occasionName;\n\n // Select swatch slider and color list\n this._selectSwatch(occasionName, swatchIndex, colorId);\n }\n\n _selectSwatch (occasionName, swatchIndex, colorId) {\n // Reset all swatches\n $(this.swatchesContainer).removeClass('selected');\n $(this.swatchesElement).removeClass('selected');\n\n // Select swatch container\n const $selectedSwatchContainer = $(`${this.swatchesContainer}[data-occasion=\"${occasionName}\"]`);\n $selectedSwatchContainer.addClass('selected');\n\n // Select swatch element\n const $selectedSwatch = $selectedSwatchContainer.find(`${this.swatchesElement}[data-index=\"${swatchIndex}\"]`);\n $selectedSwatch.addClass('selected');\n\n // Update selected swatch index\n this.selectedSwatchIndex = swatchIndex;\n\n // Select color list\n this._selectColorsList(occasionName, swatchIndex, colorId);\n }\n\n _selectColorsList (occasionName, swatchIndex, colorId) {\n // Reset colors list\n $(this.colorsContainer).removeClass('selected');\n\n // Select color list (hide entire container if no color list is available)\n const $selectedColorList = $(`${this.colorsContainer}[data-occasion=\"${occasionName}\"]`);\n $(this.colorsSection).toggleClass('hide', $selectedColorList.length === 0);\n $selectedColorList.addClass('selected');\n\n this._selectColor(occasionName, swatchIndex, colorId);\n }\n\n _selectColor (occasionName, swatchIndex, colorId) {\n // Reset colors\n $(this.colorsElement).removeClass('selected');\n\n // Retrieve selected color of current list and highlight it\n const $selectedColorList = $(`${this.colorsContainer}[data-occasion=\"${occasionName}\"]`);\n const $selectedColor = $selectedColorList.find(`${this.colorsElement}[data-color-id=\"${colorId}\"]`);\n $selectedColor.addClass('selected');\n $(this.colorName).text($selectedColor.data('display-value'));\n this.selectedColor = colorId;\n\n // Update carousel\n var $carousel = '';\n $(this.giftCardImage).each(function (index, element) {\n if ($(element).data('occasion') === occasionName && $(element).data('color-id') === colorId) {\n let src = $(element).val();\n let alt = $(element).data('alt') || `${occasionName} occasion ${ colorId ? 'of color ' + colorId : ''}`; // Remove fallback when alt label is provided\n $carousel += applyRendering('sliderCarouselItem', {\n src: src,\n alt: alt,\n index: String(index)\n });\n }\n });\n\n // Rebuild slick slider\n if ($(this.carousel).hasClass('slick-initialized')) {\n $(this.carousel).slick('unslick');\n }\n $(this.giftCardPriceBanner).addClass('hide');\n $(this.carousel).empty();\n $(this.carousel).html($carousel);\n $(this.carousel).slick(this.sliderConfig);\n $(this.giftCardPriceBanner).removeClass('hide');\n $(this.carousel).slick('slickGoTo', swatchIndex, true);\n\n // Update image name to be added\n var selectedImageUrl = $(`${this.giftCardImage}[data-occasion=\"${occasionName}\"][data-index=\"${swatchIndex}\"][data-color-id=\"${colorId}\"]`).val();\n if (selectedImageUrl && selectedImageUrl.length > 0) {\n var selectedImageUrlArray = selectedImageUrl.split('/');\n var selectedImageName = selectedImageUrlArray[selectedImageUrlArray.length - 1].replace('.jpg', '');\n $('.js-giftCardPage-giftCardAddToCartGlobal').data('egc-image-name', selectedImageName).attr('data-egc-image-name', selectedImageName);\n }\n }\n\n giftCardEventListeners () {\n const _self = this;\n\n // Manage occasion selection\n $('body').on('click', this.occasionElement + ':not(.selected)', function (e) {\n e.preventDefault();\n var newOccasionSelection = $(e.currentTarget).data('occasion');\n var firstColorId = $(`${_self.colorsContainer}[data-occasion=\"${newOccasionSelection}\"]`).find(_self.colorsElement).first().data('color-id') || '';\n _self._selectOccasion(newOccasionSelection, 0, firstColorId);\n });\n\n // Manage swatch selection\n $('body').on('click', this.swatchesElement + ':not(.selected)', function (e) {\n e.preventDefault();\n var newSwatchSelection = $(e.currentTarget).data('index');\n _self._selectSwatch(_self.selectedOccasion, newSwatchSelection, _self.selectedColor);\n });\n\n // Manage color selection\n $('body').on('click', this.colorsElement + ':not(.selected)', function (e) {\n e.preventDefault();\n var newColorSelection = $(e.currentTarget).data('color-id');\n _self._selectColor(_self.selectedOccasion, _self.selectedSwatchIndex, newColorSelection);\n });\n\n // Manage amount selection\n $('body').on('click', this.amounts, function (e) {\n var amount = $(e.currentTarget).val();\n if (parseInt(amount) !== 0 && amount !== null && amount !== 'null') {\n $('.js-price-value').text(amount);\n $('.js-sliderForPriceStamp_amount').text(amount);\n\n // Clear manual amount input\n $(_self.manualAmount).val('');\n }\n });\n\n $(this.manualAmount).on('click', function () {\n // De-select amount options\n $(`${_self.amounts}:checked`).prop('checked', false);\n });\n\n $(this.manualAmount).siblings('.form-fields-item__clearIcon').on('click', function () {\n // Abled amount options\n $(`${_self.amounts}`).prop('disabled', false);\n });\n\n // Manage amount manual input\n $(this.manualAmount).on('input', function (e) {\n e.preventDefault();\n const value = $(this).val();\n\n // If blank pre-select first option instead\n if (!value || value.length === 0) {\n const $firstAmountOption = $(_self.amounts).first();\n var firstAmountOptionValue = $firstAmountOption.val();\n\n $firstAmountOption.trigger('click');\n $('.js-sliderForPriceStamp_amount').text(firstAmountOptionValue);\n $('.js-price-value').text(firstAmountOptionValue);\n $(`${_self.amounts}`).prop('disabled', false);\n\n $('.js-price-validation-error').hide();\n return;\n }\n $(`${_self.amounts}`).prop('disabled', true);\n $('.js-price-validation-error').hide();\n if (!value || /[^0-9]/.test(value)) {\n $('.js-price-validation-error').show();\n return;\n }\n\n var parsedValue = parseInt(value, 10);\n var minimumValue = parseInt($(e.currentTarget).data('min'), 10);\n var maximumValue = parseInt($(e.currentTarget).data('max'), 10);\n if (parsedValue < minimumValue || parsedValue > maximumValue) {\n $('.js-price-validation-error').show();\n $('.js-sliderForPriceStamp_amount').text('--');\n return;\n }\n\n $('.js-sliderForPriceStamp_amount').text(value);\n $('.js-price-value').text(value);\n });\n }\n\n formListeners () {\n $('.js-giftcardNameTo').on('keyup', function (e) {\n e.preventDefault();\n const value = $(this).val();\n $('.js-giftcardNameToStamp').text(value);\n });\n\n $('.js-giftcardYourName').on('keyup', function (e) {\n e.preventDefault();\n const value = $(this).val();\n $('.js-giftcardYourNameStamp').text(value);\n });\n\n $('.js-contactFormMessage').on('keyup', function (e) {\n e.preventDefault();\n const value = $(this).val();\n $('.js-contactFormMessageStamp').text(value);\n });\n\n var maxLength = 230;\n $('.js-contactFormMessage').on('keyup', function (e) {\n e.preventDefault();\n const textlen = maxLength - $(this).val().length;\n $('#egcMessageFeedbackNumber').text(textlen);\n });\n }\n\n initializeDateSelector () {\n var firstDate = new Date();\n var year = firstDate.getFullYear();\n var month = firstDate.getMonth();\n var day = firstDate.getDate();\n var expiryDate = new Date(year + 3, month, day);\n var formatPattern = $('.datepickerTriggerElement').data('date-format-pattern');\n\n var formattedDate = formatDate(firstDate, formatPattern);\n var formattedExpiryDate = formatDate(expiryDate, formatPattern);\n $('.js-giftCardDateExpiryStamp').html(formattedExpiryDate);\n $('.datepickerTriggerElement').data('date', formatDate(firstDate, 'dd-mm-yyyy'));\n $('#dp1').val(formattedDate);\n\n $('.datepickerTriggerElement').fdatepicker({\n format: 'dd-mm-yyyy',\n disableDblClickSelection: true,\n leftArrow: '<<',\n rightArrow: '>>',\n closeIcon: 'X',\n closeButton: false,\n initialDate: new Date(),\n startDate: new Date()\n }).on('changeDate', function (ev) {\n let date = new Date(ev.date.valueOf() + ev.date.getTimezoneOffset() * 60000);\n var datestring = formatDate(date, formatPattern);\n $('#dp1').val(datestring);\n $('.datepickerTriggerElement').data('date', formatDate(date, 'dd-mm-yyyy'));\n\n let year = date.getFullYear();\n let month = date.getMonth();\n let day = date.getDate();\n let expiry = new Date(year + 3, month, day);\n $('.js-giftCardDateExpiryStamp').html(formatDate(expiry, formatPattern));\n });\n }\n\n initParsleyValidator () {\n var items = $('.parsleyValidatableElement');\n for (let i = 0; i < items.length; i++) {\n items.eq(i).parsley();\n }\n }\n\n initSwatches () {\n const _self = this;\n\n $(this.carousel).on('afterChange', function (event, slick, currentSlide, nextSlide) {\n $(`${_self.swatchesElement}.selected`).removeClass('selected');\n $(`${_self.swatchesElement}[data-index=\"${currentSlide}\"]`).addClass('selected');\n });\n }\n\n initModalPreview () {\n const _self = this;\n\n $('.js-linkModalGiftCard').on('click', function (e) {\n e.preventDefault();\n const htmlContent = $('.js-ModalGiftCard').html();\n const modalBigContent = newModalFromString(htmlContent, false, ['wrapperModalGiftCard']);\n\n var giftCardHtmlPreview = $(_self.carousel).find('.slick-active').html() + $(_self.giftCardPriceBanner)[0].outerHTML;\n $('.js-ImgGiftCardStamp').html(giftCardHtmlPreview);\n\n modalBigContent.open();\n\n $(modalBigContent.modalBox).find('.close').on('click', function (e) {\n modalBigContent.close();\n });\n\n $('.js-inside-close-modal').on('click', function (e) {\n e.preventDefault();\n modalBigContent.close();\n });\n });\n }\n}\n\ndocument.addEventListener('DOMContentLoaded', () => {\n const giftCard = new GiftCard();\n giftCard.init();\n});\n","import ProductHelpers from '../product/base';\n\nfunction formatDate (date, formatPattern) {\n if (formatPattern === 'dd-mm-yyyy') {\n return ('0' + date.getDate()).slice(-2) + '-' + ('0' + (date.getMonth() + 1)).slice(-2) + '-' +\n date.getFullYear();\n } else if (formatPattern === 'mm-dd-yyyy') {\n return ('0' + (date.getMonth() + 1)).slice(-2) + '-' + ('0' + date.getDate()).slice(-2) + '-' +\n date.getFullYear();\n } else if (formatPattern === 'yyyy年mm月dd日') {\n var dateParsed = (date.getFullYear() + '年' + ('0' + (date.getMonth() + 1)).slice(-2) + '月' + ('0' + date.getDate()).slice(-2) + '日');\n return dateParsed;\n }\n}\n\n/**\n * Updates the Mini-Cart quantity value after the customer has pressed the \"Add to Cart\" button\n * @param {string} response - ajax response from clicking the add to cart button\n */\nconst getAddToCartUrl = () => {\n return $('.add-to-cart-url').val();\n};\n\nclass GiftcardHelpers {\n addToCart () {\n $('body').on('click', 'button.js-giftCardPage-giftCardAddToCartGlobal', e => {\n e.preventDefault();\n\n // Validate price\n let amountSelectorOk = true;\n var formatPattern = $('.datepickerTriggerElement').data('date-format-pattern');\n if (!$('.js-giftcard-amount-option:checked').val() && !$('.js-giftcard-amount-manual').val()) {\n $('.js-price-validation-error-not-selected').removeClass('hidden');\n amountSelectorOk = false;\n }\n\n // check if custom amount is in the possible range\n let minAmount = $('.js-giftcard-amount-manual').data('min');\n let maxAmount = $('.js-giftcard-amount-manual').data('max');\n\n if ($('.js-giftcard-amount-manual').val() && (parseFloat($('.js-giftcard-amount-manual').val()) < minAmount || parseFloat($('.js-giftcard-amount-manual').val()) > maxAmount)) {\n amountSelectorOk = false;\n }\n\n let errors = [];\n let container = $('.parsleyValidatableElement');\n for (let i = 0; i < container.length; i++) {\n let validator = container.eq(i).parsley();\n validator.validate();\n if (!validator.isValid()) {\n errors.push(validator);\n }\n }\n\n if (errors.length > 0 || !amountSelectorOk) {\n return;\n }\n\n let addToCartUrl;\n let pid;\n\n pid = ProductHelpers.methods.getPidValue($(e.currentTarget));\n\n var $productContainer = $(e.currentTarget).closest('.product-detail');\n if (!$productContainer.length) {\n $productContainer = $(e.currentTarget).closest('.quickview-modals').find('.product-detail');\n }\n\n addToCartUrl = getAddToCartUrl();\n\n let uid = $(e.currentTarget).data('uid');\n\n let country = $('#countrySelector').val();\n let destinationName = $('.js-giftcardNameTo').val();\n let destinationMail = $('#giftcard--mail-to').val();\n let senderName = $('.js-giftcardYourName').val();\n let message = $('#contact-form-message').val() || '';\n\n let amount = $('.js-giftcard-amount-manual').val() || $('.js-giftcard-amount-option:checked').val();\n\n let dateString = $('.datepickerTriggerElement').data('date');\n if (dateString.match(/-/g).length !== 2) {\n dateString = formatDate(new Date(dateString), formatPattern);\n }\n\n let imgCode = $(e.currentTarget).data('egc-image-name');\n let giftcardGender;\n let urlParams = new URLSearchParams(window.location.search);\n let productGender = urlParams.get('type');\n if (productGender) {\n giftcardGender = productGender === 'M' ? '2' : '1';\n } else {\n giftcardGender = '';\n }\n var form = {\n pid: pid,\n quantity: 1,\n uuid: uid,\n destinationName: destinationName,\n destinationMail: destinationMail,\n message: message,\n senderName: senderName,\n amount: amount,\n shippingDate: dateString,\n country: country,\n imageCode: imgCode,\n giftcardGender: giftcardGender\n };\n\n $(e.currentTarget).trigger('updateAddToCartFormData', form);\n if (addToCartUrl) {\n $.spinner().start();\n $.ajax({\n url: addToCartUrl,\n method: 'POST',\n data: form,\n success: data => {\n $('body').trigger('product:afterAddToCartGiftCard', data);\n $('.js-mainHeader-minicart').trigger('count:update', data);\n $.spinner().stop();\n },\n error: () => {\n $.spinner().stop();\n }\n });\n }\n });\n };\n}\n\nconst giftcardHelper = new GiftcardHelpers();\nexport default giftcardHelper;\n","$('#button-scroll').on('click', function () {\n var smooth = [$('a.smooth'), 100, 750];\n $('html, body').animate({\n scrollTop: $('[id=\"' + $.attr(this, 'href').substr(1) + '\"]').offset().top - smooth[1]\n }, smooth[2]);\n return false;\n});\n\n// Change the state of the input field according to the tab\n$('#input-radio-box').on('change', function (e) {\n if (e.target.value === '1') {\n $('#field-pin').addClass('hide');\n } else {\n $('#field-pin').removeClass('hide');\n }\n});\n\n$(document).ready(function () {\n $('#ctaButtonsContainer').removeAttr('style');\n $('.cta-gift-card-balance .button').eq(0).addClass('button--primary');\n $('.cta-gift-card-balance .button').eq(1).addClass('button--secondary');\n $('.cc-contentBox, #cnt-carta-reso').removeClass('content-box-choose-gift');\n $('#cnt-gift-cards').insertAfter('#form-gift-card');\n $('#button-scroll').on('click', function (e) {\n e.preventDefault();\n $('html, body').animate({\n scrollTop: $('#balance-gift').offset().top - $('.cc-mainHeader-container').height()\n }, 1000, 'linear');\n });\n\n $('body').on('click', '.js-myAccountGiftCard-checkAnotherCard', e => {\n $('[name=\"inputCode\"]').val('');\n $('[name=\"inputPin\"]').val('');\n $('.wrapper-content-slot').addClass('hiddenGiftCard');\n $('html, body').animate({ scrollTop: $('.cc-myAccountGiftCard').position().top - $('.js-mainHeader-container').height() }, 'slow');\n });\n});\n"],"sourceRoot":""}