@ui5/webcomponents-base 0.0.0-b4cbc43ba → 0.0.0-b93c2a321
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 -0
- package/CHANGELOG.md +214 -0
- package/README.md +26 -2
- package/bundle.esm.js +10 -7
- package/dist/AssetRegistry.js +8 -9
- package/dist/Boot.js +17 -6
- 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/DOMObserver.js +6 -2
- package/dist/Device.js +69 -776
- package/dist/EventProvider.js +19 -25
- package/dist/FeaturesRegistry.js +4 -1
- package/dist/FontFace.js +7 -95
- package/dist/InitialConfiguration.js +37 -21
- package/dist/Keys.js +74 -0
- package/dist/ManagedStyles.js +83 -0
- package/dist/MediaRange.js +109 -0
- package/dist/{util/parseProperties.js → PropertiesFileFormat.js} +6 -0
- package/dist/Render.js +3 -2
- package/dist/Runtimes.js +107 -0
- package/dist/StaticArea.js +3 -0
- package/dist/StaticAreaItem.js +31 -10
- package/dist/SystemCSSVars.js +4 -25
- package/dist/UI5Element.js +66 -65
- package/dist/UI5ElementMetadata.js +18 -2
- package/dist/asset-registries/Icons.js +117 -14
- package/dist/asset-registries/Illustrations.js +30 -0
- package/dist/asset-registries/LocaleData.js +97 -68
- package/dist/asset-registries/Themes.js +23 -33
- package/dist/asset-registries/i18n.js +61 -50
- package/dist/assets-meta/IconCollectionsAlias.js +18 -0
- package/dist/config/Icons.js +52 -0
- package/dist/config/Language.js +15 -15
- package/dist/config/Theme.js +25 -0
- package/dist/css/BusyIndicator.css +76 -0
- package/dist/css/FontFace.css +75 -0
- package/dist/css/OverrideFontFace.css +32 -0
- package/dist/css/SystemCSSVars.css +17 -0
- package/dist/delegate/ItemNavigation.js +163 -105
- package/dist/delegate/ScrollEnablement.js +25 -19
- package/dist/features/F6Navigation.js +108 -0
- package/dist/features/OpenUI5Enablement.js +119 -0
- package/dist/features/OpenUI5Support.js +41 -6
- 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 +38 -4
- package/dist/renderer/LitRenderer.js +39 -18
- package/dist/renderer/directives/style-map.js +72 -0
- package/dist/renderer/executeTemplate.js +19 -2
- package/dist/resources/bundle.esm.js +15 -104
- package/dist/resources/bundle.esm.js.map +1 -1
- package/dist/sap/base/Log.js +241 -0
- package/dist/sap/base/assert.js +8 -0
- package/dist/sap/base/security/URLListValidator.js +148 -0
- package/dist/sap/base/security/encodeCSS.js +14 -0
- package/dist/sap/base/security/encodeXML.js +23 -0
- package/dist/sap/base/security/sanitizeHTML.js +16 -0
- package/dist/sap/base/strings/toHex.js +8 -0
- package/dist/sap/base/util/now.js +7 -0
- package/dist/sap/ui/thirdparty/caja-html-sanitizer.js +3585 -0
- package/dist/test-resources/assets/Themes.js +8 -8
- package/dist/test-resources/elements/WithStaticArea.js +2 -1
- package/dist/test-resources/pages/AllTestElements.html +3 -0
- package/dist/test-resources/pages/i18n.html +2 -9
- package/dist/test-resources/specs/ConfigurationChange.spec.js +10 -8
- package/dist/test-resources/specs/ConfigurationScript.spec.js +25 -23
- package/dist/test-resources/specs/ConfigurationURL.spec.js +65 -17
- package/dist/test-resources/specs/CustomTheme.spec.js +9 -7
- package/dist/test-resources/specs/EventProvider.spec.js +63 -0
- package/dist/test-resources/specs/StaticArea.spec.js +56 -12
- package/dist/test-resources/specs/Theming.spec.js +12 -10
- package/dist/test-resources/specs/UI5ElementInvalidation.js +30 -28
- package/dist/test-resources/specs/UI5ElementLifecycle.js +12 -10
- package/dist/test-resources/specs/UI5ElementListenForChildPropChanges.spec.js +12 -10
- package/dist/test-resources/specs/UI5ElementMetadataExt.js +9 -7
- package/dist/test-resources/specs/UI5ElementPropertyValidation.js +7 -5
- package/dist/test-resources/specs/UI5ElementPropsAndAttrs.spec.js +37 -35
- package/dist/test-resources/specs/UI5ElementShadowDOM.js +10 -8
- package/dist/test-resources/specs/UI5ElementSlots.js +10 -8
- 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/CSSColor.js +9 -0
- package/dist/types/DataType.js +12 -0
- package/dist/types/Float.js +4 -0
- package/dist/types/Integer.js +4 -0
- package/dist/types/InvisibleMessageMode.js +30 -0
- package/dist/updateShadowRoot.js +8 -4
- package/dist/util/AriaLabelHelper.js +4 -4
- package/dist/util/ColorConversion.js +370 -0
- package/dist/util/FocusableElements.js +13 -7
- package/dist/util/HTMLSanitizer.js +7 -0
- package/dist/util/InvisibleMessage.js +60 -0
- package/dist/util/PopupUtils.js +93 -0
- package/dist/util/TabbableElements.js +5 -1
- package/dist/util/clamp.js +12 -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/getClassCopy.js +10 -0
- package/dist/util/getNormalizedTarget.js +16 -0
- package/dist/util/isElementInView.js +15 -0
- package/dist/util/isNodeHidden.js +1 -1
- package/dist/util/isNodeTabbable.js +4 -4
- package/hash.txt +1 -0
- package/index.js +1 -1
- package/lib/generate-asset-parameters/index.js +0 -1
- package/lib/generate-styles/index.js +18 -0
- package/lib/generate-version-info/index.js +27 -0
- package/package-scripts.js +31 -15
- package/package.json +19 -10
- package/src/AssetRegistry.js +8 -9
- package/src/Boot.js +17 -6
- 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/DOMObserver.js +6 -2
- package/src/Device.js +69 -776
- package/src/EventProvider.js +19 -25
- package/src/FeaturesRegistry.js +4 -1
- package/src/FontFace.js +7 -95
- package/src/InitialConfiguration.js +37 -21
- package/src/Keys.js +74 -0
- package/src/ManagedStyles.js +83 -0
- package/src/MediaRange.js +109 -0
- package/src/{util/parseProperties.js → PropertiesFileFormat.js} +6 -0
- package/src/Render.js +3 -2
- package/src/Runtimes.js +107 -0
- package/src/StaticArea.js +3 -0
- package/src/StaticAreaItem.js +31 -10
- package/src/SystemCSSVars.js +4 -25
- package/src/UI5Element.js +66 -65
- package/src/UI5ElementMetadata.js +18 -2
- package/src/asset-registries/Icons.js +117 -14
- package/src/asset-registries/Illustrations.js +30 -0
- package/src/asset-registries/LocaleData.js +97 -68
- package/src/asset-registries/Themes.js +23 -33
- package/src/asset-registries/i18n.js +61 -50
- package/src/assets-meta/IconCollectionsAlias.js +18 -0
- package/src/config/Icons.js +52 -0
- package/src/config/Language.js +15 -15
- package/src/config/Theme.js +25 -0
- package/src/css/BusyIndicator.css +76 -0
- package/src/css/FontFace.css +75 -0
- package/src/css/OverrideFontFace.css +32 -0
- package/src/css/SystemCSSVars.css +17 -0
- package/src/delegate/ItemNavigation.js +163 -105
- package/src/delegate/ScrollEnablement.js +25 -19
- package/src/features/F6Navigation.js +108 -0
- package/src/features/OpenUI5Enablement.js +119 -0
- package/src/features/OpenUI5Support.js +41 -6
- package/src/i18nBundle.js +38 -4
- package/src/renderer/LitRenderer.js +39 -18
- 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/CSSColor.js +9 -0
- package/src/types/DataType.js +12 -0
- package/src/types/Float.js +4 -0
- package/src/types/Integer.js +4 -0
- package/src/types/InvisibleMessageMode.js +30 -0
- package/src/updateShadowRoot.js +8 -4
- package/src/util/AriaLabelHelper.js +4 -4
- package/src/util/ColorConversion.js +370 -0
- package/src/util/FocusableElements.js +13 -7
- package/src/util/HTMLSanitizer.js +7 -0
- package/src/util/InvisibleMessage.js +60 -0
- package/src/util/PopupUtils.js +93 -0
- package/src/util/TabbableElements.js +5 -1
- package/src/util/clamp.js +12 -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/getClassCopy.js +10 -0
- package/src/util/getNormalizedTarget.js +16 -0
- package/src/util/isElementInView.js +15 -0
- package/src/util/isNodeHidden.js +1 -1
- package/src/util/isNodeTabbable.js +4 -4
- package/used-modules.txt +10 -0
- package/dist/SVGIconRegistry.js +0 -73
- package/dist/config/AssetsPath.js +0 -17
- package/dist/features/PropertiesFormatSupport.js +0 -8
- package/dist/renderer/ifDefined.js +0 -21
- package/dist/renderer/scopeHTML.js +0 -32
- package/dist/theming/createThemePropertiesStyleTag.js +0 -20
- package/dist/util/EffectiveAssetPath.js +0 -27
- package/dist/util/encodeCSS.js +0 -24
- package/src/SVGIconRegistry.js +0 -73
- package/src/config/AssetsPath.js +0 -17
- package/src/features/PropertiesFormatSupport.js +0 -8
- package/src/renderer/ifDefined.js +0 -21
- package/src/renderer/scopeHTML.js +0 -32
- package/src/theming/createThemePropertiesStyleTag.js +0 -20
- package/src/util/EffectiveAssetPath.js +0 -27
- package/src/util/encodeCSS.js +0 -24
|
@@ -1,22 +1,37 @@
|
|
|
1
|
-
import
|
|
2
|
-
import
|
|
3
|
-
import {
|
|
1
|
+
import getSharedResource from "../getSharedResource.js";
|
|
2
|
+
import IconCollectionsAlias from "../assets-meta/IconCollectionsAlias.js";
|
|
3
|
+
import { getEffectiveDefaultIconCollection } from "../config/Icons.js";
|
|
4
4
|
|
|
5
|
+
const loaders = new Map();
|
|
6
|
+
const registry = getSharedResource("SVGIcons.registry", new Map());
|
|
7
|
+
const iconCollectionPromises = getSharedResource("SVGIcons.promises", new Map());
|
|
8
|
+
|
|
9
|
+
const ICON_NOT_FOUND = "ICON_NOT_FOUND";
|
|
10
|
+
|
|
11
|
+
/**
|
|
12
|
+
* @deprecated
|
|
13
|
+
*/
|
|
5
14
|
const registerIconBundle = async (collectionName, bundleData) => {
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
resolveFn = resolve;
|
|
9
|
-
});
|
|
10
|
-
registerCollectionPromise(collectionName, collectionFetched);
|
|
15
|
+
throw new Error("This method has been removed. Use `registerIconLoader` instead.");
|
|
16
|
+
};
|
|
11
17
|
|
|
12
|
-
|
|
13
|
-
|
|
18
|
+
const registerIconLoader = async (collectionName, loader) => {
|
|
19
|
+
loaders.set(collectionName, loader);
|
|
20
|
+
};
|
|
21
|
+
|
|
22
|
+
const _loadIconCollectionOnce = async collectionName => {
|
|
23
|
+
if (!iconCollectionPromises.has(collectionName)) {
|
|
24
|
+
if (!loaders.has(collectionName)) {
|
|
25
|
+
throw new Error(`No loader registered for the ${collectionName} icons collection. Probably you forgot to import the "AllIcons.js" module for the respective package.`);
|
|
26
|
+
}
|
|
27
|
+
const loadIcons = loaders.get(collectionName);
|
|
28
|
+
iconCollectionPromises.set(collectionName, loadIcons(collectionName));
|
|
14
29
|
}
|
|
15
|
-
|
|
16
|
-
|
|
30
|
+
|
|
31
|
+
return iconCollectionPromises.get(collectionName);
|
|
17
32
|
};
|
|
18
33
|
|
|
19
|
-
const
|
|
34
|
+
const _fillRegistry = bundleData => {
|
|
20
35
|
Object.keys(bundleData.data).forEach(iconName => {
|
|
21
36
|
const iconData = bundleData.data[iconName];
|
|
22
37
|
|
|
@@ -25,8 +40,96 @@ const fillRegistry = bundleData => {
|
|
|
25
40
|
ltr: iconData.ltr,
|
|
26
41
|
accData: iconData.acc,
|
|
27
42
|
collection: bundleData.collection,
|
|
43
|
+
packageName: bundleData.packageName,
|
|
28
44
|
});
|
|
29
45
|
});
|
|
30
46
|
};
|
|
31
47
|
|
|
32
|
-
|
|
48
|
+
// set
|
|
49
|
+
const registerIcon = (name, { pathData, ltr, accData, collection, packageName } = {}) => { // eslint-disable-line
|
|
50
|
+
if (!collection) {
|
|
51
|
+
collection = getEffectiveDefaultIconCollection();
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
const key = `${collection}/${name}`;
|
|
55
|
+
registry.set(key, {
|
|
56
|
+
pathData,
|
|
57
|
+
ltr,
|
|
58
|
+
accData,
|
|
59
|
+
packageName,
|
|
60
|
+
});
|
|
61
|
+
};
|
|
62
|
+
|
|
63
|
+
const _parseName = name => {
|
|
64
|
+
// silently support ui5-compatible URIs
|
|
65
|
+
if (name.startsWith("sap-icon://")) {
|
|
66
|
+
name = name.replace("sap-icon://", "");
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
let collection;
|
|
70
|
+
[name, collection] = name.split("/").reverse();
|
|
71
|
+
collection = collection || getEffectiveDefaultIconCollection();
|
|
72
|
+
|
|
73
|
+
// Normalize collection name.
|
|
74
|
+
// - resolve `SAP-icons-TNT` to `tnt`.
|
|
75
|
+
// - resolve `BusinessSuiteInAppSymbols` to `business-suite`.
|
|
76
|
+
// - resolve `horizon` to `SAP-icons-v5`,
|
|
77
|
+
// Note: aliases can be made as a feature, if more collections need it or more aliases are needed.
|
|
78
|
+
collection = _normalizeCollection(collection);
|
|
79
|
+
name = name.replace("icon-", "");
|
|
80
|
+
|
|
81
|
+
const registryKey = `${collection}/${name}`;
|
|
82
|
+
return { name, collection, registryKey };
|
|
83
|
+
};
|
|
84
|
+
|
|
85
|
+
const getIconDataSync = nameProp => {
|
|
86
|
+
const { registryKey } = _parseName(nameProp);
|
|
87
|
+
return registry.get(registryKey);
|
|
88
|
+
};
|
|
89
|
+
|
|
90
|
+
const getIconData = async nameProp => {
|
|
91
|
+
const { collection, registryKey } = _parseName(nameProp);
|
|
92
|
+
|
|
93
|
+
let iconData = ICON_NOT_FOUND;
|
|
94
|
+
try {
|
|
95
|
+
iconData = await _loadIconCollectionOnce(collection);
|
|
96
|
+
} catch (e) {
|
|
97
|
+
console.error(e.message); /* eslint-disable-line */
|
|
98
|
+
}
|
|
99
|
+
|
|
100
|
+
if (iconData === ICON_NOT_FOUND) {
|
|
101
|
+
return iconData;
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
if (!registry.has(registryKey)) {
|
|
105
|
+
// not filled by another await. many getters will await on the same loader, but fill only once
|
|
106
|
+
_fillRegistry(iconData);
|
|
107
|
+
}
|
|
108
|
+
return registry.get(registryKey);
|
|
109
|
+
};
|
|
110
|
+
|
|
111
|
+
// test page usage only
|
|
112
|
+
const _getRegisteredNames = async () => {
|
|
113
|
+
// fetch one icon of each collection to trigger the bundle load
|
|
114
|
+
await getIconData("edit");
|
|
115
|
+
await getIconData("tnt/arrow");
|
|
116
|
+
await getIconData("business-suite/3d");
|
|
117
|
+
return Array.from(registry.keys());
|
|
118
|
+
};
|
|
119
|
+
|
|
120
|
+
const _normalizeCollection = collectionName => {
|
|
121
|
+
if (IconCollectionsAlias[collectionName]) {
|
|
122
|
+
return IconCollectionsAlias[collectionName];
|
|
123
|
+
}
|
|
124
|
+
|
|
125
|
+
return collectionName;
|
|
126
|
+
};
|
|
127
|
+
|
|
128
|
+
export {
|
|
129
|
+
registerIconBundle,
|
|
130
|
+
registerIconLoader,
|
|
131
|
+
getIconData,
|
|
132
|
+
getIconDataSync,
|
|
133
|
+
registerIcon,
|
|
134
|
+
_getRegisteredNames,
|
|
135
|
+
};
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
import getSharedResource from "../getSharedResource.js";
|
|
2
|
+
|
|
3
|
+
const registry = getSharedResource("SVGIllustration.registry", new Map());
|
|
4
|
+
const ILLUSTRATION_NOT_FOUND = "ILLUSTRATION_NOT_FOUND";
|
|
5
|
+
|
|
6
|
+
const registerIllustration = (name, { dialogSvg, sceneSvg, spotSvg, set, title, subtitle } = {}) => { // eslint-disable-line
|
|
7
|
+
registry.set(`${set}/${name}`, {
|
|
8
|
+
dialogSvg,
|
|
9
|
+
sceneSvg,
|
|
10
|
+
spotSvg,
|
|
11
|
+
title,
|
|
12
|
+
subtitle,
|
|
13
|
+
});
|
|
14
|
+
};
|
|
15
|
+
|
|
16
|
+
const getIllustrationDataSync = nameProp => {
|
|
17
|
+
let set = "fiori";
|
|
18
|
+
|
|
19
|
+
if (nameProp.startsWith("Tnt")) {
|
|
20
|
+
set = "tnt";
|
|
21
|
+
nameProp = nameProp.replace(/^Tnt/, "");
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
return registry.get(`${set}/${nameProp}`) || ILLUSTRATION_NOT_FOUND;
|
|
25
|
+
};
|
|
26
|
+
|
|
27
|
+
export {
|
|
28
|
+
getIllustrationDataSync,
|
|
29
|
+
registerIllustration,
|
|
30
|
+
};
|
|
@@ -1,23 +1,34 @@
|
|
|
1
|
-
import { fetchJsonOnce } from "../util/FetchHelper.js";
|
|
2
1
|
import { attachLanguageChange } from "../locale/languageChange.js";
|
|
3
2
|
import getLocale from "../locale/getLocale.js";
|
|
4
|
-
import { getFeature } from "../FeaturesRegistry.js";
|
|
5
3
|
import { DEFAULT_LOCALE, SUPPORTED_LOCALES } from "../generated/AssetParameters.js";
|
|
6
|
-
import {
|
|
7
|
-
|
|
8
|
-
const resources = new Map();
|
|
9
|
-
const cldrData = {};
|
|
10
|
-
const cldrUrls = {};
|
|
4
|
+
import { getFeature } from "../FeaturesRegistry.js";
|
|
11
5
|
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
6
|
+
const localeDataMap = new Map();
|
|
7
|
+
const loaders = new Map();
|
|
8
|
+
const cldrPromises = new Map();
|
|
9
|
+
const reportedErrors = new Set();
|
|
10
|
+
let warningShown = false;
|
|
15
11
|
|
|
16
12
|
const M_ISO639_OLD_TO_NEW = {
|
|
17
13
|
"iw": "he",
|
|
18
14
|
"ji": "yi",
|
|
19
15
|
"in": "id",
|
|
20
|
-
|
|
16
|
+
};
|
|
17
|
+
|
|
18
|
+
const DEV_MODE = false;
|
|
19
|
+
|
|
20
|
+
const _showAssetsWarningOnce = localeId => {
|
|
21
|
+
if (warningShown) {
|
|
22
|
+
return;
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
if (!DEV_MODE) {
|
|
26
|
+
console.warn(`[LocaleData] Supported locale "${localeId}" not configured, import the "Assets.js" module from the webcomponents package you are using.`); /* eslint-disable-line */
|
|
27
|
+
} else {
|
|
28
|
+
console.warn(`[LocaleData] Note: in dev mode, CLDR assets might be disabled for performance reasons. Try running "ENABLE_CLDR=1 yarn start" to test CLDR assets.`); /* eslint-disable-line */
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
warningShown = true;
|
|
21
32
|
};
|
|
22
33
|
|
|
23
34
|
const calcLocale = (language, region, script) => {
|
|
@@ -36,87 +47,108 @@ const calcLocale = (language, region, script) => {
|
|
|
36
47
|
}
|
|
37
48
|
}
|
|
38
49
|
|
|
50
|
+
// Special case 3: for Serbian, there are cyrillic and latin scripts, "sh" and "sr-latn" map to "latin", "sr" maps to cyrillic.
|
|
51
|
+
if (language === "sh" || (language === "sr" && script === "Latn")) {
|
|
52
|
+
language = "sr";
|
|
53
|
+
region = "Latn";
|
|
54
|
+
}
|
|
55
|
+
|
|
39
56
|
// try language + region
|
|
40
57
|
let localeId = `${language}_${region}`;
|
|
41
|
-
if (
|
|
42
|
-
|
|
43
|
-
|
|
58
|
+
if (SUPPORTED_LOCALES.includes(localeId)) {
|
|
59
|
+
if (loaders.has(localeId)) {
|
|
60
|
+
// supported and has loader
|
|
61
|
+
return localeId;
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
// supported, no loader - fallback to default and warn
|
|
65
|
+
_showAssetsWarningOnce(localeId);
|
|
66
|
+
return DEFAULT_LOCALE;
|
|
44
67
|
}
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
68
|
+
|
|
69
|
+
// not supported, try language only
|
|
70
|
+
localeId = language;
|
|
71
|
+
if (SUPPORTED_LOCALES.includes(localeId)) {
|
|
72
|
+
if (loaders.has(localeId)) {
|
|
73
|
+
// supported and has loader
|
|
74
|
+
return localeId;
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
// supported, no loader - fallback to default and warn
|
|
78
|
+
_showAssetsWarningOnce(localeId);
|
|
79
|
+
return DEFAULT_LOCALE;
|
|
48
80
|
}
|
|
49
81
|
|
|
50
|
-
|
|
82
|
+
// not supported - fallback to default locale
|
|
83
|
+
return DEFAULT_LOCALE;
|
|
51
84
|
};
|
|
52
85
|
|
|
86
|
+
// internal set data
|
|
87
|
+
const setLocaleData = (localeId, content) => {
|
|
88
|
+
localeDataMap.set(localeId, content);
|
|
89
|
+
};
|
|
53
90
|
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
91
|
+
// external getSync
|
|
92
|
+
const getLocaleData = localeId => {
|
|
93
|
+
// if there is no loader, the default fallback was fetched and a warning was given - use default locale instead
|
|
94
|
+
if (!loaders.has(localeId)) {
|
|
95
|
+
localeId = DEFAULT_LOCALE;
|
|
57
96
|
}
|
|
58
97
|
|
|
59
|
-
const
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
}
|
|
63
|
-
};
|
|
98
|
+
const content = localeDataMap.get(localeId);
|
|
99
|
+
if (!content) {
|
|
100
|
+
throw new Error(`CLDR data for locale ${localeId} is not loaded!`);
|
|
101
|
+
}
|
|
64
102
|
|
|
65
|
-
|
|
66
|
-
resources.set(moduleName, content);
|
|
103
|
+
return content;
|
|
67
104
|
};
|
|
68
105
|
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
return moduleContent;
|
|
73
|
-
}
|
|
106
|
+
// load bundle over the network once
|
|
107
|
+
const _loadCldrOnce = localeId => {
|
|
108
|
+
const loadCldr = loaders.get(localeId);
|
|
74
109
|
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
throw new Error(`CLDR data for locale ${missingModule[1]} is not loaded!`);
|
|
110
|
+
if (!cldrPromises.get(localeId)) {
|
|
111
|
+
cldrPromises.set(localeId, loadCldr(localeId));
|
|
78
112
|
}
|
|
79
113
|
|
|
80
|
-
|
|
114
|
+
return cldrPromises.get(localeId);
|
|
81
115
|
};
|
|
82
116
|
|
|
117
|
+
// external getAsync
|
|
83
118
|
const fetchCldr = async (language, region, script) => {
|
|
84
|
-
resolveMissingMappings();
|
|
85
119
|
const localeId = calcLocale(language, region, script);
|
|
86
120
|
|
|
87
|
-
|
|
88
|
-
const url = cldrUrls[localeId];
|
|
89
|
-
|
|
121
|
+
// reuse OpenUI5 CLDR if present
|
|
90
122
|
const OpenUI5Support = getFeature("OpenUI5Support");
|
|
91
|
-
if (
|
|
92
|
-
|
|
123
|
+
if (OpenUI5Support) {
|
|
124
|
+
const cldrContent = OpenUI5Support.getLocaleDataObject();
|
|
125
|
+
if (cldrContent) {
|
|
126
|
+
// only if openui5 actually returned valid content
|
|
127
|
+
setLocaleData(localeId, cldrContent);
|
|
128
|
+
return;
|
|
129
|
+
}
|
|
93
130
|
}
|
|
94
131
|
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
132
|
+
// fetch it
|
|
133
|
+
try {
|
|
134
|
+
const cldrContent = await _loadCldrOnce(localeId);
|
|
135
|
+
setLocaleData(localeId, cldrContent);
|
|
136
|
+
} catch (e) {
|
|
137
|
+
if (!reportedErrors.has(e.message)) {
|
|
138
|
+
reportedErrors.add(e.message);
|
|
139
|
+
console.error(e.message); /* eslint-disable-line */
|
|
140
|
+
}
|
|
102
141
|
}
|
|
103
142
|
};
|
|
104
143
|
|
|
105
|
-
const
|
|
106
|
-
|
|
107
|
-
};
|
|
108
|
-
|
|
109
|
-
const setCldrData = (locale, data) => {
|
|
110
|
-
cldrData[locale] = data;
|
|
144
|
+
const registerLocaleDataLoader = (localeId, loader) => {
|
|
145
|
+
loaders.set(localeId, loader);
|
|
111
146
|
};
|
|
112
147
|
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
const _registerMappingFunction = mappingFn => {
|
|
118
|
-
cldrMappingFn = mappingFn;
|
|
119
|
-
};
|
|
148
|
+
// register default loader for "en" from ui5 CDN (dev workflow without assets)
|
|
149
|
+
registerLocaleDataLoader("en", async runtimeLocaleId => {
|
|
150
|
+
return (await fetch(`https://ui5.sap.com/1.60.2/resources/sap/ui/core/cldr/en.json`)).json();
|
|
151
|
+
});
|
|
120
152
|
|
|
121
153
|
// When the language changes dynamically (the user calls setLanguage),
|
|
122
154
|
// re-fetch the required CDRD data.
|
|
@@ -126,10 +158,7 @@ attachLanguageChange(() => {
|
|
|
126
158
|
});
|
|
127
159
|
|
|
128
160
|
export {
|
|
161
|
+
registerLocaleDataLoader,
|
|
129
162
|
fetchCldr,
|
|
130
|
-
|
|
131
|
-
setCldrData,
|
|
132
|
-
getCldrData,
|
|
133
|
-
getModuleContent,
|
|
134
|
-
_registerMappingFunction,
|
|
163
|
+
getLocaleData,
|
|
135
164
|
};
|
|
@@ -1,10 +1,7 @@
|
|
|
1
|
-
import { fetchJsonOnce, fetchTextOnce } from "../util/FetchHelper.js";
|
|
2
1
|
import { DEFAULT_THEME } from "../generated/AssetParameters.js";
|
|
3
|
-
import getFileExtension from "../util/getFileExtension.js";
|
|
4
|
-
import { getEffectiveAssetPath } from "../util/EffectiveAssetPath.js";
|
|
5
2
|
|
|
6
|
-
const themeURLs = new Map();
|
|
7
3
|
const themeStyles = new Map();
|
|
4
|
+
const loaders = new Map();
|
|
8
5
|
const registeredPackages = new Set();
|
|
9
6
|
const registeredThemes = new Set();
|
|
10
7
|
|
|
@@ -16,29 +13,19 @@ const registeredThemes = new Set();
|
|
|
16
13
|
* Example usage:
|
|
17
14
|
* 1) Pass the CSS Vars as a string directly.
|
|
18
15
|
* registerThemeProperties("my-package", "my_theme", ":root{--var1: red;}");
|
|
19
|
-
* 2) Pass the CSS Vars as an object directly
|
|
20
|
-
* registerThemeProperties("my-package", "my_theme", {"_": ":root{--var1: red;}"});
|
|
21
|
-
* 3) Pass a URL to a CSS file, containing the CSS Vars. Will be fetched on demand, not upon registration.
|
|
22
|
-
* registerThemeProperties("my-package", "my_theme", "http://url/to/my/theme.css");
|
|
23
|
-
* 4) Pass a URL to a JSON file, containing the CSS Vars in its "_" property. Will be fetched on demand, not upon registration.
|
|
24
|
-
* registerThemeProperties("my-package", "my_theme", "http://url/to/my/theme.json");
|
|
25
16
|
*
|
|
26
17
|
* @public
|
|
27
18
|
* @param packageName - the NPM package for which CSS Vars are registered
|
|
28
19
|
* @param themeName - the theme which the CSS Vars implement
|
|
29
|
-
* @param style -
|
|
20
|
+
* @param style - the style content directly
|
|
21
|
+
* @deprecated
|
|
30
22
|
*/
|
|
31
|
-
const registerThemeProperties = (
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
themeStyles.set(`${packageName}_${themeName}`, style);
|
|
38
|
-
} else {
|
|
39
|
-
// url for fetching
|
|
40
|
-
themeURLs.set(`${packageName}_${themeName}`, style);
|
|
41
|
-
}
|
|
23
|
+
const registerThemeProperties = (_packageName, _themeName, _style) => {
|
|
24
|
+
throw new Error("`registerThemeProperties` has been depracated. Use `registerThemePropertiesLoader` instead.");
|
|
25
|
+
};
|
|
26
|
+
|
|
27
|
+
const registerThemePropertiesLoader = (packageName, themeName, loader) => {
|
|
28
|
+
loaders.set(`${packageName}/${themeName}`, loader);
|
|
42
29
|
registeredPackages.add(packageName);
|
|
43
30
|
registeredThemes.add(themeName);
|
|
44
31
|
};
|
|
@@ -55,23 +42,25 @@ const getThemeProperties = async (packageName, themeName) => {
|
|
|
55
42
|
return themeStyles.get(`${packageName}_${DEFAULT_THEME}`);
|
|
56
43
|
}
|
|
57
44
|
|
|
58
|
-
const
|
|
45
|
+
const loader = loaders.get(`${packageName}/${themeName}`);
|
|
46
|
+
if (!loader) {
|
|
47
|
+
// no themes for package
|
|
48
|
+
console.error(`Theme [${themeName}] not registered for package [${packageName}]`); /* eslint-disable-line */
|
|
49
|
+
return;
|
|
50
|
+
}
|
|
51
|
+
let data;
|
|
52
|
+
try {
|
|
53
|
+
data = await loader(themeName);
|
|
54
|
+
} catch (e) {
|
|
55
|
+
console.error(packageName, e.message); /* eslint-disable-line */
|
|
56
|
+
return;
|
|
57
|
+
}
|
|
59
58
|
const themeProps = data._ || data;
|
|
60
59
|
|
|
61
60
|
themeStyles.set(`${packageName}_${themeName}`, themeProps);
|
|
62
61
|
return themeProps;
|
|
63
62
|
};
|
|
64
63
|
|
|
65
|
-
const fetchThemeProperties = async (packageName, themeName) => {
|
|
66
|
-
const url = themeURLs.get(`${packageName}_${themeName}`);
|
|
67
|
-
|
|
68
|
-
if (!url) {
|
|
69
|
-
throw new Error(`You have to import the ${packageName}/dist/Assets.js module to switch to additional themes`);
|
|
70
|
-
}
|
|
71
|
-
|
|
72
|
-
return getFileExtension(url) === ".css" ? fetchTextOnce(url) : fetchJsonOnce(getEffectiveAssetPath(url));
|
|
73
|
-
};
|
|
74
|
-
|
|
75
64
|
const getRegisteredPackages = () => {
|
|
76
65
|
return registeredPackages;
|
|
77
66
|
};
|
|
@@ -81,6 +70,7 @@ const isThemeRegistered = theme => {
|
|
|
81
70
|
};
|
|
82
71
|
|
|
83
72
|
export {
|
|
73
|
+
registerThemePropertiesLoader,
|
|
84
74
|
registerThemeProperties,
|
|
85
75
|
getThemeProperties,
|
|
86
76
|
getRegisteredPackages,
|
|
@@ -1,23 +1,31 @@
|
|
|
1
|
-
import { getFeature } from "../FeaturesRegistry.js";
|
|
2
1
|
import getLocale from "../locale/getLocale.js";
|
|
3
2
|
import { attachLanguageChange } from "../locale/languageChange.js";
|
|
4
|
-
import { fetchTextOnce } from "../util/FetchHelper.js";
|
|
5
3
|
import normalizeLocale from "../locale/normalizeLocale.js";
|
|
6
4
|
import nextFallbackLocale from "../locale/nextFallbackLocale.js";
|
|
7
5
|
import { DEFAULT_LANGUAGE } from "../generated/AssetParameters.js";
|
|
8
|
-
import {
|
|
9
|
-
|
|
6
|
+
import { getFetchDefaultLanguage } from "../config/Language.js";
|
|
7
|
+
|
|
8
|
+
// contains package names for which the warning has been shown
|
|
9
|
+
const warningShown = new Set();
|
|
10
|
+
const reportedErrors = new Set();
|
|
10
11
|
|
|
11
12
|
const bundleData = new Map();
|
|
12
|
-
const
|
|
13
|
+
const bundlePromises = new Map();
|
|
14
|
+
const loaders = new Map();
|
|
13
15
|
|
|
14
16
|
/**
|
|
15
|
-
*
|
|
16
|
-
* @param {string} packageName
|
|
17
|
-
* @param {
|
|
18
|
-
* @
|
|
17
|
+
*
|
|
18
|
+
* @param {string} packageName for which package this loader can fetch data
|
|
19
|
+
* @param {function} loader async function that will be passed a localeId and should return a JSON object
|
|
20
|
+
* @param {Array} localeIds Array of locale IDs that this loader can handle
|
|
19
21
|
*/
|
|
20
|
-
const
|
|
22
|
+
const registerI18nLoader = (packageName, localeId, loader) => {
|
|
23
|
+
// register loader by key
|
|
24
|
+
const bundleKey = `${packageName}/${localeId}`;
|
|
25
|
+
loaders.set(bundleKey, loader);
|
|
26
|
+
};
|
|
27
|
+
|
|
28
|
+
const _setI18nBundleData = (packageName, data) => {
|
|
21
29
|
bundleData.set(packageName, data);
|
|
22
30
|
};
|
|
23
31
|
|
|
@@ -26,18 +34,36 @@ const getI18nBundleData = packageName => {
|
|
|
26
34
|
};
|
|
27
35
|
|
|
28
36
|
/**
|
|
29
|
-
* Registers a map of locale/url information, to be used by the <code>fetchI18nBundle</code> method.
|
|
30
|
-
* Note: In order to be able to register ".properties" files, you must import the following module:
|
|
31
|
-
* import "@ui5/webcomponents-base/dist/features/PropertiesFormatSupport.js";
|
|
32
|
-
*
|
|
33
|
-
* @param {string} packageName package ID that the i18n bundle will be related to
|
|
34
|
-
* @param {Object} bundle an object with string locales as keys and the URLs (in .json or .properties format - see the note above) where the corresponding locale can be fetched from, f.e {"en": "path/en.json", ...}
|
|
35
|
-
*
|
|
36
37
|
* @public
|
|
38
|
+
* @deprecated
|
|
37
39
|
*/
|
|
38
|
-
const registerI18nBundle = (
|
|
39
|
-
|
|
40
|
-
|
|
40
|
+
const registerI18nBundle = (_packageName, _bundle) => {
|
|
41
|
+
throw new Error("This method has been removed. Use `registerI18nLoader` instead.");
|
|
42
|
+
};
|
|
43
|
+
|
|
44
|
+
const _hasLoader = (packageName, localeId) => {
|
|
45
|
+
const bundleKey = `${packageName}/${localeId}`;
|
|
46
|
+
return loaders.has(bundleKey);
|
|
47
|
+
};
|
|
48
|
+
|
|
49
|
+
// load bundle over the network once
|
|
50
|
+
const _loadMessageBundleOnce = (packageName, localeId) => {
|
|
51
|
+
const bundleKey = `${packageName}/${localeId}`;
|
|
52
|
+
const loadMessageBundle = loaders.get(bundleKey);
|
|
53
|
+
|
|
54
|
+
if (!bundlePromises.get(bundleKey)) {
|
|
55
|
+
bundlePromises.set(bundleKey, loadMessageBundle(localeId));
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
return bundlePromises.get(bundleKey);
|
|
59
|
+
};
|
|
60
|
+
|
|
61
|
+
const _showAssetsWarningOnce = packageName => {
|
|
62
|
+
if (!warningShown.has(packageName)) {
|
|
63
|
+
console.warn(`[${packageName}]: Message bundle assets are not configured. Falling back to English texts.`, /* eslint-disable-line */
|
|
64
|
+
` Add \`import "${packageName}/dist/Assets.js"\` in your bundle and make sure your build tool supports dynamic imports and JSON imports. See section "Assets" in the documentation for more information.`); /* eslint-disable-line */
|
|
65
|
+
warningShown.add(packageName);
|
|
66
|
+
}
|
|
41
67
|
};
|
|
42
68
|
|
|
43
69
|
/**
|
|
@@ -50,50 +76,35 @@ const registerI18nBundle = (packageName, bundle) => {
|
|
|
50
76
|
* @public
|
|
51
77
|
*/
|
|
52
78
|
const fetchI18nBundle = async packageName => {
|
|
53
|
-
const bundlesForPackage = bundleURLs.get(packageName);
|
|
54
|
-
|
|
55
|
-
if (!bundlesForPackage) {
|
|
56
|
-
console.warn(`Message bundle assets are not configured. Falling back to English texts.`, /* eslint-disable-line */
|
|
57
|
-
` You need to import ${packageName}/dist/Assets.js with a build tool that supports JSON imports.`); /* eslint-disable-line */
|
|
58
|
-
return;
|
|
59
|
-
}
|
|
60
|
-
|
|
61
79
|
const language = getLocale().getLanguage();
|
|
62
80
|
const region = getLocale().getRegion();
|
|
63
|
-
const useDefaultLanguage = getUseDefaultLanguage();
|
|
64
81
|
let localeId = normalizeLocale(language + (region ? `-${region}` : ``));
|
|
65
82
|
|
|
66
|
-
while (localeId !== DEFAULT_LANGUAGE && !
|
|
83
|
+
while (localeId !== DEFAULT_LANGUAGE && !_hasLoader(packageName, localeId)) {
|
|
67
84
|
localeId = nextFallbackLocale(localeId);
|
|
68
85
|
}
|
|
69
86
|
|
|
70
|
-
|
|
71
|
-
|
|
87
|
+
// use default language unless configured to always fetch it from the network
|
|
88
|
+
const fetchDefaultLanguage = getFetchDefaultLanguage();
|
|
89
|
+
if (localeId === DEFAULT_LANGUAGE && !fetchDefaultLanguage) {
|
|
90
|
+
_setI18nBundleData(packageName, null); // reset for the default language (if data was set for a previous language)
|
|
72
91
|
return;
|
|
73
92
|
}
|
|
74
93
|
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
if (typeof bundleURL === "object") { // inlined from build
|
|
78
|
-
setI18nBundleData(packageName, bundleURL);
|
|
94
|
+
if (!_hasLoader(packageName, localeId)) {
|
|
95
|
+
_showAssetsWarningOnce(packageName);
|
|
79
96
|
return;
|
|
80
97
|
}
|
|
81
98
|
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
throw new Error(`In order to support .properties files, please: import "@ui5/webcomponents-base/dist/features/PropertiesFormatSupport.js";`);
|
|
99
|
+
try {
|
|
100
|
+
const data = await _loadMessageBundleOnce(packageName, localeId);
|
|
101
|
+
_setI18nBundleData(packageName, data);
|
|
102
|
+
} catch (e) {
|
|
103
|
+
if (!reportedErrors.has(e.message)) {
|
|
104
|
+
reportedErrors.add(e.message);
|
|
105
|
+
console.error(e.message); /* eslint-disable-line */
|
|
90
106
|
}
|
|
91
|
-
parser = PropertiesFormatSupport.parser;
|
|
92
107
|
}
|
|
93
|
-
|
|
94
|
-
const data = parser(content);
|
|
95
|
-
|
|
96
|
-
setI18nBundleData(packageName, data);
|
|
97
108
|
};
|
|
98
109
|
|
|
99
110
|
// When the language changes dynamically (the user calls setLanguage), re-fetch all previously fetched bundles
|
|
@@ -103,8 +114,8 @@ attachLanguageChange(() => {
|
|
|
103
114
|
});
|
|
104
115
|
|
|
105
116
|
export {
|
|
117
|
+
registerI18nLoader,
|
|
106
118
|
fetchI18nBundle,
|
|
107
119
|
registerI18nBundle,
|
|
108
|
-
setI18nBundleData,
|
|
109
120
|
getI18nBundleData,
|
|
110
121
|
};
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Supported icon collection names and aliases.
|
|
3
|
+
*
|
|
4
|
+
* Users might specify a collection, using both the key and the value in the following key-value pairs,
|
|
5
|
+
* e.g the following pairs are completely exchangeable:
|
|
6
|
+
* "SAP-icons-TNT/actor" and "tnt/actor", "BusinessSuiteInAppSymbols/3d" and "business-suite/3d",
|
|
7
|
+
* "SAP-icons-v5/accept" and "horizon/accept".
|
|
8
|
+
*
|
|
9
|
+
* Note: technically, in the code we maintain the collections under the "value" name - "tnt", "business-suite",
|
|
10
|
+
* SAP-icons-v5" and "SAP-icons"(which does not have an alias).
|
|
11
|
+
*/
|
|
12
|
+
const IconCollectionsAlias = {
|
|
13
|
+
"SAP-icons-TNT": "tnt",
|
|
14
|
+
"BusinessSuiteInAppSymbols": "business-suite",
|
|
15
|
+
"horizon": "SAP-icons-v5",
|
|
16
|
+
};
|
|
17
|
+
|
|
18
|
+
export default IconCollectionsAlias;
|