igniteui-dockmanager 2.0.2-alpha.3 → 2.1.0-RC.0

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.
package/CHANGELOG.md CHANGED
@@ -6,6 +6,8 @@ All notable changes for each version of this project will be documented in this
6
6
 
7
7
  ### New features
8
8
  - Added `paneFlyoutToggle` event that fires when an unpinned pane's flyout opens or closes (distinct from pin/unpin operations).
9
+ - Added `minResizeWidth` and `minResizeHeight` properties to `IgcContentPane`, `IgcSplitPane`, and `IgcTabGroupPane` to constrain resizing behavior during resize operations. These properties set minimum size constraints (in pixels, default: 42) that are enforced when a user interacts with splitters or resizes floating panes. **Note:** These constraints only apply during active resize operations and do not prevent docking into smaller containers or affect container sizing during docking operations.
10
+ - The `layoutChange` event now includes the updated layout in its `detail.layout` property.
9
11
 
10
12
  ### Bug Fixes
11
13
  - The hover area for showing pane headers when `showPaneHeaders` is set to `onHoverOnly` now correctly accounts for the actual pane header height, including custom heights set via `::part(pane-header)` styles. Note that when customizing the header height, the `min-height` property should also be overridden, as it defaults to 40px to ensure header elements are properly displayed.
@@ -1,13 +1,13 @@
1
1
  import { LitElement, type TemplateResult } from 'lit';
2
2
  import type { Constructor } from '../../common/mixins/constructor.js';
3
3
  import type { ContextMenuPosition, PaneActionBehavior } from './backfill-types-dockmanager.js';
4
- import { type IgcActivePaneEventArgs, type IgcContentPane, type IgcContextMenuMetadata, type IgcDockManagerComponentBase, type IgcDockManagerLayout, type IgcDockManagerPane, type IgcDockManagerPoint, type IgcDockManagerResourceStrings, type IgcDropTargetPaneInfo, type IgcFloatingPaneResizeEventArgs, type IgcFloatingPaneResizeMoveEventArgs, type IgcPaneCloseEventArgs, type IgcPaneDragEndEventArgs, type IgcPaneDragOverEventArgs, type IgcPaneDragStartEventArgs, type IgcPaneFlyoutEventArgs, type IgcPaneHeaderConnectionEventArgs, type IgcPaneNavigatorMetadata, type IgcPanePinnedEventArgs, type IgcPaneScrollEventArgs, type IgcSplitPane, type IgcSplitterResizeEventArgs, type IgcTabGroupPane, type IgcTabHeaderConnectionEventArgs } from './dockmanager.interfaces.js';
4
+ import { type IgcActivePaneEventArgs, type IgcContentPane, type IgcContextMenuMetadata, type IgcDockManagerComponentBase, type IgcDockManagerLayout, type IgcDockManagerPane, type IgcDockManagerPoint, type IgcDockManagerResourceStrings, type IgcDropTargetPaneInfo, type IgcFloatingPaneResizeEventArgs, type IgcFloatingPaneResizeMoveEventArgs, type IgcLayoutChangeEventArgs, type IgcPaneCloseEventArgs, type IgcPaneDragEndEventArgs, type IgcPaneDragOverEventArgs, type IgcPaneDragStartEventArgs, type IgcPaneFlyoutEventArgs, type IgcPaneHeaderConnectionEventArgs, type IgcPaneNavigatorMetadata, type IgcPanePinnedEventArgs, type IgcPaneScrollEventArgs, type IgcScrollConfig, type IgcSplitPane, type IgcSplitterResizeEventArgs, type IgcTabGroupPane, type IgcTabHeaderConnectionEventArgs } from './dockmanager.interfaces.js';
5
5
  export interface IgcDockManagerEventMap {
6
6
  activePaneChanged: CustomEvent<IgcActivePaneEventArgs>;
7
7
  floatingPaneResizeEnd: CustomEvent<IgcFloatingPaneResizeEventArgs>;
8
8
  floatingPaneResizeMove: CustomEvent<IgcFloatingPaneResizeMoveEventArgs>;
9
9
  floatingPaneResizeStart: CustomEvent<IgcFloatingPaneResizeEventArgs>;
10
- layoutChange: CustomEvent;
10
+ layoutChange: CustomEvent<IgcLayoutChangeEventArgs>;
11
11
  paneDragEnd: CustomEvent<IgcPaneDragEndEventArgs>;
12
12
  paneDragOver: CustomEvent<IgcPaneDragOverEventArgs>;
13
13
  paneDragStart: CustomEvent<IgcPaneDragStartEventArgs>;
@@ -105,6 +105,7 @@ export default class IgcDockManagerComponent extends IgcDockManagerComponent_bas
105
105
  private cachedHeaderHeight;
106
106
  private templatableComponents;
107
107
  private readonly _resourceChangeHandler;
108
+ /** @hidden @internal **/
108
109
  documentOnlyDrag: boolean;
109
110
  draggedPaneElement?: HTMLElement;
110
111
  /**
@@ -217,10 +218,7 @@ export default class IgcDockManagerComponent extends IgcDockManagerComponent_bas
217
218
  * @type {{ edgeThreshold: number, scrollSpeed: number }}
218
219
  * @default { edgeThreshold: 20, scrollSpeed: 15 }
219
220
  */
220
- autoScrollConfig: {
221
- edgeThreshold: number;
222
- scrollSpeed: number;
223
- };
221
+ autoScrollConfig: IgcScrollConfig;
224
222
  /**
225
223
  * Determines whether docking indicators are displayed while docking
226
224
  *
@@ -332,18 +330,26 @@ export default class IgcDockManagerComponent extends IgcDockManagerComponent_bas
332
330
  protected draggedPaneChanged(): void;
333
331
  protected layoutChanged(): void;
334
332
  protected containedInBoundariesChanged(): void;
333
+ /** @hidden @internal **/
335
334
  dropPositionChanged(): void;
336
335
  constructor();
336
+ /** @hidden @internal **/
337
337
  connectedCallback(): void;
338
338
  private onResourceChangeHandler;
339
+ /** @hidden @internal **/
339
340
  willUpdate(): void;
341
+ /** @hidden @internal **/
340
342
  updated(): void;
343
+ /** @hidden @internal **/
341
344
  firstUpdated(): void;
345
+ /** @hidden @internal **/
342
346
  disconnectedCallback(): void;
347
+ /** @hidden @internal **/
343
348
  focusElement(): void;
344
349
  dropPane(): Promise<boolean>;
345
350
  removePane(pane: IgcDockManagerPane): Promise<void>;
346
351
  focusPane(contentId: string): Promise<void>;
352
+ /** @hidden @internal **/
347
353
  getDockedPanesContainerRect(): DOMRect | undefined;
348
354
  private updateLayout;
349
355
  private handleFocusOut;
@@ -375,6 +381,7 @@ export default class IgcDockManagerComponent extends IgcDockManagerComponent_bas
375
381
  private handleUnpinnedHeaderFocus;
376
382
  private clearActivePane;
377
383
  private isPaneSizeWithinConstraints;
384
+ private _getMinSizeFromPane;
378
385
  private restrictFloatingPaneSize;
379
386
  private renderDocumentHost;
380
387
  private renderSplitter;
@@ -434,6 +441,7 @@ export default class IgcDockManagerComponent extends IgcDockManagerComponent_bas
434
441
  private handleAutoScroll;
435
442
  private setSplitterDockingIndicatorVisibility;
436
443
  private setSplitterDockTarget;
444
+ /** @hidden @internal **/
437
445
  scrollPaneIntoView(pane: IgcDockManagerPane): void;
438
446
  private handlePaneDragStart;
439
447
  private handlePaneDragMove;
@@ -467,8 +475,11 @@ export default class IgcDockManagerComponent extends IgcDockManagerComponent_bas
467
475
  private updateTemplates;
468
476
  private emitTabHeaderConnected;
469
477
  private emitTabHeaderDisconnected;
478
+ /** @hidden @internal **/
470
479
  paneClose(args: IgcPaneCloseEventArgs): CustomEvent<IgcPaneCloseEventArgs>;
480
+ /** @hidden @internal **/
471
481
  paneScroll(args: IgcPaneScrollEventArgs): CustomEvent<IgcPaneScrollEventArgs>;
482
+ /** @hidden @internal **/
472
483
  panePinnedToggle(args: IgcPanePinnedEventArgs): CustomEvent<IgcPanePinnedEventArgs>;
473
484
  /**
474
485
  * Emitted when an unpinned pane's flyout state changes (opens or closes).
@@ -499,13 +510,20 @@ export default class IgcDockManagerComponent extends IgcDockManagerComponent_bas
499
510
  * ```
500
511
  */
501
512
  paneFlyoutToggle(args: IgcPaneFlyoutEventArgs): CustomEvent<IgcPaneFlyoutEventArgs>;
513
+ /** @hidden @internal **/
502
514
  paneDragStart(args: IgcPaneDragStartEventArgs): CustomEvent<IgcPaneDragStartEventArgs>;
515
+ /** @hidden @internal **/
503
516
  paneDragOver(args: IgcPaneDragOverEventArgs): CustomEvent<IgcPaneDragOverEventArgs>;
517
+ /** @hidden @internal **/
504
518
  paneDragEnd(args: IgcPaneDragEndEventArgs): CustomEvent<IgcPaneDragEndEventArgs>;
519
+ /** @hidden @internal **/
505
520
  floatingPaneResizeStart(args: IgcFloatingPaneResizeEventArgs): CustomEvent<IgcFloatingPaneResizeEventArgs>;
521
+ /** @hidden @internal **/
506
522
  floatingPaneResizeMove(eventArgs: IgcFloatingPaneResizeMoveEventArgs): CustomEvent<IgcFloatingPaneResizeMoveEventArgs>;
523
+ /** @hidden @internal **/
507
524
  floatingPaneResizeEnd(args: IgcFloatingPaneResizeEventArgs): CustomEvent<IgcFloatingPaneResizeEventArgs>;
508
- layoutChange(): CustomEvent;
525
+ /** @hidden @internal **/
526
+ layoutChange(): CustomEvent<IgcLayoutChangeEventArgs>;
509
527
  private renderContentPane;
510
528
  private renderSplitPane;
511
529
  private renderPlaceholder;
@@ -145,7 +145,9 @@ class IgcDockManagerComponent extends EventEmitterMixin(LitElement) {
145
145
  this.service.processLayout();
146
146
  this.restoreDraggedPanes();
147
147
  if (!this.isDragging) {
148
- this.emitEvent('layoutChange');
148
+ this.emitEvent('layoutChange', {
149
+ detail: { layout: this.layout },
150
+ });
149
151
  }
150
152
  }
151
153
  containedInBoundariesChanged() {
@@ -904,8 +906,9 @@ class IgcDockManagerComponent extends EventEmitterMixin(LitElement) {
904
906
  pane.unpinnedSize = minSize;
905
907
  }
906
908
  const parent = this.service.getParent(pane);
909
+ const unpinnedLocation = this.service.unpinnedLocationMap.get(pane);
907
910
  let offset = this.service.isSplitPaneIgnoringResizeConstraints(parent) ||
908
- this.isPaneSizeWithinConstraints(previousPane, event.detail, orientation, 'previous')
911
+ this.isPaneSizeWithinConstraints(previousPane, event.detail, orientation, 'previous', unpinnedLocation)
909
912
  ? this.splitterOffset * event.detail
910
913
  : 0;
911
914
  if (this.direction === 'rtl' && orientation === 'horizontal') {
@@ -955,14 +958,14 @@ class IgcDockManagerComponent extends EventEmitterMixin(LitElement) {
955
958
  this.setActivePane(null);
956
959
  }
957
960
  }
958
- isPaneSizeWithinConstraints(pane, offset, orientation, position = 'next') {
961
+ isPaneSizeWithinConstraints(pane, offset, orientation, position = 'next', unpinnedLocation) {
959
962
  let size;
960
963
  let minSize;
961
964
  let maxSize;
962
965
  let adjustedOffset = offset;
963
966
  if (orientation === 'horizontal') {
964
967
  size = pane.getBoundingClientRect().width;
965
- minSize = Number.parseFloat(getComputedStyle(pane).minWidth);
968
+ minSize = this._getMinSizeFromPane(pane, 'minResizeWidth');
966
969
  maxSize = Number.parseFloat(getComputedStyle(pane).maxWidth);
967
970
  if (this.direction === 'rtl') {
968
971
  adjustedOffset *= -1;
@@ -970,20 +973,46 @@ class IgcDockManagerComponent extends EventEmitterMixin(LitElement) {
970
973
  }
971
974
  else {
972
975
  size = pane.getBoundingClientRect().height;
973
- minSize = Number.parseFloat(getComputedStyle(pane).minHeight);
976
+ minSize = this._getMinSizeFromPane(pane, 'minResizeHeight');
974
977
  maxSize = Number.parseFloat(getComputedStyle(pane).maxHeight);
975
978
  }
976
979
  if (position === 'previous') {
977
- return adjustedOffset < 0
978
- ? size + adjustedOffset >= minSize ||
979
- Number.isNaN(minSize) ||
980
- minSize === 0
981
- : size + adjustedOffset <= maxSize || Number.isNaN(maxSize);
980
+ let newSize;
981
+ if (unpinnedLocation) {
982
+ const shouldAddOffset = unpinnedLocation === 'top' || unpinnedLocation === 'left';
983
+ newSize = shouldAddOffset
984
+ ? size + adjustedOffset
985
+ : size - adjustedOffset;
986
+ }
987
+ else {
988
+ newSize = size + adjustedOffset;
989
+ }
990
+ if (newSize > size) {
991
+ if (unpinnedLocation) {
992
+ return true;
993
+ }
994
+ return newSize <= maxSize || Number.isNaN(maxSize);
995
+ }
996
+ return newSize >= minSize || Number.isNaN(minSize) || minSize === 0;
982
997
  }
983
998
  return adjustedOffset > 0
984
- ? size - adjustedOffset >= minSize || Number.isNaN(minSize)
999
+ ? size - adjustedOffset >= minSize ||
1000
+ Number.isNaN(minSize) ||
1001
+ minSize === 0
985
1002
  : size - adjustedOffset <= maxSize || Number.isNaN(maxSize);
986
1003
  }
1004
+ _getMinSizeFromPane(pane, property) {
1005
+ const customElement = pane;
1006
+ if (property in customElement &&
1007
+ typeof customElement[property] === 'number') {
1008
+ const value = customElement[property];
1009
+ if (value > 0) {
1010
+ return value;
1011
+ }
1012
+ }
1013
+ const cssProperty = property === 'minResizeWidth' ? 'minWidth' : 'minHeight';
1014
+ return Number.parseFloat(getComputedStyle(pane)[cssProperty]);
1015
+ }
987
1016
  restrictFloatingPaneSize() {
988
1017
  if (this.containedInBoundaries) {
989
1018
  if (!this.shadowRoot)
@@ -1038,6 +1067,7 @@ class IgcDockManagerComponent extends EventEmitterMixin(LitElement) {
1038
1067
  ${ref((el) => {
1039
1068
  if (el instanceof HTMLElement) {
1040
1069
  this.panesElementMap.set(docHost, el);
1070
+ el._layoutPane = docHost;
1041
1071
  }
1042
1072
  })}
1043
1073
  >
@@ -2299,7 +2329,9 @@ class IgcDockManagerComponent extends EventEmitterMixin(LitElement) {
2299
2329
  return this.createAndDispatchEvent('floatingPaneResizeEnd', args);
2300
2330
  }
2301
2331
  layoutChange() {
2302
- return this.createAndDispatchEvent('layoutChange', { cancelable: true });
2332
+ return this.createAndDispatchEvent('layoutChange', { layout: this.layout }, {
2333
+ cancelable: true,
2334
+ });
2303
2335
  }
2304
2336
  renderContentPane(pane, isFloating, isFlyout) {
2305
2337
  const parentPane = this.service.getParent(pane);
@@ -2327,6 +2359,8 @@ class IgcDockManagerComponent extends EventEmitterMixin(LitElement) {
2327
2359
  <igc-content-pane
2328
2360
  .contentId=${pane.contentId}
2329
2361
  .size=${pane.size ?? IGC_DEFAULT_PANE_SIZE}
2362
+ .minResizeWidth=${pane.minResizeWidth}
2363
+ .minResizeHeight=${pane.minResizeHeight}
2330
2364
  .isFlyout=${isFlyout}
2331
2365
  .unpinnedSize=${pane.unpinnedSize ?? IGC_DEFAULT_UNPIN_PANE_SIZE}
2332
2366
  ?disabled=${pane.disabled}
@@ -2341,6 +2375,7 @@ class IgcDockManagerComponent extends EventEmitterMixin(LitElement) {
2341
2375
  if (el instanceof HTMLElement) {
2342
2376
  this.panesElementMap.set(pane, el);
2343
2377
  this.contentPanesElementMap.set(pane, el);
2378
+ el._layoutPane = pane;
2344
2379
  }
2345
2380
  })}
2346
2381
  >
@@ -2412,12 +2447,15 @@ class IgcDockManagerComponent extends EventEmitterMixin(LitElement) {
2412
2447
  <igc-split-pane
2413
2448
  orientation=${splitPane.orientation}
2414
2449
  .size=${splitPane.size}
2450
+ .minResizeWidth=${splitPane.minResizeWidth}
2451
+ .minResizeHeight=${splitPane.minResizeHeight}
2415
2452
  .useFixedSize=${splitPane.useFixedSize ?? false}
2416
2453
  .parentUseFixedSize=${this.service.isParentUseFixedSize(splitPane)}
2417
2454
  @rendered=${() => this.handleSplitPaneRendered(panes)}
2418
2455
  ${ref((el) => {
2419
2456
  if (el instanceof HTMLElement) {
2420
2457
  this.panesElementMap.set(splitPane, el);
2458
+ el._layoutPane = splitPane;
2421
2459
  }
2422
2460
  })}
2423
2461
  >
@@ -2652,6 +2690,8 @@ class IgcDockManagerComponent extends EventEmitterMixin(LitElement) {
2652
2690
  class=${classMap(tabClassMap)}
2653
2691
  .contentIds=${contentIds}
2654
2692
  .size=${pane.size ?? IGC_DEFAULT_PANE_SIZE}
2693
+ .minResizeWidth=${pane.minResizeWidth}
2694
+ .minResizeHeight=${pane.minResizeHeight}
2655
2695
  .selectedIndex=${selectedIndex}
2656
2696
  .hasHeaders=${!isSingleTab}
2657
2697
  .parentUseFixedSize=${this.service.isParentUseFixedSize(pane)}
@@ -2668,6 +2708,7 @@ class IgcDockManagerComponent extends EventEmitterMixin(LitElement) {
2668
2708
  ${ref((el) => {
2669
2709
  if (el instanceof HTMLElement) {
2670
2710
  this.panesElementMap.set(pane, el);
2711
+ el._layoutPane = pane;
2671
2712
  }
2672
2713
  })}
2673
2714
  >
@@ -16,6 +16,10 @@ export declare const IGC_DEFAULT_UNPIN_PANE_SIZE = 200;
16
16
  * @hidden
17
17
  */
18
18
  export declare const IGC_RESIZING_MIN_SIZE = 42;
19
+ /**
20
+ * @hidden
21
+ */
22
+ export declare const IGC_DEFAULT_SPLITTER_SIZE = 4;
19
23
  /**
20
24
  * @hidden
21
25
  */
@@ -24,6 +28,10 @@ export declare const IGC_DEFAULT_RESIZE = 10;
24
28
  * @hidden
25
29
  */
26
30
  export declare const IGC_DRAG_FLYOUT_THRESHOLD = 50;
31
+ /**
32
+ * @hidden
33
+ */
34
+ export declare const IGC_DEFAULT_FLOATING_PANE_HEADER_HEIGHT = 30;
27
35
  /**
28
36
  * @hidden
29
37
  * @deprecated Use TabHeadersPosition instead.
@@ -94,7 +102,7 @@ export interface IgcDockManagerComponentBase {
94
102
  floatingPaneResizeStart(eventArgs: IgcFloatingPaneResizeEventArgs): CustomEvent<IgcFloatingPaneResizeEventArgs>;
95
103
  floatingPaneResizeMove(eventArgs: IgcFloatingPaneResizeMoveEventArgs): CustomEvent<IgcFloatingPaneResizeMoveEventArgs>;
96
104
  floatingPaneResizeEnd(eventArgs: IgcFloatingPaneResizeEventArgs): CustomEvent<IgcFloatingPaneResizeEventArgs>;
97
- layoutChange(eventArgs?: IgcDockManagerLayout): CustomEvent;
105
+ layoutChange(): CustomEvent<IgcLayoutChangeEventArgs>;
98
106
  direction: string;
99
107
  allowInnerDock: boolean;
100
108
  closeBehavior: IgcPaneActionBehavior;
@@ -135,15 +143,16 @@ export interface IgcTabRectsInfo {
135
143
  lastVisibleHeaderRect: DOMRect;
136
144
  tabsRect: DOMRect;
137
145
  }
138
- /**
139
- * @hidden
140
- */
141
146
  export interface IgcPaneNavigatorMetadata {
142
147
  activePanes: IgcContentPane[];
143
148
  activeDocuments: IgcContentPane[];
144
149
  initialIndex: number;
145
150
  previousActivePaneIndex: number;
146
151
  }
152
+ export interface IgcScrollConfig {
153
+ edgeThreshold: number;
154
+ scrollSpeed: number;
155
+ }
147
156
  /**
148
157
  * @hidden
149
158
  */
@@ -378,6 +387,12 @@ export interface IgcPaneDragEndEventArgs {
378
387
  */
379
388
  readonly panes: IgcContentPane[];
380
389
  }
390
+ export interface IgcLayoutChangeEventArgs {
391
+ /**
392
+ * The new layout of the Dock Manager.
393
+ */
394
+ layout: IgcDockManagerLayout;
395
+ }
381
396
  export interface IgcContentPane {
382
397
  /**
383
398
  * The id of the pane. If not set the Dock Manager generates it automatically.
@@ -471,6 +486,14 @@ export interface IgcContentPane {
471
486
  * Marks that a content pane can be docked only inside a document host.
472
487
  */
473
488
  documentOnly?: boolean;
489
+ /**
490
+ * The minimum width of the pane in pixels during resizing. Defaults to 42.
491
+ */
492
+ minResizeWidth?: number;
493
+ /**
494
+ * The minimum height of the pane in pixels during resizing. Defaults to 42.
495
+ */
496
+ minResizeHeight?: number;
474
497
  }
475
498
  export interface IgcSplitPane {
476
499
  /**
@@ -524,6 +547,14 @@ export interface IgcSplitPane {
524
547
  * Defaults to false.
525
548
  */
526
549
  useFixedSize?: boolean;
550
+ /**
551
+ * The minimum width of child panes in pixels during resizing. Defaults to 42.
552
+ */
553
+ minResizeWidth?: number;
554
+ /**
555
+ * The minimum height of child panes in pixels during resizing. Defaults to 42.
556
+ */
557
+ minResizeHeight?: number;
527
558
  }
528
559
  export interface IgcTabGroupPane {
529
560
  /**
@@ -554,6 +585,14 @@ export interface IgcTabGroupPane {
554
585
  * Determines whether a tab group is maximized or not. Defaults to false.
555
586
  */
556
587
  isMaximized?: boolean;
588
+ /**
589
+ * The minimum width of the tab group pane in pixels during resizing. Defaults to 42.
590
+ */
591
+ minResizeWidth?: number;
592
+ /**
593
+ * The minimum height of the tab group pane in pixels during resizing. Defaults to 42.
594
+ */
595
+ minResizeHeight?: number;
557
596
  }
558
597
  export interface IgcDocumentHost {
559
598
  /**
@@ -2,8 +2,10 @@ export const IGC_DEFAULT_PANE_SIZE = 100;
2
2
  export const IGC_DEFAULT_PANE_SIZE_IN_PIXELS = 100;
3
3
  export const IGC_DEFAULT_UNPIN_PANE_SIZE = 200;
4
4
  export const IGC_RESIZING_MIN_SIZE = 42;
5
+ export const IGC_DEFAULT_SPLITTER_SIZE = 4;
5
6
  export const IGC_DEFAULT_RESIZE = 10;
6
7
  export const IGC_DRAG_FLYOUT_THRESHOLD = 50;
8
+ export const IGC_DEFAULT_FLOATING_PANE_HEADER_HEIGHT = 30;
7
9
  export const IgcTabHeadersPosition = {
8
10
  top: 'top',
9
11
  bottom: 'bottom',
@@ -19,9 +19,9 @@ export declare class IgcDockManagerService {
19
19
  private shiftRightThreshold;
20
20
  private documentsCache;
21
21
  private contentPanesCache;
22
- private defaultSplitterSize;
23
22
  private isUpdatingLayout;
24
23
  private lastSwapCenter;
24
+ private _splitterSize;
25
25
  visibleDocuments: IgcContentPane[];
26
26
  visibleContentPanes: IgcContentPane[];
27
27
  documentHosts: IgcDocumentHost[];
@@ -56,6 +56,26 @@ export declare class IgcDockManagerService {
56
56
  private getChildContentPanesRecursive;
57
57
  getChildDocHostRecursive(pane: IgcSplitPane): IgcDocumentHost | null;
58
58
  getVisibleContentPanes(parent: IgcTabGroupPane): IgcContentPane[];
59
+ /**
60
+ * Get the actual rendered size of a splitter element from the DOM.
61
+ * The result is cached after the first successful measurement since splitter
62
+ * size is consistent across the component and rarely changes at runtime.
63
+ * @returns The splitter thickness in pixels, or IGC_DEFAULT_SPLITTER_SIZE if not found
64
+ */
65
+ private getSplitterSize;
66
+ /**
67
+ * Get the actual rendered height of a floating pane header from the DOM.
68
+ * This accounts for user customization via slots, CSS parts, or other styling.
69
+ * @param pane The floating pane to check
70
+ * @returns The header height in pixels, or default as a fallback if not found
71
+ */
72
+ private getFloatingPaneHeaderHeight;
73
+ /**
74
+ * Calculate the minimum width and height constraints for a floating pane
75
+ * based on all its child panes' minResizeWidth and minResizeHeight properties.
76
+ * This properly handles split panes by summing constraints in the split direction.
77
+ */
78
+ private getFloatingPaneMinConstraints;
59
79
  findPaneById(paneId: string | undefined): IgcDockManagerPane | null;
60
80
  private getPaneToDock;
61
81
  private removeDocumentHost;
@@ -1,5 +1,5 @@
1
- import { closestElement, getDirection, isDockingIndicatorBefore, isDockingIndicatorBeforeRTL, isDockingIndicatorOuter, isDockingIndicatorVertical, isSplitPaneVertical, } from '../../utils/utils.js';
2
- import { IGC_DEFAULT_PANE_SIZE, IGC_DEFAULT_PANE_SIZE_IN_PIXELS, IGC_DEFAULT_UNPIN_PANE_SIZE, IGC_DRAG_FLYOUT_THRESHOLD, } from './dockmanager.interfaces.js';
1
+ import { calculatePaneMinSize, closestElement, getDirection, isDockingIndicatorBefore, isDockingIndicatorBeforeRTL, isDockingIndicatorOuter, isDockingIndicatorVertical, isSplitPaneVertical, } from '../../utils/utils.js';
2
+ import { IGC_DEFAULT_FLOATING_PANE_HEADER_HEIGHT, IGC_DEFAULT_PANE_SIZE, IGC_DEFAULT_PANE_SIZE_IN_PIXELS, IGC_DEFAULT_SPLITTER_SIZE, IGC_DEFAULT_UNPIN_PANE_SIZE, IGC_DRAG_FLYOUT_THRESHOLD, } from './dockmanager.interfaces.js';
3
3
  export class IgcDockManagerService {
4
4
  constructor(dockManager) {
5
5
  this.dockManager = dockManager;
@@ -9,8 +9,8 @@ export class IgcDockManagerService {
9
9
  this.draggedPaneParent = null;
10
10
  this.documentsCache = [];
11
11
  this.contentPanesCache = [];
12
- this.defaultSplitterSize = 4;
13
12
  this.isUpdatingLayout = false;
13
+ this._splitterSize = null;
14
14
  this.visibleDocuments = [];
15
15
  this.visibleContentPanes = [];
16
16
  this.documentHosts = [];
@@ -301,6 +301,61 @@ export class IgcDockManagerService {
301
301
  getVisibleContentPanes(parent) {
302
302
  return parent.panes.filter((t) => this.isContentPaneVisible(t));
303
303
  }
304
+ getSplitterSize() {
305
+ if (this._splitterSize !== null) {
306
+ return this._splitterSize;
307
+ }
308
+ const dockManagerElement = this.dockManager;
309
+ if (!dockManagerElement || !dockManagerElement.shadowRoot) {
310
+ return IGC_DEFAULT_SPLITTER_SIZE;
311
+ }
312
+ const splitter = dockManagerElement.shadowRoot.querySelector('igc-splitter');
313
+ if (splitter) {
314
+ const rect = splitter.getBoundingClientRect();
315
+ const thickness = Math.min(rect.width, rect.height);
316
+ if (thickness > 0) {
317
+ this._splitterSize = thickness;
318
+ return this._splitterSize;
319
+ }
320
+ }
321
+ return IGC_DEFAULT_SPLITTER_SIZE;
322
+ }
323
+ getFloatingPaneHeaderHeight(pane) {
324
+ const dockManagerElement = this.dockManager;
325
+ if (!dockManagerElement || !dockManagerElement.shadowRoot) {
326
+ return IGC_DEFAULT_FLOATING_PANE_HEADER_HEIGHT + 2;
327
+ }
328
+ const floatingPaneElements = dockManagerElement.shadowRoot.querySelectorAll('igc-floating-pane');
329
+ let floatingPaneElement = null;
330
+ for (const element of Array.from(floatingPaneElements)) {
331
+ if (element.floatingId === pane.id) {
332
+ floatingPaneElement = element;
333
+ break;
334
+ }
335
+ }
336
+ if (floatingPaneElement) {
337
+ const headerElement = floatingPaneElement.querySelector('igc-pane-header[slot="header"]');
338
+ if (headerElement) {
339
+ const rect = headerElement.getBoundingClientRect();
340
+ if (rect.height > 0) {
341
+ return rect.height;
342
+ }
343
+ }
344
+ }
345
+ return IGC_DEFAULT_FLOATING_PANE_HEADER_HEIGHT + 2;
346
+ }
347
+ getFloatingPaneMinConstraints(pane) {
348
+ const splitterSize = this.getSplitterSize();
349
+ let minWidth = calculatePaneMinSize(pane, 'horizontal', splitterSize);
350
+ let minHeight = calculatePaneMinSize(pane, 'vertical', splitterSize);
351
+ if (this.hasFloatingPaneHeader(pane)) {
352
+ const headerHeight = this.getFloatingPaneHeaderHeight(pane);
353
+ minHeight += headerHeight;
354
+ }
355
+ minWidth += 2;
356
+ minHeight += 2;
357
+ return { minWidth, minHeight };
358
+ }
304
359
  findPaneById(paneId) {
305
360
  const layout = this.dockManager.layout;
306
361
  if (!layout || !paneId)
@@ -749,7 +804,6 @@ export class IgcDockManagerService {
749
804
  this.setFlyoutPane(null, this.dockManager.flyoutPane);
750
805
  }
751
806
  this.updateLayout();
752
- this.dockManager.layoutChange();
753
807
  }
754
808
  }
755
809
  checkUseFixedSizeParent(pane) {
@@ -902,8 +956,9 @@ export class IgcDockManagerService {
902
956
  const currH = pane.floatingHeight
903
957
  ? pane.floatingHeight
904
958
  : IGC_DEFAULT_PANE_SIZE;
905
- const minW = IGC_DEFAULT_PANE_SIZE;
906
- const minH = IGC_DEFAULT_PANE_SIZE;
959
+ const constraints = this.getFloatingPaneMinConstraints(pane);
960
+ const minW = constraints.minWidth;
961
+ const minH = constraints.minHeight;
907
962
  const initialWidth = this.initialFloatingPaneWidth;
908
963
  const initialHeight = this.initialFloatingPaneHeight;
909
964
  const initialLocation = this.initialFloatingPaneLocation;
@@ -920,10 +975,14 @@ export class IgcDockManagerService {
920
975
  case 'topLeft':
921
976
  case 'topRight':
922
977
  newHeight = initialHeight - totalOffsetY;
923
- if (newHeight < minH) {
978
+ if (initialHeight >= minH && newHeight < minH) {
924
979
  totalOffsetY = initialHeight - minH;
925
980
  newHeight = minH;
926
981
  }
982
+ else if (initialHeight < minH && newHeight < initialHeight) {
983
+ totalOffsetY = 0;
984
+ newHeight = initialHeight;
985
+ }
927
986
  newY = initialLocation.y + totalOffsetY;
928
987
  if (newY < 0) {
929
988
  newHeight += newY;
@@ -937,9 +996,12 @@ export class IgcDockManagerService {
937
996
  case 'bottomLeft':
938
997
  case 'bottomRight':
939
998
  newHeight = initialHeight + totalOffsetY;
940
- if (newHeight < minH) {
999
+ if (initialHeight >= minH && newHeight < minH) {
941
1000
  newHeight = minH;
942
1001
  }
1002
+ else if (initialHeight < minH && newHeight < initialHeight) {
1003
+ newHeight = initialHeight;
1004
+ }
943
1005
  if (newY + newHeight > maxHeight) {
944
1006
  newHeight = maxHeight - newY;
945
1007
  }
@@ -950,10 +1012,14 @@ export class IgcDockManagerService {
950
1012
  case 'topLeft':
951
1013
  case 'bottomLeft':
952
1014
  newWidth = initialWidth - totalOffsetX;
953
- if (newWidth < minW) {
1015
+ if (initialWidth >= minW && newWidth < minW) {
954
1016
  totalOffsetX = initialWidth - minW;
955
1017
  newWidth = minW;
956
1018
  }
1019
+ else if (initialWidth < minW && newWidth < initialWidth) {
1020
+ totalOffsetX = 0;
1021
+ newWidth = initialWidth;
1022
+ }
957
1023
  newX = initialLocation.x + totalOffsetX;
958
1024
  if (newX < 0) {
959
1025
  newWidth += newX;
@@ -967,9 +1033,12 @@ export class IgcDockManagerService {
967
1033
  case 'topRight':
968
1034
  case 'bottomRight':
969
1035
  newWidth = initialWidth + totalOffsetX;
970
- if (newWidth < minW) {
1036
+ if (initialWidth >= minW && newWidth < minW) {
971
1037
  newWidth = minW;
972
1038
  }
1039
+ else if (initialWidth < minW && newWidth < initialWidth) {
1040
+ newWidth = initialWidth;
1041
+ }
973
1042
  if (newX + newWidth > maxWidth) {
974
1043
  newWidth = maxWidth - newX;
975
1044
  }
@@ -1164,12 +1233,12 @@ export class IgcDockManagerService {
1164
1233
  (isHorizontal
1165
1234
  ? paneContainerRect?.width / 2
1166
1235
  : paneContainerRect?.height / 2) -
1167
- 2 * this.defaultSplitterSize;
1236
+ 2 * this.getSplitterSize();
1168
1237
  rootPane.size =
1169
1238
  (isHorizontal
1170
1239
  ? paneContainerRect.width - paneToDock.size
1171
1240
  : paneContainerRect.height - paneToDock.size) -
1172
- 2 * this.defaultSplitterSize;
1241
+ 2 * this.getSplitterSize();
1173
1242
  this.checkAndAddPlaceholderPane(layout.rootPane, true);
1174
1243
  }
1175
1244
  }
@@ -1229,7 +1298,6 @@ export class IgcDockManagerService {
1229
1298
  }
1230
1299
  }
1231
1300
  this.updateLayout();
1232
- this.dockManager.layoutChange();
1233
1301
  }
1234
1302
  getActualIsPinned(pane) {
1235
1303
  return pane.isPinned !== false;
@@ -1872,9 +1940,7 @@ export class IgcDockManagerService {
1872
1940
  const isSameSplitPane = (isIndicatorVertical && isTargetSplitPaneVertical) ||
1873
1941
  (!isIndicatorVertical && !isTargetSplitPaneVertical);
1874
1942
  const isRTL = finalDockingDirection === 'rtl';
1875
- const splitterSize = targetParent.useFixedSize
1876
- ? this.defaultSplitterSize
1877
- : 0;
1943
+ const splitterSize = targetParent.useFixedSize ? this.getSplitterSize() : 0;
1878
1944
  const panesTotalSize = panes.reduce((a, b) => a + (b?.size && b.size >= 0 ? b.size : IGC_DEFAULT_PANE_SIZE), 0) +
1879
1945
  (panes.length - 1) * splitterSize;
1880
1946
  const beforePanesTotalSize = !isRTL || isIndicatorVertical
@@ -91,6 +91,24 @@ export default class IgcContentPaneComponent extends IgcContentPaneComponent_bas
91
91
  */
92
92
  set unpinnedSize(value: number);
93
93
  get unpinnedSize(): number;
94
+ private _minResizeWidth;
95
+ private _minResizeHeight;
96
+ /**
97
+ * The minimum width of the pane in pixels during resizing.
98
+ *
99
+ * @attr min-resize-width
100
+ * @default 42
101
+ */
102
+ set minResizeWidth(value: number | undefined);
103
+ get minResizeWidth(): number;
104
+ /**
105
+ * The minimum height of the pane in pixels during resizing.
106
+ *
107
+ * @attr min-resize-height
108
+ * @default 42
109
+ */
110
+ set minResizeHeight(value: number | undefined);
111
+ get minResizeHeight(): number;
94
112
  connectedCallback(): void;
95
113
  protected updated(): void;
96
114
  private _updateFlex;