@bud.sh/app 0.4.1 → 0.5.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/dist/client/assets/bud/design.js +1 -1
- package/dist/client/assets/{canvas-DIKX_HCJ.js → canvas-Cu6R6xxT.js} +1 -1
- package/dist/client/assets/difference-worker-jfTSn-Tw.js +8 -0
- package/dist/client/assets/{edit-B050x0rV.js → edit-DUotSxjS.js} +12 -12
- package/dist/client/assets/files-js6ElfkU.js +1 -0
- package/dist/client/assets/i18n-DxqFr2mi.js +1 -0
- package/dist/client/assets/index-CFFxP0gS.css +2 -0
- package/dist/client/assets/{index-COvyj5zV.js → index-ChANGtl-.js} +2 -2
- package/dist/client/assets/lru-DzKYIXMA.js +1 -0
- package/dist/client/assets/pages-6_lhiQmz.js +1 -0
- package/dist/client/assets/{project-branches-DwKjCwZv.js → project-branches-DO897zM6.js} +1 -1
- package/dist/client/assets/project-comments-DFFKVpia.js +1 -0
- package/dist/client/assets/project-thread-links-NLFWQRD2.js +1 -0
- package/dist/client/assets/{project-threads-DeKXNqeP.js → project-threads-Lay351p4.js} +105 -105
- package/dist/client/assets/{project-work-B7PGQtV9.js → project-work-du0Y-L5Y.js} +1 -1
- package/dist/client/assets/rolldown-runtime-XKyaHtl9.js +1 -0
- package/dist/client/assets/task-design-Avb2RO4w.js +23 -0
- package/dist/client/assets/tasks-CA-E8bbK.js +1 -0
- package/dist/client/assets/{tasks-request-CsUB5__X.js → tasks-request-C55IeuiP.js} +1 -1
- package/dist/client/assets/workspace-Cw5HvX5d.js +2 -0
- package/dist/client/index.html +3 -3
- package/dist/hosted/assets/{canvas-gWj_ocKK.js → canvas-V36732ER.js} +6 -4
- package/dist/hosted/assets/{comment-data-C-rNCB1n.js → comment-data-CF2ZV_3k.js} +4021 -3645
- package/dist/hosted/assets/{files-CAPvbavY.js → files-DjSCjfU7.js} +5 -3
- package/dist/hosted/assets/{pages-DJiOvT-l.js → pages-BzjzeuPu.js} +3 -3
- package/dist/hosted/assets/{project-branches-BgrfdvtL.js → project-branches-BT97J9i7.js} +1 -1
- package/dist/hosted/assets/{project-thread-links-B7uzThL9.js → project-thread-links-BRLgByEe.js} +2 -2
- package/dist/hosted/assets/{screen-D4D9nh4V.js → screen-CKp2C7kx.js} +68 -137
- package/dist/hosted/assets/{tasks-C7aGLzBw.js → tasks-Dj7AyBJB.js} +12 -5
- package/dist/hosted/assets/{tasks-request-CikFdCgP.js → tasks-request-DZob623r.js} +1 -1
- package/dist/hosted/hosted.js +164 -16
- package/dist/node/assets/{src-BdvZ2mYc.js → src-CerrKjID.js} +57 -1
- package/dist/node/design.js +829 -789
- package/dist/node/server.js +25 -3
- package/dist/node-host/assets/{canvas-kXzp80a5.js → canvas-TRUfxfL5.js} +6 -4
- package/dist/node-host/assets/{comment-data-CeuJbJKJ.js → comment-data-DyIZNpfG.js} +4003 -3627
- package/dist/node-host/assets/{files-0YIuvKzb.js → files-Dh2TiQZq.js} +5 -3
- package/dist/node-host/assets/{pages-DOF22SyG.js → pages-BxpjbYhs.js} +3 -3
- package/dist/node-host/assets/{project-branches-BeEwMBIw.js → project-branches-B7HUGiVK.js} +1 -1
- package/dist/node-host/assets/{project-thread-links-Bs_MtfBC.js → project-thread-links-CauJF0Cz.js} +2 -2
- package/dist/node-host/assets/{screen-DRTAKkn3.js → screen-CZXWJEds.js} +68 -137
- package/dist/node-host/assets/{tasks-BA_hcbj5.js → tasks-Bs1IOpeU.js} +12 -5
- package/dist/node-host/assets/{tasks-request-Doc9y_20.js → tasks-request-ZWmbc8fE.js} +1 -1
- package/dist/node-host/node-host.js +164 -16
- package/dist/server/assets/{canvas-CiN6jNIZ.js → canvas-Dc1mYCwQ.js} +7 -5
- package/dist/server/assets/{comment-data-9SqALQjT.js → comment-data-CsjukwAW.js} +3773 -3608
- package/dist/server/assets/{events-6z5v7Uca.js → events-iHpLGr3k.js} +213 -2
- package/dist/server/assets/{files-DBVqeLdL.js → files-E9mSFeoc.js} +6 -4
- package/dist/server/assets/{listener-DGWKUc2o.js → listener-DN5TyOjJ.js} +35 -9
- package/dist/server/assets/{pages-DJMLr6j9.js → pages-BBBXyJWV.js} +4 -4
- package/dist/server/assets/{project-branches-DbKEmiQT.js → project-branches-B0YIK6Ur.js} +2 -2
- package/dist/server/assets/{project-thread-links-C0kV_Pcl.js → project-thread-links-CBOpf6zk.js} +3 -3
- package/dist/server/assets/{project-work-C0FN3w5Y.js → project-work-qSKFO5yj.js} +3 -3
- package/dist/server/assets/{screen-BtvzEiIa.js → screen-BIQA2mr4.js} +69 -138
- package/dist/server/assets/{server-CYvuOSBA.js → server-DxK-UB_Z.js} +30 -4
- package/dist/server/assets/{services-DK4fqrlF.js → services-BRrgXYlT.js} +105 -9
- package/dist/server/assets/{tasks-DX71x8f9.js → tasks-CiXodsLN.js} +14 -7
- package/dist/server/assets/{tasks-request-C3jk9Jyu.js → tasks-request-DhwCzpRi.js} +2 -2
- package/dist/server/migration.js +3 -3
- package/dist/server/runtime.js +3 -3
- package/dist/server/server.js +2 -2
- package/dist/types/server.d.ts +11 -1
- package/package.json +1 -1
- package/dist/client/assets/difference-worker-CwQNxTJL.js +0 -8
- package/dist/client/assets/files-BQ9O3Z8-.js +0 -1
- package/dist/client/assets/i18n-CL0jBP7Y.js +0 -1
- package/dist/client/assets/index-CjhJtepP.css +0 -2
- package/dist/client/assets/lru-BkhKJhvt.js +0 -1
- package/dist/client/assets/pages-BGl2Yuza.js +0 -1
- package/dist/client/assets/project-comments-Cdip2Y10.js +0 -1
- package/dist/client/assets/project-thread-links-BGIkGQeU.js +0 -1
- package/dist/client/assets/task-design-DJp5yho1.js +0 -23
- package/dist/client/assets/tasks-BHXj727C.js +0 -1
- package/dist/client/assets/workspace-CbO7RsI2.js +0 -2
package/dist/node/design.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { a as FieldCardFooter, c as Button, i as FieldCardContent, l as Text, o as FieldCardHeader, r as FieldCard, s as ariaAttributes, t as Loader } from "./assets/loader-QRRDmKqp.js";
|
|
2
|
-
import {
|
|
2
|
+
import { C as valueByRole, g as parseWorkItemRef, j as statusCategory, k as fieldByRole, p as parseWorkCreate, v as parseWorkPatch } from "./assets/src-CerrKjID.js";
|
|
3
3
|
import { createElement, on, ref } from "remix/component";
|
|
4
4
|
import { Fragment, jsx, jsxs } from "remix/component/jsx-runtime";
|
|
5
5
|
import { createMatcher } from "remix/route-pattern/match";
|
|
@@ -3230,6 +3230,10 @@ var de = {
|
|
|
3230
3230
|
text: "Bud hat eine Kommentaränderung rückgängig gemacht",
|
|
3231
3231
|
source: "1f7e1986"
|
|
3232
3232
|
},
|
|
3233
|
+
"app.client.projectComments.commentDeleted": {
|
|
3234
|
+
text: "Kommentar gelöscht",
|
|
3235
|
+
source: "e442d3f3"
|
|
3236
|
+
},
|
|
3233
3237
|
"app.client.projectComments.commentSaved": {
|
|
3234
3238
|
text: "Kommentar gespeichert",
|
|
3235
3239
|
source: "f7901519"
|
|
@@ -3250,6 +3254,10 @@ var de = {
|
|
|
3250
3254
|
text: "Die Diskussion konnte nicht geladen werden.",
|
|
3251
3255
|
source: "bac34014"
|
|
3252
3256
|
},
|
|
3257
|
+
"app.client.projectComments.discussionDeleted": {
|
|
3258
|
+
text: "Diskussion gelöscht",
|
|
3259
|
+
source: "156ebf8c"
|
|
3260
|
+
},
|
|
3253
3261
|
"app.client.projectComments.discussionNoLongerInView": {
|
|
3254
3262
|
text: "Diese Diskussion gehört nicht mehr zu dieser Ansicht.",
|
|
3255
3263
|
source: "12e3b200"
|
|
@@ -4053,6 +4061,30 @@ var de = {
|
|
|
4053
4061
|
text: "Kommentar",
|
|
4054
4062
|
source: "984f9ffe"
|
|
4055
4063
|
},
|
|
4064
|
+
"comments.commentThread.commentActions": {
|
|
4065
|
+
text: "Kommentaraktionen",
|
|
4066
|
+
source: "ebed7451"
|
|
4067
|
+
},
|
|
4068
|
+
"comments.commentThread.confirmDeleteComment": {
|
|
4069
|
+
text: "Diesen Kommentar löschen?",
|
|
4070
|
+
source: "46eacc70"
|
|
4071
|
+
},
|
|
4072
|
+
"comments.commentThread.confirmDeleteDiscussion": {
|
|
4073
|
+
text: "Diese Diskussion löschen?",
|
|
4074
|
+
source: "860d22bf"
|
|
4075
|
+
},
|
|
4076
|
+
"comments.commentThread.delete": {
|
|
4077
|
+
text: "Löschen",
|
|
4078
|
+
source: "5797ea6a"
|
|
4079
|
+
},
|
|
4080
|
+
"comments.commentThread.deleteComment": {
|
|
4081
|
+
text: "Kommentar löschen",
|
|
4082
|
+
source: "d8c741d3"
|
|
4083
|
+
},
|
|
4084
|
+
"comments.commentThread.deleteDiscussion": {
|
|
4085
|
+
text: "Diskussion löschen",
|
|
4086
|
+
source: "af680606"
|
|
4087
|
+
},
|
|
4056
4088
|
"comments.commentThread.leaveCommentPlaceholder": {
|
|
4057
4089
|
text: "Kommentar schreiben…",
|
|
4058
4090
|
source: "98a1ef74"
|
|
@@ -7751,11 +7783,13 @@ var en = {
|
|
|
7751
7783
|
"app.client.projectComments.adapterDoesNotSupportOperation": "The comment adapter does not support this operation.",
|
|
7752
7784
|
"app.client.projectComments.adapterUnavailable": "The comment adapter is unavailable.",
|
|
7753
7785
|
"app.client.projectComments.budUndidCommentChange": "Bud undid a comment change",
|
|
7786
|
+
"app.client.projectComments.commentDeleted": "Comment deleted",
|
|
7754
7787
|
"app.client.projectComments.commentSaved": "Comment saved",
|
|
7755
7788
|
"app.client.projectComments.commentWriteNotConfirmed": "The comment write was not confirmed.",
|
|
7756
7789
|
"app.client.projectComments.commentsSynced": "Comments synced",
|
|
7757
7790
|
"app.client.projectComments.couldNotLoadComments": "Could not load comments.",
|
|
7758
7791
|
"app.client.projectComments.couldNotLoadDiscussion": "Could not load the discussion.",
|
|
7792
|
+
"app.client.projectComments.discussionDeleted": "Discussion deleted",
|
|
7759
7793
|
"app.client.projectComments.discussionNoLongerInView": "This discussion is no longer part of this view.",
|
|
7760
7794
|
"app.client.projectComments.loadCommentsBeforeSaving": "Load comments before saving.",
|
|
7761
7795
|
"app.client.projectComments.refreshBeforeTryingAgain": "The comment write could not be confirmed. Refresh before trying again.",
|
|
@@ -7977,6 +8011,12 @@ var en = {
|
|
|
7977
8011
|
"comments.commentPins.detachedTitle": "{name} · Its element is no longer on the page",
|
|
7978
8012
|
"comments.commentThread.cancel": "Cancel",
|
|
7979
8013
|
"comments.commentThread.comment": "Comment",
|
|
8014
|
+
"comments.commentThread.commentActions": "Comment actions",
|
|
8015
|
+
"comments.commentThread.confirmDeleteComment": "Delete this comment?",
|
|
8016
|
+
"comments.commentThread.confirmDeleteDiscussion": "Delete this discussion?",
|
|
8017
|
+
"comments.commentThread.delete": "Delete",
|
|
8018
|
+
"comments.commentThread.deleteComment": "Delete comment",
|
|
8019
|
+
"comments.commentThread.deleteDiscussion": "Delete discussion",
|
|
7980
8020
|
"comments.commentThread.leaveCommentPlaceholder": "Leave a comment…",
|
|
7981
8021
|
"comments.commentThread.loadingDiscussion": "Loading discussion…",
|
|
7982
8022
|
"comments.commentThread.openDiscussion": "Open discussion",
|
|
@@ -24192,131 +24232,202 @@ function Breadcrumb(handle) {
|
|
|
24192
24232
|
};
|
|
24193
24233
|
}
|
|
24194
24234
|
//#endregion
|
|
24195
|
-
//#region
|
|
24196
|
-
|
|
24197
|
-
|
|
24198
|
-
|
|
24199
|
-
|
|
24200
|
-
|
|
24201
|
-
|
|
24202
|
-
return () => {
|
|
24203
|
-
let { class: className, type = "button", ...props } = handle.props;
|
|
24204
|
-
let attributes = ariaAttributes(props);
|
|
24205
|
-
return /* @__PURE__ */ jsx("button", {
|
|
24206
|
-
...attributes,
|
|
24207
|
-
type,
|
|
24208
|
-
class: ["bud-headless-button", className].filter(Boolean).join(" ")
|
|
24209
|
-
});
|
|
24235
|
+
//#region ../../node_modules/.pnpm/@remix-run+component@1.0.0_patch_hash=ed95ce6ac654c31698f27fd52f980c5f1d3e725ba0116b6d666a9b6b3a67016b/node_modules/@remix-run/component/dist/runtime/core/vnode.js
|
|
24236
|
+
function createRemixElement(type, props, key) {
|
|
24237
|
+
return {
|
|
24238
|
+
$rmx: true,
|
|
24239
|
+
key,
|
|
24240
|
+
props: normalizeElementProps(props),
|
|
24241
|
+
type
|
|
24210
24242
|
};
|
|
24211
24243
|
}
|
|
24244
|
+
function isRemixElement(node) {
|
|
24245
|
+
if (typeof node !== "object" || node === null) return false;
|
|
24246
|
+
let type = Reflect.get(node, "type");
|
|
24247
|
+
let props = Reflect.get(node, "props");
|
|
24248
|
+
return Reflect.get(node, "$rmx") === true && (typeof type === "string" || typeof type === "function") && typeof props === "object" && props !== null;
|
|
24249
|
+
}
|
|
24250
|
+
function normalizeElementProps(props) {
|
|
24251
|
+
if (!props) return {};
|
|
24252
|
+
if (!("mix" in props)) return props;
|
|
24253
|
+
if (isNormalizedMix(props.mix)) return props;
|
|
24254
|
+
let { mix, ...rest } = props;
|
|
24255
|
+
let normalizedMix = normalizeMixValue(mix);
|
|
24256
|
+
return normalizedMix === void 0 ? rest : {
|
|
24257
|
+
...rest,
|
|
24258
|
+
mix: normalizedMix
|
|
24259
|
+
};
|
|
24260
|
+
}
|
|
24261
|
+
function isNormalizedMix(mix) {
|
|
24262
|
+
if (!Array.isArray(mix) || mix.length === 0) return false;
|
|
24263
|
+
for (let i = 0; i < mix.length; i++) {
|
|
24264
|
+
let item = mix[i];
|
|
24265
|
+
if (!item || Array.isArray(item)) return false;
|
|
24266
|
+
}
|
|
24267
|
+
return true;
|
|
24268
|
+
}
|
|
24269
|
+
function normalizeMixValue(mix) {
|
|
24270
|
+
if (!mix) return void 0;
|
|
24271
|
+
let normalizedMix = [];
|
|
24272
|
+
flattenMixValue(mix, normalizedMix);
|
|
24273
|
+
return normalizedMix.length === 0 ? void 0 : normalizedMix;
|
|
24274
|
+
}
|
|
24275
|
+
function flattenMixValue(mix, out) {
|
|
24276
|
+
if (!mix) return;
|
|
24277
|
+
if (!Array.isArray(mix)) {
|
|
24278
|
+
out.push(mix);
|
|
24279
|
+
return;
|
|
24280
|
+
}
|
|
24281
|
+
for (let item of mix) flattenMixValue(item, out);
|
|
24282
|
+
}
|
|
24212
24283
|
//#endregion
|
|
24213
|
-
//#region
|
|
24214
|
-
|
|
24215
|
-
|
|
24216
|
-
* @param name - The author's name.
|
|
24217
|
-
* @returns One or two capital letters, or `?` for an empty name.
|
|
24218
|
-
*/
|
|
24219
|
-
function commentInitials(name) {
|
|
24220
|
-
let parts = name.trim().split(/\s+/u).filter(Boolean);
|
|
24221
|
-
return `${parts[0]?.[0] ?? "?"}${parts.length > 1 ? parts.at(-1)[0] : ""}`.toUpperCase();
|
|
24284
|
+
//#region ../../node_modules/.pnpm/@remix-run+component@1.0.0_patch_hash=ed95ce6ac654c31698f27fd52f980c5f1d3e725ba0116b6d666a9b6b3a67016b/node_modules/@remix-run/component/dist/runtime/jsx.js
|
|
24285
|
+
function jsx$1(type, props, key) {
|
|
24286
|
+
return createRemixElement(type, props, key);
|
|
24222
24287
|
}
|
|
24288
|
+
//#endregion
|
|
24289
|
+
//#region ../../node_modules/.pnpm/@remix-run+component@1.0.0_patch_hash=ed95ce6ac654c31698f27fd52f980c5f1d3e725ba0116b6d666a9b6b3a67016b/node_modules/@remix-run/component/dist/runtime/invariant.js
|
|
24223
24290
|
/**
|
|
24224
|
-
*
|
|
24225
|
-
*
|
|
24226
|
-
*
|
|
24291
|
+
* Use this when framework code is incorrect, indicating an internal bug rather
|
|
24292
|
+
* than application code error.
|
|
24293
|
+
*
|
|
24294
|
+
* @param assertion The value to check for truthiness
|
|
24295
|
+
* @param message Optional message to include in the error
|
|
24227
24296
|
*/
|
|
24228
|
-
function
|
|
24229
|
-
let
|
|
24230
|
-
|
|
24231
|
-
|
|
24297
|
+
function invariant(assertion, message) {
|
|
24298
|
+
let prefix = "Framework invariant";
|
|
24299
|
+
if (assertion) return;
|
|
24300
|
+
throw new Error(message ? `${prefix}: ${message}` : prefix);
|
|
24232
24301
|
}
|
|
24233
24302
|
//#endregion
|
|
24234
|
-
//#region
|
|
24303
|
+
//#region ../../node_modules/.pnpm/@remix-run+component@1.0.0_patch_hash=ed95ce6ac654c31698f27fd52f980c5f1d3e725ba0116b6d666a9b6b3a67016b/node_modules/@remix-run/component/dist/runtime/core/children.js
|
|
24304
|
+
function normalizeChildren(children) {
|
|
24305
|
+
for (let i = 0; i < children.length; i++) if (Array.isArray(children[i])) return children.flat(Infinity);
|
|
24306
|
+
return children;
|
|
24307
|
+
}
|
|
24308
|
+
function assertRemixNodes(values) {
|
|
24309
|
+
for (let value of values) invariant(isRemixNode(value), "Invalid child node");
|
|
24310
|
+
}
|
|
24311
|
+
function isRemixNode(value) {
|
|
24312
|
+
if (value == null) return true;
|
|
24313
|
+
let type = typeof value;
|
|
24314
|
+
if (type === "string" || type === "number" || type === "bigint" || type === "boolean") return true;
|
|
24315
|
+
if (isRemixElement(value)) return true;
|
|
24316
|
+
if (!Array.isArray(value)) return false;
|
|
24317
|
+
for (let child of value) if (!isRemixNode(child)) return false;
|
|
24318
|
+
return true;
|
|
24319
|
+
}
|
|
24320
|
+
//#endregion
|
|
24321
|
+
//#region ../../node_modules/.pnpm/@remix-run+component@1.0.0_patch_hash=ed95ce6ac654c31698f27fd52f980c5f1d3e725ba0116b6d666a9b6b3a67016b/node_modules/@remix-run/component/dist/runtime/mixins/mixin.js
|
|
24235
24322
|
/**
|
|
24236
|
-
*
|
|
24237
|
-
*
|
|
24238
|
-
* @
|
|
24323
|
+
* Creates a typed mixin factory that can be passed through the `mix` prop.
|
|
24324
|
+
*
|
|
24325
|
+
* @param type Mixin setup function.
|
|
24326
|
+
* @returns A function that captures mixin arguments and returns a descriptor.
|
|
24239
24327
|
*/
|
|
24240
|
-
function
|
|
24241
|
-
return () => {
|
|
24242
|
-
|
|
24243
|
-
|
|
24244
|
-
|
|
24245
|
-
weight: "medium",
|
|
24246
|
-
class: `flex shrink-0 items-center justify-center rounded-full text-white ${compact ? "size-5" : "size-6"} ${className}`,
|
|
24247
|
-
title: author.name,
|
|
24248
|
-
"data-testid": "comment-avatar",
|
|
24249
|
-
style: { backgroundColor: `oklch(0.55 0.14 ${commentAuthorHue(author.id)})` },
|
|
24250
|
-
children: /* @__PURE__ */ jsx("span", {
|
|
24251
|
-
class: compact ? "scale-[0.833]" : void 0,
|
|
24252
|
-
children: commentInitials(author.name)
|
|
24253
|
-
})
|
|
24254
|
-
});
|
|
24255
|
-
};
|
|
24328
|
+
function createMixin(type) {
|
|
24329
|
+
return (...args) => ({
|
|
24330
|
+
type,
|
|
24331
|
+
args
|
|
24332
|
+
});
|
|
24256
24333
|
}
|
|
24257
24334
|
//#endregion
|
|
24258
|
-
//#region
|
|
24259
|
-
var
|
|
24260
|
-
|
|
24261
|
-
|
|
24262
|
-
|
|
24335
|
+
//#region ../../node_modules/.pnpm/@remix-run+component@1.0.0_patch_hash=ed95ce6ac654c31698f27fd52f980c5f1d3e725ba0116b6d666a9b6b3a67016b/node_modules/@remix-run/component/dist/runtime/mixins/on-mixin.js
|
|
24336
|
+
var onMixinType = (handle) => {
|
|
24337
|
+
let currentHandler = () => {};
|
|
24338
|
+
let currentType = "";
|
|
24339
|
+
let currentCapture = false;
|
|
24340
|
+
let currentNode = null;
|
|
24341
|
+
let reentry = null;
|
|
24342
|
+
let stableHandler = (event) => {
|
|
24343
|
+
reentry?.abort(new DOMException("", "EventReentry"));
|
|
24344
|
+
reentry = new AbortController();
|
|
24345
|
+
currentHandler(event, reentry.signal);
|
|
24346
|
+
};
|
|
24347
|
+
handle.addEventListener("insert", (event) => {
|
|
24348
|
+
currentNode = event.node;
|
|
24349
|
+
currentNode.addEventListener(currentType, stableHandler, currentCapture);
|
|
24350
|
+
});
|
|
24351
|
+
handle.addEventListener("remove", () => {
|
|
24352
|
+
currentNode?.removeEventListener(currentType, stableHandler, currentCapture);
|
|
24353
|
+
currentNode = null;
|
|
24354
|
+
reentry?.abort(new DOMException("", "AbortError"));
|
|
24355
|
+
});
|
|
24356
|
+
return (type, handler, captureBoolean = false) => {
|
|
24357
|
+
let previousType = currentType;
|
|
24358
|
+
let previousCapture = currentCapture;
|
|
24359
|
+
let needsRebind = currentType !== type || currentCapture !== captureBoolean;
|
|
24360
|
+
currentType = type;
|
|
24361
|
+
currentHandler = handler;
|
|
24362
|
+
currentCapture = captureBoolean;
|
|
24363
|
+
if (needsRebind && currentNode) {
|
|
24364
|
+
currentNode.removeEventListener(previousType, stableHandler, previousCapture);
|
|
24365
|
+
currentNode.addEventListener(type, stableHandler, captureBoolean);
|
|
24366
|
+
}
|
|
24367
|
+
return handle.element;
|
|
24368
|
+
};
|
|
24263
24369
|
};
|
|
24370
|
+
var onMixin = createMixin(onMixinType);
|
|
24264
24371
|
/**
|
|
24265
|
-
*
|
|
24266
|
-
*
|
|
24267
|
-
*
|
|
24268
|
-
* @param
|
|
24269
|
-
* @
|
|
24372
|
+
* Attaches a typed DOM event handler through the mixin system.
|
|
24373
|
+
*
|
|
24374
|
+
* @param type Event type to listen for.
|
|
24375
|
+
* @param handler Event handler.
|
|
24376
|
+
* @param captureBoolean Whether to listen during capture.
|
|
24377
|
+
* @returns A mixin descriptor for the target element.
|
|
24270
24378
|
*/
|
|
24271
|
-
function
|
|
24272
|
-
|
|
24273
|
-
function close() {
|
|
24274
|
-
if (handle.props.dismissible !== false) handle.props.onClose();
|
|
24275
|
-
}
|
|
24276
|
-
return () => {
|
|
24277
|
-
let { label, size = "default", initialFocus, children } = handle.props;
|
|
24278
|
-
return /* @__PURE__ */ jsx("dialog", {
|
|
24279
|
-
"aria-label": label,
|
|
24280
|
-
class: `fixed inset-0 m-auto flex max-h-full w-full flex-col overflow-hidden border-0 bg-transparent p-3 text-ink transition-[opacity,scale] duration-200 ease-out backdrop:bg-black/25 backdrop:backdrop-blur-sm backdrop:transition-opacity backdrop:duration-200 starting:scale-[0.97] starting:opacity-0 starting:backdrop:opacity-0 motion-reduce:transition-none motion-reduce:backdrop:transition-none sm:p-6 ${sizes[size]}`,
|
|
24281
|
-
mix: [
|
|
24282
|
-
ref((node, signal) => openDialog(node, signal, initialFocus)),
|
|
24283
|
-
on("cancel", (event) => {
|
|
24284
|
-
event.preventDefault();
|
|
24285
|
-
close();
|
|
24286
|
-
}),
|
|
24287
|
-
on("pointerdown", (event) => {
|
|
24288
|
-
pressedOutside = event.target === event.currentTarget;
|
|
24289
|
-
}),
|
|
24290
|
-
on("click", (event) => {
|
|
24291
|
-
if (pressedOutside && event.target === event.currentTarget) close();
|
|
24292
|
-
})
|
|
24293
|
-
],
|
|
24294
|
-
children
|
|
24295
|
-
});
|
|
24296
|
-
};
|
|
24379
|
+
function on$1(type, handler, captureBoolean) {
|
|
24380
|
+
return onMixin(type, handler, captureBoolean);
|
|
24297
24381
|
}
|
|
24382
|
+
//#endregion
|
|
24383
|
+
//#region ../../node_modules/.pnpm/@remix-run+component@1.0.0_patch_hash=ed95ce6ac654c31698f27fd52f980c5f1d3e725ba0116b6d666a9b6b3a67016b/node_modules/@remix-run/component/dist/runtime/create-element.js
|
|
24298
24384
|
/**
|
|
24299
|
-
*
|
|
24300
|
-
*
|
|
24301
|
-
* @param
|
|
24302
|
-
* @param
|
|
24385
|
+
* Creates a Remix virtual element from a JSX-like call signature.
|
|
24386
|
+
*
|
|
24387
|
+
* @param type Host tag, component function, or mixin host placeholder.
|
|
24388
|
+
* @param props Element props.
|
|
24389
|
+
* @param children Child nodes.
|
|
24390
|
+
* @returns A Remix virtual element.
|
|
24303
24391
|
*/
|
|
24304
|
-
function
|
|
24305
|
-
let
|
|
24306
|
-
|
|
24307
|
-
|
|
24308
|
-
|
|
24309
|
-
|
|
24310
|
-
|
|
24311
|
-
|
|
24312
|
-
|
|
24313
|
-
|
|
24314
|
-
|
|
24315
|
-
|
|
24316
|
-
|
|
24317
|
-
}
|
|
24318
|
-
|
|
24319
|
-
|
|
24392
|
+
function createElement$1(type, props, ...children) {
|
|
24393
|
+
let nextProps = { ...props ?? {} };
|
|
24394
|
+
if (isMixinElementType(type)) {
|
|
24395
|
+
if (children.length > 0) console.error(/* @__PURE__ */ new Error("mixin elements must not receive children"));
|
|
24396
|
+
} else {
|
|
24397
|
+
assertRemixNodes(children);
|
|
24398
|
+
nextProps.children = normalizeChildren(children);
|
|
24399
|
+
}
|
|
24400
|
+
if (nextProps.key != null) {
|
|
24401
|
+
let { key, ...rest } = nextProps;
|
|
24402
|
+
return jsx$1(type, rest, key);
|
|
24403
|
+
}
|
|
24404
|
+
return jsx$1(type, nextProps);
|
|
24405
|
+
}
|
|
24406
|
+
function isMixinElementType(type) {
|
|
24407
|
+
return typeof type === "function" && "__rmxMixinElementType" in type;
|
|
24408
|
+
}
|
|
24409
|
+
//#endregion
|
|
24410
|
+
//#region ../../node_modules/.pnpm/@remix-run+component@1.0.0_patch_hash=ed95ce6ac654c31698f27fd52f980c5f1d3e725ba0116b6d666a9b6b3a67016b/node_modules/@remix-run/component/dist/runtime/mixins/attrs-mixin.js
|
|
24411
|
+
var attrsMixin = createMixin((handle) => (defaults, props) => {
|
|
24412
|
+
let nextProps = props;
|
|
24413
|
+
for (let key in defaults) {
|
|
24414
|
+
if (props[key] !== void 0) continue;
|
|
24415
|
+
if (nextProps === props) nextProps = { ...props };
|
|
24416
|
+
nextProps[key] = defaults[key];
|
|
24417
|
+
}
|
|
24418
|
+
return nextProps === props ? handle.element : createElement$1(handle.element, nextProps);
|
|
24419
|
+
});
|
|
24420
|
+
/**
|
|
24421
|
+
* Applies default host props unless the element already provides them explicitly.
|
|
24422
|
+
*
|
|
24423
|
+
* @param defaults Default props to apply when the element does not already define them.
|
|
24424
|
+
* @returns A mixin descriptor that provides default host props.
|
|
24425
|
+
*/
|
|
24426
|
+
function attrs(defaults) {
|
|
24427
|
+
return attrsMixin(defaults);
|
|
24428
|
+
}
|
|
24429
|
+
//#endregion
|
|
24430
|
+
//#region ../../node_modules/.pnpm/@remix-run+ui@0.12.1/node_modules/@remix-run/ui/dist/anchor.js
|
|
24320
24431
|
var viewportPaddingPx = 16;
|
|
24321
24432
|
function isHorizontalPlacement(placement) {
|
|
24322
24433
|
return placement.startsWith("left") || placement.startsWith("right");
|
|
@@ -24760,548 +24871,238 @@ function anchor$1(floating, anchorTarget, options = {}) {
|
|
|
24760
24871
|
};
|
|
24761
24872
|
}
|
|
24762
24873
|
//#endregion
|
|
24763
|
-
//#region
|
|
24764
|
-
var
|
|
24765
|
-
|
|
24766
|
-
|
|
24767
|
-
|
|
24768
|
-
|
|
24769
|
-
|
|
24770
|
-
|
|
24771
|
-
|
|
24772
|
-
|
|
24773
|
-
|
|
24774
|
-
|
|
24775
|
-
|
|
24776
|
-
|
|
24777
|
-
|
|
24778
|
-
|
|
24779
|
-
|
|
24780
|
-
|
|
24781
|
-
|
|
24782
|
-
|
|
24783
|
-
|
|
24784
|
-
|
|
24785
|
-
|
|
24786
|
-
shift: modifiers.includes("shift"),
|
|
24787
|
-
alt: modifiers.includes("alt")
|
|
24874
|
+
//#region ../../node_modules/.pnpm/@remix-run+ui@0.12.1/node_modules/@remix-run/ui/dist/lib/outside-click.js
|
|
24875
|
+
var onOutsideClick = createMixin((handle) => {
|
|
24876
|
+
let active = false;
|
|
24877
|
+
let handler = () => {};
|
|
24878
|
+
let isInsideTarget = () => false;
|
|
24879
|
+
let stopPropagation = true;
|
|
24880
|
+
handle.addEventListener("insert", (event) => {
|
|
24881
|
+
let node = event.node;
|
|
24882
|
+
node.ownerDocument.addEventListener("click", (event) => {
|
|
24883
|
+
let target = event.target instanceof Node ? event.target : null;
|
|
24884
|
+
if (!active || target && (node.contains(target) || isInsideTarget(target))) return;
|
|
24885
|
+
if (stopPropagation) event.stopPropagation();
|
|
24886
|
+
handler(target);
|
|
24887
|
+
}, {
|
|
24888
|
+
capture: true,
|
|
24889
|
+
signal: handle.signal
|
|
24890
|
+
});
|
|
24891
|
+
});
|
|
24892
|
+
return (nextActive, nextHandler, nextIsInsideTarget = () => false, nextStopPropagation = true) => {
|
|
24893
|
+
active = nextActive;
|
|
24894
|
+
handler = nextHandler;
|
|
24895
|
+
isInsideTarget = nextIsInsideTarget;
|
|
24896
|
+
stopPropagation = nextStopPropagation;
|
|
24788
24897
|
};
|
|
24789
|
-
}
|
|
24790
|
-
/**
|
|
24791
|
-
* The keycaps to show for a combo, in the platform's order and notation.
|
|
24792
|
-
* @param combo - Modifiers and a key joined by `+`.
|
|
24793
|
-
* @param apple - Whether to use Apple symbols; detected from the browser by default.
|
|
24794
|
-
* @returns One label per key.
|
|
24795
|
-
*/
|
|
24796
|
-
function shortcutKeys(combo, apple = isApple()) {
|
|
24797
|
-
let { key, mod, shift, alt } = parseShortcut(combo);
|
|
24798
|
-
let label = symbols[key.toLowerCase()] ?? (key.length === 1 ? key.toUpperCase() : key);
|
|
24799
|
-
if (apple) return [
|
|
24800
|
-
alt && "⌥",
|
|
24801
|
-
shift && "⇧",
|
|
24802
|
-
mod && "⌘",
|
|
24803
|
-
label
|
|
24804
|
-
].filter((part) => part !== false);
|
|
24805
|
-
return [
|
|
24806
|
-
mod && "Ctrl",
|
|
24807
|
-
alt && "Alt",
|
|
24808
|
-
shift && "Shift",
|
|
24809
|
-
label
|
|
24810
|
-
].filter((part) => part !== false);
|
|
24811
|
-
}
|
|
24812
|
-
function isApple() {
|
|
24813
|
-
return typeof navigator !== "undefined" && /mac|iphone|ipad|ipod/i.test(navigator.platform);
|
|
24814
|
-
}
|
|
24898
|
+
});
|
|
24815
24899
|
//#endregion
|
|
24816
|
-
//#region
|
|
24817
|
-
var
|
|
24818
|
-
|
|
24819
|
-
|
|
24820
|
-
|
|
24821
|
-
|
|
24822
|
-
|
|
24823
|
-
|
|
24824
|
-
|
|
24825
|
-
|
|
24826
|
-
|
|
24827
|
-
|
|
24828
|
-
|
|
24829
|
-
|
|
24830
|
-
|
|
24831
|
-
|
|
24832
|
-
|
|
24833
|
-
|
|
24834
|
-
|
|
24835
|
-
let reveal = () => {
|
|
24836
|
-
open = true;
|
|
24837
|
-
handle.update();
|
|
24900
|
+
//#region ../../node_modules/.pnpm/@remix-run+ui@0.12.1/node_modules/@remix-run/ui/dist/lib/scroll-lock.js
|
|
24901
|
+
var scrollLocks = /* @__PURE__ */ new WeakMap();
|
|
24902
|
+
function lockScroll(targetDocument = globalThis.document) {
|
|
24903
|
+
if (!targetDocument?.body || !targetDocument.defaultView) return () => {};
|
|
24904
|
+
let document = targetDocument;
|
|
24905
|
+
let documentElement = document.documentElement;
|
|
24906
|
+
let view = document.defaultView;
|
|
24907
|
+
let state = scrollLocks.get(document);
|
|
24908
|
+
if (!state) {
|
|
24909
|
+
let scrollX = view.scrollX;
|
|
24910
|
+
let scrollY = view.scrollY;
|
|
24911
|
+
let scrollbarWidth = documentElement.clientWidth > 0 ? Math.max(view.innerWidth - documentElement.clientWidth, 0) : 0;
|
|
24912
|
+
let computedScrollbarGutter = view.getComputedStyle(documentElement).scrollbarGutter;
|
|
24913
|
+
state = {
|
|
24914
|
+
count: 0,
|
|
24915
|
+
documentOverflow: documentElement.style.overflow,
|
|
24916
|
+
documentScrollbarGutter: documentElement.style.scrollbarGutter,
|
|
24917
|
+
scrollX,
|
|
24918
|
+
scrollY
|
|
24838
24919
|
};
|
|
24839
|
-
|
|
24840
|
-
|
|
24841
|
-
|
|
24842
|
-
function hide() {
|
|
24843
|
-
clearTimeout(timer);
|
|
24844
|
-
if (!open) return;
|
|
24845
|
-
open = false;
|
|
24846
|
-
closedAt = Date.now();
|
|
24847
|
-
handle.update();
|
|
24920
|
+
documentElement.style.overflow = "hidden";
|
|
24921
|
+
if (scrollbarWidth > 0 && computedScrollbarGutter === "auto") documentElement.style.scrollbarGutter = "stable";
|
|
24922
|
+
scrollLocks.set(document, state);
|
|
24848
24923
|
}
|
|
24849
|
-
|
|
24850
|
-
|
|
24851
|
-
|
|
24852
|
-
|
|
24853
|
-
|
|
24854
|
-
|
|
24855
|
-
|
|
24856
|
-
|
|
24857
|
-
|
|
24858
|
-
|
|
24859
|
-
|
|
24860
|
-
|
|
24861
|
-
|
|
24862
|
-
|
|
24863
|
-
}),
|
|
24864
|
-
on("pointerleave", hide),
|
|
24865
|
-
on("pointerdown", hide),
|
|
24866
|
-
on("focusin", (event) => {
|
|
24867
|
-
if (event.target.dataset.focusMethod === "keyboard") show(true);
|
|
24868
|
-
}),
|
|
24869
|
-
on("focusout", hide)
|
|
24870
|
-
],
|
|
24871
|
-
children: handle.props.children
|
|
24872
|
-
}), /* @__PURE__ */ jsxs("div", {
|
|
24873
|
-
id,
|
|
24874
|
-
role: "tooltip",
|
|
24875
|
-
popover: "manual",
|
|
24876
|
-
class: "bud-tooltip pointer-events-none m-0 inline-flex items-center gap-1.5 rounded-[10px] px-2 py-1.5 transition-[opacity,scale] duration-100 ease-out starting:scale-95 starting:opacity-0 motion-reduce:transition-none",
|
|
24877
|
-
mix: ref((node, signal) => {
|
|
24878
|
-
if (!open || !trigger) return;
|
|
24879
|
-
node.showPopover();
|
|
24880
|
-
release = anchor$1(node, trigger, {
|
|
24881
|
-
placement: handle.props.placement ?? "top",
|
|
24882
|
-
offset: 6
|
|
24883
|
-
});
|
|
24884
|
-
signal.addEventListener("abort", () => {
|
|
24885
|
-
release();
|
|
24886
|
-
if (node.isConnected && node.matches(":popover-open")) node.hidePopover();
|
|
24887
|
-
}, { once: true });
|
|
24888
|
-
}),
|
|
24889
|
-
hidden: !open,
|
|
24890
|
-
children: [/* @__PURE__ */ jsx(Text, {
|
|
24891
|
-
variant: "ui-caption",
|
|
24892
|
-
weight: "medium",
|
|
24893
|
-
children: handle.props.label
|
|
24894
|
-
}), handle.props.shortcut ? /* @__PURE__ */ jsx(Kbd, { shortcut: handle.props.shortcut }) : null]
|
|
24895
|
-
}, open ? "open" : "closed")] });
|
|
24924
|
+
state.count++;
|
|
24925
|
+
let unlocked = false;
|
|
24926
|
+
return () => {
|
|
24927
|
+
if (unlocked) return;
|
|
24928
|
+
unlocked = true;
|
|
24929
|
+
let currentState = scrollLocks.get(document);
|
|
24930
|
+
if (!currentState) return;
|
|
24931
|
+
currentState.count--;
|
|
24932
|
+
if (currentState.count > 0) return;
|
|
24933
|
+
scrollLocks.delete(document);
|
|
24934
|
+
documentElement.style.overflow = currentState.documentOverflow;
|
|
24935
|
+
documentElement.style.scrollbarGutter = currentState.documentScrollbarGutter;
|
|
24936
|
+
view.scrollTo(currentState.scrollX, currentState.scrollY);
|
|
24937
|
+
};
|
|
24896
24938
|
}
|
|
24897
|
-
|
|
24898
|
-
|
|
24899
|
-
|
|
24900
|
-
|
|
24901
|
-
|
|
24902
|
-
|
|
24903
|
-
|
|
24904
|
-
|
|
24905
|
-
children: shortcutKeys(handle.props.shortcut).map((key, index) => /* @__PURE__ */ jsx(Text, {
|
|
24906
|
-
as: "kbd",
|
|
24907
|
-
variant: "kbd",
|
|
24908
|
-
class: "inline-flex h-4.5 min-w-4.5 items-center justify-center rounded-[5px] bg-current/12 px-1 opacity-80",
|
|
24909
|
-
"data-slot": "kbd",
|
|
24910
|
-
children: key
|
|
24911
|
-
}, index))
|
|
24939
|
+
//#endregion
|
|
24940
|
+
//#region ../../node_modules/.pnpm/@remix-run+ui@0.12.1/node_modules/@remix-run/ui/dist/popover.js
|
|
24941
|
+
function PopoverProvider(handle) {
|
|
24942
|
+
handle.context.set({
|
|
24943
|
+
hideFocusTarget: null,
|
|
24944
|
+
showFocusTarget: null,
|
|
24945
|
+
surface: null,
|
|
24946
|
+
anchor: null
|
|
24912
24947
|
});
|
|
24948
|
+
return () => handle.props.children;
|
|
24913
24949
|
}
|
|
24914
|
-
|
|
24915
|
-
|
|
24916
|
-
|
|
24917
|
-
|
|
24918
|
-
|
|
24919
|
-
|
|
24920
|
-
|
|
24921
|
-
|
|
24922
|
-
return () => {
|
|
24923
|
-
let { icon, label, active, surface, size = "default", iconSize = size === "small" ? 14 : 16, tooltip, shortcut, class: className = "", ...props } = handle.props;
|
|
24924
|
-
let button = /* @__PURE__ */ jsx(HeadlessButton, {
|
|
24925
|
-
...props,
|
|
24926
|
-
"aria-label": label,
|
|
24927
|
-
title: tooltip ? void 0 : props.title ?? label,
|
|
24928
|
-
"aria-pressed": props["aria-pressed"] ?? active,
|
|
24929
|
-
"data-active": active,
|
|
24930
|
-
class: `bud-interaction ${surface ? "bud-control" : ""} flex shrink-0 items-center justify-center ${size === "small" ? "size-6 rounded-md" : "size-control rounded-lg"} ${className}`,
|
|
24931
|
-
children: /* @__PURE__ */ jsx(Icon, {
|
|
24932
|
-
name: icon,
|
|
24933
|
-
size: iconSize
|
|
24934
|
-
})
|
|
24950
|
+
var anchorMixin = createMixin((handle) => {
|
|
24951
|
+
let context = handle.context.get(PopoverProvider);
|
|
24952
|
+
return (options) => {
|
|
24953
|
+
handle.queueTask((node) => {
|
|
24954
|
+
context.anchor = {
|
|
24955
|
+
target: node,
|
|
24956
|
+
options
|
|
24957
|
+
};
|
|
24935
24958
|
});
|
|
24936
|
-
return tooltip ? /* @__PURE__ */ jsx(Tooltip, {
|
|
24937
|
-
label,
|
|
24938
|
-
shortcut,
|
|
24939
|
-
children: button
|
|
24940
|
-
}) : button;
|
|
24941
24959
|
};
|
|
24960
|
+
});
|
|
24961
|
+
function anchorContains(anchor, target) {
|
|
24962
|
+
return anchor?.target instanceof HTMLElement && anchor.target.contains(target);
|
|
24942
24963
|
}
|
|
24943
|
-
|
|
24944
|
-
|
|
24945
|
-
|
|
24946
|
-
|
|
24947
|
-
|
|
24948
|
-
|
|
24949
|
-
|
|
24950
|
-
*/
|
|
24951
|
-
function scrollFade(axis = "x") {
|
|
24952
|
-
return ref((node, signal) => {
|
|
24953
|
-
let update = () => {
|
|
24954
|
-
if (axis === "x" ? node.scrollWidth > node.clientWidth + 1 : node.scrollHeight > node.clientHeight + 1) node.dataset.scrollFade = axis;
|
|
24955
|
-
else delete node.dataset.scrollFade;
|
|
24956
|
-
};
|
|
24957
|
-
let resize = new ResizeObserver(update);
|
|
24958
|
-
let mutation = new MutationObserver(update);
|
|
24959
|
-
resize.observe(node);
|
|
24960
|
-
mutation.observe(node, {
|
|
24961
|
-
childList: true,
|
|
24962
|
-
subtree: true,
|
|
24963
|
-
characterData: true
|
|
24964
|
-
});
|
|
24965
|
-
update();
|
|
24964
|
+
var surfaceMixin = createMixin((handle) => {
|
|
24965
|
+
let openProp = false;
|
|
24966
|
+
let cleanupAnchor = () => {};
|
|
24967
|
+
let unlockScroll = () => {};
|
|
24968
|
+
let context = handle.context.get(PopoverProvider);
|
|
24969
|
+
handle.queueTask((node, signal) => {
|
|
24970
|
+
context.surface = node;
|
|
24966
24971
|
signal.addEventListener("abort", () => {
|
|
24967
|
-
|
|
24968
|
-
|
|
24969
|
-
}, { once: true });
|
|
24972
|
+
if (context.surface === node) context.surface = null;
|
|
24973
|
+
});
|
|
24970
24974
|
});
|
|
24971
|
-
|
|
24972
|
-
|
|
24973
|
-
|
|
24974
|
-
|
|
24975
|
-
|
|
24976
|
-
|
|
24977
|
-
|
|
24978
|
-
|
|
24979
|
-
|
|
24980
|
-
|
|
24981
|
-
|
|
24982
|
-
|
|
24983
|
-
|
|
24984
|
-
|
|
24985
|
-
|
|
24986
|
-
|
|
24987
|
-
|
|
24988
|
-
|
|
24975
|
+
return (options) => {
|
|
24976
|
+
let wasOpen = openProp;
|
|
24977
|
+
openProp = options.open;
|
|
24978
|
+
handle.queueTask(async (node) => {
|
|
24979
|
+
if (openProp && !wasOpen) node.showPopover();
|
|
24980
|
+
else if (!openProp && wasOpen) node.hidePopover();
|
|
24981
|
+
});
|
|
24982
|
+
return [
|
|
24983
|
+
attrs({ popover: "manual" }),
|
|
24984
|
+
on$1("beforetoggle", (event) => {
|
|
24985
|
+
if (event.newState === "open") {
|
|
24986
|
+
let anchor = context.anchor;
|
|
24987
|
+
if (!anchor) throw new Error("popover.surface() requires a registered anchor before opening");
|
|
24988
|
+
cleanupAnchor = anchor$1(event.currentTarget, anchor.target, anchor.options);
|
|
24989
|
+
unlockScroll = lockScroll();
|
|
24990
|
+
} else if (event.newState === "closed") {
|
|
24991
|
+
cleanupAnchor();
|
|
24992
|
+
unlockScroll();
|
|
24993
|
+
}
|
|
24994
|
+
}),
|
|
24995
|
+
on$1("toggle", async (event) => {
|
|
24996
|
+
if (event.newState === "open") context.showFocusTarget?.focus();
|
|
24997
|
+
else if (event.newState === "closed" && options.restoreFocusOnHide !== false) context.hideFocusTarget?.focus();
|
|
24998
|
+
}),
|
|
24999
|
+
on$1("keydown", (event) => {
|
|
25000
|
+
if (event.key === "Escape") {
|
|
25001
|
+
event.preventDefault();
|
|
25002
|
+
options.onHide({ reason: "escape-key" });
|
|
25003
|
+
}
|
|
25004
|
+
}),
|
|
25005
|
+
onOutsideClick(openProp, (target) => {
|
|
25006
|
+
options.onHide({
|
|
25007
|
+
reason: "outside-click",
|
|
25008
|
+
target
|
|
25009
|
+
});
|
|
25010
|
+
}, (target) => options.closeOnAnchorClick === false && anchorContains(context.anchor, target), options.stopOutsideClickPropagation ?? true)
|
|
25011
|
+
];
|
|
25012
|
+
};
|
|
25013
|
+
});
|
|
25014
|
+
var focusOnShowMixin = createMixin((handle) => {
|
|
25015
|
+
handle.addEventListener("insert", (event) => {
|
|
25016
|
+
let context = handle.context.get(PopoverProvider);
|
|
25017
|
+
context.showFocusTarget = event.node;
|
|
25018
|
+
});
|
|
25019
|
+
});
|
|
25020
|
+
var focusOnHideMixin = createMixin((handle) => {
|
|
25021
|
+
handle.addEventListener("insert", (event) => {
|
|
25022
|
+
let context = handle.context.get(PopoverProvider);
|
|
25023
|
+
context.hideFocusTarget = event.node;
|
|
24989
25024
|
});
|
|
25025
|
+
});
|
|
25026
|
+
var Context$1 = PopoverProvider;
|
|
25027
|
+
var anchor = anchorMixin;
|
|
25028
|
+
var surface = surfaceMixin;
|
|
25029
|
+
var focusOnHide = focusOnHideMixin;
|
|
25030
|
+
var focusOnShow = focusOnShowMixin;
|
|
25031
|
+
//#endregion
|
|
25032
|
+
//#region ../../node_modules/.pnpm/@remix-run+ui@0.12.1/node_modules/@remix-run/ui/dist/lib/typeahead.js
|
|
25033
|
+
var HIDDEN_TYPEAHEAD_TIMEOUT = 750;
|
|
25034
|
+
var hiddenTypeahead = createMixin((handle) => {
|
|
25035
|
+
let text = "";
|
|
25036
|
+
let timeoutId = 0;
|
|
25037
|
+
function clearTypeahead() {
|
|
25038
|
+
clearTimeout(timeoutId);
|
|
25039
|
+
timeoutId = 0;
|
|
25040
|
+
text = "";
|
|
25041
|
+
}
|
|
25042
|
+
function updateTypeahead(nextText, onTypeahead) {
|
|
25043
|
+
text = nextText;
|
|
25044
|
+
onTypeahead(text);
|
|
25045
|
+
}
|
|
25046
|
+
handle.addEventListener("remove", clearTypeahead);
|
|
25047
|
+
return (onTypeahead) => [on$1("focusout", (event) => {
|
|
25048
|
+
if (event.relatedTarget instanceof Node && event.currentTarget.contains(event.relatedTarget)) return;
|
|
25049
|
+
clearTypeahead();
|
|
25050
|
+
}), on$1("keydown", (event) => {
|
|
25051
|
+
if (event.key.length === 1 && !event.ctrlKey && !event.altKey && !event.metaKey) {
|
|
25052
|
+
clearTimeout(timeoutId);
|
|
25053
|
+
updateTypeahead(text + event.key.toLowerCase(), onTypeahead);
|
|
25054
|
+
timeoutId = window.setTimeout(clearTypeahead, HIDDEN_TYPEAHEAD_TIMEOUT);
|
|
25055
|
+
} else if (event.key === "Escape") clearTypeahead();
|
|
25056
|
+
else if (event.key === "Backspace" && text.length > 0) {
|
|
25057
|
+
clearTimeout(timeoutId);
|
|
25058
|
+
updateTypeahead(text.slice(0, -1), onTypeahead);
|
|
25059
|
+
timeoutId = window.setTimeout(clearTypeahead, HIDDEN_TYPEAHEAD_TIMEOUT);
|
|
25060
|
+
}
|
|
25061
|
+
})];
|
|
25062
|
+
});
|
|
25063
|
+
function itemMatchesSearchText(item, text, getSearchValues) {
|
|
25064
|
+
let values = getSearchValues(item);
|
|
25065
|
+
let searchValues = Array.isArray(values) ? values : [values];
|
|
25066
|
+
let normalizedText = text.toLowerCase();
|
|
25067
|
+
return searchValues.some((value) => value.toLowerCase().startsWith(normalizedText));
|
|
25068
|
+
}
|
|
25069
|
+
function matchNextItemBySearchText(text, items, options) {
|
|
25070
|
+
if (text === "") return null;
|
|
25071
|
+
for (let offset = 1; offset <= items.length; offset++) {
|
|
25072
|
+
let item = items[(options.fromIndex + offset + items.length) % items.length];
|
|
25073
|
+
if (itemMatchesSearchText(item, text, options.getSearchValues)) return item;
|
|
25074
|
+
}
|
|
25075
|
+
return null;
|
|
24990
25076
|
}
|
|
25077
|
+
//#endregion
|
|
25078
|
+
//#region ../ui/src/lib/headless-button.tsx
|
|
24991
25079
|
/**
|
|
24992
|
-
* A
|
|
24993
|
-
* @param handle - Native
|
|
24994
|
-
* @returns The
|
|
25080
|
+
* A native button with shared interactions; callers own its content and geometry.
|
|
25081
|
+
* @param handle - Native button props, content, and Remix mixins.
|
|
25082
|
+
* @returns The button render function.
|
|
24995
25083
|
*/
|
|
24996
|
-
function
|
|
25084
|
+
function HeadlessButton(handle) {
|
|
24997
25085
|
return () => {
|
|
24998
|
-
let { class: className = "",
|
|
24999
|
-
|
|
25000
|
-
|
|
25001
|
-
|
|
25002
|
-
|
|
25086
|
+
let { class: className, type = "button", ...props } = handle.props;
|
|
25087
|
+
let attributes = ariaAttributes(props);
|
|
25088
|
+
return /* @__PURE__ */ jsx("button", {
|
|
25089
|
+
...attributes,
|
|
25090
|
+
type,
|
|
25091
|
+
class: ["bud-headless-button", className].filter(Boolean).join(" ")
|
|
25003
25092
|
});
|
|
25004
25093
|
};
|
|
25005
25094
|
}
|
|
25006
25095
|
//#endregion
|
|
25007
|
-
//#region
|
|
25008
|
-
|
|
25009
|
-
|
|
25010
|
-
|
|
25011
|
-
|
|
25012
|
-
function publish() {
|
|
25013
|
-
for (let listener of listeners) listener(items);
|
|
25096
|
+
//#region ../../node_modules/.pnpm/@remix-run+ui@0.12.1/node_modules/@remix-run/ui/dist/lib/flash-attribute.js
|
|
25097
|
+
function wait(ms) {
|
|
25098
|
+
return new Promise((resolve) => {
|
|
25099
|
+
setTimeout(resolve, ms);
|
|
25100
|
+
});
|
|
25014
25101
|
}
|
|
25015
|
-
|
|
25016
|
-
|
|
25017
|
-
|
|
25018
|
-
|
|
25019
|
-
* @returns The toast's id, for dismissing it early.
|
|
25020
|
-
*/
|
|
25021
|
-
function toast(title, options = {}) {
|
|
25022
|
-
let id = options.id ?? `toast-${++next}`;
|
|
25023
|
-
items = [{
|
|
25024
|
-
id,
|
|
25025
|
-
title,
|
|
25026
|
-
description: options.description,
|
|
25027
|
-
type: options.type ?? "default",
|
|
25028
|
-
duration: options.duration ?? defaultDuration,
|
|
25029
|
-
removed: false
|
|
25030
|
-
}, ...items.filter((existing) => existing.id !== id)];
|
|
25031
|
-
publish();
|
|
25032
|
-
return id;
|
|
25033
|
-
}
|
|
25034
|
-
toast.success = (title, options = {}) => toast(title, {
|
|
25035
|
-
...options,
|
|
25036
|
-
type: "success"
|
|
25037
|
-
});
|
|
25038
|
-
toast.error = (title, options = {}) => toast(title, {
|
|
25039
|
-
...options,
|
|
25040
|
-
type: "error"
|
|
25041
|
-
});
|
|
25042
|
-
/**
|
|
25043
|
-
* Starts a toast's exit; the Toaster removes it once it has animated out.
|
|
25044
|
-
* @param id - The toast to dismiss; every toast when omitted.
|
|
25045
|
-
*/
|
|
25046
|
-
toast.dismiss = (id) => {
|
|
25047
|
-
items = items.map((item) => id === void 0 || item.id === id ? {
|
|
25048
|
-
...item,
|
|
25049
|
-
removed: true
|
|
25050
|
-
} : item);
|
|
25051
|
-
publish();
|
|
25052
|
-
};
|
|
25053
|
-
//#endregion
|
|
25054
|
-
//#region ../../node_modules/.pnpm/@remix-run+component@1.0.0_patch_hash=ed95ce6ac654c31698f27fd52f980c5f1d3e725ba0116b6d666a9b6b3a67016b/node_modules/@remix-run/component/dist/runtime/core/vnode.js
|
|
25055
|
-
function createRemixElement(type, props, key) {
|
|
25056
|
-
return {
|
|
25057
|
-
$rmx: true,
|
|
25058
|
-
key,
|
|
25059
|
-
props: normalizeElementProps(props),
|
|
25060
|
-
type
|
|
25061
|
-
};
|
|
25062
|
-
}
|
|
25063
|
-
function isRemixElement(node) {
|
|
25064
|
-
if (typeof node !== "object" || node === null) return false;
|
|
25065
|
-
let type = Reflect.get(node, "type");
|
|
25066
|
-
let props = Reflect.get(node, "props");
|
|
25067
|
-
return Reflect.get(node, "$rmx") === true && (typeof type === "string" || typeof type === "function") && typeof props === "object" && props !== null;
|
|
25068
|
-
}
|
|
25069
|
-
function normalizeElementProps(props) {
|
|
25070
|
-
if (!props) return {};
|
|
25071
|
-
if (!("mix" in props)) return props;
|
|
25072
|
-
if (isNormalizedMix(props.mix)) return props;
|
|
25073
|
-
let { mix, ...rest } = props;
|
|
25074
|
-
let normalizedMix = normalizeMixValue(mix);
|
|
25075
|
-
return normalizedMix === void 0 ? rest : {
|
|
25076
|
-
...rest,
|
|
25077
|
-
mix: normalizedMix
|
|
25078
|
-
};
|
|
25079
|
-
}
|
|
25080
|
-
function isNormalizedMix(mix) {
|
|
25081
|
-
if (!Array.isArray(mix) || mix.length === 0) return false;
|
|
25082
|
-
for (let i = 0; i < mix.length; i++) {
|
|
25083
|
-
let item = mix[i];
|
|
25084
|
-
if (!item || Array.isArray(item)) return false;
|
|
25085
|
-
}
|
|
25086
|
-
return true;
|
|
25087
|
-
}
|
|
25088
|
-
function normalizeMixValue(mix) {
|
|
25089
|
-
if (!mix) return void 0;
|
|
25090
|
-
let normalizedMix = [];
|
|
25091
|
-
flattenMixValue(mix, normalizedMix);
|
|
25092
|
-
return normalizedMix.length === 0 ? void 0 : normalizedMix;
|
|
25093
|
-
}
|
|
25094
|
-
function flattenMixValue(mix, out) {
|
|
25095
|
-
if (!mix) return;
|
|
25096
|
-
if (!Array.isArray(mix)) {
|
|
25097
|
-
out.push(mix);
|
|
25098
|
-
return;
|
|
25099
|
-
}
|
|
25100
|
-
for (let item of mix) flattenMixValue(item, out);
|
|
25101
|
-
}
|
|
25102
|
-
//#endregion
|
|
25103
|
-
//#region ../../node_modules/.pnpm/@remix-run+component@1.0.0_patch_hash=ed95ce6ac654c31698f27fd52f980c5f1d3e725ba0116b6d666a9b6b3a67016b/node_modules/@remix-run/component/dist/runtime/jsx.js
|
|
25104
|
-
function jsx$1(type, props, key) {
|
|
25105
|
-
return createRemixElement(type, props, key);
|
|
25106
|
-
}
|
|
25107
|
-
//#endregion
|
|
25108
|
-
//#region ../../node_modules/.pnpm/@remix-run+component@1.0.0_patch_hash=ed95ce6ac654c31698f27fd52f980c5f1d3e725ba0116b6d666a9b6b3a67016b/node_modules/@remix-run/component/dist/runtime/invariant.js
|
|
25109
|
-
/**
|
|
25110
|
-
* Use this when framework code is incorrect, indicating an internal bug rather
|
|
25111
|
-
* than application code error.
|
|
25112
|
-
*
|
|
25113
|
-
* @param assertion The value to check for truthiness
|
|
25114
|
-
* @param message Optional message to include in the error
|
|
25115
|
-
*/
|
|
25116
|
-
function invariant(assertion, message) {
|
|
25117
|
-
let prefix = "Framework invariant";
|
|
25118
|
-
if (assertion) return;
|
|
25119
|
-
throw new Error(message ? `${prefix}: ${message}` : prefix);
|
|
25120
|
-
}
|
|
25121
|
-
//#endregion
|
|
25122
|
-
//#region ../../node_modules/.pnpm/@remix-run+component@1.0.0_patch_hash=ed95ce6ac654c31698f27fd52f980c5f1d3e725ba0116b6d666a9b6b3a67016b/node_modules/@remix-run/component/dist/runtime/core/children.js
|
|
25123
|
-
function normalizeChildren(children) {
|
|
25124
|
-
for (let i = 0; i < children.length; i++) if (Array.isArray(children[i])) return children.flat(Infinity);
|
|
25125
|
-
return children;
|
|
25126
|
-
}
|
|
25127
|
-
function assertRemixNodes(values) {
|
|
25128
|
-
for (let value of values) invariant(isRemixNode(value), "Invalid child node");
|
|
25129
|
-
}
|
|
25130
|
-
function isRemixNode(value) {
|
|
25131
|
-
if (value == null) return true;
|
|
25132
|
-
let type = typeof value;
|
|
25133
|
-
if (type === "string" || type === "number" || type === "bigint" || type === "boolean") return true;
|
|
25134
|
-
if (isRemixElement(value)) return true;
|
|
25135
|
-
if (!Array.isArray(value)) return false;
|
|
25136
|
-
for (let child of value) if (!isRemixNode(child)) return false;
|
|
25137
|
-
return true;
|
|
25138
|
-
}
|
|
25139
|
-
//#endregion
|
|
25140
|
-
//#region ../../node_modules/.pnpm/@remix-run+component@1.0.0_patch_hash=ed95ce6ac654c31698f27fd52f980c5f1d3e725ba0116b6d666a9b6b3a67016b/node_modules/@remix-run/component/dist/runtime/mixins/mixin.js
|
|
25141
|
-
/**
|
|
25142
|
-
* Creates a typed mixin factory that can be passed through the `mix` prop.
|
|
25143
|
-
*
|
|
25144
|
-
* @param type Mixin setup function.
|
|
25145
|
-
* @returns A function that captures mixin arguments and returns a descriptor.
|
|
25146
|
-
*/
|
|
25147
|
-
function createMixin(type) {
|
|
25148
|
-
return (...args) => ({
|
|
25149
|
-
type,
|
|
25150
|
-
args
|
|
25151
|
-
});
|
|
25152
|
-
}
|
|
25153
|
-
//#endregion
|
|
25154
|
-
//#region ../../node_modules/.pnpm/@remix-run+component@1.0.0_patch_hash=ed95ce6ac654c31698f27fd52f980c5f1d3e725ba0116b6d666a9b6b3a67016b/node_modules/@remix-run/component/dist/runtime/mixins/on-mixin.js
|
|
25155
|
-
var onMixinType = (handle) => {
|
|
25156
|
-
let currentHandler = () => {};
|
|
25157
|
-
let currentType = "";
|
|
25158
|
-
let currentCapture = false;
|
|
25159
|
-
let currentNode = null;
|
|
25160
|
-
let reentry = null;
|
|
25161
|
-
let stableHandler = (event) => {
|
|
25162
|
-
reentry?.abort(new DOMException("", "EventReentry"));
|
|
25163
|
-
reentry = new AbortController();
|
|
25164
|
-
currentHandler(event, reentry.signal);
|
|
25165
|
-
};
|
|
25166
|
-
handle.addEventListener("insert", (event) => {
|
|
25167
|
-
currentNode = event.node;
|
|
25168
|
-
currentNode.addEventListener(currentType, stableHandler, currentCapture);
|
|
25169
|
-
});
|
|
25170
|
-
handle.addEventListener("remove", () => {
|
|
25171
|
-
currentNode?.removeEventListener(currentType, stableHandler, currentCapture);
|
|
25172
|
-
currentNode = null;
|
|
25173
|
-
reentry?.abort(new DOMException("", "AbortError"));
|
|
25174
|
-
});
|
|
25175
|
-
return (type, handler, captureBoolean = false) => {
|
|
25176
|
-
let previousType = currentType;
|
|
25177
|
-
let previousCapture = currentCapture;
|
|
25178
|
-
let needsRebind = currentType !== type || currentCapture !== captureBoolean;
|
|
25179
|
-
currentType = type;
|
|
25180
|
-
currentHandler = handler;
|
|
25181
|
-
currentCapture = captureBoolean;
|
|
25182
|
-
if (needsRebind && currentNode) {
|
|
25183
|
-
currentNode.removeEventListener(previousType, stableHandler, previousCapture);
|
|
25184
|
-
currentNode.addEventListener(type, stableHandler, captureBoolean);
|
|
25185
|
-
}
|
|
25186
|
-
return handle.element;
|
|
25187
|
-
};
|
|
25188
|
-
};
|
|
25189
|
-
var onMixin = createMixin(onMixinType);
|
|
25190
|
-
/**
|
|
25191
|
-
* Attaches a typed DOM event handler through the mixin system.
|
|
25192
|
-
*
|
|
25193
|
-
* @param type Event type to listen for.
|
|
25194
|
-
* @param handler Event handler.
|
|
25195
|
-
* @param captureBoolean Whether to listen during capture.
|
|
25196
|
-
* @returns A mixin descriptor for the target element.
|
|
25197
|
-
*/
|
|
25198
|
-
function on$1(type, handler, captureBoolean) {
|
|
25199
|
-
return onMixin(type, handler, captureBoolean);
|
|
25200
|
-
}
|
|
25201
|
-
//#endregion
|
|
25202
|
-
//#region ../../node_modules/.pnpm/@remix-run+component@1.0.0_patch_hash=ed95ce6ac654c31698f27fd52f980c5f1d3e725ba0116b6d666a9b6b3a67016b/node_modules/@remix-run/component/dist/runtime/create-element.js
|
|
25203
|
-
/**
|
|
25204
|
-
* Creates a Remix virtual element from a JSX-like call signature.
|
|
25205
|
-
*
|
|
25206
|
-
* @param type Host tag, component function, or mixin host placeholder.
|
|
25207
|
-
* @param props Element props.
|
|
25208
|
-
* @param children Child nodes.
|
|
25209
|
-
* @returns A Remix virtual element.
|
|
25210
|
-
*/
|
|
25211
|
-
function createElement$1(type, props, ...children) {
|
|
25212
|
-
let nextProps = { ...props ?? {} };
|
|
25213
|
-
if (isMixinElementType(type)) {
|
|
25214
|
-
if (children.length > 0) console.error(/* @__PURE__ */ new Error("mixin elements must not receive children"));
|
|
25215
|
-
} else {
|
|
25216
|
-
assertRemixNodes(children);
|
|
25217
|
-
nextProps.children = normalizeChildren(children);
|
|
25218
|
-
}
|
|
25219
|
-
if (nextProps.key != null) {
|
|
25220
|
-
let { key, ...rest } = nextProps;
|
|
25221
|
-
return jsx$1(type, rest, key);
|
|
25222
|
-
}
|
|
25223
|
-
return jsx$1(type, nextProps);
|
|
25224
|
-
}
|
|
25225
|
-
function isMixinElementType(type) {
|
|
25226
|
-
return typeof type === "function" && "__rmxMixinElementType" in type;
|
|
25227
|
-
}
|
|
25228
|
-
//#endregion
|
|
25229
|
-
//#region ../../node_modules/.pnpm/@remix-run+component@1.0.0_patch_hash=ed95ce6ac654c31698f27fd52f980c5f1d3e725ba0116b6d666a9b6b3a67016b/node_modules/@remix-run/component/dist/runtime/mixins/attrs-mixin.js
|
|
25230
|
-
var attrsMixin = createMixin((handle) => (defaults, props) => {
|
|
25231
|
-
let nextProps = props;
|
|
25232
|
-
for (let key in defaults) {
|
|
25233
|
-
if (props[key] !== void 0) continue;
|
|
25234
|
-
if (nextProps === props) nextProps = { ...props };
|
|
25235
|
-
nextProps[key] = defaults[key];
|
|
25236
|
-
}
|
|
25237
|
-
return nextProps === props ? handle.element : createElement$1(handle.element, nextProps);
|
|
25238
|
-
});
|
|
25239
|
-
/**
|
|
25240
|
-
* Applies default host props unless the element already provides them explicitly.
|
|
25241
|
-
*
|
|
25242
|
-
* @param defaults Default props to apply when the element does not already define them.
|
|
25243
|
-
* @returns A mixin descriptor that provides default host props.
|
|
25244
|
-
*/
|
|
25245
|
-
function attrs(defaults) {
|
|
25246
|
-
return attrsMixin(defaults);
|
|
25247
|
-
}
|
|
25248
|
-
//#endregion
|
|
25249
|
-
//#region ../../node_modules/.pnpm/@remix-run+ui@0.12.1/node_modules/@remix-run/ui/dist/lib/typeahead.js
|
|
25250
|
-
var HIDDEN_TYPEAHEAD_TIMEOUT = 750;
|
|
25251
|
-
var hiddenTypeahead = createMixin((handle) => {
|
|
25252
|
-
let text = "";
|
|
25253
|
-
let timeoutId = 0;
|
|
25254
|
-
function clearTypeahead() {
|
|
25255
|
-
clearTimeout(timeoutId);
|
|
25256
|
-
timeoutId = 0;
|
|
25257
|
-
text = "";
|
|
25258
|
-
}
|
|
25259
|
-
function updateTypeahead(nextText, onTypeahead) {
|
|
25260
|
-
text = nextText;
|
|
25261
|
-
onTypeahead(text);
|
|
25262
|
-
}
|
|
25263
|
-
handle.addEventListener("remove", clearTypeahead);
|
|
25264
|
-
return (onTypeahead) => [on$1("focusout", (event) => {
|
|
25265
|
-
if (event.relatedTarget instanceof Node && event.currentTarget.contains(event.relatedTarget)) return;
|
|
25266
|
-
clearTypeahead();
|
|
25267
|
-
}), on$1("keydown", (event) => {
|
|
25268
|
-
if (event.key.length === 1 && !event.ctrlKey && !event.altKey && !event.metaKey) {
|
|
25269
|
-
clearTimeout(timeoutId);
|
|
25270
|
-
updateTypeahead(text + event.key.toLowerCase(), onTypeahead);
|
|
25271
|
-
timeoutId = window.setTimeout(clearTypeahead, HIDDEN_TYPEAHEAD_TIMEOUT);
|
|
25272
|
-
} else if (event.key === "Escape") clearTypeahead();
|
|
25273
|
-
else if (event.key === "Backspace" && text.length > 0) {
|
|
25274
|
-
clearTimeout(timeoutId);
|
|
25275
|
-
updateTypeahead(text.slice(0, -1), onTypeahead);
|
|
25276
|
-
timeoutId = window.setTimeout(clearTypeahead, HIDDEN_TYPEAHEAD_TIMEOUT);
|
|
25277
|
-
}
|
|
25278
|
-
})];
|
|
25279
|
-
});
|
|
25280
|
-
function itemMatchesSearchText(item, text, getSearchValues) {
|
|
25281
|
-
let values = getSearchValues(item);
|
|
25282
|
-
let searchValues = Array.isArray(values) ? values : [values];
|
|
25283
|
-
let normalizedText = text.toLowerCase();
|
|
25284
|
-
return searchValues.some((value) => value.toLowerCase().startsWith(normalizedText));
|
|
25285
|
-
}
|
|
25286
|
-
function matchNextItemBySearchText(text, items, options) {
|
|
25287
|
-
if (text === "") return null;
|
|
25288
|
-
for (let offset = 1; offset <= items.length; offset++) {
|
|
25289
|
-
let item = items[(options.fromIndex + offset + items.length) % items.length];
|
|
25290
|
-
if (itemMatchesSearchText(item, text, options.getSearchValues)) return item;
|
|
25291
|
-
}
|
|
25292
|
-
return null;
|
|
25293
|
-
}
|
|
25294
|
-
//#endregion
|
|
25295
|
-
//#region ../../node_modules/.pnpm/@remix-run+ui@0.12.1/node_modules/@remix-run/ui/dist/lib/flash-attribute.js
|
|
25296
|
-
function wait(ms) {
|
|
25297
|
-
return new Promise((resolve) => {
|
|
25298
|
-
setTimeout(resolve, ms);
|
|
25299
|
-
});
|
|
25300
|
-
}
|
|
25301
|
-
async function flashAttribute(node, attributeName, duration) {
|
|
25302
|
-
node.setAttribute(attributeName, "true");
|
|
25303
|
-
await wait(duration);
|
|
25304
|
-
node.removeAttribute(attributeName);
|
|
25102
|
+
async function flashAttribute(node, attributeName, duration) {
|
|
25103
|
+
node.setAttribute(attributeName, "true");
|
|
25104
|
+
await wait(duration);
|
|
25105
|
+
node.removeAttribute(attributeName);
|
|
25305
25106
|
}
|
|
25306
25107
|
//#endregion
|
|
25307
25108
|
//#region ../../node_modules/.pnpm/@remix-run+ui@0.12.1/node_modules/@remix-run/ui/dist/listbox.js
|
|
@@ -25528,168 +25329,10 @@ var optionMixin = createMixin((handle) => {
|
|
|
25528
25329
|
]];
|
|
25529
25330
|
};
|
|
25530
25331
|
});
|
|
25531
|
-
var Context
|
|
25332
|
+
var Context = ListboxProvider;
|
|
25532
25333
|
var list = listMixin;
|
|
25533
25334
|
var option = optionMixin;
|
|
25534
25335
|
//#endregion
|
|
25535
|
-
//#region ../../node_modules/.pnpm/@remix-run+ui@0.12.1/node_modules/@remix-run/ui/dist/lib/outside-click.js
|
|
25536
|
-
var onOutsideClick = createMixin((handle) => {
|
|
25537
|
-
let active = false;
|
|
25538
|
-
let handler = () => {};
|
|
25539
|
-
let isInsideTarget = () => false;
|
|
25540
|
-
let stopPropagation = true;
|
|
25541
|
-
handle.addEventListener("insert", (event) => {
|
|
25542
|
-
let node = event.node;
|
|
25543
|
-
node.ownerDocument.addEventListener("click", (event) => {
|
|
25544
|
-
let target = event.target instanceof Node ? event.target : null;
|
|
25545
|
-
if (!active || target && (node.contains(target) || isInsideTarget(target))) return;
|
|
25546
|
-
if (stopPropagation) event.stopPropagation();
|
|
25547
|
-
handler(target);
|
|
25548
|
-
}, {
|
|
25549
|
-
capture: true,
|
|
25550
|
-
signal: handle.signal
|
|
25551
|
-
});
|
|
25552
|
-
});
|
|
25553
|
-
return (nextActive, nextHandler, nextIsInsideTarget = () => false, nextStopPropagation = true) => {
|
|
25554
|
-
active = nextActive;
|
|
25555
|
-
handler = nextHandler;
|
|
25556
|
-
isInsideTarget = nextIsInsideTarget;
|
|
25557
|
-
stopPropagation = nextStopPropagation;
|
|
25558
|
-
};
|
|
25559
|
-
});
|
|
25560
|
-
//#endregion
|
|
25561
|
-
//#region ../../node_modules/.pnpm/@remix-run+ui@0.12.1/node_modules/@remix-run/ui/dist/lib/scroll-lock.js
|
|
25562
|
-
var scrollLocks = /* @__PURE__ */ new WeakMap();
|
|
25563
|
-
function lockScroll(targetDocument = globalThis.document) {
|
|
25564
|
-
if (!targetDocument?.body || !targetDocument.defaultView) return () => {};
|
|
25565
|
-
let document = targetDocument;
|
|
25566
|
-
let documentElement = document.documentElement;
|
|
25567
|
-
let view = document.defaultView;
|
|
25568
|
-
let state = scrollLocks.get(document);
|
|
25569
|
-
if (!state) {
|
|
25570
|
-
let scrollX = view.scrollX;
|
|
25571
|
-
let scrollY = view.scrollY;
|
|
25572
|
-
let scrollbarWidth = documentElement.clientWidth > 0 ? Math.max(view.innerWidth - documentElement.clientWidth, 0) : 0;
|
|
25573
|
-
let computedScrollbarGutter = view.getComputedStyle(documentElement).scrollbarGutter;
|
|
25574
|
-
state = {
|
|
25575
|
-
count: 0,
|
|
25576
|
-
documentOverflow: documentElement.style.overflow,
|
|
25577
|
-
documentScrollbarGutter: documentElement.style.scrollbarGutter,
|
|
25578
|
-
scrollX,
|
|
25579
|
-
scrollY
|
|
25580
|
-
};
|
|
25581
|
-
documentElement.style.overflow = "hidden";
|
|
25582
|
-
if (scrollbarWidth > 0 && computedScrollbarGutter === "auto") documentElement.style.scrollbarGutter = "stable";
|
|
25583
|
-
scrollLocks.set(document, state);
|
|
25584
|
-
}
|
|
25585
|
-
state.count++;
|
|
25586
|
-
let unlocked = false;
|
|
25587
|
-
return () => {
|
|
25588
|
-
if (unlocked) return;
|
|
25589
|
-
unlocked = true;
|
|
25590
|
-
let currentState = scrollLocks.get(document);
|
|
25591
|
-
if (!currentState) return;
|
|
25592
|
-
currentState.count--;
|
|
25593
|
-
if (currentState.count > 0) return;
|
|
25594
|
-
scrollLocks.delete(document);
|
|
25595
|
-
documentElement.style.overflow = currentState.documentOverflow;
|
|
25596
|
-
documentElement.style.scrollbarGutter = currentState.documentScrollbarGutter;
|
|
25597
|
-
view.scrollTo(currentState.scrollX, currentState.scrollY);
|
|
25598
|
-
};
|
|
25599
|
-
}
|
|
25600
|
-
//#endregion
|
|
25601
|
-
//#region ../../node_modules/.pnpm/@remix-run+ui@0.12.1/node_modules/@remix-run/ui/dist/popover.js
|
|
25602
|
-
function PopoverProvider(handle) {
|
|
25603
|
-
handle.context.set({
|
|
25604
|
-
hideFocusTarget: null,
|
|
25605
|
-
showFocusTarget: null,
|
|
25606
|
-
surface: null,
|
|
25607
|
-
anchor: null
|
|
25608
|
-
});
|
|
25609
|
-
return () => handle.props.children;
|
|
25610
|
-
}
|
|
25611
|
-
var anchorMixin = createMixin((handle) => {
|
|
25612
|
-
let context = handle.context.get(PopoverProvider);
|
|
25613
|
-
return (options) => {
|
|
25614
|
-
handle.queueTask((node) => {
|
|
25615
|
-
context.anchor = {
|
|
25616
|
-
target: node,
|
|
25617
|
-
options
|
|
25618
|
-
};
|
|
25619
|
-
});
|
|
25620
|
-
};
|
|
25621
|
-
});
|
|
25622
|
-
function anchorContains(anchor, target) {
|
|
25623
|
-
return anchor?.target instanceof HTMLElement && anchor.target.contains(target);
|
|
25624
|
-
}
|
|
25625
|
-
var surfaceMixin = createMixin((handle) => {
|
|
25626
|
-
let openProp = false;
|
|
25627
|
-
let cleanupAnchor = () => {};
|
|
25628
|
-
let unlockScroll = () => {};
|
|
25629
|
-
let context = handle.context.get(PopoverProvider);
|
|
25630
|
-
handle.queueTask((node, signal) => {
|
|
25631
|
-
context.surface = node;
|
|
25632
|
-
signal.addEventListener("abort", () => {
|
|
25633
|
-
if (context.surface === node) context.surface = null;
|
|
25634
|
-
});
|
|
25635
|
-
});
|
|
25636
|
-
return (options) => {
|
|
25637
|
-
let wasOpen = openProp;
|
|
25638
|
-
openProp = options.open;
|
|
25639
|
-
handle.queueTask(async (node) => {
|
|
25640
|
-
if (openProp && !wasOpen) node.showPopover();
|
|
25641
|
-
else if (!openProp && wasOpen) node.hidePopover();
|
|
25642
|
-
});
|
|
25643
|
-
return [
|
|
25644
|
-
attrs({ popover: "manual" }),
|
|
25645
|
-
on$1("beforetoggle", (event) => {
|
|
25646
|
-
if (event.newState === "open") {
|
|
25647
|
-
let anchor = context.anchor;
|
|
25648
|
-
if (!anchor) throw new Error("popover.surface() requires a registered anchor before opening");
|
|
25649
|
-
cleanupAnchor = anchor$1(event.currentTarget, anchor.target, anchor.options);
|
|
25650
|
-
unlockScroll = lockScroll();
|
|
25651
|
-
} else if (event.newState === "closed") {
|
|
25652
|
-
cleanupAnchor();
|
|
25653
|
-
unlockScroll();
|
|
25654
|
-
}
|
|
25655
|
-
}),
|
|
25656
|
-
on$1("toggle", async (event) => {
|
|
25657
|
-
if (event.newState === "open") context.showFocusTarget?.focus();
|
|
25658
|
-
else if (event.newState === "closed" && options.restoreFocusOnHide !== false) context.hideFocusTarget?.focus();
|
|
25659
|
-
}),
|
|
25660
|
-
on$1("keydown", (event) => {
|
|
25661
|
-
if (event.key === "Escape") {
|
|
25662
|
-
event.preventDefault();
|
|
25663
|
-
options.onHide({ reason: "escape-key" });
|
|
25664
|
-
}
|
|
25665
|
-
}),
|
|
25666
|
-
onOutsideClick(openProp, (target) => {
|
|
25667
|
-
options.onHide({
|
|
25668
|
-
reason: "outside-click",
|
|
25669
|
-
target
|
|
25670
|
-
});
|
|
25671
|
-
}, (target) => options.closeOnAnchorClick === false && anchorContains(context.anchor, target), options.stopOutsideClickPropagation ?? true)
|
|
25672
|
-
];
|
|
25673
|
-
};
|
|
25674
|
-
});
|
|
25675
|
-
var focusOnShowMixin = createMixin((handle) => {
|
|
25676
|
-
handle.addEventListener("insert", (event) => {
|
|
25677
|
-
let context = handle.context.get(PopoverProvider);
|
|
25678
|
-
context.showFocusTarget = event.node;
|
|
25679
|
-
});
|
|
25680
|
-
});
|
|
25681
|
-
var focusOnHideMixin = createMixin((handle) => {
|
|
25682
|
-
handle.addEventListener("insert", (event) => {
|
|
25683
|
-
let context = handle.context.get(PopoverProvider);
|
|
25684
|
-
context.hideFocusTarget = event.node;
|
|
25685
|
-
});
|
|
25686
|
-
});
|
|
25687
|
-
var Context = PopoverProvider;
|
|
25688
|
-
var anchor = anchorMixin;
|
|
25689
|
-
var surface = surfaceMixin;
|
|
25690
|
-
var focusOnHide = focusOnHideMixin;
|
|
25691
|
-
var focusOnShow = focusOnShowMixin;
|
|
25692
|
-
//#endregion
|
|
25693
25336
|
//#region ../ui/src/lib/select.tsx
|
|
25694
25337
|
/** The popup surface shared by selects and menus. */
|
|
25695
25338
|
var menuSurface = "bud-overlay bud-menu m-0 min-w-44 rounded-lg p-1 text-ink";
|
|
@@ -25755,7 +25398,7 @@ function Select(handle) {
|
|
|
25755
25398
|
let summary = current.length === 0 ? props.placeholder ?? "" : current.length === 1 ? current[0].label : `${current[0].label} +${current.length - 1}`;
|
|
25756
25399
|
let leading = current.length === 1 && current[0].icon ? current[0].icon : props.icon;
|
|
25757
25400
|
let search = props.search ? typeof props.search === "string" ? props.search : t("select.searchPlaceholder") : void 0;
|
|
25758
|
-
return /* @__PURE__ */ jsxs(Context, { children: [
|
|
25401
|
+
return /* @__PURE__ */ jsxs(Context$1, { children: [
|
|
25759
25402
|
/* @__PURE__ */ jsx(HeadlessButton, {
|
|
25760
25403
|
"aria-label": props.label,
|
|
25761
25404
|
"aria-haspopup": "listbox",
|
|
@@ -25846,7 +25489,7 @@ function Select(handle) {
|
|
|
25846
25489
|
})
|
|
25847
25490
|
]
|
|
25848
25491
|
})]
|
|
25849
|
-
}) : null, /* @__PURE__ */ jsx(Context
|
|
25492
|
+
}) : null, /* @__PURE__ */ jsx(Context, {
|
|
25850
25493
|
ref: (value) => {
|
|
25851
25494
|
list$2 = value;
|
|
25852
25495
|
},
|
|
@@ -25919,6 +25562,403 @@ function Select(handle) {
|
|
|
25919
25562
|
};
|
|
25920
25563
|
}
|
|
25921
25564
|
//#endregion
|
|
25565
|
+
//#region ../ui/src/lib/comments/comment-data.ts
|
|
25566
|
+
/**
|
|
25567
|
+
* Takes the first letters of a name's first and last words.
|
|
25568
|
+
* @param name - The author's name.
|
|
25569
|
+
* @returns One or two capital letters, or `?` for an empty name.
|
|
25570
|
+
*/
|
|
25571
|
+
function commentInitials(name) {
|
|
25572
|
+
let parts = name.trim().split(/\s+/u).filter(Boolean);
|
|
25573
|
+
return `${parts[0]?.[0] ?? "?"}${parts.length > 1 ? parts.at(-1)[0] : ""}`.toUpperCase();
|
|
25574
|
+
}
|
|
25575
|
+
/**
|
|
25576
|
+
* Gives an author a stable color.
|
|
25577
|
+
* @param id - The author's id.
|
|
25578
|
+
* @returns A hue from 0 to 359.
|
|
25579
|
+
*/
|
|
25580
|
+
function commentAuthorHue(id) {
|
|
25581
|
+
let hash = 0;
|
|
25582
|
+
for (let character of id) hash = (hash * 31 + character.codePointAt(0)) % 360;
|
|
25583
|
+
return hash;
|
|
25584
|
+
}
|
|
25585
|
+
//#endregion
|
|
25586
|
+
//#region ../ui/src/lib/comments/comment-thread.tsx
|
|
25587
|
+
/**
|
|
25588
|
+
* Shows an author's initials on a circle in their color.
|
|
25589
|
+
* @param handle - The author, and whether the avatar is the compact size.
|
|
25590
|
+
* @returns The avatar render function.
|
|
25591
|
+
*/
|
|
25592
|
+
function CommentAvatar(handle) {
|
|
25593
|
+
return () => {
|
|
25594
|
+
let { author, compact = false, class: className = "" } = handle.props;
|
|
25595
|
+
return /* @__PURE__ */ jsx(Text, {
|
|
25596
|
+
variant: "ui-caption",
|
|
25597
|
+
weight: "medium",
|
|
25598
|
+
class: `flex shrink-0 items-center justify-center rounded-full text-white ${compact ? "size-5" : "size-6"} ${className}`,
|
|
25599
|
+
title: author.name,
|
|
25600
|
+
"data-testid": "comment-avatar",
|
|
25601
|
+
style: { backgroundColor: `oklch(0.55 0.14 ${commentAuthorHue(author.id)})` },
|
|
25602
|
+
children: /* @__PURE__ */ jsx("span", {
|
|
25603
|
+
class: compact ? "scale-[0.833]" : void 0,
|
|
25604
|
+
children: commentInitials(author.name)
|
|
25605
|
+
})
|
|
25606
|
+
});
|
|
25607
|
+
};
|
|
25608
|
+
}
|
|
25609
|
+
//#endregion
|
|
25610
|
+
//#region ../ui/src/lib/dialog.tsx
|
|
25611
|
+
var sizes = {
|
|
25612
|
+
default: "max-w-[35rem]",
|
|
25613
|
+
large: "max-w-[39rem]",
|
|
25614
|
+
wide: "max-w-[51rem]"
|
|
25615
|
+
};
|
|
25616
|
+
/**
|
|
25617
|
+
* The one modal: a native dialog on a dimmed, blurred backdrop whose content is a FieldCard,
|
|
25618
|
+
* raised above the page. It takes focus when it opens, returns it when it closes, and closes on
|
|
25619
|
+
* Escape or a click on the backdrop.
|
|
25620
|
+
* @param handle - The label, size, close handler and content.
|
|
25621
|
+
* @returns The dialog's render function.
|
|
25622
|
+
*/
|
|
25623
|
+
function Dialog(handle) {
|
|
25624
|
+
let pressedOutside = false;
|
|
25625
|
+
function close() {
|
|
25626
|
+
if (handle.props.dismissible !== false) handle.props.onClose();
|
|
25627
|
+
}
|
|
25628
|
+
return () => {
|
|
25629
|
+
let { label, size = "default", initialFocus, children } = handle.props;
|
|
25630
|
+
return /* @__PURE__ */ jsx("dialog", {
|
|
25631
|
+
"aria-label": label,
|
|
25632
|
+
class: `fixed inset-0 m-auto flex max-h-full w-full flex-col overflow-hidden border-0 bg-transparent p-3 text-ink transition-[opacity,scale] duration-200 ease-out backdrop:bg-black/25 backdrop:backdrop-blur-sm backdrop:transition-opacity backdrop:duration-200 starting:scale-[0.97] starting:opacity-0 starting:backdrop:opacity-0 motion-reduce:transition-none motion-reduce:backdrop:transition-none sm:p-6 ${sizes[size]}`,
|
|
25633
|
+
mix: [
|
|
25634
|
+
ref((node, signal) => openDialog(node, signal, initialFocus)),
|
|
25635
|
+
on("cancel", (event) => {
|
|
25636
|
+
event.preventDefault();
|
|
25637
|
+
close();
|
|
25638
|
+
}),
|
|
25639
|
+
on("pointerdown", (event) => {
|
|
25640
|
+
pressedOutside = event.target === event.currentTarget;
|
|
25641
|
+
}),
|
|
25642
|
+
on("click", (event) => {
|
|
25643
|
+
if (pressedOutside && event.target === event.currentTarget) close();
|
|
25644
|
+
})
|
|
25645
|
+
],
|
|
25646
|
+
children
|
|
25647
|
+
});
|
|
25648
|
+
};
|
|
25649
|
+
}
|
|
25650
|
+
/**
|
|
25651
|
+
* Owns a native modal and returns focus once Remix removes its host node.
|
|
25652
|
+
* @param node - The mounted dialog.
|
|
25653
|
+
* @param signal - The host's lifetime, including its removal.
|
|
25654
|
+
* @param initialFocus - An optional selector for the element to focus first.
|
|
25655
|
+
*/
|
|
25656
|
+
function openDialog(node, signal, initialFocus) {
|
|
25657
|
+
let document = node.ownerDocument;
|
|
25658
|
+
let previous = document.activeElement;
|
|
25659
|
+
node.showModal();
|
|
25660
|
+
if (initialFocus) queueMicrotask(() => {
|
|
25661
|
+
if (!signal.aborted) node.querySelector(initialFocus)?.focus();
|
|
25662
|
+
});
|
|
25663
|
+
signal.addEventListener("abort", () => {
|
|
25664
|
+
node.close();
|
|
25665
|
+
queueMicrotask(() => {
|
|
25666
|
+
if (previous instanceof HTMLElement && previous.isConnected && [...document.querySelectorAll("dialog:modal")].every((dialog) => dialog.contains(previous))) previous.focus({ preventScroll: true });
|
|
25667
|
+
});
|
|
25668
|
+
}, { once: true });
|
|
25669
|
+
}
|
|
25670
|
+
//#endregion
|
|
25671
|
+
//#region ../ui/src/lib/shortcut.ts
|
|
25672
|
+
var symbols = {
|
|
25673
|
+
arrowup: "↑",
|
|
25674
|
+
arrowdown: "↓",
|
|
25675
|
+
arrowleft: "←",
|
|
25676
|
+
arrowright: "→",
|
|
25677
|
+
enter: "↵",
|
|
25678
|
+
escape: "Esc",
|
|
25679
|
+
backspace: "⌫",
|
|
25680
|
+
tab: "⇥",
|
|
25681
|
+
space: "Space"
|
|
25682
|
+
};
|
|
25683
|
+
/**
|
|
25684
|
+
* Reads a combo such as `mod+shift+k`; the last part is the key, so `mod++` means mod and plus.
|
|
25685
|
+
* @param combo - Modifiers and a key joined by `+`.
|
|
25686
|
+
* @returns The key and its modifiers.
|
|
25687
|
+
*/
|
|
25688
|
+
function parseShortcut(combo) {
|
|
25689
|
+
let separator = combo.length < 2 ? -1 : combo.lastIndexOf("+", combo.length - 2);
|
|
25690
|
+
let modifiers = separator < 0 ? [] : combo.slice(0, separator).toLowerCase().split("+");
|
|
25691
|
+
return {
|
|
25692
|
+
key: combo.slice(separator + 1),
|
|
25693
|
+
mod: modifiers.includes("mod"),
|
|
25694
|
+
shift: modifiers.includes("shift"),
|
|
25695
|
+
alt: modifiers.includes("alt")
|
|
25696
|
+
};
|
|
25697
|
+
}
|
|
25698
|
+
/**
|
|
25699
|
+
* The keycaps to show for a combo, in the platform's order and notation.
|
|
25700
|
+
* @param combo - Modifiers and a key joined by `+`.
|
|
25701
|
+
* @param apple - Whether to use Apple symbols; detected from the browser by default.
|
|
25702
|
+
* @returns One label per key.
|
|
25703
|
+
*/
|
|
25704
|
+
function shortcutKeys(combo, apple = isApple()) {
|
|
25705
|
+
let { key, mod, shift, alt } = parseShortcut(combo);
|
|
25706
|
+
let label = symbols[key.toLowerCase()] ?? (key.length === 1 ? key.toUpperCase() : key);
|
|
25707
|
+
if (apple) return [
|
|
25708
|
+
alt && "⌥",
|
|
25709
|
+
shift && "⇧",
|
|
25710
|
+
mod && "⌘",
|
|
25711
|
+
label
|
|
25712
|
+
].filter((part) => part !== false);
|
|
25713
|
+
return [
|
|
25714
|
+
mod && "Ctrl",
|
|
25715
|
+
alt && "Alt",
|
|
25716
|
+
shift && "Shift",
|
|
25717
|
+
label
|
|
25718
|
+
].filter((part) => part !== false);
|
|
25719
|
+
}
|
|
25720
|
+
function isApple() {
|
|
25721
|
+
return typeof navigator !== "undefined" && /mac|iphone|ipad|ipod/i.test(navigator.platform);
|
|
25722
|
+
}
|
|
25723
|
+
//#endregion
|
|
25724
|
+
//#region ../ui/src/lib/tooltip.tsx
|
|
25725
|
+
var delay = 400;
|
|
25726
|
+
var warmFor = 300;
|
|
25727
|
+
var closedAt = 0;
|
|
25728
|
+
/**
|
|
25729
|
+
* Names a control on hover or keyboard focus, with its shortcut. The control keeps its own
|
|
25730
|
+
* accessible name; the tooltip describes it.
|
|
25731
|
+
* @param handle - The label, optional shortcut and the control it describes.
|
|
25732
|
+
* @returns The tooltip render function.
|
|
25733
|
+
*/
|
|
25734
|
+
function Tooltip(handle) {
|
|
25735
|
+
let open = false;
|
|
25736
|
+
let timer;
|
|
25737
|
+
let trigger;
|
|
25738
|
+
let release = () => {};
|
|
25739
|
+
let id = `${handle.id}-tooltip`;
|
|
25740
|
+
function show(immediately) {
|
|
25741
|
+
clearTimeout(timer);
|
|
25742
|
+
if (open) return;
|
|
25743
|
+
let reveal = () => {
|
|
25744
|
+
open = true;
|
|
25745
|
+
handle.update();
|
|
25746
|
+
};
|
|
25747
|
+
if (immediately || Date.now() - closedAt < warmFor) reveal();
|
|
25748
|
+
else timer = setTimeout(reveal, delay);
|
|
25749
|
+
}
|
|
25750
|
+
function hide() {
|
|
25751
|
+
clearTimeout(timer);
|
|
25752
|
+
if (!open) return;
|
|
25753
|
+
open = false;
|
|
25754
|
+
closedAt = Date.now();
|
|
25755
|
+
handle.update();
|
|
25756
|
+
}
|
|
25757
|
+
return () => /* @__PURE__ */ jsxs(Fragment, { children: [/* @__PURE__ */ jsx("span", {
|
|
25758
|
+
class: "inline-flex",
|
|
25759
|
+
mix: [
|
|
25760
|
+
ref((node, signal) => {
|
|
25761
|
+
trigger = node.firstElementChild instanceof HTMLElement ? node.firstElementChild : node;
|
|
25762
|
+
trigger.setAttribute("aria-describedby", id);
|
|
25763
|
+
let escape = (event) => {
|
|
25764
|
+
if (event.key === "Escape") hide();
|
|
25765
|
+
};
|
|
25766
|
+
document.addEventListener("keydown", escape, { signal });
|
|
25767
|
+
signal.addEventListener("abort", () => clearTimeout(timer), { once: true });
|
|
25768
|
+
}),
|
|
25769
|
+
on("pointerenter", (event) => {
|
|
25770
|
+
if (event.pointerType === "mouse") show(false);
|
|
25771
|
+
}),
|
|
25772
|
+
on("pointerleave", hide),
|
|
25773
|
+
on("pointerdown", hide),
|
|
25774
|
+
on("focusin", (event) => {
|
|
25775
|
+
if (event.target.dataset.focusMethod === "keyboard") show(true);
|
|
25776
|
+
}),
|
|
25777
|
+
on("focusout", hide)
|
|
25778
|
+
],
|
|
25779
|
+
children: handle.props.children
|
|
25780
|
+
}), /* @__PURE__ */ jsxs("div", {
|
|
25781
|
+
id,
|
|
25782
|
+
role: "tooltip",
|
|
25783
|
+
popover: "manual",
|
|
25784
|
+
class: "bud-tooltip pointer-events-none m-0 inline-flex items-center gap-1.5 rounded-[10px] px-2 py-1.5 transition-[opacity,scale] duration-100 ease-out starting:scale-95 starting:opacity-0 motion-reduce:transition-none",
|
|
25785
|
+
mix: ref((node, signal) => {
|
|
25786
|
+
if (!open || !trigger) return;
|
|
25787
|
+
node.showPopover();
|
|
25788
|
+
release = anchor$1(node, trigger, {
|
|
25789
|
+
placement: handle.props.placement ?? "top",
|
|
25790
|
+
offset: 6
|
|
25791
|
+
});
|
|
25792
|
+
signal.addEventListener("abort", () => {
|
|
25793
|
+
release();
|
|
25794
|
+
if (node.isConnected && node.matches(":popover-open")) node.hidePopover();
|
|
25795
|
+
}, { once: true });
|
|
25796
|
+
}),
|
|
25797
|
+
hidden: !open,
|
|
25798
|
+
children: [/* @__PURE__ */ jsx(Text, {
|
|
25799
|
+
variant: "ui-caption",
|
|
25800
|
+
weight: "medium",
|
|
25801
|
+
children: handle.props.label
|
|
25802
|
+
}), handle.props.shortcut ? /* @__PURE__ */ jsx(Kbd, { shortcut: handle.props.shortcut }) : null]
|
|
25803
|
+
}, open ? "open" : "closed")] });
|
|
25804
|
+
}
|
|
25805
|
+
/**
|
|
25806
|
+
* A shortcut as keycaps, such as ⌘ K, in the platform's notation.
|
|
25807
|
+
* @param handle - A combo such as `mod+shift+k`.
|
|
25808
|
+
* @returns The keycaps render function.
|
|
25809
|
+
*/
|
|
25810
|
+
function Kbd(handle) {
|
|
25811
|
+
return () => /* @__PURE__ */ jsx("span", {
|
|
25812
|
+
class: `inline-flex items-center gap-0.5 ${handle.props.class ?? ""}`,
|
|
25813
|
+
children: shortcutKeys(handle.props.shortcut).map((key, index) => /* @__PURE__ */ jsx(Text, {
|
|
25814
|
+
as: "kbd",
|
|
25815
|
+
variant: "kbd",
|
|
25816
|
+
class: "inline-flex h-4.5 min-w-4.5 items-center justify-center rounded-[5px] bg-current/12 px-1 opacity-80",
|
|
25817
|
+
"data-slot": "kbd",
|
|
25818
|
+
children: key
|
|
25819
|
+
}, index))
|
|
25820
|
+
});
|
|
25821
|
+
}
|
|
25822
|
+
//#endregion
|
|
25823
|
+
//#region ../ui/src/lib/icon-button.tsx
|
|
25824
|
+
/**
|
|
25825
|
+
* Compact control shared by the canvas, sidebar, and embedded product demo.
|
|
25826
|
+
* @param handle - Native button props, icon, label, and active state.
|
|
25827
|
+
* @returns The button render function.
|
|
25828
|
+
*/
|
|
25829
|
+
function IconButton(handle) {
|
|
25830
|
+
return () => {
|
|
25831
|
+
let { icon, label, active, surface, size = "default", iconSize = size === "small" ? 14 : 16, tooltip, shortcut, class: className = "", ...props } = handle.props;
|
|
25832
|
+
let button = /* @__PURE__ */ jsx(HeadlessButton, {
|
|
25833
|
+
...props,
|
|
25834
|
+
"aria-label": label,
|
|
25835
|
+
title: tooltip ? void 0 : props.title ?? label,
|
|
25836
|
+
"aria-pressed": props["aria-pressed"] ?? active,
|
|
25837
|
+
"data-active": active,
|
|
25838
|
+
class: `bud-interaction ${surface ? "bud-control" : ""} flex shrink-0 items-center justify-center ${size === "small" ? "size-6 rounded-md" : "size-control rounded-lg"} ${className}`,
|
|
25839
|
+
children: /* @__PURE__ */ jsx(Icon, {
|
|
25840
|
+
name: icon,
|
|
25841
|
+
size: iconSize
|
|
25842
|
+
})
|
|
25843
|
+
});
|
|
25844
|
+
return tooltip ? /* @__PURE__ */ jsx(Tooltip, {
|
|
25845
|
+
label,
|
|
25846
|
+
shortcut,
|
|
25847
|
+
children: button
|
|
25848
|
+
}) : button;
|
|
25849
|
+
};
|
|
25850
|
+
}
|
|
25851
|
+
//#endregion
|
|
25852
|
+
//#region ../ui/src/lib/scroll-fade.ts
|
|
25853
|
+
/**
|
|
25854
|
+
* Fades a scroller's edges while it has more content past them, after Divine's scroll-fade
|
|
25855
|
+
* utility. The fade only applies while the content overflows, so a short list keeps crisp edges.
|
|
25856
|
+
* @param axis - The direction the element scrolls.
|
|
25857
|
+
* @returns A mixin for the scrolling element.
|
|
25858
|
+
*/
|
|
25859
|
+
function scrollFade(axis = "x") {
|
|
25860
|
+
return ref((node, signal) => {
|
|
25861
|
+
let update = () => {
|
|
25862
|
+
if (axis === "x" ? node.scrollWidth > node.clientWidth + 1 : node.scrollHeight > node.clientHeight + 1) node.dataset.scrollFade = axis;
|
|
25863
|
+
else delete node.dataset.scrollFade;
|
|
25864
|
+
};
|
|
25865
|
+
let resize = new ResizeObserver(update);
|
|
25866
|
+
let mutation = new MutationObserver(update);
|
|
25867
|
+
resize.observe(node);
|
|
25868
|
+
mutation.observe(node, {
|
|
25869
|
+
childList: true,
|
|
25870
|
+
subtree: true,
|
|
25871
|
+
characterData: true
|
|
25872
|
+
});
|
|
25873
|
+
update();
|
|
25874
|
+
signal.addEventListener("abort", () => {
|
|
25875
|
+
resize.disconnect();
|
|
25876
|
+
mutation.disconnect();
|
|
25877
|
+
}, { once: true });
|
|
25878
|
+
});
|
|
25879
|
+
}
|
|
25880
|
+
//#endregion
|
|
25881
|
+
//#region ../ui/src/lib/workspace.tsx
|
|
25882
|
+
/**
|
|
25883
|
+
* A panel's toolbar: content on the left, such as a path, and actions on the right. On narrow
|
|
25884
|
+
* screens the actions scroll, fading at their edges.
|
|
25885
|
+
* @param handle - The start content, the actions, and whether a line separates it from the
|
|
25886
|
+
* panel, which content that fades as it scrolls doesn't need.
|
|
25887
|
+
* @returns The toolbar render function.
|
|
25888
|
+
*/
|
|
25889
|
+
function WorkspaceToolbar(handle) {
|
|
25890
|
+
return () => /* @__PURE__ */ jsxs("div", {
|
|
25891
|
+
class: `bud-toolbar flex h-12 shrink-0 items-center gap-2 ps-2 pe-2 ${handle.props.divider === false ? "" : "border-b border-line"}`,
|
|
25892
|
+
children: [handle.props.start, /* @__PURE__ */ jsx(ToolbarGroup, {
|
|
25893
|
+
class: "ms-auto min-w-0 [scrollbar-width:none] max-md:overflow-x-auto max-md:p-1",
|
|
25894
|
+
mix: scrollFade("x"),
|
|
25895
|
+
children: handle.props.children
|
|
25896
|
+
})]
|
|
25897
|
+
});
|
|
25898
|
+
}
|
|
25899
|
+
/**
|
|
25900
|
+
* A row of toolbar buttons and separators, spaced alike in every toolbar.
|
|
25901
|
+
* @param handle - Native div props and the buttons.
|
|
25902
|
+
* @returns The group render function.
|
|
25903
|
+
*/
|
|
25904
|
+
function ToolbarGroup(handle) {
|
|
25905
|
+
return () => {
|
|
25906
|
+
let { class: className = "", children, ...props } = handle.props;
|
|
25907
|
+
return /* @__PURE__ */ jsx("div", {
|
|
25908
|
+
...props,
|
|
25909
|
+
class: `flex items-center gap-1.5 ${className}`,
|
|
25910
|
+
children
|
|
25911
|
+
});
|
|
25912
|
+
};
|
|
25913
|
+
}
|
|
25914
|
+
//#endregion
|
|
25915
|
+
//#region ../ui/src/lib/toast-store.ts
|
|
25916
|
+
var defaultDuration = 4e3;
|
|
25917
|
+
var items = [];
|
|
25918
|
+
var listeners = /* @__PURE__ */ new Set();
|
|
25919
|
+
var next = 0;
|
|
25920
|
+
function publish() {
|
|
25921
|
+
for (let listener of listeners) listener(items);
|
|
25922
|
+
}
|
|
25923
|
+
/**
|
|
25924
|
+
* Shows a notification; the newest is in front.
|
|
25925
|
+
* @param title - The message.
|
|
25926
|
+
* @param options - A description, type, duration or stable id.
|
|
25927
|
+
* @returns The toast's id, for dismissing it early.
|
|
25928
|
+
*/
|
|
25929
|
+
function toast(title, options = {}) {
|
|
25930
|
+
let id = options.id ?? `toast-${++next}`;
|
|
25931
|
+
items = [{
|
|
25932
|
+
id,
|
|
25933
|
+
title,
|
|
25934
|
+
description: options.description,
|
|
25935
|
+
type: options.type ?? "default",
|
|
25936
|
+
duration: options.duration ?? defaultDuration,
|
|
25937
|
+
removed: false
|
|
25938
|
+
}, ...items.filter((existing) => existing.id !== id)];
|
|
25939
|
+
publish();
|
|
25940
|
+
return id;
|
|
25941
|
+
}
|
|
25942
|
+
toast.success = (title, options = {}) => toast(title, {
|
|
25943
|
+
...options,
|
|
25944
|
+
type: "success"
|
|
25945
|
+
});
|
|
25946
|
+
toast.error = (title, options = {}) => toast(title, {
|
|
25947
|
+
...options,
|
|
25948
|
+
type: "error"
|
|
25949
|
+
});
|
|
25950
|
+
/**
|
|
25951
|
+
* Starts a toast's exit; the Toaster removes it once it has animated out.
|
|
25952
|
+
* @param id - The toast to dismiss; every toast when omitted.
|
|
25953
|
+
*/
|
|
25954
|
+
toast.dismiss = (id) => {
|
|
25955
|
+
items = items.map((item) => id === void 0 || item.id === id ? {
|
|
25956
|
+
...item,
|
|
25957
|
+
removed: true
|
|
25958
|
+
} : item);
|
|
25959
|
+
publish();
|
|
25960
|
+
};
|
|
25961
|
+
//#endregion
|
|
25922
25962
|
//#region ../ui/src/lib/tasks/task-draft.ts
|
|
25923
25963
|
function editValue(value, field) {
|
|
25924
25964
|
return field.kind === "json" ? JSON.stringify(value ?? {}, null, 2) : taskValueText(value);
|