@chayns-components/translation 5.0.0-beta.1261 → 5.0.0-beta.1271
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/lib/cjs/components/AdaptiveTranslation.js +20 -8
- package/lib/cjs/components/AdaptiveTranslation.js.map +1 -1
- package/lib/cjs/hooks/useAdaptiveTranslation.js +5 -4
- package/lib/cjs/hooks/useAdaptiveTranslation.js.map +1 -1
- package/lib/cjs/types/translation.js.map +1 -1
- package/lib/cjs/utils/translationHandler.js +7 -4
- package/lib/cjs/utils/translationHandler.js.map +1 -1
- package/lib/esm/components/AdaptiveTranslation.js +20 -8
- package/lib/esm/components/AdaptiveTranslation.js.map +1 -1
- package/lib/esm/hooks/useAdaptiveTranslation.js +5 -4
- package/lib/esm/hooks/useAdaptiveTranslation.js.map +1 -1
- package/lib/esm/types/translation.js.map +1 -1
- package/lib/esm/utils/translationHandler.js +7 -4
- package/lib/esm/utils/translationHandler.js.map +1 -1
- package/lib/types/components/AdaptiveTranslation.d.ts +12 -3
- package/lib/types/hooks/useAdaptiveTranslation.d.ts +5 -1
- package/lib/types/types/translation.d.ts +1 -0
- package/lib/types/utils/translationHandler.d.ts +1 -1
- package/package.json +2 -2
|
@@ -14,25 +14,37 @@ const AdaptiveTranslation = ({
|
|
|
14
14
|
from,
|
|
15
15
|
tagName: TagName = 'span',
|
|
16
16
|
style,
|
|
17
|
-
className
|
|
17
|
+
className,
|
|
18
|
+
textType,
|
|
19
|
+
text = ''
|
|
18
20
|
}) => {
|
|
19
21
|
const {
|
|
20
|
-
text,
|
|
22
|
+
text: translated,
|
|
21
23
|
isLoading,
|
|
22
24
|
isFetching
|
|
23
|
-
} = (0, _useAdaptiveTranslation.useAdaptiveTranslation)(children, {
|
|
25
|
+
} = (0, _useAdaptiveTranslation.useAdaptiveTranslation)(typeof children === 'function' ? text : children, {
|
|
24
26
|
from,
|
|
25
|
-
to
|
|
27
|
+
to,
|
|
28
|
+
textType
|
|
26
29
|
});
|
|
30
|
+
|
|
31
|
+
// eslint-disable-next-line no-nested-ternary
|
|
32
|
+
const opacity = isLoading ? 0 : isFetching ? 0.5 : 1;
|
|
27
33
|
return /*#__PURE__*/_react.default.createElement(TagName, {
|
|
28
|
-
className: (0, _clsx.default)('notranslate', className),
|
|
34
|
+
className: (0, _clsx.default)('notranslate adaptive-translation', className),
|
|
29
35
|
style: {
|
|
30
|
-
// eslint-disable-next-line no-nested-ternary
|
|
31
|
-
opacity: isLoading ? 0 : isFetching ? 0.5 : 1,
|
|
32
36
|
transition: 'opacity 0.5s ease',
|
|
33
37
|
...style
|
|
34
38
|
}
|
|
35
|
-
},
|
|
39
|
+
}, typeof children === 'function' ? children(translated) : translated, /*#__PURE__*/_react.default.createElement("style", null, `
|
|
40
|
+
.adaptive-translation > *:not(img) {
|
|
41
|
+
opacity: ${opacity};
|
|
42
|
+
transition: opacity 0.5s ease;
|
|
43
|
+
}
|
|
44
|
+
.adaptive-translation img {
|
|
45
|
+
opacity: 1 !important;
|
|
46
|
+
}
|
|
47
|
+
`));
|
|
36
48
|
};
|
|
37
49
|
var _default = exports.default = AdaptiveTranslation;
|
|
38
50
|
//# sourceMappingURL=AdaptiveTranslation.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"AdaptiveTranslation.js","names":["_react","_interopRequireDefault","require","_clsx","_useAdaptiveTranslation","e","__esModule","default","AdaptiveTranslation","children","to","from","tagName","TagName","style","className","text","isLoading","isFetching","useAdaptiveTranslation","
|
|
1
|
+
{"version":3,"file":"AdaptiveTranslation.js","names":["_react","_interopRequireDefault","require","_clsx","_useAdaptiveTranslation","e","__esModule","default","AdaptiveTranslation","children","to","from","tagName","TagName","style","className","textType","text","translated","isLoading","isFetching","useAdaptiveTranslation","opacity","createElement","clsx","transition","_default","exports"],"sources":["../../../src/components/AdaptiveTranslation.tsx"],"sourcesContent":["import React, { CSSProperties, ReactNode } from 'react';\nimport clsx from 'clsx';\nimport { useAdaptiveTranslation } from '../hooks/useAdaptiveTranslation';\nimport { Language } from 'chayns-api';\n\ntype TranslationChildren = ((text: string) => ReactNode) | string;\n\ntype AdaptiveTranslationProps = {\n /**\n * The Text that should be translated.\n */\n children: TranslationChildren;\n /**\n * The className of the element.\n */\n className?: string;\n /**\n * The language from which the text should be translated.\n */\n from?: Exclude<Language, Language.Unknown>;\n /**\n * Optional styles of the HTML element.\n */\n style?: CSSProperties;\n /**\n * The HTML tag of the children.\n */\n tagName?: keyof HTMLElementTagNameMap;\n /**\n * The text that should be translated. Only active if the children is type of function.\n */\n text?: string;\n /**\n * The type of the text.\n */\n textType?: string;\n /**\n * The language to which the text should be translated.\n */\n to?: Exclude<Language, Language.Unknown>;\n};\n\nconst AdaptiveTranslation = ({\n children,\n to,\n from,\n tagName: TagName = 'span',\n style,\n className,\n textType,\n text = '',\n}: AdaptiveTranslationProps) => {\n const {\n text: translated,\n isLoading,\n isFetching,\n } = useAdaptiveTranslation(typeof children === 'function' ? text : children, {\n from,\n to,\n textType,\n });\n\n // eslint-disable-next-line no-nested-ternary\n const opacity = isLoading ? 0 : isFetching ? 0.5 : 1;\n\n return (\n <TagName\n className={clsx('notranslate adaptive-translation', className)}\n style={{\n transition: 'opacity 0.5s ease',\n ...style,\n }}\n >\n {typeof children === 'function' ? children(translated) : translated}\n\n <style>\n {`\n .adaptive-translation > *:not(img) {\n opacity: ${opacity};\n transition: opacity 0.5s ease;\n }\n .adaptive-translation img {\n opacity: 1 !important;\n }\n `}\n </style>\n </TagName>\n );\n};\nexport default AdaptiveTranslation;\n"],"mappings":";;;;;;AAAC,IAAAA,MAAA,GAAAC,sBAAA,CAAAC,OAAA;AACD,IAAAC,KAAA,GAAAF,sBAAA,CAAAC,OAAA;AACA,IAAAE,uBAAA,GAAAF,OAAA;AAAyE,SAAAD,uBAAAI,CAAA,WAAAA,CAAA,IAAAA,CAAA,CAAAC,UAAA,GAAAD,CAAA,KAAAE,OAAA,EAAAF,CAAA;AAwCzE,MAAMG,mBAAmB,GAAGA,CAAC;EACzBC,QAAQ;EACRC,EAAE;EACFC,IAAI;EACJC,OAAO,EAAEC,OAAO,GAAG,MAAM;EACzBC,KAAK;EACLC,SAAS;EACTC,QAAQ;EACRC,IAAI,GAAG;AACe,CAAC,KAAK;EAC5B,MAAM;IACFA,IAAI,EAAEC,UAAU;IAChBC,SAAS;IACTC;EACJ,CAAC,GAAG,IAAAC,8CAAsB,EAAC,OAAOZ,QAAQ,KAAK,UAAU,GAAGQ,IAAI,GAAGR,QAAQ,EAAE;IACzEE,IAAI;IACJD,EAAE;IACFM;EACJ,CAAC,CAAC;;EAEF;EACA,MAAMM,OAAO,GAAGH,SAAS,GAAG,CAAC,GAAGC,UAAU,GAAG,GAAG,GAAG,CAAC;EAEpD,oBACIpB,MAAA,CAAAO,OAAA,CAAAgB,aAAA,CAACV,OAAO;IACJE,SAAS,EAAE,IAAAS,aAAI,EAAC,kCAAkC,EAAET,SAAS,CAAE;IAC/DD,KAAK,EAAE;MACHW,UAAU,EAAE,mBAAmB;MAC/B,GAAGX;IACP;EAAE,GAED,OAAOL,QAAQ,KAAK,UAAU,GAAGA,QAAQ,CAACS,UAAU,CAAC,GAAGA,UAAU,eAEnElB,MAAA,CAAAO,OAAA,CAAAgB,aAAA,gBACK;AACjB;AACA,mCAAmCD,OAAO;AAC1C;AACA;AACA;AACA;AACA;AACA,iBACmB,CACF,CAAC;AAElB,CAAC;AAAC,IAAAI,QAAA,GAAAC,OAAA,CAAApB,OAAA,GACaC,mBAAmB","ignoreList":[]}
|
|
@@ -10,12 +10,13 @@ var _translationHandler = _interopRequireDefault(require("../utils/translationHa
|
|
|
10
10
|
function _interopRequireDefault(e) { return e && e.__esModule ? e : { default: e }; }
|
|
11
11
|
const useAdaptiveTranslation = (originalText, {
|
|
12
12
|
to,
|
|
13
|
-
from
|
|
13
|
+
from,
|
|
14
|
+
textType
|
|
14
15
|
} = {}) => {
|
|
15
16
|
const options = (0, _react.useContext)(_translationOptionsContext.TranslationOptionsContext);
|
|
16
17
|
const toLanguage = to || options.to;
|
|
17
18
|
const fromLanguage = from || options.from;
|
|
18
|
-
const shouldTranslate = (0, _react.useMemo)(() => toLanguage !== fromLanguage, [fromLanguage, toLanguage]);
|
|
19
|
+
const shouldTranslate = (0, _react.useMemo)(() => toLanguage !== fromLanguage && originalText.length !== 0, [fromLanguage, originalText.length, toLanguage]);
|
|
19
20
|
const [translatedText, setTranslatedText] = (0, _react.useState)(originalText);
|
|
20
21
|
const [isLoading, setIsLoading] = (0, _react.useState)(shouldTranslate);
|
|
21
22
|
const [isFetching, setIsFetching] = (0, _react.useState)(false);
|
|
@@ -23,7 +24,7 @@ const useAdaptiveTranslation = (originalText, {
|
|
|
23
24
|
const timeoutRef = setTimeout(() => {
|
|
24
25
|
if (shouldTranslate) {
|
|
25
26
|
setIsFetching(true);
|
|
26
|
-
void _translationHandler.default.translateText(originalText, fromLanguage, toLanguage).then(text => {
|
|
27
|
+
void _translationHandler.default.translateText(originalText, fromLanguage, toLanguage, textType).then(text => {
|
|
27
28
|
setTranslatedText(text);
|
|
28
29
|
}).finally(() => {
|
|
29
30
|
setIsLoading(false);
|
|
@@ -32,7 +33,7 @@ const useAdaptiveTranslation = (originalText, {
|
|
|
32
33
|
}
|
|
33
34
|
}, 200);
|
|
34
35
|
return () => clearTimeout(timeoutRef);
|
|
35
|
-
}, [originalText, shouldTranslate, toLanguage, fromLanguage]);
|
|
36
|
+
}, [originalText, shouldTranslate, toLanguage, fromLanguage, textType]);
|
|
36
37
|
return (0, _react.useMemo)(() => ({
|
|
37
38
|
text: shouldTranslate ? translatedText : originalText,
|
|
38
39
|
isFetching: shouldTranslate ? isFetching : false,
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"useAdaptiveTranslation.js","names":["_react","require","_translationOptionsContext","_translationHandler","_interopRequireDefault","e","__esModule","default","useAdaptiveTranslation","originalText","to","from","options","useContext","TranslationOptionsContext","toLanguage","fromLanguage","shouldTranslate","useMemo","translatedText","setTranslatedText","useState","isLoading","setIsLoading","isFetching","setIsFetching","useEffect","timeoutRef","setTimeout","translationHandler","translateText","then","text","finally","clearTimeout","exports"],"sources":["../../../src/hooks/useAdaptiveTranslation.ts"],"sourcesContent":["import { useContext, useEffect, useMemo, useState } from 'react';\nimport { Language } from 'chayns-api';\nimport { TranslationOptionsContext } from '../constants/translationOptionsContext';\nimport translationHandler from '../utils/translationHandler';\n\ninterface UseAdaptiveTranslationOptions {\n /**\n * The language from which the text should be translated.\n */\n from?: Exclude<Language, Language.Unknown>;\n /**\n * The language to which the text should be translated.\n */\n to?: Exclude<Language, Language.Unknown>;\n}\n\nexport const useAdaptiveTranslation = (\n originalText: string,\n { to, from }: UseAdaptiveTranslationOptions = {},\n): { text: string; isLoading: boolean; isFetching: boolean } => {\n const options = useContext(TranslationOptionsContext);\n const toLanguage = to || options.to;\n const fromLanguage = from || options.from;\n const shouldTranslate = useMemo(() => toLanguage !== fromLanguage
|
|
1
|
+
{"version":3,"file":"useAdaptiveTranslation.js","names":["_react","require","_translationOptionsContext","_translationHandler","_interopRequireDefault","e","__esModule","default","useAdaptiveTranslation","originalText","to","from","textType","options","useContext","TranslationOptionsContext","toLanguage","fromLanguage","shouldTranslate","useMemo","length","translatedText","setTranslatedText","useState","isLoading","setIsLoading","isFetching","setIsFetching","useEffect","timeoutRef","setTimeout","translationHandler","translateText","then","text","finally","clearTimeout","exports"],"sources":["../../../src/hooks/useAdaptiveTranslation.ts"],"sourcesContent":["import { useContext, useEffect, useMemo, useState } from 'react';\nimport { Language } from 'chayns-api';\nimport { TranslationOptionsContext } from '../constants/translationOptionsContext';\nimport translationHandler from '../utils/translationHandler';\n\ninterface UseAdaptiveTranslationOptions {\n /**\n * The language from which the text should be translated.\n */\n from?: Exclude<Language, Language.Unknown>;\n /**\n * The type of the text.\n */\n textType?: string;\n /**\n * The language to which the text should be translated.\n */\n to?: Exclude<Language, Language.Unknown>;\n}\n\nexport const useAdaptiveTranslation = (\n originalText: string,\n { to, from, textType }: UseAdaptiveTranslationOptions = {},\n): { text: string; isLoading: boolean; isFetching: boolean } => {\n const options = useContext(TranslationOptionsContext);\n const toLanguage = to || options.to;\n const fromLanguage = from || options.from;\n const shouldTranslate = useMemo(\n () => toLanguage !== fromLanguage && originalText.length !== 0,\n [fromLanguage, originalText.length, toLanguage],\n );\n const [translatedText, setTranslatedText] = useState<string>(originalText);\n const [isLoading, setIsLoading] = useState(shouldTranslate);\n const [isFetching, setIsFetching] = useState(false);\n\n useEffect(() => {\n const timeoutRef = setTimeout(() => {\n if (shouldTranslate) {\n setIsFetching(true);\n void translationHandler\n .translateText(originalText, fromLanguage, toLanguage, textType)\n .then((text) => {\n setTranslatedText(text);\n })\n .finally(() => {\n setIsLoading(false);\n setIsFetching(false);\n });\n }\n }, 200);\n\n return () => clearTimeout(timeoutRef);\n }, [originalText, shouldTranslate, toLanguage, fromLanguage, textType]);\n\n return useMemo(\n () => ({\n text: shouldTranslate ? translatedText : originalText,\n isFetching: shouldTranslate ? isFetching : false,\n isLoading: shouldTranslate ? isLoading : false,\n }),\n [isFetching, isLoading, originalText, shouldTranslate, translatedText],\n );\n};\n"],"mappings":";;;;;;AAAC,IAAAA,MAAA,GAAAC,OAAA;AAED,IAAAC,0BAAA,GAAAD,OAAA;AACA,IAAAE,mBAAA,GAAAC,sBAAA,CAAAH,OAAA;AAA6D,SAAAG,uBAAAC,CAAA,WAAAA,CAAA,IAAAA,CAAA,CAAAC,UAAA,GAAAD,CAAA,KAAAE,OAAA,EAAAF,CAAA;AAiBtD,MAAMG,sBAAsB,GAAGA,CAClCC,YAAoB,EACpB;EAAEC,EAAE;EAAEC,IAAI;EAAEC;AAAwC,CAAC,GAAG,CAAC,CAAC,KACE;EAC5D,MAAMC,OAAO,GAAG,IAAAC,iBAAU,EAACC,oDAAyB,CAAC;EACrD,MAAMC,UAAU,GAAGN,EAAE,IAAIG,OAAO,CAACH,EAAE;EACnC,MAAMO,YAAY,GAAGN,IAAI,IAAIE,OAAO,CAACF,IAAI;EACzC,MAAMO,eAAe,GAAG,IAAAC,cAAO,EAC3B,MAAMH,UAAU,KAAKC,YAAY,IAAIR,YAAY,CAACW,MAAM,KAAK,CAAC,EAC9D,CAACH,YAAY,EAAER,YAAY,CAACW,MAAM,EAAEJ,UAAU,CAClD,CAAC;EACD,MAAM,CAACK,cAAc,EAAEC,iBAAiB,CAAC,GAAG,IAAAC,eAAQ,EAASd,YAAY,CAAC;EAC1E,MAAM,CAACe,SAAS,EAAEC,YAAY,CAAC,GAAG,IAAAF,eAAQ,EAACL,eAAe,CAAC;EAC3D,MAAM,CAACQ,UAAU,EAAEC,aAAa,CAAC,GAAG,IAAAJ,eAAQ,EAAC,KAAK,CAAC;EAEnD,IAAAK,gBAAS,EAAC,MAAM;IACZ,MAAMC,UAAU,GAAGC,UAAU,CAAC,MAAM;MAChC,IAAIZ,eAAe,EAAE;QACjBS,aAAa,CAAC,IAAI,CAAC;QACnB,KAAKI,2BAAkB,CAClBC,aAAa,CAACvB,YAAY,EAAEQ,YAAY,EAAED,UAAU,EAAEJ,QAAQ,CAAC,CAC/DqB,IAAI,CAAEC,IAAI,IAAK;UACZZ,iBAAiB,CAACY,IAAI,CAAC;QAC3B,CAAC,CAAC,CACDC,OAAO,CAAC,MAAM;UACXV,YAAY,CAAC,KAAK,CAAC;UACnBE,aAAa,CAAC,KAAK,CAAC;QACxB,CAAC,CAAC;MACV;IACJ,CAAC,EAAE,GAAG,CAAC;IAEP,OAAO,MAAMS,YAAY,CAACP,UAAU,CAAC;EACzC,CAAC,EAAE,CAACpB,YAAY,EAAES,eAAe,EAAEF,UAAU,EAAEC,YAAY,EAAEL,QAAQ,CAAC,CAAC;EAEvE,OAAO,IAAAO,cAAO,EACV,OAAO;IACHe,IAAI,EAAEhB,eAAe,GAAGG,cAAc,GAAGZ,YAAY;IACrDiB,UAAU,EAAER,eAAe,GAAGQ,UAAU,GAAG,KAAK;IAChDF,SAAS,EAAEN,eAAe,GAAGM,SAAS,GAAG;EAC7C,CAAC,CAAC,EACF,CAACE,UAAU,EAAEF,SAAS,EAAEf,YAAY,EAAES,eAAe,EAAEG,cAAc,CACzE,CAAC;AACL,CAAC;AAACgB,OAAA,CAAA7B,sBAAA,GAAAA,sBAAA","ignoreList":[]}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"translation.js","names":[],"sources":["../../../src/types/translation.ts"],"sourcesContent":["import { Deferred } from '../utils/deferred';\n\ninterface BaseTranslation {\n text: string;\n to: string;\n from: string;\n}\n\nexport interface QueuedItem extends BaseTranslation {\n deferred: Deferred<string>;\n}\n\nexport interface TranslationBatchItem extends TranslationRequest {\n deferred: Deferred<string>;\n}\n\nexport interface TranslationRequest extends BaseTranslation {\n id: number;\n}\n"],"mappings":"","ignoreList":[]}
|
|
1
|
+
{"version":3,"file":"translation.js","names":[],"sources":["../../../src/types/translation.ts"],"sourcesContent":["import { Deferred } from '../utils/deferred';\n\ninterface BaseTranslation {\n text: string;\n to: string;\n from: string;\n textType?: string;\n}\n\nexport interface QueuedItem extends BaseTranslation {\n deferred: Deferred<string>;\n}\n\nexport interface TranslationBatchItem extends TranslationRequest {\n deferred: Deferred<string>;\n}\n\nexport interface TranslationRequest extends BaseTranslation {\n id: number;\n}\n"],"mappings":"","ignoreList":[]}
|
|
@@ -47,7 +47,8 @@ class TranslationHandler {
|
|
|
47
47
|
text,
|
|
48
48
|
deferred,
|
|
49
49
|
to,
|
|
50
|
-
from
|
|
50
|
+
from,
|
|
51
|
+
textType
|
|
51
52
|
} = this.translationQueue.shift();
|
|
52
53
|
totalLength += text.length;
|
|
53
54
|
batch.push({
|
|
@@ -55,7 +56,8 @@ class TranslationHandler {
|
|
|
55
56
|
to,
|
|
56
57
|
from,
|
|
57
58
|
id: batch.length,
|
|
58
|
-
deferred
|
|
59
|
+
deferred,
|
|
60
|
+
textType
|
|
59
61
|
});
|
|
60
62
|
if (totalLength > _constants.BATCH_SIZE_LIMIT || batch.length >= _constants.MAX_ITEMS_PER_BATCH) {
|
|
61
63
|
// eslint-disable-next-line no-await-in-loop
|
|
@@ -71,7 +73,7 @@ class TranslationHandler {
|
|
|
71
73
|
#throttledProcessTranslationQueue = (0, _lodash.default)(this.#processedTranslationQueue, 200, {
|
|
72
74
|
leading: false
|
|
73
75
|
});
|
|
74
|
-
translateText = (original, from, to) => {
|
|
76
|
+
translateText = (original, from, to, textType) => {
|
|
75
77
|
var _this$cachedTranslati;
|
|
76
78
|
const cachedTranslation = (_this$cachedTranslati = this.cachedTranslations[from]) === null || _this$cachedTranslati === void 0 || (_this$cachedTranslati = _this$cachedTranslati[to]) === null || _this$cachedTranslati === void 0 ? void 0 : _this$cachedTranslati[original];
|
|
77
79
|
if (typeof cachedTranslation === 'string') {
|
|
@@ -86,7 +88,8 @@ class TranslationHandler {
|
|
|
86
88
|
text: original,
|
|
87
89
|
deferred,
|
|
88
90
|
to,
|
|
89
|
-
from
|
|
91
|
+
from,
|
|
92
|
+
textType
|
|
90
93
|
});
|
|
91
94
|
void this.#throttledProcessTranslationQueue();
|
|
92
95
|
if (this.translationQueue.length >= _constants.MAX_ITEMS_PER_BATCH) {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"translationHandler.js","names":["_constants","require","_lodash","_interopRequireDefault","_deferred","_translation","e","__esModule","default","TranslationHandler","translationQueue","cachedTranslations","handleTranslation","batch","result","fetchTranslations","map","deferred","d","item","forEach","index","batchItem","from","to","text","resolve","ex","reject","processedTranslationQueue","#processedTranslationQueue","totalLength","length","shift","push","id","BATCH_SIZE_LIMIT","MAX_ITEMS_PER_BATCH","throttledProcessTranslationQueue","throttle","leading","translateText","original","_this$cachedTranslati","cachedTranslation","Promise","existingItem","find","promise","Deferred","flush","translationHandler","_default","exports"],"sources":["../../../src/utils/translationHandler.ts"],"sourcesContent":["import { QueuedItem, TranslationBatchItem } from '../types/translation';\nimport { BATCH_SIZE_LIMIT, MAX_ITEMS_PER_BATCH } from '../constants/constants';\nimport throttle from 'lodash.throttle';\nimport { Deferred } from './deferred';\nimport { fetchTranslations } from '../api/translation';\n\nclass TranslationHandler {\n translationQueue: QueuedItem[] = [];\n\n cachedTranslations: Record<string, Record<string, Record<string, string>>> = {};\n\n #handleTranslation = async (batch: TranslationBatchItem[]) => {\n try {\n const result = await fetchTranslations(batch.map(({ deferred: d, ...item }) => item));\n\n result.forEach((item, index) => {\n const batchItem = batch[index];\n\n if (!batchItem) {\n return;\n }\n\n const { from, to, text } = batchItem;\n\n batchItem.deferred.resolve(item);\n this.cachedTranslations[from] ??= {};\n this.cachedTranslations[from][to] ??= {};\n this.cachedTranslations[from][to][text] = item;\n });\n } catch (ex) {\n batch.forEach((item) => {\n item.deferred.reject(ex);\n });\n }\n };\n\n #processedTranslationQueue = async () => {\n let totalLength = 0;\n let batch: TranslationBatchItem[] = [];\n\n while (this.translationQueue.length) {\n const { text, deferred, to, from }
|
|
1
|
+
{"version":3,"file":"translationHandler.js","names":["_constants","require","_lodash","_interopRequireDefault","_deferred","_translation","e","__esModule","default","TranslationHandler","translationQueue","cachedTranslations","handleTranslation","batch","result","fetchTranslations","map","deferred","d","item","forEach","index","batchItem","from","to","text","resolve","ex","reject","processedTranslationQueue","#processedTranslationQueue","totalLength","length","textType","shift","push","id","BATCH_SIZE_LIMIT","MAX_ITEMS_PER_BATCH","throttledProcessTranslationQueue","throttle","leading","translateText","original","_this$cachedTranslati","cachedTranslation","Promise","existingItem","find","promise","Deferred","flush","translationHandler","_default","exports"],"sources":["../../../src/utils/translationHandler.ts"],"sourcesContent":["import { QueuedItem, TranslationBatchItem } from '../types/translation';\nimport { BATCH_SIZE_LIMIT, MAX_ITEMS_PER_BATCH } from '../constants/constants';\nimport throttle from 'lodash.throttle';\nimport { Deferred } from './deferred';\nimport { fetchTranslations } from '../api/translation';\n\nclass TranslationHandler {\n translationQueue: QueuedItem[] = [];\n\n cachedTranslations: Record<string, Record<string, Record<string, string>>> = {};\n\n #handleTranslation = async (batch: TranslationBatchItem[]) => {\n try {\n const result = await fetchTranslations(batch.map(({ deferred: d, ...item }) => item));\n\n result.forEach((item, index) => {\n const batchItem = batch[index];\n\n if (!batchItem) {\n return;\n }\n\n const { from, to, text } = batchItem;\n\n batchItem.deferred.resolve(item);\n this.cachedTranslations[from] ??= {};\n this.cachedTranslations[from][to] ??= {};\n this.cachedTranslations[from][to][text] = item;\n });\n } catch (ex) {\n batch.forEach((item) => {\n item.deferred.reject(ex);\n });\n }\n };\n\n #processedTranslationQueue = async () => {\n let totalLength = 0;\n let batch: TranslationBatchItem[] = [];\n\n while (this.translationQueue.length) {\n const { text, deferred, to, from, textType } =\n this.translationQueue.shift() as QueuedItem;\n totalLength += text.length;\n batch.push({\n text,\n to,\n from,\n id: batch.length,\n deferred,\n textType,\n });\n\n if (totalLength > BATCH_SIZE_LIMIT || batch.length >= MAX_ITEMS_PER_BATCH) {\n // eslint-disable-next-line no-await-in-loop\n await this.#handleTranslation(batch);\n batch = [];\n totalLength = 0;\n }\n }\n\n if (batch.length > 0) {\n await this.#handleTranslation(batch);\n }\n };\n\n #throttledProcessTranslationQueue = throttle(this.#processedTranslationQueue, 200, {\n leading: false,\n });\n\n translateText = (original: string, from: string, to: string, textType?: string) => {\n const cachedTranslation = this.cachedTranslations[from]?.[to]?.[original];\n if (typeof cachedTranslation === 'string') {\n return Promise.resolve(cachedTranslation);\n }\n\n const existingItem = this.translationQueue.find(\n (item) => item.text === original && item.to === to && item.from === from,\n );\n if (existingItem) {\n return existingItem.deferred.promise;\n }\n const deferred = new Deferred<string>();\n this.translationQueue.push({ text: original, deferred, to, from, textType });\n void this.#throttledProcessTranslationQueue();\n if (this.translationQueue.length >= MAX_ITEMS_PER_BATCH) {\n void this.#throttledProcessTranslationQueue.flush();\n }\n return deferred.promise;\n };\n}\n\nconst translationHandler = new TranslationHandler();\n\nexport default translationHandler;\n"],"mappings":"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","ignoreList":[]}
|
|
@@ -7,25 +7,37 @@ const AdaptiveTranslation = ({
|
|
|
7
7
|
from,
|
|
8
8
|
tagName: TagName = 'span',
|
|
9
9
|
style,
|
|
10
|
-
className
|
|
10
|
+
className,
|
|
11
|
+
textType,
|
|
12
|
+
text = ''
|
|
11
13
|
}) => {
|
|
12
14
|
const {
|
|
13
|
-
text,
|
|
15
|
+
text: translated,
|
|
14
16
|
isLoading,
|
|
15
17
|
isFetching
|
|
16
|
-
} = useAdaptiveTranslation(children, {
|
|
18
|
+
} = useAdaptiveTranslation(typeof children === 'function' ? text : children, {
|
|
17
19
|
from,
|
|
18
|
-
to
|
|
20
|
+
to,
|
|
21
|
+
textType
|
|
19
22
|
});
|
|
23
|
+
|
|
24
|
+
// eslint-disable-next-line no-nested-ternary
|
|
25
|
+
const opacity = isLoading ? 0 : isFetching ? 0.5 : 1;
|
|
20
26
|
return /*#__PURE__*/React.createElement(TagName, {
|
|
21
|
-
className: clsx('notranslate', className),
|
|
27
|
+
className: clsx('notranslate adaptive-translation', className),
|
|
22
28
|
style: {
|
|
23
|
-
// eslint-disable-next-line no-nested-ternary
|
|
24
|
-
opacity: isLoading ? 0 : isFetching ? 0.5 : 1,
|
|
25
29
|
transition: 'opacity 0.5s ease',
|
|
26
30
|
...style
|
|
27
31
|
}
|
|
28
|
-
},
|
|
32
|
+
}, typeof children === 'function' ? children(translated) : translated, /*#__PURE__*/React.createElement("style", null, `
|
|
33
|
+
.adaptive-translation > *:not(img) {
|
|
34
|
+
opacity: ${opacity};
|
|
35
|
+
transition: opacity 0.5s ease;
|
|
36
|
+
}
|
|
37
|
+
.adaptive-translation img {
|
|
38
|
+
opacity: 1 !important;
|
|
39
|
+
}
|
|
40
|
+
`));
|
|
29
41
|
};
|
|
30
42
|
export default AdaptiveTranslation;
|
|
31
43
|
//# sourceMappingURL=AdaptiveTranslation.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"AdaptiveTranslation.js","names":["React","clsx","useAdaptiveTranslation","AdaptiveTranslation","children","to","from","tagName","TagName","style","className","text","isLoading","isFetching","
|
|
1
|
+
{"version":3,"file":"AdaptiveTranslation.js","names":["React","clsx","useAdaptiveTranslation","AdaptiveTranslation","children","to","from","tagName","TagName","style","className","textType","text","translated","isLoading","isFetching","opacity","createElement","transition"],"sources":["../../../src/components/AdaptiveTranslation.tsx"],"sourcesContent":["import React, { CSSProperties, ReactNode } from 'react';\nimport clsx from 'clsx';\nimport { useAdaptiveTranslation } from '../hooks/useAdaptiveTranslation';\nimport { Language } from 'chayns-api';\n\ntype TranslationChildren = ((text: string) => ReactNode) | string;\n\ntype AdaptiveTranslationProps = {\n /**\n * The Text that should be translated.\n */\n children: TranslationChildren;\n /**\n * The className of the element.\n */\n className?: string;\n /**\n * The language from which the text should be translated.\n */\n from?: Exclude<Language, Language.Unknown>;\n /**\n * Optional styles of the HTML element.\n */\n style?: CSSProperties;\n /**\n * The HTML tag of the children.\n */\n tagName?: keyof HTMLElementTagNameMap;\n /**\n * The text that should be translated. Only active if the children is type of function.\n */\n text?: string;\n /**\n * The type of the text.\n */\n textType?: string;\n /**\n * The language to which the text should be translated.\n */\n to?: Exclude<Language, Language.Unknown>;\n};\n\nconst AdaptiveTranslation = ({\n children,\n to,\n from,\n tagName: TagName = 'span',\n style,\n className,\n textType,\n text = '',\n}: AdaptiveTranslationProps) => {\n const {\n text: translated,\n isLoading,\n isFetching,\n } = useAdaptiveTranslation(typeof children === 'function' ? text : children, {\n from,\n to,\n textType,\n });\n\n // eslint-disable-next-line no-nested-ternary\n const opacity = isLoading ? 0 : isFetching ? 0.5 : 1;\n\n return (\n <TagName\n className={clsx('notranslate adaptive-translation', className)}\n style={{\n transition: 'opacity 0.5s ease',\n ...style,\n }}\n >\n {typeof children === 'function' ? children(translated) : translated}\n\n <style>\n {`\n .adaptive-translation > *:not(img) {\n opacity: ${opacity};\n transition: opacity 0.5s ease;\n }\n .adaptive-translation img {\n opacity: 1 !important;\n }\n `}\n </style>\n </TagName>\n );\n};\nexport default AdaptiveTranslation;\n"],"mappings":"AAAC,OAAOA,KAAK,MAAoC,OAAO;AACxD,OAAOC,IAAI,MAAM,MAAM;AACvB,SAASC,sBAAsB,QAAQ,iCAAiC;AAwCxE,MAAMC,mBAAmB,GAAGA,CAAC;EACzBC,QAAQ;EACRC,EAAE;EACFC,IAAI;EACJC,OAAO,EAAEC,OAAO,GAAG,MAAM;EACzBC,KAAK;EACLC,SAAS;EACTC,QAAQ;EACRC,IAAI,GAAG;AACe,CAAC,KAAK;EAC5B,MAAM;IACFA,IAAI,EAAEC,UAAU;IAChBC,SAAS;IACTC;EACJ,CAAC,GAAGb,sBAAsB,CAAC,OAAOE,QAAQ,KAAK,UAAU,GAAGQ,IAAI,GAAGR,QAAQ,EAAE;IACzEE,IAAI;IACJD,EAAE;IACFM;EACJ,CAAC,CAAC;;EAEF;EACA,MAAMK,OAAO,GAAGF,SAAS,GAAG,CAAC,GAAGC,UAAU,GAAG,GAAG,GAAG,CAAC;EAEpD,oBACIf,KAAA,CAAAiB,aAAA,CAACT,OAAO;IACJE,SAAS,EAAET,IAAI,CAAC,kCAAkC,EAAES,SAAS,CAAE;IAC/DD,KAAK,EAAE;MACHS,UAAU,EAAE,mBAAmB;MAC/B,GAAGT;IACP;EAAE,GAED,OAAOL,QAAQ,KAAK,UAAU,GAAGA,QAAQ,CAACS,UAAU,CAAC,GAAGA,UAAU,eAEnEb,KAAA,CAAAiB,aAAA,gBACK;AACjB;AACA,mCAAmCD,OAAO;AAC1C;AACA;AACA;AACA;AACA;AACA,iBACmB,CACF,CAAC;AAElB,CAAC;AACD,eAAeb,mBAAmB","ignoreList":[]}
|
|
@@ -3,12 +3,13 @@ import { TranslationOptionsContext } from '../constants/translationOptionsContex
|
|
|
3
3
|
import translationHandler from '../utils/translationHandler';
|
|
4
4
|
export const useAdaptiveTranslation = (originalText, {
|
|
5
5
|
to,
|
|
6
|
-
from
|
|
6
|
+
from,
|
|
7
|
+
textType
|
|
7
8
|
} = {}) => {
|
|
8
9
|
const options = useContext(TranslationOptionsContext);
|
|
9
10
|
const toLanguage = to || options.to;
|
|
10
11
|
const fromLanguage = from || options.from;
|
|
11
|
-
const shouldTranslate = useMemo(() => toLanguage !== fromLanguage, [fromLanguage, toLanguage]);
|
|
12
|
+
const shouldTranslate = useMemo(() => toLanguage !== fromLanguage && originalText.length !== 0, [fromLanguage, originalText.length, toLanguage]);
|
|
12
13
|
const [translatedText, setTranslatedText] = useState(originalText);
|
|
13
14
|
const [isLoading, setIsLoading] = useState(shouldTranslate);
|
|
14
15
|
const [isFetching, setIsFetching] = useState(false);
|
|
@@ -16,7 +17,7 @@ export const useAdaptiveTranslation = (originalText, {
|
|
|
16
17
|
const timeoutRef = setTimeout(() => {
|
|
17
18
|
if (shouldTranslate) {
|
|
18
19
|
setIsFetching(true);
|
|
19
|
-
void translationHandler.translateText(originalText, fromLanguage, toLanguage).then(text => {
|
|
20
|
+
void translationHandler.translateText(originalText, fromLanguage, toLanguage, textType).then(text => {
|
|
20
21
|
setTranslatedText(text);
|
|
21
22
|
}).finally(() => {
|
|
22
23
|
setIsLoading(false);
|
|
@@ -25,7 +26,7 @@ export const useAdaptiveTranslation = (originalText, {
|
|
|
25
26
|
}
|
|
26
27
|
}, 200);
|
|
27
28
|
return () => clearTimeout(timeoutRef);
|
|
28
|
-
}, [originalText, shouldTranslate, toLanguage, fromLanguage]);
|
|
29
|
+
}, [originalText, shouldTranslate, toLanguage, fromLanguage, textType]);
|
|
29
30
|
return useMemo(() => ({
|
|
30
31
|
text: shouldTranslate ? translatedText : originalText,
|
|
31
32
|
isFetching: shouldTranslate ? isFetching : false,
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"useAdaptiveTranslation.js","names":["useContext","useEffect","useMemo","useState","TranslationOptionsContext","translationHandler","useAdaptiveTranslation","originalText","to","from","options","toLanguage","fromLanguage","shouldTranslate","translatedText","setTranslatedText","isLoading","setIsLoading","isFetching","setIsFetching","timeoutRef","setTimeout","translateText","then","text","finally","clearTimeout"],"sources":["../../../src/hooks/useAdaptiveTranslation.ts"],"sourcesContent":["import { useContext, useEffect, useMemo, useState } from 'react';\nimport { Language } from 'chayns-api';\nimport { TranslationOptionsContext } from '../constants/translationOptionsContext';\nimport translationHandler from '../utils/translationHandler';\n\ninterface UseAdaptiveTranslationOptions {\n /**\n * The language from which the text should be translated.\n */\n from?: Exclude<Language, Language.Unknown>;\n /**\n * The language to which the text should be translated.\n */\n to?: Exclude<Language, Language.Unknown>;\n}\n\nexport const useAdaptiveTranslation = (\n originalText: string,\n { to, from }: UseAdaptiveTranslationOptions = {},\n): { text: string; isLoading: boolean; isFetching: boolean } => {\n const options = useContext(TranslationOptionsContext);\n const toLanguage = to || options.to;\n const fromLanguage = from || options.from;\n const shouldTranslate = useMemo(() => toLanguage !== fromLanguage
|
|
1
|
+
{"version":3,"file":"useAdaptiveTranslation.js","names":["useContext","useEffect","useMemo","useState","TranslationOptionsContext","translationHandler","useAdaptiveTranslation","originalText","to","from","textType","options","toLanguage","fromLanguage","shouldTranslate","length","translatedText","setTranslatedText","isLoading","setIsLoading","isFetching","setIsFetching","timeoutRef","setTimeout","translateText","then","text","finally","clearTimeout"],"sources":["../../../src/hooks/useAdaptiveTranslation.ts"],"sourcesContent":["import { useContext, useEffect, useMemo, useState } from 'react';\nimport { Language } from 'chayns-api';\nimport { TranslationOptionsContext } from '../constants/translationOptionsContext';\nimport translationHandler from '../utils/translationHandler';\n\ninterface UseAdaptiveTranslationOptions {\n /**\n * The language from which the text should be translated.\n */\n from?: Exclude<Language, Language.Unknown>;\n /**\n * The type of the text.\n */\n textType?: string;\n /**\n * The language to which the text should be translated.\n */\n to?: Exclude<Language, Language.Unknown>;\n}\n\nexport const useAdaptiveTranslation = (\n originalText: string,\n { to, from, textType }: UseAdaptiveTranslationOptions = {},\n): { text: string; isLoading: boolean; isFetching: boolean } => {\n const options = useContext(TranslationOptionsContext);\n const toLanguage = to || options.to;\n const fromLanguage = from || options.from;\n const shouldTranslate = useMemo(\n () => toLanguage !== fromLanguage && originalText.length !== 0,\n [fromLanguage, originalText.length, toLanguage],\n );\n const [translatedText, setTranslatedText] = useState<string>(originalText);\n const [isLoading, setIsLoading] = useState(shouldTranslate);\n const [isFetching, setIsFetching] = useState(false);\n\n useEffect(() => {\n const timeoutRef = setTimeout(() => {\n if (shouldTranslate) {\n setIsFetching(true);\n void translationHandler\n .translateText(originalText, fromLanguage, toLanguage, textType)\n .then((text) => {\n setTranslatedText(text);\n })\n .finally(() => {\n setIsLoading(false);\n setIsFetching(false);\n });\n }\n }, 200);\n\n return () => clearTimeout(timeoutRef);\n }, [originalText, shouldTranslate, toLanguage, fromLanguage, textType]);\n\n return useMemo(\n () => ({\n text: shouldTranslate ? translatedText : originalText,\n isFetching: shouldTranslate ? isFetching : false,\n isLoading: shouldTranslate ? isLoading : false,\n }),\n [isFetching, isLoading, originalText, shouldTranslate, translatedText],\n );\n};\n"],"mappings":"AAAC,SAASA,UAAU,EAAEC,SAAS,EAAEC,OAAO,EAAEC,QAAQ,QAAQ,OAAO;AAEjE,SAASC,yBAAyB,QAAQ,wCAAwC;AAClF,OAAOC,kBAAkB,MAAM,6BAA6B;AAiB5D,OAAO,MAAMC,sBAAsB,GAAGA,CAClCC,YAAoB,EACpB;EAAEC,EAAE;EAAEC,IAAI;EAAEC;AAAwC,CAAC,GAAG,CAAC,CAAC,KACE;EAC5D,MAAMC,OAAO,GAAGX,UAAU,CAACI,yBAAyB,CAAC;EACrD,MAAMQ,UAAU,GAAGJ,EAAE,IAAIG,OAAO,CAACH,EAAE;EACnC,MAAMK,YAAY,GAAGJ,IAAI,IAAIE,OAAO,CAACF,IAAI;EACzC,MAAMK,eAAe,GAAGZ,OAAO,CAC3B,MAAMU,UAAU,KAAKC,YAAY,IAAIN,YAAY,CAACQ,MAAM,KAAK,CAAC,EAC9D,CAACF,YAAY,EAAEN,YAAY,CAACQ,MAAM,EAAEH,UAAU,CAClD,CAAC;EACD,MAAM,CAACI,cAAc,EAAEC,iBAAiB,CAAC,GAAGd,QAAQ,CAASI,YAAY,CAAC;EAC1E,MAAM,CAACW,SAAS,EAAEC,YAAY,CAAC,GAAGhB,QAAQ,CAACW,eAAe,CAAC;EAC3D,MAAM,CAACM,UAAU,EAAEC,aAAa,CAAC,GAAGlB,QAAQ,CAAC,KAAK,CAAC;EAEnDF,SAAS,CAAC,MAAM;IACZ,MAAMqB,UAAU,GAAGC,UAAU,CAAC,MAAM;MAChC,IAAIT,eAAe,EAAE;QACjBO,aAAa,CAAC,IAAI,CAAC;QACnB,KAAKhB,kBAAkB,CAClBmB,aAAa,CAACjB,YAAY,EAAEM,YAAY,EAAED,UAAU,EAAEF,QAAQ,CAAC,CAC/De,IAAI,CAAEC,IAAI,IAAK;UACZT,iBAAiB,CAACS,IAAI,CAAC;QAC3B,CAAC,CAAC,CACDC,OAAO,CAAC,MAAM;UACXR,YAAY,CAAC,KAAK,CAAC;UACnBE,aAAa,CAAC,KAAK,CAAC;QACxB,CAAC,CAAC;MACV;IACJ,CAAC,EAAE,GAAG,CAAC;IAEP,OAAO,MAAMO,YAAY,CAACN,UAAU,CAAC;EACzC,CAAC,EAAE,CAACf,YAAY,EAAEO,eAAe,EAAEF,UAAU,EAAEC,YAAY,EAAEH,QAAQ,CAAC,CAAC;EAEvE,OAAOR,OAAO,CACV,OAAO;IACHwB,IAAI,EAAEZ,eAAe,GAAGE,cAAc,GAAGT,YAAY;IACrDa,UAAU,EAAEN,eAAe,GAAGM,UAAU,GAAG,KAAK;IAChDF,SAAS,EAAEJ,eAAe,GAAGI,SAAS,GAAG;EAC7C,CAAC,CAAC,EACF,CAACE,UAAU,EAAEF,SAAS,EAAEX,YAAY,EAAEO,eAAe,EAAEE,cAAc,CACzE,CAAC;AACL,CAAC","ignoreList":[]}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"translation.js","names":[],"sources":["../../../src/types/translation.ts"],"sourcesContent":["import { Deferred } from '../utils/deferred';\n\ninterface BaseTranslation {\n text: string;\n to: string;\n from: string;\n}\n\nexport interface QueuedItem extends BaseTranslation {\n deferred: Deferred<string>;\n}\n\nexport interface TranslationBatchItem extends TranslationRequest {\n deferred: Deferred<string>;\n}\n\nexport interface TranslationRequest extends BaseTranslation {\n id: number;\n}\n"],"mappings":"","ignoreList":[]}
|
|
1
|
+
{"version":3,"file":"translation.js","names":[],"sources":["../../../src/types/translation.ts"],"sourcesContent":["import { Deferred } from '../utils/deferred';\n\ninterface BaseTranslation {\n text: string;\n to: string;\n from: string;\n textType?: string;\n}\n\nexport interface QueuedItem extends BaseTranslation {\n deferred: Deferred<string>;\n}\n\nexport interface TranslationBatchItem extends TranslationRequest {\n deferred: Deferred<string>;\n}\n\nexport interface TranslationRequest extends BaseTranslation {\n id: number;\n}\n"],"mappings":"","ignoreList":[]}
|
|
@@ -40,7 +40,8 @@ class TranslationHandler {
|
|
|
40
40
|
text,
|
|
41
41
|
deferred,
|
|
42
42
|
to,
|
|
43
|
-
from
|
|
43
|
+
from,
|
|
44
|
+
textType
|
|
44
45
|
} = this.translationQueue.shift();
|
|
45
46
|
totalLength += text.length;
|
|
46
47
|
batch.push({
|
|
@@ -48,7 +49,8 @@ class TranslationHandler {
|
|
|
48
49
|
to,
|
|
49
50
|
from,
|
|
50
51
|
id: batch.length,
|
|
51
|
-
deferred
|
|
52
|
+
deferred,
|
|
53
|
+
textType
|
|
52
54
|
});
|
|
53
55
|
if (totalLength > BATCH_SIZE_LIMIT || batch.length >= MAX_ITEMS_PER_BATCH) {
|
|
54
56
|
// eslint-disable-next-line no-await-in-loop
|
|
@@ -64,7 +66,7 @@ class TranslationHandler {
|
|
|
64
66
|
#throttledProcessTranslationQueue = throttle(this.#processedTranslationQueue, 200, {
|
|
65
67
|
leading: false
|
|
66
68
|
});
|
|
67
|
-
translateText = (original, from, to) => {
|
|
69
|
+
translateText = (original, from, to, textType) => {
|
|
68
70
|
const cachedTranslation = this.cachedTranslations[from]?.[to]?.[original];
|
|
69
71
|
if (typeof cachedTranslation === 'string') {
|
|
70
72
|
return Promise.resolve(cachedTranslation);
|
|
@@ -78,7 +80,8 @@ class TranslationHandler {
|
|
|
78
80
|
text: original,
|
|
79
81
|
deferred,
|
|
80
82
|
to,
|
|
81
|
-
from
|
|
83
|
+
from,
|
|
84
|
+
textType
|
|
82
85
|
});
|
|
83
86
|
void this.#throttledProcessTranslationQueue();
|
|
84
87
|
if (this.translationQueue.length >= MAX_ITEMS_PER_BATCH) {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"translationHandler.js","names":["BATCH_SIZE_LIMIT","MAX_ITEMS_PER_BATCH","throttle","Deferred","fetchTranslations","TranslationHandler","translationQueue","cachedTranslations","handleTranslation","batch","result","map","deferred","d","item","forEach","index","batchItem","from","to","text","resolve","ex","reject","processedTranslationQueue","#processedTranslationQueue","totalLength","length","shift","push","id","throttledProcessTranslationQueue","leading","translateText","original","cachedTranslation","Promise","existingItem","find","promise","flush","translationHandler"],"sources":["../../../src/utils/translationHandler.ts"],"sourcesContent":["import { QueuedItem, TranslationBatchItem } from '../types/translation';\nimport { BATCH_SIZE_LIMIT, MAX_ITEMS_PER_BATCH } from '../constants/constants';\nimport throttle from 'lodash.throttle';\nimport { Deferred } from './deferred';\nimport { fetchTranslations } from '../api/translation';\n\nclass TranslationHandler {\n translationQueue: QueuedItem[] = [];\n\n cachedTranslations: Record<string, Record<string, Record<string, string>>> = {};\n\n #handleTranslation = async (batch: TranslationBatchItem[]) => {\n try {\n const result = await fetchTranslations(batch.map(({ deferred: d, ...item }) => item));\n\n result.forEach((item, index) => {\n const batchItem = batch[index];\n\n if (!batchItem) {\n return;\n }\n\n const { from, to, text } = batchItem;\n\n batchItem.deferred.resolve(item);\n this.cachedTranslations[from] ??= {};\n this.cachedTranslations[from][to] ??= {};\n this.cachedTranslations[from][to][text] = item;\n });\n } catch (ex) {\n batch.forEach((item) => {\n item.deferred.reject(ex);\n });\n }\n };\n\n #processedTranslationQueue = async () => {\n let totalLength = 0;\n let batch: TranslationBatchItem[] = [];\n\n while (this.translationQueue.length) {\n const { text, deferred, to, from }
|
|
1
|
+
{"version":3,"file":"translationHandler.js","names":["BATCH_SIZE_LIMIT","MAX_ITEMS_PER_BATCH","throttle","Deferred","fetchTranslations","TranslationHandler","translationQueue","cachedTranslations","handleTranslation","batch","result","map","deferred","d","item","forEach","index","batchItem","from","to","text","resolve","ex","reject","processedTranslationQueue","#processedTranslationQueue","totalLength","length","textType","shift","push","id","throttledProcessTranslationQueue","leading","translateText","original","cachedTranslation","Promise","existingItem","find","promise","flush","translationHandler"],"sources":["../../../src/utils/translationHandler.ts"],"sourcesContent":["import { QueuedItem, TranslationBatchItem } from '../types/translation';\nimport { BATCH_SIZE_LIMIT, MAX_ITEMS_PER_BATCH } from '../constants/constants';\nimport throttle from 'lodash.throttle';\nimport { Deferred } from './deferred';\nimport { fetchTranslations } from '../api/translation';\n\nclass TranslationHandler {\n translationQueue: QueuedItem[] = [];\n\n cachedTranslations: Record<string, Record<string, Record<string, string>>> = {};\n\n #handleTranslation = async (batch: TranslationBatchItem[]) => {\n try {\n const result = await fetchTranslations(batch.map(({ deferred: d, ...item }) => item));\n\n result.forEach((item, index) => {\n const batchItem = batch[index];\n\n if (!batchItem) {\n return;\n }\n\n const { from, to, text } = batchItem;\n\n batchItem.deferred.resolve(item);\n this.cachedTranslations[from] ??= {};\n this.cachedTranslations[from][to] ??= {};\n this.cachedTranslations[from][to][text] = item;\n });\n } catch (ex) {\n batch.forEach((item) => {\n item.deferred.reject(ex);\n });\n }\n };\n\n #processedTranslationQueue = async () => {\n let totalLength = 0;\n let batch: TranslationBatchItem[] = [];\n\n while (this.translationQueue.length) {\n const { text, deferred, to, from, textType } =\n this.translationQueue.shift() as QueuedItem;\n totalLength += text.length;\n batch.push({\n text,\n to,\n from,\n id: batch.length,\n deferred,\n textType,\n });\n\n if (totalLength > BATCH_SIZE_LIMIT || batch.length >= MAX_ITEMS_PER_BATCH) {\n // eslint-disable-next-line no-await-in-loop\n await this.#handleTranslation(batch);\n batch = [];\n totalLength = 0;\n }\n }\n\n if (batch.length > 0) {\n await this.#handleTranslation(batch);\n }\n };\n\n #throttledProcessTranslationQueue = throttle(this.#processedTranslationQueue, 200, {\n leading: false,\n });\n\n translateText = (original: string, from: string, to: string, textType?: string) => {\n const cachedTranslation = this.cachedTranslations[from]?.[to]?.[original];\n if (typeof cachedTranslation === 'string') {\n return Promise.resolve(cachedTranslation);\n }\n\n const existingItem = this.translationQueue.find(\n (item) => item.text === original && item.to === to && item.from === from,\n );\n if (existingItem) {\n return existingItem.deferred.promise;\n }\n const deferred = new Deferred<string>();\n this.translationQueue.push({ text: original, deferred, to, from, textType });\n void this.#throttledProcessTranslationQueue();\n if (this.translationQueue.length >= MAX_ITEMS_PER_BATCH) {\n void this.#throttledProcessTranslationQueue.flush();\n }\n return deferred.promise;\n };\n}\n\nconst translationHandler = new TranslationHandler();\n\nexport default translationHandler;\n"],"mappings":"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","ignoreList":[]}
|
|
@@ -1,10 +1,11 @@
|
|
|
1
|
-
import React, { CSSProperties } from 'react';
|
|
1
|
+
import React, { CSSProperties, ReactNode } from 'react';
|
|
2
2
|
import { Language } from 'chayns-api';
|
|
3
|
+
type TranslationChildren = ((text: string) => ReactNode) | string;
|
|
3
4
|
type AdaptiveTranslationProps = {
|
|
4
5
|
/**
|
|
5
6
|
* The Text that should be translated.
|
|
6
7
|
*/
|
|
7
|
-
children:
|
|
8
|
+
children: TranslationChildren;
|
|
8
9
|
/**
|
|
9
10
|
* The className of the element.
|
|
10
11
|
*/
|
|
@@ -21,10 +22,18 @@ type AdaptiveTranslationProps = {
|
|
|
21
22
|
* The HTML tag of the children.
|
|
22
23
|
*/
|
|
23
24
|
tagName?: keyof HTMLElementTagNameMap;
|
|
25
|
+
/**
|
|
26
|
+
* The text that should be translated. Only active if the children is type of function.
|
|
27
|
+
*/
|
|
28
|
+
text?: string;
|
|
29
|
+
/**
|
|
30
|
+
* The type of the text.
|
|
31
|
+
*/
|
|
32
|
+
textType?: string;
|
|
24
33
|
/**
|
|
25
34
|
* The language to which the text should be translated.
|
|
26
35
|
*/
|
|
27
36
|
to?: Exclude<Language, Language.Unknown>;
|
|
28
37
|
};
|
|
29
|
-
declare const AdaptiveTranslation: ({ children, to, from, tagName: TagName, style, className, }: AdaptiveTranslationProps) => React.JSX.Element;
|
|
38
|
+
declare const AdaptiveTranslation: ({ children, to, from, tagName: TagName, style, className, textType, text, }: AdaptiveTranslationProps) => React.JSX.Element;
|
|
30
39
|
export default AdaptiveTranslation;
|
|
@@ -4,12 +4,16 @@ interface UseAdaptiveTranslationOptions {
|
|
|
4
4
|
* The language from which the text should be translated.
|
|
5
5
|
*/
|
|
6
6
|
from?: Exclude<Language, Language.Unknown>;
|
|
7
|
+
/**
|
|
8
|
+
* The type of the text.
|
|
9
|
+
*/
|
|
10
|
+
textType?: string;
|
|
7
11
|
/**
|
|
8
12
|
* The language to which the text should be translated.
|
|
9
13
|
*/
|
|
10
14
|
to?: Exclude<Language, Language.Unknown>;
|
|
11
15
|
}
|
|
12
|
-
export declare const useAdaptiveTranslation: (originalText: string, { to, from }?: UseAdaptiveTranslationOptions) => {
|
|
16
|
+
export declare const useAdaptiveTranslation: (originalText: string, { to, from, textType }?: UseAdaptiveTranslationOptions) => {
|
|
13
17
|
text: string;
|
|
14
18
|
isLoading: boolean;
|
|
15
19
|
isFetching: boolean;
|
|
@@ -3,7 +3,7 @@ declare class TranslationHandler {
|
|
|
3
3
|
#private;
|
|
4
4
|
translationQueue: QueuedItem[];
|
|
5
5
|
cachedTranslations: Record<string, Record<string, Record<string, string>>>;
|
|
6
|
-
translateText: (original: string, from: string, to: string) => Promise<string>;
|
|
6
|
+
translateText: (original: string, from: string, to: string, textType?: string) => Promise<string>;
|
|
7
7
|
}
|
|
8
8
|
declare const translationHandler: TranslationHandler;
|
|
9
9
|
export default translationHandler;
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@chayns-components/translation",
|
|
3
|
-
"version": "5.0.0-beta.
|
|
3
|
+
"version": "5.0.0-beta.1271",
|
|
4
4
|
"description": "A set of beautiful React components for developing your own applications with chayns.",
|
|
5
5
|
"sideEffects": false,
|
|
6
6
|
"browserslist": [
|
|
@@ -79,5 +79,5 @@
|
|
|
79
79
|
"publishConfig": {
|
|
80
80
|
"access": "public"
|
|
81
81
|
},
|
|
82
|
-
"gitHead": "
|
|
82
|
+
"gitHead": "c9ad0a1eb627e67c0f134817996aacd09ec03cae"
|
|
83
83
|
}
|