1 line
40 KiB
Plaintext
1 line
40 KiB
Plaintext
{"version":3,"file":"BitmapText.mjs","sources":["../src/BitmapText.ts"],"sourcesContent":["import { BLEND_MODES, Color, ObservablePoint, Point, Program, settings, Texture, utils } from '@pixi/core';\nimport { Container } from '@pixi/display';\nimport { Mesh, MeshGeometry, MeshMaterial } from '@pixi/mesh';\nimport { BitmapFont } from './BitmapFont';\nimport msdfFrag from './shader/msdf.frag';\nimport msdfVert from './shader/msdf.vert';\nimport { extractCharCode, splitTextToCharacters } from './utils';\n\nimport type { ColorSource, Rectangle, Renderer } from '@pixi/core';\nimport type { IDestroyOptions } from '@pixi/display';\nimport type { TextStyleAlign } from '@pixi/text';\nimport type { IBitmapTextStyle } from './BitmapTextStyle';\n\ninterface PageMeshData\n{\n index: number;\n indexCount: number;\n vertexCount: number;\n uvsCount: number;\n total: number;\n mesh: Mesh;\n vertices?: Float32Array;\n uvs?: Float32Array;\n indices?: Uint16Array;\n}\ninterface CharRenderData\n{\n texture: Texture;\n line: number;\n charCode: number;\n position: Point;\n prevSpaces: number;\n}\n\n// If we ever need more than two pools, please make a Dict or something better.\nconst pageMeshDataDefaultPageMeshData: PageMeshData[] = [];\nconst pageMeshDataMSDFPageMeshData: PageMeshData[] = [];\nconst charRenderDataPool: CharRenderData[] = [];\n\n/**\n * A BitmapText object will create a line or multiple lines of text using bitmap font.\n *\n * The primary advantage of this class over Text is that all of your textures are pre-generated and loading,\n * meaning that rendering is fast, and changing text has no performance implications.\n *\n * Supporting character sets other than latin, such as CJK languages, may be impractical due to the number of characters.\n *\n * To split a line you can use '\\n', '\\r' or '\\r\\n' in your string.\n *\n * PixiJS can auto-generate fonts on-the-fly using BitmapFont or use fnt files provided by:\n * http://www.angelcode.com/products/bmfont/ for Windows or\n * http://www.bmglyph.com/ for Mac.\n *\n * You can also use SDF, MSDF and MTSDF BitmapFonts for vector-like scaling appearance provided by:\n * https://github.com/soimy/msdf-bmfont-xml for SDF and MSDF fnt files or\n * https://github.com/Chlumsky/msdf-atlas-gen for SDF, MSDF and MTSDF json files\n *\n * A BitmapText can only be created when the font is loaded.\n * @example\n * import { BitmapText } from 'pixi.js';\n *\n * // in this case the font is in a file called 'desyrel.fnt'\n * const bitmapText = new BitmapText('text using a fancy font!', {\n * fontName: 'Desyrel',\n * fontSize: 35,\n * align: 'right',\n * });\n * @memberof PIXI\n */\nexport class BitmapText extends Container\n{\n public static styleDefaults: Partial<IBitmapTextStyle> = {\n align: 'left',\n tint: 0xFFFFFF,\n maxWidth: 0,\n letterSpacing: 0,\n };\n\n /** Set to `true` if the BitmapText needs to be redrawn. */\n public dirty: boolean;\n\n /**\n * The resolution / device pixel ratio of the canvas.\n *\n * This is set to automatically match the renderer resolution by default, but can be overridden by setting manually.\n * @default PIXI.settings.RESOLUTION\n */\n _resolution: number;\n _autoResolution: boolean;\n\n /**\n * Private tracker for the width of the overall text.\n * @private\n */\n protected _textWidth: number;\n\n /**\n * Private tracker for the height of the overall text.\n * @private\n */\n protected _textHeight: number;\n\n /**\n * Private tracker for the current text.\n * @private\n */\n protected _text: string;\n\n /**\n * The max width of this bitmap text in pixels. If the text provided is longer than the\n * value provided, line breaks will be automatically inserted in the last whitespace.\n * Disable by setting value to 0\n * @private\n */\n protected _maxWidth: number;\n\n /**\n * The max line height. This is useful when trying to use the total height of the Text,\n * ie: when trying to vertically align. (Internally used)\n * @private\n */\n protected _maxLineHeight: number;\n\n /**\n * Letter spacing. This is useful for setting the space between characters.\n * @private\n */\n protected _letterSpacing: number;\n\n /**\n * Text anchor.\n * @readonly\n * @private\n */\n protected _anchor: ObservablePoint;\n\n /**\n * Private tracker for the current font.\n * @private\n */\n protected _font?: BitmapFont;\n\n /**\n * Private tracker for the current font name.\n * @private\n */\n protected _fontName: string;\n\n /**\n * Private tracker for the current font size.\n * @private\n */\n protected _fontSize?: number;\n\n /**\n * Private tracker for the current text align.\n * @type {string}\n * @private\n */\n protected _align: TextStyleAlign;\n\n /** Collection of page mesh data. */\n protected _activePagesMeshData: PageMeshData[];\n\n /**\n * Private tracker for the current tint.\n * @private\n */\n protected _tintColor: Color;\n\n /**\n * If true PixiJS will Math.floor() x/y values when rendering.\n * @default PIXI.settings.ROUND_PIXELS\n */\n protected _roundPixels: boolean;\n\n /** Cached char texture is destroyed when BitmapText is destroyed. */\n private _textureCache: Record<number, Texture>;\n\n /**\n * @param text - A string that you would like the text to display.\n * @param style - The style parameters.\n * @param {string} style.fontName - The installed BitmapFont name.\n * @param {number} [style.fontSize] - The size of the font in pixels, e.g. 24. If undefined,\n *. this will default to the BitmapFont size.\n * @param {string} [style.align='left'] - Alignment for multiline text ('left', 'center', 'right' or 'justify'),\n * does not affect single line text.\n * @param {PIXI.ColorSource} [style.tint=0xFFFFFF] - The tint color.\n * @param {number} [style.letterSpacing=0] - The amount of spacing between letters.\n * @param {number} [style.maxWidth=0] - The max width of the text before line wrapping.\n */\n constructor(text: string, style: Partial<IBitmapTextStyle> = {})\n {\n super();\n\n // Apply the defaults\n const { align, tint, maxWidth, letterSpacing, fontName, fontSize } = Object.assign(\n {}, BitmapText.styleDefaults, style);\n\n if (!BitmapFont.available[fontName])\n {\n throw new Error(`Missing BitmapFont \"${fontName}\"`);\n }\n\n this._activePagesMeshData = [];\n this._textWidth = 0;\n this._textHeight = 0;\n this._align = align;\n this._tintColor = new Color(tint);\n this._font = undefined;\n this._fontName = fontName;\n this._fontSize = fontSize;\n this.text = text;\n this._maxWidth = maxWidth;\n this._maxLineHeight = 0;\n this._letterSpacing = letterSpacing;\n this._anchor = new ObservablePoint((): void => { this.dirty = true; }, this, 0, 0);\n this._roundPixels = settings.ROUND_PIXELS;\n this.dirty = true;\n this._resolution = settings.RESOLUTION;\n this._autoResolution = true;\n this._textureCache = {};\n }\n\n /** Renders text and updates it when needed. This should only be called if the BitmapFont is regenerated. */\n public updateText(): void\n {\n const data = BitmapFont.available[this._fontName];\n const fontSize = this.fontSize;\n const scale = fontSize / data.size;\n const pos = new Point();\n const chars: CharRenderData[] = [];\n const lineWidths = [];\n const lineSpaces = [];\n const text = this._text.replace(/(?:\\r\\n|\\r)/g, '\\n') || ' ';\n const charsInput = splitTextToCharacters(text);\n const maxWidth = this._maxWidth * data.size / fontSize;\n const pageMeshDataPool = data.distanceFieldType === 'none'\n ? pageMeshDataDefaultPageMeshData : pageMeshDataMSDFPageMeshData;\n\n let prevCharCode = null;\n let lastLineWidth = 0;\n let maxLineWidth = 0;\n let line = 0;\n let lastBreakPos = -1;\n let lastBreakWidth = 0;\n let spacesRemoved = 0;\n let maxLineHeight = 0;\n let spaceCount = 0;\n\n for (let i = 0; i < charsInput.length; i++)\n {\n const char = charsInput[i];\n const charCode = extractCharCode(char);\n\n if ((/(?:\\s)/).test(char))\n {\n lastBreakPos = i;\n lastBreakWidth = lastLineWidth;\n spaceCount++;\n }\n\n if (char === '\\r' || char === '\\n')\n {\n lineWidths.push(lastLineWidth);\n lineSpaces.push(-1);\n maxLineWidth = Math.max(maxLineWidth, lastLineWidth);\n ++line;\n ++spacesRemoved;\n\n pos.x = 0;\n pos.y += data.lineHeight;\n prevCharCode = null;\n spaceCount = 0;\n continue;\n }\n\n const charData = data.chars[charCode];\n\n if (!charData)\n {\n continue;\n }\n\n if (prevCharCode && charData.kerning[prevCharCode])\n {\n pos.x += charData.kerning[prevCharCode];\n }\n\n const charRenderData: CharRenderData = charRenderDataPool.pop() || {\n texture: Texture.EMPTY,\n line: 0,\n charCode: 0,\n prevSpaces: 0,\n position: new Point(),\n };\n\n charRenderData.texture = charData.texture;\n charRenderData.line = line;\n charRenderData.charCode = charCode;\n charRenderData.position.x = Math.round(pos.x + charData.xOffset + (this._letterSpacing / 2));\n charRenderData.position.y = Math.round(pos.y + charData.yOffset);\n charRenderData.prevSpaces = spaceCount;\n\n chars.push(charRenderData);\n\n lastLineWidth = charRenderData.position.x\n + Math.max(charData.xAdvance - charData.xOffset, charData.texture.orig.width);\n pos.x += charData.xAdvance + this._letterSpacing;\n maxLineHeight = Math.max(maxLineHeight, (charData.yOffset + charData.texture.height));\n prevCharCode = charCode;\n\n if (lastBreakPos !== -1 && maxWidth > 0 && pos.x > maxWidth)\n {\n ++spacesRemoved;\n utils.removeItems(chars, 1 + lastBreakPos - spacesRemoved, 1 + i - lastBreakPos);\n i = lastBreakPos;\n lastBreakPos = -1;\n\n lineWidths.push(lastBreakWidth);\n lineSpaces.push(chars.length > 0 ? chars[chars.length - 1].prevSpaces : 0);\n maxLineWidth = Math.max(maxLineWidth, lastBreakWidth);\n line++;\n\n pos.x = 0;\n pos.y += data.lineHeight;\n prevCharCode = null;\n spaceCount = 0;\n }\n }\n\n const lastChar = charsInput[charsInput.length - 1];\n\n if (lastChar !== '\\r' && lastChar !== '\\n')\n {\n if ((/(?:\\s)/).test(lastChar))\n {\n lastLineWidth = lastBreakWidth;\n }\n\n lineWidths.push(lastLineWidth);\n maxLineWidth = Math.max(maxLineWidth, lastLineWidth);\n lineSpaces.push(-1);\n }\n\n const lineAlignOffsets = [];\n\n for (let i = 0; i <= line; i++)\n {\n let alignOffset = 0;\n\n if (this._align === 'right')\n {\n alignOffset = maxLineWidth - lineWidths[i];\n }\n else if (this._align === 'center')\n {\n alignOffset = (maxLineWidth - lineWidths[i]) / 2;\n }\n else if (this._align === 'justify')\n {\n alignOffset = lineSpaces[i] < 0 ? 0 : (maxLineWidth - lineWidths[i]) / lineSpaces[i];\n }\n\n lineAlignOffsets.push(alignOffset);\n }\n\n const lenChars = chars.length;\n\n const pagesMeshData: Record<number, PageMeshData> = {};\n\n const newPagesMeshData: PageMeshData[] = [];\n\n const activePagesMeshData = this._activePagesMeshData;\n\n pageMeshDataPool.push(...activePagesMeshData);\n\n for (let i = 0; i < lenChars; i++)\n {\n const texture = chars[i].texture;\n const baseTextureUid = texture.baseTexture.uid;\n\n if (!pagesMeshData[baseTextureUid])\n {\n let pageMeshData = pageMeshDataPool.pop();\n\n if (!pageMeshData)\n {\n const geometry = new MeshGeometry();\n let material: MeshMaterial;\n let meshBlendMode: BLEND_MODES;\n\n if (data.distanceFieldType === 'none')\n {\n material = new MeshMaterial(Texture.EMPTY);\n meshBlendMode = BLEND_MODES.NORMAL;\n }\n else\n {\n material = new MeshMaterial(Texture.EMPTY,\n { program: Program.from(msdfVert, msdfFrag), uniforms: { uFWidth: 0 } });\n meshBlendMode = BLEND_MODES.NORMAL_NPM;\n }\n\n const mesh = new Mesh(geometry, material);\n\n mesh.blendMode = meshBlendMode;\n\n pageMeshData = {\n index: 0,\n indexCount: 0,\n vertexCount: 0,\n uvsCount: 0,\n total: 0,\n mesh,\n vertices: null,\n uvs: null,\n indices: null,\n };\n }\n\n // reset data..\n pageMeshData.index = 0;\n pageMeshData.indexCount = 0;\n pageMeshData.vertexCount = 0;\n pageMeshData.uvsCount = 0;\n pageMeshData.total = 0;\n\n // TODO need to get page texture here somehow..\n const { _textureCache } = this;\n\n _textureCache[baseTextureUid] = _textureCache[baseTextureUid] || new Texture(texture.baseTexture);\n pageMeshData.mesh.texture = _textureCache[baseTextureUid];\n\n pageMeshData.mesh.tint = this._tintColor.value;\n\n newPagesMeshData.push(pageMeshData);\n\n pagesMeshData[baseTextureUid] = pageMeshData;\n }\n\n pagesMeshData[baseTextureUid].total++;\n }\n\n // lets find any previously active pageMeshDatas that are no longer required for\n // the updated text (if any), removed and return them to the pool.\n for (let i = 0; i < activePagesMeshData.length; i++)\n {\n if (!newPagesMeshData.includes(activePagesMeshData[i]))\n {\n this.removeChild(activePagesMeshData[i].mesh);\n }\n }\n\n // next lets add any new meshes, that have not yet been added to this BitmapText\n // we only add if its not already a child of this BitmapObject\n for (let i = 0; i < newPagesMeshData.length; i++)\n {\n if (newPagesMeshData[i].mesh.parent !== this)\n {\n this.addChild(newPagesMeshData[i].mesh);\n }\n }\n\n // active page mesh datas are set to be the new pages added.\n this._activePagesMeshData = newPagesMeshData;\n\n for (const i in pagesMeshData)\n {\n const pageMeshData = pagesMeshData[i];\n const total = pageMeshData.total;\n\n // lets only allocate new buffers if we can fit the new text in the current ones..\n // unless that is, we will be batching. Currently batching dose not respect the size property of mesh\n if (!(pageMeshData.indices?.length > 6 * total) || pageMeshData.vertices.length < Mesh.BATCHABLE_SIZE * 2)\n {\n pageMeshData.vertices = new Float32Array(4 * 2 * total);\n pageMeshData.uvs = new Float32Array(4 * 2 * total);\n pageMeshData.indices = new Uint16Array(6 * total);\n }\n else\n {\n const total = pageMeshData.total;\n const vertices = pageMeshData.vertices;\n\n // Clear the garbage at the end of the vertices buffer. This will prevent the bounds miscalculation.\n for (let i = total * 4 * 2; i < vertices.length; i++)\n {\n vertices[i] = 0;\n }\n }\n\n // as a buffer maybe bigger than the current word, we set the size of the meshMaterial\n // to match the number of letters needed\n pageMeshData.mesh.size = 6 * total;\n }\n\n for (let i = 0; i < lenChars; i++)\n {\n const char = chars[i];\n let offset = char.position.x + (lineAlignOffsets[char.line] * (this._align === 'justify' ? char.prevSpaces : 1));\n\n if (this._roundPixels)\n {\n offset = Math.round(offset);\n }\n\n const xPos = offset * scale;\n const yPos = char.position.y * scale;\n const texture = char.texture;\n\n const pageMesh = pagesMeshData[texture.baseTexture.uid];\n\n const textureFrame = texture.frame;\n const textureUvs = texture._uvs;\n\n const index = pageMesh.index++;\n\n pageMesh.indices[(index * 6) + 0] = 0 + (index * 4);\n pageMesh.indices[(index * 6) + 1] = 1 + (index * 4);\n pageMesh.indices[(index * 6) + 2] = 2 + (index * 4);\n pageMesh.indices[(index * 6) + 3] = 0 + (index * 4);\n pageMesh.indices[(index * 6) + 4] = 2 + (index * 4);\n pageMesh.indices[(index * 6) + 5] = 3 + (index * 4);\n\n pageMesh.vertices[(index * 8) + 0] = xPos;\n pageMesh.vertices[(index * 8) + 1] = yPos;\n\n pageMesh.vertices[(index * 8) + 2] = xPos + (textureFrame.width * scale);\n pageMesh.vertices[(index * 8) + 3] = yPos;\n\n pageMesh.vertices[(index * 8) + 4] = xPos + (textureFrame.width * scale);\n pageMesh.vertices[(index * 8) + 5] = yPos + (textureFrame.height * scale);\n\n pageMesh.vertices[(index * 8) + 6] = xPos;\n pageMesh.vertices[(index * 8) + 7] = yPos + (textureFrame.height * scale);\n\n pageMesh.uvs[(index * 8) + 0] = textureUvs.x0;\n pageMesh.uvs[(index * 8) + 1] = textureUvs.y0;\n\n pageMesh.uvs[(index * 8) + 2] = textureUvs.x1;\n pageMesh.uvs[(index * 8) + 3] = textureUvs.y1;\n\n pageMesh.uvs[(index * 8) + 4] = textureUvs.x2;\n pageMesh.uvs[(index * 8) + 5] = textureUvs.y2;\n\n pageMesh.uvs[(index * 8) + 6] = textureUvs.x3;\n pageMesh.uvs[(index * 8) + 7] = textureUvs.y3;\n }\n\n this._textWidth = maxLineWidth * scale;\n this._textHeight = (pos.y + data.lineHeight) * scale;\n\n for (const i in pagesMeshData)\n {\n const pageMeshData = pagesMeshData[i];\n\n // apply anchor\n if (this.anchor.x !== 0 || this.anchor.y !== 0)\n {\n let vertexCount = 0;\n\n const anchorOffsetX = this._textWidth * this.anchor.x;\n const anchorOffsetY = this._textHeight * this.anchor.y;\n\n for (let i = 0; i < pageMeshData.total; i++)\n {\n pageMeshData.vertices[vertexCount++] -= anchorOffsetX;\n pageMeshData.vertices[vertexCount++] -= anchorOffsetY;\n\n pageMeshData.vertices[vertexCount++] -= anchorOffsetX;\n pageMeshData.vertices[vertexCount++] -= anchorOffsetY;\n\n pageMeshData.vertices[vertexCount++] -= anchorOffsetX;\n pageMeshData.vertices[vertexCount++] -= anchorOffsetY;\n\n pageMeshData.vertices[vertexCount++] -= anchorOffsetX;\n pageMeshData.vertices[vertexCount++] -= anchorOffsetY;\n }\n }\n\n this._maxLineHeight = maxLineHeight * scale;\n\n const vertexBuffer = pageMeshData.mesh.geometry.getBuffer('aVertexPosition');\n const textureBuffer = pageMeshData.mesh.geometry.getBuffer('aTextureCoord');\n const indexBuffer = pageMeshData.mesh.geometry.getIndex();\n\n vertexBuffer.data = pageMeshData.vertices;\n textureBuffer.data = pageMeshData.uvs;\n indexBuffer.data = pageMeshData.indices;\n\n vertexBuffer.update();\n textureBuffer.update();\n indexBuffer.update();\n }\n\n for (let i = 0; i < chars.length; i++)\n {\n charRenderDataPool.push(chars[i]);\n }\n\n this._font = data;\n this.dirty = false;\n }\n\n updateTransform(): void\n {\n this.validate();\n this.containerUpdateTransform();\n }\n\n _render(renderer: Renderer): void\n {\n if (this._autoResolution && this._resolution !== renderer.resolution)\n {\n this._resolution = renderer.resolution;\n this.dirty = true;\n }\n\n // Update the uniform\n const { distanceFieldRange, distanceFieldType, size } = BitmapFont.available[this._fontName];\n\n if (distanceFieldType !== 'none')\n {\n // Inject the shader code with the correct value\n const { a, b, c, d } = this.worldTransform;\n\n const dx = Math.sqrt((a * a) + (b * b));\n const dy = Math.sqrt((c * c) + (d * d));\n const worldScale = (Math.abs(dx) + Math.abs(dy)) / 2;\n\n const fontScale = this.fontSize / size;\n\n const resolution = renderer._view.resolution;\n\n for (const mesh of this._activePagesMeshData)\n {\n mesh.mesh.shader.uniforms.uFWidth = worldScale * distanceFieldRange * fontScale * resolution;\n }\n }\n\n super._render(renderer);\n }\n\n /**\n * Validates text before calling parent's getLocalBounds\n * @returns - The rectangular bounding area\n */\n public getLocalBounds(): Rectangle\n {\n this.validate();\n\n return super.getLocalBounds();\n }\n\n /**\n * Updates text when needed\n * @private\n */\n protected validate(): void\n {\n const font = BitmapFont.available[this._fontName];\n\n if (!font)\n {\n throw new Error(`Missing BitmapFont \"${this._fontName}\"`);\n }\n if (this._font !== font)\n {\n this.dirty = true;\n }\n\n if (this.dirty)\n {\n this.updateText();\n }\n }\n\n /**\n * The tint of the BitmapText object.\n * @default 0xffffff\n */\n public get tint(): ColorSource\n {\n return this._tintColor.value;\n }\n\n public set tint(value: ColorSource)\n {\n if (this.tint === value) return;\n\n this._tintColor.setValue(value);\n\n for (let i = 0; i < this._activePagesMeshData.length; i++)\n {\n this._activePagesMeshData[i].mesh.tint = value;\n }\n }\n\n /**\n * The alignment of the BitmapText object.\n * @member {string}\n * @default 'left'\n */\n public get align(): TextStyleAlign\n {\n return this._align;\n }\n\n public set align(value: TextStyleAlign)\n {\n if (this._align !== value)\n {\n this._align = value;\n this.dirty = true;\n }\n }\n\n /** The name of the BitmapFont. */\n public get fontName(): string\n {\n return this._fontName;\n }\n\n public set fontName(value: string)\n {\n if (!BitmapFont.available[value])\n {\n throw new Error(`Missing BitmapFont \"${value}\"`);\n }\n\n if (this._fontName !== value)\n {\n this._fontName = value;\n this.dirty = true;\n }\n }\n\n /** The size of the font to display. */\n public get fontSize(): number\n {\n return this._fontSize ?? BitmapFont.available[this._fontName].size;\n }\n\n public set fontSize(value: number | undefined)\n {\n if (this._fontSize !== value)\n {\n this._fontSize = value;\n this.dirty = true;\n }\n }\n\n /**\n * The anchor sets the origin point of the text.\n *\n * The default is `(0,0)`, this means the text's origin is the top left.\n *\n * Setting the anchor to `(0.5,0.5)` means the text's origin is centered.\n *\n * Setting the anchor to `(1,1)` would mean the text's origin point will be the bottom right corner.\n */\n public get anchor(): ObservablePoint\n {\n return this._anchor;\n }\n\n public set anchor(value: ObservablePoint)\n {\n if (typeof value === 'number')\n {\n this._anchor.set(value);\n }\n else\n {\n this._anchor.copyFrom(value);\n }\n }\n\n /** The text of the BitmapText object. */\n public get text(): string\n {\n return this._text;\n }\n\n public set text(text: string)\n {\n text = String(text === null || text === undefined ? '' : text);\n\n if (this._text === text)\n {\n return;\n }\n this._text = text;\n this.dirty = true;\n }\n\n /**\n * The max width of this bitmap text in pixels. If the text provided is longer than the\n * value provided, line breaks will be automatically inserted in the last whitespace.\n * Disable by setting the value to 0.\n */\n public get maxWidth(): number\n {\n return this._maxWidth;\n }\n\n public set maxWidth(value: number)\n {\n if (this._maxWidth === value)\n {\n return;\n }\n this._maxWidth = value;\n this.dirty = true;\n }\n\n /**\n * The max line height. This is useful when trying to use the total height of the Text,\n * i.e. when trying to vertically align.\n * @readonly\n */\n public get maxLineHeight(): number\n {\n this.validate();\n\n return this._maxLineHeight;\n }\n\n /**\n * The width of the overall text, different from fontSize,\n * which is defined in the style object.\n * @readonly\n */\n public get textWidth(): number\n {\n this.validate();\n\n return this._textWidth;\n }\n\n /** Additional space between characters. */\n public get letterSpacing(): number\n {\n return this._letterSpacing;\n }\n\n public set letterSpacing(value: number)\n {\n if (this._letterSpacing !== value)\n {\n this._letterSpacing = value;\n this.dirty = true;\n }\n }\n\n /**\n * If true PixiJS will Math.floor() x/y values when rendering, stopping pixel interpolation.\n * Advantages can include sharper image quality (like text) and faster rendering on canvas.\n * The main disadvantage is movement of objects may appear less smooth.\n * To set the global default, change {@link PIXI.settings.ROUND_PIXELS}\n * @default PIXI.settings.ROUND_PIXELS\n */\n public get roundPixels(): boolean\n {\n return this._roundPixels;\n }\n\n public set roundPixels(value: boolean)\n {\n if (value !== this._roundPixels)\n {\n this._roundPixels = value;\n this.dirty = true;\n }\n }\n\n /**\n * The height of the overall text, different from fontSize,\n * which is defined in the style object.\n * @readonly\n */\n public get textHeight(): number\n {\n this.validate();\n\n return this._textHeight;\n }\n\n /**\n * The resolution / device pixel ratio of the canvas.\n *\n * This is set to automatically match the renderer resolution by default, but can be overridden by setting manually.\n * @default 1\n */\n get resolution(): number\n {\n return this._resolution;\n }\n\n set resolution(value: number)\n {\n this._autoResolution = false;\n\n if (this._resolution === value)\n {\n return;\n }\n\n this._resolution = value;\n this.dirty = true;\n }\n\n destroy(options?: boolean | IDestroyOptions): void\n {\n const { _textureCache } = this;\n const data = BitmapFont.available[this._fontName];\n const pageMeshDataPool = data.distanceFieldType === 'none'\n ? pageMeshDataDefaultPageMeshData : pageMeshDataMSDFPageMeshData;\n\n pageMeshDataPool.push(...this._activePagesMeshData);\n for (const pageMeshData of this._activePagesMeshData)\n {\n this.removeChild(pageMeshData.mesh);\n }\n this._activePagesMeshData = [];\n\n // Release references to any cached textures in page pool\n pageMeshDataPool\n .filter((page) => _textureCache[page.mesh.texture.baseTexture.uid])\n .forEach((page) =>\n {\n page.mesh.texture = Texture.EMPTY;\n });\n\n for (const id in _textureCache)\n {\n const texture = _textureCache[id];\n\n texture.destroy();\n delete _textureCache[id];\n }\n\n this._font = null;\n this._tintColor = null;\n this._textureCache = null;\n\n super.destroy(options);\n }\n}\n"],"names":["_BitmapText","total","i"],"mappings":"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"} |