@sv443-network/userutils 7.2.1 → 7.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/CHANGELOG.md CHANGED
@@ -1,5 +1,18 @@
1
1
  # @sv443-network/userutils
2
2
 
3
+ ## 7.3.0
4
+
5
+ ### Minor Changes
6
+
7
+ - 7e8e147: - Added `tr.forLang()` to get the translation for a specified language code
8
+ - Added `tr.getTranslations()` to return the translations object for the given or currently active language
9
+
10
+ ## 7.2.2
11
+
12
+ ### Patch Changes
13
+
14
+ - a171b0d: Fix color functions not being exported 🥴
15
+
3
16
  ## 7.2.1
4
17
 
5
18
  ### Patch Changes
package/README.md CHANGED
@@ -4,7 +4,7 @@
4
4
  ## UserUtils
5
5
  Lightweight library with various utilities for userscripts - register listeners for when CSS selectors exist, intercept events, create persistent & synchronous data stores, modify the DOM more easily and more.
6
6
 
7
- Contains builtin TypeScript declarations. Supports ESM and CJS imports via a bundler and UMD / global declaration via `@require`.
7
+ Contains builtin TypeScript declarations. Supports ESM and CJS imports via a bundler and global declaration via `@require`
8
8
  If you like using this library, please consider [supporting the development ❤️](https://github.com/sponsors/Sv443)
9
9
 
10
10
  <br>
@@ -63,9 +63,11 @@ View the documentation of previous major releases:
63
63
  - [`randomizeArray()`](#randomizearray) - returns a copy of the array with its items in a random order
64
64
  - [**Translation:**](#translation)
65
65
  - [`tr()`](#tr) - simple translation of a string to another language
66
+ - [`tr.forLang()`](#trforlang) - specify a language besides the currently set one for the translation
66
67
  - [`tr.addLanguage()`](#traddlanguage) - add a language and its translations
67
68
  - [`tr.setLanguage()`](#trsetlanguage) - set the currently active language for translations
68
69
  - [`tr.getLanguage()`](#trgetlanguage) - returns the currently active language
70
+ - [`tr.getTranslations()`](#trgettranslations) - returns the translations for the given language or the currently active one
69
71
  - [**Colors:**](#colors)
70
72
  - [`hexToRgb()`](#hextorgb) - convert a hex color string to an RGB number tuple
71
73
  - [`rgbToHex()`](#rgbtohex) - convert RGB numbers to a hex color string
@@ -1960,6 +1962,39 @@ console.log(tr("welcome_name", "John")); // "Willkommen, John"
1960
1962
 
1961
1963
  <br>
1962
1964
 
1965
+ ### tr.forLang()
1966
+ Usage:
1967
+ ```ts
1968
+ tr.forLang(language: string, key: string, ...values: Stringifiable[]): string
1969
+ ```
1970
+
1971
+ Returns the translation of the passed key in the specified language. Otherwise behaves exactly like [`tr()`](#tr)
1972
+ This function does not change the currently active language set by [`tr.setLanguage()`](#trsetlanguage)
1973
+
1974
+ <details><summary><b>Example - click to view</b></summary>
1975
+
1976
+ ```ts
1977
+ import { tr } from "@sv443-network/userutils";
1978
+
1979
+ tr.addLanguage("en", {
1980
+ "welcome_name": "Welcome, %1",
1981
+ });
1982
+
1983
+ tr.addLanguage("de", {
1984
+ "welcome_name": "Willkommen, %1",
1985
+ });
1986
+
1987
+ // the language is set to "en"
1988
+ tr.setLanguage("en");
1989
+
1990
+ console.log(tr("welcome_name", "John")); // "Welcome"
1991
+ // the language doesn't need to be changed:
1992
+ console.log(tr.forLang("de", "welcome_name", "John")); // "Willkommen, John"
1993
+ ```
1994
+ </details>
1995
+
1996
+ <br>
1997
+
1963
1998
  ### tr.addLanguage()
1964
1999
  Usage:
1965
2000
  ```ts
@@ -2080,6 +2115,37 @@ tr.getLanguage(): string | undefined
2080
2115
  Returns the currently active language set by [`tr.setLanguage()`](#trsetlanguage)
2081
2116
  If no language has been set yet, it will return undefined.
2082
2117
 
2118
+ <br>
2119
+
2120
+ ### tr.getTranslations()
2121
+ Usage:
2122
+ ```ts
2123
+ tr.getTranslations(language?: string): Record<string, string> | undefined
2124
+ ```
2125
+
2126
+ Returns the translations of the specified language.
2127
+ If no language is specified, it will return the translations of the currently active language set by [`tr.setLanguage()`](#trsetlanguage)
2128
+ If no translations are found, it will return undefined.
2129
+
2130
+ <details><summary><b>Example - click to view</b></summary>
2131
+
2132
+ ```ts
2133
+ import { tr } from "@sv443-network/userutils";
2134
+
2135
+ tr.addLanguage("en", {
2136
+ "welcome": "Welcome",
2137
+ });
2138
+
2139
+ console.log(tr.getTranslations()); // undefined
2140
+ tr.setLanguage("en");
2141
+ console.log(tr.getTranslations()); // { "welcome": "Welcome" }
2142
+
2143
+ console.log(tr.getTranslations("en")); // { "welcome": "Welcome" }
2144
+
2145
+ console.log(tr.getTranslations("de")); // undefined
2146
+ ```
2147
+ </details>
2148
+
2083
2149
  <br><br>
2084
2150
 
2085
2151
  ## Colors:
@@ -8,7 +8,7 @@
8
8
  // ==UserLibrary==
9
9
  // @name UserUtils
10
10
  // @description Library with various utilities for userscripts - register listeners for when CSS selectors exist, intercept events, create persistent & synchronous data stores, modify the DOM more easily and more
11
- // @version 7.2.1
11
+ // @version 7.3.0
12
12
  // @license MIT
13
13
  // @copyright Sv443 (https://github.com/Sv443)
14
14
 
@@ -128,6 +128,55 @@ var UserUtils = (function (exports) {
128
128
  return retArray;
129
129
  }
130
130
 
131
+ // lib/colors.ts
132
+ function hexToRgb(hex) {
133
+ hex = hex.trim();
134
+ const bigint = parseInt(hex.startsWith("#") ? hex.slice(1) : hex, 16);
135
+ const r = bigint >> 16 & 255;
136
+ const g = bigint >> 8 & 255;
137
+ const b = bigint & 255;
138
+ return [clamp(r, 0, 255), clamp(g, 0, 255), clamp(b, 0, 255)];
139
+ }
140
+ function rgbToHex(red, green, blue, withHash = true, upperCase = false) {
141
+ const toHexVal = (n) => clamp(Math.round(n), 0, 255).toString(16).padStart(2, "0")[upperCase ? "toUpperCase" : "toLowerCase"]();
142
+ return `${withHash ? "#" : ""}${toHexVal(red)}${toHexVal(green)}${toHexVal(blue)}`;
143
+ }
144
+ function lightenColor(color, percent) {
145
+ return darkenColor(color, percent * -1);
146
+ }
147
+ function darkenColor(color, percent) {
148
+ var _a;
149
+ color = color.trim();
150
+ const darkenRgb = (r2, g2, b2, percent2) => {
151
+ r2 = Math.max(0, Math.min(255, r2 - r2 * percent2 / 100));
152
+ g2 = Math.max(0, Math.min(255, g2 - g2 * percent2 / 100));
153
+ b2 = Math.max(0, Math.min(255, b2 - b2 * percent2 / 100));
154
+ return [r2, g2, b2];
155
+ };
156
+ let r, g, b, a;
157
+ const isHexCol = color.match(/^#?([0-9A-Fa-f]{3}|[0-9A-Fa-f]{6})$/);
158
+ if (isHexCol)
159
+ [r, g, b] = hexToRgb(color);
160
+ else if (color.startsWith("rgb")) {
161
+ const rgbValues = (_a = color.match(/\d+(\.\d+)?/g)) == null ? void 0 : _a.map(Number);
162
+ if (rgbValues)
163
+ [r, g, b, a] = rgbValues;
164
+ else
165
+ throw new Error("Invalid RGB/RGBA color format");
166
+ } else
167
+ throw new Error("Unsupported color format");
168
+ [r, g, b] = darkenRgb(r, g, b, percent);
169
+ const upperCase = color.match(/[A-F]/) !== null;
170
+ if (isHexCol)
171
+ return rgbToHex(r, g, b, color.startsWith("#"), upperCase);
172
+ else if (color.startsWith("rgba"))
173
+ return `rgba(${r}, ${g}, ${b}, ${a})`;
174
+ else if (color.startsWith("rgb"))
175
+ return `rgb(${r}, ${g}, ${b})`;
176
+ else
177
+ throw new Error("Unsupported color format");
178
+ }
179
+
131
180
  // lib/dom.ts
132
181
  function getUnsafeWindow() {
133
182
  try {
@@ -1343,18 +1392,22 @@ Has: ${checksum}`);
1343
1392
  // lib/translation.ts
1344
1393
  var trans = {};
1345
1394
  var curLang;
1346
- function tr(key, ...args) {
1395
+ var trLang = (language, key, ...args) => {
1347
1396
  var _a;
1348
- if (!curLang)
1397
+ if (!language)
1349
1398
  return key;
1350
- const trText = (_a = trans[curLang]) == null ? void 0 : _a[key];
1399
+ const trText = (_a = trans[language]) == null ? void 0 : _a[key];
1351
1400
  if (!trText)
1352
1401
  return key;
1353
1402
  if (args.length > 0 && trText.match(/%\d/)) {
1354
1403
  return insertValues(trText, ...args);
1355
1404
  }
1356
1405
  return trText;
1406
+ };
1407
+ function tr(key, ...args) {
1408
+ return trLang(curLang, key, ...args);
1357
1409
  }
1410
+ tr.forLang = trLang;
1358
1411
  tr.addLanguage = (language, translations) => {
1359
1412
  trans[language] = translations;
1360
1413
  };
@@ -1364,6 +1417,9 @@ Has: ${checksum}`);
1364
1417
  tr.getLanguage = () => {
1365
1418
  return curLang;
1366
1419
  };
1420
+ tr.getTranslations = (language) => {
1421
+ return trans[language != null ? language : curLang];
1422
+ };
1367
1423
 
1368
1424
  exports.DataStore = DataStore;
1369
1425
  exports.DataStoreSerializer = DataStoreSerializer;
@@ -1376,6 +1432,7 @@ Has: ${checksum}`);
1376
1432
  exports.clamp = clamp;
1377
1433
  exports.compress = compress;
1378
1434
  exports.computeHash = computeHash;
1435
+ exports.darkenColor = darkenColor;
1379
1436
  exports.debounce = debounce;
1380
1437
  exports.decompress = decompress;
1381
1438
  exports.defaultDialogCss = defaultDialogCss;
@@ -1383,10 +1440,12 @@ Has: ${checksum}`);
1383
1440
  exports.fetchAdvanced = fetchAdvanced;
1384
1441
  exports.getSiblingsFrame = getSiblingsFrame;
1385
1442
  exports.getUnsafeWindow = getUnsafeWindow;
1443
+ exports.hexToRgb = hexToRgb;
1386
1444
  exports.insertValues = insertValues;
1387
1445
  exports.interceptEvent = interceptEvent;
1388
1446
  exports.interceptWindowEvent = interceptWindowEvent;
1389
1447
  exports.isScrollable = isScrollable;
1448
+ exports.lightenColor = lightenColor;
1390
1449
  exports.mapRange = mapRange;
1391
1450
  exports.observeElementProp = observeElementProp;
1392
1451
  exports.openDialogs = openDialogs;
@@ -1398,6 +1457,7 @@ Has: ${checksum}`);
1398
1457
  exports.randomItem = randomItem;
1399
1458
  exports.randomItemIndex = randomItemIndex;
1400
1459
  exports.randomizeArray = randomizeArray;
1460
+ exports.rgbToHex = rgbToHex;
1401
1461
  exports.setInnerHtmlUnsafe = setInnerHtmlUnsafe;
1402
1462
  exports.takeRandomItem = takeRandomItem;
1403
1463
  exports.tr = tr;
package/dist/index.js CHANGED
@@ -108,6 +108,55 @@ function randomizeArray(array) {
108
108
  return retArray;
109
109
  }
110
110
 
111
+ // lib/colors.ts
112
+ function hexToRgb(hex) {
113
+ hex = hex.trim();
114
+ const bigint = parseInt(hex.startsWith("#") ? hex.slice(1) : hex, 16);
115
+ const r = bigint >> 16 & 255;
116
+ const g = bigint >> 8 & 255;
117
+ const b = bigint & 255;
118
+ return [clamp(r, 0, 255), clamp(g, 0, 255), clamp(b, 0, 255)];
119
+ }
120
+ function rgbToHex(red, green, blue, withHash = true, upperCase = false) {
121
+ const toHexVal = (n) => clamp(Math.round(n), 0, 255).toString(16).padStart(2, "0")[upperCase ? "toUpperCase" : "toLowerCase"]();
122
+ return `${withHash ? "#" : ""}${toHexVal(red)}${toHexVal(green)}${toHexVal(blue)}`;
123
+ }
124
+ function lightenColor(color, percent) {
125
+ return darkenColor(color, percent * -1);
126
+ }
127
+ function darkenColor(color, percent) {
128
+ var _a;
129
+ color = color.trim();
130
+ const darkenRgb = (r2, g2, b2, percent2) => {
131
+ r2 = Math.max(0, Math.min(255, r2 - r2 * percent2 / 100));
132
+ g2 = Math.max(0, Math.min(255, g2 - g2 * percent2 / 100));
133
+ b2 = Math.max(0, Math.min(255, b2 - b2 * percent2 / 100));
134
+ return [r2, g2, b2];
135
+ };
136
+ let r, g, b, a;
137
+ const isHexCol = color.match(/^#?([0-9A-Fa-f]{3}|[0-9A-Fa-f]{6})$/);
138
+ if (isHexCol)
139
+ [r, g, b] = hexToRgb(color);
140
+ else if (color.startsWith("rgb")) {
141
+ const rgbValues = (_a = color.match(/\d+(\.\d+)?/g)) == null ? void 0 : _a.map(Number);
142
+ if (rgbValues)
143
+ [r, g, b, a] = rgbValues;
144
+ else
145
+ throw new Error("Invalid RGB/RGBA color format");
146
+ } else
147
+ throw new Error("Unsupported color format");
148
+ [r, g, b] = darkenRgb(r, g, b, percent);
149
+ const upperCase = color.match(/[A-F]/) !== null;
150
+ if (isHexCol)
151
+ return rgbToHex(r, g, b, color.startsWith("#"), upperCase);
152
+ else if (color.startsWith("rgba"))
153
+ return `rgba(${r}, ${g}, ${b}, ${a})`;
154
+ else if (color.startsWith("rgb"))
155
+ return `rgb(${r}, ${g}, ${b})`;
156
+ else
157
+ throw new Error("Unsupported color format");
158
+ }
159
+
111
160
  // lib/dom.ts
112
161
  function getUnsafeWindow() {
113
162
  try {
@@ -1303,18 +1352,22 @@ var SelectorObserver = class {
1303
1352
  // lib/translation.ts
1304
1353
  var trans = {};
1305
1354
  var curLang;
1306
- function tr(key, ...args) {
1355
+ var trLang = (language, key, ...args) => {
1307
1356
  var _a;
1308
- if (!curLang)
1357
+ if (!language)
1309
1358
  return key;
1310
- const trText = (_a = trans[curLang]) == null ? void 0 : _a[key];
1359
+ const trText = (_a = trans[language]) == null ? void 0 : _a[key];
1311
1360
  if (!trText)
1312
1361
  return key;
1313
1362
  if (args.length > 0 && trText.match(/%\d/)) {
1314
1363
  return insertValues(trText, ...args);
1315
1364
  }
1316
1365
  return trText;
1366
+ };
1367
+ function tr(key, ...args) {
1368
+ return trLang(curLang, key, ...args);
1317
1369
  }
1370
+ tr.forLang = trLang;
1318
1371
  tr.addLanguage = (language, translations) => {
1319
1372
  trans[language] = translations;
1320
1373
  };
@@ -1324,5 +1377,8 @@ tr.setLanguage = (language) => {
1324
1377
  tr.getLanguage = () => {
1325
1378
  return curLang;
1326
1379
  };
1380
+ tr.getTranslations = (language) => {
1381
+ return trans[language != null ? language : curLang];
1382
+ };
1327
1383
 
1328
- export { DataStore, DataStoreSerializer, Dialog, NanoEmitter, SelectorObserver, addGlobalStyle, addParent, autoPlural, clamp, compress, computeHash, currentDialogId, debounce, decompress, defaultDialogCss, defaultStrings, fetchAdvanced, getSiblingsFrame, getUnsafeWindow, insertValues, interceptEvent, interceptWindowEvent, isScrollable, mapRange, observeElementProp, openDialogs, openInNewTab, pauseFor, preloadImages, randRange, randomId, randomItem, randomItemIndex, randomizeArray, setInnerHtmlUnsafe, takeRandomItem, tr };
1384
+ export { DataStore, DataStoreSerializer, Dialog, NanoEmitter, SelectorObserver, addGlobalStyle, addParent, autoPlural, clamp, compress, computeHash, currentDialogId, darkenColor, debounce, decompress, defaultDialogCss, defaultStrings, fetchAdvanced, getSiblingsFrame, getUnsafeWindow, hexToRgb, insertValues, interceptEvent, interceptWindowEvent, isScrollable, lightenColor, mapRange, observeElementProp, openDialogs, openInNewTab, pauseFor, preloadImages, randRange, randomId, randomItem, randomItemIndex, randomizeArray, rgbToHex, setInnerHtmlUnsafe, takeRandomItem, tr };
@@ -1,4 +1,5 @@
1
1
  export * from "./array.js";
2
+ export * from "./colors.js";
2
3
  export * from "./crypto.js";
3
4
  export * from "./DataStore.js";
4
5
  export * from "./DataStoreSerializer.js";
@@ -1,7 +1,8 @@
1
1
  import type { Stringifiable } from "./types.js";
2
2
  /**
3
3
  * Returns the translated text for the specified key in the current language set by {@linkcode tr.setLanguage()}
4
- * If the key is not found in the previously registered translation, the key itself is returned.
4
+ * Use {@linkcode tr.forLang()} to get the translation for a specific language instead of the currently set one.
5
+ * If the key is not found in the currently set language, the key itself is returned.
5
6
  *
6
7
  * ⚠️ Remember to register a language with {@linkcode tr.addLanguage()} and set it as active with {@linkcode tr.setLanguage()} before using this function, otherwise it will always return the key itself.
7
8
  * @param key Key of the translation to return
@@ -9,8 +10,10 @@ import type { Stringifiable } from "./types.js";
9
10
  */
10
11
  declare function tr(key: string, ...args: Stringifiable[]): string;
11
12
  declare namespace tr {
13
+ var forLang: (language: string, key: string, ...args: Stringifiable[]) => string;
12
14
  var addLanguage: (language: string, translations: Record<string, string>) => void;
13
15
  var setLanguage: (language: string) => void;
14
16
  var getLanguage: () => string;
17
+ var getTranslations: (language?: string | undefined) => Record<string, string> | undefined;
15
18
  }
16
19
  export { tr };
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@sv443-network/userutils",
3
3
  "libName": "UserUtils",
4
- "version": "7.2.1",
4
+ "version": "7.3.0",
5
5
  "description": "Library with various utilities for userscripts - register listeners for when CSS selectors exist, intercept events, create persistent & synchronous data stores, modify the DOM more easily and more",
6
6
  "main": "dist/index.js",
7
7
  "module": "dist/index.mjs",