@ui5/webcomponents-base 0.0.0-2723566a3 → 0.0.0-274170508
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/.eslintignore +3 -2
- package/CHANGELOG.md +241 -0
- package/README.md +53 -7
- package/bundle.esm.js +13 -11
- package/dist/Boot.js +34 -18
- package/dist/CSP.js +59 -0
- package/dist/CustomElementsRegistry.js +60 -4
- package/dist/CustomElementsScope.js +20 -98
- package/dist/CustomElementsScopeUtils.js +108 -0
- package/dist/Device.js +20 -1
- package/dist/EventProvider.js +19 -25
- package/dist/FeaturesRegistry.js +4 -1
- package/dist/FontFace.js +7 -95
- package/dist/InitialConfiguration.js +11 -7
- package/dist/Keys.js +56 -0
- package/dist/ManagedStyles.js +83 -0
- package/dist/Render.js +3 -1
- package/dist/Runtimes.js +107 -0
- package/dist/StaticAreaItem.js +15 -10
- package/dist/SystemCSSVars.js +4 -25
- package/dist/UI5Element.js +71 -60
- package/dist/UI5ElementMetadata.js +18 -2
- package/dist/asset-registries/Icons.js +23 -9
- package/dist/asset-registries/Illustrations.js +10 -3
- package/dist/asset-registries/LocaleData.js +18 -4
- package/dist/asset-registries/Themes.js +6 -2
- package/dist/asset-registries/i18n.js +3 -1
- package/dist/assets/bundle.esm.3bc98648.js +43 -0
- package/dist/assets-meta/IconCollectionsAlias.js +18 -0
- package/dist/config/Icons.js +52 -0
- package/dist/config/Theme.js +25 -0
- package/dist/css/BusyIndicator.css +80 -0
- package/dist/css/FontFace.css +66 -0
- package/dist/css/OverrideFontFace.css +32 -0
- package/dist/css/SystemCSSVars.css +17 -0
- package/dist/delegate/ItemNavigation.js +75 -4
- package/dist/features/F6Navigation.js +110 -0
- package/dist/features/OpenUI5Enablement.js +119 -0
- package/dist/generated/AssetParameters.js +1 -1
- package/dist/generated/VersionInfo.js +10 -0
- package/dist/generated/css/BusyIndicator.css.js +5 -0
- package/dist/generated/css/FontFace.css.js +5 -0
- package/dist/generated/css/OverrideFontFace.css.js +5 -0
- package/dist/generated/css/SystemCSSVars.css.js +5 -0
- package/dist/i18nBundle.js +34 -3
- package/dist/renderer/LitRenderer.js +33 -12
- package/dist/renderer/directives/style-map.js +72 -0
- package/dist/renderer/executeTemplate.js +19 -2
- package/dist/sap/base/Log.js +2 -10
- package/dist/sap/base/assert.js +1 -5
- package/dist/sap/base/security/encodeCSS.js +14 -0
- package/dist/sap/base/security/encodeXML.js +23 -0
- package/dist/sap/base/strings/toHex.js +8 -0
- package/dist/sap/ui/thirdparty/caja-html-sanitizer.js +1 -1
- package/dist/theming/CustomStyle.js +23 -3
- package/dist/theming/applyTheme.js +11 -10
- package/dist/theming/getEffectiveLinksHrefs.js +27 -0
- package/dist/theming/getEffectiveStyle.js +9 -0
- package/dist/theming/getStylesString.js +4 -2
- package/dist/theming/getThemeDesignerTheme.js +25 -5
- package/dist/theming/preloadLinks.js +23 -0
- package/dist/types/DOMReference.js +24 -0
- package/dist/types/DataType.js +12 -0
- package/dist/types/Float.js +4 -0
- package/dist/types/Integer.js +4 -0
- package/dist/updateShadowRoot.js +9 -6
- package/dist/util/AriaLabelHelper.js +2 -4
- package/dist/util/Caret.js +1 -14
- package/dist/util/ColorConversion.js +30 -2
- package/dist/util/FocusableElements.js +8 -6
- package/dist/util/InvisibleMessage.js +20 -9
- package/dist/util/TabbableElements.js +4 -0
- package/dist/util/createLinkInHead.js +19 -0
- package/dist/util/escapeRegex.js +10 -0
- package/dist/util/generateHighlightedMarkup.js +42 -0
- package/dist/util/getEffectiveScrollbarStyle.js +5 -0
- package/dist/util/getNormalizedTarget.js +16 -0
- package/dist/util/isDefaultSlotProvided.js +11 -0
- package/dist/util/isNodeHidden.js +1 -1
- package/hash.txt +1 -1
- package/lib/generate-asset-parameters/index.js +8 -5
- package/lib/generate-styles/index.js +26 -0
- package/lib/generate-version-info/index.js +32 -0
- package/package-scripts.js +25 -31
- package/package.json +11 -12
- package/src/Boot.js +34 -18
- package/src/CSP.js +59 -0
- package/src/CustomElementsRegistry.js +60 -4
- package/src/CustomElementsScope.js +20 -98
- package/src/CustomElementsScopeUtils.js +108 -0
- package/src/Device.js +20 -1
- package/src/EventProvider.js +19 -25
- package/src/FeaturesRegistry.js +4 -1
- package/src/FontFace.js +7 -95
- package/src/InitialConfiguration.js +11 -7
- package/src/Keys.js +56 -0
- package/src/ManagedStyles.js +83 -0
- package/src/Render.js +3 -1
- package/src/Runtimes.js +107 -0
- package/src/StaticAreaItem.js +15 -10
- package/src/SystemCSSVars.js +4 -25
- package/src/UI5Element.js +71 -60
- package/src/UI5ElementMetadata.js +18 -2
- package/src/asset-registries/Icons.js +23 -9
- package/src/asset-registries/Illustrations.js +10 -3
- package/src/asset-registries/LocaleData.js +18 -4
- package/src/asset-registries/Themes.js +6 -2
- package/src/asset-registries/i18n.js +3 -1
- package/src/assets-meta/IconCollectionsAlias.js +18 -0
- package/src/config/Icons.js +52 -0
- package/src/config/Theme.js +25 -0
- package/src/css/BusyIndicator.css +80 -0
- package/src/css/FontFace.css +66 -0
- package/src/css/OverrideFontFace.css +32 -0
- package/src/css/SystemCSSVars.css +17 -0
- package/src/delegate/ItemNavigation.js +75 -4
- package/src/features/F6Navigation.js +110 -0
- package/src/features/OpenUI5Enablement.js +119 -0
- package/src/i18nBundle.js +34 -3
- package/src/renderer/LitRenderer.js +33 -12
- package/src/renderer/directives/style-map.js +72 -0
- package/src/renderer/executeTemplate.js +19 -2
- package/src/theming/CustomStyle.js +23 -3
- package/src/theming/applyTheme.js +11 -10
- package/src/theming/getEffectiveLinksHrefs.js +27 -0
- package/src/theming/getEffectiveStyle.js +9 -0
- package/src/theming/getStylesString.js +4 -2
- package/src/theming/getThemeDesignerTheme.js +25 -5
- package/src/theming/preloadLinks.js +23 -0
- package/src/types/DOMReference.js +24 -0
- package/src/types/DataType.js +12 -0
- package/src/types/Float.js +4 -0
- package/src/types/Integer.js +4 -0
- package/src/updateShadowRoot.js +9 -6
- package/src/util/AriaLabelHelper.js +2 -4
- package/src/util/Caret.js +1 -14
- package/src/util/ColorConversion.js +30 -2
- package/src/util/FocusableElements.js +8 -6
- package/src/util/InvisibleMessage.js +20 -9
- package/src/util/TabbableElements.js +4 -0
- package/src/util/createLinkInHead.js +19 -0
- package/src/util/escapeRegex.js +10 -0
- package/src/util/generateHighlightedMarkup.js +42 -0
- package/src/util/getEffectiveScrollbarStyle.js +5 -0
- package/src/util/getNormalizedTarget.js +16 -0
- package/src/util/isDefaultSlotProvided.js +11 -0
- package/src/util/isNodeHidden.js +1 -1
- package/used-modules.txt +4 -1
- package/config/.eslintrc.js +0 -3
- package/config/rollup.config.js +0 -1
- package/dist/config/AssetsPath.js +0 -17
- package/dist/isLegacyBrowser.js +0 -3
- package/dist/resources/bundle.esm.js +0 -26
- package/dist/resources/bundle.esm.js.map +0 -1
- package/dist/test-resources/assets/Themes.js +0 -17
- package/dist/test-resources/elements/Child.js +0 -35
- package/dist/test-resources/elements/Generic.js +0 -84
- package/dist/test-resources/elements/GenericExt.js +0 -26
- package/dist/test-resources/elements/NoShadowDOM.js +0 -13
- package/dist/test-resources/elements/Parent.js +0 -41
- package/dist/test-resources/elements/WithStaticArea.js +0 -76
- package/dist/test-resources/pages/AllTestElements.html +0 -39
- package/dist/test-resources/pages/Configuration.html +0 -18
- package/dist/test-resources/pages/ConfigurationScript.html +0 -34
- package/dist/test-resources/pages/assets/messagebundle_de.properties +0 -1
- package/dist/test-resources/pages/assets/messagebundle_en.properties +0 -1
- package/dist/test-resources/pages/assets/messagebundle_es.properties +0 -1
- package/dist/test-resources/pages/assets/messagebundle_fr.properties +0 -1
- package/dist/test-resources/pages/i18n.html +0 -35
- package/dist/test-resources/specs/ConfigurationChange.spec.js +0 -27
- package/dist/test-resources/specs/ConfigurationScript.spec.js +0 -63
- package/dist/test-resources/specs/ConfigurationURL.spec.js +0 -93
- package/dist/test-resources/specs/CustomTheme.spec.js +0 -27
- package/dist/test-resources/specs/StaticArea.spec.js +0 -36
- package/dist/test-resources/specs/Theming.spec.js +0 -33
- package/dist/test-resources/specs/UI5ElementInvalidation.js +0 -242
- package/dist/test-resources/specs/UI5ElementLifecycle.js +0 -98
- package/dist/test-resources/specs/UI5ElementListenForChildPropChanges.spec.js +0 -75
- package/dist/test-resources/specs/UI5ElementMetadataExt.js +0 -42
- package/dist/test-resources/specs/UI5ElementPropertyValidation.js +0 -14
- package/dist/test-resources/specs/UI5ElementPropsAndAttrs.spec.js +0 -67
- package/dist/test-resources/specs/UI5ElementShadowDOM.js +0 -24
- package/dist/test-resources/specs/UI5ElementSlots.js +0 -36
- package/dist/theming/createThemePropertiesStyleTag.js +0 -20
- package/dist/util/encodeCSS.js +0 -24
- package/dist/util/findNodeOwner.js +0 -35
- package/src/config/AssetsPath.js +0 -17
- package/src/isLegacyBrowser.js +0 -3
- package/src/theming/createThemePropertiesStyleTag.js +0 -20
- package/src/util/encodeCSS.js +0 -24
- package/src/util/findNodeOwner.js +0 -35
|
@@ -1,31 +1,52 @@
|
|
|
1
|
-
import { render } from "lit-html";
|
|
2
1
|
import {
|
|
2
|
+
render,
|
|
3
3
|
html,
|
|
4
4
|
svg,
|
|
5
|
-
|
|
6
|
-
} from "
|
|
5
|
+
} from "lit-html";
|
|
6
|
+
import { getFeature } from "../FeaturesRegistry.js";
|
|
7
7
|
|
|
8
|
-
const
|
|
9
|
-
|
|
10
|
-
|
|
8
|
+
const effectiveHtml = (...args) => {
|
|
9
|
+
const LitStatic = getFeature("LitStatic");
|
|
10
|
+
const fn = LitStatic ? LitStatic.html : html;
|
|
11
|
+
return fn(...args);
|
|
12
|
+
};
|
|
13
|
+
|
|
14
|
+
const effectiveSvg = (...args) => {
|
|
15
|
+
const LitStatic = getFeature("LitStatic");
|
|
16
|
+
const fn = LitStatic ? LitStatic.svg : svg;
|
|
17
|
+
return fn(...args);
|
|
18
|
+
};
|
|
19
|
+
|
|
20
|
+
const litRender = (templateResult, domNode, styleStrOrHrefsArr, forStaticArea, { host } = {}) => {
|
|
21
|
+
const OpenUI5Enablement = getFeature("OpenUI5Enablement");
|
|
22
|
+
if (OpenUI5Enablement && !forStaticArea) {
|
|
23
|
+
templateResult = OpenUI5Enablement.wrapTemplateResultInBusyMarkup(effectiveHtml, host, templateResult);
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
if (typeof styleStrOrHrefsArr === "string") {
|
|
27
|
+
templateResult = effectiveHtml`<style>${styleStrOrHrefsArr}</style>${templateResult}`;
|
|
28
|
+
} else if (Array.isArray(styleStrOrHrefsArr) && styleStrOrHrefsArr.length) {
|
|
29
|
+
templateResult = effectiveHtml`${styleStrOrHrefsArr.map(href => effectiveHtml`<link type="text/css" rel="stylesheet" href="${href}">`)}${templateResult}`;
|
|
11
30
|
}
|
|
12
31
|
render(templateResult, domNode, { host });
|
|
13
32
|
};
|
|
14
33
|
|
|
15
34
|
const scopeTag = (tag, tags, suffix) => {
|
|
16
|
-
const
|
|
17
|
-
|
|
35
|
+
const LitStatic = getFeature("LitStatic");
|
|
36
|
+
if (LitStatic) {
|
|
37
|
+
return LitStatic.unsafeStatic((tags || []).includes(tag) ? `${tag}-${suffix}` : tag);
|
|
38
|
+
}
|
|
18
39
|
};
|
|
19
40
|
|
|
20
41
|
export {
|
|
21
|
-
html,
|
|
22
|
-
svg,
|
|
23
|
-
unsafeStatic,
|
|
42
|
+
effectiveHtml as html,
|
|
43
|
+
effectiveSvg as svg,
|
|
24
44
|
};
|
|
25
45
|
export { scopeTag };
|
|
26
46
|
export { repeat } from "lit-html/directives/repeat.js";
|
|
27
47
|
export { classMap } from "lit-html/directives/class-map.js";
|
|
28
|
-
export { styleMap } from "
|
|
48
|
+
export { styleMap } from "./directives/style-map.js";
|
|
49
|
+
export { ifDefined } from "lit-html/directives/if-defined.js";
|
|
29
50
|
export { unsafeHTML } from "lit-html/directives/unsafe-html.js";
|
|
30
51
|
|
|
31
52
|
export default litRender;
|
|
@@ -0,0 +1,72 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @license
|
|
3
|
+
* Copyright 2018 Google LLC
|
|
4
|
+
* SPDX-License-Identifier: BSD-3-Clause
|
|
5
|
+
*/
|
|
6
|
+
|
|
7
|
+
/**
|
|
8
|
+
* This is the original style-map.js directive from lit-html 2 with the only difference that "render" is not called even for the first rendering (update is used instead)
|
|
9
|
+
*/
|
|
10
|
+
|
|
11
|
+
import { noChange } from 'lit-html';
|
|
12
|
+
import { directive, Directive, PartType, } from 'lit-html/directive.js';
|
|
13
|
+
class StyleMapDirective extends Directive {
|
|
14
|
+
constructor(partInfo) {
|
|
15
|
+
var _a;
|
|
16
|
+
super(partInfo);
|
|
17
|
+
if (partInfo.type !== PartType.ATTRIBUTE ||
|
|
18
|
+
partInfo.name !== 'style' ||
|
|
19
|
+
((_a = partInfo.strings) === null || _a === void 0 ? void 0 : _a.length) > 2) {
|
|
20
|
+
throw new Error('The `styleMap` directive must be used in the `style` attribute ' +
|
|
21
|
+
'and must be the only part in the attribute.');
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
render(styleInfo) {
|
|
25
|
+
return "";
|
|
26
|
+
}
|
|
27
|
+
update(part, [styleInfo]) {
|
|
28
|
+
const { style } = part.element;
|
|
29
|
+
if (this._previousStyleProperties === undefined) {
|
|
30
|
+
this._previousStyleProperties = new Set();
|
|
31
|
+
for (const name in styleInfo) {
|
|
32
|
+
this._previousStyleProperties.add(name);
|
|
33
|
+
}
|
|
34
|
+
// return this.render(styleInfo);
|
|
35
|
+
}
|
|
36
|
+
// Remove old properties that no longer exist in styleInfo
|
|
37
|
+
// We use forEach() instead of for-of so that re don't require down-level
|
|
38
|
+
// iteration.
|
|
39
|
+
this._previousStyleProperties.forEach((name) => {
|
|
40
|
+
// If the name isn't in styleInfo or it's null/undefined
|
|
41
|
+
if (styleInfo[name] == null) {
|
|
42
|
+
this._previousStyleProperties.delete(name);
|
|
43
|
+
if (name.includes('-')) {
|
|
44
|
+
style.removeProperty(name);
|
|
45
|
+
}
|
|
46
|
+
else {
|
|
47
|
+
// Note reset using empty string (vs null) as IE11 does not always
|
|
48
|
+
// reset via null (https://developer.mozilla.org/en-US/docs/Web/API/ElementCSSInlineStyle/style#setting_styles)
|
|
49
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
50
|
+
style[name] = '';
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
});
|
|
54
|
+
// Add or update properties
|
|
55
|
+
for (const name in styleInfo) {
|
|
56
|
+
const value = styleInfo[name];
|
|
57
|
+
if (value != null) {
|
|
58
|
+
this._previousStyleProperties.add(name);
|
|
59
|
+
if (name.includes('-')) {
|
|
60
|
+
style.setProperty(name, value);
|
|
61
|
+
}
|
|
62
|
+
else {
|
|
63
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
64
|
+
style[name] = value;
|
|
65
|
+
}
|
|
66
|
+
}
|
|
67
|
+
}
|
|
68
|
+
return noChange;
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
export const styleMap = directive(StyleMapDirective);
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { getCustomElementsScopingSuffix, shouldScopeCustomElement } from "../
|
|
1
|
+
import { getCustomElementsScopingSuffix, shouldScopeCustomElement } from "../CustomElementsScopeUtils.js";
|
|
2
2
|
|
|
3
3
|
/**
|
|
4
4
|
* Runs a component's template with the component's current state, while also scoping HTML
|
|
@@ -9,9 +9,26 @@ import { getCustomElementsScopingSuffix, shouldScopeCustomElement } from "../Cus
|
|
|
9
9
|
* @returns {*}
|
|
10
10
|
*/
|
|
11
11
|
const executeTemplate = (template, component) => {
|
|
12
|
-
const tagsToScope = component
|
|
12
|
+
const tagsToScope = getTagsToScope(component);
|
|
13
13
|
const scope = getCustomElementsScopingSuffix();
|
|
14
14
|
return template(component, tagsToScope, scope);
|
|
15
15
|
};
|
|
16
16
|
|
|
17
|
+
/**
|
|
18
|
+
* Returns all tags, used inside component's template subject to scoping.
|
|
19
|
+
* @param component - the component
|
|
20
|
+
* @returns {Array[]}
|
|
21
|
+
* @private
|
|
22
|
+
*/
|
|
23
|
+
const getTagsToScope = component => {
|
|
24
|
+
const componentTag = component.constructor.getMetadata().getPureTag();
|
|
25
|
+
const tagsToScope = component.constructor.getUniqueDependencies().map(dep => dep.getMetadata().getPureTag()).filter(shouldScopeCustomElement);
|
|
26
|
+
|
|
27
|
+
if (shouldScopeCustomElement(componentTag)) {
|
|
28
|
+
tagsToScope.push(componentTag);
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
return tagsToScope;
|
|
32
|
+
};
|
|
33
|
+
|
|
17
34
|
export default executeTemplate;
|
|
@@ -1,7 +1,8 @@
|
|
|
1
1
|
import { reRenderAllUI5Elements } from "../Render.js";
|
|
2
|
+
import getSharedResource from "../getSharedResource.js";
|
|
2
3
|
import EventProvider from "../EventProvider.js";
|
|
3
4
|
|
|
4
|
-
const eventProvider = new EventProvider();
|
|
5
|
+
const eventProvider = getSharedResource("CustomStyle.eventProvider", new EventProvider());
|
|
5
6
|
const CUSTOM_CSS_CHANGE = "CustomCSSChange";
|
|
6
7
|
|
|
7
8
|
const attachCustomCSSChange = listener => {
|
|
@@ -16,14 +17,33 @@ const fireCustomCSSChange = tag => {
|
|
|
16
17
|
return eventProvider.fireEvent(CUSTOM_CSS_CHANGE, tag);
|
|
17
18
|
};
|
|
18
19
|
|
|
19
|
-
const customCSSFor = {};
|
|
20
|
+
const customCSSFor = getSharedResource("CustomStyle.customCSSFor", {});
|
|
21
|
+
|
|
22
|
+
// Listen to the eventProvider, in case other copies of this CustomStyle module fire this
|
|
23
|
+
// event, and this copy would therefore need to reRender the ui5 webcomponents; but
|
|
24
|
+
// don't reRender if it was this copy that fired the event to begin with.
|
|
25
|
+
let skipRerender;
|
|
26
|
+
attachCustomCSSChange(tag => {
|
|
27
|
+
if (!skipRerender) {
|
|
28
|
+
reRenderAllUI5Elements({ tag });
|
|
29
|
+
}
|
|
30
|
+
});
|
|
20
31
|
|
|
21
32
|
const addCustomCSS = (tag, css) => {
|
|
22
33
|
if (!customCSSFor[tag]) {
|
|
23
34
|
customCSSFor[tag] = [];
|
|
24
35
|
}
|
|
25
36
|
customCSSFor[tag].push(css);
|
|
26
|
-
|
|
37
|
+
|
|
38
|
+
skipRerender = true;
|
|
39
|
+
try {
|
|
40
|
+
// The event is fired and the attached event listeners are all called synchronously
|
|
41
|
+
// The skipRerender flag will be used to avoid calling reRenderAllUI5Elements twice when it is this copy
|
|
42
|
+
// of CustomStyle.js which is firing the `CustomCSSChange` event.
|
|
43
|
+
fireCustomCSSChange(tag);
|
|
44
|
+
} finally {
|
|
45
|
+
skipRerender = false;
|
|
46
|
+
}
|
|
27
47
|
|
|
28
48
|
return reRenderAllUI5Elements({ tag });
|
|
29
49
|
};
|
|
@@ -1,10 +1,10 @@
|
|
|
1
1
|
import { getThemeProperties, getRegisteredPackages, isThemeRegistered } from "../asset-registries/Themes.js";
|
|
2
|
-
import
|
|
2
|
+
import { removeStyle, createOrUpdateStyle } from "../ManagedStyles.js";
|
|
3
3
|
import getThemeDesignerTheme from "./getThemeDesignerTheme.js";
|
|
4
4
|
import { fireThemeLoaded } from "./ThemeLoaded.js";
|
|
5
5
|
import { getFeature } from "../FeaturesRegistry.js";
|
|
6
6
|
|
|
7
|
-
const BASE_THEME_PACKAGE = "@ui5/webcomponents-
|
|
7
|
+
const BASE_THEME_PACKAGE = "@ui5/webcomponents-theming";
|
|
8
8
|
|
|
9
9
|
const isThemeBaseRegistered = () => {
|
|
10
10
|
const registeredPackages = getRegisteredPackages();
|
|
@@ -16,15 +16,14 @@ const loadThemeBase = async theme => {
|
|
|
16
16
|
return;
|
|
17
17
|
}
|
|
18
18
|
|
|
19
|
-
const
|
|
20
|
-
|
|
19
|
+
const cssData = await getThemeProperties(BASE_THEME_PACKAGE, theme);
|
|
20
|
+
if (cssData) {
|
|
21
|
+
createOrUpdateStyle(cssData, "data-ui5-theme-properties", BASE_THEME_PACKAGE);
|
|
22
|
+
}
|
|
21
23
|
};
|
|
22
24
|
|
|
23
25
|
const deleteThemeBase = () => {
|
|
24
|
-
|
|
25
|
-
if (styleElement) {
|
|
26
|
-
styleElement.parentElement.removeChild(styleElement);
|
|
27
|
-
}
|
|
26
|
+
removeStyle("data-ui5-theme-properties", BASE_THEME_PACKAGE);
|
|
28
27
|
};
|
|
29
28
|
|
|
30
29
|
const loadComponentPackages = async theme => {
|
|
@@ -34,8 +33,10 @@ const loadComponentPackages = async theme => {
|
|
|
34
33
|
return;
|
|
35
34
|
}
|
|
36
35
|
|
|
37
|
-
const
|
|
38
|
-
|
|
36
|
+
const cssData = await getThemeProperties(packageName, theme);
|
|
37
|
+
if (cssData) {
|
|
38
|
+
createOrUpdateStyle(cssData, "data-ui5-theme-properties", packageName);
|
|
39
|
+
}
|
|
39
40
|
});
|
|
40
41
|
};
|
|
41
42
|
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
import { getUrl } from "../CSP.js";
|
|
2
|
+
import { getFeature } from "../FeaturesRegistry.js";
|
|
3
|
+
|
|
4
|
+
const flatten = arr => {
|
|
5
|
+
return arr.reduce((acc, val) => acc.concat(Array.isArray(val) ? flatten(val) : val), []);
|
|
6
|
+
};
|
|
7
|
+
|
|
8
|
+
const getEffectiveLinksHrefs = (ElementClass, forStaticArea = false) => {
|
|
9
|
+
let stylesData = ElementClass[forStaticArea ? "staticAreaStyles" : "styles"];
|
|
10
|
+
const OpenUI5Enablement = getFeature("OpenUI5Enablement");
|
|
11
|
+
|
|
12
|
+
if (!stylesData) {
|
|
13
|
+
return;
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
if (!Array.isArray(stylesData)) {
|
|
17
|
+
stylesData = [stylesData];
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
if (OpenUI5Enablement) {
|
|
21
|
+
stylesData.push(OpenUI5Enablement.getBusyIndicatorStyles());
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
return flatten(stylesData).filter(data => !!data).map(data => getUrl(data.packageName, data.fileName));
|
|
25
|
+
};
|
|
26
|
+
|
|
27
|
+
export default getEffectiveLinksHrefs;
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { getCustomCSS, attachCustomCSSChange } from "./CustomStyle.js";
|
|
2
2
|
import getStylesString from "./getStylesString.js";
|
|
3
|
+
import { getFeature } from "../FeaturesRegistry.js";
|
|
3
4
|
|
|
4
5
|
const effectiveStyleMap = new Map();
|
|
5
6
|
|
|
@@ -10,9 +11,15 @@ attachCustomCSSChange(tag => {
|
|
|
10
11
|
const getEffectiveStyle = (ElementClass, forStaticArea = false) => {
|
|
11
12
|
const tag = ElementClass.getMetadata().getTag();
|
|
12
13
|
const key = `${tag}_${forStaticArea ? "static" : "normal"}`;
|
|
14
|
+
const OpenUI5Enablement = getFeature("OpenUI5Enablement");
|
|
13
15
|
|
|
14
16
|
if (!effectiveStyleMap.has(key)) {
|
|
15
17
|
let effectiveStyle;
|
|
18
|
+
let busyIndicatorStyles = "";
|
|
19
|
+
|
|
20
|
+
if (OpenUI5Enablement) {
|
|
21
|
+
busyIndicatorStyles = getStylesString(OpenUI5Enablement.getBusyIndicatorStyles());
|
|
22
|
+
}
|
|
16
23
|
|
|
17
24
|
if (forStaticArea) {
|
|
18
25
|
effectiveStyle = getStylesString(ElementClass.staticAreaStyles);
|
|
@@ -21,6 +28,8 @@ const getEffectiveStyle = (ElementClass, forStaticArea = false) => {
|
|
|
21
28
|
const builtInStyles = getStylesString(ElementClass.styles);
|
|
22
29
|
effectiveStyle = `${builtInStyles} ${customStyle}`;
|
|
23
30
|
}
|
|
31
|
+
|
|
32
|
+
effectiveStyle = `${effectiveStyle} ${busyIndicatorStyles}`;
|
|
24
33
|
effectiveStyleMap.set(key, effectiveStyle);
|
|
25
34
|
}
|
|
26
35
|
|
|
@@ -1,9 +1,11 @@
|
|
|
1
1
|
const getStylesString = styles => {
|
|
2
2
|
if (Array.isArray(styles)) {
|
|
3
|
-
return flatten(styles.filter(style => !!style)).
|
|
3
|
+
return flatten(styles.filter(style => !!style)).map(style => {
|
|
4
|
+
return typeof style === "string" ? style : style.content;
|
|
5
|
+
}).join(" ");
|
|
4
6
|
}
|
|
5
7
|
|
|
6
|
-
return styles;
|
|
8
|
+
return typeof styles === "string" ? styles : styles.content;
|
|
7
9
|
};
|
|
8
10
|
|
|
9
11
|
const flatten = arr => {
|
|
@@ -1,15 +1,26 @@
|
|
|
1
|
+
const warnings = new Set();
|
|
2
|
+
|
|
1
3
|
const getThemeMetadata = () => {
|
|
2
4
|
// Check if the class was already applied, most commonly to the link/style tag with the CSS Variables
|
|
3
|
-
let el = document.querySelector(".sapThemeMetaData-Base-baseLib");
|
|
5
|
+
let el = document.querySelector(".sapThemeMetaData-Base-baseLib") || document.querySelector(".sapThemeMetaData-UI5-sap-ui-core");
|
|
4
6
|
if (el) {
|
|
5
7
|
return getComputedStyle(el).backgroundImage;
|
|
6
8
|
}
|
|
7
9
|
|
|
8
10
|
el = document.createElement("span");
|
|
9
11
|
el.style.display = "none";
|
|
12
|
+
|
|
13
|
+
// Try with sapThemeMetaData-Base-baseLib first
|
|
10
14
|
el.classList.add("sapThemeMetaData-Base-baseLib");
|
|
11
15
|
document.body.appendChild(el);
|
|
12
|
-
|
|
16
|
+
let metadata = getComputedStyle(el).backgroundImage;
|
|
17
|
+
|
|
18
|
+
// Try with sapThemeMetaData-UI5-sap-ui-core only if the previous selector was not found
|
|
19
|
+
if (metadata === "none") {
|
|
20
|
+
el.classList.add("sapThemeMetaData-UI5-sap-ui-core");
|
|
21
|
+
metadata = getComputedStyle(el).backgroundImage;
|
|
22
|
+
}
|
|
23
|
+
|
|
13
24
|
document.body.removeChild(el);
|
|
14
25
|
|
|
15
26
|
return metadata;
|
|
@@ -24,14 +35,20 @@ const parseThemeMetadata = metadataString => {
|
|
|
24
35
|
try {
|
|
25
36
|
paramsString = decodeURIComponent(paramsString);
|
|
26
37
|
} catch (ex) {
|
|
27
|
-
|
|
38
|
+
if (!warnings.has("decode")) {
|
|
39
|
+
console.warn("Malformed theme metadata string, unable to decodeURIComponent"); // eslint-disable-line
|
|
40
|
+
warnings.add("decode");
|
|
41
|
+
}
|
|
28
42
|
return;
|
|
29
43
|
}
|
|
30
44
|
}
|
|
31
45
|
try {
|
|
32
46
|
return JSON.parse(paramsString);
|
|
33
47
|
} catch (ex) {
|
|
34
|
-
|
|
48
|
+
if (!warnings.has("parse")) {
|
|
49
|
+
console.warn("Malformed theme metadata string, unable to parse JSON"); // eslint-disable-line
|
|
50
|
+
warnings.add("parse");
|
|
51
|
+
}
|
|
35
52
|
}
|
|
36
53
|
}
|
|
37
54
|
};
|
|
@@ -44,7 +61,10 @@ const processThemeMetadata = metadata => {
|
|
|
44
61
|
themeName = metadata.Path.match(/\.([^.]+)\.css_variables$/)[1];
|
|
45
62
|
baseThemeName = metadata.Extends[0];
|
|
46
63
|
} catch (ex) {
|
|
47
|
-
|
|
64
|
+
if (!warnings.has("object")) {
|
|
65
|
+
console.warn("Malformed theme metadata Object", metadata); // eslint-disable-line
|
|
66
|
+
warnings.add("object");
|
|
67
|
+
}
|
|
48
68
|
return;
|
|
49
69
|
}
|
|
50
70
|
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
import getEffectiveLinksHrefs from "./getEffectiveLinksHrefs.js";
|
|
2
|
+
import createLinkInHead from "../util/createLinkInHead.js";
|
|
3
|
+
import { shouldUseLinks, shouldPreloadLinks } from "../CSP.js";
|
|
4
|
+
|
|
5
|
+
const preloaded = new Set();
|
|
6
|
+
|
|
7
|
+
const preloadLinks = ElementClass => {
|
|
8
|
+
if (!shouldUseLinks() || !shouldPreloadLinks()) {
|
|
9
|
+
return;
|
|
10
|
+
}
|
|
11
|
+
|
|
12
|
+
const linksHrefs = getEffectiveLinksHrefs(ElementClass, false) || [];
|
|
13
|
+
const staticAreaLinksHrefs = getEffectiveLinksHrefs(ElementClass, true) || [];
|
|
14
|
+
|
|
15
|
+
[...linksHrefs, ...staticAreaLinksHrefs].forEach(href => {
|
|
16
|
+
if (!preloaded.has(href)) {
|
|
17
|
+
createLinkInHead(href, { rel: "preload", as: "style" });
|
|
18
|
+
preloaded.add(href);
|
|
19
|
+
}
|
|
20
|
+
});
|
|
21
|
+
};
|
|
22
|
+
|
|
23
|
+
export default preloadLinks;
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
import DataType from "./DataType.js";
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* @class
|
|
5
|
+
* DOM Element reference or ID.
|
|
6
|
+
* <b>Note:</b> If an ID is passed, it is expected to be part of the same <code>document</code> element as the consuming component.
|
|
7
|
+
*
|
|
8
|
+
* @public
|
|
9
|
+
*/
|
|
10
|
+
class DOMReference extends DataType {
|
|
11
|
+
static isValid(value) {
|
|
12
|
+
return (typeof value === "string" || value instanceof HTMLElement);
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
static propertyToAttribute(propertyValue) {
|
|
16
|
+
if (propertyValue instanceof HTMLElement) {
|
|
17
|
+
return null;
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
return propertyValue;
|
|
21
|
+
}
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
export default DOMReference;
|
package/src/types/DataType.js
CHANGED
|
@@ -11,6 +11,18 @@ class DataType {
|
|
|
11
11
|
static isValid(value) {
|
|
12
12
|
}
|
|
13
13
|
|
|
14
|
+
static attributeToProperty(attributeValue) {
|
|
15
|
+
return attributeValue;
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
static propertyToAttribute(propertyValue) {
|
|
19
|
+
return `${propertyValue}`;
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
static valuesAreEqual(value1, value2) {
|
|
23
|
+
return value1 === value2;
|
|
24
|
+
}
|
|
25
|
+
|
|
14
26
|
static generateTypeAccessors(types) {
|
|
15
27
|
Object.keys(types).forEach(type => {
|
|
16
28
|
Object.defineProperty(this, type, {
|
package/src/types/Float.js
CHANGED
package/src/types/Integer.js
CHANGED
package/src/updateShadowRoot.js
CHANGED
|
@@ -1,7 +1,8 @@
|
|
|
1
1
|
import executeTemplate from "./renderer/executeTemplate.js";
|
|
2
2
|
import getConstructableStyle from "./theming/getConstructableStyle.js";
|
|
3
3
|
import getEffectiveStyle from "./theming/getEffectiveStyle.js";
|
|
4
|
-
import
|
|
4
|
+
import getEffectiveLinksHrefs from "./theming/getEffectiveLinksHrefs.js";
|
|
5
|
+
import { shouldUseLinks } from "./CSP.js";
|
|
5
6
|
|
|
6
7
|
/**
|
|
7
8
|
* Updates the shadow root of a UI5Element or its static area item
|
|
@@ -9,18 +10,20 @@ import isLegacyBrowser from "./isLegacyBrowser.js";
|
|
|
9
10
|
* @param forStaticArea
|
|
10
11
|
*/
|
|
11
12
|
const updateShadowRoot = (element, forStaticArea = false) => {
|
|
12
|
-
let
|
|
13
|
+
let styleStrOrHrefsArr;
|
|
13
14
|
const template = forStaticArea ? "staticAreaTemplate" : "template";
|
|
14
15
|
const shadowRoot = forStaticArea ? element.staticAreaItem.shadowRoot : element.shadowRoot;
|
|
15
16
|
const renderResult = executeTemplate(element.constructor[template], element);
|
|
16
17
|
|
|
17
|
-
if (
|
|
18
|
+
if (shouldUseLinks()) {
|
|
19
|
+
styleStrOrHrefsArr = getEffectiveLinksHrefs(element.constructor, forStaticArea);
|
|
20
|
+
} else if (document.adoptedStyleSheets) { // Chrome
|
|
18
21
|
shadowRoot.adoptedStyleSheets = getConstructableStyle(element.constructor, forStaticArea);
|
|
19
|
-
} else
|
|
20
|
-
|
|
22
|
+
} else { // FF, Safari
|
|
23
|
+
styleStrOrHrefsArr = getEffectiveStyle(element.constructor, forStaticArea);
|
|
21
24
|
}
|
|
22
25
|
|
|
23
|
-
element.constructor.render(renderResult, shadowRoot,
|
|
26
|
+
element.constructor.render(renderResult, shadowRoot, styleStrOrHrefsArr, forStaticArea, { host: element });
|
|
24
27
|
};
|
|
25
28
|
|
|
26
29
|
export default updateShadowRoot;
|
|
@@ -1,5 +1,3 @@
|
|
|
1
|
-
import findNodeOwner from "./findNodeOwner.js";
|
|
2
|
-
|
|
3
1
|
const getEffectiveAriaLabelText = el => {
|
|
4
2
|
if (!el.accessibleNameRef) {
|
|
5
3
|
if (el.accessibleName) {
|
|
@@ -15,12 +13,12 @@ const getEffectiveAriaLabelText = el => {
|
|
|
15
13
|
/**
|
|
16
14
|
*
|
|
17
15
|
* @param {HTMLElement} el Defines the HTMLElement, for which you need to get all related texts
|
|
18
|
-
* @param {HTMLElement} ownerDocument (Optional) Defines the
|
|
16
|
+
* @param {Document|HTMLElement} ownerDocument (Optional) Defines the document or element where you want to search for the texts
|
|
19
17
|
* @param {String} readyIds (Optional) Defines a string of elements ids. The text of these elements will be returned. If used you should provide either el or ownerDocument
|
|
20
18
|
*/
|
|
21
19
|
const getAriaLabelledByTexts = (el, ownerDocument, readyIds = "") => {
|
|
22
20
|
const ids = (readyIds && readyIds.split(" ")) || el.accessibleNameRef.split(" ");
|
|
23
|
-
const owner = ownerDocument ||
|
|
21
|
+
const owner = ownerDocument || el.getRootNode();
|
|
24
22
|
let result = "";
|
|
25
23
|
|
|
26
24
|
ids.forEach((elementId, index) => {
|
package/src/util/Caret.js
CHANGED
|
@@ -6,20 +6,7 @@ const getCaretPosition = field => {
|
|
|
6
6
|
// Initialize
|
|
7
7
|
let caretPos = 0;
|
|
8
8
|
|
|
9
|
-
//
|
|
10
|
-
if (document.selection) {
|
|
11
|
-
// Set focus on the element
|
|
12
|
-
field.focus();
|
|
13
|
-
|
|
14
|
-
// To get cursor position, get empty selection range
|
|
15
|
-
const selection = document.selection.createRange();
|
|
16
|
-
|
|
17
|
-
// Move selection start to 0 position
|
|
18
|
-
selection.moveStart("character", -field.value.length);
|
|
19
|
-
|
|
20
|
-
// The caret position is selection length
|
|
21
|
-
caretPos = selection.text.length;
|
|
22
|
-
} else if (field.selectionStart || field.selectionStart === "0") { // Firefox support
|
|
9
|
+
if (field.selectionStart || field.selectionStart === "0") { // Firefox support
|
|
23
10
|
caretPos = field.selectionDirection === "backward" ? field.selectionStart : field.selectionEnd;
|
|
24
11
|
}
|
|
25
12
|
|
|
@@ -163,7 +163,7 @@ const getRGBColor = color => {
|
|
|
163
163
|
}
|
|
164
164
|
|
|
165
165
|
if (color.startsWith("rgb")) {
|
|
166
|
-
return
|
|
166
|
+
return RGBStringToRGBObject(color);
|
|
167
167
|
}
|
|
168
168
|
|
|
169
169
|
// HEX
|
|
@@ -209,7 +209,7 @@ const RGBAToRGB = color => {
|
|
|
209
209
|
* Return an object with the properties for each of the main colors(red, green, blue)
|
|
210
210
|
* @param {String} color Receives a color in the following format: "rgb(0, 0, 0)
|
|
211
211
|
*/
|
|
212
|
-
const
|
|
212
|
+
const RGBStringToRGBObject = color => {
|
|
213
213
|
const openingBracketIndex = color.indexOf("("),
|
|
214
214
|
closingBraketIndex = color.indexOf(")"),
|
|
215
215
|
commasIndexes = [];
|
|
@@ -319,6 +319,32 @@ const HEXToRGB = hex => {
|
|
|
319
319
|
return rgbValues;
|
|
320
320
|
};
|
|
321
321
|
|
|
322
|
+
/**
|
|
323
|
+
* Returns the hex value of the color as string
|
|
324
|
+
* @param {Object} color Receives an object with the properties for each of the main colors(r, g, b)
|
|
325
|
+
*/
|
|
326
|
+
const RGBtoHEX = color => {
|
|
327
|
+
const hexMap = ["0", "1", "2", "3", "4", "5", "6", "7", "8", "9", "A", "B", "C", "D", "E"];
|
|
328
|
+
let hexValue = "#";
|
|
329
|
+
|
|
330
|
+
let divisionNumber = color.r / 16;
|
|
331
|
+
let remainder = color.r % 16;
|
|
332
|
+
hexValue += String(hexMap[Math.floor(divisionNumber)]);
|
|
333
|
+
hexValue += String(hexMap[remainder]);
|
|
334
|
+
|
|
335
|
+
divisionNumber = color.g / 16;
|
|
336
|
+
remainder = color.g % 16;
|
|
337
|
+
hexValue += String(hexMap[Math.floor(divisionNumber)]);
|
|
338
|
+
hexValue += String(hexMap[remainder]);
|
|
339
|
+
|
|
340
|
+
divisionNumber = color.b / 16;
|
|
341
|
+
remainder = color.b % 16;
|
|
342
|
+
hexValue += String(hexMap[Math.floor(divisionNumber)]);
|
|
343
|
+
hexValue += String(hexMap[remainder]);
|
|
344
|
+
|
|
345
|
+
return hexValue;
|
|
346
|
+
};
|
|
347
|
+
|
|
322
348
|
const RGBToHSL = (color = {
|
|
323
349
|
r: undefined,
|
|
324
350
|
g: undefined,
|
|
@@ -367,4 +393,6 @@ export {
|
|
|
367
393
|
HSLToRGB,
|
|
368
394
|
HEXToRGB,
|
|
369
395
|
RGBToHSL,
|
|
396
|
+
RGBStringToRGBObject,
|
|
397
|
+
RGBtoHEX,
|
|
370
398
|
};
|