From c6fd52c2c91bb180808e0d1ec99848edc4aabe9f Mon Sep 17 00:00:00 2001 From: Rene Haas Date: Mon, 29 May 2023 12:35:45 +0200 Subject: [PATCH] move padding & content elements classnames to data attribute to prevent overwriting by 3rd party libs --- packages/overlayscrollbars/src/classnames.ts | 5 +++-- .../structureSetup/structureSetup.elements.ts | 13 ++++++------ .../updateSegments/overflowUpdateSegment.ts | 21 +++++++++---------- .../src/styles/structure.scss | 21 +++++++++---------- .../structureSetup.elements.test.ts | 8 +++---- 5 files changed, 33 insertions(+), 35 deletions(-) diff --git a/packages/overlayscrollbars/src/classnames.ts b/packages/overlayscrollbars/src/classnames.ts index 0ff9630..81c24a2 100644 --- a/packages/overlayscrollbars/src/classnames.ts +++ b/packages/overlayscrollbars/src/classnames.ts @@ -3,7 +3,9 @@ export const classNameEnvironmentFlexboxGlue = `${classNameEnvironment}-flexbox- export const classNameEnvironmentFlexboxGlueMax = `${classNameEnvironmentFlexboxGlue}-max`; export const dataAttributeHost = 'data-overlayscrollbars'; +export const dataAttributePadding = 'data-overlayscrollbars-padding'; export const dataAttributeViewport = 'data-overlayscrollbars-viewport'; +export const dataAttributeContent = 'data-overlayscrollbars-content'; export const dataAttributeInitialize = 'data-overlayscrollbars-initialize'; export const dataAttributeHostOverflowX = `${dataAttributeHost}-overflow-x`; export const dataAttributeHostOverflowY = `${dataAttributeHost}-overflow-y`; @@ -11,11 +13,10 @@ export const dataValueHostOverflowVisible = 'overflowVisible'; export const dataValueHostScrollbarHidden = 'scrollbarHidden'; export const dataValueHostScrollbarPressed = 'scrollbarPressed'; export const dataValueHostUpdating = 'updating'; -export const classNamePadding = 'os-padding'; export const dataValueViewportArrange = 'arrange'; export const dataValueViewportScrollbarHidden = 'scrollbarHidden'; export const dataValueViewportOverflowVisible = 'overflowVisible'; -export const classNameContent = 'os-content'; +export const dataValuePaddingOverflowVisible = 'overflowVisible'; export const classNameOverflowVisible = `os-overflow-visible`; export const classNameScrollbarHidden = `os-scrollbar-hidden`; diff --git a/packages/overlayscrollbars/src/setups/structureSetup/structureSetup.elements.ts b/packages/overlayscrollbars/src/setups/structureSetup/structureSetup.elements.ts index cf0cc1d..f80b8e3 100644 --- a/packages/overlayscrollbars/src/setups/structureSetup/structureSetup.elements.ts +++ b/packages/overlayscrollbars/src/setups/structureSetup/structureSetup.elements.ts @@ -25,11 +25,11 @@ import { dataAttributeInitialize, dataAttributeHostOverflowX, dataAttributeHostOverflowY, - classNamePadding, - classNameContent, classNameScrollbarHidden, dataAttributeViewport, dataValueViewportScrollbarHidden, + dataAttributePadding, + dataAttributeContent, } from '~/classnames'; import { getEnvironment } from '~/environment'; import { getPlugins, scrollbarsHidingPluginName } from '~/plugins'; @@ -238,13 +238,13 @@ export const createStructureSetupElements = ( const contentSlot = viewportIsTargetBody ? _target : _content || _viewport; const appendElements = () => { attr(_host, dataAttributeHost, viewportIsTarget ? 'viewport' : 'host'); + attr(_padding, dataAttributePadding, ''); + attr(_content, dataAttributeContent, ''); if (!viewportIsTarget) { attr(_viewport, dataAttributeViewport, ''); } - const removePaddingClass = addClass(_padding, classNamePadding); - const removeContentClass = addClass(_content, classNameContent); const removeHtmlClass = isBody && !viewportIsTarget ? addClass(parent(targetElement), classNameScrollbarHidden) @@ -267,6 +267,8 @@ export const createStructureSetupElements = ( push(destroyFns, () => { removeHtmlClass(); + removeAttr(_padding, dataAttributePadding); + removeAttr(_content, dataAttributeContent); removeAttr(_viewport, dataAttributeHostOverflowX); removeAttr(_viewport, dataAttributeHostOverflowY); removeAttr(_viewport, dataAttributeViewport); @@ -280,9 +282,6 @@ export const createStructureSetupElements = ( if (elementIsGenerated(_padding)) { unwrap(_padding); } - - removePaddingClass(); - removeContentClass(); }); if (_nativeScrollbarsHiding && !viewportIsTarget) { diff --git a/packages/overlayscrollbars/src/setups/structureSetup/updateSegments/overflowUpdateSegment.ts b/packages/overlayscrollbars/src/setups/structureSetup/updateSegments/overflowUpdateSegment.ts index aa7697a..ab21c4f 100644 --- a/packages/overlayscrollbars/src/setups/structureSetup/updateSegments/overflowUpdateSegment.ts +++ b/packages/overlayscrollbars/src/setups/structureSetup/updateSegments/overflowUpdateSegment.ts @@ -5,8 +5,6 @@ import { scrollSize, fractionalSize, equalWH, - addClass, - removeClass, clientSize, equalXY, attrClass, @@ -14,7 +12,6 @@ import { } from '~/support'; import { getEnvironment } from '~/environment'; import { - classNameOverflowVisible, dataAttributeHost, dataAttributeHostOverflowX, dataAttributeHostOverflowY, @@ -22,6 +19,9 @@ import { dataValueHostOverflowVisible, dataValueViewportScrollbarHidden, dataValueViewportOverflowVisible, + dataAttributeViewport, + dataAttributePadding, + dataValuePaddingOverflowVisible, } from '~/classnames'; import { getPlugins, scrollbarsHidingPluginName } from '~/plugins'; import type { WH, XY } from '~/support'; @@ -80,12 +80,6 @@ const getOverflowAmount = (viewportScrollSize: WH, viewportClientSize: W }; }; -const conditionalClass = ( - elm: Element | false | null | undefined, - classNames: string, - add: boolean -) => (add ? addClass(elm, classNames) : removeClass(elm, classNames)); - const overflowIsVisible = (overflowBehavior: string) => overflowBehavior.indexOf(strVisible) === 0; /** @@ -508,9 +502,14 @@ export const createOverflowUpdateSegment: CreateStructureUpdateSegment = ( } attrClass(_host, dataAttributeHost, dataValueHostOverflowVisible, removeClipping); - conditionalClass(_padding, classNameOverflowVisible, removeClipping); + attrClass(_padding, dataAttributePadding, dataValuePaddingOverflowVisible, removeClipping); if (!_viewportIsTarget) { - _viewportAddRemoveClass(dataValueViewportOverflowVisible, '', overflowVisible); + attrClass( + _viewport, + dataAttributeViewport, + dataValueViewportOverflowVisible, + overflowVisible + ); } const [overflowStyle, overflowStyleChanged] = updateOverflowStyleCache( diff --git a/packages/overlayscrollbars/src/styles/structure.scss b/packages/overlayscrollbars/src/styles/structure.scss index 497f9bf..445ec77 100644 --- a/packages/overlayscrollbars/src/styles/structure.scss +++ b/packages/overlayscrollbars/src/styles/structure.scss @@ -113,13 +113,13 @@ html[data-overlayscrollbars] > body { position: relative; } [data-overlayscrollbars~='host'], -.os-padding { +[data-overlayscrollbars-padding] { display: flex; flex-direction: row !important; flex-wrap: nowrap !important; } -.os-padding, +[data-overlayscrollbars-padding], [data-overlayscrollbars-viewport] { box-sizing: inherit; position: relative; // needed for correct padding styles @@ -148,7 +148,7 @@ html[data-overlayscrollbars] > body { } } -.os-padding, +[data-overlayscrollbars-padding], [data-overlayscrollbars-viewport] { overflow: hidden; } @@ -158,6 +158,7 @@ html[data-overlayscrollbars] > body { overflow: hidden; } [data-overlayscrollbars~='overflowVisible'], +[data-overlayscrollbars-padding~='overflowVisible'], [data-overlayscrollbars-viewport~='overflowVisible'] { overflow: visible; } @@ -179,11 +180,7 @@ html[data-overlayscrollbars] > body { scroll-behavior: auto !important; } -.os-overflow-visible { - overflow: visible; -} - -.os-content { +[data-overlayscrollbars-content] { box-sizing: inherit; } @@ -192,13 +189,15 @@ html[data-overlayscrollbars] > body { */ [data-overlayscrollbars-grid], -[data-overlayscrollbars-grid] .os-padding { +[data-overlayscrollbars-grid] [data-overlayscrollbars-padding] { display: grid; grid-template: 1fr / 1fr; } -[data-overlayscrollbars-grid] > .os-padding, +[data-overlayscrollbars-grid] > [data-overlayscrollbars-padding], [data-overlayscrollbars-grid] > [data-overlayscrollbars-viewport], -[data-overlayscrollbars-grid] > .os-padding > [data-overlayscrollbars-viewport] { +[data-overlayscrollbars-grid] + > [data-overlayscrollbars-padding] + > [data-overlayscrollbars-viewport] { height: auto !important; width: auto !important; } diff --git a/packages/overlayscrollbars/test/jest-jsdom/setups/structureSetup/structureSetup.elements.test.ts b/packages/overlayscrollbars/test/jest-jsdom/setups/structureSetup/structureSetup.elements.test.ts index 0a6e391..e83a7e5 100644 --- a/packages/overlayscrollbars/test/jest-jsdom/setups/structureSetup/structureSetup.elements.test.ts +++ b/packages/overlayscrollbars/test/jest-jsdom/setups/structureSetup/structureSetup.elements.test.ts @@ -3,8 +3,8 @@ import { resolveInitialization } from '~/initialization'; import { dataAttributeHost, dataAttributeInitialize, - classNamePadding, - classNameContent, + dataAttributePadding, + dataAttributeContent, dataAttributeViewport, } from '~/classnames'; import { getEnvironment } from '~/environment'; @@ -88,9 +88,9 @@ const clearBody = () => { const getElements = (targetType: TargetType) => { const target = getTarget(targetType); const host = document.querySelector(`[${dataAttributeHost}]`)!; - const padding = document.querySelector(`.${classNamePadding}`)!; + const padding = document.querySelector(`[${dataAttributePadding}]`)!; const viewport = document.querySelector(`[${dataAttributeViewport}]`)!; - const content = document.querySelector(`.${classNameContent}`)!; + const content = document.querySelector(`[${dataAttributeContent}]`)!; const children = targetType === 'textarea' ? document.querySelector(`#${textareaId}`)