{"version":3,"file":"XTextbox.mjs","sources":["../../../../src/shapes/canvasx/XTextbox.ts"],"sourcesContent":["import { TClassProperties, TOriginX, TOriginY } from '../../typedefs';\nimport { IText } from '../IText/IText';\nimport { classRegistry } from '../../ClassRegistry';\nimport { createTextboxDefaultControls } from '../../controls/X_commonControls';\nimport { XTextbase } from './XTextbase';\nimport { isTransformCentered, getLocalPoint } from '../../controls/util';\nimport { EntityKeys } from './type/widget.entity.textbox';\nimport { WidgetType } from './type/widget.type';\nimport { Point } from '../../Point';\nimport { WidgetTextInterface } from './type/widget.entity.text';\n\n// Default values for the textbox\nexport const textboxDefaultValues: Partial<TClassProperties<XTextbase>> = {\n    minWidth: 20,\n    dynamicMinWidth: 2,\n    splitByGrapheme: false,\n    cornerColor: 'white',\n    cornerSize: 10,\n    cornerStyle: 'circle',\n    transparentCorners: false,\n    cornerStrokeColor: 'gray',\n    connectors: [],\n};\n\n// Connector class definition\nclass Connector {\n    connectorId: string;\n    connectorType: string;\n    point: Point;\n}\n\nexport const XTextboxProps: Partial<TClassProperties<XTextbase>> = {};\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 */\nexport class XTextbox extends XTextbase implements WidgetTextInterface {\n    // Property declarations\n    declare minWidth: number;\n    declare tempTop: number;\n    declare hasNoText: boolean;\n    static objType: WidgetType = 'XTextbox';\n    static type: WidgetType = 'XTextbox';\n\n    declare dynamicMinWidth: number;\n    declare oneLine: boolean;\n    declare fromCopy: boolean;\n    declare originX: TOriginX;\n    declare originY: TOriginY;\n    declare connectors: Connector[];\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/Japanese.\n     * @type Boolean\n     * @since 2.6.0\n     */\n    declare splitByGrapheme: boolean;\n\n    static textLayoutProperties = [...IText.textLayoutProperties, 'width'];\n\n    static ownDefaults: Record<string, any> = textboxDefaultValues;\n\n    /**\n     * Override the getDefaults method to set default origin to center\n     */\n    static getDefaults() {\n        return {\n            ...super.getDefaults(),\n            controls: createTextboxDefaultControls(),\n            originX: 'center', // Default originX\n            originY: 'center', // Default originY\n            ...XTextbox.ownDefaults,\n        };\n    }\n\n\n    /**\n     * Constructor to initialize the textbox with default origin\n     * @param text - The initial text content\n     * @param options - Configuration options\n     */\n    constructor(text: string, options: any) {\n        super(text, options);\n\n        // Initialize dimensions\n        this.initDimensions();\n\n        // Remove height from options to manage it dynamically\n        delete options.height;\n        Object.assign(this, options);\n        this.objType = 'XTextbox';\n\n        this.dirty = true;\n\n        // Lock scaling flip and rotation to maintain aspect\n        this.lockScalingFlip = true;\n        this.lockRotation = true;\n        // Setup custom resize controls\n        this.setupCustomResizeControls();\n        // Bind event listeners for editing\n        this.on('editing:entered', this.onEditingEntered.bind(this));\n        this.on('editing:exited', this.onEditingExited.bind(this));\n    }\n    /**\n     * Set up custom resize controls that use our implementation\n     */\n    setupCustomResizeControls() {\n        // Override the action handler for 'mr' (middle right) control\n        if (this.controls && this.controls.mr) {\n            this.controls.mr.actionHandler = this.handleWidthChange.bind(this);\n        }\n\n        // Override the action handler for 'ml' (middle left) control\n        if (this.controls && this.controls.ml) {\n            this.controls.ml.actionHandler = this.handleWidthChange.bind(this);\n        }\n\n\n    }\n\n    // reserve for external interface\n    handleWidthChange2(eventData: any, transform: any, x: number, y: number) {\n\n    }\n    /**\n     * Event handler for entering edit mode\n     */\n    private onEditingEntered() {\n        const canvas = this.canvas;\n        if (!canvas) return;\n\n        // Calculate the current top-left corner in canvas coordinates\n        const topLeft = this.getBoundingRect();\n\n        // Store the current center position\n        const center = this.getCenterPoint();\n\n        // Change origin to 'left' and 'top'\n        this.originX = 'left';\n        this.originY = 'top';\n\n        // Update the position to keep the top-left corner fixed\n        this.set({\n            left: topLeft.left,\n            top: topLeft.top,\n        });\n\n        this.setCoords();\n    }\n\n    /**\n     * Event handler for exiting edit mode\n     */\n    private onEditingExited() {\n        const canvas = this.canvas;\n        if (!canvas) return;\n\n        // Calculate the current top-left corner in canvas coordinates\n        const topLeft = this.getBoundingRect();\n\n        // Change origin back to 'center'\n        this.originX = 'center';\n        this.originY = 'center';\n\n        // Calculate the new center based on top-left to keep position fixed\n        this.set({\n            left: topLeft.left + this.width / 2,\n            top: topLeft.top + this.height / 2,\n        });\n\n        this.setCoords();\n    }\n\n    /**\n     * Retrieves the object's properties\n     * @returns A record of the object's properties\n     */\n    getObject() {\n        const entityKeys: string[] = EntityKeys;\n        const result: Record<string, any> = {};\n\n        entityKeys.forEach((key) => {\n            if (key in this) {\n                result[key] = (this as any)[key];\n            }\n        });\n\n        return result;\n    }\n\n    /**\n     * Override the initDimensions method to ensure height increases downward\n     */\n    initDimensions() {\n        if (!this.initialized) {\n            return;\n        }\n        if (this.isEditing) {\n            this.initDelayedCursor();\n        }\n        this._clearCache();\n        // Clear dynamicMinWidth as it will be different after we re-wrap line\n        this.dynamicMinWidth = 0;\n\n        // Check if text contains Chinese characters\n        if (/[\\u3400-\\u9FBF]/.test(this.text)) {\n            this.splitByGrapheme = true;\n        }\n\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        // Calculate height based on wrapped text\n        const newHeight = this.calcTextHeight();\n        if (newHeight !== this.height) {\n            this.set('height', newHeight);\n            this.setCoords(); // Update coordinates after height change\n        }\n    }\n\n\n    /**\n     * Handler for width changes that maintains top-left position\n     */\n    handleWidthChange(eventData: any, transform: any, x: number, y: number) {\n        // Store original top-left position\n        const oldBoundingRect = this.getBoundingRect();\n\n        // Calculate new width based on mouse position\n        const localPoint = getLocalPoint(\n            transform,\n            transform.originX,\n            transform.originY,\n            x,\n            y\n        );\n\n        const strokePadding =\n            this.strokeWidth / (this.strokeUniform ? this.scaleX : 1);\n        const multiplier = isTransformCentered(transform) ? 2 : 1;\n        const oldWidth = this.width;\n\n        // Calculate and set new width\n        const newWidth =\n            Math.abs((localPoint.x * multiplier) / this.scaleX) - strokePadding;\n\n        // Record original left/top before width change\n        const originalLeft = this.left;\n        const originalTop = this.top;\n\n        // Set new width and update dimensions\n        this.set('width', Math.max(newWidth, this.getMinWidth()));\n\n        // Recalculate text dimensions and height\n        this.initDimensions();\n        this.set('dirty', true);\n\n        // After dimensions update, get new bounding rectangle\n        const newBoundingRect = this.getBoundingRect();\n\n        // Calculate position adjustment to keep top-left fixed\n        const dx = newBoundingRect.left - oldBoundingRect.left;\n        const dy = newBoundingRect.top - oldBoundingRect.top;\n\n        // Apply position adjustment\n        this.set({\n            left: originalLeft - dx,\n            top: originalTop - dy\n        });\n\n        // Update coordinates\n        this.setCoords();\n        this.handleWidthChange2(eventData, transform, x, y);\n\n        return oldWidth !== this.width;\n    }\n}\n\n// Register the XTextbox class with the class registry\nclassRegistry.setClass(XTextbox);\n// classRegistry.getSVGClass(Textbox); // Uncomment if SVG class registration is needed\n"],"names":["textboxDefaultValues","minWidth","dynamicMinWidth","splitByGrapheme","cornerColor","cornerSize","cornerStyle","transparentCorners","cornerStrokeColor","connectors","XTextbox","XTextbase","getDefaults","_objectSpread","controls","createTextboxDefaultControls","originX","originY","ownDefaults","constructor","text","options","initDimensions","height","Object","assign","objType","dirty","lockScalingFlip","lockRotation","setupCustomResizeControls","on","onEditingEntered","bind","onEditingExited","mr","actionHandler","handleWidthChange","ml","handleWidthChange2","eventData","transform","x","y","canvas","topLeft","getBoundingRect","getCenterPoint","set","left","top","setCoords","width","getObject","entityKeys","EntityKeys","result","forEach","key","initialized","isEditing","initDelayedCursor","_clearCache","test","_styleMap","_generateStyleMap","_splitText","textAlign","indexOf","enlargeSpaces","newHeight","calcTextHeight","oldBoundingRect","localPoint","getLocalPoint","strokePadding","strokeWidth","strokeUniform","scaleX","multiplier","isTransformCentered","oldWidth","newWidth","Math","abs","originalLeft","originalTop","max","getMinWidth","newBoundingRect","dx","dy","_defineProperty","IText","textLayoutProperties","classRegistry","setClass"],"mappings":"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"}