@progress/kendo-angular-common 23.3.0-develop.8 → 23.3.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.
@@ -369,6 +369,9 @@ const hasFocusableParent = (element, container) => {
369
369
  };
370
370
 
371
371
  const isVisible = (element) => {
372
+ if (!isDocumentAvailable() || !element?.getBoundingClientRect) {
373
+ return false;
374
+ }
372
375
  const rect = element.getBoundingClientRect();
373
376
  const hasSize = rect.width > 0 && rect.height > 0;
374
377
  const hasPosition = rect.x !== 0 && rect.y !== 0;
@@ -555,17 +558,39 @@ class ResizeService {
555
558
  }
556
559
 
557
560
  // eslint-disable import/no-deprecated
558
- // TODO:NG13 CSP
559
- const div = (style) => {
561
+ const applyStyles = (el, styles) => {
562
+ for (const prop in styles) {
563
+ el.style.setProperty(prop, styles[prop]);
564
+ }
565
+ };
566
+ const div = (styles) => {
560
567
  const el = document.createElement('div');
561
- el.style.cssText = style;
568
+ applyStyles(el, styles);
562
569
  return el;
563
570
  };
564
571
  const computedProp = (elem, prop) => getComputedStyle(elem, null).getPropertyValue(prop);
565
- const WRAP_STYLE = 'position: absolute; display: block; left: 0; top: 0; right: 0; bottom: 0; z-index: -1;' +
566
- 'overflow: hidden; visibility: hidden;';
567
- const EXPAND_CHILD_STYLE = 'position: absolute; left: 0; top: 0; transition: 0s;';
568
- const SHRINK_CHILD_STYLE = EXPAND_CHILD_STYLE + 'width: 200%; height: 200%;';
572
+ const WRAP_STYLES = {
573
+ 'position': 'absolute',
574
+ 'display': 'block',
575
+ 'left': '0',
576
+ 'top': '0',
577
+ 'right': '0',
578
+ 'bottom': '0',
579
+ 'z-index': '-1',
580
+ 'overflow': 'hidden',
581
+ 'visibility': 'hidden'
582
+ };
583
+ const EXPAND_CHILD_STYLES = {
584
+ 'position': 'absolute',
585
+ 'left': '0',
586
+ 'top': '0',
587
+ 'transition': '0s'
588
+ };
589
+ const SHRINK_CHILD_STYLES = {
590
+ ...EXPAND_CHILD_STYLES,
591
+ 'width': '200%',
592
+ 'height': '200%'
593
+ };
569
594
  class ResizeCompatService extends ResizeService {
570
595
  element;
571
596
  ngZone;
@@ -620,14 +645,14 @@ class ResizeCompatService extends ResizeService {
620
645
  }
621
646
  render() {
622
647
  const element = this.element?.nativeElement;
623
- element.style.cssText = WRAP_STYLE;
648
+ applyStyles(element, WRAP_STYLES);
624
649
  element.setAttribute('dir', 'ltr');
625
- this.expand = div(WRAP_STYLE);
626
- this.expandChild = div(EXPAND_CHILD_STYLE);
650
+ this.expand = div(WRAP_STYLES);
651
+ this.expandChild = div(EXPAND_CHILD_STYLES);
627
652
  this.expand.appendChild(this.expandChild);
628
653
  element.appendChild(this.expand);
629
- this.shrink = div(WRAP_STYLE);
630
- const shrinkChild = div(SHRINK_CHILD_STYLE);
654
+ this.shrink = div(WRAP_STYLES);
655
+ const shrinkChild = div(SHRINK_CHILD_STYLES);
631
656
  this.shrink.appendChild(shrinkChild);
632
657
  element.appendChild(this.shrink);
633
658
  }
@@ -1649,40 +1674,99 @@ class PreventableEvent {
1649
1674
 
1650
1675
  const canCreateElement = () => isDocumentAvailable() && document.createElement;
1651
1676
  const propName = '--kendo-scrollbar-width';
1677
+ let cachedScrollbarWidth = null;
1678
+ let cachedPixelRatio;
1679
+ let cachedRtlScrollLeft = null;
1652
1680
  /**
1653
1681
  * @hidden
1654
1682
  */
1655
1683
  const scrollbarWidth = () => {
1656
- let scrollbarWidth = 0;
1657
- if (canCreateElement()) {
1658
- const div = document.createElement('div');
1659
- div.style.cssText = 'overflow:scroll;overflow-x:hidden;zoom:1;clear:both;display:block';
1660
- div.innerHTML = ' ';
1661
- document.body.appendChild(div);
1662
- scrollbarWidth = div.offsetWidth - div.scrollWidth;
1663
- document.body.removeChild(div);
1664
- }
1665
- return scrollbarWidth;
1684
+ if (cachedScrollbarWidth === null && canCreateElement()) {
1685
+ cachedPixelRatio = window.devicePixelRatio || 1;
1686
+ const outer = document.createElement('div');
1687
+ const inner = document.createElement('div');
1688
+ outer.style.overflow = 'scroll';
1689
+ outer.style.overflowX = 'hidden';
1690
+ outer.style.zoom = '1';
1691
+ outer.style.clear = 'both';
1692
+ outer.style.display = 'block';
1693
+ outer.style.width = '100px';
1694
+ outer.style.visibility = 'hidden';
1695
+ inner.style.width = '100%';
1696
+ inner.style.display = 'block';
1697
+ outer.appendChild(inner);
1698
+ document.body.appendChild(outer);
1699
+ cachedScrollbarWidth = outer.getBoundingClientRect().width - inner.getBoundingClientRect().width;
1700
+ document.body.removeChild(outer);
1701
+ }
1702
+ return cachedScrollbarWidth;
1703
+ };
1704
+ /**
1705
+ * @hidden
1706
+ */
1707
+ const rtlScrollLeft = () => {
1708
+ if (cachedRtlScrollLeft === null && canCreateElement()) {
1709
+ const outer = document.createElement('div');
1710
+ outer.style.direction = 'rtl';
1711
+ outer.style.display = 'block';
1712
+ outer.style.clear = 'both';
1713
+ outer.style.width = '100px';
1714
+ outer.style.visibility = 'hidden';
1715
+ outer.style.position = 'absolute';
1716
+ outer.style.left = '-10000px';
1717
+ outer.style.overflow = 'scroll';
1718
+ outer.style.zoom = '1';
1719
+ const inner = document.createElement('div');
1720
+ inner.style.width = '200px';
1721
+ inner.style.height = '1px';
1722
+ outer.append(inner);
1723
+ document.body.appendChild(outer);
1724
+ const initial = outer.scrollLeft;
1725
+ outer.scrollLeft = -1;
1726
+ cachedRtlScrollLeft = outer.scrollLeft < 0 ? outer.scrollLeft : initial;
1727
+ document.body.removeChild(outer);
1728
+ }
1729
+ return cachedRtlScrollLeft;
1666
1730
  };
1667
1731
  /**
1668
1732
  * @hidden
1669
1733
  */
1670
- class ScrollbarWidthService {
1734
+ class ScrollbarService {
1671
1735
  changes = new EventEmitter();
1672
- constructor() {
1736
+ subscription;
1737
+ constructor(ngZone) {
1673
1738
  if (typeof window !== 'undefined' && isDocumentAvailable()) {
1674
1739
  document.body.style.setProperty(propName, `${scrollbarWidth()}px`);
1740
+ ngZone.runOutsideAngular(() => {
1741
+ this.subscription = fromEvent(window, 'resize').pipe(auditTime(100)).subscribe(() => {
1742
+ if (cachedPixelRatio !== window.devicePixelRatio) {
1743
+ cachedScrollbarWidth = null;
1744
+ document.body.style.setProperty(propName, `${scrollbarWidth()}px`);
1745
+ this.changes.emit();
1746
+ }
1747
+ });
1748
+ });
1675
1749
  }
1676
1750
  }
1677
- static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: ScrollbarWidthService, deps: [], target: i0.ɵɵFactoryTarget.Injectable });
1678
- static ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: ScrollbarWidthService, providedIn: 'root' });
1751
+ get scrollbarWidth() {
1752
+ return scrollbarWidth();
1753
+ }
1754
+ get rtlScrollLeft() {
1755
+ return rtlScrollLeft();
1756
+ }
1757
+ ngOnDestroy() {
1758
+ this.subscription?.unsubscribe();
1759
+ this.subscription = null;
1760
+ }
1761
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: ScrollbarService, deps: [{ token: i0.NgZone }], target: i0.ɵɵFactoryTarget.Injectable });
1762
+ static ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: ScrollbarService, providedIn: 'root' });
1679
1763
  }
1680
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: ScrollbarWidthService, decorators: [{
1764
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: ScrollbarService, decorators: [{
1681
1765
  type: Injectable,
1682
1766
  args: [{
1683
1767
  providedIn: 'root'
1684
1768
  }]
1685
- }], ctorParameters: () => [] });
1769
+ }], ctorParameters: () => [{ type: i0.NgZone }] });
1686
1770
 
1687
1771
  /**
1688
1772
  * @hidden
@@ -2037,5 +2121,5 @@ const replaceMessagePlaceholder = (message, name, value) => (message ?? '').repl
2037
2121
  * Generated bundle index. Do not edit.
2038
2122
  */
2039
2123
 
2040
- export { DraggableDirective, EventsOutsideAngularDirective, KENDO_ADORNMENTS, KENDO_COMMON, KENDO_DRAGGABLE, KENDO_EVENTS, KENDO_RESIZESENSOR, KENDO_TEMPLATE_CONTEXT, KENDO_TOGGLEBUTTONTABSTOP, KENDO_WATERMARK, KendoInput, Keys, MultiTabStop, PrefixTemplateDirective, PreventableEvent, ResizeBatchService, ResizeCompatService, ResizeObserverService, ResizeSensorComponent, ScrollbarWidthService, SeparatorComponent, SuffixTemplateDirective, TemplateContextDirective, ToggleButtonTabStopDirective, WatermarkOverlayComponent, anyChanged, applyAttributes, areObjectsEqual, closest, closestBySelector, closestInScope, contains, findElement, findFocusable, findFocusableChild, firefoxMaxHeight, focusableSelector, getLicenseMessage, getter, guid, hasClasses, hasFocusableParent, hasObservers, isChanged, isControlRequired, isDocumentAvailable, isFirefox, isFocusable, isFocusableWithTabKey, isObject, isObjectPresent, isPresent, isSafari, isSet, isString, isVisible, matchesClasses, matchesNodeName, normalizeKeys, parseAttributes, parseCSSClassNames, processCssValue, removeHTMLAttributes, replaceMessagePlaceholder, rtlScrollPosition, scrollbarWidth, setHTMLAttributes, setter, shouldShowValidationUI, splitStringToArray };
2124
+ export { ScrollbarService as BrowserSupportService, DraggableDirective, EventsOutsideAngularDirective, KENDO_ADORNMENTS, KENDO_COMMON, KENDO_DRAGGABLE, KENDO_EVENTS, KENDO_RESIZESENSOR, KENDO_TEMPLATE_CONTEXT, KENDO_TOGGLEBUTTONTABSTOP, KENDO_WATERMARK, KendoInput, Keys, MultiTabStop, PrefixTemplateDirective, PreventableEvent, ResizeBatchService, ResizeCompatService, ResizeObserverService, ResizeSensorComponent, ScrollbarService, SeparatorComponent, SuffixTemplateDirective, TemplateContextDirective, ToggleButtonTabStopDirective, WatermarkOverlayComponent, anyChanged, applyAttributes, areObjectsEqual, closest, closestBySelector, closestInScope, contains, findElement, findFocusable, findFocusableChild, firefoxMaxHeight, focusableSelector, getLicenseMessage, getter, guid, hasClasses, hasFocusableParent, hasObservers, isChanged, isControlRequired, isDocumentAvailable, isFirefox, isFocusable, isFocusableWithTabKey, isObject, isObjectPresent, isPresent, isSafari, isSet, isString, isVisible, matchesClasses, matchesNodeName, normalizeKeys, parseAttributes, parseCSSClassNames, processCssValue, removeHTMLAttributes, replaceMessagePlaceholder, rtlScrollLeft, rtlScrollPosition, scrollbarWidth, setHTMLAttributes, setter, shouldShowValidationUI, splitStringToArray };
2041
2125
 
package/index.d.ts CHANGED
@@ -17,7 +17,7 @@ export * from './utils/setter';
17
17
  export * from './watermark';
18
18
  export * from './adornments';
19
19
  export { PreventableEvent } from './preventable-event';
20
- export { ScrollbarWidthService, scrollbarWidth } from './utils/scrollbar-width.service';
20
+ export { ScrollbarService, ScrollbarService as BrowserSupportService, scrollbarWidth, rtlScrollLeft } from './utils/scrollbar.service';
21
21
  export * from './toggle-button-tab-stop';
22
22
  export * from './directives';
23
23
  export * from './template-context';
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@progress/kendo-angular-common",
3
- "version": "23.3.0-develop.8",
3
+ "version": "23.3.0",
4
4
  "description": "Kendo UI for Angular - Utility Package",
5
5
  "license": "SEE LICENSE IN LICENSE.md",
6
6
  "author": "Progress",
@@ -23,7 +23,7 @@
23
23
  "@progress/kendo-common": "^1.0.1",
24
24
  "@progress/kendo-draggable": "^3.0.2",
25
25
  "tslib": "^2.3.1",
26
- "@progress/kendo-angular-schematics": "23.3.0-develop.8"
26
+ "@progress/kendo-angular-schematics": "23.3.0"
27
27
  },
28
28
  "publishConfig": {
29
29
  "access": "public"
@@ -2,7 +2,7 @@
2
2
  * Copyright © 2026 Progress Software Corporation. All rights reserved.
3
3
  * Licensed under commercial license. See LICENSE.md in the project root for more information
4
4
  *-------------------------------------------------------------------------------------------*/
5
- import { EventEmitter } from '@angular/core';
5
+ import { EventEmitter, NgZone, OnDestroy } from '@angular/core';
6
6
  import * as i0 from "@angular/core";
7
7
  /**
8
8
  * @hidden
@@ -11,9 +11,17 @@ export declare const scrollbarWidth: () => number;
11
11
  /**
12
12
  * @hidden
13
13
  */
14
- export declare class ScrollbarWidthService {
14
+ export declare const rtlScrollLeft: () => number;
15
+ /**
16
+ * @hidden
17
+ */
18
+ export declare class ScrollbarService implements OnDestroy {
15
19
  changes: EventEmitter<any>;
16
- constructor();
17
- static ɵfac: i0.ɵɵFactoryDeclaration<ScrollbarWidthService, never>;
18
- static ɵprov: i0.ɵɵInjectableDeclaration<ScrollbarWidthService>;
20
+ private subscription;
21
+ constructor(ngZone: NgZone);
22
+ get scrollbarWidth(): number;
23
+ get rtlScrollLeft(): number;
24
+ ngOnDestroy(): void;
25
+ static ɵfac: i0.ɵɵFactoryDeclaration<ScrollbarService, never>;
26
+ static ɵprov: i0.ɵɵInjectableDeclaration<ScrollbarService>;
19
27
  }