@ascentgl/ads-ui 21.112.0 → 21.114.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.
|
@@ -6302,6 +6302,8 @@ class AdsDatepickerComponent extends AdsDatetimepickerComponent {
|
|
|
6302
6302
|
this.inputModifiedByKeyHandler = false;
|
|
6303
6303
|
/** @ignore */
|
|
6304
6304
|
this.elementRef = inject(ElementRef);
|
|
6305
|
+
/** @ignore */
|
|
6306
|
+
this.overlayContainerRef = inject(OverlayContainer);
|
|
6305
6307
|
}
|
|
6306
6308
|
/** @ignore */
|
|
6307
6309
|
ngOnInit() {
|
|
@@ -6314,6 +6316,8 @@ class AdsDatepickerComponent extends AdsDatetimepickerComponent {
|
|
|
6314
6316
|
ngOnDestroy() {
|
|
6315
6317
|
super.ngOnDestroy();
|
|
6316
6318
|
this.intersectionObserver?.disconnect();
|
|
6319
|
+
this.scrollPassthroughCleanup?.();
|
|
6320
|
+
this.scrollPassthroughCleanup = undefined;
|
|
6317
6321
|
}
|
|
6318
6322
|
/** @ignore */
|
|
6319
6323
|
setupIntersectionObserver() {
|
|
@@ -6330,6 +6334,85 @@ class AdsDatepickerComponent extends AdsDatetimepickerComponent {
|
|
|
6330
6334
|
});
|
|
6331
6335
|
this.intersectionObserver.observe(this.elementRef.nativeElement);
|
|
6332
6336
|
}
|
|
6337
|
+
/**
|
|
6338
|
+
* @ignore
|
|
6339
|
+
* The CDK overlay backdrop has `pointer-events: auto` which intercepts all
|
|
6340
|
+
* pointer / wheel events, preventing native scroll on underlying containers.
|
|
6341
|
+
* Disabling pointer events on the backdrop lets the browser handle scrolling
|
|
6342
|
+
* natively (preserving momentum / inertia). A document-level pointerdown
|
|
6343
|
+
* listener replaces the lost backdrop click-to-close behaviour.
|
|
6344
|
+
*/
|
|
6345
|
+
onOpened() {
|
|
6346
|
+
super.onOpened();
|
|
6347
|
+
this.setupScrollPassthrough();
|
|
6348
|
+
}
|
|
6349
|
+
/** @ignore */
|
|
6350
|
+
onClosed() {
|
|
6351
|
+
this.scrollPassthroughCleanup?.();
|
|
6352
|
+
this.scrollPassthroughCleanup = undefined;
|
|
6353
|
+
super.onClosed();
|
|
6354
|
+
}
|
|
6355
|
+
/** @ignore */
|
|
6356
|
+
setupScrollPassthrough() {
|
|
6357
|
+
this.scrollPassthroughCleanup?.();
|
|
6358
|
+
this.scrollPassthroughCleanup = undefined;
|
|
6359
|
+
const container = this.overlayContainerRef.getContainerElement();
|
|
6360
|
+
const backdrop = container.querySelector('.cdk-overlay-backdrop');
|
|
6361
|
+
// Disable pointer events on the backdrop so that wheel / touch events
|
|
6362
|
+
// reach the scroll container natively. This preserves momentum scrolling
|
|
6363
|
+
// and avoids the scroll-stop when closeOnOutOfView closes the picker mid-scroll.
|
|
6364
|
+
if (backdrop) {
|
|
6365
|
+
backdrop.style.pointerEvents = 'none';
|
|
6366
|
+
}
|
|
6367
|
+
const cleanupFns = [];
|
|
6368
|
+
// Replace the backdrop click-to-close with a document-level pointerdown
|
|
6369
|
+
// listener. Delay one animation frame so the interaction that opened the
|
|
6370
|
+
// picker does not immediately close it.
|
|
6371
|
+
let pointerDownCleanup;
|
|
6372
|
+
const rafId = requestAnimationFrame(() => {
|
|
6373
|
+
const onPointerDown = (event) => {
|
|
6374
|
+
if (!this.picker?.opened)
|
|
6375
|
+
return;
|
|
6376
|
+
const overlayPane = container.querySelector('.cdk-overlay-pane');
|
|
6377
|
+
const clickedInside = overlayPane?.contains(event.target) ||
|
|
6378
|
+
this.elementRef.nativeElement.contains(event.target);
|
|
6379
|
+
if (!clickedInside) {
|
|
6380
|
+
this.picker.close();
|
|
6381
|
+
}
|
|
6382
|
+
};
|
|
6383
|
+
document.addEventListener('pointerdown', onPointerDown);
|
|
6384
|
+
pointerDownCleanup = () => document.removeEventListener('pointerdown', onPointerDown);
|
|
6385
|
+
});
|
|
6386
|
+
cleanupFns.push(() => {
|
|
6387
|
+
cancelAnimationFrame(rafId);
|
|
6388
|
+
pointerDownCleanup?.();
|
|
6389
|
+
});
|
|
6390
|
+
// Reposition the calendar overlay when a non-document scroll container scrolls.
|
|
6391
|
+
// CDK ScrollDispatcher only detects window scroll and CdkScrollable directives,
|
|
6392
|
+
// not arbitrary overflow containers, so we trigger the update manually.
|
|
6393
|
+
const scrollTarget = this.findScrollableAncestor(this.elementRef.nativeElement);
|
|
6394
|
+
if (scrollTarget) {
|
|
6395
|
+
const onScroll = () => {
|
|
6396
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
6397
|
+
this.picker?._popupRef?.updatePosition();
|
|
6398
|
+
};
|
|
6399
|
+
scrollTarget.addEventListener('scroll', onScroll, { passive: true });
|
|
6400
|
+
cleanupFns.push(() => scrollTarget.removeEventListener('scroll', onScroll));
|
|
6401
|
+
}
|
|
6402
|
+
this.scrollPassthroughCleanup = () => cleanupFns.forEach((fn) => fn());
|
|
6403
|
+
}
|
|
6404
|
+
/** @ignore - Walk up the DOM to find the first ancestor with overflow-y: auto|scroll */
|
|
6405
|
+
findScrollableAncestor(node) {
|
|
6406
|
+
let current = node.parentElement;
|
|
6407
|
+
while (current) {
|
|
6408
|
+
const { overflowY } = getComputedStyle(current);
|
|
6409
|
+
if (overflowY === 'auto' || overflowY === 'scroll') {
|
|
6410
|
+
return current;
|
|
6411
|
+
}
|
|
6412
|
+
current = current.parentElement;
|
|
6413
|
+
}
|
|
6414
|
+
return null;
|
|
6415
|
+
}
|
|
6333
6416
|
/** @ignore - Override to dispatch change event on blur when input was modified programmatically */
|
|
6334
6417
|
touchControls() {
|
|
6335
6418
|
// Mark controls as touched BEFORE dispatching the change event.
|