igniteui-webcomponents 7.2.2 → 7.2.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -2,17 +2,26 @@ import { type DatePart, DatePartType, type IDatePart } from '../date-time-input/
2
2
  import { type DateTimeMaskOptions } from '../date-time-input/datetime-mask-parser.js';
3
3
  import { MaskParser } from '../mask-input/mask-parser.js';
4
4
  import type { DateRangeValue } from '../types.js';
5
+ /**
6
+ * @ignore
7
+ */
5
8
  export interface DateRangePart {
6
9
  part: DatePart;
7
10
  position: DateRangePosition;
8
11
  }
9
- /** Position of a date part within the date range */
12
+ /**
13
+ * @ignore
14
+ * Position of a date part within the date range
15
+ */
10
16
  export declare enum DateRangePosition {
11
17
  Start = "start",
12
18
  End = "end",
13
19
  Separator = "separator"
14
20
  }
15
- /** Extended date part with range position information */
21
+ /**
22
+ * @ignore
23
+ * Extended date part with range position information
24
+ */
16
25
  export interface IDateRangePart extends IDatePart {
17
26
  position: DateRangePosition;
18
27
  }
@@ -1 +1 @@
1
- {"version":3,"file":"date-range-mask-parser.js","sourceRoot":"","sources":["../../../src/components/date-range-picker/date-range-mask-parser.ts"],"names":[],"mappings":"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","sourcesContent":["import {\n type DatePart,\n DatePartType,\n type IDatePart,\n type SpinOptions,\n} from '../date-time-input/date-part.js';\nimport {\n type DateTimeMaskOptions,\n DateTimeMaskParser,\n DEFAULT_DATETIME_FORMAT,\n} from '../date-time-input/datetime-mask-parser.js';\nimport { MaskParser } from '../mask-input/mask-parser.js';\nimport type { DateRangeValue } from '../types.js';\n\n//#region Types and Enums\n\nexport interface DateRangePart {\n part: DatePart;\n position: DateRangePosition;\n}\n\n/** Position of a date part within the date range */\nexport enum DateRangePosition {\n Start = 'start',\n End = 'end',\n Separator = 'separator',\n}\n\n/** Extended date part with range position information */\nexport interface IDateRangePart extends IDatePart {\n position: DateRangePosition;\n}\n\n/** Options for the DateRangeMaskParser */\nexport interface DateRangeMaskOptions extends DateTimeMaskOptions {\n /** Separator (defaults to ' - ') */\n separator?: string;\n}\n\n//#endregion\n\n//#region Constants\n\n/** Default separator between start and end dates */\nconst DEFAULT_SEPARATOR = ' - ';\n\n//#endregion\n\n/**\n * A specialized mask parser for date range input fields.\n * Uses composition with two DateTimeMaskParser instances to handle start and end dates.\n *\n * Accepts a single date format (e.g., 'MM/dd/yyyy') which creates two parsers\n * internally, one for the start date and one for the end date.\n *\n * @example\n * ```ts\n * const parser = new DateRangeMaskParser({ format: 'MM/dd/yyyy' });\n * parser.parseDateRange('12/25/2023 - 12/31/2023'); // Returns DateRangeValue\n * parser.formatDateRange({ start: date1, end: date2 }); // Returns formatted string\n * ```\n */\nexport class DateRangeMaskParser extends MaskParser {\n private _startParser: DateTimeMaskParser;\n private _endParser: DateTimeMaskParser;\n\n /** Cached date range parts with position information */\n private _rangeParts: IDateRangePart[] = [];\n\n /** The separator between start and end dates */\n private _separator: string;\n\n /** Start position of the separator in the mask */\n private _separatorStart: number;\n\n /** End position of the separator in the mask */\n private _separatorEnd: number;\n\n /**\n * Gets the parsed date range parts with position information.\n */\n public get rangeParts(): ReadonlyArray<IDateRangePart> {\n return this._rangeParts;\n }\n\n /**\n * Gets the separator string used between start and end dates.\n */\n public get separator(): string {\n return this._separator;\n }\n\n constructor(options?: DateRangeMaskOptions) {\n const format = options?.format || DEFAULT_DATETIME_FORMAT;\n const separator = options?.separator || DEFAULT_SEPARATOR;\n const promptCharacter = options?.promptCharacter;\n\n // Build the combined range format for the parent MaskParser\n const rangeFormat = `${format}${separator}${format}`;\n\n super(\n options?.promptCharacter\n ? { format: rangeFormat, promptCharacter: options.promptCharacter }\n : { format: rangeFormat }\n );\n\n // Create two parsers for start and end dates\n this._startParser = new DateTimeMaskParser({ format, promptCharacter });\n this._endParser = new DateTimeMaskParser({ format, promptCharacter });\n this._separator = separator;\n\n this._separatorStart = this._startParser.mask.length;\n this._separatorEnd = this._separatorStart + separator.length;\n\n this._buildRangeParts();\n }\n\n //#region Mask Format Conversion\n\n /**\n * Overrides base class to convert date format to mask format\n * before parsing literals. This ensures date format characters\n * (M, d, y, etc.) are properly converted to mask characters (0, L).\n */\n protected override _parseMaskLiterals(): void {\n // Convert the range format to mask format\n // e.g., \"M/d/yyyy - M/d/yyyy\" → \"0/0/0000 - 0/0/0000\"\n const dateFormat = this._options.format;\n const maskFormat =\n DateTimeMaskParser.convertDateFormatToMaskFormat(dateFormat);\n\n // Temporarily set the converted format for base class parsing\n const originalFormat = this._options.format;\n this._options.format = maskFormat;\n\n super._parseMaskLiterals();\n\n // Restore the original date format\n this._options.format = originalFormat;\n }\n\n //#endregion\n\n /**\n * Builds the range parts array by combining parts from start and end parsers\n * and adding position information.\n */\n private _buildRangeParts(): void {\n const startParts = this._startParser.dateParts.map(\n (part): IDateRangePart => ({\n ...part,\n position: DateRangePosition.Start,\n getValue: part.getValue.bind(part),\n validate: part.validate.bind(part),\n spin: part.spin.bind(part),\n })\n );\n\n const endParts = this._endParser.dateParts.map(\n (part): IDateRangePart => ({\n ...part,\n // Adjust positions for end date (offset by separator)\n start: part.start + this._separatorEnd,\n end: part.end + this._separatorEnd,\n position: DateRangePosition.End,\n getValue: part.getValue.bind(part),\n validate: part.validate.bind(part),\n spin: part.spin.bind(part),\n })\n );\n\n this._rangeParts = [...startParts, ...endParts];\n }\n\n /**\n * Sets a new date format and updates both parsers.\n */\n public override set mask(value: string) {\n this._startParser.mask = value;\n this._endParser.mask = value;\n\n this._separatorStart = this._startParser.mask.length;\n this._separatorEnd = this._separatorStart + this._separator.length;\n\n const rangeFormat = `${value}${this._separator}${value}`;\n super.mask = rangeFormat;\n\n this._buildRangeParts();\n }\n\n public override get mask(): string {\n return super.mask;\n }\n\n //#region Date Range Parsing\n\n /**\n * Parses a masked string into a DateRangeValue using the two internal parsers.\n * Returns null if the string cannot be parsed.\n */\n public parseDateRange(masked: string): DateRangeValue | null {\n if (!masked || masked === this.emptyMask) {\n return null;\n }\n\n const startString = masked.substring(0, this._separatorStart);\n const endString = masked.substring(this._separatorEnd);\n\n const start = this._startParser.parseDate(startString);\n const end = this._endParser.parseDate(endString);\n\n return { start, end };\n }\n\n //#endregion\n\n //#region Date Range Formatting\n\n /**\n * Formats a DateRangeValue into a masked string using the two internal parsers.\n */\n public formatDateRange(range: DateRangeValue | null): string {\n const startString = range?.start\n ? this._startParser.formatDate(range.start)\n : this._startParser.emptyMask;\n\n const endString = range?.end\n ? this._endParser.formatDate(range.end)\n : this._endParser.emptyMask;\n\n return startString + this._separator + endString;\n }\n\n //#endregion\n\n //#region Part Queries\n\n /**\n * Gets the date range part at a cursor position.\n * Uses exclusive end for precise character targeting.\n */\n public getDateRangePartAtPosition(\n position: number\n ): IDateRangePart | undefined {\n return this._rangeParts.find(\n (part) => position >= part.start && position < part.end\n );\n }\n\n /**\n * Gets the date range part for cursor (inclusive end).\n * Handles the edge case where cursor is at the end of the last part.\n */\n public getDateRangePartForCursor(\n position: number\n ): IDateRangePart | undefined {\n return this._rangeParts.find(\n (part) => position >= part.start && position <= part.end\n );\n }\n\n /**\n * Gets a specific part type for a position.\n */\n public getPartByTypeAndPosition(\n type: DatePartType,\n position: DateRangePosition\n ): IDateRangePart | undefined {\n return this._rangeParts.find(\n (p) => p.type === type && p.position === position\n );\n }\n\n /**\n * Gets the first non-literal date part for a position.\n */\n public getFirstDatePartForPosition(\n position: DateRangePosition\n ): IDateRangePart | undefined {\n return this._rangeParts.find(\n (p) => p.position === position && p.type !== DatePartType.Literal\n );\n }\n\n //#endregion\n\n //#region Spinning Support\n\n /**\n * Spins a date part within the range (for stepUp/stepDown functionality).\n * Delegates to the underlying date part's spin method.\n */\n public spinDateRangePart(\n part: IDateRangePart,\n delta: number,\n currentValue: DateRangeValue | null,\n spinLoop: boolean,\n amPmValue?: string\n ): DateRangeValue {\n const value = currentValue || { start: null, end: null };\n\n const targetDate =\n part.position === DateRangePosition.Start ? value.start : value.end;\n\n // If no date exists, create one with today's date\n const dateToSpin = targetDate || new Date();\n\n // Create a new date instance to spin\n const newDate = new Date(dateToSpin.getTime());\n\n // Spin using the part's built-in spin method\n const spinOptions: SpinOptions = {\n date: newDate,\n spinLoop,\n originalDate: dateToSpin,\n amPmValue,\n };\n\n part.spin(delta, spinOptions);\n\n return part.position === DateRangePosition.Start\n ? { ...value, start: newDate }\n : { ...value, end: newDate };\n }\n\n //#endregion\n}\n"]}
1
+ {"version":3,"file":"date-range-mask-parser.js","sourceRoot":"","sources":["../../../src/components/date-range-picker/date-range-mask-parser.ts"],"names":[],"mappings":"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","sourcesContent":["import {\n type DatePart,\n DatePartType,\n type IDatePart,\n type SpinOptions,\n} from '../date-time-input/date-part.js';\nimport {\n type DateTimeMaskOptions,\n DateTimeMaskParser,\n DEFAULT_DATETIME_FORMAT,\n} from '../date-time-input/datetime-mask-parser.js';\nimport { MaskParser } from '../mask-input/mask-parser.js';\nimport type { DateRangeValue } from '../types.js';\n\n//#region Types and Enums\n\n/**\n * @ignore\n */\nexport interface DateRangePart {\n part: DatePart;\n position: DateRangePosition;\n}\n\n/**\n * @ignore\n * Position of a date part within the date range\n */\nexport enum DateRangePosition {\n Start = 'start',\n End = 'end',\n Separator = 'separator',\n}\n\n/**\n * @ignore\n * Extended date part with range position information\n */\nexport interface IDateRangePart extends IDatePart {\n position: DateRangePosition;\n}\n\n/** Options for the DateRangeMaskParser */\nexport interface DateRangeMaskOptions extends DateTimeMaskOptions {\n /** Separator (defaults to ' - ') */\n separator?: string;\n}\n\n//#endregion\n\n//#region Constants\n\n/** Default separator between start and end dates */\nconst DEFAULT_SEPARATOR = ' - ';\n\n//#endregion\n\n/**\n * A specialized mask parser for date range input fields.\n * Uses composition with two DateTimeMaskParser instances to handle start and end dates.\n *\n * Accepts a single date format (e.g., 'MM/dd/yyyy') which creates two parsers\n * internally, one for the start date and one for the end date.\n *\n * @example\n * ```ts\n * const parser = new DateRangeMaskParser({ format: 'MM/dd/yyyy' });\n * parser.parseDateRange('12/25/2023 - 12/31/2023'); // Returns DateRangeValue\n * parser.formatDateRange({ start: date1, end: date2 }); // Returns formatted string\n * ```\n */\nexport class DateRangeMaskParser extends MaskParser {\n private _startParser: DateTimeMaskParser;\n private _endParser: DateTimeMaskParser;\n\n /** Cached date range parts with position information */\n private _rangeParts: IDateRangePart[] = [];\n\n /** The separator between start and end dates */\n private _separator: string;\n\n /** Start position of the separator in the mask */\n private _separatorStart: number;\n\n /** End position of the separator in the mask */\n private _separatorEnd: number;\n\n /**\n * Gets the parsed date range parts with position information.\n */\n public get rangeParts(): ReadonlyArray<IDateRangePart> {\n return this._rangeParts;\n }\n\n /**\n * Gets the separator string used between start and end dates.\n */\n public get separator(): string {\n return this._separator;\n }\n\n constructor(options?: DateRangeMaskOptions) {\n const format = options?.format || DEFAULT_DATETIME_FORMAT;\n const separator = options?.separator || DEFAULT_SEPARATOR;\n const promptCharacter = options?.promptCharacter;\n\n // Build the combined range format for the parent MaskParser\n const rangeFormat = `${format}${separator}${format}`;\n\n super(\n options?.promptCharacter\n ? { format: rangeFormat, promptCharacter: options.promptCharacter }\n : { format: rangeFormat }\n );\n\n // Create two parsers for start and end dates\n this._startParser = new DateTimeMaskParser({ format, promptCharacter });\n this._endParser = new DateTimeMaskParser({ format, promptCharacter });\n this._separator = separator;\n\n this._separatorStart = this._startParser.mask.length;\n this._separatorEnd = this._separatorStart + separator.length;\n\n this._buildRangeParts();\n }\n\n //#region Mask Format Conversion\n\n /**\n * Overrides base class to convert date format to mask format\n * before parsing literals. This ensures date format characters\n * (M, d, y, etc.) are properly converted to mask characters (0, L).\n */\n protected override _parseMaskLiterals(): void {\n // Convert the range format to mask format\n // e.g., \"M/d/yyyy - M/d/yyyy\" → \"0/0/0000 - 0/0/0000\"\n const dateFormat = this._options.format;\n const maskFormat =\n DateTimeMaskParser.convertDateFormatToMaskFormat(dateFormat);\n\n // Temporarily set the converted format for base class parsing\n const originalFormat = this._options.format;\n this._options.format = maskFormat;\n\n super._parseMaskLiterals();\n\n // Restore the original date format\n this._options.format = originalFormat;\n }\n\n //#endregion\n\n /**\n * Builds the range parts array by combining parts from start and end parsers\n * and adding position information.\n */\n private _buildRangeParts(): void {\n const startParts = this._startParser.dateParts.map(\n (part): IDateRangePart => ({\n ...part,\n position: DateRangePosition.Start,\n getValue: part.getValue.bind(part),\n validate: part.validate.bind(part),\n spin: part.spin.bind(part),\n })\n );\n\n const endParts = this._endParser.dateParts.map(\n (part): IDateRangePart => ({\n ...part,\n // Adjust positions for end date (offset by separator)\n start: part.start + this._separatorEnd,\n end: part.end + this._separatorEnd,\n position: DateRangePosition.End,\n getValue: part.getValue.bind(part),\n validate: part.validate.bind(part),\n spin: part.spin.bind(part),\n })\n );\n\n this._rangeParts = [...startParts, ...endParts];\n }\n\n /**\n * Sets a new date format and updates both parsers.\n */\n public override set mask(value: string) {\n this._startParser.mask = value;\n this._endParser.mask = value;\n\n this._separatorStart = this._startParser.mask.length;\n this._separatorEnd = this._separatorStart + this._separator.length;\n\n const rangeFormat = `${value}${this._separator}${value}`;\n super.mask = rangeFormat;\n\n this._buildRangeParts();\n }\n\n public override get mask(): string {\n return super.mask;\n }\n\n //#region Date Range Parsing\n\n /**\n * Parses a masked string into a DateRangeValue using the two internal parsers.\n * Returns null if the string cannot be parsed.\n */\n public parseDateRange(masked: string): DateRangeValue | null {\n if (!masked || masked === this.emptyMask) {\n return null;\n }\n\n const startString = masked.substring(0, this._separatorStart);\n const endString = masked.substring(this._separatorEnd);\n\n const start = this._startParser.parseDate(startString);\n const end = this._endParser.parseDate(endString);\n\n return { start, end };\n }\n\n //#endregion\n\n //#region Date Range Formatting\n\n /**\n * Formats a DateRangeValue into a masked string using the two internal parsers.\n */\n public formatDateRange(range: DateRangeValue | null): string {\n const startString = range?.start\n ? this._startParser.formatDate(range.start)\n : this._startParser.emptyMask;\n\n const endString = range?.end\n ? this._endParser.formatDate(range.end)\n : this._endParser.emptyMask;\n\n return startString + this._separator + endString;\n }\n\n //#endregion\n\n //#region Part Queries\n\n /**\n * Gets the date range part at a cursor position.\n * Uses exclusive end for precise character targeting.\n */\n public getDateRangePartAtPosition(\n position: number\n ): IDateRangePart | undefined {\n return this._rangeParts.find(\n (part) => position >= part.start && position < part.end\n );\n }\n\n /**\n * Gets the date range part for cursor (inclusive end).\n * Handles the edge case where cursor is at the end of the last part.\n */\n public getDateRangePartForCursor(\n position: number\n ): IDateRangePart | undefined {\n return this._rangeParts.find(\n (part) => position >= part.start && position <= part.end\n );\n }\n\n /**\n * Gets a specific part type for a position.\n */\n public getPartByTypeAndPosition(\n type: DatePartType,\n position: DateRangePosition\n ): IDateRangePart | undefined {\n return this._rangeParts.find(\n (p) => p.type === type && p.position === position\n );\n }\n\n /**\n * Gets the first non-literal date part for a position.\n */\n public getFirstDatePartForPosition(\n position: DateRangePosition\n ): IDateRangePart | undefined {\n return this._rangeParts.find(\n (p) => p.position === position && p.type !== DatePartType.Literal\n );\n }\n\n //#endregion\n\n //#region Spinning Support\n\n /**\n * Spins a date part within the range (for stepUp/stepDown functionality).\n * Delegates to the underlying date part's spin method.\n */\n public spinDateRangePart(\n part: IDateRangePart,\n delta: number,\n currentValue: DateRangeValue | null,\n spinLoop: boolean,\n amPmValue?: string\n ): DateRangeValue {\n const value = currentValue || { start: null, end: null };\n\n const targetDate =\n part.position === DateRangePosition.Start ? value.start : value.end;\n\n // If no date exists, create one with today's date\n const dateToSpin = targetDate || new Date();\n\n // Create a new date instance to spin\n const newDate = new Date(dateToSpin.getTime());\n\n // Spin using the part's built-in spin method\n const spinOptions: SpinOptions = {\n date: newDate,\n spinLoop,\n originalDate: dateToSpin,\n amPmValue,\n };\n\n part.spin(delta, spinOptions);\n\n return part.position === DateRangePosition.Start\n ? { ...value, start: newDate }\n : { ...value, end: newDate };\n }\n\n //#endregion\n}\n"]}
@@ -1 +1 @@
1
- {"version":3,"file":"date-part.js","sourceRoot":"","sources":["../../../src/components/date-time-input/date-part.ts"],"names":[],"mappings":"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","sourcesContent":["/**\n * Date Part Classes Module\n *\n * This module provides structured classes for date/time parts used in date-time input.\n * Each part type has its own class with specific validation and spin behavior.\n *\n * Classes are private to this module - only types and factory function are exported.\n */\n\n//#region Types and Enums\n\nexport enum DatePart {\n Month = 'month',\n Year = 'year',\n Date = 'date',\n Hours = 'hours',\n Minutes = 'minutes',\n Seconds = 'seconds',\n AmPm = 'amPm',\n}\n\n/** Types of date/time parts that can appear in a format string */\nexport const DatePartType = {\n Month: 'month',\n Year: 'year',\n Date: 'date',\n Hours: 'hours',\n Minutes: 'minutes',\n Seconds: 'seconds',\n AmPm: 'amPm',\n Literal: 'literal',\n} as const;\n\nexport type DatePartType = (typeof DatePartType)[keyof typeof DatePartType];\n\n// Spin delta defaults\nexport const DEFAULT_DATE_PARTS_SPIN_DELTAS = Object.freeze<DatePartDeltas>({\n date: 1,\n month: 1,\n year: 1,\n hours: 1,\n minutes: 1,\n seconds: 1,\n});\n\nexport interface DatePartDeltas {\n date?: number;\n month?: number;\n year?: number;\n hours?: number;\n minutes?: number;\n seconds?: number;\n}\n\n/** Options for creating a date part */\nexport interface DatePartOptions {\n /** Start position in the masked string */\n start: number;\n /** End position in the masked string */\n end: number;\n /** The format string for this part (e.g., 'MM', 'yyyy') */\n format: string;\n}\n\n/** Options for spin operations */\nexport interface SpinOptions {\n /** The current date value */\n date: Date;\n /** Whether to loop values at boundaries */\n spinLoop: boolean;\n /** For AM/PM: the current masked value to determine AM or PM */\n amPmValue?: string;\n /** For AM/PM: the original date (for rollover prevention) */\n originalDate?: Date;\n}\n\n/** Read-only interface for date part information */\nexport interface IDatePart {\n /** The type of date part */\n readonly type: DatePartType;\n /** Start position in the masked string */\n readonly start: number;\n /** End position in the masked string */\n readonly end: number;\n /** The format string for this part */\n readonly format: string;\n\n /**\n * Validates a numeric value for this part.\n * @param value - The value to validate\n * @param context - Optional context (year, month) for date-dependent validation\n * @returns true if the value is valid for this part\n */\n validate(value: number, context?: DateValidationContext): boolean;\n\n /**\n * Spins (increments/decrements) this part's value on the given date.\n * @param delta - The amount to spin (positive = up, negative = down)\n * @param options - Spin options including the date and loop behavior\n */\n spin(delta: number, options: SpinOptions): void;\n\n /**\n * Extracts the value of this part from a Date object.\n * @param date - The date to extract from\n * @returns The formatted string value\n */\n getValue(date: Date): string;\n}\n\n/** Context for date validation (needed for day-of-month validation) */\nexport interface DateValidationContext {\n year?: number;\n month?: number;\n}\n\n//#endregion\n\n//#region Constants\n\n/** Time bounds for validation */\nconst TIME_BOUNDS = {\n hours: { min: 0, max: 23 },\n minutes: { min: 0, max: 59 },\n seconds: { min: 0, max: 59 },\n} as const;\n\n/** Date bounds for validation */\nconst DATE_BOUNDS = {\n month: { min: 0, max: 11 },\n date: { min: 1, max: 31 },\n} as const;\n\n//#endregion\n\n//#region Helper Functions\n\n/**\n * Gets the number of days in a specific month/year.\n */\nfunction daysInMonth(year: number, month: number): number {\n return new Date(year, month + 1, 0).getDate();\n}\n\n/**\n * Pads a value with zeros to the specified length.\n */\nfunction padValue(value: string | number, length: number): string {\n return String(value).padStart(length, '0');\n}\n\n/**\n * Converts 24-hour format to 12-hour format.\n */\nfunction toTwelveHourFormat(hours: number): number {\n const h = hours % 12;\n return h === 0 ? 12 : h;\n}\n\n/**\n * Generic spin helper for time parts.\n */\nfunction spinTimePart(\n date: Date,\n delta: number,\n max: number,\n min: number,\n setter: (value: number) => number,\n getter: () => number,\n spinLoop: boolean\n): void {\n let value = getter.call(date) + delta;\n\n if (value > max) {\n value = spinLoop ? value % (max + 1) : max;\n } else if (value < min) {\n value = spinLoop ? max + 1 + (value % (max + 1)) : min;\n }\n\n setter.call(date, value);\n}\n\n//#endregion\n\n//#region Abstract Base Class\n\n/**\n * Abstract base class for all date parts.\n * Provides common functionality and defines the contract for concrete implementations.\n */\nabstract class DatePartBase implements IDatePart {\n readonly type: DatePartType;\n readonly start: number;\n readonly end: number;\n readonly format: string;\n\n constructor(type: DatePartType, options: DatePartOptions) {\n this.type = type;\n this.start = options.start;\n this.end = options.end;\n this.format = options.format;\n }\n\n abstract validate(value: number, context?: DateValidationContext): boolean;\n abstract spin(delta: number, options: SpinOptions): void;\n abstract getValue(date: Date): string;\n}\n\n//#endregion\n\n//#region Concrete Implementations\n\n/**\n * Year part (yyyy, yy)\n */\nclass YearPart extends DatePartBase {\n constructor(options: DatePartOptions) {\n super(DatePartType.Year, options);\n }\n\n validate(_value: number): boolean {\n // Years are always valid (no upper bound)\n return _value >= 0;\n }\n\n spin(delta: number, options: SpinOptions): void {\n const { date } = options;\n const maxDate = daysInMonth(date.getFullYear() + delta, date.getMonth());\n\n // Clip to max day to avoid leap year change shifting the entire value\n if (date.getDate() > maxDate) {\n date.setDate(maxDate);\n }\n\n date.setFullYear(date.getFullYear() + delta);\n }\n\n getValue(date: Date): string {\n const length = this.format.length;\n const year =\n length === 2\n ? date.getFullYear().toString().slice(-2)\n : date.getFullYear();\n return padValue(year, length);\n }\n}\n\n/**\n * Month part (MM, M)\n */\nclass MonthPart extends DatePartBase {\n constructor(options: DatePartOptions) {\n super(DatePartType.Month, options);\n }\n\n validate(value: number): boolean {\n // Month is 0-based internally, but 1-12 in display\n return value >= DATE_BOUNDS.month.min && value <= DATE_BOUNDS.month.max;\n }\n\n spin(delta: number, options: SpinOptions): void {\n const { date, spinLoop } = options;\n const { min, max } = DATE_BOUNDS.month;\n\n const maxDate = daysInMonth(date.getFullYear(), date.getMonth() + delta);\n if (date.getDate() > maxDate) {\n date.setDate(maxDate);\n }\n\n let month = date.getMonth() + delta;\n\n if (month > max) {\n month = spinLoop ? (month % max) - 1 : max;\n } else if (month < min) {\n month = spinLoop ? max + (month % max) + 1 : min;\n }\n\n date.setMonth(month);\n }\n\n getValue(date: Date): string {\n return padValue(date.getMonth() + 1, this.format.length);\n }\n}\n\n/**\n * Date (day of month) part (dd, d)\n */\nclass DateOfMonthPart extends DatePartBase {\n constructor(options: DatePartOptions) {\n super(DatePartType.Date, options);\n }\n\n validate(value: number, context?: DateValidationContext): boolean {\n if (value < DATE_BOUNDS.date.min) {\n return false;\n }\n\n if (context?.year !== undefined && context?.month !== undefined) {\n const maxDays = daysInMonth(context.year, context.month);\n return value <= maxDays;\n }\n\n return value <= DATE_BOUNDS.date.max;\n }\n\n spin(delta: number, options: SpinOptions): void {\n const { date, spinLoop } = options;\n const maxDate = daysInMonth(date.getFullYear(), date.getMonth());\n const { min } = DATE_BOUNDS.date;\n\n let dayOfMonth = date.getDate() + delta;\n\n if (dayOfMonth > maxDate) {\n dayOfMonth = spinLoop ? dayOfMonth % maxDate : maxDate;\n } else if (dayOfMonth < min) {\n dayOfMonth = spinLoop ? maxDate + (dayOfMonth % maxDate) : min;\n }\n\n date.setDate(dayOfMonth);\n }\n\n getValue(date: Date): string {\n return padValue(date.getDate(), this.format.length);\n }\n}\n\n/**\n * Hours part (HH, H, hh, h)\n */\nclass HoursPart extends DatePartBase {\n constructor(options: DatePartOptions) {\n super(DatePartType.Hours, options);\n }\n\n validate(value: number): boolean {\n return value >= TIME_BOUNDS.hours.min && value <= TIME_BOUNDS.hours.max;\n }\n\n spin(delta: number, options: SpinOptions): void {\n const { date, spinLoop } = options;\n const { min, max } = TIME_BOUNDS.hours;\n spinTimePart(date, delta, max, min, date.setHours, date.getHours, spinLoop);\n }\n\n getValue(date: Date): string {\n const isTwelveHour = this.format.includes('h');\n const hours = isTwelveHour\n ? toTwelveHourFormat(date.getHours())\n : date.getHours();\n return padValue(hours, this.format.length);\n }\n}\n\n/**\n * Minutes part (mm, m)\n */\nclass MinutesPart extends DatePartBase {\n constructor(options: DatePartOptions) {\n super(DatePartType.Minutes, options);\n }\n\n validate(value: number): boolean {\n return value >= TIME_BOUNDS.minutes.min && value <= TIME_BOUNDS.minutes.max;\n }\n\n spin(delta: number, options: SpinOptions): void {\n const { date, spinLoop } = options;\n const { min, max } = TIME_BOUNDS.minutes;\n spinTimePart(\n date,\n delta,\n max,\n min,\n date.setMinutes,\n date.getMinutes,\n spinLoop\n );\n }\n\n getValue(date: Date): string {\n return padValue(date.getMinutes(), this.format.length);\n }\n}\n\n/**\n * Seconds part (ss, s)\n */\nclass SecondsPart extends DatePartBase {\n constructor(options: DatePartOptions) {\n super(DatePartType.Seconds, options);\n }\n\n validate(value: number): boolean {\n return value >= TIME_BOUNDS.seconds.min && value <= TIME_BOUNDS.seconds.max;\n }\n\n spin(delta: number, options: SpinOptions): void {\n const { date, spinLoop } = options;\n const { min, max } = TIME_BOUNDS.seconds;\n spinTimePart(\n date,\n delta,\n max,\n min,\n date.setSeconds,\n date.getSeconds,\n spinLoop\n );\n }\n\n getValue(date: Date): string {\n return padValue(date.getSeconds(), this.format.length);\n }\n}\n\n/**\n * AM/PM part (tt, t)\n */\nclass AmPmPart extends DatePartBase {\n constructor(options: DatePartOptions) {\n super(DatePartType.AmPm, options);\n }\n\n validate(_value: number): boolean {\n // AM/PM doesn't have numeric validation\n return true;\n }\n\n spin(_delta: number, options: SpinOptions): void {\n const { date, amPmValue, originalDate } = options;\n\n if (!amPmValue) return;\n\n const isAM = amPmValue.toLowerCase() === 'am';\n const newHours = date.getHours() + (isAM ? 12 : -12);\n date.setHours(newHours);\n\n // Prevent date rollover\n if (originalDate && date.getDate() !== originalDate.getDate()) {\n date.setTime(originalDate.getTime());\n }\n }\n\n getValue(date: Date): string {\n return date.getHours() >= 12 ? 'PM' : 'AM';\n }\n}\n\n/**\n * Literal part (separators like /, -, :, space, etc.)\n */\nclass LiteralPart extends DatePartBase {\n constructor(options: DatePartOptions) {\n super(DatePartType.Literal, options);\n }\n\n validate(_value: number): boolean {\n // Literals don't have validation\n return true;\n }\n\n spin(_delta: number, _options: SpinOptions): void {\n // Literals can't be spun\n }\n\n getValue(_date: Date): string {\n return this.format;\n }\n}\n\n//#endregion\n\n//#region Factory Function\n\n/**\n * Creates a date part instance based on the type.\n * This is the only way to create date part instances outside this module.\n *\n * @param type - The type of date part to create\n * @param options - The options for the date part\n * @returns A date part instance implementing IDatePart\n */\nexport function createDatePart(\n type: DatePartType,\n options: DatePartOptions\n): IDatePart {\n switch (type) {\n case DatePartType.Year:\n return new YearPart(options);\n case DatePartType.Month:\n return new MonthPart(options);\n case DatePartType.Date:\n return new DateOfMonthPart(options);\n case DatePartType.Hours:\n return new HoursPart(options);\n case DatePartType.Minutes:\n return new MinutesPart(options);\n case DatePartType.Seconds:\n return new SecondsPart(options);\n case DatePartType.AmPm:\n return new AmPmPart(options);\n case DatePartType.Literal:\n return new LiteralPart(options);\n default:\n throw new Error(`Unknown date part type: ${type}`);\n }\n}\n\n//#endregion\n"]}
1
+ {"version":3,"file":"date-part.js","sourceRoot":"","sources":["../../../src/components/date-time-input/date-part.ts"],"names":[],"mappings":"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","sourcesContent":["/**\n * Date Part Classes Module\n *\n * This module provides structured classes for date/time parts used in date-time input.\n * Each part type has its own class with specific validation and spin behavior.\n *\n * Classes are private to this module - only types and factory function are exported.\n */\n\n//#region Types and Enums\n\nexport enum DatePart {\n Month = 'month',\n Year = 'year',\n Date = 'date',\n Hours = 'hours',\n Minutes = 'minutes',\n Seconds = 'seconds',\n AmPm = 'amPm',\n}\n\n/** Types of date/time parts that can appear in a format string */\nexport const DatePartType = {\n Month: 'month',\n Year: 'year',\n Date: 'date',\n Hours: 'hours',\n Minutes: 'minutes',\n Seconds: 'seconds',\n AmPm: 'amPm',\n Literal: 'literal',\n} as const;\n\nexport type DatePartType = (typeof DatePartType)[keyof typeof DatePartType];\n\n// Spin delta defaults\nexport const DEFAULT_DATE_PARTS_SPIN_DELTAS = Object.freeze<DatePartDeltas>({\n date: 1,\n month: 1,\n year: 1,\n hours: 1,\n minutes: 1,\n seconds: 1,\n});\n\nexport interface DatePartDeltas {\n date?: number;\n month?: number;\n year?: number;\n hours?: number;\n minutes?: number;\n seconds?: number;\n}\n\n/** Options for creating a date part */\nexport interface DatePartOptions {\n /** Start position in the masked string */\n start: number;\n /** End position in the masked string */\n end: number;\n /** The format string for this part (e.g., 'MM', 'yyyy') */\n format: string;\n}\n/* blazorSuppress */\n/** Options for spin operations */\nexport interface SpinOptions {\n /** The current date value */\n date: Date;\n /** Whether to loop values at boundaries */\n spinLoop: boolean;\n /** For AM/PM: the current masked value to determine AM or PM */\n amPmValue?: string;\n /** For AM/PM: the original date (for rollover prevention) */\n originalDate?: Date;\n}\n\n/** Read-only interface for date part information */\nexport interface IDatePart {\n /** The type of date part */\n readonly type: DatePartType;\n /** Start position in the masked string */\n readonly start: number;\n /** End position in the masked string */\n readonly end: number;\n /** The format string for this part */\n readonly format: string;\n\n /**\n * Validates a numeric value for this part.\n * @param value - The value to validate\n * @param context - Optional context (year, month) for date-dependent validation\n * @returns true if the value is valid for this part\n */\n validate(value: number, context?: DateValidationContext): boolean;\n\n /**\n * Spins (increments/decrements) this part's value on the given date.\n * @param delta - The amount to spin (positive = up, negative = down)\n * @param options - Spin options including the date and loop behavior\n */\n spin(delta: number, options: SpinOptions): void;\n\n /**\n * Extracts the value of this part from a Date object.\n * @param date - The date to extract from\n * @returns The formatted string value\n */\n getValue(date: Date): string;\n}\n\n/* blazorSuppress */\n/** Context for date validation (needed for day-of-month validation) */\nexport interface DateValidationContext {\n year?: number;\n month?: number;\n}\n\n//#endregion\n\n//#region Constants\n\n/** Time bounds for validation */\nconst TIME_BOUNDS = {\n hours: { min: 0, max: 23 },\n minutes: { min: 0, max: 59 },\n seconds: { min: 0, max: 59 },\n} as const;\n\n/** Date bounds for validation */\nconst DATE_BOUNDS = {\n month: { min: 0, max: 11 },\n date: { min: 1, max: 31 },\n} as const;\n\n//#endregion\n\n//#region Helper Functions\n\n/**\n * Gets the number of days in a specific month/year.\n */\nfunction daysInMonth(year: number, month: number): number {\n return new Date(year, month + 1, 0).getDate();\n}\n\n/**\n * Pads a value with zeros to the specified length.\n */\nfunction padValue(value: string | number, length: number): string {\n return String(value).padStart(length, '0');\n}\n\n/**\n * Converts 24-hour format to 12-hour format.\n */\nfunction toTwelveHourFormat(hours: number): number {\n const h = hours % 12;\n return h === 0 ? 12 : h;\n}\n\n/**\n * Generic spin helper for time parts.\n */\nfunction spinTimePart(\n date: Date,\n delta: number,\n max: number,\n min: number,\n setter: (value: number) => number,\n getter: () => number,\n spinLoop: boolean\n): void {\n let value = getter.call(date) + delta;\n\n if (value > max) {\n value = spinLoop ? value % (max + 1) : max;\n } else if (value < min) {\n value = spinLoop ? max + 1 + (value % (max + 1)) : min;\n }\n\n setter.call(date, value);\n}\n\n//#endregion\n\n//#region Abstract Base Class\n\n/**\n * Abstract base class for all date parts.\n * Provides common functionality and defines the contract for concrete implementations.\n */\nabstract class DatePartBase implements IDatePart {\n readonly type: DatePartType;\n readonly start: number;\n readonly end: number;\n readonly format: string;\n\n constructor(type: DatePartType, options: DatePartOptions) {\n this.type = type;\n this.start = options.start;\n this.end = options.end;\n this.format = options.format;\n }\n\n abstract validate(value: number, context?: DateValidationContext): boolean;\n abstract spin(delta: number, options: SpinOptions): void;\n abstract getValue(date: Date): string;\n}\n\n//#endregion\n\n//#region Concrete Implementations\n\n/**\n * Year part (yyyy, yy)\n */\nclass YearPart extends DatePartBase {\n constructor(options: DatePartOptions) {\n super(DatePartType.Year, options);\n }\n\n validate(_value: number): boolean {\n // Years are always valid (no upper bound)\n return _value >= 0;\n }\n\n spin(delta: number, options: SpinOptions): void {\n const { date } = options;\n const maxDate = daysInMonth(date.getFullYear() + delta, date.getMonth());\n\n // Clip to max day to avoid leap year change shifting the entire value\n if (date.getDate() > maxDate) {\n date.setDate(maxDate);\n }\n\n date.setFullYear(date.getFullYear() + delta);\n }\n\n getValue(date: Date): string {\n const length = this.format.length;\n const year =\n length === 2\n ? date.getFullYear().toString().slice(-2)\n : date.getFullYear();\n return padValue(year, length);\n }\n}\n\n/**\n * Month part (MM, M)\n */\nclass MonthPart extends DatePartBase {\n constructor(options: DatePartOptions) {\n super(DatePartType.Month, options);\n }\n\n validate(value: number): boolean {\n // Month is 0-based internally, but 1-12 in display\n return value >= DATE_BOUNDS.month.min && value <= DATE_BOUNDS.month.max;\n }\n\n spin(delta: number, options: SpinOptions): void {\n const { date, spinLoop } = options;\n const { min, max } = DATE_BOUNDS.month;\n\n const maxDate = daysInMonth(date.getFullYear(), date.getMonth() + delta);\n if (date.getDate() > maxDate) {\n date.setDate(maxDate);\n }\n\n let month = date.getMonth() + delta;\n\n if (month > max) {\n month = spinLoop ? (month % max) - 1 : max;\n } else if (month < min) {\n month = spinLoop ? max + (month % max) + 1 : min;\n }\n\n date.setMonth(month);\n }\n\n getValue(date: Date): string {\n return padValue(date.getMonth() + 1, this.format.length);\n }\n}\n\n/**\n * Date (day of month) part (dd, d)\n */\nclass DateOfMonthPart extends DatePartBase {\n constructor(options: DatePartOptions) {\n super(DatePartType.Date, options);\n }\n\n validate(value: number, context?: DateValidationContext): boolean {\n if (value < DATE_BOUNDS.date.min) {\n return false;\n }\n\n if (context?.year !== undefined && context?.month !== undefined) {\n const maxDays = daysInMonth(context.year, context.month);\n return value <= maxDays;\n }\n\n return value <= DATE_BOUNDS.date.max;\n }\n\n spin(delta: number, options: SpinOptions): void {\n const { date, spinLoop } = options;\n const maxDate = daysInMonth(date.getFullYear(), date.getMonth());\n const { min } = DATE_BOUNDS.date;\n\n let dayOfMonth = date.getDate() + delta;\n\n if (dayOfMonth > maxDate) {\n dayOfMonth = spinLoop ? dayOfMonth % maxDate : maxDate;\n } else if (dayOfMonth < min) {\n dayOfMonth = spinLoop ? maxDate + (dayOfMonth % maxDate) : min;\n }\n\n date.setDate(dayOfMonth);\n }\n\n getValue(date: Date): string {\n return padValue(date.getDate(), this.format.length);\n }\n}\n\n/**\n * Hours part (HH, H, hh, h)\n */\nclass HoursPart extends DatePartBase {\n constructor(options: DatePartOptions) {\n super(DatePartType.Hours, options);\n }\n\n validate(value: number): boolean {\n return value >= TIME_BOUNDS.hours.min && value <= TIME_BOUNDS.hours.max;\n }\n\n spin(delta: number, options: SpinOptions): void {\n const { date, spinLoop } = options;\n const { min, max } = TIME_BOUNDS.hours;\n spinTimePart(date, delta, max, min, date.setHours, date.getHours, spinLoop);\n }\n\n getValue(date: Date): string {\n const isTwelveHour = this.format.includes('h');\n const hours = isTwelveHour\n ? toTwelveHourFormat(date.getHours())\n : date.getHours();\n return padValue(hours, this.format.length);\n }\n}\n\n/**\n * Minutes part (mm, m)\n */\nclass MinutesPart extends DatePartBase {\n constructor(options: DatePartOptions) {\n super(DatePartType.Minutes, options);\n }\n\n validate(value: number): boolean {\n return value >= TIME_BOUNDS.minutes.min && value <= TIME_BOUNDS.minutes.max;\n }\n\n spin(delta: number, options: SpinOptions): void {\n const { date, spinLoop } = options;\n const { min, max } = TIME_BOUNDS.minutes;\n spinTimePart(\n date,\n delta,\n max,\n min,\n date.setMinutes,\n date.getMinutes,\n spinLoop\n );\n }\n\n getValue(date: Date): string {\n return padValue(date.getMinutes(), this.format.length);\n }\n}\n\n/**\n * Seconds part (ss, s)\n */\nclass SecondsPart extends DatePartBase {\n constructor(options: DatePartOptions) {\n super(DatePartType.Seconds, options);\n }\n\n validate(value: number): boolean {\n return value >= TIME_BOUNDS.seconds.min && value <= TIME_BOUNDS.seconds.max;\n }\n\n spin(delta: number, options: SpinOptions): void {\n const { date, spinLoop } = options;\n const { min, max } = TIME_BOUNDS.seconds;\n spinTimePart(\n date,\n delta,\n max,\n min,\n date.setSeconds,\n date.getSeconds,\n spinLoop\n );\n }\n\n getValue(date: Date): string {\n return padValue(date.getSeconds(), this.format.length);\n }\n}\n\n/**\n * AM/PM part (tt, t)\n */\nclass AmPmPart extends DatePartBase {\n constructor(options: DatePartOptions) {\n super(DatePartType.AmPm, options);\n }\n\n validate(_value: number): boolean {\n // AM/PM doesn't have numeric validation\n return true;\n }\n\n spin(_delta: number, options: SpinOptions): void {\n const { date, amPmValue, originalDate } = options;\n\n if (!amPmValue) return;\n\n const isAM = amPmValue.toLowerCase() === 'am';\n const newHours = date.getHours() + (isAM ? 12 : -12);\n date.setHours(newHours);\n\n // Prevent date rollover\n if (originalDate && date.getDate() !== originalDate.getDate()) {\n date.setTime(originalDate.getTime());\n }\n }\n\n getValue(date: Date): string {\n return date.getHours() >= 12 ? 'PM' : 'AM';\n }\n}\n\n/**\n * Literal part (separators like /, -, :, space, etc.)\n */\nclass LiteralPart extends DatePartBase {\n constructor(options: DatePartOptions) {\n super(DatePartType.Literal, options);\n }\n\n validate(_value: number): boolean {\n // Literals don't have validation\n return true;\n }\n\n spin(_delta: number, _options: SpinOptions): void {\n // Literals can't be spun\n }\n\n getValue(_date: Date): string {\n return this.format;\n }\n}\n\n//#endregion\n\n//#region Factory Function\n\n/**\n * Creates a date part instance based on the type.\n * This is the only way to create date part instances outside this module.\n *\n * @param type - The type of date part to create\n * @param options - The options for the date part\n * @returns A date part instance implementing IDatePart\n */\nexport function createDatePart(\n type: DatePartType,\n options: DatePartOptions\n): IDatePart {\n switch (type) {\n case DatePartType.Year:\n return new YearPart(options);\n case DatePartType.Month:\n return new MonthPart(options);\n case DatePartType.Date:\n return new DateOfMonthPart(options);\n case DatePartType.Hours:\n return new HoursPart(options);\n case DatePartType.Minutes:\n return new MinutesPart(options);\n case DatePartType.Seconds:\n return new SecondsPart(options);\n case DatePartType.AmPm:\n return new AmPmPart(options);\n case DatePartType.Literal:\n return new LiteralPart(options);\n default:\n throw new Error(`Unknown date part type: ${type}`);\n }\n}\n\n//#endregion\n"]}
@@ -18,6 +18,15 @@ export default class IgcPopoverComponent extends LitElement {
18
18
  static register(): void;
19
19
  private _dispose?;
20
20
  private _target?;
21
+ /**
22
+ * The positioning strategy resolved when the popover is opened. The `fixed`
23
+ * strategy is used when the anchor has a `position: sticky` ancestor, otherwise
24
+ * the default `absolute` strategy is used. Cached here to avoid repeated DOM
25
+ * traversals and style reflows on every scroll/resize reposition.
26
+ *
27
+ * Also, time to migrate to CSS Anchor positioning!!!
28
+ */
29
+ private _strategy;
21
30
  private readonly _slots;
22
31
  private readonly _container;
23
32
  /**
@@ -76,7 +85,7 @@ export default class IgcPopoverComponent extends LitElement {
76
85
  private _setPopoverState;
77
86
  private _setDispose;
78
87
  private _clearDispose;
79
- private _updateState;
88
+ private _resetAutoUpdate;
80
89
  private _createMiddleware;
81
90
  private _updatePosition;
82
91
  private _updateArrowPosition;
@@ -9,11 +9,24 @@ import { html, LitElement } from 'lit';
9
9
  import { property, query } from 'lit/decorators.js';
10
10
  import { addSlotController, setSlots, } from '../common/controllers/slot.js';
11
11
  import { registerComponent } from '../common/definitions/register.js';
12
- import { first, getElementByIdFromRoot, isString, roundByDPR, setStyles, } from '../common/util.js';
12
+ import { first, getElementByIdFromRoot, getRoot, isString, roundByDPR, setStyles, } from '../common/util.js';
13
13
  import { styles } from './themes/light/popover.base.css.js';
14
+ function hasStickyAncestor(element) {
15
+ let node = element;
16
+ while (node) {
17
+ if (getComputedStyle(node).position === 'sticky') {
18
+ return true;
19
+ }
20
+ const root = getRoot(node);
21
+ node =
22
+ node.parentElement ?? (root instanceof ShadowRoot ? root.host : null);
23
+ }
24
+ return false;
25
+ }
14
26
  export default class IgcPopoverComponent extends LitElement {
15
27
  constructor() {
16
28
  super(...arguments);
29
+ this._strategy = 'absolute';
17
30
  this._slots = addSlotController(this, {
18
31
  slots: setSlots('anchor'),
19
32
  onChange: this._handleSlotChange,
@@ -41,18 +54,22 @@ export default class IgcPopoverComponent extends LitElement {
41
54
  registerComponent(IgcPopoverComponent);
42
55
  }
43
56
  update(properties) {
57
+ let targetChanged = false;
44
58
  if (properties.has('anchor')) {
45
59
  const target = isString(this.anchor)
46
60
  ? getElementByIdFromRoot(this, this.anchor)
47
61
  : this.anchor;
48
62
  if (target) {
49
63
  this._target = target;
64
+ targetChanged = true;
50
65
  }
51
66
  }
52
67
  if (this.hasUpdated && properties.has('open')) {
53
68
  this._setOpenState(this.open);
54
69
  }
55
- this._updateState();
70
+ else if (this.hasUpdated && this.open) {
71
+ targetChanged ? this._resetAutoUpdate() : this._updatePosition();
72
+ }
56
73
  super.update(properties);
57
74
  }
58
75
  connectedCallback() {
@@ -74,7 +91,9 @@ export default class IgcPopoverComponent extends LitElement {
74
91
  return;
75
92
  }
76
93
  this._target = possibleTarget;
77
- this._updateState();
94
+ if (this.open) {
95
+ this._resetAutoUpdate();
96
+ }
78
97
  }
79
98
  _setOpenState(state) {
80
99
  state ? this._setDispose() : this._clearDispose();
@@ -90,20 +109,16 @@ export default class IgcPopoverComponent extends LitElement {
90
109
  if (!this._target) {
91
110
  return;
92
111
  }
112
+ this._strategy = hasStickyAncestor(this._target) ? 'fixed' : 'absolute';
93
113
  this._dispose = autoUpdate(this._target, this._container, this._updatePosition.bind(this));
94
114
  }
95
115
  _clearDispose() {
96
- return new Promise((resolve) => {
97
- this._dispose?.();
98
- this._dispose = undefined;
99
- resolve();
100
- });
116
+ this._dispose?.();
117
+ this._dispose = undefined;
101
118
  }
102
- async _updateState() {
103
- if (this.open) {
104
- await this._clearDispose();
105
- this._setDispose();
106
- }
119
+ _resetAutoUpdate() {
120
+ this._clearDispose();
121
+ this._setDispose();
107
122
  }
108
123
  _createMiddleware() {
109
124
  const middleware = [];
@@ -140,12 +155,14 @@ export default class IgcPopoverComponent extends LitElement {
140
155
  if (!(this.open && this._target)) {
141
156
  return;
142
157
  }
158
+ const strategy = this._strategy;
143
159
  const { x, y, middlewareData, placement } = await computePosition(this._target, this._container, {
144
160
  placement: this.placement ?? 'bottom-start',
145
161
  middleware: this._createMiddleware(),
146
- strategy: 'absolute',
162
+ strategy,
147
163
  });
148
164
  setStyles(this._container, {
165
+ position: strategy,
149
166
  left: '0',
150
167
  top: '0',
151
168
  transform: `translate(${roundByDPR(x)}px,${roundByDPR(y)}px)`,
@@ -1 +1 @@
1
- {"version":3,"file":"popover.js","sourceRoot":"","sources":["../../../src/components/popover/popover.ts"],"names":[],"mappings":"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","sourcesContent":["import {\n arrow,\n autoUpdate,\n computePosition,\n flip,\n inline,\n limitShift,\n type Middleware,\n type MiddlewareData,\n offset,\n type Placement,\n shift,\n size,\n} from '@floating-ui/dom';\nimport { html, LitElement, type PropertyValues } from 'lit';\nimport { property, query } from 'lit/decorators.js';\nimport {\n addSlotController,\n type SlotChangeCallbackParameters,\n setSlots,\n} from '../common/controllers/slot.js';\nimport { registerComponent } from '../common/definitions/register.js';\nimport {\n first,\n getElementByIdFromRoot,\n isString,\n roundByDPR,\n setStyles,\n} from '../common/util.js';\nimport { styles } from './themes/light/popover.base.css.js';\n\n/**\n * Describes the preferred placement of a toggle component.\n */\nexport type PopoverPlacement =\n | 'top'\n | 'top-start'\n | 'top-end'\n | 'bottom'\n | 'bottom-start'\n | 'bottom-end'\n | 'right'\n | 'right-start'\n | 'right-end'\n | 'left'\n | 'left-start'\n | 'left-end';\n\n/* blazorSuppress */\n/**\n * @element igc-popover\n *\n * @slot - Content of the popover.\n * @slot anchor - The element the popover will be anchored to.\n *\n * @csspart container - The container wrapping the slotted content in the popover.\n */\nexport default class IgcPopoverComponent extends LitElement {\n public static readonly tagName = 'igc-popover';\n public static override styles = styles;\n\n private static _oppositeArrowSide = new Map(\n Object.entries({\n top: 'bottom',\n right: 'left',\n bottom: 'top',\n left: 'right',\n })\n );\n\n /* blazorSuppress */\n public static register(): void {\n registerComponent(IgcPopoverComponent);\n }\n\n //#region Internal properties and state\n\n private _dispose?: ReturnType<typeof autoUpdate>;\n private _target?: Element;\n\n private readonly _slots = addSlotController(this, {\n slots: setSlots('anchor'),\n onChange: this._handleSlotChange,\n });\n\n @query('#container', true)\n private readonly _container!: HTMLElement;\n\n //#endregion\n\n //#region Public attributes and properties\n\n /**\n * Pass an IDREF or an DOM element reference to use as the\n * anchor target for the floating element.\n */\n @property()\n public anchor?: Element | string;\n\n /**\n * Element to render as an \"arrow\" element for the current popover.\n */\n @property({ attribute: false })\n public arrow: HTMLElement | null = null;\n\n /** Additional offset to apply to the arrow element if enabled. */\n @property({ type: Number, attribute: 'arrow-offset' })\n public arrowOffset = 0;\n\n /**\n * Improves positioning for inline reference elements that span over multiple lines.\n * Useful for tooltips or similar components.\n */\n @property({ type: Boolean, reflect: true })\n public inline = false;\n\n /**\n * When enabled this changes the placement of the floating element in order to keep it\n * in view along the main axis.\n */\n @property({ type: Boolean, reflect: true })\n public flip = false;\n\n /**\n * Placement modifier which translates the floating element along the main axis.\n */\n @property({ type: Number })\n public offset = 0;\n\n /**\n * The visibility state of the popover component.\n */\n @property({ type: Boolean, reflect: true })\n public open = false;\n\n /**\n * Where to place the floating element relative to the parent anchor element.\n */\n @property()\n public placement: PopoverPlacement = 'bottom-start';\n\n /**\n * When enabled the floating element will match the width of its parent anchor element.\n */\n @property({ type: Boolean, reflect: true, attribute: 'same-width' })\n public sameWidth = false;\n\n /**\n * When enabled this tries to shift the floating element along the main axis\n * keeping it in view, preventing overflow while maintaining the desired placement.\n */\n @property({ type: Boolean, reflect: true })\n public shift = false;\n\n /**\n * Virtual padding for the resolved overflow detection offsets in pixels.\n */\n @property({ type: Number, attribute: 'shift-padding' })\n public shiftPadding = 0;\n\n //#endregion\n\n //#region Life-cycle hooks\n\n protected override update(properties: PropertyValues<this>): void {\n if (properties.has('anchor')) {\n const target = isString(this.anchor)\n ? getElementByIdFromRoot(this, this.anchor)\n : this.anchor;\n\n if (target) {\n this._target = target;\n }\n }\n\n if (this.hasUpdated && properties.has('open')) {\n this._setOpenState(this.open);\n }\n\n this._updateState();\n super.update(properties);\n }\n\n /** @internal */\n public override connectedCallback(): void {\n super.connectedCallback();\n this.updateComplete.then(() => {\n this._setOpenState(this.open);\n });\n }\n\n /** @internal */\n public override disconnectedCallback(): void {\n super.disconnectedCallback();\n this._setOpenState(false);\n }\n\n //#endregion\n\n private _handleSlotChange({\n isDefault,\n }: SlotChangeCallbackParameters<unknown>): void {\n if (isDefault) {\n return;\n }\n\n const possibleTarget = first(\n this._slots.getAssignedElements('anchor', { flatten: true })\n );\n\n if (this.anchor || !possibleTarget) {\n return;\n }\n\n this._target = possibleTarget;\n this._updateState();\n }\n\n //#region Internal open state API\n private _setOpenState(state: boolean): void {\n state ? this._setDispose() : this._clearDispose();\n this._setPopoverState(state);\n }\n\n private _setPopoverState(open: boolean): void {\n if (!this._target) {\n return;\n }\n open ? this._container?.showPopover() : this._container?.hidePopover();\n }\n\n private _setDispose(): void {\n if (!this._target) {\n return;\n }\n\n this._dispose = autoUpdate(\n this._target,\n this._container,\n this._updatePosition.bind(this)\n );\n }\n\n private _clearDispose(): Promise<void> {\n return new Promise((resolve) => {\n this._dispose?.();\n this._dispose = undefined;\n resolve();\n });\n }\n\n private async _updateState(): Promise<void> {\n if (this.open) {\n await this._clearDispose();\n this._setDispose();\n }\n }\n\n //#endregion\n\n //#region Internal position API\n\n private _createMiddleware(): Middleware[] {\n const middleware: Middleware[] = [];\n const container = this._container;\n\n if (this.offset) {\n middleware.push(offset(this.offset));\n }\n\n if (this.inline) {\n middleware.push(inline());\n }\n\n if (this.shift) {\n middleware.push(\n shift({\n padding: this.shiftPadding,\n limiter: limitShift(),\n })\n );\n }\n\n if (this.arrow) {\n middleware.push(arrow({ element: this.arrow }));\n }\n\n if (this.flip) {\n middleware.push(flip());\n }\n\n if (this.sameWidth) {\n middleware.push(\n size({\n apply: ({ rects }) =>\n setStyles(container, { width: `${rects.reference.width}px` }),\n })\n );\n } else {\n setStyles(container, { width: '' });\n }\n\n return middleware;\n }\n\n private async _updatePosition(): Promise<void> {\n if (!(this.open && this._target)) {\n return;\n }\n\n const { x, y, middlewareData, placement } = await computePosition(\n this._target,\n this._container,\n {\n placement: this.placement ?? 'bottom-start',\n middleware: this._createMiddleware(),\n strategy: 'absolute',\n }\n );\n\n setStyles(this._container, {\n left: '0',\n top: '0',\n transform: `translate(${roundByDPR(x)}px,${roundByDPR(y)}px)`,\n });\n\n this._updateArrowPosition(placement, middlewareData);\n }\n\n private _updateArrowPosition(placement: Placement, data: MiddlewareData) {\n if (!(data.arrow && this.arrow)) {\n return;\n }\n\n const { x, y } = data.arrow;\n const arrow = this.arrow;\n const offset = this.arrowOffset;\n\n // The current placement of the popover along the x/y axis\n const currentPlacement = first(placement.split('-'));\n\n // The opposite side where the arrow element should render based on the `currentPlacement`\n const staticSide =\n IgcPopoverComponent._oppositeArrowSide.get(currentPlacement)!;\n\n arrow.part = currentPlacement;\n\n setStyles(arrow, {\n left: x != null ? `${roundByDPR(x + offset)}px` : '',\n top: y != null ? `${roundByDPR(y + offset)}px` : '',\n [staticSide]: '-4px',\n });\n }\n\n //#endregion\n\n protected override render() {\n return html`\n <slot name=\"anchor\"></slot>\n <div id=\"container\" part=\"container\" popover=\"manual\">\n <slot></slot>\n </div>\n `;\n }\n}\n\ndeclare global {\n interface HTMLElementTagNameMap {\n 'igc-popover': IgcPopoverComponent;\n }\n}\n"]}
1
+ {"version":3,"file":"popover.js","sourceRoot":"","sources":["../../../src/components/popover/popover.ts"],"names":[],"mappings":"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","sourcesContent":["import {\n arrow,\n autoUpdate,\n computePosition,\n flip,\n inline,\n limitShift,\n type Middleware,\n type MiddlewareData,\n offset,\n type Placement,\n shift,\n size,\n} from '@floating-ui/dom';\nimport { html, LitElement, type PropertyValues } from 'lit';\nimport { property, query } from 'lit/decorators.js';\nimport {\n addSlotController,\n type SlotChangeCallbackParameters,\n setSlots,\n} from '../common/controllers/slot.js';\nimport { registerComponent } from '../common/definitions/register.js';\nimport {\n first,\n getElementByIdFromRoot,\n getRoot,\n isString,\n roundByDPR,\n setStyles,\n} from '../common/util.js';\nimport { styles } from './themes/light/popover.base.css.js';\n\n/**\n * Describes the preferred placement of a toggle component.\n */\nexport type PopoverPlacement =\n | 'top'\n | 'top-start'\n | 'top-end'\n | 'bottom'\n | 'bottom-start'\n | 'bottom-end'\n | 'right'\n | 'right-start'\n | 'right-end'\n | 'left'\n | 'left-start'\n | 'left-end';\n\n/**\n * Walks up the DOM tree of the given element, crossing shadow boundaries, and\n * returns whether any ancestor is positioned as `sticky`.\n */\nfunction hasStickyAncestor(element: Element): boolean {\n let node: Element | null = element;\n\n while (node) {\n if (getComputedStyle(node).position === 'sticky') {\n return true;\n }\n\n const root = getRoot(node);\n node =\n node.parentElement ?? (root instanceof ShadowRoot ? root.host : null);\n }\n\n return false;\n}\n\n/* blazorSuppress */\n/**\n * @element igc-popover\n *\n * @slot - Content of the popover.\n * @slot anchor - The element the popover will be anchored to.\n *\n * @csspart container - The container wrapping the slotted content in the popover.\n */\nexport default class IgcPopoverComponent extends LitElement {\n public static readonly tagName = 'igc-popover';\n public static override styles = styles;\n\n private static _oppositeArrowSide = new Map(\n Object.entries({\n top: 'bottom',\n right: 'left',\n bottom: 'top',\n left: 'right',\n })\n );\n\n /* blazorSuppress */\n public static register(): void {\n registerComponent(IgcPopoverComponent);\n }\n\n //#region Internal properties and state\n\n private _dispose?: ReturnType<typeof autoUpdate>;\n private _target?: Element;\n\n /**\n * The positioning strategy resolved when the popover is opened. The `fixed`\n * strategy is used when the anchor has a `position: sticky` ancestor, otherwise\n * the default `absolute` strategy is used. Cached here to avoid repeated DOM\n * traversals and style reflows on every scroll/resize reposition.\n *\n * Also, time to migrate to CSS Anchor positioning!!!\n */\n private _strategy: 'absolute' | 'fixed' = 'absolute';\n\n private readonly _slots = addSlotController(this, {\n slots: setSlots('anchor'),\n onChange: this._handleSlotChange,\n });\n\n @query('#container', true)\n private readonly _container!: HTMLElement;\n\n //#endregion\n\n //#region Public attributes and properties\n\n /**\n * Pass an IDREF or an DOM element reference to use as the\n * anchor target for the floating element.\n */\n @property()\n public anchor?: Element | string;\n\n /**\n * Element to render as an \"arrow\" element for the current popover.\n */\n @property({ attribute: false })\n public arrow: HTMLElement | null = null;\n\n /** Additional offset to apply to the arrow element if enabled. */\n @property({ type: Number, attribute: 'arrow-offset' })\n public arrowOffset = 0;\n\n /**\n * Improves positioning for inline reference elements that span over multiple lines.\n * Useful for tooltips or similar components.\n */\n @property({ type: Boolean, reflect: true })\n public inline = false;\n\n /**\n * When enabled this changes the placement of the floating element in order to keep it\n * in view along the main axis.\n */\n @property({ type: Boolean, reflect: true })\n public flip = false;\n\n /**\n * Placement modifier which translates the floating element along the main axis.\n */\n @property({ type: Number })\n public offset = 0;\n\n /**\n * The visibility state of the popover component.\n */\n @property({ type: Boolean, reflect: true })\n public open = false;\n\n /**\n * Where to place the floating element relative to the parent anchor element.\n */\n @property()\n public placement: PopoverPlacement = 'bottom-start';\n\n /**\n * When enabled the floating element will match the width of its parent anchor element.\n */\n @property({ type: Boolean, reflect: true, attribute: 'same-width' })\n public sameWidth = false;\n\n /**\n * When enabled this tries to shift the floating element along the main axis\n * keeping it in view, preventing overflow while maintaining the desired placement.\n */\n @property({ type: Boolean, reflect: true })\n public shift = false;\n\n /**\n * Virtual padding for the resolved overflow detection offsets in pixels.\n */\n @property({ type: Number, attribute: 'shift-padding' })\n public shiftPadding = 0;\n\n //#endregion\n\n //#region Life-cycle hooks\n\n protected override update(properties: PropertyValues<this>): void {\n let targetChanged = false;\n\n if (properties.has('anchor')) {\n const target = isString(this.anchor)\n ? getElementByIdFromRoot(this, this.anchor)\n : this.anchor;\n\n if (target) {\n this._target = target;\n targetChanged = true;\n }\n }\n\n if (this.hasUpdated && properties.has('open')) {\n this._setOpenState(this.open);\n } else if (this.hasUpdated && this.open) {\n targetChanged ? this._resetAutoUpdate() : this._updatePosition();\n }\n\n super.update(properties);\n }\n\n /** @internal */\n public override connectedCallback(): void {\n super.connectedCallback();\n this.updateComplete.then(() => {\n this._setOpenState(this.open);\n });\n }\n\n /** @internal */\n public override disconnectedCallback(): void {\n super.disconnectedCallback();\n this._setOpenState(false);\n }\n\n //#endregion\n\n private _handleSlotChange({\n isDefault,\n }: SlotChangeCallbackParameters<unknown>): void {\n if (isDefault) {\n return;\n }\n\n const possibleTarget = first(\n this._slots.getAssignedElements('anchor', { flatten: true })\n );\n\n if (this.anchor || !possibleTarget) {\n return;\n }\n\n this._target = possibleTarget;\n\n if (this.open) {\n this._resetAutoUpdate();\n }\n }\n\n //#region Internal open state API\n private _setOpenState(state: boolean): void {\n state ? this._setDispose() : this._clearDispose();\n this._setPopoverState(state);\n }\n\n private _setPopoverState(open: boolean): void {\n if (!this._target) {\n return;\n }\n open ? this._container?.showPopover() : this._container?.hidePopover();\n }\n\n private _setDispose(): void {\n if (!this._target) {\n return;\n }\n\n this._strategy = hasStickyAncestor(this._target) ? 'fixed' : 'absolute';\n\n this._dispose = autoUpdate(\n this._target,\n this._container,\n this._updatePosition.bind(this)\n );\n }\n\n private _clearDispose(): void {\n this._dispose?.();\n this._dispose = undefined;\n }\n\n private _resetAutoUpdate(): void {\n this._clearDispose();\n this._setDispose();\n }\n //#endregion\n\n //#region Internal position API\n\n private _createMiddleware(): Middleware[] {\n const middleware: Middleware[] = [];\n const container = this._container;\n\n if (this.offset) {\n middleware.push(offset(this.offset));\n }\n\n if (this.inline) {\n middleware.push(inline());\n }\n\n if (this.shift) {\n middleware.push(\n shift({\n padding: this.shiftPadding,\n limiter: limitShift(),\n })\n );\n }\n\n if (this.arrow) {\n middleware.push(arrow({ element: this.arrow }));\n }\n\n if (this.flip) {\n middleware.push(flip());\n }\n\n if (this.sameWidth) {\n middleware.push(\n size({\n apply: ({ rects }) =>\n setStyles(container, { width: `${rects.reference.width}px` }),\n })\n );\n } else {\n setStyles(container, { width: '' });\n }\n\n return middleware;\n }\n\n private async _updatePosition(): Promise<void> {\n if (!(this.open && this._target)) {\n return;\n }\n\n const strategy = this._strategy;\n\n const { x, y, middlewareData, placement } = await computePosition(\n this._target,\n this._container,\n {\n placement: this.placement ?? 'bottom-start',\n middleware: this._createMiddleware(),\n strategy,\n }\n );\n\n setStyles(this._container, {\n position: strategy,\n left: '0',\n top: '0',\n transform: `translate(${roundByDPR(x)}px,${roundByDPR(y)}px)`,\n });\n\n this._updateArrowPosition(placement, middlewareData);\n }\n\n private _updateArrowPosition(placement: Placement, data: MiddlewareData) {\n if (!(data.arrow && this.arrow)) {\n return;\n }\n\n const { x, y } = data.arrow;\n const arrow = this.arrow;\n const offset = this.arrowOffset;\n\n // The current placement of the popover along the x/y axis\n const currentPlacement = first(placement.split('-'));\n\n // The opposite side where the arrow element should render based on the `currentPlacement`\n const staticSide =\n IgcPopoverComponent._oppositeArrowSide.get(currentPlacement)!;\n\n arrow.part = currentPlacement;\n\n setStyles(arrow, {\n left: x != null ? `${roundByDPR(x + offset)}px` : '',\n top: y != null ? `${roundByDPR(y + offset)}px` : '',\n [staticSide]: '-4px',\n });\n }\n\n //#endregion\n\n protected override render() {\n return html`\n <slot name=\"anchor\"></slot>\n <div id=\"container\" part=\"container\" popover=\"manual\">\n <slot></slot>\n </div>\n `;\n }\n}\n\ndeclare global {\n interface HTMLElementTagNameMap {\n 'igc-popover': IgcPopoverComponent;\n }\n}\n"]}
@@ -1,3 +1,3 @@
1
1
  import { css } from 'lit';
2
- export const styles = css `:host{--is-large: clamp(0, (var(--component-size, 1) + 1) - var(--ig-size-large, 3), 1);--is-medium: min( clamp(0, (var(--component-size, 1) + 1) - var(--ig-size-medium, 2), 1), clamp(0, var(--ig-size-large, 3) - var(--component-size, 1), 1) );--is-small: clamp(0, var(--ig-size-medium) - var(--component-size, 1), 1);position:relative;box-sizing:border-box;scrollbar-width:var(--ig-scrollbar-size, var(--sb-size));scrollbar-color:var(--ig-scrollbar-thumb-background, var(--sb-thumb-bg-color)) var(--ig-scrollbar-track-background, var(--sb-track-bg-color))}:host ::-webkit-scrollbar{width:var(--ig-scrollbar-size, var(--sb-size));height:var(--ig-scrollbar-size, var(--sb-size));background:var(--ig-scrollbar-track-background, var(--sb-track-bg-color))}:host ::-webkit-scrollbar-thumb{background:var(--ig-scrollbar-thumb-background, var(--sb-thumb-bg-color))}:host *,:host *::before,:host *::after{box-sizing:border-box}:host([hidden]),[hidden]{display:none !important}:host{display:contents}:popover-open{position:absolute;overflow:visible;isolation:isolate;height:-moz-fit-content;height:fit-content;inset:unset;border:none;padding:0;background:rgba(0,0,0,0)}`;
2
+ export const styles = css `:host{--is-large: clamp(0, (var(--component-size, 1) + 1) - var(--ig-size-large, 3), 1);--is-medium: min( clamp(0, (var(--component-size, 1) + 1) - var(--ig-size-medium, 2), 1), clamp(0, var(--ig-size-large, 3) - var(--component-size, 1), 1) );--is-small: clamp(0, var(--ig-size-medium) - var(--component-size, 1), 1);position:relative;box-sizing:border-box;scrollbar-width:var(--ig-scrollbar-size, var(--sb-size));scrollbar-color:var(--ig-scrollbar-thumb-background, var(--sb-thumb-bg-color)) var(--ig-scrollbar-track-background, var(--sb-track-bg-color))}:host ::-webkit-scrollbar{width:var(--ig-scrollbar-size, var(--sb-size));height:var(--ig-scrollbar-size, var(--sb-size));background:var(--ig-scrollbar-track-background, var(--sb-track-bg-color))}:host ::-webkit-scrollbar-thumb{background:var(--ig-scrollbar-thumb-background, var(--sb-thumb-bg-color))}:host *,:host *::before,:host *::after{box-sizing:border-box}:host([hidden]),[hidden]{display:none !important}:host{display:contents}:popover-open{overflow:visible;isolation:isolate;height:-moz-fit-content;height:fit-content;inset:unset;border:none;padding:0;background:rgba(0,0,0,0)}`;
3
3
  //# sourceMappingURL=popover.base.css.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"popover.base.css.js","sourceRoot":"","sources":["../../../../../src/components/popover/themes/light/popover.base.css.ts"],"names":[],"mappings":"AACE,OAAO,EAAE,GAAG,EAAE,MAAM,KAAK,CAAC;AAC1B,MAAM,CAAC,MAAM,MAAM,GAAG,GAAG,CAAA,0oCAA0oC,CAAC","sourcesContent":["\n import { css } from 'lit';\n export const styles = css`:host{--is-large: clamp(0, (var(--component-size, 1) + 1) - var(--ig-size-large, 3), 1);--is-medium: min( clamp(0, (var(--component-size, 1) + 1) - var(--ig-size-medium, 2), 1), clamp(0, var(--ig-size-large, 3) - var(--component-size, 1), 1) );--is-small: clamp(0, var(--ig-size-medium) - var(--component-size, 1), 1);position:relative;box-sizing:border-box;scrollbar-width:var(--ig-scrollbar-size, var(--sb-size));scrollbar-color:var(--ig-scrollbar-thumb-background, var(--sb-thumb-bg-color)) var(--ig-scrollbar-track-background, var(--sb-track-bg-color))}:host ::-webkit-scrollbar{width:var(--ig-scrollbar-size, var(--sb-size));height:var(--ig-scrollbar-size, var(--sb-size));background:var(--ig-scrollbar-track-background, var(--sb-track-bg-color))}:host ::-webkit-scrollbar-thumb{background:var(--ig-scrollbar-thumb-background, var(--sb-thumb-bg-color))}:host *,:host *::before,:host *::after{box-sizing:border-box}:host([hidden]),[hidden]{display:none !important}:host{display:contents}:popover-open{position:absolute;overflow:visible;isolation:isolate;height:-moz-fit-content;height:fit-content;inset:unset;border:none;padding:0;background:rgba(0,0,0,0)}`;\n "]}
1
+ {"version":3,"file":"popover.base.css.js","sourceRoot":"","sources":["../../../../../src/components/popover/themes/light/popover.base.css.ts"],"names":[],"mappings":"AACE,OAAO,EAAE,GAAG,EAAE,MAAM,KAAK,CAAC;AAC1B,MAAM,CAAC,MAAM,MAAM,GAAG,GAAG,CAAA,wnCAAwnC,CAAC","sourcesContent":["\n import { css } from 'lit';\n export const styles = css`:host{--is-large: clamp(0, (var(--component-size, 1) + 1) - var(--ig-size-large, 3), 1);--is-medium: min( clamp(0, (var(--component-size, 1) + 1) - var(--ig-size-medium, 2), 1), clamp(0, var(--ig-size-large, 3) - var(--component-size, 1), 1) );--is-small: clamp(0, var(--ig-size-medium) - var(--component-size, 1), 1);position:relative;box-sizing:border-box;scrollbar-width:var(--ig-scrollbar-size, var(--sb-size));scrollbar-color:var(--ig-scrollbar-thumb-background, var(--sb-thumb-bg-color)) var(--ig-scrollbar-track-background, var(--sb-track-bg-color))}:host ::-webkit-scrollbar{width:var(--ig-scrollbar-size, var(--sb-size));height:var(--ig-scrollbar-size, var(--sb-size));background:var(--ig-scrollbar-track-background, var(--sb-track-bg-color))}:host ::-webkit-scrollbar-thumb{background:var(--ig-scrollbar-thumb-background, var(--sb-thumb-bg-color))}:host *,:host *::before,:host *::after{box-sizing:border-box}:host([hidden]),[hidden]{display:none !important}:host{display:contents}:popover-open{overflow:visible;isolation:isolate;height:-moz-fit-content;height:fit-content;inset:unset;border:none;padding:0;background:rgba(0,0,0,0)}`;\n "]}
@@ -86,6 +86,17 @@ export default class IgcTileManagerComponent extends LitElement {
86
86
  protected updated(): void;
87
87
  protected firstUpdated(): void;
88
88
  private _observerCallback;
89
+ /**
90
+ * Locks/unlocks the grid container height in response to a tile's maximized state changing.
91
+ *
92
+ * @remarks
93
+ * Maximizing a tile removes it from the grid flow (absolute positioning), so it no longer
94
+ * contributes to the grid's intrinsic height. When that tile is the sole contributor to the
95
+ * tallest row track, the container would otherwise collapse to the remaining tiles and cut off
96
+ * the maximized tile's content. Capturing the current height before the layout change keeps the
97
+ * container stable, and it is released once no tile remains maximized.
98
+ */
99
+ private _setMaximizedState;
89
100
  /**
90
101
  * Returns the properties of the current tile collections as a JSON payload.
91
102
  *
@@ -34,6 +34,7 @@ let IgcTileManagerComponent = class IgcTileManagerComponent extends LitElement {
34
34
  return {
35
35
  instance: this,
36
36
  grid: this._grid,
37
+ setMaximizedState: () => this._setMaximizedState(),
37
38
  };
38
39
  }
39
40
  _setManagerContext() {
@@ -133,6 +134,20 @@ let IgcTileManagerComponent = class IgcTileManagerComponent extends LitElement {
133
134
  }
134
135
  this._tilesState.assignTiles();
135
136
  }
137
+ _setMaximizedState() {
138
+ const grid = this._grid.value;
139
+ if (grid) {
140
+ if (this.tiles.some((tile) => tile.maximized)) {
141
+ if (!grid.style.minHeight) {
142
+ grid.style.minHeight = `${grid.offsetHeight}px`;
143
+ }
144
+ }
145
+ else {
146
+ grid.style.minHeight = '';
147
+ }
148
+ }
149
+ this.requestUpdate();
150
+ }
136
151
  saveLayout() {
137
152
  return this._serializer.saveAsJSON();
138
153
  }
@@ -1 +1 @@
1
- {"version":3,"file":"tile-manager.js","sourceRoot":"","sources":["../../../src/components/tile-manager/tile-manager.ts"],"names":[],"mappings":";;;;;;;AAAA,OAAO,EAAE,eAAe,EAAE,MAAM,cAAc,CAAC;AAC/C,OAAO,EAAE,IAAI,EAAE,UAAU,EAAE,MAAM,KAAK,CAAC;AACvC,OAAO,EAAE,QAAQ,EAAE,MAAM,mBAAmB,CAAC;AAC7C,OAAO,EAAE,SAAS,EAAE,GAAG,EAAE,MAAM,uBAAuB,CAAC;AACvD,OAAO,EAAkB,QAAQ,EAAE,MAAM,6BAA6B,CAAC;AACvE,OAAO,EAAE,oBAAoB,EAAE,MAAM,qCAAqC,CAAC;AAC3E,OAAO,EAEL,kBAAkB,GACnB,MAAM,sBAAsB,CAAC;AAC9B,OAAO,EACL,wBAAwB,GAEzB,MAAM,4CAA4C,CAAC;AACpD,OAAO,EAAE,aAAa,EAAE,MAAM,wCAAwC,CAAC;AACvE,OAAO,EAAE,iBAAiB,EAAE,MAAM,mCAAmC,CAAC;AACtE,OAAO,EAAE,OAAO,EAAE,MAAM,uBAAuB,CAAC;AAChD,OAAO,EAAE,QAAQ,EAAE,MAAM,mBAAmB,CAAC;AAE7C,OAAO,EAAE,gBAAgB,EAAE,MAAM,eAAe,CAAC;AACjD,OAAO,EAAE,gBAAgB,EAAE,MAAM,iBAAiB,CAAC;AACnD,OAAO,EAAE,GAAG,EAAE,MAAM,uBAAuB,CAAC;AAC5C,OAAO,EAAE,MAAM,IAAI,MAAM,EAAE,MAAM,4CAA4C,CAAC;AAC9E,OAAO,EAAE,MAAM,EAAE,MAAM,mCAAmC,CAAC;AAC3D,OAAO,gBAAgB,MAAM,WAAW,CAAC;AAmB1B,IAAM,uBAAuB,GAA7B,MAAM,uBAAwB,SAAQ,UAAU;;aACtC,YAAO,GAAG,kBAAkB,AAArB,CAAsB;aAC7B,WAAM,GAAG,CAAC,MAAM,EAAE,MAAM,CAAC,AAAnB,CAAoB;IAG1C,MAAM,CAAC,QAAQ;QACpB,iBAAiB,CAAC,yBAAuB,EAAE,gBAAgB,CAAC,CAAC;IAC/D,CAAC;IA0BO,cAAc;QACpB,OAAO;YACL,QAAQ,EAAE,IAAI;YACd,IAAI,EAAE,IAAI,CAAC,KAAK;SACjB,CAAC;IACJ,CAAC;IAEO,kBAAkB;QACxB,IAAI,CAAC,QAAQ,CAAC,QAAQ,CAAC,IAAI,CAAC,cAAc,EAAE,EAAE,IAAI,CAAC,CAAC;IACtD,CAAC;IAaD,IAAW,UAAU,CAAC,KAA4B;QAChD,IAAI,CAAC,WAAW,GAAG,KAAK,CAAC;QACzB,IAAI,CAAC,kBAAkB,EAAE,CAAC;IAC5B,CAAC;IAED,IAAW,UAAU;QACnB,OAAO,IAAI,CAAC,WAAW,CAAC;IAC1B,CAAC;IASD,IAAW,QAAQ,CAAC,KAA0B;QAC5C,IAAI,CAAC,SAAS,GAAG,KAAK,CAAC;QACvB,IAAI,CAAC,kBAAkB,EAAE,CAAC;IAC5B,CAAC;IAED,IAAW,QAAQ;QACjB,OAAO,IAAI,CAAC,SAAS,CAAC;IACxB,CAAC;IAUD,IAAW,WAAW,CAAC,KAAa;QAClC,IAAI,CAAC,YAAY,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,QAAQ,CAAC,KAAK,CAAC,CAAC,CAAC;QACjD,MAAM,CAAC,MAAM,CAAC,IAAI,CAAC,eAAe,EAAE;YAClC,gBAAgB,EAAE,IAAI,CAAC,YAAY,IAAI,SAAS;SACjD,CAAC,CAAC;IACL,CAAC;IAED,IAAW,WAAW;QACpB,OAAO,IAAI,CAAC,YAAY,CAAC;IAC3B,CAAC;IAOD,IAAW,cAAc,CAAC,KAAyB;QACjD,IAAI,CAAC,YAAY,GAAG,KAAK,IAAI,SAAS,CAAC;QACvC,MAAM,CAAC,MAAM,CAAC,IAAI,CAAC,eAAe,EAAE;YAClC,iBAAiB,EAAE,IAAI,CAAC,YAAY;SACrC,CAAC,CAAC;IACL,CAAC;IAED,IAAW,cAAc;QACvB,OAAO,IAAI,CAAC,YAAY,CAAC;IAC3B,CAAC;IAOD,IAAW,YAAY,CAAC,KAAyB;QAC/C,IAAI,CAAC,aAAa,GAAG,KAAK,IAAI,SAAS,CAAC;QACxC,MAAM,CAAC,MAAM,CAAC,IAAI,CAAC,eAAe,EAAE;YAClC,kBAAkB,EAAE,IAAI,CAAC,aAAa;SACvC,CAAC,CAAC;IACL,CAAC;IAED,IAAW,YAAY;QACrB,OAAO,IAAI,CAAC,aAAa,CAAC;IAC5B,CAAC;IAQD,IAAW,GAAG,CAAC,KAAyB;QACtC,IAAI,CAAC,IAAI,GAAG,KAAK,IAAI,SAAS,CAAC;QAC/B,MAAM,CAAC,MAAM,CAAC,IAAI,CAAC,eAAe,EAAE;YAClC,YAAY,EAAE,IAAI,CAAC,IAAI;SACxB,CAAC,CAAC;IACL,CAAC;IAED,IAAW,GAAG;QACZ,OAAO,IAAI,CAAC,IAAI,CAAC;IACnB,CAAC;IAMD,IAAW,KAAK;QACd,OAAO,IAAI,CAAC,WAAW,CAAC,KAAK,CAAC;IAChC,CAAC;IAMD;QACE,KAAK,EAAE,CAAC;QAtJF,oBAAe,GAAc,EAAE,CAAC;QAChC,cAAS,GAAwB,MAAM,CAAC;QACxC,gBAAW,GAA0B,MAAM,CAAC;QAC5C,iBAAY,GAAG,CAAC,CAAC;QAKjB,gBAAW,GAAG,gBAAgB,CAAC,IAAI,CAAC,CAAC;QACrC,gBAAW,GAAG,gBAAgB,CAAC,IAAI,CAAC,CAAC;QAErC,UAAK,GAAG,SAAS,EAAe,CAAC;QAMjC,aAAQ,GAAG,IAAI,eAAe,CAAC,IAAI,EAAE;YAC3C,OAAO,EAAE,kBAAkB;YAC3B,YAAY,EAAE,IAAI,CAAC,cAAc,EAAE;SACpC,CAAC,CAAC;QAoID,oBAAoB,CAAC,IAAI,EAAE,GAAG,CAAC,CAAC;QAEhC,wBAAwB,CAAC,IAAI,EAAE;YAC7B,QAAQ,EAAE,IAAI,CAAC,iBAAiB;YAChC,MAAM,EAAE,CAAC,gBAAgB,CAAC,OAAO,CAAC;YAClC,MAAM,EAAE;gBACN,SAAS,EAAE,IAAI;aAChB;SACF,CAAC,CAAC;IACL,CAAC;IAEkB,OAAO;QACxB,IAAI,CAAC,WAAW,CAAC,sBAAsB,EAAE,CAAC;IAC5C,CAAC;IAEkB,YAAY;QAC7B,IAAI,CAAC,WAAW,CAAC,eAAe,EAAE,CAAC;QACnC,IAAI,CAAC,WAAW,CAAC,WAAW,EAAE,CAAC;QAC/B,IAAI,CAAC,kBAAkB,EAAE,CAAC;IAC5B,CAAC;IAEO,iBAAiB,CAAC,EACxB,OAAO,EAAE,EAAE,KAAK,EAAE,OAAO,EAAE,GACgB;QAC3C,MAAM,QAAQ,GAAG,KAAK,CAAC,MAAM,CAC3B,CAAC,EAAE,MAAM,EAAE,EAAE,EAAE,CAAC,MAAM,CAAC,OAAO,CAAC,IAAI,CAAC,OAAO,CAAC,KAAK,IAAI,CACtD,CAAC;QACF,MAAM,UAAU,GAAG,OAAO,CAAC,MAAM,CAC/B,CAAC,EAAE,MAAM,EAAE,EAAE,EAAE,CAAC,MAAM,CAAC,OAAO,CAAC,IAAI,CAAC,OAAO,CAAC,KAAK,IAAI,CACtD,CAAC;QAEF,KAAK,MAAM,MAAM,IAAI,UAAU,EAAE,CAAC;YAChC,IAAI,CAAC,WAAW,CAAC,MAAM,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC;QACvC,CAAC;QAED,KAAK,MAAM,KAAK,IAAI,QAAQ,EAAE,CAAC;YAC7B,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC;QACnC,CAAC;QAED,IAAI,CAAC,WAAW,CAAC,WAAW,EAAE,CAAC;IACjC,CAAC;IAaM,UAAU;QACf,OAAO,IAAI,CAAC,WAAW,CAAC,UAAU,EAAE,CAAC;IACvC,CAAC;IAKM,UAAU,CAAC,IAAY;QAC5B,IAAI,CAAC,WAAW,CAAC,YAAY,CAAC,IAAI,CAAC,CAAC;IACtC,CAAC;IAMkB,MAAM;QACvB,MAAM,KAAK,GAAG;YACZ,IAAI,EAAE,IAAI;YACV,gBAAgB,EAAE,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,IAAI,CAAC,SAAS,CAAC;SAC5D,CAAC;QAEF,OAAO,IAAI,CAAA;;UAEL,GAAG,CAAC,IAAI,CAAC,KAAK,CAAC;gBACT,QAAQ,CAAC,IAAI,CAAC,eAAe,CAAC;eAC/B,OAAO,CAAC,KAAK,CAAC;;;;KAIxB,CAAC;IACJ,CAAC;;AA/LD;IADC,QAAQ,CAAC,EAAE,SAAS,EAAE,aAAa,EAAE,CAAC;yDAItC;AAaD;IADC,QAAQ,CAAC,EAAE,SAAS,EAAE,WAAW,EAAE,CAAC;uDAIpC;AAcD;IADC,QAAQ,CAAC,EAAE,IAAI,EAAE,MAAM,EAAE,SAAS,EAAE,cAAc,EAAE,CAAC;0DAMrD;AAWD;IADC,QAAQ,CAAC,EAAE,SAAS,EAAE,kBAAkB,EAAE,CAAC;6DAM3C;AAWD;IADC,QAAQ,CAAC,EAAE,SAAS,EAAE,gBAAgB,EAAE,CAAC;2DAMzC;AAYD;IADC,QAAQ,EAAE;kDAMV;AA9IkB,uBAAuB;IAD3C,aAAa,CAAC,EAAE,cAAc,EAAE,QAAQ,EAAE,CAAC;GACvB,uBAAuB,CAyP3C;eAzPoB,uBAAuB","sourcesContent":["import { ContextProvider } from '@lit/context';\nimport { html, LitElement } from 'lit';\nimport { property } from 'lit/decorators.js';\nimport { createRef, ref } from 'lit/directives/ref.js';\nimport { type StyleInfo, styleMap } from 'lit/directives/style-map.js';\nimport { addThemingController } from '../../theming/theming-controller.js';\nimport {\n type TileManagerContext,\n tileManagerContext,\n} from '../common/context.js';\nimport {\n createMutationController,\n type MutationControllerParams,\n} from '../common/controllers/mutation-observer.js';\nimport { shadowOptions } from '../common/decorators/shadow-options.js';\nimport { registerComponent } from '../common/definitions/register.js';\nimport { partMap } from '../common/part-map.js';\nimport { asNumber } from '../common/util.js';\nimport type { TileManagerDragMode, TileManagerResizeMode } from '../types.js';\nimport { createTilesState } from './position.js';\nimport { createSerializer } from './serializer.js';\nimport { all } from './themes/container.js';\nimport { styles as shared } from './themes/shared/tile-manager.common.css.js';\nimport { styles } from './themes/tile-manager.base.css.js';\nimport IgcTileComponent from './tile.js';\n\n/* blazorAdditionalDependency: IgcTileComponent */\n/**\n * The tile manager component enables the dynamic arrangement, resizing, and interaction of tiles.\n *\n * @element igc-tile-manager\n *\n * @slot - Default slot for the tile manager. Only `igc-tile` elements will be projected inside the CSS grid container.\n *\n * @csspart base - The tile manager CSS Grid container.\n *\n * @cssproperty --column-count - The number of columns for the tile manager. The `column-count` attribute sets this variable.\n * @cssproperty --min-col-width - The minimum size of the columns in the tile-manager. The `min-column-width` attribute sets this variable.\n * @cssproperty --min-row-height - The minimum size of the rows in the tile-manager. The `min-row-height` attribute sets this variable.\n * @cssproperty --grid-gap - The gap size of the underlying CSS grid container. The `gap` attributes sts this variable.\n *\n */\n@shadowOptions({ slotAssignment: 'manual' })\nexport default class IgcTileManagerComponent extends LitElement {\n public static readonly tagName = 'igc-tile-manager';\n public static override styles = [styles, shared];\n\n /* blazorSuppress */\n public static register() {\n registerComponent(IgcTileManagerComponent, IgcTileComponent);\n }\n\n // #region Internal state\n\n private _internalStyles: StyleInfo = {};\n private _dragMode: TileManagerDragMode = 'none';\n private _resizeMode: TileManagerResizeMode = 'none';\n private _columnCount = 0;\n private _gap?: string;\n private _minColWidth?: string;\n private _minRowHeight?: string;\n\n private _serializer = createSerializer(this);\n private _tilesState = createTilesState(this);\n\n private _grid = createRef<HTMLElement>();\n\n // #endregion\n\n // #region Context helpers\n\n private _context = new ContextProvider(this, {\n context: tileManagerContext,\n initialValue: this._createContext(),\n });\n\n private _createContext(): TileManagerContext {\n return {\n instance: this,\n grid: this._grid,\n };\n }\n\n private _setManagerContext(): void {\n this._context.setValue(this._createContext(), true);\n }\n\n // #endregion\n\n // #region Properties and Attributes\n\n /**\n * Whether resize operations are enabled.\n *\n * @attr resize-mode\n * @default none\n */\n @property({ attribute: 'resize-mode' })\n public set resizeMode(value: TileManagerResizeMode) {\n this._resizeMode = value;\n this._setManagerContext();\n }\n\n public get resizeMode(): TileManagerResizeMode {\n return this._resizeMode;\n }\n\n /**\n * Whether drag and drop operations are enabled.\n *\n * @attr drag-mode\n * @default none\n */\n @property({ attribute: 'drag-mode' })\n public set dragMode(value: TileManagerDragMode) {\n this._dragMode = value;\n this._setManagerContext();\n }\n\n public get dragMode(): TileManagerDragMode {\n return this._dragMode;\n }\n\n /**\n * Sets the number of columns for the tile manager.\n * Setting value <= than zero will trigger a responsive layout.\n *\n * @attr column-count\n * @default 0\n */\n @property({ type: Number, attribute: 'column-count' })\n public set columnCount(value: number) {\n this._columnCount = Math.max(0, asNumber(value));\n Object.assign(this._internalStyles, {\n '--column-count': this._columnCount || undefined,\n });\n }\n\n public get columnCount(): number {\n return this._columnCount;\n }\n\n /**\n * Sets the minimum width for a column unit in the tile manager.\n * @attr min-column-width\n */\n @property({ attribute: 'min-column-width' })\n public set minColumnWidth(value: string | undefined) {\n this._minColWidth = value ?? undefined;\n Object.assign(this._internalStyles, {\n '--min-col-width': this._minColWidth,\n });\n }\n\n public get minColumnWidth(): string | undefined {\n return this._minColWidth;\n }\n\n /**\n * Sets the minimum height for a row unit in the tile manager.\n * @attr min-row-height\n */\n @property({ attribute: 'min-row-height' })\n public set minRowHeight(value: string | undefined) {\n this._minRowHeight = value ?? undefined;\n Object.assign(this._internalStyles, {\n '--min-row-height': this._minRowHeight,\n });\n }\n\n public get minRowHeight(): string | undefined {\n return this._minRowHeight;\n }\n\n /**\n * Sets the gap size between tiles in the tile manager.\n *\n * @attr gap\n */\n @property()\n public set gap(value: string | undefined) {\n this._gap = value ?? undefined;\n Object.assign(this._internalStyles, {\n '--grid-gap': this._gap,\n });\n }\n\n public get gap(): string | undefined {\n return this._gap;\n }\n\n /**\n * Gets the tiles sorted by their position in the layout.\n * @property\n */\n public get tiles() {\n return this._tilesState.tiles;\n }\n\n // #endregion\n\n // #region Internal API\n\n constructor() {\n super();\n\n addThemingController(this, all);\n\n createMutationController(this, {\n callback: this._observerCallback,\n filter: [IgcTileComponent.tagName],\n config: {\n childList: true,\n },\n });\n }\n\n protected override updated() {\n this._tilesState.adjustTileGridPosition();\n }\n\n protected override firstUpdated() {\n this._tilesState.assignPositions();\n this._tilesState.assignTiles();\n this._setManagerContext();\n }\n\n private _observerCallback({\n changes: { added, removed },\n }: MutationControllerParams<IgcTileComponent>) {\n const ownAdded = added.filter(\n ({ target }) => target.closest(this.tagName) === this\n );\n const ownRemoved = removed.filter(\n ({ target }) => target.closest(this.tagName) === this\n );\n\n for (const remove of ownRemoved) {\n this._tilesState.remove(remove.node);\n }\n\n for (const added of ownAdded) {\n this._tilesState.add(added.node);\n }\n\n this._tilesState.assignTiles();\n }\n\n // #endregion\n\n // #region Public API\n\n /**\n * Returns the properties of the current tile collections as a JSON payload.\n *\n * @remarks\n * The content of the tiles is not serialized or saved. Only tile properties\n * are serialized.\n */\n public saveLayout(): string {\n return this._serializer.saveAsJSON();\n }\n\n /**\n * Restores a previously serialized state produced by `saveLayout`.\n */\n public loadLayout(data: string): void {\n this._serializer.loadFromJSON(data);\n }\n\n // #endregion\n\n // #region Rendering\n\n protected override render() {\n const parts = {\n base: true,\n 'maximized-tile': this.tiles.some((tile) => tile.maximized),\n };\n\n return html`\n <div\n ${ref(this._grid)}\n style=${styleMap(this._internalStyles)}\n part=${partMap(parts)}\n >\n <slot></slot>\n </div>\n `;\n }\n\n // #endregion\n}\n\ndeclare global {\n interface HTMLElementTagNameMap {\n 'igc-tile-manager': IgcTileManagerComponent;\n }\n}\n"]}
1
+ {"version":3,"file":"tile-manager.js","sourceRoot":"","sources":["../../../src/components/tile-manager/tile-manager.ts"],"names":[],"mappings":"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","sourcesContent":["import { ContextProvider } from '@lit/context';\nimport { html, LitElement } from 'lit';\nimport { property } from 'lit/decorators.js';\nimport { createRef, ref } from 'lit/directives/ref.js';\nimport { type StyleInfo, styleMap } from 'lit/directives/style-map.js';\nimport { addThemingController } from '../../theming/theming-controller.js';\nimport {\n type TileManagerContext,\n tileManagerContext,\n} from '../common/context.js';\nimport {\n createMutationController,\n type MutationControllerParams,\n} from '../common/controllers/mutation-observer.js';\nimport { shadowOptions } from '../common/decorators/shadow-options.js';\nimport { registerComponent } from '../common/definitions/register.js';\nimport { partMap } from '../common/part-map.js';\nimport { asNumber } from '../common/util.js';\nimport type { TileManagerDragMode, TileManagerResizeMode } from '../types.js';\nimport { createTilesState } from './position.js';\nimport { createSerializer } from './serializer.js';\nimport { all } from './themes/container.js';\nimport { styles as shared } from './themes/shared/tile-manager.common.css.js';\nimport { styles } from './themes/tile-manager.base.css.js';\nimport IgcTileComponent from './tile.js';\n\n/* blazorAdditionalDependency: IgcTileComponent */\n/**\n * The tile manager component enables the dynamic arrangement, resizing, and interaction of tiles.\n *\n * @element igc-tile-manager\n *\n * @slot - Default slot for the tile manager. Only `igc-tile` elements will be projected inside the CSS grid container.\n *\n * @csspart base - The tile manager CSS Grid container.\n *\n * @cssproperty --column-count - The number of columns for the tile manager. The `column-count` attribute sets this variable.\n * @cssproperty --min-col-width - The minimum size of the columns in the tile-manager. The `min-column-width` attribute sets this variable.\n * @cssproperty --min-row-height - The minimum size of the rows in the tile-manager. The `min-row-height` attribute sets this variable.\n * @cssproperty --grid-gap - The gap size of the underlying CSS grid container. The `gap` attributes sts this variable.\n *\n */\n@shadowOptions({ slotAssignment: 'manual' })\nexport default class IgcTileManagerComponent extends LitElement {\n public static readonly tagName = 'igc-tile-manager';\n public static override styles = [styles, shared];\n\n /* blazorSuppress */\n public static register() {\n registerComponent(IgcTileManagerComponent, IgcTileComponent);\n }\n\n // #region Internal state\n\n private _internalStyles: StyleInfo = {};\n private _dragMode: TileManagerDragMode = 'none';\n private _resizeMode: TileManagerResizeMode = 'none';\n private _columnCount = 0;\n private _gap?: string;\n private _minColWidth?: string;\n private _minRowHeight?: string;\n\n private _serializer = createSerializer(this);\n private _tilesState = createTilesState(this);\n\n private _grid = createRef<HTMLElement>();\n\n // #endregion\n\n // #region Context helpers\n\n private _context = new ContextProvider(this, {\n context: tileManagerContext,\n initialValue: this._createContext(),\n });\n\n private _createContext(): TileManagerContext {\n return {\n instance: this,\n grid: this._grid,\n setMaximizedState: () => this._setMaximizedState(),\n };\n }\n\n private _setManagerContext(): void {\n this._context.setValue(this._createContext(), true);\n }\n\n // #endregion\n\n // #region Properties and Attributes\n\n /**\n * Whether resize operations are enabled.\n *\n * @attr resize-mode\n * @default none\n */\n @property({ attribute: 'resize-mode' })\n public set resizeMode(value: TileManagerResizeMode) {\n this._resizeMode = value;\n this._setManagerContext();\n }\n\n public get resizeMode(): TileManagerResizeMode {\n return this._resizeMode;\n }\n\n /**\n * Whether drag and drop operations are enabled.\n *\n * @attr drag-mode\n * @default none\n */\n @property({ attribute: 'drag-mode' })\n public set dragMode(value: TileManagerDragMode) {\n this._dragMode = value;\n this._setManagerContext();\n }\n\n public get dragMode(): TileManagerDragMode {\n return this._dragMode;\n }\n\n /**\n * Sets the number of columns for the tile manager.\n * Setting value <= than zero will trigger a responsive layout.\n *\n * @attr column-count\n * @default 0\n */\n @property({ type: Number, attribute: 'column-count' })\n public set columnCount(value: number) {\n this._columnCount = Math.max(0, asNumber(value));\n Object.assign(this._internalStyles, {\n '--column-count': this._columnCount || undefined,\n });\n }\n\n public get columnCount(): number {\n return this._columnCount;\n }\n\n /**\n * Sets the minimum width for a column unit in the tile manager.\n * @attr min-column-width\n */\n @property({ attribute: 'min-column-width' })\n public set minColumnWidth(value: string | undefined) {\n this._minColWidth = value ?? undefined;\n Object.assign(this._internalStyles, {\n '--min-col-width': this._minColWidth,\n });\n }\n\n public get minColumnWidth(): string | undefined {\n return this._minColWidth;\n }\n\n /**\n * Sets the minimum height for a row unit in the tile manager.\n * @attr min-row-height\n */\n @property({ attribute: 'min-row-height' })\n public set minRowHeight(value: string | undefined) {\n this._minRowHeight = value ?? undefined;\n Object.assign(this._internalStyles, {\n '--min-row-height': this._minRowHeight,\n });\n }\n\n public get minRowHeight(): string | undefined {\n return this._minRowHeight;\n }\n\n /**\n * Sets the gap size between tiles in the tile manager.\n *\n * @attr gap\n */\n @property()\n public set gap(value: string | undefined) {\n this._gap = value ?? undefined;\n Object.assign(this._internalStyles, {\n '--grid-gap': this._gap,\n });\n }\n\n public get gap(): string | undefined {\n return this._gap;\n }\n\n /**\n * Gets the tiles sorted by their position in the layout.\n * @property\n */\n public get tiles() {\n return this._tilesState.tiles;\n }\n\n // #endregion\n\n // #region Internal API\n\n constructor() {\n super();\n\n addThemingController(this, all);\n\n createMutationController(this, {\n callback: this._observerCallback,\n filter: [IgcTileComponent.tagName],\n config: {\n childList: true,\n },\n });\n }\n\n protected override updated() {\n this._tilesState.adjustTileGridPosition();\n }\n\n protected override firstUpdated() {\n this._tilesState.assignPositions();\n this._tilesState.assignTiles();\n this._setManagerContext();\n }\n\n private _observerCallback({\n changes: { added, removed },\n }: MutationControllerParams<IgcTileComponent>) {\n const ownAdded = added.filter(\n ({ target }) => target.closest(this.tagName) === this\n );\n const ownRemoved = removed.filter(\n ({ target }) => target.closest(this.tagName) === this\n );\n\n for (const remove of ownRemoved) {\n this._tilesState.remove(remove.node);\n }\n\n for (const added of ownAdded) {\n this._tilesState.add(added.node);\n }\n\n this._tilesState.assignTiles();\n }\n\n /**\n * Locks/unlocks the grid container height in response to a tile's maximized state changing.\n *\n * @remarks\n * Maximizing a tile removes it from the grid flow (absolute positioning), so it no longer\n * contributes to the grid's intrinsic height. When that tile is the sole contributor to the\n * tallest row track, the container would otherwise collapse to the remaining tiles and cut off\n * the maximized tile's content. Capturing the current height before the layout change keeps the\n * container stable, and it is released once no tile remains maximized.\n */\n private _setMaximizedState(): void {\n const grid = this._grid.value;\n\n if (grid) {\n if (this.tiles.some((tile) => tile.maximized)) {\n if (!grid.style.minHeight) {\n grid.style.minHeight = `${grid.offsetHeight}px`;\n }\n } else {\n grid.style.minHeight = '';\n }\n }\n\n this.requestUpdate();\n }\n\n // #endregion\n\n // #region Public API\n\n /**\n * Returns the properties of the current tile collections as a JSON payload.\n *\n * @remarks\n * The content of the tiles is not serialized or saved. Only tile properties\n * are serialized.\n */\n public saveLayout(): string {\n return this._serializer.saveAsJSON();\n }\n\n /**\n * Restores a previously serialized state produced by `saveLayout`.\n */\n public loadLayout(data: string): void {\n this._serializer.loadFromJSON(data);\n }\n\n // #endregion\n\n // #region Rendering\n\n protected override render() {\n const parts = {\n base: true,\n 'maximized-tile': this.tiles.some((tile) => tile.maximized),\n };\n\n return html`\n <div\n ${ref(this._grid)}\n style=${styleMap(this._internalStyles)}\n part=${partMap(parts)}\n >\n <slot></slot>\n </div>\n `;\n }\n\n // #endregion\n}\n\ndeclare global {\n interface HTMLElementTagNameMap {\n 'igc-tile-manager': IgcTileManagerComponent;\n }\n}\n"]}
@@ -87,7 +87,7 @@ export default class IgcTileComponent extends EventEmitterMixin(LitElement) {
87
87
  set maximized(value) {
88
88
  this._maximized = value;
89
89
  if (this._tileManagerCtx) {
90
- this._tileManagerCtx.instance.requestUpdate();
90
+ this._tileManagerCtx.setMaximizedState();
91
91
  }
92
92
  }
93
93
  get maximized() {