dirk-cfx-react 1.1.89 → 1.1.91
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/dist/components/index.cjs +499 -247
- package/dist/components/index.cjs.map +1 -1
- package/dist/components/index.d.cts +39 -9
- package/dist/components/index.d.ts +39 -9
- package/dist/components/index.js +500 -249
- package/dist/components/index.js.map +1 -1
- package/dist/hooks/index.cjs +22 -12
- package/dist/hooks/index.cjs.map +1 -1
- package/dist/hooks/index.js +22 -12
- package/dist/hooks/index.js.map +1 -1
- package/dist/index.cjs +502 -248
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +43 -2
- package/dist/index.d.ts +43 -2
- package/dist/index.js +500 -250
- package/dist/index.js.map +1 -1
- package/dist/providers/index.cjs +51 -17
- package/dist/providers/index.cjs.map +1 -1
- package/dist/providers/index.js +51 -17
- package/dist/providers/index.js.map +1 -1
- package/dist/utils/index.cjs +51 -17
- package/dist/utils/index.cjs.map +1 -1
- package/dist/utils/index.js +51 -17
- package/dist/utils/index.js.map +1 -1
- package/package.json +1 -1
package/dist/index.cjs
CHANGED
|
@@ -4,6 +4,7 @@ var core = require('@mantine/core');
|
|
|
4
4
|
var jsxRuntime = require('react/jsx-runtime');
|
|
5
5
|
var React4 = require('react');
|
|
6
6
|
var zustand = require('zustand');
|
|
7
|
+
var zod = require('zod');
|
|
7
8
|
var axios = require('axios');
|
|
8
9
|
var reactFontawesome = require('@fortawesome/react-fontawesome');
|
|
9
10
|
var framerMotion = require('framer-motion');
|
|
@@ -28,7 +29,6 @@ var leaflet = require('leaflet');
|
|
|
28
29
|
require('leaflet/dist/leaflet.css');
|
|
29
30
|
var reactLeaflet = require('react-leaflet');
|
|
30
31
|
var reactLeafletComponentMarker = require('@adamscybot/react-leaflet-component-marker');
|
|
31
|
-
var zod = require('zod');
|
|
32
32
|
|
|
33
33
|
function _interopDefault (e) { return e && e.__esModule ? e : { default: e }; }
|
|
34
34
|
|
|
@@ -1321,6 +1321,32 @@ var openLink = (url) => {
|
|
|
1321
1321
|
window.invokeNative("openLink", url);
|
|
1322
1322
|
}
|
|
1323
1323
|
};
|
|
1324
|
+
var DEFAULT_PALETTE = [
|
|
1325
|
+
"#f0f4ff",
|
|
1326
|
+
"#d9e3ff",
|
|
1327
|
+
"#bfcfff",
|
|
1328
|
+
"#a6bbff",
|
|
1329
|
+
"#8ca7ff",
|
|
1330
|
+
"#7393ff",
|
|
1331
|
+
"#5a7fff",
|
|
1332
|
+
"#406bff",
|
|
1333
|
+
"#2547ff",
|
|
1334
|
+
"#0b33ff"
|
|
1335
|
+
];
|
|
1336
|
+
var ThemeOverrideSchema = zod.z.object({
|
|
1337
|
+
useOverride: zod.z.boolean(),
|
|
1338
|
+
primaryColor: zod.z.string(),
|
|
1339
|
+
primaryShade: zod.z.number(),
|
|
1340
|
+
customTheme: zod.z.array(zod.z.string())
|
|
1341
|
+
});
|
|
1342
|
+
var defaultThemeOverride = {
|
|
1343
|
+
useOverride: false,
|
|
1344
|
+
primaryColor: "dirk",
|
|
1345
|
+
primaryShade: 5,
|
|
1346
|
+
customTheme: DEFAULT_PALETTE
|
|
1347
|
+
};
|
|
1348
|
+
|
|
1349
|
+
// src/utils/useSettings.ts
|
|
1324
1350
|
var useSettings = zustand.create(() => ({
|
|
1325
1351
|
currency: "$",
|
|
1326
1352
|
game: "fivem",
|
|
@@ -1328,18 +1354,7 @@ var useSettings = zustand.create(() => ({
|
|
|
1328
1354
|
primaryShade: 9,
|
|
1329
1355
|
itemImgPath: "",
|
|
1330
1356
|
resourceVersion: "dev",
|
|
1331
|
-
customTheme:
|
|
1332
|
-
"#f0f4ff",
|
|
1333
|
-
"#d9e3ff",
|
|
1334
|
-
"#bfcfff",
|
|
1335
|
-
"#a6bbff",
|
|
1336
|
-
"#8ca7ff",
|
|
1337
|
-
"#7393ff",
|
|
1338
|
-
"#5a7fff",
|
|
1339
|
-
"#406bff",
|
|
1340
|
-
"#2547ff",
|
|
1341
|
-
"#0b33ff"
|
|
1342
|
-
]
|
|
1357
|
+
customTheme: DEFAULT_PALETTE
|
|
1343
1358
|
}));
|
|
1344
1359
|
|
|
1345
1360
|
// src/utils/fetchNui.ts
|
|
@@ -1423,11 +1438,35 @@ function reportMissingLocale(key) {
|
|
|
1423
1438
|
fetchNui("REPORT_MISSING_LOCALE", { key }).catch(() => {
|
|
1424
1439
|
});
|
|
1425
1440
|
}
|
|
1441
|
+
var PACKAGE_DEFAULTS = {
|
|
1442
|
+
"OccupantsDesc": "Here you can view and manage the occupants of your traphouse. These occupants can be used mainly for selling drugs to the NPCs surrounding your traphouse. However they have other uses to so be careful who you add as an occupant.",
|
|
1443
|
+
"cfgpanel_discard": "Discard",
|
|
1444
|
+
"cfgpanel_manual_edit": "Manual Edit",
|
|
1445
|
+
"cfgpanel_reset_defaults": "Reset Defaults",
|
|
1446
|
+
"cfgpanel_version": "Version",
|
|
1447
|
+
"cfgpanel_back_title": "Back to script list",
|
|
1448
|
+
"cfgpanel_undo": "Undo",
|
|
1449
|
+
"cfgpanel_redo": "Redo",
|
|
1450
|
+
"cfgpanel_save": "Save",
|
|
1451
|
+
"cfgpanel_saving": "Saving...",
|
|
1452
|
+
"cfgpanel_history": "History",
|
|
1453
|
+
"cfgpanel_reset_title": "Reset to Defaults",
|
|
1454
|
+
"cfgpanel_reset_desc": "This will permanently reset ALL config back to the defaults. Every value you have configured will be overwritten. This cannot be undone.",
|
|
1455
|
+
"cfgpanel_reset_confirm": "Reset Config",
|
|
1456
|
+
"cfgpanel_discard_title": "Discard Unsaved Changes?",
|
|
1457
|
+
"cfgpanel_discard_desc_back": "You have unsaved changes. Going back now will discard them.",
|
|
1458
|
+
"cfgpanel_discard_desc_close": "You have unsaved changes. Closing now will discard them.",
|
|
1459
|
+
"cfgpanel_discard_confirm_back": "Go Back Without Saving",
|
|
1460
|
+
"cfgpanel_discard_confirm_close": "Close Without Saving",
|
|
1461
|
+
"cfgpanel_json_title": "Config JSON",
|
|
1462
|
+
"cfgpanel_cancel": "Cancel",
|
|
1463
|
+
"cfgpanel_apply": "Apply",
|
|
1464
|
+
"cfgpanel_history_title": "Config History",
|
|
1465
|
+
"cfgpanel_close": "Close"
|
|
1466
|
+
};
|
|
1426
1467
|
var localeStore = zustand.create((set, get) => {
|
|
1427
1468
|
return {
|
|
1428
|
-
locales: {
|
|
1429
|
-
"OccupantsDesc": "Here you can view and manage the occupants of your traphouse. These occupants can be used mainly for selling drugs to the NPCs surrounding your traphouse. However they have other uses to so be careful who you add as an occupant."
|
|
1430
|
-
},
|
|
1469
|
+
locales: { ...PACKAGE_DEFAULTS },
|
|
1431
1470
|
locale: (key, ...args) => {
|
|
1432
1471
|
const exists = get().locales[key];
|
|
1433
1472
|
if (!exists) reportMissingLocale(key);
|
|
@@ -1441,7 +1480,7 @@ var localeStore = zustand.create((set, get) => {
|
|
|
1441
1480
|
});
|
|
1442
1481
|
var locale = localeStore.getState().locale;
|
|
1443
1482
|
registerInitialFetch("GET_LOCALES", void 0).then((data) => {
|
|
1444
|
-
localeStore.setState({ locales: data });
|
|
1483
|
+
localeStore.setState({ locales: { ...PACKAGE_DEFAULTS, ...data } });
|
|
1445
1484
|
}).catch(() => {
|
|
1446
1485
|
});
|
|
1447
1486
|
if (typeof window !== "undefined") {
|
|
@@ -1450,7 +1489,7 @@ if (typeof window !== "undefined") {
|
|
|
1450
1489
|
if (!msg || msg.action !== "UPDATE_DIRK_LIB_LOCALES") return;
|
|
1451
1490
|
if (!msg.data || typeof msg.data !== "object") return;
|
|
1452
1491
|
if (Object.keys(msg.data).length === 0) return;
|
|
1453
|
-
localeStore.setState({ locales: msg.data });
|
|
1492
|
+
localeStore.setState({ locales: { ...PACKAGE_DEFAULTS, ...msg.data } });
|
|
1454
1493
|
});
|
|
1455
1494
|
}
|
|
1456
1495
|
|
|
@@ -3727,11 +3766,11 @@ function ConfirmModal({
|
|
|
3727
3766
|
placeholder: confirmText,
|
|
3728
3767
|
value: typed,
|
|
3729
3768
|
onChange: (e) => setTyped(e.currentTarget.value),
|
|
3730
|
-
styles: (
|
|
3769
|
+
styles: (t4) => ({
|
|
3731
3770
|
input: {
|
|
3732
|
-
backgroundColor: core.alpha(
|
|
3771
|
+
backgroundColor: core.alpha(t4.colors.dark[7], 0.5),
|
|
3733
3772
|
border: `0.1vh solid ${core.alpha(
|
|
3734
|
-
typed === confirmText ? "#ef4444" :
|
|
3773
|
+
typed === confirmText ? "#ef4444" : t4.colors.dark[5],
|
|
3735
3774
|
0.5
|
|
3736
3775
|
)}`,
|
|
3737
3776
|
color: "rgba(255,255,255,0.85)",
|
|
@@ -4409,7 +4448,7 @@ function useAdminState(key, initial) {
|
|
|
4409
4448
|
React4.useEffect(() => {
|
|
4410
4449
|
const set = listeners.get(key) ?? /* @__PURE__ */ new Set();
|
|
4411
4450
|
listeners.set(key, set);
|
|
4412
|
-
const handler = () => setTick((
|
|
4451
|
+
const handler = () => setTick((t4) => t4 + 1);
|
|
4413
4452
|
set.add(handler);
|
|
4414
4453
|
return () => {
|
|
4415
4454
|
set.delete(handler);
|
|
@@ -5021,7 +5060,7 @@ function ConfigJsonModal({
|
|
|
5021
5060
|
setError(e.message);
|
|
5022
5061
|
}
|
|
5023
5062
|
};
|
|
5024
|
-
return /* @__PURE__ */ jsxRuntime.jsxs(Modal, { title: "
|
|
5063
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(Modal, { title: locale("cfgpanel_json_title"), icon: lucideReact.Code2, iconColor: color, onClose, width: "60vh", maxHeight: "80vh", zIndex: 200, children: [
|
|
5025
5064
|
/* @__PURE__ */ jsxRuntime.jsxs(core.Box, { flex: 1, p: "0.8vh", style: { overflowY: "auto" }, children: [
|
|
5026
5065
|
/* @__PURE__ */ jsxRuntime.jsx(
|
|
5027
5066
|
core.JsonInput,
|
|
@@ -5049,7 +5088,7 @@ function ConfigJsonModal({
|
|
|
5049
5088
|
style: { background: "transparent", border: `0.1vh solid ${theme2.colors.dark[6]}`, borderRadius: theme2.radius.xs, padding: `${theme2.spacing.xxs} ${theme2.spacing.xs}`, cursor: "pointer", display: "flex", alignItems: "center", gap: theme2.spacing.xxs },
|
|
5050
5089
|
children: [
|
|
5051
5090
|
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.X, { color: "rgba(255,255,255,0.4)" }),
|
|
5052
|
-
/* @__PURE__ */ jsxRuntime.jsx(core.Text, { ff: "Akrobat Bold", size: "xs", tt: "uppercase", lts: "0.05em", c: "rgba(255,255,255,0.4)", children: "
|
|
5091
|
+
/* @__PURE__ */ jsxRuntime.jsx(core.Text, { ff: "Akrobat Bold", size: "xs", tt: "uppercase", lts: "0.05em", c: "rgba(255,255,255,0.4)", children: locale("cfgpanel_cancel") })
|
|
5053
5092
|
]
|
|
5054
5093
|
}
|
|
5055
5094
|
),
|
|
@@ -5062,7 +5101,7 @@ function ConfigJsonModal({
|
|
|
5062
5101
|
style: { background: core.alpha(color, 0.14), border: `0.1vh solid ${core.alpha(color, 0.4)}`, borderRadius: theme2.radius.xs, padding: `${theme2.spacing.xxs} ${theme2.spacing.xs}`, cursor: "pointer", display: "flex", alignItems: "center", gap: theme2.spacing.xxs },
|
|
5063
5102
|
children: [
|
|
5064
5103
|
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.Check, { color }),
|
|
5065
|
-
/* @__PURE__ */ jsxRuntime.jsx(core.Text, { ff: "Akrobat Bold", size: "xs", tt: "uppercase", lts: "0.05em", c: color, children: "
|
|
5104
|
+
/* @__PURE__ */ jsxRuntime.jsx(core.Text, { ff: "Akrobat Bold", size: "xs", tt: "uppercase", lts: "0.05em", c: color, children: locale("cfgpanel_apply") })
|
|
5066
5105
|
]
|
|
5067
5106
|
}
|
|
5068
5107
|
)
|
|
@@ -5203,7 +5242,7 @@ function ConfigHistoryModal({
|
|
|
5203
5242
|
historyQuery.fetchNextPage();
|
|
5204
5243
|
}
|
|
5205
5244
|
};
|
|
5206
|
-
return /* @__PURE__ */ jsxRuntime.jsxs(Modal, { title: "
|
|
5245
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(Modal, { title: locale("cfgpanel_history_title"), icon: lucideReact.History, iconColor: color, onClose, width: "88vh", maxHeight: "82vh", zIndex: 260, children: [
|
|
5207
5246
|
/* @__PURE__ */ jsxRuntime.jsxs(core.Flex, { direction: "column", style: { flex: 1, minHeight: 0 }, children: [
|
|
5208
5247
|
/* @__PURE__ */ jsxRuntime.jsxs(core.Flex, { gap: "xs", p: "sm", style: { borderBottom: `0.1vh solid ${core.alpha(theme2.colors.dark[7], 0.8)}` }, children: [
|
|
5209
5248
|
/* @__PURE__ */ jsxRuntime.jsx(core.TextInput, { leftSection: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Search, { size: "1.4vh" }), placeholder: "Search path/admin/value", value: queryInput, onChange: (e) => setQueryInput(e.currentTarget.value), size: "xs", style: { flex: 1 } }),
|
|
@@ -5246,7 +5285,7 @@ function ConfigHistoryModal({
|
|
|
5246
5285
|
style: { background: "transparent", border: `0.1vh solid ${theme2.colors.dark[6]}`, borderRadius: theme2.radius.xs, padding: `${theme2.spacing.xxs} ${theme2.spacing.xs}`, cursor: "pointer", display: "flex", alignItems: "center", gap: theme2.spacing.xxs },
|
|
5247
5286
|
children: [
|
|
5248
5287
|
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.X, { color: "rgba(255,255,255,0.4)", size: "1.5vh" }),
|
|
5249
|
-
/* @__PURE__ */ jsxRuntime.jsx(core.Text, { ff: "Akrobat Bold", size: "xs", tt: "uppercase", lts: "0.05em", c: "rgba(255,255,255,0.4)", children: "
|
|
5288
|
+
/* @__PURE__ */ jsxRuntime.jsx(core.Text, { ff: "Akrobat Bold", size: "xs", tt: "uppercase", lts: "0.05em", c: "rgba(255,255,255,0.4)", children: locale("cfgpanel_close") })
|
|
5250
5289
|
]
|
|
5251
5290
|
}
|
|
5252
5291
|
) })
|
|
@@ -5306,9 +5345,9 @@ function ConfigPanelInner({
|
|
|
5306
5345
|
/* @__PURE__ */ jsxRuntime.jsx(framerMotion.AnimatePresence, { children: resetOpen && /* @__PURE__ */ jsxRuntime.jsx(
|
|
5307
5346
|
ConfirmModal,
|
|
5308
5347
|
{
|
|
5309
|
-
title: "
|
|
5310
|
-
description: "
|
|
5311
|
-
confirmLabel: "
|
|
5348
|
+
title: locale("cfgpanel_reset_title"),
|
|
5349
|
+
description: locale("cfgpanel_reset_desc"),
|
|
5350
|
+
confirmLabel: locale("cfgpanel_reset_confirm"),
|
|
5312
5351
|
confirmText: resetConfirmText,
|
|
5313
5352
|
onConfirm: async () => {
|
|
5314
5353
|
setResetOpen(false);
|
|
@@ -5340,9 +5379,9 @@ function ConfigPanelInner({
|
|
|
5340
5379
|
/* @__PURE__ */ jsxRuntime.jsx(framerMotion.AnimatePresence, { children: pendingAction !== null && /* @__PURE__ */ jsxRuntime.jsx(
|
|
5341
5380
|
ConfirmModal,
|
|
5342
5381
|
{
|
|
5343
|
-
title: "
|
|
5344
|
-
description: pendingAction === "back" ? "
|
|
5345
|
-
confirmLabel: pendingAction === "back" ? "
|
|
5382
|
+
title: locale("cfgpanel_discard_title"),
|
|
5383
|
+
description: pendingAction === "back" ? locale("cfgpanel_discard_desc_back") : locale("cfgpanel_discard_desc_close"),
|
|
5384
|
+
confirmLabel: pendingAction === "back" ? locale("cfgpanel_discard_confirm_back") : locale("cfgpanel_discard_confirm_close"),
|
|
5346
5385
|
onConfirm: () => {
|
|
5347
5386
|
const action = pendingAction;
|
|
5348
5387
|
setPendingAction(null);
|
|
@@ -5380,7 +5419,7 @@ function ConfigPanelInner({
|
|
|
5380
5419
|
/* @__PURE__ */ jsxRuntime.jsx(
|
|
5381
5420
|
framerMotion.motion.button,
|
|
5382
5421
|
{
|
|
5383
|
-
title: "
|
|
5422
|
+
title: locale("cfgpanel_back_title"),
|
|
5384
5423
|
onClick: handleBack,
|
|
5385
5424
|
whileHover: { background: core.alpha(color, 0.16), borderColor: core.alpha(color, 0.45) },
|
|
5386
5425
|
whileTap: { scale: 0.95 },
|
|
@@ -5408,7 +5447,7 @@ function ConfigPanelInner({
|
|
|
5408
5447
|
/* @__PURE__ */ jsxRuntime.jsx(
|
|
5409
5448
|
framerMotion.motion.button,
|
|
5410
5449
|
{
|
|
5411
|
-
title: "
|
|
5450
|
+
title: locale("cfgpanel_undo"),
|
|
5412
5451
|
onClick: () => form.canBack && form.back(),
|
|
5413
5452
|
disabled: !form.canBack,
|
|
5414
5453
|
whileHover: form.canBack ? { background: "rgba(255,255,255,0.07)" } : void 0,
|
|
@@ -5420,7 +5459,7 @@ function ConfigPanelInner({
|
|
|
5420
5459
|
/* @__PURE__ */ jsxRuntime.jsx(
|
|
5421
5460
|
framerMotion.motion.button,
|
|
5422
5461
|
{
|
|
5423
|
-
title: "
|
|
5462
|
+
title: locale("cfgpanel_redo"),
|
|
5424
5463
|
onClick: () => form.canForward && form.forward(),
|
|
5425
5464
|
disabled: !form.canForward,
|
|
5426
5465
|
whileHover: form.canForward ? { background: "rgba(255,255,255,0.07)" } : void 0,
|
|
@@ -5432,7 +5471,7 @@ function ConfigPanelInner({
|
|
|
5432
5471
|
/* @__PURE__ */ jsxRuntime.jsx(
|
|
5433
5472
|
framerMotion.motion.button,
|
|
5434
5473
|
{
|
|
5435
|
-
title: isSaving ? "
|
|
5474
|
+
title: isSaving ? locale("cfgpanel_saving") : isDirty ? `${locale("cfgpanel_save")} (${changedCount})` : locale("cfgpanel_save"),
|
|
5436
5475
|
onClick: () => isDirty && !isSaving && form.submit(),
|
|
5437
5476
|
disabled: !isDirty || isSaving,
|
|
5438
5477
|
whileHover: isDirty && !isSaving ? { background: core.alpha(color, 0.25), borderColor: core.alpha(color, 0.5) } : void 0,
|
|
@@ -5444,7 +5483,7 @@ function ConfigPanelInner({
|
|
|
5444
5483
|
/* @__PURE__ */ jsxRuntime.jsx(
|
|
5445
5484
|
framerMotion.motion.button,
|
|
5446
5485
|
{
|
|
5447
|
-
title: "
|
|
5486
|
+
title: locale("cfgpanel_history"),
|
|
5448
5487
|
onClick: () => setHistoryOpen(true),
|
|
5449
5488
|
whileHover: { background: core.alpha("#22d3ee", 0.16), borderColor: core.alpha("#22d3ee", 0.5) },
|
|
5450
5489
|
whileTap: { scale: 0.97 },
|
|
@@ -5465,7 +5504,7 @@ function ConfigPanelInner({
|
|
|
5465
5504
|
style: { width: "100%", background: "transparent", border: `0.1vh solid ${isDirty ? core.alpha("#f97316", 0.35) : core.alpha(theme2.colors.dark[5], 0.3)}`, borderRadius: theme2.radius.xs, padding: "0.65vh 0.8vh", cursor: isDirty ? "pointer" : "default", display: "flex", alignItems: "center", gap: "0.55vh", opacity: isDirty ? 1 : 0.35, transition: "opacity 0.2s" },
|
|
5466
5505
|
children: [
|
|
5467
5506
|
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.XCircle, { color: isDirty ? "#f97316" : "rgba(255,255,255,0.35)", size: "1.6vh" }),
|
|
5468
|
-
/* @__PURE__ */ jsxRuntime.jsx(core.Text, { ff: "Akrobat Bold", size: "xxs", tt: "uppercase", lts: "0.06em", c: isDirty ? "#f97316" : "rgba(255,255,255,0.35)", children: "
|
|
5507
|
+
/* @__PURE__ */ jsxRuntime.jsx(core.Text, { ff: "Akrobat Bold", size: "xxs", tt: "uppercase", lts: "0.06em", c: isDirty ? "#f97316" : "rgba(255,255,255,0.35)", children: locale("cfgpanel_discard") })
|
|
5469
5508
|
]
|
|
5470
5509
|
}
|
|
5471
5510
|
),
|
|
@@ -5479,7 +5518,7 @@ function ConfigPanelInner({
|
|
|
5479
5518
|
style: { width: "100%", background: core.alpha(color, 0.07), border: `0.1vh solid ${core.alpha(color, 0.28)}`, borderRadius: theme2.radius.xs, padding: "0.65vh 0.8vh", cursor: "pointer", display: "flex", alignItems: "center", gap: "0.55vh" },
|
|
5480
5519
|
children: [
|
|
5481
5520
|
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.Code2, { color, size: "1.6vh" }),
|
|
5482
|
-
/* @__PURE__ */ jsxRuntime.jsx(core.Text, { ff: "Akrobat Bold", size: "xxs", tt: "uppercase", lts: "0.06em", c: color, children: "
|
|
5521
|
+
/* @__PURE__ */ jsxRuntime.jsx(core.Text, { ff: "Akrobat Bold", size: "xxs", tt: "uppercase", lts: "0.06em", c: color, children: locale("cfgpanel_manual_edit") })
|
|
5483
5522
|
]
|
|
5484
5523
|
}
|
|
5485
5524
|
),
|
|
@@ -5492,12 +5531,13 @@ function ConfigPanelInner({
|
|
|
5492
5531
|
style: { width: "100%", background: core.alpha("#ef4444", 0.07), border: `0.1vh solid ${core.alpha("#ef4444", 0.25)}`, borderRadius: theme2.radius.xs, padding: "0.65vh 0.8vh", cursor: "pointer", display: "flex", alignItems: "center", gap: "0.55vh" },
|
|
5493
5532
|
children: [
|
|
5494
5533
|
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.RotateCcw, { color: "#ef4444", size: "1.6vh" }),
|
|
5495
|
-
/* @__PURE__ */ jsxRuntime.jsx(core.Text, { ff: "Akrobat Bold", size: "xxs", tt: "uppercase", lts: "0.06em", c: "#ef4444", children: "
|
|
5534
|
+
/* @__PURE__ */ jsxRuntime.jsx(core.Text, { ff: "Akrobat Bold", size: "xxs", tt: "uppercase", lts: "0.06em", c: "#ef4444", children: locale("cfgpanel_reset_defaults") })
|
|
5496
5535
|
]
|
|
5497
5536
|
}
|
|
5498
5537
|
),
|
|
5499
5538
|
version && /* @__PURE__ */ jsxRuntime.jsxs(core.Text, { size: "0.95vh", c: "dimmed", ta: "center", style: { letterSpacing: "0.04em", opacity: 0.8 }, children: [
|
|
5500
|
-
"
|
|
5539
|
+
locale("cfgpanel_version"),
|
|
5540
|
+
" ",
|
|
5501
5541
|
version
|
|
5502
5542
|
] })
|
|
5503
5543
|
] })
|
|
@@ -6588,24 +6628,6 @@ var MANTINE_COLOR_OPTIONS = [
|
|
|
6588
6628
|
"yellow",
|
|
6589
6629
|
"orange"
|
|
6590
6630
|
].map((value) => ({ value, label: value }));
|
|
6591
|
-
var DEFAULT_PALETTE = [
|
|
6592
|
-
"#f0f4ff",
|
|
6593
|
-
"#d9e3ff",
|
|
6594
|
-
"#bfcfff",
|
|
6595
|
-
"#a6bbff",
|
|
6596
|
-
"#8ca7ff",
|
|
6597
|
-
"#7393ff",
|
|
6598
|
-
"#5a7fff",
|
|
6599
|
-
"#406bff",
|
|
6600
|
-
"#2547ff",
|
|
6601
|
-
"#0b33ff"
|
|
6602
|
-
];
|
|
6603
|
-
var DEFAULT_VALUE = {
|
|
6604
|
-
useOverride: false,
|
|
6605
|
-
primaryColor: "dirk",
|
|
6606
|
-
primaryShade: 5,
|
|
6607
|
-
customTheme: DEFAULT_PALETTE
|
|
6608
|
-
};
|
|
6609
6631
|
function GroupLabel({ label: label2 }) {
|
|
6610
6632
|
return /* @__PURE__ */ jsxRuntime.jsxs(core.Flex, { align: "center", gap: "xs", mt: "xxs", children: [
|
|
6611
6633
|
/* @__PURE__ */ jsxRuntime.jsx(core.Text, { ff: "Akrobat Bold", size: "xxs", tt: "uppercase", lts: "0.07em", c: "rgba(255,255,255,0.2)", children: label2 }),
|
|
@@ -6620,10 +6642,10 @@ function ThemeOverrideSection({
|
|
|
6620
6642
|
const color = mantineTheme.colors[mantineTheme.primaryColor][5];
|
|
6621
6643
|
const raw = useFormField(schemaKey);
|
|
6622
6644
|
const value = {
|
|
6623
|
-
useOverride: raw?.useOverride ??
|
|
6624
|
-
primaryColor: raw?.primaryColor ??
|
|
6625
|
-
primaryShade: raw?.primaryShade ??
|
|
6626
|
-
customTheme: Array.isArray(raw?.customTheme) && raw.customTheme.length === 10 ? raw.customTheme :
|
|
6645
|
+
useOverride: raw?.useOverride ?? defaultThemeOverride.useOverride,
|
|
6646
|
+
primaryColor: raw?.primaryColor ?? defaultThemeOverride.primaryColor,
|
|
6647
|
+
primaryShade: raw?.primaryShade ?? defaultThemeOverride.primaryShade,
|
|
6648
|
+
customTheme: Array.isArray(raw?.customTheme) && raw.customTheme.length === 10 ? raw.customTheme : defaultThemeOverride.customTheme
|
|
6627
6649
|
};
|
|
6628
6650
|
const { setValue } = useFormActions();
|
|
6629
6651
|
const set = (key, val) => setValue(schemaKey, { ...value, [key]: val });
|
|
@@ -6830,6 +6852,403 @@ function SwatchTile({
|
|
|
6830
6852
|
) })
|
|
6831
6853
|
] });
|
|
6832
6854
|
}
|
|
6855
|
+
function usePlayers(opts = {}) {
|
|
6856
|
+
const {
|
|
6857
|
+
includeOffline = false,
|
|
6858
|
+
search = "",
|
|
6859
|
+
limit = 50,
|
|
6860
|
+
staleTimeMs,
|
|
6861
|
+
refetchIntervalMs
|
|
6862
|
+
} = opts;
|
|
6863
|
+
const query = reactQuery.useQuery({
|
|
6864
|
+
queryKey: includeOffline ? ["dirk:players", "search", search.trim().toLowerCase(), limit] : ["dirk:players", "online"],
|
|
6865
|
+
queryFn: async () => {
|
|
6866
|
+
const toolId = includeOffline ? "searchPlayers" : "getOnlinePlayers";
|
|
6867
|
+
const payload = includeOffline ? { id: toolId, value: { search: search.trim(), limit } } : { id: toolId };
|
|
6868
|
+
const result = await fetchNui(
|
|
6869
|
+
"ADMIN_TOOL_QUERY",
|
|
6870
|
+
payload,
|
|
6871
|
+
// Browser-dev fallback. Returns a couple of mock players so the
|
|
6872
|
+
// dev shell isn't blank.
|
|
6873
|
+
includeOffline ? [
|
|
6874
|
+
{ id: 1, citizenId: "ABC12345", name: "Dev User", charName: "John Doe", online: true },
|
|
6875
|
+
{ id: null, citizenId: "DEF67890", name: "", charName: "Jane Offline", online: false }
|
|
6876
|
+
] : [
|
|
6877
|
+
{ id: 1, citizenId: "ABC12345", name: "Dev User", charName: "John Doe", online: true }
|
|
6878
|
+
]
|
|
6879
|
+
);
|
|
6880
|
+
return Array.isArray(result) ? result : [];
|
|
6881
|
+
},
|
|
6882
|
+
staleTime: staleTimeMs ?? (includeOffline ? 3e4 : 5e3),
|
|
6883
|
+
gcTime: 5 * 6e4,
|
|
6884
|
+
refetchInterval: refetchIntervalMs ?? false,
|
|
6885
|
+
refetchOnWindowFocus: false,
|
|
6886
|
+
placeholderData: includeOffline ? reactQuery.keepPreviousData : void 0
|
|
6887
|
+
});
|
|
6888
|
+
return {
|
|
6889
|
+
players: query.data ?? [],
|
|
6890
|
+
isLoading: query.isLoading,
|
|
6891
|
+
isFetching: query.isFetching,
|
|
6892
|
+
error: query.error ?? null,
|
|
6893
|
+
refresh: () => query.refetch()
|
|
6894
|
+
};
|
|
6895
|
+
}
|
|
6896
|
+
var DEBOUNCE_MS = 300;
|
|
6897
|
+
var ONLINE_COLOR = "#3FA83F";
|
|
6898
|
+
var OFFLINE_COLOR = "#E54141";
|
|
6899
|
+
function PlayerSelect({
|
|
6900
|
+
value,
|
|
6901
|
+
onChange,
|
|
6902
|
+
includeOffline = false,
|
|
6903
|
+
limit = 50,
|
|
6904
|
+
searchable: searchableProp,
|
|
6905
|
+
placeholder,
|
|
6906
|
+
nothingFoundMessage: nothingFoundMessageProp,
|
|
6907
|
+
loadingLabel = "Loading\u2026",
|
|
6908
|
+
onlineLabel = "Online",
|
|
6909
|
+
offlineLabel = "Offline",
|
|
6910
|
+
refreshLabel = "Refresh player list",
|
|
6911
|
+
...rest
|
|
6912
|
+
}) {
|
|
6913
|
+
const theme2 = core.useMantineTheme();
|
|
6914
|
+
const color = theme2.colors[theme2.primaryColor][5];
|
|
6915
|
+
const [searchInput, setSearchInput] = React4.useState("");
|
|
6916
|
+
const [debouncedSearch, setDebouncedSearch] = React4.useState("");
|
|
6917
|
+
const { players, isFetching, refresh } = usePlayers({
|
|
6918
|
+
includeOffline,
|
|
6919
|
+
search: includeOffline ? debouncedSearch : void 0,
|
|
6920
|
+
limit
|
|
6921
|
+
});
|
|
6922
|
+
const sortedPlayers = React4.useMemo(
|
|
6923
|
+
() => [...players].sort((a, b) => {
|
|
6924
|
+
if (a.online !== b.online) return a.online ? -1 : 1;
|
|
6925
|
+
return a.charName.localeCompare(b.charName);
|
|
6926
|
+
}),
|
|
6927
|
+
[players]
|
|
6928
|
+
);
|
|
6929
|
+
const playerByCitizen = React4.useMemo(() => {
|
|
6930
|
+
const m = /* @__PURE__ */ new Map();
|
|
6931
|
+
for (const p of sortedPlayers) m.set(p.citizenId, p);
|
|
6932
|
+
return m;
|
|
6933
|
+
}, [sortedPlayers]);
|
|
6934
|
+
const data = React4.useMemo(() => {
|
|
6935
|
+
const items = sortedPlayers.map((p) => ({
|
|
6936
|
+
value: p.citizenId,
|
|
6937
|
+
label: formatLabel(p)
|
|
6938
|
+
}));
|
|
6939
|
+
if (value && !items.some((i) => i.value === value)) {
|
|
6940
|
+
items.unshift({ value, label: value });
|
|
6941
|
+
}
|
|
6942
|
+
return items;
|
|
6943
|
+
}, [sortedPlayers, value]);
|
|
6944
|
+
const selectedPlayer = value ? playerByCitizen.get(value) ?? null : null;
|
|
6945
|
+
const selectedLabel = selectedPlayer ? formatLabel(selectedPlayer) : null;
|
|
6946
|
+
React4.useEffect(() => {
|
|
6947
|
+
if (!includeOffline) return;
|
|
6948
|
+
if (selectedLabel && searchInput === selectedLabel) return;
|
|
6949
|
+
const t4 = setTimeout(() => setDebouncedSearch(searchInput), DEBOUNCE_MS);
|
|
6950
|
+
return () => clearTimeout(t4);
|
|
6951
|
+
}, [searchInput, includeOffline, selectedLabel]);
|
|
6952
|
+
const renderOption = ({ option }) => {
|
|
6953
|
+
const p = playerByCitizen.get(option.value);
|
|
6954
|
+
if (!p) return option.label;
|
|
6955
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(core.Group, { justify: "space-between", wrap: "nowrap", gap: "xs", style: { width: "100%" }, children: [
|
|
6956
|
+
/* @__PURE__ */ jsxRuntime.jsx(core.Text, { size: "xs", truncate: true, style: { flex: 1 }, children: formatLabel(p) }),
|
|
6957
|
+
/* @__PURE__ */ jsxRuntime.jsx(StatusDot, { online: p.online, onlineLabel, offlineLabel })
|
|
6958
|
+
] });
|
|
6959
|
+
};
|
|
6960
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
6961
|
+
core.Select,
|
|
6962
|
+
{
|
|
6963
|
+
...rest,
|
|
6964
|
+
data,
|
|
6965
|
+
value: value ?? null,
|
|
6966
|
+
onChange: (v) => {
|
|
6967
|
+
if (!v) return onChange(null);
|
|
6968
|
+
const player = playerByCitizen.get(v) ?? null;
|
|
6969
|
+
onChange(player);
|
|
6970
|
+
},
|
|
6971
|
+
searchable: searchableProp ?? true,
|
|
6972
|
+
searchValue: includeOffline ? searchInput : void 0,
|
|
6973
|
+
onSearchChange: includeOffline ? setSearchInput : void 0,
|
|
6974
|
+
placeholder,
|
|
6975
|
+
nothingFoundMessage: isFetching ? loadingLabel : nothingFoundMessageProp ?? "No players found",
|
|
6976
|
+
maxDropdownHeight: 300,
|
|
6977
|
+
renderOption,
|
|
6978
|
+
leftSection: selectedPlayer ? /* @__PURE__ */ jsxRuntime.jsx(StatusDot, { online: selectedPlayer.online, onlineLabel, offlineLabel }) : void 0,
|
|
6979
|
+
rightSectionWidth: "3.5vh",
|
|
6980
|
+
rightSectionPointerEvents: "all",
|
|
6981
|
+
rightSection: /* @__PURE__ */ jsxRuntime.jsx(
|
|
6982
|
+
core.ActionIcon,
|
|
6983
|
+
{
|
|
6984
|
+
variant: "subtle",
|
|
6985
|
+
size: "sm",
|
|
6986
|
+
onClick: (e) => {
|
|
6987
|
+
e.stopPropagation();
|
|
6988
|
+
refresh();
|
|
6989
|
+
},
|
|
6990
|
+
"aria-label": refreshLabel,
|
|
6991
|
+
title: refreshLabel,
|
|
6992
|
+
style: { marginRight: "0.6vh" },
|
|
6993
|
+
children: isFetching ? /* @__PURE__ */ jsxRuntime.jsx(core.Loader, { size: "1.2vh", color }) : /* @__PURE__ */ jsxRuntime.jsx(lucideReact.RefreshCw, { size: "1.4vh", color })
|
|
6994
|
+
}
|
|
6995
|
+
)
|
|
6996
|
+
}
|
|
6997
|
+
);
|
|
6998
|
+
}
|
|
6999
|
+
function StatusDot({ online, onlineLabel, offlineLabel }) {
|
|
7000
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
7001
|
+
"span",
|
|
7002
|
+
{
|
|
7003
|
+
title: online ? onlineLabel : offlineLabel,
|
|
7004
|
+
style: {
|
|
7005
|
+
display: "inline-block",
|
|
7006
|
+
width: "0.9vh",
|
|
7007
|
+
height: "0.9vh",
|
|
7008
|
+
borderRadius: "50%",
|
|
7009
|
+
backgroundColor: online ? ONLINE_COLOR : OFFLINE_COLOR,
|
|
7010
|
+
boxShadow: `0 0 0.4vh ${online ? ONLINE_COLOR : OFFLINE_COLOR}`,
|
|
7011
|
+
flexShrink: 0
|
|
7012
|
+
}
|
|
7013
|
+
}
|
|
7014
|
+
);
|
|
7015
|
+
}
|
|
7016
|
+
function formatLabel(p) {
|
|
7017
|
+
const parts = [p.charName || p.citizenId];
|
|
7018
|
+
if (p.online) {
|
|
7019
|
+
if (p.name) parts.push(p.name);
|
|
7020
|
+
if (p.id != null) parts.push(`#${p.id}`);
|
|
7021
|
+
}
|
|
7022
|
+
return parts.join(" \xB7 ");
|
|
7023
|
+
}
|
|
7024
|
+
var t = (key, fallback) => {
|
|
7025
|
+
const v = locale(key);
|
|
7026
|
+
return v === key ? fallback : v;
|
|
7027
|
+
};
|
|
7028
|
+
var DEFAULT_VALUE = {
|
|
7029
|
+
groups: [],
|
|
7030
|
+
identifiers: []
|
|
7031
|
+
};
|
|
7032
|
+
function SectionLabel({ icon: Icon, label: label2 }) {
|
|
7033
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(core.Flex, { align: "center", gap: "xs", mt: "xs", children: [
|
|
7034
|
+
/* @__PURE__ */ jsxRuntime.jsx(Icon, { size: "1.4vh", color: "rgba(255,255,255,0.3)" }),
|
|
7035
|
+
/* @__PURE__ */ jsxRuntime.jsx(core.Text, { ff: "Akrobat Bold", size: "xxs", tt: "uppercase", lts: "0.07em", c: "rgba(255,255,255,0.2)", children: label2 }),
|
|
7036
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { style: { flex: 1, height: "0.05vh", background: "rgba(255,255,255,0.06)" } })
|
|
7037
|
+
] });
|
|
7038
|
+
}
|
|
7039
|
+
function EmptyHint({ text }) {
|
|
7040
|
+
return /* @__PURE__ */ jsxRuntime.jsx(core.Text, { ff: "Akrobat Bold", size: "xxs", c: "rgba(255,255,255,0.25)", ta: "center", py: "xs", children: text });
|
|
7041
|
+
}
|
|
7042
|
+
function AccessOverrideSection({
|
|
7043
|
+
schemaKey = "access",
|
|
7044
|
+
title,
|
|
7045
|
+
description: description2,
|
|
7046
|
+
groupType,
|
|
7047
|
+
includeOffline = true
|
|
7048
|
+
}) {
|
|
7049
|
+
const mantineTheme = core.useMantineTheme();
|
|
7050
|
+
const color = mantineTheme.colors[mantineTheme.primaryColor][5];
|
|
7051
|
+
const raw = useFormField(schemaKey);
|
|
7052
|
+
const value = {
|
|
7053
|
+
groups: Array.isArray(raw?.groups) ? raw.groups : DEFAULT_VALUE.groups,
|
|
7054
|
+
identifiers: Array.isArray(raw?.identifiers) ? raw.identifiers : DEFAULT_VALUE.identifiers
|
|
7055
|
+
};
|
|
7056
|
+
const { setValue } = useFormActions();
|
|
7057
|
+
const set = (key, val) => setValue(schemaKey, { ...value, [key]: val });
|
|
7058
|
+
const [addingGroup, setAddingGroup] = React4.useState(false);
|
|
7059
|
+
const [addingPlayer, setAddingPlayer] = React4.useState(false);
|
|
7060
|
+
const commitGroup = (name) => {
|
|
7061
|
+
if (!name) return;
|
|
7062
|
+
set("groups", [...value.groups, name]);
|
|
7063
|
+
setAddingGroup(false);
|
|
7064
|
+
};
|
|
7065
|
+
const setGroup = (index, name) => {
|
|
7066
|
+
const next = [...value.groups];
|
|
7067
|
+
next[index] = name;
|
|
7068
|
+
set("groups", next.filter((g) => g !== ""));
|
|
7069
|
+
};
|
|
7070
|
+
const removeGroup = (index) => set("groups", value.groups.filter((_, i) => i !== index));
|
|
7071
|
+
const commitIdentifier = (id) => {
|
|
7072
|
+
if (!id) return;
|
|
7073
|
+
set("identifiers", [...value.identifiers, id]);
|
|
7074
|
+
setAddingPlayer(false);
|
|
7075
|
+
};
|
|
7076
|
+
const setIdentifier = (index, id) => {
|
|
7077
|
+
const next = [...value.identifiers];
|
|
7078
|
+
next[index] = id;
|
|
7079
|
+
set("identifiers", next.filter((x) => x !== ""));
|
|
7080
|
+
};
|
|
7081
|
+
const removeIdentifier = (index) => set("identifiers", value.identifiers.filter((_, i) => i !== index));
|
|
7082
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
7083
|
+
core.Flex,
|
|
7084
|
+
{
|
|
7085
|
+
direction: "column",
|
|
7086
|
+
gap: "xs",
|
|
7087
|
+
p: "sm",
|
|
7088
|
+
style: { flex: 1, minHeight: 0, overflowY: "auto" },
|
|
7089
|
+
children: [
|
|
7090
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
7091
|
+
AdminPageTitle,
|
|
7092
|
+
{
|
|
7093
|
+
icon: lucideReact.ShieldCheck,
|
|
7094
|
+
title: title || t("Access", "Access"),
|
|
7095
|
+
color
|
|
7096
|
+
}
|
|
7097
|
+
),
|
|
7098
|
+
/* @__PURE__ */ jsxRuntime.jsx(core.Text, { ff: "Akrobat Bold", size: "xxs", c: "rgba(255,255,255,0.4)", children: description2 || t(
|
|
7099
|
+
"AccessOverrideDesc",
|
|
7100
|
+
"Grant access to this resource's admin panel to specific groups and players, in addition to your global dirk_lib admins. Enforcement is server-side."
|
|
7101
|
+
) }),
|
|
7102
|
+
/* @__PURE__ */ jsxRuntime.jsx(SectionLabel, { icon: lucideReact.Users, label: t("AccessGroups", "Groups") }),
|
|
7103
|
+
/* @__PURE__ */ jsxRuntime.jsxs(core.Flex, { direction: "column", gap: "xxs", children: [
|
|
7104
|
+
value.groups.length === 0 && !addingGroup && /* @__PURE__ */ jsxRuntime.jsx(EmptyHint, { text: t("AccessNoGroups", "No groups added.") }),
|
|
7105
|
+
value.groups.map((name, i) => /* @__PURE__ */ jsxRuntime.jsxs(core.Flex, { align: "center", gap: "xs", children: [
|
|
7106
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
7107
|
+
GroupName,
|
|
7108
|
+
{
|
|
7109
|
+
value: name,
|
|
7110
|
+
onChange: (v) => setGroup(i, v),
|
|
7111
|
+
type: groupType,
|
|
7112
|
+
placeholder: t("AccessPickGroup", "Pick a group\u2026"),
|
|
7113
|
+
style: { flex: 1 }
|
|
7114
|
+
}
|
|
7115
|
+
),
|
|
7116
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
7117
|
+
core.ActionIcon,
|
|
7118
|
+
{
|
|
7119
|
+
variant: "subtle",
|
|
7120
|
+
color: "red",
|
|
7121
|
+
size: "md",
|
|
7122
|
+
onClick: () => removeGroup(i),
|
|
7123
|
+
title: t("Remove", "Remove"),
|
|
7124
|
+
"aria-label": t("Remove", "Remove"),
|
|
7125
|
+
children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Trash2, { size: "1.4vh" })
|
|
7126
|
+
}
|
|
7127
|
+
)
|
|
7128
|
+
] }, i)),
|
|
7129
|
+
addingGroup && /* @__PURE__ */ jsxRuntime.jsxs(core.Flex, { align: "center", gap: "xs", children: [
|
|
7130
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
7131
|
+
GroupName,
|
|
7132
|
+
{
|
|
7133
|
+
value: "",
|
|
7134
|
+
onChange: (v) => commitGroup(v),
|
|
7135
|
+
type: groupType,
|
|
7136
|
+
placeholder: t("AccessPickGroup", "Pick a group\u2026"),
|
|
7137
|
+
style: { flex: 1 }
|
|
7138
|
+
}
|
|
7139
|
+
),
|
|
7140
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
7141
|
+
core.ActionIcon,
|
|
7142
|
+
{
|
|
7143
|
+
variant: "subtle",
|
|
7144
|
+
color: "red",
|
|
7145
|
+
size: "md",
|
|
7146
|
+
onClick: () => setAddingGroup(false),
|
|
7147
|
+
title: t("Remove", "Remove"),
|
|
7148
|
+
"aria-label": t("Remove", "Remove"),
|
|
7149
|
+
children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Trash2, { size: "1.4vh" })
|
|
7150
|
+
}
|
|
7151
|
+
)
|
|
7152
|
+
] })
|
|
7153
|
+
] }),
|
|
7154
|
+
!addingGroup && /* @__PURE__ */ jsxRuntime.jsx(AddRowButton, { label: t("AccessAddGroup", "Add group"), onClick: () => setAddingGroup(true) }),
|
|
7155
|
+
/* @__PURE__ */ jsxRuntime.jsx(SectionLabel, { icon: lucideReact.UserRound, label: t("AccessPlayers", "Players") }),
|
|
7156
|
+
/* @__PURE__ */ jsxRuntime.jsxs(core.Flex, { direction: "column", gap: "xxs", children: [
|
|
7157
|
+
value.identifiers.length === 0 && !addingPlayer && /* @__PURE__ */ jsxRuntime.jsx(EmptyHint, { text: t("AccessNoPlayers", "No players added.") }),
|
|
7158
|
+
value.identifiers.map((id, i) => /* @__PURE__ */ jsxRuntime.jsxs(core.Flex, { align: "center", gap: "xs", children: [
|
|
7159
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
7160
|
+
PlayerSelect,
|
|
7161
|
+
{
|
|
7162
|
+
value: id || null,
|
|
7163
|
+
onChange: (p) => setIdentifier(i, p?.citizenId ?? ""),
|
|
7164
|
+
includeOffline,
|
|
7165
|
+
placeholder: t("AccessPickPlayer", "Pick a player\u2026"),
|
|
7166
|
+
style: { flex: 1 },
|
|
7167
|
+
size: "xs"
|
|
7168
|
+
}
|
|
7169
|
+
),
|
|
7170
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
7171
|
+
core.ActionIcon,
|
|
7172
|
+
{
|
|
7173
|
+
variant: "subtle",
|
|
7174
|
+
color: "red",
|
|
7175
|
+
size: "md",
|
|
7176
|
+
onClick: () => removeIdentifier(i),
|
|
7177
|
+
title: t("Remove", "Remove"),
|
|
7178
|
+
"aria-label": t("Remove", "Remove"),
|
|
7179
|
+
children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Trash2, { size: "1.4vh" })
|
|
7180
|
+
}
|
|
7181
|
+
)
|
|
7182
|
+
] }, i)),
|
|
7183
|
+
addingPlayer && /* @__PURE__ */ jsxRuntime.jsxs(core.Flex, { align: "center", gap: "xs", children: [
|
|
7184
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
7185
|
+
PlayerSelect,
|
|
7186
|
+
{
|
|
7187
|
+
value: null,
|
|
7188
|
+
onChange: (p) => commitIdentifier(p?.citizenId ?? ""),
|
|
7189
|
+
includeOffline,
|
|
7190
|
+
placeholder: t("AccessPickPlayer", "Pick a player\u2026"),
|
|
7191
|
+
style: { flex: 1 },
|
|
7192
|
+
size: "xs"
|
|
7193
|
+
}
|
|
7194
|
+
),
|
|
7195
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
7196
|
+
core.ActionIcon,
|
|
7197
|
+
{
|
|
7198
|
+
variant: "subtle",
|
|
7199
|
+
color: "red",
|
|
7200
|
+
size: "md",
|
|
7201
|
+
onClick: () => setAddingPlayer(false),
|
|
7202
|
+
title: t("Remove", "Remove"),
|
|
7203
|
+
"aria-label": t("Remove", "Remove"),
|
|
7204
|
+
children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Trash2, { size: "1.4vh" })
|
|
7205
|
+
}
|
|
7206
|
+
)
|
|
7207
|
+
] })
|
|
7208
|
+
] }),
|
|
7209
|
+
!addingPlayer && /* @__PURE__ */ jsxRuntime.jsx(AddRowButton, { label: t("AccessAddPlayer", "Add player"), onClick: () => setAddingPlayer(true) })
|
|
7210
|
+
]
|
|
7211
|
+
}
|
|
7212
|
+
);
|
|
7213
|
+
}
|
|
7214
|
+
function AddRowButton({ label: label2, onClick }) {
|
|
7215
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
7216
|
+
core.Flex,
|
|
7217
|
+
{
|
|
7218
|
+
align: "center",
|
|
7219
|
+
justify: "center",
|
|
7220
|
+
gap: "xs",
|
|
7221
|
+
onClick,
|
|
7222
|
+
role: "button",
|
|
7223
|
+
tabIndex: 0,
|
|
7224
|
+
onKeyDown: (e) => {
|
|
7225
|
+
if (e.key === "Enter" || e.key === " ") {
|
|
7226
|
+
e.preventDefault();
|
|
7227
|
+
onClick();
|
|
7228
|
+
}
|
|
7229
|
+
},
|
|
7230
|
+
py: "xs",
|
|
7231
|
+
style: {
|
|
7232
|
+
cursor: "pointer",
|
|
7233
|
+
border: "0.1vh dashed rgba(255,255,255,0.12)",
|
|
7234
|
+
borderRadius: "0.4vh",
|
|
7235
|
+
transition: "background 0.15s, border-color 0.15s"
|
|
7236
|
+
},
|
|
7237
|
+
onMouseEnter: (e) => {
|
|
7238
|
+
e.currentTarget.style.background = "rgba(255,255,255,0.03)";
|
|
7239
|
+
e.currentTarget.style.borderColor = "rgba(255,255,255,0.2)";
|
|
7240
|
+
},
|
|
7241
|
+
onMouseLeave: (e) => {
|
|
7242
|
+
e.currentTarget.style.background = "transparent";
|
|
7243
|
+
e.currentTarget.style.borderColor = "rgba(255,255,255,0.12)";
|
|
7244
|
+
},
|
|
7245
|
+
children: [
|
|
7246
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.Plus, { size: "1.4vh", color: "rgba(255,255,255,0.4)" }),
|
|
7247
|
+
/* @__PURE__ */ jsxRuntime.jsx(core.Text, { ff: "Akrobat Bold", size: "xxs", tt: "uppercase", lts: "0.06em", c: "rgba(255,255,255,0.4)", children: label2 })
|
|
7248
|
+
]
|
|
7249
|
+
}
|
|
7250
|
+
);
|
|
7251
|
+
}
|
|
6833
7252
|
|
|
6834
7253
|
// src/utils/gtaAnimPostFx.ts
|
|
6835
7254
|
var GTA_ANIM_POST_FX_GROUP_ORDER = [
|
|
@@ -7419,7 +7838,7 @@ function ScenarioSelect({
|
|
|
7419
7838
|
}
|
|
7420
7839
|
);
|
|
7421
7840
|
}
|
|
7422
|
-
var
|
|
7841
|
+
var t2 = (key, fallback) => {
|
|
7423
7842
|
const v = locale(key);
|
|
7424
7843
|
return v === key ? fallback : v;
|
|
7425
7844
|
};
|
|
@@ -7487,7 +7906,7 @@ function DiscordRoleSelect(props) {
|
|
|
7487
7906
|
return map;
|
|
7488
7907
|
}, [roles]);
|
|
7489
7908
|
if (errorCode === "NotConfigured") {
|
|
7490
|
-
const notConfiguredPlaceholder =
|
|
7909
|
+
const notConfiguredPlaceholder = t2(
|
|
7491
7910
|
"DiscordNotConfigured",
|
|
7492
7911
|
"Not configured \u2014 set in /dirk_lib"
|
|
7493
7912
|
);
|
|
@@ -7555,9 +7974,9 @@ function DiscordRoleSelect(props) {
|
|
|
7555
7974
|
e.stopPropagation();
|
|
7556
7975
|
refresh();
|
|
7557
7976
|
},
|
|
7558
|
-
title:
|
|
7977
|
+
title: t2("Refresh", "Refresh"),
|
|
7559
7978
|
loading,
|
|
7560
|
-
"aria-label":
|
|
7979
|
+
"aria-label": t2("Refresh", "Refresh"),
|
|
7561
7980
|
children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.RefreshCw, { size: "1.2vh" })
|
|
7562
7981
|
}
|
|
7563
7982
|
);
|
|
@@ -7567,7 +7986,7 @@ function DiscordRoleSelect(props) {
|
|
|
7567
7986
|
{
|
|
7568
7987
|
label: label2,
|
|
7569
7988
|
size,
|
|
7570
|
-
placeholder: placeholder ||
|
|
7989
|
+
placeholder: placeholder || t2("PickRoles", "Pick roles..."),
|
|
7571
7990
|
data,
|
|
7572
7991
|
value: props.value || [],
|
|
7573
7992
|
onChange: (ids) => props.onChange(ids),
|
|
@@ -7579,7 +7998,7 @@ function DiscordRoleSelect(props) {
|
|
|
7579
7998
|
rightSectionPointerEvents: "all",
|
|
7580
7999
|
style,
|
|
7581
8000
|
styles,
|
|
7582
|
-
nothingFoundMessage: errorCode ? `${
|
|
8001
|
+
nothingFoundMessage: errorCode ? `${t2("Error", "Error")} (${errorCode})` : t2("NoRoles", "No roles found")
|
|
7583
8002
|
}
|
|
7584
8003
|
);
|
|
7585
8004
|
}
|
|
@@ -7588,7 +8007,7 @@ function DiscordRoleSelect(props) {
|
|
|
7588
8007
|
{
|
|
7589
8008
|
label: label2,
|
|
7590
8009
|
size,
|
|
7591
|
-
placeholder: placeholder ||
|
|
8010
|
+
placeholder: placeholder || t2("PickRole", "Pick a role..."),
|
|
7592
8011
|
data,
|
|
7593
8012
|
value: props.value || null,
|
|
7594
8013
|
onChange: (id) => props.onChange(id),
|
|
@@ -7600,11 +8019,11 @@ function DiscordRoleSelect(props) {
|
|
|
7600
8019
|
rightSectionPointerEvents: "all",
|
|
7601
8020
|
style,
|
|
7602
8021
|
styles,
|
|
7603
|
-
nothingFoundMessage: errorCode ? `${
|
|
8022
|
+
nothingFoundMessage: errorCode ? `${t2("Error", "Error")} (${errorCode})` : t2("NoRoles", "No roles found")
|
|
7604
8023
|
}
|
|
7605
8024
|
);
|
|
7606
8025
|
}
|
|
7607
|
-
var
|
|
8026
|
+
var t3 = (key, fallback) => {
|
|
7608
8027
|
const v = locale(key);
|
|
7609
8028
|
return v === key ? fallback : v;
|
|
7610
8029
|
};
|
|
@@ -7625,7 +8044,7 @@ function FrameworkHint({ framework }) {
|
|
|
7625
8044
|
const theme2 = core.useMantineTheme();
|
|
7626
8045
|
if (!framework) return null;
|
|
7627
8046
|
const hintKey = `AccountFrameworkHint_${framework}`;
|
|
7628
|
-
const text =
|
|
8047
|
+
const text = t3(hintKey, FRAMEWORK_HINTS[framework] || FRAMEWORK_HINTS.unknown);
|
|
7629
8048
|
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
7630
8049
|
core.Flex,
|
|
7631
8050
|
{
|
|
@@ -7709,9 +8128,9 @@ function AccountSelect(props) {
|
|
|
7709
8128
|
e.stopPropagation();
|
|
7710
8129
|
refresh();
|
|
7711
8130
|
},
|
|
7712
|
-
title:
|
|
8131
|
+
title: t3("Refresh", "Refresh"),
|
|
7713
8132
|
loading,
|
|
7714
|
-
"aria-label":
|
|
8133
|
+
"aria-label": t3("Refresh", "Refresh"),
|
|
7715
8134
|
children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.RefreshCw, { size: "1.2vh" })
|
|
7716
8135
|
}
|
|
7717
8136
|
);
|
|
@@ -7725,14 +8144,14 @@ function AccountSelect(props) {
|
|
|
7725
8144
|
rightSection: refreshButton,
|
|
7726
8145
|
rightSectionPointerEvents: "all",
|
|
7727
8146
|
style,
|
|
7728
|
-
nothingFoundMessage:
|
|
8147
|
+
nothingFoundMessage: t3("NoAccounts", "No accounts available")
|
|
7729
8148
|
};
|
|
7730
8149
|
return /* @__PURE__ */ jsxRuntime.jsxs(core.Flex, { direction: "column", gap: "0.3vh", style, children: [
|
|
7731
8150
|
props.multi ? /* @__PURE__ */ jsxRuntime.jsx(
|
|
7732
8151
|
core.MultiSelect,
|
|
7733
8152
|
{
|
|
7734
8153
|
...sharedSelectProps,
|
|
7735
|
-
placeholder: placeholder ||
|
|
8154
|
+
placeholder: placeholder || t3("PickAccounts", "Pick accounts (or type custom)..."),
|
|
7736
8155
|
value: props.value || [],
|
|
7737
8156
|
onChange: (names) => props.onChange(names),
|
|
7738
8157
|
renderOption,
|
|
@@ -7744,7 +8163,7 @@ function AccountSelect(props) {
|
|
|
7744
8163
|
core.Select,
|
|
7745
8164
|
{
|
|
7746
8165
|
...sharedSelectProps,
|
|
7747
|
-
placeholder: placeholder ||
|
|
8166
|
+
placeholder: placeholder || t3("PickAccount", "Pick an account..."),
|
|
7748
8167
|
value: props.value || null,
|
|
7749
8168
|
onChange: (name) => props.onChange(name),
|
|
7750
8169
|
renderOption,
|
|
@@ -8036,175 +8455,6 @@ function WorldPositionGotoButton2({
|
|
|
8036
8455
|
}
|
|
8037
8456
|
) });
|
|
8038
8457
|
}
|
|
8039
|
-
function usePlayers(opts = {}) {
|
|
8040
|
-
const {
|
|
8041
|
-
includeOffline = false,
|
|
8042
|
-
search = "",
|
|
8043
|
-
limit = 50,
|
|
8044
|
-
staleTimeMs,
|
|
8045
|
-
refetchIntervalMs
|
|
8046
|
-
} = opts;
|
|
8047
|
-
const query = reactQuery.useQuery({
|
|
8048
|
-
queryKey: includeOffline ? ["dirk:players", "search", search.trim().toLowerCase(), limit] : ["dirk:players", "online"],
|
|
8049
|
-
queryFn: async () => {
|
|
8050
|
-
const toolId = includeOffline ? "searchPlayers" : "getOnlinePlayers";
|
|
8051
|
-
const payload = includeOffline ? { id: toolId, value: { search: search.trim(), limit } } : { id: toolId };
|
|
8052
|
-
const result = await fetchNui(
|
|
8053
|
-
"ADMIN_TOOL_QUERY",
|
|
8054
|
-
payload,
|
|
8055
|
-
// Browser-dev fallback. Returns a couple of mock players so the
|
|
8056
|
-
// dev shell isn't blank.
|
|
8057
|
-
includeOffline ? [
|
|
8058
|
-
{ id: 1, citizenId: "ABC12345", name: "Dev User", charName: "John Doe", online: true },
|
|
8059
|
-
{ id: null, citizenId: "DEF67890", name: "", charName: "Jane Offline", online: false }
|
|
8060
|
-
] : [
|
|
8061
|
-
{ id: 1, citizenId: "ABC12345", name: "Dev User", charName: "John Doe", online: true }
|
|
8062
|
-
]
|
|
8063
|
-
);
|
|
8064
|
-
return Array.isArray(result) ? result : [];
|
|
8065
|
-
},
|
|
8066
|
-
staleTime: staleTimeMs ?? (includeOffline ? 3e4 : 5e3),
|
|
8067
|
-
gcTime: 5 * 6e4,
|
|
8068
|
-
refetchInterval: refetchIntervalMs ?? false,
|
|
8069
|
-
refetchOnWindowFocus: false,
|
|
8070
|
-
placeholderData: includeOffline ? reactQuery.keepPreviousData : void 0
|
|
8071
|
-
});
|
|
8072
|
-
return {
|
|
8073
|
-
players: query.data ?? [],
|
|
8074
|
-
isLoading: query.isLoading,
|
|
8075
|
-
isFetching: query.isFetching,
|
|
8076
|
-
error: query.error ?? null,
|
|
8077
|
-
refresh: () => query.refetch()
|
|
8078
|
-
};
|
|
8079
|
-
}
|
|
8080
|
-
var DEBOUNCE_MS = 300;
|
|
8081
|
-
var ONLINE_COLOR = "#3FA83F";
|
|
8082
|
-
var OFFLINE_COLOR = "#E54141";
|
|
8083
|
-
function PlayerSelect({
|
|
8084
|
-
value,
|
|
8085
|
-
onChange,
|
|
8086
|
-
includeOffline = false,
|
|
8087
|
-
limit = 50,
|
|
8088
|
-
searchable: searchableProp,
|
|
8089
|
-
placeholder,
|
|
8090
|
-
nothingFoundMessage: nothingFoundMessageProp,
|
|
8091
|
-
loadingLabel = "Loading\u2026",
|
|
8092
|
-
onlineLabel = "Online",
|
|
8093
|
-
offlineLabel = "Offline",
|
|
8094
|
-
refreshLabel = "Refresh player list",
|
|
8095
|
-
...rest
|
|
8096
|
-
}) {
|
|
8097
|
-
const theme2 = core.useMantineTheme();
|
|
8098
|
-
const color = theme2.colors[theme2.primaryColor][5];
|
|
8099
|
-
const [searchInput, setSearchInput] = React4.useState("");
|
|
8100
|
-
const [debouncedSearch, setDebouncedSearch] = React4.useState("");
|
|
8101
|
-
const { players, isFetching, refresh } = usePlayers({
|
|
8102
|
-
includeOffline,
|
|
8103
|
-
search: includeOffline ? debouncedSearch : void 0,
|
|
8104
|
-
limit
|
|
8105
|
-
});
|
|
8106
|
-
const sortedPlayers = React4.useMemo(
|
|
8107
|
-
() => [...players].sort((a, b) => {
|
|
8108
|
-
if (a.online !== b.online) return a.online ? -1 : 1;
|
|
8109
|
-
return a.charName.localeCompare(b.charName);
|
|
8110
|
-
}),
|
|
8111
|
-
[players]
|
|
8112
|
-
);
|
|
8113
|
-
const playerByCitizen = React4.useMemo(() => {
|
|
8114
|
-
const m = /* @__PURE__ */ new Map();
|
|
8115
|
-
for (const p of sortedPlayers) m.set(p.citizenId, p);
|
|
8116
|
-
return m;
|
|
8117
|
-
}, [sortedPlayers]);
|
|
8118
|
-
const data = React4.useMemo(() => {
|
|
8119
|
-
const items = sortedPlayers.map((p) => ({
|
|
8120
|
-
value: p.citizenId,
|
|
8121
|
-
label: formatLabel(p)
|
|
8122
|
-
}));
|
|
8123
|
-
if (value && !items.some((i) => i.value === value)) {
|
|
8124
|
-
items.unshift({ value, label: value });
|
|
8125
|
-
}
|
|
8126
|
-
return items;
|
|
8127
|
-
}, [sortedPlayers, value]);
|
|
8128
|
-
const selectedPlayer = value ? playerByCitizen.get(value) ?? null : null;
|
|
8129
|
-
const selectedLabel = selectedPlayer ? formatLabel(selectedPlayer) : null;
|
|
8130
|
-
React4.useEffect(() => {
|
|
8131
|
-
if (!includeOffline) return;
|
|
8132
|
-
if (selectedLabel && searchInput === selectedLabel) return;
|
|
8133
|
-
const t3 = setTimeout(() => setDebouncedSearch(searchInput), DEBOUNCE_MS);
|
|
8134
|
-
return () => clearTimeout(t3);
|
|
8135
|
-
}, [searchInput, includeOffline, selectedLabel]);
|
|
8136
|
-
const renderOption = ({ option }) => {
|
|
8137
|
-
const p = playerByCitizen.get(option.value);
|
|
8138
|
-
if (!p) return option.label;
|
|
8139
|
-
return /* @__PURE__ */ jsxRuntime.jsxs(core.Group, { justify: "space-between", wrap: "nowrap", gap: "xs", style: { width: "100%" }, children: [
|
|
8140
|
-
/* @__PURE__ */ jsxRuntime.jsx(core.Text, { size: "xs", truncate: true, style: { flex: 1 }, children: formatLabel(p) }),
|
|
8141
|
-
/* @__PURE__ */ jsxRuntime.jsx(StatusDot, { online: p.online, onlineLabel, offlineLabel })
|
|
8142
|
-
] });
|
|
8143
|
-
};
|
|
8144
|
-
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
8145
|
-
core.Select,
|
|
8146
|
-
{
|
|
8147
|
-
...rest,
|
|
8148
|
-
data,
|
|
8149
|
-
value: value ?? null,
|
|
8150
|
-
onChange: (v) => {
|
|
8151
|
-
if (!v) return onChange(null);
|
|
8152
|
-
const player = playerByCitizen.get(v) ?? null;
|
|
8153
|
-
onChange(player);
|
|
8154
|
-
},
|
|
8155
|
-
searchable: searchableProp ?? true,
|
|
8156
|
-
searchValue: includeOffline ? searchInput : void 0,
|
|
8157
|
-
onSearchChange: includeOffline ? setSearchInput : void 0,
|
|
8158
|
-
placeholder,
|
|
8159
|
-
nothingFoundMessage: isFetching ? loadingLabel : nothingFoundMessageProp ?? "No players found",
|
|
8160
|
-
maxDropdownHeight: 300,
|
|
8161
|
-
renderOption,
|
|
8162
|
-
leftSection: selectedPlayer ? /* @__PURE__ */ jsxRuntime.jsx(StatusDot, { online: selectedPlayer.online, onlineLabel, offlineLabel }) : void 0,
|
|
8163
|
-
rightSectionWidth: "3.5vh",
|
|
8164
|
-
rightSectionPointerEvents: "all",
|
|
8165
|
-
rightSection: /* @__PURE__ */ jsxRuntime.jsx(
|
|
8166
|
-
core.ActionIcon,
|
|
8167
|
-
{
|
|
8168
|
-
variant: "subtle",
|
|
8169
|
-
size: "sm",
|
|
8170
|
-
onClick: (e) => {
|
|
8171
|
-
e.stopPropagation();
|
|
8172
|
-
refresh();
|
|
8173
|
-
},
|
|
8174
|
-
"aria-label": refreshLabel,
|
|
8175
|
-
title: refreshLabel,
|
|
8176
|
-
style: { marginRight: "0.6vh" },
|
|
8177
|
-
children: isFetching ? /* @__PURE__ */ jsxRuntime.jsx(core.Loader, { size: "1.2vh", color }) : /* @__PURE__ */ jsxRuntime.jsx(lucideReact.RefreshCw, { size: "1.4vh", color })
|
|
8178
|
-
}
|
|
8179
|
-
)
|
|
8180
|
-
}
|
|
8181
|
-
);
|
|
8182
|
-
}
|
|
8183
|
-
function StatusDot({ online, onlineLabel, offlineLabel }) {
|
|
8184
|
-
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
8185
|
-
"span",
|
|
8186
|
-
{
|
|
8187
|
-
title: online ? onlineLabel : offlineLabel,
|
|
8188
|
-
style: {
|
|
8189
|
-
display: "inline-block",
|
|
8190
|
-
width: "0.9vh",
|
|
8191
|
-
height: "0.9vh",
|
|
8192
|
-
borderRadius: "50%",
|
|
8193
|
-
backgroundColor: online ? ONLINE_COLOR : OFFLINE_COLOR,
|
|
8194
|
-
boxShadow: `0 0 0.4vh ${online ? ONLINE_COLOR : OFFLINE_COLOR}`,
|
|
8195
|
-
flexShrink: 0
|
|
8196
|
-
}
|
|
8197
|
-
}
|
|
8198
|
-
);
|
|
8199
|
-
}
|
|
8200
|
-
function formatLabel(p) {
|
|
8201
|
-
const parts = [p.charName || p.citizenId];
|
|
8202
|
-
if (p.online) {
|
|
8203
|
-
if (p.name) parts.push(p.name);
|
|
8204
|
-
if (p.id != null) parts.push(`#${p.id}`);
|
|
8205
|
-
}
|
|
8206
|
-
return parts.join(" \xB7 ");
|
|
8207
|
-
}
|
|
8208
8458
|
function usePickDoor() {
|
|
8209
8459
|
const begin = useAdminToolStore((s) => s.begin);
|
|
8210
8460
|
return async () => {
|
|
@@ -8596,6 +8846,7 @@ var Vector4Schema = zod.z.object({
|
|
|
8596
8846
|
w: zod.z.number()
|
|
8597
8847
|
});
|
|
8598
8848
|
|
|
8849
|
+
exports.AccessOverrideSection = AccessOverrideSection;
|
|
8599
8850
|
exports.AccountSelect = AccountSelect;
|
|
8600
8851
|
exports.AdminPageTitle = AdminPageTitle;
|
|
8601
8852
|
exports.AnimPostFxSelect = AnimPostFxSelect;
|
|
@@ -8610,6 +8861,7 @@ exports.ConfirmModal = ConfirmModal;
|
|
|
8610
8861
|
exports.ControlMultiSelect = ControlMultiSelect;
|
|
8611
8862
|
exports.ControlSelect = ControlSelect;
|
|
8612
8863
|
exports.Counter = Counter;
|
|
8864
|
+
exports.DEFAULT_PALETTE = DEFAULT_PALETTE;
|
|
8613
8865
|
exports.DirkProvider = DirkProvider;
|
|
8614
8866
|
exports.DiscordRoleSelect = DiscordRoleSelect;
|
|
8615
8867
|
exports.DoorPickerButton = DoorPickerButton;
|
|
@@ -8650,6 +8902,7 @@ exports.SegmentedProgress = SegmentedProgress;
|
|
|
8650
8902
|
exports.SelectItem = SelectItem;
|
|
8651
8903
|
exports.SwitchPanel = SwitchPanel;
|
|
8652
8904
|
exports.TestBed = TestBed;
|
|
8905
|
+
exports.ThemeOverrideSchema = ThemeOverrideSchema;
|
|
8653
8906
|
exports.ThemeOverrideSection = ThemeOverrideSection;
|
|
8654
8907
|
exports.Title = Title;
|
|
8655
8908
|
exports.TornEdgeSVGFilter = TornEdgeSVGFilter;
|
|
@@ -8670,6 +8923,7 @@ exports.copyToClipboard = copyToClipboard;
|
|
|
8670
8923
|
exports.createFormStore = createFormStore;
|
|
8671
8924
|
exports.createScriptConfig = createScriptConfig;
|
|
8672
8925
|
exports.createSkill = createSkill;
|
|
8926
|
+
exports.defaultThemeOverride = defaultThemeOverride;
|
|
8673
8927
|
exports.dirkQueryClient = dirkQueryClient;
|
|
8674
8928
|
exports.ensureFrameworkGroups = ensureFrameworkGroups;
|
|
8675
8929
|
exports.extractDefaults = extractDefaults;
|