{"version":3,"file":"Pattern.mjs","sources":["../../../src/Pattern/Pattern.ts"],"sourcesContent":["import { config } from '../config';\nimport type { Abortable, TCrossOrigin, TMat2D, TSize } from '../typedefs';\nimport { ifNaN } from '../util/internals';\nimport { uid } from '../util/internals/uid';\nimport { loadImage } from '../util/misc/objectEnlive';\nimport { pick } from '../util/misc/pick';\nimport { toFixed } from '../util/misc/toFixed';\nimport { classRegistry } from '../ClassRegistry';\nimport type {\n  PatternRepeat,\n  PatternOptions,\n  SerializedPatternOptions,\n} from './types';\nimport { log } from '../util/internals/console';\n\n/**\n * @see {@link http://fabricjs.com/patterns demo}\n * @see {@link http://fabricjs.com/dynamic-patterns demo}\n */\nexport class Pattern {\n  static type = 'Pattern';\n\n  /**\n   * Legacy identifier of the class. Prefer using this.constructor.type 'Pattern'\n   * or utils like isPattern, or instance of to indentify a pattern in your code.\n   * Will be removed in future versiones\n   * @TODO add sustainable warning message\n   * @type string\n   * @deprecated\n   */\n  get type() {\n    return 'pattern';\n  }\n\n  set type(value) {\n    log('warn', 'Setting type has no effect', value);\n  }\n\n  /**\n   * @type PatternRepeat\n   * @defaults\n   */\n  repeat: PatternRepeat = 'repeat';\n\n  /**\n   * Pattern horizontal offset from object's left/top corner\n   * @type Number\n   * @default\n   */\n  offsetX = 0;\n\n  /**\n   * Pattern vertical offset from object's left/top corner\n   * @type Number\n   * @default\n   */\n  offsetY = 0;\n\n  /**\n   * @type TCrossOrigin\n   * @default\n   */\n  crossOrigin: TCrossOrigin = '';\n\n  /**\n   * transform matrix to change the pattern, imported from svgs.\n   * @todo verify if using the identity matrix as default makes the rest of the code more easy\n   * @type Array\n   * @default\n   */\n  patternTransform: TMat2D | null = null;\n\n  /**\n   * The actual pixel source of the pattern\n   */\n  declare source: CanvasImageSource;\n\n  /**\n   * If true, this object will not be exported during the serialization of a canvas\n   * @type boolean\n   */\n  declare excludeFromExport?: boolean;\n\n  /**\n   * ID used for SVG export functionalities\n   * @type number\n   */\n  declare readonly id: number;\n\n  /**\n   * Constructor\n   * @param {Object} [options] Options object\n   * @param {option.source} [source] the pattern source, eventually empty or a drawable\n   */\n  constructor(options: PatternOptions) {\n    this.id = uid();\n    Object.assign(this, options);\n  }\n\n  /**\n   * @returns true if {@link source} is an <img> element\n   */\n  isImageSource(): this is { source: HTMLImageElement } {\n    return (\n      !!this.source && typeof (this.source as HTMLImageElement).src === 'string'\n    );\n  }\n\n  /**\n   * @returns true if {@link source} is a <canvas> element\n   */\n  isCanvasSource(): this is { source: HTMLCanvasElement } {\n    return !!this.source && !!(this.source as HTMLCanvasElement).toDataURL;\n  }\n\n  sourceToString(): string {\n    return this.isImageSource()\n      ? this.source.src\n      : this.isCanvasSource()\n      ? this.source.toDataURL()\n      : '';\n  }\n\n  /**\n   * Returns an instance of CanvasPattern\n   * @param {CanvasRenderingContext2D} ctx Context to create pattern\n   * @return {CanvasPattern}\n   */\n  toLive(ctx: CanvasRenderingContext2D): CanvasPattern | null {\n    if (\n      // if the image failed to load, return, and allow rest to continue loading\n      !this.source ||\n      // if an image\n      (this.isImageSource() &&\n        (!this.source.complete ||\n          this.source.naturalWidth === 0 ||\n          this.source.naturalHeight === 0))\n    ) {\n      return null;\n    }\n\n    return ctx.createPattern(this.source, this.repeat)!;\n  }\n\n  /**\n   * Returns object representation of a pattern\n   * @param {Array} [propertiesToInclude] Any properties that you might want to additionally include in the output\n   * @return {object} Object representation of a pattern instance\n   */\n  toObject(propertiesToInclude: string[] = []): Record<string, any> {\n    const { repeat, crossOrigin } = this;\n    return {\n      ...pick(this, propertiesToInclude as (keyof this)[]),\n      type: 'pattern',\n      source: this.sourceToString(),\n      repeat,\n      crossOrigin,\n      offsetX: toFixed(this.offsetX, config.NUM_FRACTION_DIGITS),\n      offsetY: toFixed(this.offsetY, config.NUM_FRACTION_DIGITS),\n      patternTransform: this.patternTransform\n        ? [...this.patternTransform]\n        : null,\n    };\n  }\n\n  /* _TO_SVG_START_ */\n  /**\n   * Returns SVG representation of a pattern\n   */\n  toSVG({ width, height }: TSize): string {\n    const { source: patternSource, repeat, id } = this,\n      patternOffsetX = ifNaN(this.offsetX / width, 0),\n      patternOffsetY = ifNaN(this.offsetY / height, 0),\n      patternWidth =\n        repeat === 'repeat-y' || repeat === 'no-repeat'\n          ? 1 + Math.abs(patternOffsetX || 0)\n          : ifNaN(\n              ((patternSource as HTMLImageElement).width as number) / width,\n              0\n            ),\n      patternHeight =\n        repeat === 'repeat-x' || repeat === 'no-repeat'\n          ? 1 + Math.abs(patternOffsetY || 0)\n          : ifNaN(\n              ((patternSource as HTMLImageElement).height as number) / height,\n              0\n            );\n\n    return [\n      `<pattern id=\"SVGID_${id}\" x=\"${patternOffsetX}\" y=\"${patternOffsetY}\" width=\"${patternWidth}\" height=\"${patternHeight}\">`,\n      `<image x=\"0\" y=\"0\" width=\"${\n        (patternSource as HTMLImageElement).width\n      }\" height=\"${\n        (patternSource as HTMLImageElement).height\n      }\" xlink:href=\"${this.sourceToString()}\"></image>`,\n      `</pattern>`,\n      '',\n    ].join('\\n');\n  }\n  /* _TO_SVG_END_ */\n\n  static async fromObject(\n    { type, source, ...serialized }: SerializedPatternOptions,\n    options?: Abortable\n  ): Promise<Pattern> {\n    const img = await loadImage(source, {\n      ...options,\n      crossOrigin: serialized.crossOrigin,\n    });\n    return new this({ ...serialized, source: img });\n  }\n}\n\nclassRegistry.setClass(Pattern);\n// kept for compatibility reason\nclassRegistry.setClass(Pattern, 'pattern');\n"],"names":["Pattern","type","value","log","constructor","options","_defineProperty","id","uid","Object","assign","isImageSource","source","src","isCanvasSource","toDataURL","sourceToString","toLive","ctx","complete","naturalWidth","naturalHeight","createPattern","repeat","toObject","propertiesToInclude","arguments","length","undefined","crossOrigin","_objectSpread","pick","offsetX","toFixed","config","NUM_FRACTION_DIGITS","offsetY","patternTransform","toSVG","_ref","width","height","patternSource","patternOffsetX","ifNaN","patternOffsetY","patternWidth","Math","abs","patternHeight","concat","join","fromObject","_ref2","serialized","_objectWithoutProperties","_excluded","img","loadImage","classRegistry","setClass"],"mappings":"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"}