@riverbankcms/sdk 0.94.0 → 0.96.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.
Files changed (189) hide show
  1. package/README.md +30 -4
  2. package/dist/{PreviewEditorSidebar-D3PAF7NW.mjs → PreviewEditorSidebar-46VT4QVU.mjs} +3 -3
  3. package/dist/{PreviewEditorUI-G5JVJEIJ.mjs → PreviewEditorUI-JD75GE5F.mjs} +3 -3
  4. package/dist/SdkPreviewModeRuntime-MJUSYUFB.mjs +8 -0
  5. package/dist/_dts/ai/src/contracts/proposals.d.ts +10 -10
  6. package/dist/_dts/api/src/bookingOperations.d.ts +7 -0
  7. package/dist/_dts/api/src/bookingRecords.d.ts +3 -0
  8. package/dist/_dts/api/src/cache-tags.d.ts +4 -0
  9. package/dist/_dts/api/src/contentRuntime.d.ts +14 -0
  10. package/dist/_dts/api/src/endpoints.d.ts +8 -0
  11. package/dist/_dts/api/src/event-presentation.d.ts +15 -0
  12. package/dist/_dts/api/src/index.d.ts +1 -1
  13. package/dist/_dts/api/src/public/endpoints.d.ts +1 -1
  14. package/dist/_dts/api/src/publicExperienceEndpoints.d.ts +17 -4
  15. package/dist/_dts/api/src/shared-contracts.d.ts +19 -9
  16. package/dist/_dts/api/src/siteRuntimeEndpoints.d.ts +6 -1
  17. package/dist/_dts/block-form/src/client/index.d.ts +1 -1
  18. package/dist/_dts/block-form/src/fields/types.d.ts +9 -1
  19. package/dist/_dts/block-form/src/registry/schemas.d.ts +4 -0
  20. package/dist/_dts/block-form/src/registry/widgets.d.ts +1 -0
  21. package/dist/_dts/block-form/src/widgets/InlineTextField/InlineTextField.d.ts +4 -0
  22. package/dist/_dts/block-form/src/widgets/InlineTextField/index.d.ts +3 -0
  23. package/dist/_dts/block-form/src/widgets/InlineTextField/inlineTextFieldDefaults.d.ts +2 -0
  24. package/dist/_dts/block-form/src/widgets/InlineTextField/inlineTextFieldSchema.d.ts +3 -0
  25. package/dist/_dts/blocks/src/bindings/index.d.ts +1 -0
  26. package/dist/_dts/blocks/src/bindings/types.d.ts +1 -0
  27. package/dist/_dts/blocks/src/index.d.ts +2 -0
  28. package/dist/_dts/blocks/src/portal/types.d.ts +7 -0
  29. package/dist/_dts/blocks/src/system/blocks/appointment-booking.d.ts +2 -29631
  30. package/dist/_dts/blocks/src/system/blocks/blog-listing.d.ts +2 -29614
  31. package/dist/_dts/blocks/src/system/blocks/cart.d.ts +2 -29634
  32. package/dist/_dts/blocks/src/system/blocks/checkout.d.ts +2 -29627
  33. package/dist/_dts/blocks/src/system/blocks/collection.d.ts +2 -29585
  34. package/dist/_dts/blocks/src/system/blocks/faq.d.ts +2 -29677
  35. package/dist/_dts/blocks/src/system/blocks/gifting.d.ts +2 -29655
  36. package/dist/_dts/blocks/src/system/blocks/media-text.d.ts +220 -0
  37. package/dist/_dts/blocks/src/system/blocks/product-detail.d.ts +2 -29655
  38. package/dist/_dts/blocks/src/system/blocks/product-list.d.ts +2 -29685
  39. package/dist/_dts/blocks/src/system/blocks/shop.d.ts +2 -29761
  40. package/dist/_dts/blocks/src/system/fragments/library/heroCopy.d.ts +9 -0
  41. package/dist/_dts/blocks/src/system/inlineText.d.ts +78 -0
  42. package/dist/_dts/blocks/src/system/manifest/derivedContent.d.ts +3 -1
  43. package/dist/_dts/blocks/src/system/manifest/fieldValidation/index.d.ts +15 -3
  44. package/dist/_dts/blocks/src/system/manifest/schema.d.ts +188 -7
  45. package/dist/_dts/blocks/src/system/runtime/api/index.d.ts +1 -1
  46. package/dist/_dts/blocks/src/system/runtime/api/types.d.ts +21 -6
  47. package/dist/_dts/blocks/src/system/runtime/nodes/basic.d.ts +2 -1
  48. package/dist/_dts/blocks/src/system/runtime/nodes/event-registration/TicketSelectionStep.d.ts +5 -3
  49. package/dist/_dts/blocks/src/system/runtime/nodes/event-registration/event-registration.headless.contract.d.ts +5 -1
  50. package/dist/_dts/blocks/src/system/runtime/nodes/event-registration/hooks.d.ts +2 -2
  51. package/dist/_dts/blocks/src/system/runtime/nodes/event-registration/sessionStorage.d.ts +9 -6
  52. package/dist/_dts/blocks/src/system/runtime/nodes/event-registration/ticketSelectionLines.d.ts +36 -0
  53. package/dist/_dts/blocks/src/system/runtime/nodes/event-registration/types.d.ts +7 -1
  54. package/dist/_dts/blocks/src/system/runtime/nodes/event-registration/useEventRegistrationStripeReturn.d.ts +2 -2
  55. package/dist/_dts/blocks/src/system/runtime/nodes/event-registration/useEventRegistrationSubmit.d.ts +2 -3
  56. package/dist/_dts/blocks/src/system/runtime/nodes/event-registration/useEventRegistrationWizard.d.ts +19 -4
  57. package/dist/_dts/blocks/src/system/runtime/nodes/renderInlineText.d.ts +3 -0
  58. package/dist/_dts/content-editor/src/index.d.ts +1 -0
  59. package/dist/_dts/content-editor/src/primitives/PreviewInlineTextEditor.d.ts +9 -0
  60. package/dist/_dts/content-model/src/entry-slots/types.d.ts +6 -0
  61. package/dist/_dts/content-model/src/templates/bindingTypeCompatibility.d.ts +1 -1
  62. package/dist/_dts/content-model/src/templates/defaults.d.ts +30 -0
  63. package/dist/_dts/content-model/src/templates/types.d.ts +1 -0
  64. package/dist/_dts/db/src/generated/supabase/database.types.d.ts +163 -2
  65. package/dist/_dts/editor/src/inline/FloatingToolbar.d.ts +18 -0
  66. package/dist/_dts/editor/src/inline/InlineTextEditor.d.ts +18 -1
  67. package/dist/_dts/editor/src/inline/InlineTextEditorStyles.d.ts +1 -0
  68. package/dist/_dts/editor/src/inline/domParse.d.ts +3 -0
  69. package/dist/_dts/editor/src/inline/presentation.d.ts +48 -0
  70. package/dist/_dts/editor/src/inline/selection.d.ts +12 -0
  71. package/dist/_dts/editor-blocks/src/widgets/index.d.ts +1 -0
  72. package/dist/_dts/editor-blocks/src/widgets/inline-text/InlineTextField.d.ts +3 -0
  73. package/dist/_dts/editor-blocks/src/widgets/inline-text/index.d.ts +1 -0
  74. package/dist/_dts/media-core/src/assetsInUseSummary.d.ts +7 -0
  75. package/dist/_dts/media-core/src/mediaUsageProjection.d.ts +29 -1
  76. package/dist/_dts/path-utils/src/index.d.ts +1 -0
  77. package/dist/_dts/preview-next/src/client/widgets/widgetOverrides.d.ts +1 -0
  78. package/dist/_dts/sdk/src/cli/commands/content.d.ts +56 -0
  79. package/dist/_dts/sdk/src/cli/commands/push/options.d.ts +4 -0
  80. package/dist/_dts/sdk/src/cli/commands/push/scopes/commandBackedDatedOfferingScope.d.ts +2 -6
  81. package/dist/_dts/sdk/src/cli/commands/push/scopes/types.d.ts +2 -0
  82. package/dist/_dts/sdk/src/cli/commands/push/verification.d.ts +56 -0
  83. package/dist/_dts/sdk/src/cli/commands/push-execute.d.ts +2 -1
  84. package/dist/_dts/sdk/src/cli/content/edit/format.d.ts +2 -0
  85. package/dist/_dts/sdk/src/cli/content/edit/path.d.ts +14 -0
  86. package/dist/_dts/sdk/src/cli/content/edit/planner.d.ts +46 -0
  87. package/dist/_dts/sdk/src/cli/content/fs-utils.d.ts +4 -0
  88. package/dist/_dts/sdk/src/cli/content/writer.d.ts +2 -0
  89. package/dist/_dts/sdk/src/cli/merge-remote/mergeFieldChanges.d.ts +22 -0
  90. package/dist/_dts/sdk/src/cli/merge-remote/pageLocal.d.ts +3 -0
  91. package/dist/_dts/sdk/src/cli/merge-remote/pageMerge.d.ts +78 -0
  92. package/dist/_dts/sdk/src/cli/merge-remote/pageMergePlan.d.ts +36 -0
  93. package/dist/_dts/sdk/src/cli/merge-remote/pageMergePush.d.ts +21 -0
  94. package/dist/_dts/sdk/src/cli/merge-remote/pageMergeReport.d.ts +29 -0
  95. package/dist/_dts/sdk/src/cli/merge-remote/pageSnapshots.d.ts +48 -0
  96. package/dist/_dts/sdk/src/cli/sync/diff.d.ts +3 -6
  97. package/dist/_dts/sdk/src/cli/sync/field-diff.d.ts +39 -0
  98. package/dist/_dts/sdk/src/cli/sync/index.d.ts +1 -0
  99. package/dist/_dts/sdk/src/client/types.d.ts +7 -2
  100. package/dist/_dts/sdk/src/config/field-definitions.d.ts +8 -3
  101. package/dist/_dts/sdk/src/config/typed-entries.d.ts +5 -3
  102. package/dist/_dts/sdk/src/contracts/bindings.d.ts +1 -0
  103. package/dist/_dts/sdk/src/contracts/content.d.ts +18 -0
  104. package/dist/_dts/sdk/src/contracts/index.d.ts +1 -1
  105. package/dist/_dts/sdk/src/contracts/system-block-content.d.ts +3 -2
  106. package/dist/_dts/sdk/src/next/middleware.d.ts +1 -0
  107. package/dist/_dts/sdk/src/next/redirect-destination.d.ts +3 -0
  108. package/dist/_dts/sdk/src/next/route-outcome-proxy.d.ts +22 -0
  109. package/dist/_dts/sdk/src/public-api/contracts.d.ts +20 -1
  110. package/dist/_dts/sdk/src/public-api/runtime.d.ts +1 -1
  111. package/dist/_dts/sdk/src/rendering/helpers/bindings.d.ts +1 -0
  112. package/dist/_dts/sdk/src/rendering/helpers/loadContent.d.ts +9 -1
  113. package/dist/_dts/sdk/src/version.d.ts +1 -1
  114. package/dist/_dts/theme-core/src/accordions/types.d.ts +1 -1
  115. package/dist/_dts/theme-core/src/buttons/types.d.ts +1 -1
  116. package/dist/_dts/theme-core/src/cards/types.d.ts +15 -15
  117. package/dist/_dts/theme-core/src/generated/containerResponsiveThemeCss.d.ts +1 -1
  118. package/dist/_dts/theme-core/src/inputs/types.d.ts +1 -1
  119. package/dist/_dts/theme-core/src/mock-themes/all.d.ts +42 -42
  120. package/dist/_dts/theme-core/src/palette/variants/types.d.ts +2 -2
  121. package/dist/_dts/theme-core/src/schema.d.ts +44 -44
  122. package/dist/_dts/theme-core/src/site-styles/backgroundAppearance.d.ts +2 -2
  123. package/dist/_dts/theme-core/src/site-styles/designState.d.ts +16 -16
  124. package/dist/_dts/theme-core/src/site-styles/pageDesignIntent.d.ts +4 -4
  125. package/dist/_dts/theme-core/src/site-styles/tokenRecipes.d.ts +1 -1
  126. package/dist/_dts/theme-core/src/tokens/themeColorTokens.d.ts +1 -1
  127. package/dist/{chunk-AQ6RT6LZ.mjs → chunk-4TLTV7OB.mjs} +2 -2
  128. package/dist/{chunk-NT76QGIJ.mjs → chunk-7ED5UNHL.mjs} +14 -0
  129. package/dist/{chunk-XIK2HYI3.mjs → chunk-EL55VV6Q.mjs} +49 -9
  130. package/dist/{chunk-A63UXN3P.mjs → chunk-VHIMXQ7Z.mjs} +106 -4
  131. package/dist/{chunk-AJZGT6YG.mjs → chunk-VTPPVAOL.mjs} +1 -1
  132. package/dist/{chunk-PCNCETBI.mjs → chunk-XMATDBXO.mjs} +2082 -408
  133. package/dist/cli/index.mjs +2809 -787
  134. package/dist/cli/init-docs/content/cli-reference.md +43 -4
  135. package/dist/cli/init-docs/content/content-management.md +22 -0
  136. package/dist/client/{accordion-RNQIPG55.mjs → accordion-GUNXIIZR.mjs} +1 -1
  137. package/dist/client/{bookingForm-HYEEVRLP.mjs → bookingForm-AOU4VHP5.mjs} +3 -3
  138. package/dist/client/bookings.mjs +211 -105
  139. package/dist/client/{carousel-W7DQ3YPU.mjs → carousel-4QSX2JPC.mjs} +1 -1
  140. package/dist/client/{cart-PXJ3SXXO.mjs → cart-JKN6C4ZB.mjs} +4 -4
  141. package/dist/client/{checkout-X3JYSOXI.mjs → checkout-YY6YMITW.mjs} +4 -4
  142. package/dist/client/{chunk-PICR3NTQ.mjs → chunk-6H27K6AA.mjs} +1 -1
  143. package/dist/client/{chunk-J6TMMMXW.mjs → chunk-A3YN7M3G.mjs} +1 -1
  144. package/dist/client/{chunk-YYVGSYBO.mjs → chunk-BFCJZODD.mjs} +3 -3
  145. package/dist/client/{chunk-IXDSXF2D.mjs → chunk-CPKMJVBD.mjs} +353 -187
  146. package/dist/client/{chunk-6SYGVVWA.mjs → chunk-GWCRCJLB.mjs} +9 -0
  147. package/dist/client/{chunk-Q47XGAGS.mjs → chunk-H7A6PUGM.mjs} +1 -1
  148. package/dist/client/{chunk-WERRJXNJ.mjs → chunk-SY543WZ3.mjs} +1 -1
  149. package/dist/client/{chunk-DUOHLWLF.mjs → chunk-VJROUYOQ.mjs} +2 -2
  150. package/dist/client/client.mjs +4495 -3855
  151. package/dist/client/{courseRegistration-QZ67PVHO.mjs → courseRegistration-UU2KMPSQ.mjs} +3 -3
  152. package/dist/client/{eventCalendar-V3BDHQNT.mjs → eventCalendar-WIVNS2TM.mjs} +6 -6
  153. package/dist/client/{eventCombined-XYFRN2RG.mjs → eventCombined-P3G5MW4J.mjs} +6 -6
  154. package/dist/client/{eventDetails-TFE5TWKV.mjs → eventDetails-2VHJ2RDG.mjs} +6 -6
  155. package/dist/client/{eventListing-IQ6AGWZ6.mjs → eventListing-TGO6JI3R.mjs} +6 -6
  156. package/dist/client/{eventRegistration-WGJVFKQJ.mjs → eventRegistration-B46HEJES.mjs} +6 -6
  157. package/dist/client/{form-6UZY6RUA.mjs → form-VKRTFUNQ.mjs} +1 -1
  158. package/dist/client/{headerSection-RSFXY6V3.mjs → headerSection-XUX4ZJLO.mjs} +2 -2
  159. package/dist/client/hooks.mjs +34 -3
  160. package/dist/client/{locationMap-24FH67I4.mjs → locationMap-NQFI5MJO.mjs} +2 -2
  161. package/dist/client/{newsletterForm-QVL3MLTN.mjs → newsletterForm-P2GETCQK.mjs} +1 -1
  162. package/dist/client/{productDetail-ZDYN3G4T.mjs → productDetail-7NQ7O5IF.mjs} +4 -4
  163. package/dist/client/{productList-4BMJLQHZ.mjs → productList-RX6ZJ7BL.mjs} +4 -4
  164. package/dist/client/rendering/client.mjs +4170 -3768
  165. package/dist/client/rendering/islands.mjs +18 -18
  166. package/dist/client/rendering.mjs +1700 -1065
  167. package/dist/client/{shop-U5C634FF.mjs → shop-BHN5AKY6.mjs} +4 -4
  168. package/dist/preview-next/before-render.mjs +14 -0
  169. package/dist/preview-next/client/runtime.mjs +5 -5
  170. package/dist/preview-next/middleware.mjs +14 -0
  171. package/dist/{sdk-runtime-VGV46WVB.mjs → sdk-runtime-X2LXQ5IC.mjs} +6 -6
  172. package/dist/server/components.mjs +3255 -2827
  173. package/dist/server/config-template-validation.mjs +29 -20
  174. package/dist/server/config-validation.mjs +36 -4
  175. package/dist/server/config.mjs +36 -4
  176. package/dist/server/data.mjs +34 -3
  177. package/dist/server/index.mjs +44 -1
  178. package/dist/server/next/middleware.mjs +120 -0
  179. package/dist/server/next.mjs +3405 -2859
  180. package/dist/server/page-converter.mjs +20 -3
  181. package/dist/server/prebuild.mjs +1 -1
  182. package/dist/server/rendering/server.mjs +3264 -2837
  183. package/dist/server/rendering.mjs +3295 -2844
  184. package/dist/server/routing.mjs +35 -4
  185. package/dist/server/server.mjs +2358 -2188
  186. package/dist/server/theme-bridge.mjs +140 -0
  187. package/dist/styles/index.css +139 -0
  188. package/package.json +5 -1
  189. package/dist/SdkPreviewModeRuntime-NHTLRNQD.mjs +0 -8
@@ -1,9 +1,9 @@
1
1
  "use client";
2
- import { unwrapResponse, ApiRequestError, ApiEnvelopeError, extractApiEnvelopeErrorDetails } from './chunk-NT76QGIJ.mjs';
2
+ import { unwrapResponse, ApiRequestError, ApiEnvelopeError, extractApiEnvelopeErrorDetails } from './chunk-7ED5UNHL.mjs';
3
3
  import { __commonJS, __export, __toESM } from './chunk-R7POPVJR.mjs';
4
4
  import * as React61 from 'react';
5
5
  import React61__default, { createContext, forwardRef, useContext, createElement, useRef, useMemo, useEffect, useState, useCallback, useImperativeHandle, useLayoutEffect, memo, createRef, Component as Component$1, useDebugValue, useId as useId$1, useSyncExternalStore, isValidElement, cloneElement, useReducer, startTransition } from 'react';
6
- import z40, { z } from 'zod';
6
+ import z41, { z } from 'zod';
7
7
  import { jsx, Fragment, jsxs } from 'react/jsx-runtime';
8
8
  import deepEqual2 from 'fast-deep-equal';
9
9
  import { useQueryClient, useMutation, useQuery } from '@tanstack/react-query';
@@ -31543,6 +31543,11 @@ var textFieldSchema = baseFieldSchema.extend({
31543
31543
  var richTextFieldSchema = baseFieldSchema.extend({
31544
31544
  type: z.literal("richText")
31545
31545
  });
31546
+ var inlineTextFieldSchema = baseFieldSchema.extend({
31547
+ type: z.literal("inlineText"),
31548
+ maxLength: z.number().int().positive().optional(),
31549
+ plainTextField: z.string().min(1).optional()
31550
+ });
31546
31551
  var mediaFieldSchema = baseFieldSchema.extend({
31547
31552
  type: z.literal("media"),
31548
31553
  // Keep full MEDIA_KINDS parse compatibility for pre-file-field manifests.
@@ -31865,6 +31870,7 @@ function getFieldSchemaInternal() {
31865
31870
  _fieldSchemaInternal = z.discriminatedUnion("type", [
31866
31871
  textFieldSchema,
31867
31872
  richTextFieldSchema,
31873
+ inlineTextFieldSchema,
31868
31874
  mediaFieldSchema,
31869
31875
  fileFieldSchema,
31870
31876
  booleanFieldSchema,
@@ -32048,6 +32054,205 @@ z.object({
32048
32054
  tags: z.array(z.string()).optional(),
32049
32055
  icon: z.string().optional()
32050
32056
  });
32057
+ var inlineTextAccentTones = ["accent", "brand", "contrast"];
32058
+ var inlineTextHighlightTones = ["soft", "accent", "brand"];
32059
+ var inlineTextMarkSchema = z.discriminatedUnion("kind", [
32060
+ z.object({ kind: z.literal("strong") }),
32061
+ z.object({ kind: z.literal("emphasis") }),
32062
+ z.object({
32063
+ kind: z.literal("accent"),
32064
+ tone: z.enum(inlineTextAccentTones)
32065
+ }),
32066
+ z.object({
32067
+ kind: z.literal("highlight"),
32068
+ tone: z.enum(inlineTextHighlightTones)
32069
+ })
32070
+ ]);
32071
+ var inlineTextRunSchema = z.object({
32072
+ text: z.string(),
32073
+ marks: z.array(inlineTextMarkSchema).optional()
32074
+ });
32075
+ z.array(inlineTextRunSchema);
32076
+ var MARK_ORDER = {
32077
+ strong: 0,
32078
+ emphasis: 1,
32079
+ accent: 2,
32080
+ highlight: 3
32081
+ };
32082
+ function plainTextToInlineText(value) {
32083
+ return normalizeInlineText(value.length > 0 ? [{ text: value }] : []);
32084
+ }
32085
+ function inlineTextToPlainText(value) {
32086
+ return value.map((run3) => run3.text).join("");
32087
+ }
32088
+ function isInlineTextEmpty(value) {
32089
+ return inlineTextToPlainText(value).trim().length === 0;
32090
+ }
32091
+ function coerceInlineTextWithFallback(value, fallbackPlainText) {
32092
+ const parsed = parseInlineTextFromUnknown(value);
32093
+ if (parsed.ok && !isInlineTextEmpty(parsed.value)) {
32094
+ return parsed.value;
32095
+ }
32096
+ if (fallbackPlainText && fallbackPlainText.length > 0) {
32097
+ return plainTextToInlineText(fallbackPlainText);
32098
+ }
32099
+ return parsed.ok ? parsed.value : [];
32100
+ }
32101
+ function parseInlineTextFromUnknown(value) {
32102
+ if (!Array.isArray(value)) {
32103
+ return { ok: false, error: { kind: "not-array" } };
32104
+ }
32105
+ const runs = [];
32106
+ for (let index2 = 0; index2 < value.length; index2 += 1) {
32107
+ const parsed = inlineTextRunSchema.safeParse(value[index2]);
32108
+ if (!parsed.success) {
32109
+ return { ok: false, error: { kind: "invalid-run", index: index2 } };
32110
+ }
32111
+ runs.push(parsed.data);
32112
+ }
32113
+ return { ok: true, value: normalizeInlineText(runs) };
32114
+ }
32115
+ function normalizeInlineText(value) {
32116
+ const normalized = [];
32117
+ for (const run3 of value) {
32118
+ if (run3.text.length === 0) continue;
32119
+ const marks = normalizeInlineTextMarks(run3.marks ?? []);
32120
+ const nextRun = marks.length > 0 ? { text: run3.text, marks } : { text: run3.text };
32121
+ const previous = normalized[normalized.length - 1];
32122
+ if (previous && inlineTextMarksEqual(previous.marks ?? [], nextRun.marks ?? [])) {
32123
+ normalized[normalized.length - 1] = previous.marks && previous.marks.length > 0 ? { text: previous.text + nextRun.text, marks: previous.marks } : { text: previous.text + nextRun.text };
32124
+ continue;
32125
+ }
32126
+ normalized.push(nextRun);
32127
+ }
32128
+ return normalized;
32129
+ }
32130
+ function normalizeInlineTextMarks(marks) {
32131
+ let strong = null;
32132
+ let emphasis = null;
32133
+ let accent = null;
32134
+ let highlight = null;
32135
+ for (const mark of marks) {
32136
+ switch (mark.kind) {
32137
+ case "strong":
32138
+ strong = { kind: "strong" };
32139
+ break;
32140
+ case "emphasis":
32141
+ emphasis = { kind: "emphasis" };
32142
+ break;
32143
+ case "accent":
32144
+ accent = { kind: "accent", tone: mark.tone };
32145
+ break;
32146
+ case "highlight":
32147
+ highlight = { kind: "highlight", tone: mark.tone };
32148
+ break;
32149
+ }
32150
+ }
32151
+ return [strong, emphasis, accent, highlight].filter((mark) => mark !== null).sort((left, right) => MARK_ORDER[left.kind] - MARK_ORDER[right.kind]);
32152
+ }
32153
+ function inlineTextMarksEqual(left, right) {
32154
+ const normalizedLeft = normalizeInlineTextMarks(left);
32155
+ const normalizedRight = normalizeInlineTextMarks(right);
32156
+ if (normalizedLeft.length !== normalizedRight.length) return false;
32157
+ return normalizedLeft.every((mark, index2) => inlineTextMarkEqual(mark, normalizedRight[index2]));
32158
+ }
32159
+ function inlineTextEqual(left, right) {
32160
+ const normalizedLeft = normalizeInlineText(left);
32161
+ const normalizedRight = normalizeInlineText(right);
32162
+ if (normalizedLeft.length !== normalizedRight.length) return false;
32163
+ return normalizedLeft.every((leftRun, index2) => {
32164
+ const rightRun = normalizedRight[index2];
32165
+ return rightRun !== void 0 && leftRun.text === rightRun.text && inlineTextMarksEqual(leftRun.marks ?? [], rightRun.marks ?? []);
32166
+ });
32167
+ }
32168
+ function inlineTextMarkEqual(left, right) {
32169
+ if (!right || left.kind !== right.kind) return false;
32170
+ switch (left.kind) {
32171
+ case "strong":
32172
+ case "emphasis":
32173
+ return true;
32174
+ case "accent":
32175
+ return right.kind === "accent" && left.tone === right.tone;
32176
+ case "highlight":
32177
+ return right.kind === "highlight" && left.tone === right.tone;
32178
+ }
32179
+ }
32180
+ function applyInlineTextMarkToRange(value, range, mark) {
32181
+ return mapInlineTextRange(value, range, (marks) => normalizeInlineTextMarks([...marks, mark]));
32182
+ }
32183
+ function removeInlineTextMarkFromRange(value, range, kind) {
32184
+ return mapInlineTextRange(value, range, (marks) => marks.filter((mark) => mark.kind !== kind));
32185
+ }
32186
+ function replaceInlineTextRange(value, range, replacement) {
32187
+ const textLength = inlineTextToPlainText(value).length;
32188
+ const start = Math.max(0, Math.min(range.start, range.end, textLength));
32189
+ const end = Math.max(0, Math.min(Math.max(range.start, range.end), textLength));
32190
+ return normalizeInlineText([
32191
+ ...sliceInlineText(value, 0, start),
32192
+ ...normalizeInlineText(replacement),
32193
+ ...sliceInlineText(value, end, textLength)
32194
+ ]);
32195
+ }
32196
+ function truncateInlineText(value, maxLength) {
32197
+ if (typeof maxLength !== "number" || !Number.isFinite(maxLength) || maxLength < 0) {
32198
+ return normalizeInlineText(value);
32199
+ }
32200
+ const next = [];
32201
+ let remaining = maxLength;
32202
+ for (const run3 of normalizeInlineText(value)) {
32203
+ if (remaining <= 0) break;
32204
+ const text2 = run3.text.slice(0, remaining);
32205
+ next.push(withMarks(text2, run3.marks ?? []));
32206
+ remaining -= text2.length;
32207
+ }
32208
+ return normalizeInlineText(next);
32209
+ }
32210
+ function sliceInlineText(value, start, end) {
32211
+ if (start >= end) return [];
32212
+ const next = [];
32213
+ let offset4 = 0;
32214
+ for (const run3 of normalizeInlineText(value)) {
32215
+ const runStart = offset4;
32216
+ const runEnd = offset4 + run3.text.length;
32217
+ offset4 = runEnd;
32218
+ if (runEnd <= start || runStart >= end) continue;
32219
+ const localStart = Math.max(0, start - runStart);
32220
+ const localEnd = Math.min(run3.text.length, end - runStart);
32221
+ next.push(withMarks(run3.text.slice(localStart, localEnd), run3.marks ?? []));
32222
+ }
32223
+ return normalizeInlineText(next);
32224
+ }
32225
+ function mapInlineTextRange(value, range, mapMarks) {
32226
+ const start = Math.max(0, Math.min(range.start, range.end));
32227
+ const end = Math.max(0, Math.max(range.start, range.end));
32228
+ if (start === end) return normalizeInlineText(value);
32229
+ const next = [];
32230
+ let offset4 = 0;
32231
+ for (const run3 of normalizeInlineText(value)) {
32232
+ const runStart = offset4;
32233
+ const runEnd = offset4 + run3.text.length;
32234
+ offset4 = runEnd;
32235
+ if (runEnd <= start || runStart >= end) {
32236
+ next.push(run3);
32237
+ continue;
32238
+ }
32239
+ const localStart = Math.max(0, start - runStart);
32240
+ const localEnd = Math.min(run3.text.length, end - runStart);
32241
+ const marks = run3.marks ?? [];
32242
+ if (localStart > 0) {
32243
+ next.push(withMarks(run3.text.slice(0, localStart), marks));
32244
+ }
32245
+ next.push(withMarks(run3.text.slice(localStart, localEnd), mapMarks(marks)));
32246
+ if (localEnd < run3.text.length) {
32247
+ next.push(withMarks(run3.text.slice(localEnd), marks));
32248
+ }
32249
+ }
32250
+ return normalizeInlineText(next);
32251
+ }
32252
+ function withMarks(text2, marks) {
32253
+ const normalized = normalizeInlineTextMarks(marks);
32254
+ return normalized.length > 0 ? { text: text2, marks: normalized } : { text: text2 };
32255
+ }
32051
32256
 
32052
32257
  // ../blocks/src/system/icons/ids.ts
32053
32258
  var GENERATED_ICON_SET_ID_PATTERN = /^generated-icon-set:[a-z0-9][a-z0-9:_-]{0,107}$/u;
@@ -32875,6 +33080,13 @@ function formatFieldPath(path) {
32875
33080
  function toZodIssuePath(path) {
32876
33081
  return [...path];
32877
33082
  }
33083
+ function parseFieldPathKey(key) {
33084
+ if (!key) return [];
33085
+ return key.split(".").map((segment) => {
33086
+ const numeric2 = Number(segment);
33087
+ return Number.isInteger(numeric2) && String(numeric2) === segment ? numeric2 : segment;
33088
+ });
33089
+ }
32878
33090
  function fieldIssueToMessage(issue2) {
32879
33091
  switch (issue2.kind) {
32880
33092
  case "required":
@@ -32913,6 +33125,8 @@ function fieldIssueToMessage(issue2) {
32913
33125
  return `${issue2.label} must have at most ${issue2.maximum} ${pluralize(issue2.itemLabel, issue2.maximum)}`;
32914
33126
  case "invalidRichText":
32915
33127
  return `${issue2.label} must be valid rich text`;
33128
+ case "invalidInlineText":
33129
+ return `${issue2.label} must be valid styled text`;
32916
33130
  case "invalidMedia":
32917
33131
  return `${issue2.label} must be a valid media item`;
32918
33132
  case "invalidLink":
@@ -33001,6 +33215,16 @@ function deriveFieldValidationPlan(field, path = [field.id]) {
33001
33215
  );
33002
33216
  case "richText":
33003
33217
  return makePlan("richText", "object", field, path, required, commonConstraints(required, { kind: "richTextDoc" }));
33218
+ case "inlineText": {
33219
+ const constraints = commonConstraints(required, { kind: "inlineText" });
33220
+ if (typeof field.maxLength === "number") {
33221
+ constraints.push({ kind: "maxPlainTextLength", maximum: field.maxLength });
33222
+ }
33223
+ return {
33224
+ ...makePlan("inlineText", "array", field, path, required, constraints),
33225
+ ...field.plainTextField ? { plainTextFallbackPath: parseFieldPathKey(field.plainTextField) } : {}
33226
+ };
33227
+ }
33004
33228
  case "media":
33005
33229
  case "file":
33006
33230
  return {
@@ -33125,6 +33349,7 @@ function normalizeStoredContentValues(plans, content, options = {}) {
33125
33349
  const plan = planMap.get(key);
33126
33350
  normalized[key] = plan ? normalizeStoredFieldValueWithContext(plan, value, ctx) : value;
33127
33351
  }
33352
+ normalizeInlineTextFallbacks(plans, normalized, ctx);
33128
33353
  return normalized;
33129
33354
  }
33130
33355
  function normalizeStoredFieldValueWithContext(plan, value, ctx) {
@@ -33140,6 +33365,7 @@ function normalizeStoredFieldValueWithContext(plan, value, ctx) {
33140
33365
  case "number":
33141
33366
  case "boolean":
33142
33367
  case "richText":
33368
+ case "inlineText":
33143
33369
  case "media":
33144
33370
  case "link":
33145
33371
  case "select":
@@ -33155,12 +33381,9 @@ function normalizeStoredObjectChildren(children, value, ctx) {
33155
33381
  }
33156
33382
  const normalized = { ...value };
33157
33383
  for (const child of children) {
33158
- normalized[child.fieldId] = normalizeStoredFieldValueWithContext(
33159
- child,
33160
- normalized[child.fieldId],
33161
- ctx
33162
- );
33384
+ normalized[child.fieldId] = normalizeStoredFieldValueWithContext(child, normalized[child.fieldId], ctx);
33163
33385
  }
33386
+ normalizeInlineTextFallbacks(children, normalized, ctx);
33164
33387
  return normalized;
33165
33388
  }
33166
33389
  function normalizeStoredRepeaterItems(plan, value, ctx) {
@@ -33191,6 +33414,7 @@ function normalizeFieldValue(plan, value, ctx) {
33191
33414
  return normalizeRepeaterItems(plan, value, ctx);
33192
33415
  case "boolean":
33193
33416
  case "richText":
33417
+ case "inlineText":
33194
33418
  case "link":
33195
33419
  case "select":
33196
33420
  case "passthrough":
@@ -33216,8 +33440,24 @@ function normalizeObjectChildren(children, value, ctx) {
33216
33440
  for (const child of children) {
33217
33441
  normalized[child.fieldId] = normalizeFieldValue(child, normalized[child.fieldId], ctx);
33218
33442
  }
33443
+ normalizeInlineTextFallbacks(children, normalized, ctx);
33219
33444
  return normalized;
33220
33445
  }
33446
+ function normalizeInlineTextFallbacks(plans, values, ctx) {
33447
+ for (const plan of plans) {
33448
+ if (plan.kind !== "inlineText" || !plan.plainTextFallbackPath) continue;
33449
+ if (!isMissingForPlan(plan, values[plan.fieldId])) continue;
33450
+ const fallback2 = getAtFieldPath(values, plan.plainTextFallbackPath);
33451
+ if (typeof fallback2 !== "string" || fallback2.trim().length === 0) continue;
33452
+ values[plan.fieldId] = normalizeFieldValue(plan, plainTextToInlineText(fallback2), ctx);
33453
+ }
33454
+ }
33455
+ function getAtFieldPath(source, path) {
33456
+ return path.reduce((current, segment) => {
33457
+ if (!current || typeof current !== "object" || Array.isArray(current)) return void 0;
33458
+ return current[String(segment)];
33459
+ }, source);
33460
+ }
33221
33461
  function normalizeRepeaterItems(plan, value, ctx) {
33222
33462
  if (!isUnknownArray(value)) return value;
33223
33463
  return value.map((item) => {
@@ -33255,6 +33495,8 @@ function validateNormalizedFieldValue(plan, value, ctx) {
33255
33495
  return validateSelectPlan(plan, value);
33256
33496
  case "richText":
33257
33497
  return isValidRichTextDoc(value) ? [] : [issue(plan, "invalidRichText")];
33498
+ case "inlineText":
33499
+ return validateInlineTextPlan(plan, value);
33258
33500
  case "media":
33259
33501
  return isPlainObject(value) ? [] : [issue(plan, "invalidMedia")];
33260
33502
  case "link":
@@ -33428,6 +33670,7 @@ function rebaseFieldPlanPath(plan, fromPrefix, toPrefix) {
33428
33670
  case "number":
33429
33671
  case "boolean":
33430
33672
  case "richText":
33673
+ case "inlineText":
33431
33674
  case "media":
33432
33675
  case "link":
33433
33676
  case "select":
@@ -33440,6 +33683,18 @@ function rebaseFieldPlanPath(plan, fromPrefix, toPrefix) {
33440
33683
  return assertNever4(plan);
33441
33684
  }
33442
33685
  }
33686
+ function validateInlineTextPlan(plan, value) {
33687
+ const parsed = parseInlineTextFromUnknown(value);
33688
+ if (!parsed.ok) return [issue(plan, "invalidInlineText")];
33689
+ const text2 = inlineTextToPlainText(parsed.value);
33690
+ const lengthIssue = plan.constraints.find(
33691
+ (constraint) => constraint.kind === "maxPlainTextLength"
33692
+ );
33693
+ if (lengthIssue && text2.length > lengthIssue.maximum) {
33694
+ return [issue(plan, "tooLong", { maximum: lengthIssue.maximum })];
33695
+ }
33696
+ return [];
33697
+ }
33443
33698
  function rebaseFieldPath(path, fromPrefix, toPrefix) {
33444
33699
  if (!startsWithFieldPath(path, fromPrefix)) {
33445
33700
  throw new Error(`Cannot rebase field path ${formatFieldPath(path)} from ${formatFieldPath(fromPrefix)}`);
@@ -33533,6 +33788,7 @@ function addFieldIssueToZodContext(zodCtx, validationIssue, rootPath) {
33533
33788
  case "tooFewItems":
33534
33789
  case "tooManyItems":
33535
33790
  case "invalidRichText":
33791
+ case "invalidInlineText":
33536
33792
  case "invalidMedia":
33537
33793
  case "invalidLink":
33538
33794
  case "invalidReference":
@@ -33580,6 +33836,7 @@ function findNestedFieldValidationPlan(plan, path) {
33580
33836
  case "number":
33581
33837
  case "boolean":
33582
33838
  case "richText":
33839
+ case "inlineText":
33583
33840
  case "media":
33584
33841
  case "link":
33585
33842
  case "select":
@@ -36709,44 +36966,44 @@ var styleTagsSchema = z.object({
36709
36966
  motion: z.enum(STYLE_AXIS_VALUES.motion).optional(),
36710
36967
  era: z.enum(STYLE_AXIS_VALUES.era).optional()
36711
36968
  });
36712
- var hotspotSchema = z40.object({
36713
- x: z40.number().min(0).max(1),
36714
- y: z40.number().min(0).max(1),
36715
- radius: z40.number().optional()
36716
- });
36717
- var rotationSchema = z40.union([z40.literal(0), z40.literal(90), z40.literal(180), z40.literal(270)]);
36718
- var rectSchema = z40.tuple([z40.number(), z40.number(), z40.number(), z40.number()]);
36719
- var aspectCropSchema = z40.object({
36720
- aspect: z40.preprocess((value) => value == null ? void 0 : value, z40.string().optional()),
36721
- rect: z40.preprocess((value) => value == null ? void 0 : value, rectSchema.optional()),
36722
- hotspot: z40.preprocess((value) => value == null ? void 0 : value, hotspotSchema.optional()),
36723
- rotation: z40.preprocess((value) => value == null ? void 0 : value, rotationSchema.optional())
36724
- });
36725
- var transformSchema = z40.object({
36726
- aspectCrops: z40.preprocess((value) => {
36969
+ var hotspotSchema = z41.object({
36970
+ x: z41.number().min(0).max(1),
36971
+ y: z41.number().min(0).max(1),
36972
+ radius: z41.number().optional()
36973
+ });
36974
+ var rotationSchema = z41.union([z41.literal(0), z41.literal(90), z41.literal(180), z41.literal(270)]);
36975
+ var rectSchema = z41.tuple([z41.number(), z41.number(), z41.number(), z41.number()]);
36976
+ var aspectCropSchema = z41.object({
36977
+ aspect: z41.preprocess((value) => value == null ? void 0 : value, z41.string().optional()),
36978
+ rect: z41.preprocess((value) => value == null ? void 0 : value, rectSchema.optional()),
36979
+ hotspot: z41.preprocess((value) => value == null ? void 0 : value, hotspotSchema.optional()),
36980
+ rotation: z41.preprocess((value) => value == null ? void 0 : value, rotationSchema.optional())
36981
+ });
36982
+ var transformSchema = z41.object({
36983
+ aspectCrops: z41.preprocess((value) => {
36727
36984
  if (!value || typeof value !== "object" || Array.isArray(value)) {
36728
36985
  return void 0;
36729
36986
  }
36730
36987
  return value;
36731
- }, z40.record(z40.string(), aspectCropSchema.catch({}))).optional(),
36988
+ }, z41.record(z41.string(), aspectCropSchema.catch({}))).optional(),
36732
36989
  rect: rectSchema.optional(),
36733
36990
  hotspot: hotspotSchema.optional(),
36734
36991
  rotation: rotationSchema.optional()
36735
36992
  });
36736
- var mediaSchema = z40.object({
36737
- type: z40.enum(["image", "video", "audio", "document", "spreadsheet", "archive"]),
36738
- purpose: z40.string().optional(),
36739
- placeholder: z40.boolean().default(true).optional(),
36740
- assetId: z40.string().optional(),
36741
- identifier: z40.string().optional(),
36742
- src: z40.string().optional(),
36743
- alt: z40.string().optional(),
36744
- filename: z40.string().optional(),
36745
- mimeType: z40.string().optional(),
36746
- width: z40.number().optional(),
36747
- height: z40.number().optional(),
36748
- storageBucket: z40.string().optional(),
36749
- storagePath: z40.string().optional(),
36993
+ var mediaSchema = z41.object({
36994
+ type: z41.enum(["image", "video", "audio", "document", "spreadsheet", "archive"]),
36995
+ purpose: z41.string().optional(),
36996
+ placeholder: z41.boolean().default(true).optional(),
36997
+ assetId: z41.string().optional(),
36998
+ identifier: z41.string().optional(),
36999
+ src: z41.string().optional(),
37000
+ alt: z41.string().optional(),
37001
+ filename: z41.string().optional(),
37002
+ mimeType: z41.string().optional(),
37003
+ width: z41.number().optional(),
37004
+ height: z41.number().optional(),
37005
+ storageBucket: z41.string().optional(),
37006
+ storagePath: z41.string().optional(),
36750
37007
  transform: transformSchema.optional()
36751
37008
  });
36752
37009
 
@@ -52057,8 +52314,16 @@ var heroCopyFragment = defineFragment({
52057
52314
  id: "headline",
52058
52315
  type: "text",
52059
52316
  label: "Headline",
52317
+ maxLength: 120,
52318
+ ui: { hidden: true }
52319
+ },
52320
+ {
52321
+ id: "headlineInline",
52322
+ type: "inlineText",
52323
+ label: "Headline",
52060
52324
  required: true,
52061
- maxLength: 120
52325
+ maxLength: 120,
52326
+ plainTextField: "headline"
52062
52327
  },
52063
52328
  {
52064
52329
  id: "subheadline",
@@ -52083,9 +52348,12 @@ var heroCopyFragment = defineFragment({
52083
52348
  as: "h1",
52084
52349
  // heading-display: uses fluid typography from theme (--fs-h1-display-fluid)
52085
52350
  // Color in blocks-static/index.css (.hero-headline)
52086
- className: "hero-headline heading-display"
52351
+ className: "hero-headline heading-display",
52352
+ // Resolved against top-level block content; keep this beside the sibling headline field.
52353
+ inlineTextFallbackPath: "headline",
52354
+ maxLength: 120
52087
52355
  },
52088
- bind("content.headline")
52356
+ bind("content.headlineInline")
52089
52357
  ),
52090
52358
  text(
52091
52359
  {
@@ -59950,66 +60218,66 @@ var PUBLIC_DOWNLOAD_MEDIA_TYPES = [
59950
60218
  "archive",
59951
60219
  "audio"
59952
60220
  ];
59953
- var hotspotSchema2 = z40.object({
59954
- x: z40.number().min(0).max(1),
59955
- y: z40.number().min(0).max(1),
59956
- radius: z40.number().optional()
59957
- });
59958
- var rotationSchema2 = z40.union([z40.literal(0), z40.literal(90), z40.literal(180), z40.literal(270)]);
59959
- var rectSchema2 = z40.tuple([z40.number(), z40.number(), z40.number(), z40.number()]);
59960
- var aspectCropSchema2 = z40.object({
59961
- aspect: z40.preprocess((value) => value == null ? void 0 : value, z40.string().optional()),
59962
- rect: z40.preprocess((value) => value == null ? void 0 : value, rectSchema2.optional()),
59963
- hotspot: z40.preprocess((value) => value == null ? void 0 : value, hotspotSchema2.optional()),
59964
- rotation: z40.preprocess((value) => value == null ? void 0 : value, rotationSchema2.optional())
59965
- });
59966
- var transformSchema2 = z40.object({
59967
- aspectCrops: z40.preprocess((value) => {
60221
+ var hotspotSchema2 = z41.object({
60222
+ x: z41.number().min(0).max(1),
60223
+ y: z41.number().min(0).max(1),
60224
+ radius: z41.number().optional()
60225
+ });
60226
+ var rotationSchema2 = z41.union([z41.literal(0), z41.literal(90), z41.literal(180), z41.literal(270)]);
60227
+ var rectSchema2 = z41.tuple([z41.number(), z41.number(), z41.number(), z41.number()]);
60228
+ var aspectCropSchema2 = z41.object({
60229
+ aspect: z41.preprocess((value) => value == null ? void 0 : value, z41.string().optional()),
60230
+ rect: z41.preprocess((value) => value == null ? void 0 : value, rectSchema2.optional()),
60231
+ hotspot: z41.preprocess((value) => value == null ? void 0 : value, hotspotSchema2.optional()),
60232
+ rotation: z41.preprocess((value) => value == null ? void 0 : value, rotationSchema2.optional())
60233
+ });
60234
+ var transformSchema2 = z41.object({
60235
+ aspectCrops: z41.preprocess((value) => {
59968
60236
  if (!value || typeof value !== "object" || Array.isArray(value)) {
59969
60237
  return void 0;
59970
60238
  }
59971
60239
  return value;
59972
- }, z40.record(z40.string(), aspectCropSchema2.catch({}))).optional(),
60240
+ }, z41.record(z41.string(), aspectCropSchema2.catch({}))).optional(),
59973
60241
  rect: rectSchema2.optional(),
59974
60242
  hotspot: hotspotSchema2.optional(),
59975
60243
  rotation: rotationSchema2.optional()
59976
60244
  });
59977
- var mediaPosterSchema = z40.discriminatedUnion("tag", [
59978
- z40.object({
59979
- tag: z40.literal("storage"),
59980
- assetId: z40.string().optional(),
59981
- storageBucket: z40.string().min(1),
59982
- storagePath: z40.string().min(1)
60245
+ var mediaPosterSchema = z41.discriminatedUnion("tag", [
60246
+ z41.object({
60247
+ tag: z41.literal("storage"),
60248
+ assetId: z41.string().optional(),
60249
+ storageBucket: z41.string().min(1),
60250
+ storagePath: z41.string().min(1)
59983
60251
  }),
59984
- z40.object({
59985
- tag: z40.literal("external-src"),
59986
- assetId: z40.string().optional(),
59987
- src: z40.string().url()
60252
+ z41.object({
60253
+ tag: z41.literal("external-src"),
60254
+ assetId: z41.string().optional(),
60255
+ src: z41.string().url()
59988
60256
  })
59989
60257
  ]);
59990
- var mediaBaseSchema = z40.object({
59991
- purpose: z40.string().optional(),
59992
- placeholder: z40.boolean().default(true).optional(),
59993
- assetId: z40.string().optional(),
59994
- identifier: z40.string().optional(),
59995
- src: z40.string().optional(),
59996
- alt: z40.string().optional(),
59997
- filename: z40.string().optional(),
59998
- mimeType: z40.string().optional(),
59999
- width: z40.number().optional(),
60000
- height: z40.number().optional(),
60001
- storageBucket: z40.string().optional(),
60002
- storagePath: z40.string().optional(),
60258
+ var mediaBaseSchema = z41.object({
60259
+ purpose: z41.string().optional(),
60260
+ placeholder: z41.boolean().default(true).optional(),
60261
+ assetId: z41.string().optional(),
60262
+ identifier: z41.string().optional(),
60263
+ src: z41.string().optional(),
60264
+ alt: z41.string().optional(),
60265
+ filename: z41.string().optional(),
60266
+ mimeType: z41.string().optional(),
60267
+ width: z41.number().optional(),
60268
+ height: z41.number().optional(),
60269
+ storageBucket: z41.string().optional(),
60270
+ storagePath: z41.string().optional(),
60003
60271
  poster: mediaPosterSchema.optional(),
60004
60272
  transform: transformSchema2.optional()
60005
60273
  });
60006
- var imageMediaSchema = mediaBaseSchema.extend({ type: z40.literal("image") });
60007
- var videoMediaSchema = mediaBaseSchema.extend({ type: z40.literal("video") });
60008
- var audioMediaSchema = mediaBaseSchema.extend({ type: z40.literal("audio") });
60009
- var documentMediaSchema = mediaBaseSchema.extend({ type: z40.literal("document") });
60010
- var spreadsheetMediaSchema = mediaBaseSchema.extend({ type: z40.literal("spreadsheet") });
60011
- var archiveMediaSchema = mediaBaseSchema.extend({ type: z40.literal("archive") });
60012
- var mediaSchema2 = z40.discriminatedUnion("type", [
60274
+ var imageMediaSchema = mediaBaseSchema.extend({ type: z41.literal("image") });
60275
+ var videoMediaSchema = mediaBaseSchema.extend({ type: z41.literal("video") });
60276
+ var audioMediaSchema = mediaBaseSchema.extend({ type: z41.literal("audio") });
60277
+ var documentMediaSchema = mediaBaseSchema.extend({ type: z41.literal("document") });
60278
+ var spreadsheetMediaSchema = mediaBaseSchema.extend({ type: z41.literal("spreadsheet") });
60279
+ var archiveMediaSchema = mediaBaseSchema.extend({ type: z41.literal("archive") });
60280
+ var mediaSchema2 = z41.discriminatedUnion("type", [
60013
60281
  imageMediaSchema,
60014
60282
  videoMediaSchema,
60015
60283
  audioMediaSchema,
@@ -60965,6 +61233,9 @@ function resolveDiscountContext(input) {
60965
61233
  if (!input.eventRequiresPayment) {
60966
61234
  return null;
60967
61235
  }
61236
+ if (input.ticketsCount <= 0) {
61237
+ return null;
61238
+ }
60968
61239
  if (selection?.method && selection.method !== "stripe") {
60969
61240
  return null;
60970
61241
  }
@@ -72605,6 +72876,123 @@ var FigureNode = ({
72605
72876
  ...props2
72606
72877
  }) => /* @__PURE__ */ jsx("figure", { ...props2 });
72607
72878
 
72879
+ // ../path-utils/src/index.ts
72880
+ var PATH_SEPARATOR_REGEX = /\./g;
72881
+ var BRACKET_ACCESS_REGEX = /\[([^\]]+)\]/g;
72882
+ function isRecord12(value) {
72883
+ return typeof value === "object" && value !== null && !Array.isArray(value);
72884
+ }
72885
+ function isPathContainer(value) {
72886
+ return Array.isArray(value) || isRecord12(value);
72887
+ }
72888
+ function createPathContainer(nextIsIndex) {
72889
+ return nextIsIndex ? [] : {};
72890
+ }
72891
+ function getContainerValue(container, segment) {
72892
+ if (typeof segment === "number") {
72893
+ return Array.isArray(container) ? container[segment] : void 0;
72894
+ }
72895
+ if (segment in container) {
72896
+ return Reflect.get(container, segment);
72897
+ }
72898
+ return void 0;
72899
+ }
72900
+ function ensureContainerProperty(container, key, nextIsIndex) {
72901
+ const existing = Reflect.get(container, key);
72902
+ if (isPathContainer(existing)) {
72903
+ return existing;
72904
+ }
72905
+ const nextContainer = createPathContainer(nextIsIndex);
72906
+ Reflect.set(container, key, nextContainer);
72907
+ return nextContainer;
72908
+ }
72909
+ function parsePath(path) {
72910
+ if (Array.isArray(path)) return path;
72911
+ const segments = [];
72912
+ const parts = path.split(PATH_SEPARATOR_REGEX);
72913
+ for (const raw of parts) {
72914
+ if (!raw) continue;
72915
+ const baseMatch = raw.match(/^[^\[]+/);
72916
+ if (baseMatch !== null) {
72917
+ const base2 = baseMatch[1] ?? baseMatch[0];
72918
+ if (/^\d+$/.test(base2)) {
72919
+ segments.push(Number(base2));
72920
+ } else {
72921
+ segments.push(base2);
72922
+ }
72923
+ }
72924
+ const bracketMatches = raw.matchAll(BRACKET_ACCESS_REGEX);
72925
+ for (const match2 of bracketMatches) {
72926
+ const token = match2[1] ?? "";
72927
+ if (token.startsWith('"') || token.startsWith("'")) {
72928
+ segments.push(token.slice(1, -1));
72929
+ } else if (/^\d+$/.test(token)) {
72930
+ segments.push(Number(token));
72931
+ } else {
72932
+ segments.push(token);
72933
+ }
72934
+ }
72935
+ if (baseMatch === null && !raw.includes("[")) {
72936
+ segments.push(raw);
72937
+ }
72938
+ }
72939
+ return segments;
72940
+ }
72941
+ function segmentsToPath(segments) {
72942
+ if (!segments.length) return void 0;
72943
+ return segments.map((s2) => String(s2)).join(".");
72944
+ }
72945
+ function siblingPath(path, siblingFieldPath) {
72946
+ const segments = parsePath(path);
72947
+ const siblingSegments = parsePath(siblingFieldPath);
72948
+ const parentSegments = segments.slice(0, -1);
72949
+ return segmentsToPath([...parentSegments, ...siblingSegments]) ?? siblingFieldPath;
72950
+ }
72951
+ function getAtPath(source, path) {
72952
+ const segments = parsePath(path);
72953
+ return segments.reduce((current, segment) => {
72954
+ if (current === void 0 || current === null) return void 0;
72955
+ if (!isPathContainer(current)) return void 0;
72956
+ return getContainerValue(current, segment);
72957
+ }, source);
72958
+ }
72959
+ function setAtPath(target, path, value) {
72960
+ const segments = parsePath(path);
72961
+ let current = target;
72962
+ for (let index2 = 0; index2 < segments.length; index2 += 1) {
72963
+ const segment = segments[index2];
72964
+ if (segment === void 0) continue;
72965
+ const isLast = index2 === segments.length - 1;
72966
+ const nextIsIndex = typeof segments[index2 + 1] === "number";
72967
+ if (isLast) {
72968
+ if (typeof segment === "number") {
72969
+ if (Array.isArray(current)) {
72970
+ current[segment] = value;
72971
+ }
72972
+ } else {
72973
+ Reflect.set(current, segment, value);
72974
+ }
72975
+ return;
72976
+ }
72977
+ if (typeof segment === "number") {
72978
+ if (Array.isArray(current)) {
72979
+ const existing = current[segment];
72980
+ if (isPathContainer(existing)) {
72981
+ current = existing;
72982
+ } else {
72983
+ const nextContainer = createPathContainer(nextIsIndex);
72984
+ current[segment] = nextContainer;
72985
+ current = nextContainer;
72986
+ }
72987
+ continue;
72988
+ }
72989
+ current = ensureContainerProperty(current, String(segment), nextIsIndex);
72990
+ continue;
72991
+ }
72992
+ current = ensureContainerProperty(current, segment, nextIsIndex);
72993
+ }
72994
+ }
72995
+
72608
72996
  // ../blocks/src/primitives/content/utils/sanitizeHref.ts
72609
72997
  var SAFE_PROTOCOLS = /* @__PURE__ */ new Set(["http:", "https:", "mailto:", "tel:"]);
72610
72998
  var CONTROL_CHARS_PATTERN = /[\u0000-\u001F\u007F]+/g;
@@ -72780,9 +73168,44 @@ function coerceRichTextDoc(value) {
72780
73168
  }
72781
73169
  return null;
72782
73170
  }
72783
- var TextNode = ({ value, children, blockId: _blockId, blockKind: _blockKind, blockContent: _blockContent, fragmentRegistry: _fragmentRegistry, pathBase: _pathBase, ...rest }) => {
72784
- return /* @__PURE__ */ jsx(Text, { ...rest, children: value ?? children });
73171
+ function renderInlineText(value) {
73172
+ return value.map((run3, index2) => renderRun(run3, index2));
73173
+ }
73174
+ function renderRun(run3, key) {
73175
+ return (run3.marks ?? []).reduceRight(
73176
+ (child, mark, index2) => renderMark(mark, `${String(key)}-${index2}`, child),
73177
+ run3.text
73178
+ );
73179
+ }
73180
+ function renderMark(mark, key, child) {
73181
+ switch (mark.kind) {
73182
+ case "strong":
73183
+ return /* @__PURE__ */ jsx("strong", { children: child }, key);
73184
+ case "emphasis":
73185
+ return /* @__PURE__ */ jsx("em", { children: child }, key);
73186
+ case "accent":
73187
+ return /* @__PURE__ */ jsx("span", { className: `rb-inline-text-accent rb-inline-text-accent-${mark.tone}`, children: child }, key);
73188
+ case "highlight":
73189
+ return /* @__PURE__ */ jsx("span", { className: `rb-inline-text-highlight rb-inline-text-highlight-${mark.tone}`, children: child }, key);
73190
+ }
73191
+ }
73192
+ var TextNode = ({ value, children, blockId: _blockId, blockKind: _blockKind, blockContent, fragmentRegistry: _fragmentRegistry, pathBase: _pathBase, inlineTextFallbackPath, ...rest }) => {
73193
+ const inlineText = parseInlineTextFromUnknown(value);
73194
+ if (inlineText.ok && !isInlineTextEmpty(inlineText.value)) {
73195
+ return /* @__PURE__ */ jsx(Text, { ...rest, children: renderInlineText(inlineText.value) });
73196
+ }
73197
+ const fallbackValue = inlineTextFallbackPath ? readStringPath(blockContent, inlineTextFallbackPath) : null;
73198
+ return /* @__PURE__ */ jsx(Text, { ...rest, children: fallbackValue ?? textNodeContent(value) ?? children });
72785
73199
  };
73200
+ function textNodeContent(value) {
73201
+ if (value === null || value === void 0) return null;
73202
+ if (typeof value === "string" || typeof value === "number") return value;
73203
+ return null;
73204
+ }
73205
+ function readStringPath(source, path) {
73206
+ const value = getAtPath(source, path);
73207
+ return typeof value === "string" ? value : null;
73208
+ }
72786
73209
  var RichTextNode = ({ value, blockId: _blockId, blockKind: _blockKind, blockContent: _blockContent, fragmentRegistry: _fragmentRegistry, pathBase: _pathBase, ...rest }) => {
72787
73210
  const doc3 = coerceRichTextDoc(value);
72788
73211
  return /* @__PURE__ */ jsx(RichText, { doc: doc3 ?? void 0, ...rest });
@@ -74009,12 +74432,12 @@ function resolveBookingSiteId(siteId, form2) {
74009
74432
  return siteId || form2?.siteId || "";
74010
74433
  }
74011
74434
  function normalizeBookingFormConfig(form2) {
74012
- if (!isRecord12(form2)) return null;
74435
+ if (!isRecord13(form2)) return null;
74013
74436
  const id = readNonEmptyString(form2.id);
74014
74437
  const name = readNonEmptyString(form2.name);
74015
74438
  if (!id || !name) return null;
74016
- const schemaSource = isRecord12(form2.schema) ? form2.schema : isRecord12(form2.schemaJson) ? form2.schemaJson : null;
74017
- const settingsSource = isRecord12(form2.settings) ? form2.settings : isRecord12(form2.settingsJson) ? form2.settingsJson : null;
74439
+ const schemaSource = isRecord13(form2.schema) ? form2.schema : isRecord13(form2.schemaJson) ? form2.schemaJson : null;
74440
+ const settingsSource = isRecord13(form2.settings) ? form2.settings : isRecord13(form2.settingsJson) ? form2.settingsJson : null;
74018
74441
  return {
74019
74442
  id,
74020
74443
  name,
@@ -74038,10 +74461,10 @@ function normalizeBookingServices(services) {
74038
74461
  if (Array.isArray(services)) {
74039
74462
  return services.filter(isBookingFormService).map(normalizeService);
74040
74463
  }
74041
- if (isRecord12(services) && "services" in services) {
74464
+ if (isRecord13(services) && "services" in services) {
74042
74465
  return Array.isArray(services.services) ? services.services.filter(isBookingFormService).map(normalizeService) : [];
74043
74466
  }
74044
- return isRecord12(services) ? Object.values(services).filter(isBookingFormService).map(normalizeService) : [];
74467
+ return isRecord13(services) ? Object.values(services).filter(isBookingFormService).map(normalizeService) : [];
74045
74468
  }
74046
74469
  function normalizeBookingSchema(value) {
74047
74470
  if (!value) return void 0;
@@ -74053,7 +74476,7 @@ function normalizeBookingSchema(value) {
74053
74476
  };
74054
74477
  }
74055
74478
  function readBookingFormField(value) {
74056
- if (!isRecord12(value)) return null;
74479
+ if (!isRecord13(value)) return null;
74057
74480
  const id = readNonEmptyString(value.id);
74058
74481
  const label = readNonEmptyString(value.label);
74059
74482
  const type = readBookingFieldType(value.type);
@@ -74099,7 +74522,7 @@ function readBookingFieldOptions(value) {
74099
74522
  return options.length > 0 ? options : void 0;
74100
74523
  }
74101
74524
  function readBookingFieldOption(value) {
74102
- if (!isRecord12(value)) return null;
74525
+ if (!isRecord13(value)) return null;
74103
74526
  const optionValue = readNonEmptyString(value.value);
74104
74527
  const label = readNonEmptyString(value.label);
74105
74528
  return optionValue && label ? { value: optionValue, label } : null;
@@ -74116,7 +74539,7 @@ function normalizeBookingSettings(value) {
74116
74539
  };
74117
74540
  }
74118
74541
  function isBookingFormService(value) {
74119
- return isRecord12(value) && typeof value.id === "string" && typeof value.siteId === "string" && typeof value.title === "string";
74542
+ return isRecord13(value) && typeof value.id === "string" && typeof value.siteId === "string" && typeof value.title === "string";
74120
74543
  }
74121
74544
  function collectBookingCustomFields(data) {
74122
74545
  const customFields = {};
@@ -74172,7 +74595,7 @@ function readStringArray(value) {
74172
74595
  const strings = value.filter((item) => typeof item === "string");
74173
74596
  return strings.length > 0 ? strings : void 0;
74174
74597
  }
74175
- function isRecord12(value) {
74598
+ function isRecord13(value) {
74176
74599
  return typeof value === "object" && value !== null;
74177
74600
  }
74178
74601
  function getBookingServicePaymentSelectionMode(service) {
@@ -77799,14 +78222,14 @@ function isDecoratedHeadingBlockKind(blockKind) {
77799
78222
  return blockKind === "block.intro" || blockKind === "block.feature-cards" || blockKind === "block.testimonials" || blockKind === "block.faq";
77800
78223
  }
77801
78224
  function readVariant(blockContent) {
77802
- if (!isRecord13(blockContent)) return void 0;
78225
+ if (!isRecord14(blockContent)) return void 0;
77803
78226
  const variant = blockContent.variant;
77804
78227
  return typeof variant === "string" ? variant : void 0;
77805
78228
  }
77806
78229
  function isFaqDecoratedVariant(variant) {
77807
78230
  return variant === "default" || variant === "question-columns";
77808
78231
  }
77809
- function isRecord13(value) {
78232
+ function isRecord14(value) {
77810
78233
  return typeof value === "object" && value !== null && !Array.isArray(value);
77811
78234
  }
77812
78235
  function buildHeadingDecorationWrapperClassName(className) {
@@ -77831,8 +78254,8 @@ var META_PATH_TO_STORE_KEY = {
77831
78254
  function mapMetaPathToStoreKey(path) {
77832
78255
  return META_PATH_TO_STORE_KEY[path] ?? path;
77833
78256
  }
77834
- var PATH_SEPARATOR_REGEX = /\./g;
77835
- var BRACKET_ACCESS_REGEX = /\[([^\]]+)\]/g;
78257
+ var PATH_SEPARATOR_REGEX2 = /\./g;
78258
+ var BRACKET_ACCESS_REGEX2 = /\[([^\]]+)\]/g;
77836
78259
  function parseBracketToken(token) {
77837
78260
  if (token.startsWith('"') || token.startsWith("'")) {
77838
78261
  return token.slice(1, -1);
@@ -77849,7 +78272,7 @@ function extractSegmentsFromPart(part) {
77849
78272
  if (baseMatch && baseMatch[1]) {
77850
78273
  segments.push(baseMatch[1]);
77851
78274
  }
77852
- const bracketMatches = Array.from(part.matchAll(BRACKET_ACCESS_REGEX));
78275
+ const bracketMatches = Array.from(part.matchAll(BRACKET_ACCESS_REGEX2));
77853
78276
  const bracketSegments = bracketMatches.map((match2) => match2[1] ?? "").filter((token) => token.length > 0).map(parseBracketToken);
77854
78277
  segments.push(...bracketSegments);
77855
78278
  if (!baseMatch && !part.includes("[")) {
@@ -77858,9 +78281,9 @@ function extractSegmentsFromPart(part) {
77858
78281
  return segments;
77859
78282
  }
77860
78283
  function splitPath(path) {
77861
- return path.split(PATH_SEPARATOR_REGEX).flatMap(extractSegmentsFromPart).filter((segment) => segment !== "");
78284
+ return path.split(PATH_SEPARATOR_REGEX2).flatMap(extractSegmentsFromPart).filter((segment) => segment !== "");
77862
78285
  }
77863
- function segmentsToPath(segments) {
78286
+ function segmentsToPath2(segments) {
77864
78287
  if (!segments.length) return void 0;
77865
78288
  return segments.map((s2) => String(s2)).join(".");
77866
78289
  }
@@ -77893,7 +78316,7 @@ function derivePreviewLinkedEntryFieldBinding(node, parsedBinding, context) {
77893
78316
  if (displaySegments.length === 0) return null;
77894
78317
  const scoped = [...context.scopes].reverse().find((entry) => entry.name === scopeName);
77895
78318
  if (!scoped) return null;
77896
- const displayPath = segmentsToPath(displaySegments);
78319
+ const displayPath = segmentsToPath2(displaySegments);
77897
78320
  if (!displayPath) return null;
77898
78321
  const eligibility = resolveLinkedEntryInlineFieldEligibility({
77899
78322
  entry: scoped.value,
@@ -78290,7 +78713,7 @@ function resolveBindingToEditorPath(fieldName, bindings, editableRouteMetadataFi
78290
78713
  function derivePreviewTextEditableTarget(parsedBinding, context) {
78291
78714
  if (!parsedBinding) return { kind: "read-only", reason: "missing-binding" };
78292
78715
  const abs = getAbsoluteSegments(parsedBinding.from, context);
78293
- const absolutePath = abs ? segmentsToPath(abs) : void 0;
78716
+ const absolutePath = abs ? segmentsToPath2(abs) : void 0;
78294
78717
  if (!absolutePath) return { kind: "read-only", reason: "unresolved-binding" };
78295
78718
  if (absolutePath !== "content" && !absolutePath.startsWith("content.")) {
78296
78719
  return { kind: "read-only", reason: "non-content-binding" };
@@ -78344,7 +78767,7 @@ function injectMediaSlotPath(props2, node, parsedBinding, context) {
78344
78767
  if (!parsedBinding) return props2;
78345
78768
  if (node.type !== "media") return props2;
78346
78769
  const abs = getAbsoluteSegments(parsedBinding.from, context);
78347
- const absolutePath = abs ? segmentsToPath(abs) : void 0;
78770
+ const absolutePath = abs ? segmentsToPath2(abs) : void 0;
78348
78771
  if (!absolutePath) return props2;
78349
78772
  if (absolutePath !== "content" && !absolutePath.startsWith("content.")) {
78350
78773
  return props2;
@@ -78762,6 +79185,7 @@ function collectNestedPreviewFieldConstraintEntries(field, path) {
78762
79185
  case "datetime":
78763
79186
  case "entryPicker":
78764
79187
  case "file":
79188
+ case "inlineText":
78765
79189
  case "link":
78766
79190
  case "media":
78767
79191
  case "number":
@@ -86861,6 +87285,103 @@ var containerResponsiveThemeCss = `/*
86861
87285
  line-height: 1.35;
86862
87286
  }
86863
87287
 
87288
+ :where(.theme-scope) :where([data-block="event-registration"]) .er-ticket-lines {
87289
+ display: grid;
87290
+ gap: 0.75rem;
87291
+ }
87292
+
87293
+ :where(.theme-scope) :where([data-block="event-registration"]) .er-ticket-line-list {
87294
+ display: grid;
87295
+ gap: 0.625rem;
87296
+ }
87297
+
87298
+ :where(.theme-scope) :where([data-block="event-registration"]) .er-ticket-line {
87299
+ display: grid;
87300
+ grid-template-columns: minmax(0, 1fr) auto;
87301
+ align-items: center;
87302
+ gap: 0.875rem;
87303
+ min-height: 4.75rem;
87304
+ padding: 0.875rem;
87305
+ border: 1px solid var(--er-border);
87306
+ border-radius: calc(var(--rb-block-radius) * 0.75);
87307
+ background: var(--er-control-bg);
87308
+ }
87309
+
87310
+ :where(.theme-scope) :where([data-block="event-registration"]) .er-ticket-line--disabled {
87311
+ color: var(--er-on-surface-disabled);
87312
+ background: var(--er-surface-muted);
87313
+ }
87314
+
87315
+ :where(.theme-scope) :where([data-block="event-registration"]) .er-ticket-line-main {
87316
+ min-width: 0;
87317
+ display: grid;
87318
+ gap: 0.25rem;
87319
+ }
87320
+
87321
+ :where(.theme-scope) :where([data-block="event-registration"]) .er-ticket-line-heading {
87322
+ display: flex;
87323
+ align-items: baseline;
87324
+ justify-content: space-between;
87325
+ gap: 0.75rem;
87326
+ }
87327
+
87328
+ :where(.theme-scope) :where([data-block="event-registration"]) .er-ticket-line-name {
87329
+ min-width: 0;
87330
+ font-size: 0.9375rem;
87331
+ font-weight: 600;
87332
+ line-height: 1.3;
87333
+ overflow-wrap: anywhere;
87334
+ }
87335
+
87336
+ :where(.theme-scope) :where([data-block="event-registration"]) .er-ticket-line-price {
87337
+ flex-shrink: 0;
87338
+ font-size: 0.875rem;
87339
+ font-weight: 600;
87340
+ line-height: 1.3;
87341
+ }
87342
+
87343
+ :where(.theme-scope) :where([data-block="event-registration"]) .er-ticket-line-detail {
87344
+ margin: 0;
87345
+ color: var(--er-on-surface-muted);
87346
+ font-size: 0.8125rem;
87347
+ line-height: 1.35;
87348
+ overflow-wrap: anywhere;
87349
+ }
87350
+
87351
+ :where(.theme-scope) :where([data-block="event-registration"]) .er-ticket-line-summary {
87352
+ padding: 0.75rem 0.875rem;
87353
+ border: 1px solid var(--er-summary-border);
87354
+ border-radius: calc(var(--rb-block-radius) * 0.75);
87355
+ background: var(--er-surface-muted);
87356
+ }
87357
+
87358
+ :where(.theme-scope) :where([data-block="event-registration"]) .er-ticket-line-summary-title {
87359
+ font-size: 0.875rem;
87360
+ font-weight: 600;
87361
+ line-height: 1.35;
87362
+ }
87363
+
87364
+ :where(.theme-scope) :where([data-block="event-registration"]) .er-ticket-line-summary-list {
87365
+ margin: 0.25rem 0 0;
87366
+ padding-left: 1.125rem;
87367
+ color: var(--er-on-surface-muted);
87368
+ font-size: 0.8125rem;
87369
+ line-height: 1.4;
87370
+ }
87371
+
87372
+ @container rb-site (max-width: 639px) {
87373
+ @scope ([data-rb-responsive-mode="container"]) to (:scope [data-rb-responsive-mode]) {
87374
+ :where(.theme-scope) :where([data-block="event-registration"]) .er-ticket-line {
87375
+ grid-template-columns: minmax(0, 1fr);
87376
+ align-items: stretch;
87377
+ }
87378
+
87379
+ :where(.theme-scope) :where([data-block="event-registration"]) .er-ticket-line .er-counter {
87380
+ justify-content: flex-start;
87381
+ }
87382
+ }
87383
+ }
87384
+
86864
87385
  /* Form inputs */
86865
87386
  :where(.theme-scope) :where([data-block="event-registration"]) .er-input {
86866
87387
  width: 100%;
@@ -90133,6 +90654,49 @@ var containerResponsiveThemeCss = `/*
90133
90654
  margin-top: 0.5rem;
90134
90655
  }
90135
90656
 
90657
+ /* =============================================================================
90658
+ * Shared: Inline Text Marks
90659
+ * =============================================================================
90660
+ */
90661
+
90662
+ :where(.theme-scope) .rb-inline-text-accent,
90663
+ :where(.theme-scope) .rb-inline-text-highlight {
90664
+ font: inherit;
90665
+ letter-spacing: inherit;
90666
+ text-transform: inherit;
90667
+ }
90668
+
90669
+ :where(.theme-scope) .rb-inline-text-accent-accent {
90670
+ color: rgb(var(--tb-accent));
90671
+ }
90672
+
90673
+ :where(.theme-scope) .rb-inline-text-accent-brand {
90674
+ color: rgb(var(--tb-primary));
90675
+ }
90676
+
90677
+ :where(.theme-scope) .rb-inline-text-accent-contrast {
90678
+ color: var(--section-text-color, rgb(var(--tb-text)));
90679
+ }
90680
+
90681
+ :where(.theme-scope) .rb-inline-text-highlight {
90682
+ border-radius: 0.22em;
90683
+ box-decoration-break: clone;
90684
+ -webkit-box-decoration-break: clone;
90685
+ padding: 0.02em 0.12em;
90686
+ }
90687
+
90688
+ :where(.theme-scope) .rb-inline-text-highlight-soft {
90689
+ background: color-mix(in oklab, var(--section-text-color, rgb(var(--tb-text))) 14%, transparent);
90690
+ }
90691
+
90692
+ :where(.theme-scope) .rb-inline-text-highlight-accent {
90693
+ background: color-mix(in oklab, rgb(var(--tb-accent)) 28%, transparent);
90694
+ }
90695
+
90696
+ :where(.theme-scope) .rb-inline-text-highlight-brand {
90697
+ background: color-mix(in oklab, rgb(var(--tb-primary)) 24%, transparent);
90698
+ }
90699
+
90136
90700
  /* =============================================================================
90137
90701
  * Block: Hero (Phase 2)
90138
90702
  * Uses theme palette vars directly (no Tier 3 vars needed)
@@ -95421,14 +95985,14 @@ function backgroundCapabilityFromModes(modeCapabilities) {
95421
95985
  };
95422
95986
  }
95423
95987
  function parseBackgroundOverrideFromContent(content) {
95424
- const sectionStyles = isRecord14(content._sectionStyles) ? content._sectionStyles : null;
95988
+ const sectionStyles = isRecord15(content._sectionStyles) ? content._sectionStyles : null;
95425
95989
  return parseBackgroundOverride(sectionStyles?.background);
95426
95990
  }
95427
95991
  function parseBackgroundOverride(value) {
95428
95992
  if (value === null || value === void 0) {
95429
95993
  return { kind: "supported", override: DEFAULT_BACKGROUND_OVERRIDE };
95430
95994
  }
95431
- if (!isRecord14(value)) {
95995
+ if (!isRecord15(value)) {
95432
95996
  return { kind: "legacy", reason: "unsupported-shape", background: {} };
95433
95997
  }
95434
95998
  if (Object.keys(value).length === 0) {
@@ -95509,7 +96073,7 @@ function serializeBackgroundOverride(override) {
95509
96073
  }
95510
96074
  }
95511
96075
  function applyBackgroundOverrideContentPatch(content, override) {
95512
- const sectionStyles = isRecord14(content._sectionStyles) ? content._sectionStyles : {};
96076
+ const sectionStyles = isRecord15(content._sectionStyles) ? content._sectionStyles : {};
95513
96077
  const serialized = serializeBackgroundOverride(override);
95514
96078
  if (serialized === null) {
95515
96079
  const nextSectionStyles = omitRecordKey2(sectionStyles, "background");
@@ -95711,7 +96275,7 @@ function imageAllowed(mediaId, pool) {
95711
96275
  return pool?.some((item) => item.mediaId === mediaId) ?? false;
95712
96276
  }
95713
96277
  function parseImageMediaAssetId(value) {
95714
- if (!isRecord14(value)) return { kind: "missing" };
96278
+ if (!isRecord15(value)) return { kind: "missing" };
95715
96279
  if (value.type !== void 0 && value.type !== "image") return { kind: "missing" };
95716
96280
  const parsed = parseMediaAssetId(value.assetId);
95717
96281
  if (!parsed.ok) {
@@ -95759,116 +96323,9 @@ function omitRecordKey2(content, key) {
95759
96323
  Object.entries(content).filter(([entryKey]) => entryKey !== key)
95760
96324
  );
95761
96325
  }
95762
- function isRecord14(value) {
95763
- return typeof value === "object" && value !== null && !Array.isArray(value);
95764
- }
95765
-
95766
- // ../path-utils/src/index.ts
95767
- var PATH_SEPARATOR_REGEX2 = /\./g;
95768
- var BRACKET_ACCESS_REGEX2 = /\[([^\]]+)\]/g;
95769
96326
  function isRecord15(value) {
95770
96327
  return typeof value === "object" && value !== null && !Array.isArray(value);
95771
96328
  }
95772
- function isPathContainer(value) {
95773
- return Array.isArray(value) || isRecord15(value);
95774
- }
95775
- function createPathContainer(nextIsIndex) {
95776
- return nextIsIndex ? [] : {};
95777
- }
95778
- function getContainerValue(container, segment) {
95779
- if (typeof segment === "number") {
95780
- return Array.isArray(container) ? container[segment] : void 0;
95781
- }
95782
- if (segment in container) {
95783
- return Reflect.get(container, segment);
95784
- }
95785
- return void 0;
95786
- }
95787
- function ensureContainerProperty(container, key, nextIsIndex) {
95788
- const existing = Reflect.get(container, key);
95789
- if (isPathContainer(existing)) {
95790
- return existing;
95791
- }
95792
- const nextContainer = createPathContainer(nextIsIndex);
95793
- Reflect.set(container, key, nextContainer);
95794
- return nextContainer;
95795
- }
95796
- function parsePath(path) {
95797
- if (Array.isArray(path)) return path;
95798
- const segments = [];
95799
- const parts = path.split(PATH_SEPARATOR_REGEX2);
95800
- for (const raw of parts) {
95801
- if (!raw) continue;
95802
- const baseMatch = raw.match(/^[^\[]+/);
95803
- if (baseMatch !== null) {
95804
- const base2 = baseMatch[1] ?? baseMatch[0];
95805
- if (/^\d+$/.test(base2)) {
95806
- segments.push(Number(base2));
95807
- } else {
95808
- segments.push(base2);
95809
- }
95810
- }
95811
- const bracketMatches = raw.matchAll(BRACKET_ACCESS_REGEX2);
95812
- for (const match2 of bracketMatches) {
95813
- const token = match2[1] ?? "";
95814
- if (token.startsWith('"') || token.startsWith("'")) {
95815
- segments.push(token.slice(1, -1));
95816
- } else if (/^\d+$/.test(token)) {
95817
- segments.push(Number(token));
95818
- } else {
95819
- segments.push(token);
95820
- }
95821
- }
95822
- if (baseMatch === null && !raw.includes("[")) {
95823
- segments.push(raw);
95824
- }
95825
- }
95826
- return segments;
95827
- }
95828
- function getAtPath(source, path) {
95829
- const segments = parsePath(path);
95830
- return segments.reduce((current, segment) => {
95831
- if (current === void 0 || current === null) return void 0;
95832
- if (!isPathContainer(current)) return void 0;
95833
- return getContainerValue(current, segment);
95834
- }, source);
95835
- }
95836
- function setAtPath(target, path, value) {
95837
- const segments = parsePath(path);
95838
- let current = target;
95839
- for (let index2 = 0; index2 < segments.length; index2 += 1) {
95840
- const segment = segments[index2];
95841
- if (segment === void 0) continue;
95842
- const isLast = index2 === segments.length - 1;
95843
- const nextIsIndex = typeof segments[index2 + 1] === "number";
95844
- if (isLast) {
95845
- if (typeof segment === "number") {
95846
- if (Array.isArray(current)) {
95847
- current[segment] = value;
95848
- }
95849
- } else {
95850
- Reflect.set(current, segment, value);
95851
- }
95852
- return;
95853
- }
95854
- if (typeof segment === "number") {
95855
- if (Array.isArray(current)) {
95856
- const existing = current[segment];
95857
- if (isPathContainer(existing)) {
95858
- current = existing;
95859
- } else {
95860
- const nextContainer = createPathContainer(nextIsIndex);
95861
- current[segment] = nextContainer;
95862
- current = nextContainer;
95863
- }
95864
- continue;
95865
- }
95866
- current = ensureContainerProperty(current, String(segment), nextIsIndex);
95867
- continue;
95868
- }
95869
- current = ensureContainerProperty(current, segment, nextIsIndex);
95870
- }
95871
- }
95872
96329
 
95873
96330
  // ../content-editor/src/linkedEntries/domain.ts
95874
96331
  function unsafeAsLinkedContentEntryId(value) {
@@ -124207,6 +124664,7 @@ function toManifestFieldInput(field) {
124207
124664
  case "button":
124208
124665
  throw new Error("Button fields do not have canonical content validation");
124209
124666
  case "text":
124667
+ case "inlineText":
124210
124668
  case "richText":
124211
124669
  case "media":
124212
124670
  case "file":
@@ -124561,6 +125019,17 @@ function getRichTextFieldDefaultValue(_config) {
124561
125019
  return EMPTY_RICH_TEXT_DOC;
124562
125020
  }
124563
125021
 
125022
+ // ../block-form/src/widgets/InlineTextField/inlineTextFieldSchema.ts
125023
+ function buildInlineTextFieldSchema(field) {
125024
+ return buildCanonicalFieldSchema(field);
125025
+ }
125026
+
125027
+ // ../block-form/src/widgets/InlineTextField/inlineTextFieldDefaults.ts
125028
+ function getInlineTextFieldDefaultValue(field) {
125029
+ if (field.defaultValue !== void 0) return field.defaultValue;
125030
+ return field.required ? plainTextToInlineText(field.label) : [];
125031
+ }
125032
+
124564
125033
  // ../block-form/src/widgets/MediaField/mediaFieldSchema.ts
124565
125034
  function buildMediaFieldSchema(config) {
124566
125035
  return buildCanonicalFieldSchema(config);
@@ -124671,6 +125140,7 @@ var SCHEMA_BUILDERS = {
124671
125140
  slug: buildSlugFieldSchema,
124672
125141
  link: buildLinkFieldSchema,
124673
125142
  richText: buildRichTextFieldSchema,
125143
+ inlineText: buildInlineTextFieldSchema,
124674
125144
  media: buildMediaFieldSchema,
124675
125145
  file: buildMediaFieldSchema,
124676
125146
  tabGroup: buildTabGroupFieldSchema,
@@ -124694,6 +125164,7 @@ var DEFAULT_VALUE_BUILDERS = {
124694
125164
  slug: getSlugFieldDefault,
124695
125165
  link: getLinkFieldDefault,
124696
125166
  richText: getRichTextFieldDefaultValue,
125167
+ inlineText: getInlineTextFieldDefaultValue,
124697
125168
  media: getMediaFieldDefaultValue,
124698
125169
  file: getMediaFieldDefaultValue,
124699
125170
  tabGroup: getTabGroupFieldDefault,
@@ -124833,6 +125304,7 @@ function shouldUseCanonicalSchema(field) {
124833
125304
  case "media":
124834
125305
  case "file":
124835
125306
  case "reference":
125307
+ case "inlineText":
124836
125308
  return true;
124837
125309
  case "group":
124838
125310
  return getGroupChildFields(field).every(shouldUseCanonicalSchema);
@@ -131910,6 +132382,7 @@ function transformEligibilityResponse(response) {
131910
132382
  requiresPayment: eligibility.requiresPayment,
131911
132383
  pricingMode: eligibility.pricingMode,
131912
132384
  selectedTicketTypeId: eligibility.selectedTicketTypeId ?? null,
132385
+ ticketLines: eligibility.ticketLines ?? [],
131913
132386
  ticketTypes: eligibility.ticketTypes ?? [],
131914
132387
  isFull: eligibility.isFull,
131915
132388
  waitlistEnabled: eligibility.waitlistEnabled,
@@ -131966,6 +132439,72 @@ function findSelectedTicketType(input) {
131966
132439
  }).find((ticketType) => ticketType.id === input.selectedTicketTypeId) ?? null;
131967
132440
  }
131968
132441
 
132442
+ // ../blocks/src/system/runtime/nodes/event-registration/ticketSelectionLines.ts
132443
+ function normalizeTicketSelectionLines(lines) {
132444
+ const quantitiesByTicketType = /* @__PURE__ */ new Map();
132445
+ for (const line of lines) {
132446
+ const quantity = Math.floor(line.quantity);
132447
+ if (quantity <= 0) continue;
132448
+ const key = line.ticketTypeId ?? null;
132449
+ quantitiesByTicketType.set(key, (quantitiesByTicketType.get(key) ?? 0) + quantity);
132450
+ }
132451
+ return [...quantitiesByTicketType.entries()].map(([ticketTypeId, quantity]) => ({
132452
+ ticketTypeId,
132453
+ quantity
132454
+ }));
132455
+ }
132456
+ function getTicketSelectionTotal(lines) {
132457
+ return normalizeTicketSelectionLines(lines).reduce((total, line) => total + line.quantity, 0);
132458
+ }
132459
+ function getTicketLineQuantity(lines, ticketTypeId) {
132460
+ return normalizeTicketSelectionLines(lines).find((line) => line.ticketTypeId === ticketTypeId)?.quantity ?? 0;
132461
+ }
132462
+ function getSingleSelectedTicketTypeId(lines) {
132463
+ const normalized = normalizeTicketSelectionLines(lines);
132464
+ return normalized.length === 1 ? normalized[0]?.ticketTypeId ?? null : null;
132465
+ }
132466
+ function setTicketLineQuantity(input) {
132467
+ const nextQuantity = Math.max(0, Math.floor(input.quantity));
132468
+ const normalized = normalizeTicketSelectionLines(input.lines).filter((line) => line.ticketTypeId !== input.ticketTypeId);
132469
+ if (nextQuantity <= 0) {
132470
+ return normalized;
132471
+ }
132472
+ return [
132473
+ ...normalized,
132474
+ {
132475
+ ticketTypeId: input.ticketTypeId,
132476
+ quantity: nextQuantity
132477
+ }
132478
+ ];
132479
+ }
132480
+ function getTicketTypeLineMax(input) {
132481
+ const otherSelectedQuantity = input.totalSelectedQuantity - input.currentQuantity;
132482
+ const maxByBlock = input.maxTickets - otherSelectedQuantity;
132483
+ const maxByEvent = input.availableSpots == null ? input.maxTickets : input.availableSpots - otherSelectedQuantity;
132484
+ const maxByTicketType = input.ticketTypeRemainingCapacity ?? input.maxTickets;
132485
+ return Math.max(0, Math.min(maxByBlock, maxByEvent, maxByTicketType));
132486
+ }
132487
+ function calculateTicketSelectionSubtotal(input) {
132488
+ return normalizeTicketSelectionLines(input.lines).reduce((subtotal, line) => {
132489
+ const ticketType = line.ticketTypeId ? input.ticketTypes.find((candidate) => candidate.id === line.ticketTypeId) ?? null : null;
132490
+ const unitPriceCents = ticketType?.priceAmount ?? input.fallbackUnitPriceCents;
132491
+ return subtotal + Math.max(0, unitPriceCents) * line.quantity;
132492
+ }, 0);
132493
+ }
132494
+ function buildTicketSelectionSummaryLines(input) {
132495
+ return normalizeTicketSelectionLines(input.lines).map((line) => {
132496
+ const ticketType = line.ticketTypeId ? input.ticketTypes.find((candidate) => candidate.id === line.ticketTypeId) ?? null : null;
132497
+ const unitPriceCents = ticketType?.priceAmount ?? input.fallbackUnitPriceCents;
132498
+ return {
132499
+ ticketTypeId: line.ticketTypeId,
132500
+ label: ticketType?.name ?? input.fallbackLabel,
132501
+ quantity: line.quantity,
132502
+ unitPriceCents,
132503
+ subtotalCents: Math.max(0, unitPriceCents) * line.quantity
132504
+ };
132505
+ });
132506
+ }
132507
+
131969
132508
  // ../blocks/src/system/runtime/nodes/event-registration/hooks.state.ts
131970
132509
  var initialEligibilityLookupState = {
131971
132510
  tag: "idle",
@@ -132072,6 +132611,7 @@ function usePortalAuth() {
132072
132611
  }
132073
132612
  function useEligibility(params) {
132074
132613
  const api = useBlockApi();
132614
+ const ticketSelectionsKey = JSON.stringify(normalizeTicketSelectionLines(params.ticketSelections));
132075
132615
  const [state, dispatch] = useReducer(
132076
132616
  eligibilityLookupReducer,
132077
132617
  initialEligibilityLookupState
@@ -132085,7 +132625,8 @@ function useEligibility(params) {
132085
132625
  dispatch({ type: "reset" });
132086
132626
  return;
132087
132627
  }
132088
- if (!params.occurrenceId || !params.email.trim()) {
132628
+ const ticketSelections = JSON.parse(ticketSelectionsKey);
132629
+ if (!params.occurrenceId || !params.email.trim() || ticketSelections.length === 0) {
132089
132630
  requestIdRef.current += 1;
132090
132631
  dispatch({ type: "reset" });
132091
132632
  return;
@@ -132097,10 +132638,9 @@ function useEligibility(params) {
132097
132638
  const result = await api.checkEligibility({
132098
132639
  occurrenceId: params.occurrenceId,
132099
132640
  attendanceMode: params.attendanceMode ?? void 0,
132100
- ticketTypeId: params.ticketTypeId ?? void 0,
132641
+ ticketSelections,
132101
132642
  selectedSlidingAmount: params.selectedSlidingAmount ?? void 0,
132102
- email: params.email.trim().toLowerCase(),
132103
- ticketsCount: params.ticketsCount
132643
+ email: params.email.trim().toLowerCase()
132104
132644
  });
132105
132645
  if (cancelled || requestIdRef.current !== requestId) return;
132106
132646
  dispatch({
@@ -132119,7 +132659,15 @@ function useEligibility(params) {
132119
132659
  return () => {
132120
132660
  cancelled = true;
132121
132661
  };
132122
- }, [api, params.enabled, params.occurrenceId, params.attendanceMode, params.ticketTypeId, params.selectedSlidingAmount, params.email, params.ticketsCount]);
132662
+ }, [
132663
+ api,
132664
+ params.enabled,
132665
+ params.occurrenceId,
132666
+ params.attendanceMode,
132667
+ ticketSelectionsKey,
132668
+ params.selectedSlidingAmount,
132669
+ params.email
132670
+ ]);
132123
132671
  return {
132124
132672
  state,
132125
132673
  eligibility: state.eligibility,
@@ -132195,9 +132743,15 @@ function savePendingRegistration(siteId, occurrenceId, data) {
132195
132743
  }
132196
132744
  try {
132197
132745
  const key = getStorageKey(siteId, occurrenceId);
132746
+ const ticketSelections = normalizeTicketSelectionLines(data.ticketSelections);
132747
+ if (ticketSelections.length === 0) {
132748
+ console.warn("[sessionStorage] No ticket selections to save, skipping registration state");
132749
+ return;
132750
+ }
132198
132751
  const entry = {
132199
132752
  ...data,
132200
- version: 3,
132753
+ ticketSelections,
132754
+ version: 4,
132201
132755
  timestamp: Date.now()
132202
132756
  };
132203
132757
  sessionStorage.setItem(key, JSON.stringify(entry));
@@ -132243,8 +132797,8 @@ function parseAndValidateEntry(stored, key) {
132243
132797
  return null;
132244
132798
  }
132245
132799
  const version2 = raw.version;
132246
- if (version2 !== 1 && version2 !== 2 && version2 !== 3) {
132247
- console.warn("[sessionStorage] Unknown version, ignoring entry");
132800
+ if (version2 !== 4) {
132801
+ console.warn("[sessionStorage] Outdated version, ignoring entry");
132248
132802
  sessionStorage.removeItem(key);
132249
132803
  return null;
132250
132804
  }
@@ -132260,34 +132814,12 @@ function parseAndValidateEntry(stored, key) {
132260
132814
  sessionStorage.removeItem(key);
132261
132815
  return null;
132262
132816
  }
132263
- if (entry.version === 1) {
132264
- const legacy = entry;
132265
- return {
132266
- version: 3,
132267
- attendeeId: legacy.attendeeId,
132268
- formData: legacy.formData,
132269
- ticketsCount: legacy.ticketsCount,
132270
- selectedEventId: legacy.selectedEventId,
132271
- selectedAttendanceMode: null,
132272
- selectedTicketTypeId: null,
132273
- paymentSelection: { method: legacy.paymentMethod },
132274
- timestamp: legacy.timestamp
132275
- };
132276
- }
132277
- if (entry.version === 2) {
132278
- return {
132279
- version: 3,
132280
- attendeeId: entry.attendeeId,
132281
- formData: entry.formData,
132282
- ticketsCount: entry.ticketsCount,
132283
- selectedEventId: entry.selectedEventId,
132284
- selectedAttendanceMode: null,
132285
- selectedTicketTypeId: null,
132286
- paymentSelection: entry.paymentSelection,
132287
- timestamp: entry.timestamp
132288
- };
132817
+ const ticketSelections = normalizeTicketSelectionLines(entry.ticketSelections);
132818
+ if (ticketSelections.length === 0 || getTicketSelectionTotal(ticketSelections) <= 0) {
132819
+ sessionStorage.removeItem(key);
132820
+ return null;
132289
132821
  }
132290
- return entry;
132822
+ return { ...entry, ticketSelections };
132291
132823
  } catch {
132292
132824
  console.warn("[sessionStorage] Failed to parse entry, removing");
132293
132825
  sessionStorage.removeItem(key);
@@ -132319,8 +132851,9 @@ function cleanupStaleRegistrations() {
132319
132851
  const stored = sessionStorage.getItem(key);
132320
132852
  if (!stored) continue;
132321
132853
  const entry = JSON.parse(stored);
132322
- const age = Date.now() - entry.timestamp;
132323
- if (age > STALE_THRESHOLD_MS) {
132854
+ const timestamp = typeof entry.timestamp === "number" ? entry.timestamp : NaN;
132855
+ const age = Date.now() - timestamp;
132856
+ if (!Number.isFinite(timestamp) || age > STALE_THRESHOLD_MS) {
132324
132857
  keysToRemove.push(key);
132325
132858
  }
132326
132859
  } catch {
@@ -132408,14 +132941,16 @@ function getEventAttendanceModeLabel(mode) {
132408
132941
  }
132409
132942
  }
132410
132943
  function TicketCounter(props2) {
132411
- const { ticketsCount, maxAllowed, onTicketsChange } = props2;
132944
+ const { ticketsCount, maxAllowed, label, onTicketsChange } = props2;
132945
+ const minAllowed = props2.minAllowed ?? 1;
132412
132946
  return /* @__PURE__ */ jsxs("div", { className: "er-row er-counter", children: [
132413
132947
  /* @__PURE__ */ jsx(
132414
132948
  "button",
132415
132949
  {
132416
132950
  type: "button",
132417
- onClick: () => onTicketsChange(Math.max(1, ticketsCount - 1)),
132418
- disabled: ticketsCount <= 1,
132951
+ "aria-label": `Decrease ${label}`,
132952
+ onClick: () => onTicketsChange(Math.max(minAllowed, ticketsCount - 1)),
132953
+ disabled: ticketsCount <= minAllowed,
132419
132954
  className: "er-counter-btn",
132420
132955
  children: "-"
132421
132956
  }
@@ -132425,6 +132960,7 @@ function TicketCounter(props2) {
132425
132960
  "button",
132426
132961
  {
132427
132962
  type: "button",
132963
+ "aria-label": `Increase ${label}`,
132428
132964
  onClick: () => onTicketsChange(Math.min(maxAllowed, ticketsCount + 1)),
132429
132965
  disabled: ticketsCount >= maxAllowed,
132430
132966
  className: "er-counter-btn",
@@ -132477,14 +133013,86 @@ function SlidingScaleAmountField(props2) {
132477
133013
  props2.message ? /* @__PURE__ */ jsx("p", { className: "er-text er-text--muted", children: props2.message }) : null
132478
133014
  ] });
132479
133015
  }
132480
- function getTicketTypeCounterAvailabilityLabel(input) {
132481
- if (input.selectedRemainingCapacity !== null) {
132482
- return `${input.selectedRemainingCapacity} remaining for this ticket type`;
132483
- }
132484
- if (input.eventAvailableSpots != null) {
132485
- return `${input.eventAvailableSpots} spots available`;
132486
- }
132487
- return null;
133016
+ function TicketTypeQuantityRows(props2) {
133017
+ const totalSelectedQuantity = getTicketSelectionTotal(props2.ticketSelections);
133018
+ const selectedTicketTypes = props2.ticketTypes.filter(
133019
+ (ticketType) => getTicketLineQuantity(props2.ticketSelections, ticketType.id) > 0
133020
+ );
133021
+ return /* @__PURE__ */ jsxs("div", { className: "er-ticket-lines", children: [
133022
+ /* @__PURE__ */ jsx("div", { className: "er-ticket-line-list", role: "list", "aria-label": "Tickets", children: props2.ticketTypes.map((ticketType) => {
133023
+ const quantity = getTicketLineQuantity(props2.ticketSelections, ticketType.id);
133024
+ const disabled = ticketType.availability.kind === "unavailable";
133025
+ const availabilityLabel = getTicketTypeAvailabilityLabel(ticketType);
133026
+ const priceLabel = ticketType.priceAmount > 0 ? formatPrice(ticketType.priceAmount, props2.currency) : "Free";
133027
+ const maxAllowed = disabled ? 0 : getTicketTypeLineMax({
133028
+ currentQuantity: quantity,
133029
+ totalSelectedQuantity,
133030
+ maxTickets: props2.maxTickets,
133031
+ availableSpots: props2.availableSpots,
133032
+ ticketTypeRemainingCapacity: ticketType.availability.remainingCapacity
133033
+ });
133034
+ return /* @__PURE__ */ jsxs(
133035
+ "div",
133036
+ {
133037
+ className: `er-ticket-line${disabled ? " er-ticket-line--disabled" : ""}`,
133038
+ role: "listitem",
133039
+ children: [
133040
+ /* @__PURE__ */ jsxs("div", { className: "er-ticket-line-main", children: [
133041
+ /* @__PURE__ */ jsxs("div", { className: "er-ticket-line-heading", children: [
133042
+ /* @__PURE__ */ jsx("span", { className: "er-ticket-line-name", children: ticketType.name }),
133043
+ /* @__PURE__ */ jsx("span", { className: "er-ticket-line-price", children: priceLabel })
133044
+ ] }),
133045
+ ticketType.description ? /* @__PURE__ */ jsx("p", { className: "er-ticket-line-detail", children: ticketType.description }) : null,
133046
+ availabilityLabel ? /* @__PURE__ */ jsx("p", { className: "er-ticket-line-detail", children: availabilityLabel }) : ticketType.availability.remainingCapacity !== null ? /* @__PURE__ */ jsxs("p", { className: "er-ticket-line-detail", children: [
133047
+ ticketType.availability.remainingCapacity,
133048
+ " remaining for this ticket type"
133049
+ ] }) : null
133050
+ ] }),
133051
+ /* @__PURE__ */ jsx(
133052
+ TicketCounter,
133053
+ {
133054
+ ticketsCount: quantity,
133055
+ minAllowed: 0,
133056
+ maxAllowed,
133057
+ label: ticketType.name,
133058
+ onTicketsChange: (nextQuantity) => {
133059
+ props2.onTicketSelectionsChange?.(setTicketLineQuantity({
133060
+ lines: props2.ticketSelections,
133061
+ ticketTypeId: ticketType.id,
133062
+ quantity: nextQuantity
133063
+ }));
133064
+ }
133065
+ }
133066
+ )
133067
+ ]
133068
+ },
133069
+ ticketType.id
133070
+ );
133071
+ }) }),
133072
+ /* @__PURE__ */ jsx(
133073
+ TicketCounterLimit,
133074
+ {
133075
+ maximumLabel: `${props2.maxTickets} tickets maximum`,
133076
+ availabilityLabel: props2.availableSpots != null ? `${props2.availableSpots} spots available` : null
133077
+ }
133078
+ ),
133079
+ selectedTicketTypes.length > 0 ? /* @__PURE__ */ jsxs("div", { className: "er-ticket-line-summary", "aria-live": "polite", children: [
133080
+ /* @__PURE__ */ jsxs("div", { className: "er-ticket-line-summary-title", children: [
133081
+ totalSelectedQuantity,
133082
+ " ticket",
133083
+ totalSelectedQuantity === 1 ? "" : "s",
133084
+ " selected"
133085
+ ] }),
133086
+ /* @__PURE__ */ jsx("ul", { className: "er-ticket-line-summary-list", children: selectedTicketTypes.map((ticketType) => {
133087
+ const quantity = getTicketLineQuantity(props2.ticketSelections, ticketType.id);
133088
+ return /* @__PURE__ */ jsxs("li", { children: [
133089
+ quantity,
133090
+ " x ",
133091
+ ticketType.name
133092
+ ] }, ticketType.id);
133093
+ }) })
133094
+ ] }) : props2.hasAvailableTicketTypes ? /* @__PURE__ */ jsx("p", { className: "er-text er-text--muted", children: "Choose at least one ticket to continue." }) : /* @__PURE__ */ jsx("p", { className: "er-text er-text--muted", children: "No ticket types are currently available." })
133095
+ ] });
132488
133096
  }
132489
133097
  function getAttendanceModeDetail(attendanceMode) {
132490
133098
  if (attendanceMode.availableSpots === null) {
@@ -132502,6 +133110,7 @@ function AttendanceModeTiles(props2) {
132502
133110
  "button",
132503
133111
  {
132504
133112
  type: "button",
133113
+ "aria-pressed": isSelected,
132505
133114
  className: `er-payment-tile${isSelected ? " er-payment-tile--selected" : ""}`,
132506
133115
  onClick: () => props2.onAttendanceModeChange?.(attendanceMode.mode),
132507
133116
  children: [
@@ -132538,8 +133147,9 @@ var TicketSelectionStep = ({
132538
133147
  onAttendanceModeChange,
132539
133148
  ticketsCount,
132540
133149
  maxTickets,
132541
- selectedTicketTypeId = null,
132542
- onTicketTypeChange,
133150
+ visibleTicketTypes: visibleTicketTypesOverride,
133151
+ ticketSelections = [],
133152
+ onTicketSelectionsChange,
132543
133153
  slidingScale = null,
132544
133154
  selectedSlidingAmountInput = "",
132545
133155
  slidingScaleSelectionMessage = null,
@@ -132557,28 +133167,22 @@ var TicketSelectionStep = ({
132557
133167
  const eventPricingMode = eventPricing ? publicEventPricingMode(eventPricing) : void 0;
132558
133168
  const eventPricingCurrency = eventPricing ? publicEventPricingCurrency(eventPricing) : null;
132559
133169
  const usesTicketTypes = eventPricingMode === "ticket_types" && !canJoinWaitlist;
132560
- const visibleTicketTypes = usesTicketTypes ? getVisibleTicketTypes({
133170
+ const visibleTicketTypes = usesTicketTypes ? visibleTicketTypesOverride ?? getVisibleTicketTypes({
132561
133171
  event,
132562
133172
  eligibility: null,
132563
133173
  selectedAttendanceMode
132564
133174
  }) : [];
132565
- const selectedTicketType = usesTicketTypes ? visibleTicketTypes.find((ticketType) => ticketType.id === selectedTicketTypeId) ?? null : null;
132566
133175
  const implicitTicketType = usesTicketTypes ? getImplicitSingleAvailableTicketType(visibleTicketTypes) : null;
132567
- const effectiveSelectedTicketType = selectedTicketType ?? implicitTicketType;
132568
- const shouldShowTicketTypeTiles = usesTicketTypes && implicitTicketType === null;
132569
- const selectedRemainingCapacity = effectiveSelectedTicketType?.availability.remainingCapacity ?? null;
132570
- const noSellableTicketTypes = usesTicketTypes && (visibleTicketTypes.length === 0 || visibleTicketTypes.every((ticketType) => ticketType.availability.kind === "unavailable"));
133176
+ const noVisibleTicketTypes = usesTicketTypes && visibleTicketTypes.length === 0;
133177
+ const hasAvailableTicketTypes = usesTicketTypes && visibleTicketTypes.some((ticketType) => ticketType.availability.kind === "available");
133178
+ const aggregateRemainingCapacity = implicitTicketType?.availability.remainingCapacity ?? null;
132571
133179
  const maxAllowed = getMaxAllowedTicketCount({
132572
133180
  canJoinWaitlist,
132573
133181
  usesTicketTypes,
132574
133182
  maxTickets,
132575
133183
  availableSpots,
132576
- selectedTicketTypeRemainingCapacity: selectedRemainingCapacity,
132577
- hasSelectedTicketType: effectiveSelectedTicketType !== null
132578
- });
132579
- const selectedTicketTypeAvailabilityLabel = getTicketTypeCounterAvailabilityLabel({
132580
- selectedRemainingCapacity,
132581
- eventAvailableSpots: event?.availableSpots
133184
+ selectedTicketTypeRemainingCapacity: aggregateRemainingCapacity,
133185
+ hasSelectedTicketType: implicitTicketType !== null
132582
133186
  });
132583
133187
  const eventAvailabilityLabel = !canJoinWaitlist && event?.availableSpots != null ? `${event.availableSpots} spots available` : null;
132584
133188
  if (deliveryMode === "hybrid" && !selectedAttendanceMode) {
@@ -132595,7 +133199,7 @@ var TicketSelectionStep = ({
132595
133199
  /* @__PURE__ */ jsx("p", { className: "er-text er-text--muted", children: "Choose whether you want to attend in person or online." })
132596
133200
  ] });
132597
133201
  }
132598
- if (isSoldOut && !canJoinWaitlist && !usesTicketTypes) {
133202
+ if (isSoldOut && !canJoinWaitlist) {
132599
133203
  return /* @__PURE__ */ jsxs("div", { className: "er-stack", children: [
132600
133204
  /* @__PURE__ */ jsx("h3", { className: "er-title", children: "Sold Out" }),
132601
133205
  /* @__PURE__ */ jsx("p", { className: "er-text er-text--muted", children: "Sorry you missed out! This event is fully booked." })
@@ -132613,52 +133217,21 @@ var TicketSelectionStep = ({
132613
133217
  }
132614
133218
  )
132615
133219
  ] }) : null,
132616
- usesTicketTypes ? /* @__PURE__ */ jsxs(Fragment, { children: [
132617
- shouldShowTicketTypeTiles ? /* @__PURE__ */ jsxs(Fragment, { children: [
132618
- /* @__PURE__ */ jsx("h3", { className: "er-title", children: "Choose a ticket type" }),
132619
- /* @__PURE__ */ jsx("div", { className: "er-payment-tiles", role: "list", "aria-label": "Ticket types", children: visibleTicketTypes.map((ticketType) => {
132620
- const availabilityLabel = getTicketTypeAvailabilityLabel(ticketType);
132621
- const disabled = ticketType.availability.kind === "unavailable";
132622
- const isSelected = selectedTicketTypeId === ticketType.id;
132623
- const priceLabel = ticketType.priceAmount > 0 ? formatPrice(ticketType.priceAmount, eventPricingCurrency ?? DEFAULT_EVENT_CURRENCY2) : "Free";
132624
- return /* @__PURE__ */ jsx("div", { role: "listitem", children: /* @__PURE__ */ jsxs(
132625
- "button",
132626
- {
132627
- type: "button",
132628
- className: `er-payment-tile${isSelected && !disabled ? " er-payment-tile--selected" : ""}${disabled ? " er-payment-tile--disabled" : ""}`,
132629
- disabled,
132630
- onClick: () => onTicketTypeChange?.(ticketType.id),
132631
- children: [
132632
- /* @__PURE__ */ jsx("div", { className: "er-payment-tile-label", children: ticketType.name }),
132633
- /* @__PURE__ */ jsx("div", { className: "er-payment-tile-detail", children: priceLabel }),
132634
- ticketType.description ? /* @__PURE__ */ jsx("div", { className: "er-payment-tile-detail", children: ticketType.description }) : null,
132635
- availabilityLabel ? /* @__PURE__ */ jsx("div", { className: "er-payment-tile-detail", children: availabilityLabel }) : null
132636
- ]
132637
- }
132638
- ) }, ticketType.id);
132639
- }) })
132640
- ] }) : null,
132641
- noSellableTicketTypes ? /* @__PURE__ */ jsx("p", { className: "er-text er-text--muted", children: "No ticket types are currently available." }) : !effectiveSelectedTicketType ? /* @__PURE__ */ jsx("p", { className: "er-text er-text--muted", children: "Select one ticket type to continue." }) : effectiveSelectedTicketType.availability.kind === "unavailable" ? /* @__PURE__ */ jsx("p", { className: "er-text er-text--muted", children: getTicketTypeAvailabilityLabel(effectiveSelectedTicketType) ?? "This ticket type is unavailable." }) : /* @__PURE__ */ jsxs(Fragment, { children: [
132642
- /* @__PURE__ */ jsx("h3", { className: "er-title", children: "How many tickets?" }),
132643
- /* @__PURE__ */ jsxs("div", { className: "er-ticket-counter-group", children: [
132644
- /* @__PURE__ */ jsx(
132645
- TicketCounter,
132646
- {
132647
- ticketsCount,
132648
- maxAllowed,
132649
- onTicketsChange
132650
- }
132651
- ),
132652
- /* @__PURE__ */ jsx(
132653
- TicketCounterLimit,
132654
- {
132655
- maximumLabel: `${maxAllowed} tickets maximum`,
132656
- availabilityLabel: selectedTicketTypeAvailabilityLabel
132657
- }
132658
- )
132659
- ] })
132660
- ] })
132661
- ] }) : /* @__PURE__ */ jsxs(Fragment, { children: [
133220
+ usesTicketTypes ? /* @__PURE__ */ jsx(Fragment, { children: noVisibleTicketTypes ? /* @__PURE__ */ jsx("p", { className: "er-text er-text--muted", children: "No ticket types are currently available." }) : /* @__PURE__ */ jsxs(Fragment, { children: [
133221
+ /* @__PURE__ */ jsx("h3", { className: "er-title", children: "Choose tickets" }),
133222
+ /* @__PURE__ */ jsx(
133223
+ TicketTypeQuantityRows,
133224
+ {
133225
+ ticketTypes: visibleTicketTypes,
133226
+ ticketSelections,
133227
+ maxTickets,
133228
+ availableSpots,
133229
+ currency: eventPricingCurrency ?? DEFAULT_EVENT_CURRENCY2,
133230
+ hasAvailableTicketTypes,
133231
+ onTicketSelectionsChange
133232
+ }
133233
+ )
133234
+ ] }) }) : /* @__PURE__ */ jsxs(Fragment, { children: [
132662
133235
  slidingScale ? /* @__PURE__ */ jsx(
132663
133236
  SlidingScaleAmountField,
132664
133237
  {
@@ -132676,6 +133249,7 @@ var TicketSelectionStep = ({
132676
133249
  {
132677
133250
  ticketsCount,
132678
133251
  maxAllowed,
133252
+ label: canJoinWaitlist ? "waitlist spots" : "tickets",
132679
133253
  onTicketsChange
132680
133254
  }
132681
133255
  ),
@@ -133119,7 +133693,7 @@ var PaymentSelectionStep = ({
133119
133693
  }) => {
133120
133694
  const occurrenceId = occurrenceContext?.id ?? event?.registrationOccurrenceId;
133121
133695
  const selectedMethod = selectedSelection.method;
133122
- const totalPrice = eligibility?.price ? eligibility.price * ticketsCount : 0;
133696
+ const totalPrice = eligibility?.price ?? 0;
133123
133697
  const canShowDirectPaymentOptions = Boolean(
133124
133698
  eligibility?.eligible && eligibility.canPayDirectly && eligibility.price
133125
133699
  );
@@ -133519,8 +134093,9 @@ function EventRegistrationWizardContent(props2) {
133519
134093
  onAttendanceModeChange: wizard.setSelectedAttendanceMode,
133520
134094
  ticketsCount: wizard.ticketsCount,
133521
134095
  maxTickets: wizard.maxTicketsNum,
133522
- selectedTicketTypeId: wizard.selectedTicketTypeId,
133523
- onTicketTypeChange: wizard.setSelectedTicketTypeId,
134096
+ visibleTicketTypes: wizard.eligibility ? wizard.visibleTicketTypes : void 0,
134097
+ ticketSelections: wizard.selectedTicketLines,
134098
+ onTicketSelectionsChange: wizard.setSelectedTicketLines,
133524
134099
  slidingScale: wizard.selectedEventSlidingScale,
133525
134100
  selectedSlidingAmountInput: wizard.selectedSlidingAmountInput,
133526
134101
  slidingScaleSelectionMessage: wizard.slidingScaleSelectionMessage,
@@ -133628,9 +134203,9 @@ function EventRegistrationWizardActions(props2) {
133628
134203
  const isWaitingForEligibility = wizard.portalAuthState === "authenticated" && wizard.eligibilityLoading;
133629
134204
  const isCheckingExistingRegistration = wizard.portalAuthState === "authenticated" && wizard.existingRegistrationLoading;
133630
134205
  const hasExistingRegistration = wizard.portalAuthState === "authenticated" && wizard.existingRegistration !== null;
133631
- const ticketTypeSelectionBlocked = wizard.ticketTypeSelectionRequired && !wizard.hasValidSelectedTicketType;
134206
+ const ticketTypeSelectionBlocked = wizard.ticketTypeSelectionRequired && !wizard.hasValidTicketSelection;
133632
134207
  const isContinueDisabled = isWaitingForEligibility || isCheckingExistingRegistration || hasExistingRegistration || isSoldOutWithoutWaitlist || ticketTypeSelectionBlocked;
133633
- const continueLabel = isCheckingExistingRegistration ? "Checking registration..." : hasExistingRegistration ? "Already registered" : isSoldOutWithoutWaitlist ? "Sold out" : ticketTypeSelectionBlocked ? "Choose a ticket type" : "Continue";
134208
+ const continueLabel = isCheckingExistingRegistration ? "Checking registration..." : hasExistingRegistration ? "Already registered" : isSoldOutWithoutWaitlist ? "Sold out" : ticketTypeSelectionBlocked ? "Choose a ticket" : "Continue";
133634
134209
  return /* @__PURE__ */ jsxs("div", { className: "er-actions", children: [
133635
134210
  !wizard.hasPreSelectedContext && /* @__PURE__ */ jsx("button", { type: "button", onClick: () => wizard.setStep("select-event"), className: "er-back-btn", children: "\u2190 Back" }),
133636
134211
  /* @__PURE__ */ jsx(
@@ -133718,13 +134293,17 @@ function EventRegistrationSummaryBar(props2) {
133718
134293
  const summaryTimeZone = wizard.occurrenceContext?.timeZone ?? summaryEvent?.timeZone ?? null;
133719
134294
  const occurrenceOverrideTitle = wizard.occurrenceContext?.overrides?.title;
133720
134295
  const summaryTitle = occurrenceOverrideTitle ?? summaryEvent?.title ?? "";
133721
- const summaryPrice = wizard.selectedTicketType?.priceAmount ?? wizard.eligibility?.price ?? (wizard.selectedEventSlidingScale ? wizard.selectedSlidingAmount : null) ?? (summaryEvent ? publicEventScalarPrice(summaryEvent.pricing) : null) ?? 0;
133722
134296
  const summaryCurrency = (summaryEvent ? publicEventPricingCurrency(summaryEvent.pricing) : null) ?? DEFAULT_EVENT_CURRENCY2;
133723
134297
  const teamMemberNames = (summaryEvent?.teamMembers ?? []).map((teamMember) => teamMember.name).filter(Boolean);
133724
- const subtotalCents = Math.max(0, summaryPrice * wizard.ticketsCount);
134298
+ const fallbackSubtotalCents = Math.max(
134299
+ 0,
134300
+ ((summaryEvent ? publicEventScalarPrice(summaryEvent.pricing) : null) ?? 0) * wizard.ticketsCount
134301
+ );
134302
+ const subtotalCents = Math.max(0, wizard.ticketSelectionSubtotalCents ?? fallbackSubtotalCents);
133725
134303
  const autoAppliedDiscount = wizard.discountCode.trim().length > 0 ? null : wizard.autoAppliedDiscount;
133726
134304
  const autoAppliedDiscountCents = Math.max(0, autoAppliedDiscount?.computedAmountCents ?? 0);
133727
134305
  const discountedTotalCents = Math.max(0, subtotalCents - autoAppliedDiscountCents);
134306
+ const selectedLineSummary = (wizard.ticketSelectionSummaryLines ?? []).filter((line) => line.ticketTypeId !== null).map((line) => `${line.quantity} x ${line.label}`).join(", ");
133728
134307
  const selectedDirectPaymentOption = getSelectedDirectPaymentOption({
133729
134308
  wizard,
133730
134309
  totalCents: discountedTotalCents,
@@ -133761,9 +134340,9 @@ function EventRegistrationSummaryBar(props2) {
133761
134340
  /* @__PURE__ */ jsx("h4", { className: "er-summary-bar-event", children: summaryTitle }),
133762
134341
  /* @__PURE__ */ jsxs("span", { className: "er-summary-bar-meta", children: [
133763
134342
  summaryDate && formatEventDateTime(summaryDate, { timeZone: summaryTimeZone }),
133764
- wizard.selectedTicketType ? /* @__PURE__ */ jsxs(Fragment, { children: [
134343
+ selectedLineSummary ? /* @__PURE__ */ jsxs(Fragment, { children: [
133765
134344
  " \xB7 ",
133766
- wizard.selectedTicketType.name
134345
+ selectedLineSummary
133767
134346
  ] }) : null,
133768
134347
  wizard.step !== "select-event" && wizard.step !== "select-tickets" && wizard.ticketsCount > 0 && /* @__PURE__ */ jsxs(Fragment, { children: [
133769
134348
  " \xB7 ",
@@ -133777,8 +134356,8 @@ function EventRegistrationSummaryBar(props2) {
133777
134356
  teamMemberNames.join(", ")
133778
134357
  ] })
133779
134358
  ] }),
133780
- summaryPrice > 0 && /* @__PURE__ */ jsx("div", { className: "er-summary-bar-pricing", children: productMethod ? /* @__PURE__ */ jsxs(Fragment, { children: [
133781
- /* @__PURE__ */ jsx("span", { className: "er-summary-bar-price er-summary-bar-price--struck", children: formatPrice(summaryPrice * wizard.ticketsCount, summaryCurrency) }),
134359
+ subtotalCents > 0 && /* @__PURE__ */ jsx("div", { className: "er-summary-bar-pricing", children: productMethod ? /* @__PURE__ */ jsxs(Fragment, { children: [
134360
+ /* @__PURE__ */ jsx("span", { className: "er-summary-bar-price er-summary-bar-price--struck", children: formatPrice(subtotalCents, summaryCurrency) }),
133782
134361
  /* @__PURE__ */ jsx("div", { className: "er-summary-bar-included", children: wizard.paymentSelection.method === "pass" || wizard.paymentSelection.method === "pass_bundle" ? "1 pass credit" : "Included in membership" })
133783
134362
  ] }) : flexibleBalanceSummary ? /* @__PURE__ */ jsxs(Fragment, { children: [
133784
134363
  flexibleBalanceSummary.total ? /* @__PURE__ */ jsxs("div", { className: "er-summary-bar-product-detail", children: [
@@ -134012,7 +134591,7 @@ function useEventRegistrationStripeReturn(options) {
134012
134591
  setRegistrationResult,
134013
134592
  setSelectedEvent,
134014
134593
  setSelectedAttendanceMode,
134015
- setSelectedTicketTypeId,
134594
+ setTicketSelections,
134016
134595
  setStep,
134017
134596
  setTicketsCount,
134018
134597
  step
@@ -134031,13 +134610,13 @@ function useEventRegistrationStripeReturn(options) {
134031
134610
  const pending = getPendingRegistration(siteId, occurrenceId || void 0);
134032
134611
  if (!pending) return;
134033
134612
  setFormData(pending.formData);
134034
- setTicketsCount(pending.ticketsCount);
134613
+ setTicketSelections(pending.ticketSelections);
134614
+ setTicketsCount(getTicketSelectionTotal(pending.ticketSelections));
134035
134615
  if (pending.selectedEventId) {
134036
134616
  const event = events2.find((e3) => e3.publicEventId === pending.selectedEventId) ?? null;
134037
134617
  if (event) setSelectedEvent(event);
134038
134618
  }
134039
134619
  setSelectedAttendanceMode(pending.selectedAttendanceMode ?? null);
134040
- setSelectedTicketTypeId(pending.selectedTicketTypeId ?? null);
134041
134620
  setPaymentSelection(pending.paymentSelection);
134042
134621
  if (registrationStatus === "cancelled") {
134043
134622
  setStep("select-payment");
@@ -134089,6 +134668,10 @@ function useEventRegistrationSubmit(options) {
134089
134668
  }
134090
134669
  options.setStep("submitting");
134091
134670
  try {
134671
+ const ticketSelections = normalizeTicketSelectionLines(options.ticketSelections);
134672
+ if (ticketSelections.length === 0) {
134673
+ throw new Error("Choose at least one ticket to continue.");
134674
+ }
134092
134675
  const isBundle = method === "pass_bundle" || method === "membership_bundle";
134093
134676
  const bundleProductId = isBundle ? passId || membershipId : void 0;
134094
134677
  const selectionSnapshot = (() => {
@@ -134117,11 +134700,10 @@ function useEventRegistrationSubmit(options) {
134117
134700
  const result = await options.api.registerForEvent({
134118
134701
  occurrenceId: submitOccurrenceId,
134119
134702
  attendanceMode: options.selectedAttendanceMode ?? void 0,
134120
- ticketTypeId: options.selectedTicketTypeId ?? void 0,
134703
+ ticketSelections,
134121
134704
  selectedSlidingAmount: options.selectedSlidingAmount ?? void 0,
134122
134705
  email: options.formData.email.trim().toLowerCase(),
134123
134706
  name: options.formData.name.trim(),
134124
- ticketsCount: options.ticketsCount,
134125
134707
  phone: options.formData.phone.trim() || void 0,
134126
134708
  notes: options.formData.notes.trim() || void 0,
134127
134709
  altchaSolution: options.altchaSolution,
@@ -134166,10 +134748,9 @@ function useEventRegistrationSubmit(options) {
134166
134748
  savePendingRegistration(siteId, submitOccurrenceId, {
134167
134749
  attendeeId: result.attendeeId,
134168
134750
  formData: options.formData,
134169
- ticketsCount: options.ticketsCount,
134751
+ ticketSelections,
134170
134752
  selectedEventId: options.registrationTarget?.selectedEventId ?? null,
134171
134753
  selectedAttendanceMode: options.selectedAttendanceMode,
134172
- selectedTicketTypeId: options.selectedTicketTypeId ?? null,
134173
134754
  paymentSelection: selectionSnapshot
134174
134755
  });
134175
134756
  }
@@ -134281,7 +134862,6 @@ function useEventRegistrationWizard(options) {
134281
134862
  createInitialRegistrationFlowState
134282
134863
  );
134283
134864
  const step = flowState.step;
134284
- const ticketsCount = flowState.ticketsCount;
134285
134865
  const paymentSelection = flowState.paymentSelection;
134286
134866
  const [selectedEvent, setSelectedEvent] = useState(preSelectedEvent ?? null);
134287
134867
  const [formData, setFormData] = useState({ name: "", email: "", phone: "", notes: "" });
@@ -134292,7 +134872,7 @@ function useEventRegistrationWizard(options) {
134292
134872
  const [selectedAttendanceMode, setSelectedAttendanceMode] = useState(
134293
134873
  preSelectedEvent?.deliveryMode === "online" ? "online" : preSelectedEvent?.deliveryMode === "in_person" ? "in_person" : null
134294
134874
  );
134295
- const [selectedTicketTypeId, setSelectedTicketTypeId] = useState(null);
134875
+ const [selectedTicketLines, setSelectedTicketLines] = useState([]);
134296
134876
  const [selectedSlidingAmountInput, setSelectedSlidingAmountInput] = useState(() => {
134297
134877
  const slidingScale = getSlidingScaleForEvent(preSelectedEvent ?? null);
134298
134878
  return slidingScale?.suggestedAmount !== null && slidingScale?.suggestedAmount !== void 0 ? formatCentsAsCurrencyInput(slidingScale.suggestedAmount) : "";
@@ -134328,14 +134908,51 @@ function useEventRegistrationWizard(options) {
134328
134908
  [options.occurrenceContext, selectedEvent]
134329
134909
  );
134330
134910
  const occurrenceId = registrationTarget?.occurrenceId ?? "";
134911
+ const currentEvent = selectedEvent ?? preSelectedEvent;
134912
+ const currentEventPricing = currentEvent ? resolveRuntimeEventPricing(currentEvent) : null;
134913
+ const currentEventUsesTicketTypes = currentEventPricing !== null && publicEventPricingMode(currentEventPricing) === "ticket_types";
134914
+ const selectedModeAvailability = selectedAttendanceMode ? (currentEvent?.attendanceModes ?? []).find((mode) => mode.mode === selectedAttendanceMode) ?? null : null;
134915
+ const currentAvailableSpots = selectedModeAvailability?.availableSpots ?? currentEvent?.availableSpots;
134916
+ const currentWaitlistEnabled = selectedModeAvailability?.waitlistEnabled ?? currentEvent?.waitlistEnabled ?? false;
134917
+ const currentCanJoinWaitlist = currentAvailableSpots === 0 && currentWaitlistEnabled === true;
134918
+ const usesTicketTypeSelections = currentEventUsesTicketTypes && !currentCanJoinWaitlist;
134919
+ const eventTicketTypesForSelection = useMemo(
134920
+ () => getVisibleTicketTypes({
134921
+ event: currentEvent,
134922
+ eligibility: null,
134923
+ selectedAttendanceMode
134924
+ }),
134925
+ [currentEvent, selectedAttendanceMode]
134926
+ );
134927
+ const normalizedSelectedTicketLines = useMemo(
134928
+ () => normalizeTicketSelectionLines(selectedTicketLines),
134929
+ [selectedTicketLines]
134930
+ );
134931
+ const ticketTypeSelectionTotal = useMemo(
134932
+ () => getTicketSelectionTotal(normalizedSelectedTicketLines),
134933
+ [normalizedSelectedTicketLines]
134934
+ );
134935
+ const ticketsCount = usesTicketTypeSelections ? ticketTypeSelectionTotal : flowState.ticketsCount;
134936
+ const ticketSelections = useMemo(() => {
134937
+ if (waitlistClaim.claim) {
134938
+ return [{ ticketTypeId: null, quantity: 1 }];
134939
+ }
134940
+ if (usesTicketTypeSelections) {
134941
+ return normalizedSelectedTicketLines;
134942
+ }
134943
+ return [{ ticketTypeId: null, quantity: ticketsCount }];
134944
+ }, [normalizedSelectedTicketLines, ticketsCount, usesTicketTypeSelections, waitlistClaim.claim]);
134945
+ useEffect(() => {
134946
+ if (flowState.ticketsCount === ticketsCount) return;
134947
+ dispatchFlow({ type: "set-tickets-count", ticketsCount });
134948
+ }, [flowState.ticketsCount, ticketsCount]);
134331
134949
  const eligibilityResult = useEligibility({
134332
134950
  enabled: portalAuthState === "authenticated" || step === "enter-details" || step === "select-payment",
134333
134951
  occurrenceId,
134334
134952
  attendanceMode: selectedAttendanceMode,
134335
- ticketTypeId: selectedTicketTypeId,
134953
+ ticketSelections,
134336
134954
  selectedSlidingAmount: parseCurrencyInputToCents(selectedSlidingAmountInput),
134337
- email: formData.email,
134338
- ticketsCount
134955
+ email: formData.email
134339
134956
  });
134340
134957
  const existingRegistrationResult = useExistingEventRegistration({
134341
134958
  isAuthenticated: portalAuthState === "authenticated",
@@ -134441,7 +135058,7 @@ function useEventRegistrationWizard(options) {
134441
135058
  setTicketsCount,
134442
135059
  setSelectedEvent,
134443
135060
  setSelectedAttendanceMode,
134444
- setSelectedTicketTypeId,
135061
+ setTicketSelections: (lines) => setSelectedTicketLines(normalizeTicketSelectionLines(lines)),
134445
135062
  setPaymentSelection: (selection) => dispatchFlow({ type: "set-manual-payment-selection", selection }),
134446
135063
  setPendingAttendeeId,
134447
135064
  setStep,
@@ -134454,20 +135071,21 @@ function useEventRegistrationWizard(options) {
134454
135071
  }, [selectedEvent, preSelectedEvent]);
134455
135072
  const visibleTicketTypes = useMemo(
134456
135073
  () => getVisibleTicketTypes({
134457
- event: selectedEvent ?? preSelectedEvent,
135074
+ event: currentEvent,
134458
135075
  eligibility,
134459
135076
  selectedAttendanceMode
134460
135077
  }),
134461
- [selectedAttendanceMode, selectedEvent, preSelectedEvent, eligibility]
135078
+ [currentEvent, selectedAttendanceMode, eligibility]
134462
135079
  );
135080
+ const singleSelectedTicketTypeId = getSingleSelectedTicketTypeId(normalizedSelectedTicketLines);
134463
135081
  const selectedTicketType = useMemo(
134464
135082
  () => findSelectedTicketType({
134465
- event: selectedEvent ?? preSelectedEvent,
135083
+ event: currentEvent,
134466
135084
  eligibility,
134467
- selectedTicketTypeId,
135085
+ selectedTicketTypeId: singleSelectedTicketTypeId,
134468
135086
  selectedAttendanceMode
134469
135087
  }),
134470
- [selectedAttendanceMode, selectedEvent, preSelectedEvent, eligibility, selectedTicketTypeId]
135088
+ [currentEvent, eligibility, selectedAttendanceMode, singleSelectedTicketTypeId]
134471
135089
  );
134472
135090
  const selectedSlidingAmount = useMemo(
134473
135091
  () => parseCurrencyInputToCents(selectedSlidingAmountInput),
@@ -134482,37 +135100,44 @@ function useEventRegistrationWizard(options) {
134482
135100
  selectedAmount: selectedSlidingAmount
134483
135101
  });
134484
135102
  const ticketTypeSelectionRequired = useMemo(() => {
134485
- const event = selectedEvent ?? preSelectedEvent;
135103
+ const event = currentEvent;
134486
135104
  if (!event || publicEventPricingMode(resolveRuntimeEventPricing(event)) !== "ticket_types") {
134487
135105
  return false;
134488
135106
  }
134489
135107
  if ((event.deliveryMode ?? "in_person") === "hybrid" && !selectedAttendanceMode) {
134490
135108
  return false;
134491
135109
  }
134492
- const selectedModeAvailability = selectedAttendanceMode ? (event.attendanceModes ?? []).find((mode) => mode.mode === selectedAttendanceMode) ?? null : null;
134493
- const canJoinWaitlist = (selectedModeAvailability?.availableSpots ?? event.availableSpots) === 0 && (selectedModeAvailability?.waitlistEnabled ?? event.waitlistEnabled) === true;
135110
+ const selectedModeAvailability2 = selectedAttendanceMode ? (event.attendanceModes ?? []).find((mode) => mode.mode === selectedAttendanceMode) ?? null : null;
135111
+ const canJoinWaitlist = (selectedModeAvailability2?.availableSpots ?? event.availableSpots) === 0 && (selectedModeAvailability2?.waitlistEnabled ?? event.waitlistEnabled) === true;
134494
135112
  return !canJoinWaitlist;
134495
- }, [selectedAttendanceMode, selectedEvent, preSelectedEvent]);
134496
- const hasValidSelectedTicketType = !ticketTypeSelectionRequired || Boolean(
134497
- selectedTicketType && selectedTicketType.availability.kind === "available"
134498
- );
135113
+ }, [currentEvent, selectedAttendanceMode]);
135114
+ const hasValidTicketSelection = !ticketTypeSelectionRequired || normalizedSelectedTicketLines.length > 0 && normalizedSelectedTicketLines.every((line) => {
135115
+ if (!line.ticketTypeId) return false;
135116
+ const ticketType = visibleTicketTypes.find((candidate) => candidate.id === line.ticketTypeId) ?? null;
135117
+ return ticketType?.availability.kind === "available";
135118
+ });
134499
135119
  useEffect(() => {
134500
- const event = selectedEvent ?? preSelectedEvent;
134501
- if (!event || publicEventPricingMode(resolveRuntimeEventPricing(event)) !== "ticket_types") {
134502
- if (selectedTicketTypeId !== null) {
134503
- setSelectedTicketTypeId(null);
135120
+ if (!usesTicketTypeSelections) {
135121
+ if (selectedTicketLines.length > 0) {
135122
+ setSelectedTicketLines([]);
134504
135123
  }
134505
135124
  return;
134506
135125
  }
134507
- const implicitTicketType = getImplicitSingleAvailableTicketType(visibleTicketTypes);
134508
- if (implicitTicketType && selectedTicketTypeId !== implicitTicketType.id) {
134509
- setSelectedTicketTypeId(implicitTicketType.id);
135126
+ const availableTicketTypes = eventTicketTypesForSelection.filter(
135127
+ (ticketType) => ticketType.availability.kind === "available"
135128
+ );
135129
+ const implicitTicketType = getImplicitSingleAvailableTicketType(eventTicketTypesForSelection);
135130
+ if (implicitTicketType && normalizedSelectedTicketLines.length === 0) {
135131
+ setSelectedTicketLines([{ ticketTypeId: implicitTicketType.id, quantity: 1 }]);
134510
135132
  return;
134511
135133
  }
134512
- if (selectedTicketTypeId && !visibleTicketTypes.some((ticketType) => ticketType.id === selectedTicketTypeId)) {
134513
- setSelectedTicketTypeId(null);
135134
+ const filteredLines = normalizedSelectedTicketLines.filter(
135135
+ (line) => line.ticketTypeId && availableTicketTypes.some((ticketType) => ticketType.id === line.ticketTypeId)
135136
+ );
135137
+ if (filteredLines.length !== normalizedSelectedTicketLines.length) {
135138
+ setSelectedTicketLines(filteredLines);
134514
135139
  }
134515
- }, [selectedEvent, preSelectedEvent, selectedTicketTypeId, visibleTicketTypes]);
135140
+ }, [eventTicketTypesForSelection, normalizedSelectedTicketLines, selectedTicketLines.length, usesTicketTypeSelections]);
134516
135141
  useEffect(() => {
134517
135142
  if (!requireGuestDetails) {
134518
135143
  if (guests.length > 0) setGuests([]);
@@ -134556,21 +135181,20 @@ function useEventRegistrationWizard(options) {
134556
135181
  return resolveEventRequiresPayment({
134557
135182
  eligibility,
134558
135183
  selectedTicketType,
134559
- event: selectedEvent ?? preSelectedEvent
135184
+ event: currentEvent
134560
135185
  });
134561
135186
  },
134562
135187
  [
134563
135188
  eligibility,
134564
135189
  selectedTicketType,
134565
- selectedEvent,
134566
- preSelectedEvent,
135190
+ currentEvent,
134567
135191
  selectedEventSlidingScale,
134568
135192
  selectedSlidingAmount
134569
135193
  ]
134570
135194
  );
134571
135195
  const handleDetailsComplete = async () => {
134572
- if (ticketTypeSelectionRequired && !hasValidSelectedTicketType) {
134573
- const message2 = "Select a ticket type to continue.";
135196
+ if (ticketTypeSelectionRequired && !hasValidTicketSelection) {
135197
+ const message2 = "Choose at least one available ticket to continue.";
134574
135198
  setErrorMessage(message2);
134575
135199
  setStep("error");
134576
135200
  return { ok: false, reason: "blocked", message: message2 };
@@ -134655,27 +135279,39 @@ function useEventRegistrationWizard(options) {
134655
135279
  const discountContext = useMemo(
134656
135280
  () => resolveDiscountContext({
134657
135281
  paymentSelection,
134658
- event: selectedEvent ?? preSelectedEvent,
135282
+ event: currentEvent,
134659
135283
  eventRequiresPayment,
134660
135284
  ticketsCount
134661
135285
  }),
134662
- [eventRequiresPayment, paymentSelection, selectedEvent, preSelectedEvent, ticketsCount]
135286
+ [currentEvent, eventRequiresPayment, paymentSelection, ticketsCount]
135287
+ );
135288
+ const fallbackUnitPriceCents = useMemo(
135289
+ () => currentEvent ? publicEventScalarPrice(resolveRuntimeEventPricing(currentEvent)) ?? 0 : 0,
135290
+ [currentEvent]
135291
+ );
135292
+ const ticketSelectionSubtotalCents = useMemo(() => {
135293
+ if (!usesTicketTypeSelections) {
135294
+ return Math.max(0, eligibility?.price ?? fallbackUnitPriceCents * ticketsCount);
135295
+ }
135296
+ return calculateTicketSelectionSubtotal({
135297
+ lines: normalizedSelectedTicketLines,
135298
+ ticketTypes: visibleTicketTypes,
135299
+ fallbackUnitPriceCents
135300
+ });
135301
+ }, [eligibility, fallbackUnitPriceCents, normalizedSelectedTicketLines, ticketsCount, usesTicketTypeSelections, visibleTicketTypes]);
135302
+ const ticketSelectionSummaryLines = useMemo(
135303
+ () => buildTicketSelectionSummaryLines({
135304
+ lines: ticketSelections,
135305
+ ticketTypes: visibleTicketTypes,
135306
+ fallbackLabel: "Ticket",
135307
+ fallbackUnitPriceCents
135308
+ }),
135309
+ [fallbackUnitPriceCents, ticketSelections, visibleTicketTypes]
134663
135310
  );
134664
135311
  const discountSubtotalCents = useMemo(() => {
134665
135312
  if (discountContext?.type !== "event") return void 0;
134666
- const event = selectedEvent ?? preSelectedEvent;
134667
- const eventPriceCents = selectedTicketType?.priceAmount ?? eligibility?.price ?? (selectedEventSlidingScale ? selectedSlidingAmount : null) ?? (event ? publicEventScalarPrice(resolveRuntimeEventPricing(event)) : null) ?? 0;
134668
- return Math.max(0, eventPriceCents * ticketsCount);
134669
- }, [
134670
- discountContext,
134671
- selectedTicketType,
134672
- eligibility,
134673
- selectedEvent,
134674
- preSelectedEvent,
134675
- selectedEventSlidingScale,
134676
- selectedSlidingAmount,
134677
- ticketsCount
134678
- ]);
135313
+ return ticketSelectionSubtotalCents;
135314
+ }, [discountContext, ticketSelectionSubtotalCents]);
134679
135315
  const discountUi = useDiscountCodeUi({ api, discountContext, subtotalCents: discountSubtotalCents });
134680
135316
  const selectionMethod = paymentSelection.method;
134681
135317
  const shouldShowDiscountToggle = discountContext !== null && discountUi.manualCodeEntryAllowed && (selectionMethod === "stripe" || selectionMethod === "pass_bundle" || selectionMethod === "membership_bundle");
@@ -134683,9 +135319,8 @@ function useEventRegistrationWizard(options) {
134683
135319
  api,
134684
135320
  registrationTarget,
134685
135321
  selectedAttendanceMode,
134686
- selectedTicketTypeId,
135322
+ ticketSelections,
134687
135323
  selectedSlidingAmount,
134688
- ticketsCount,
134689
135324
  formData,
134690
135325
  altchaSolution,
134691
135326
  requireGuestDetails,
@@ -134706,12 +135341,12 @@ function useEventRegistrationWizard(options) {
134706
135341
  setSelectedAttendanceMode(
134707
135342
  (event.deliveryMode ?? "in_person") === "hybrid" ? null : (event.deliveryMode ?? "in_person") === "online" ? "online" : "in_person"
134708
135343
  );
134709
- setSelectedTicketTypeId(null);
135344
+ setSelectedTicketLines([]);
134710
135345
  dispatchFlow({ type: "event-changed", hasPreSelectedContext: true });
134711
135346
  };
134712
135347
  const handleRetry = () => {
134713
135348
  dispatchFlow({ type: "reset", hasPreSelectedContext });
134714
- setSelectedTicketTypeId(null);
135349
+ setSelectedTicketLines([]);
134715
135350
  setSelectedSlidingAmountInput("");
134716
135351
  setSelectedAttendanceMode(
134717
135352
  preSelectedEvent?.deliveryMode === "online" ? "online" : preSelectedEvent?.deliveryMode === "in_person" ? "in_person" : null
@@ -134747,17 +135382,20 @@ function useEventRegistrationWizard(options) {
134747
135382
  setTicketsCount,
134748
135383
  selectedAttendanceMode,
134749
135384
  setSelectedAttendanceMode,
134750
- selectedTicketTypeId,
134751
- setSelectedTicketTypeId,
135385
+ ticketSelections,
135386
+ selectedTicketLines: normalizedSelectedTicketLines,
135387
+ setSelectedTicketLines: (lines) => setSelectedTicketLines(normalizeTicketSelectionLines(lines)),
134752
135388
  selectedSlidingAmountInput,
134753
135389
  setSelectedSlidingAmountInput,
134754
135390
  selectedSlidingAmount,
134755
135391
  selectedEventSlidingScale,
134756
135392
  slidingScaleSelectionMessage,
134757
135393
  selectedTicketType,
135394
+ ticketSelectionSummaryLines,
135395
+ ticketSelectionSubtotalCents,
134758
135396
  visibleTicketTypes,
134759
135397
  ticketTypeSelectionRequired,
134760
- hasValidSelectedTicketType,
135398
+ hasValidTicketSelection,
134761
135399
  eventRequiresPayment,
134762
135400
  formData,
134763
135401
  setFormData,
@@ -161162,10 +161800,92 @@ function SliderField({ path, backend, config }) {
161162
161800
  }
161163
161801
  );
161164
161802
  }
161803
+ function InlineTextField({
161804
+ path,
161805
+ backend,
161806
+ config
161807
+ }) {
161808
+ const plainTextPath = config.plainTextField ? siblingPath(path, config.plainTextField) : null;
161809
+ return plainTextPath ? /* @__PURE__ */ jsx(LinkedInlineTextField, { path, backend, config, plainTextPath }) : /* @__PURE__ */ jsx(StandaloneInlineTextField, { path, backend, config });
161810
+ }
161811
+ function StandaloneInlineTextField({
161812
+ path,
161813
+ backend,
161814
+ config
161815
+ }) {
161816
+ const { value, error, setValue } = useField(path, backend);
161817
+ const inlineValue = useMemo(
161818
+ () => coerceInlineTextWithFallback(value, void 0),
161819
+ [value]
161820
+ );
161821
+ const plainText = inlineTextToPlainText(inlineValue);
161822
+ return /* @__PURE__ */ jsx(
161823
+ FieldFrame,
161824
+ {
161825
+ fieldPath: path,
161826
+ label: config.label,
161827
+ required: config.required,
161828
+ description: config.description,
161829
+ error: error?.message,
161830
+ children: ({ id }) => /* @__PURE__ */ jsx(
161831
+ Textarea,
161832
+ {
161833
+ id,
161834
+ value: plainText,
161835
+ maxLength: config.maxLength,
161836
+ rows: 2,
161837
+ onChange: (event) => {
161838
+ const nextPlainText = event.target.value;
161839
+ setValue(plainTextToInlineText(nextPlainText));
161840
+ }
161841
+ }
161842
+ )
161843
+ }
161844
+ );
161845
+ }
161846
+ function LinkedInlineTextField({
161847
+ path,
161848
+ backend,
161849
+ config,
161850
+ plainTextPath
161851
+ }) {
161852
+ const { value, error, setValue } = useField(path, backend);
161853
+ const plainTextField = useField(plainTextPath, backend);
161854
+ const inlineValue = useMemo(
161855
+ () => coerceInlineTextWithFallback(value, plainTextField.value),
161856
+ [plainTextField.value, value]
161857
+ );
161858
+ const plainText = inlineTextToPlainText(inlineValue);
161859
+ return /* @__PURE__ */ jsx(
161860
+ FieldFrame,
161861
+ {
161862
+ fieldPath: path,
161863
+ label: config.label,
161864
+ required: config.required,
161865
+ description: config.description,
161866
+ error: error?.message,
161867
+ children: ({ id }) => /* @__PURE__ */ jsx(
161868
+ Textarea,
161869
+ {
161870
+ id,
161871
+ value: plainText,
161872
+ maxLength: config.maxLength,
161873
+ rows: 2,
161874
+ onChange: (event) => {
161875
+ const nextPlainText = event.target.value;
161876
+ setValue(plainTextToInlineText(nextPlainText));
161877
+ plainTextField.setValue(nextPlainText);
161878
+ }
161879
+ }
161880
+ )
161881
+ }
161882
+ );
161883
+ }
161165
161884
 
161166
161885
  // ../block-form/src/registry/widgets.ts
161167
161886
  var WIDGET_COMPONENTS = {
161168
161887
  text: TextField,
161888
+ inlineText: InlineTextField,
161169
161889
  number: NumberField,
161170
161890
  select: SelectField,
161171
161891
  sdkSelect: SdkSelectField,
@@ -162467,6 +163187,914 @@ function EditorChrome({
162467
163187
  ] });
162468
163188
  }
162469
163189
 
163190
+ // ../editor/src/inline/domParse.ts
163191
+ function parseEditableInlineText(root) {
163192
+ const runs = [];
163193
+ for (const child of Array.from(root.childNodes)) {
163194
+ collectInlineTextRuns(child, [], runs);
163195
+ }
163196
+ return normalizeInlineText(runs);
163197
+ }
163198
+ function inlineTextToEditableHtml(value) {
163199
+ return normalizeInlineText(value).map(runToHtml).join("");
163200
+ }
163201
+ function collectInlineTextRuns(node, inheritedMarks, runs) {
163202
+ if (node.nodeType === Node.TEXT_NODE) {
163203
+ const text2 = node.textContent ?? "";
163204
+ if (text2.length === 0) return;
163205
+ const marks = normalizeInlineTextMarks(inheritedMarks);
163206
+ runs.push(marks.length > 0 ? { text: text2, marks } : { text: text2 });
163207
+ return;
163208
+ }
163209
+ if (!(node instanceof HTMLElement)) return;
163210
+ const nextMarks = normalizeInlineTextMarks([...inheritedMarks, ...marksForElement(node)]);
163211
+ for (const child of Array.from(node.childNodes)) {
163212
+ collectInlineTextRuns(child, nextMarks, runs);
163213
+ }
163214
+ }
163215
+ function marksForElement(element) {
163216
+ const tagName = element.tagName.toLowerCase();
163217
+ const marks = [];
163218
+ if (tagName === "strong" || tagName === "b") marks.push({ kind: "strong" });
163219
+ if (tagName === "em" || tagName === "i") marks.push({ kind: "emphasis" });
163220
+ for (const tone of inlineTextAccentTones) {
163221
+ if (element.classList.contains(`rb-inline-text-accent-${tone}`)) {
163222
+ marks.push({ kind: "accent", tone });
163223
+ }
163224
+ }
163225
+ for (const tone of inlineTextHighlightTones) {
163226
+ if (element.classList.contains(`rb-inline-text-highlight-${tone}`)) {
163227
+ marks.push({ kind: "highlight", tone });
163228
+ }
163229
+ }
163230
+ return marks;
163231
+ }
163232
+ function runToHtml(run3) {
163233
+ return normalizeInlineTextMarks(run3.marks ?? []).reduceRight(
163234
+ (html, mark) => wrapHtmlWithMark(html, mark),
163235
+ escapeHtml(run3.text)
163236
+ );
163237
+ }
163238
+ function wrapHtmlWithMark(html, mark) {
163239
+ switch (mark.kind) {
163240
+ case "strong":
163241
+ return `<strong>${html}</strong>`;
163242
+ case "emphasis":
163243
+ return `<em>${html}</em>`;
163244
+ case "accent":
163245
+ return `<span class="rb-inline-text-accent rb-inline-text-accent-${accentClass(mark.tone)}">${html}</span>`;
163246
+ case "highlight":
163247
+ return `<span class="rb-inline-text-highlight rb-inline-text-highlight-${highlightClass(mark.tone)}">${html}</span>`;
163248
+ }
163249
+ }
163250
+ function accentClass(tone) {
163251
+ return tone;
163252
+ }
163253
+ function highlightClass(tone) {
163254
+ return tone;
163255
+ }
163256
+ function escapeHtml(value) {
163257
+ return value.replace(/&/g, "&amp;").replace(/</g, "&lt;").replace(/>/g, "&gt;").replace(/"/g, "&quot;");
163258
+ }
163259
+
163260
+ // ../editor/src/inline/presentation.ts
163261
+ var DARK_TOOLBAR_SURFACE = { r: 15, g: 23, b: 42, a: 1 };
163262
+ var LIGHT_TOOLBAR_SURFACE = { r: 255, g: 255, b: 255, a: 1 };
163263
+ var DARK_TEXT = { r: 15, g: 23, b: 42, a: 1 };
163264
+ var LIGHT_TEXT = { r: 255, g: 255, b: 255, a: 1 };
163265
+ var UNKNOWN_SURFACE_CANDIDATES = [
163266
+ LIGHT_TOOLBAR_SURFACE,
163267
+ DARK_TOOLBAR_SURFACE
163268
+ ];
163269
+ var MIN_SAMPLE_CONTRAST = 3;
163270
+ function defaultInlineTextPresentationContext(tone) {
163271
+ const surface = fallbackSurfaceForToolbarTone(tone);
163272
+ const selectedTextRgba = tone === "dark" ? LIGHT_TEXT : DARK_TEXT;
163273
+ return {
163274
+ surface,
163275
+ selectedTextColor: colorToCss(selectedTextRgba),
163276
+ selectedTextRgba,
163277
+ accentTextRgbaByTone: defaultAccentTextRgbaByTone(selectedTextRgba),
163278
+ typography: {}
163279
+ };
163280
+ }
163281
+ function readInlineTextPresentationContext(editable, toolbarTone) {
163282
+ const computed = window.getComputedStyle(editable);
163283
+ const selectedTextRgba = parseCssColor(computed.color) ?? fallbackTextColorForTone(toolbarTone);
163284
+ return {
163285
+ surface: readInlineTextSurface(editable, toolbarTone),
163286
+ selectedTextColor: colorToCss(selectedTextRgba),
163287
+ selectedTextRgba,
163288
+ accentTextRgbaByTone: readAccentTextRgbaByTone(editable, selectedTextRgba),
163289
+ typography: {
163290
+ fontFamily: computed.fontFamily,
163291
+ fontSize: computed.fontSize,
163292
+ fontStyle: computed.fontStyle,
163293
+ fontWeight: computed.fontWeight,
163294
+ letterSpacing: computed.letterSpacing,
163295
+ lineHeight: computed.lineHeight,
163296
+ textTransform: computed.textTransform
163297
+ }
163298
+ };
163299
+ }
163300
+ function buildAccentTonePreview(tone, context) {
163301
+ const textColor = accentColorValue(tone);
163302
+ const textRgba = context.accentTextRgbaByTone[tone] ?? context.selectedTextRgba;
163303
+ return buildPreview({ color: textColor }, textRgba, context);
163304
+ }
163305
+ function buildHighlightTonePreview(tone, context) {
163306
+ const background = highlightBackgroundValue(tone);
163307
+ return buildPreview(
163308
+ { color: context.selectedTextColor, background },
163309
+ context.selectedTextRgba,
163310
+ context
163311
+ );
163312
+ }
163313
+ function buildPlainTonePreview(context) {
163314
+ return buildPreview(
163315
+ { color: context.selectedTextColor },
163316
+ context.selectedTextRgba,
163317
+ context
163318
+ );
163319
+ }
163320
+ function buildPreview(markStyle, textRgba, context) {
163321
+ const surface = previewSurfaceForText(textRgba, context.surface);
163322
+ const textOnSurface = contrastRatio2(textRgba, surface.rgba);
163323
+ const lowContrast = textOnSurface < MIN_SAMPLE_CONTRAST;
163324
+ return {
163325
+ lowContrast,
163326
+ surfaceStyle: {
163327
+ backgroundColor: surface.color
163328
+ },
163329
+ surfaceRgba: surface.rgba,
163330
+ textRgba,
163331
+ textStyle: {
163332
+ ...previewTypography(context.typography),
163333
+ ...markStyle
163334
+ }
163335
+ };
163336
+ }
163337
+ function inlineTextTonePreviewLooksSame(left, right) {
163338
+ return sameRgba(left.surfaceRgba, right.surfaceRgba) && sameRgba(left.textRgba, right.textRgba) && left.textStyle.background === right.textStyle.background && left.textStyle.backgroundColor === right.textStyle.backgroundColor;
163339
+ }
163340
+ function previewTypography(typography) {
163341
+ const fontSize = parseCssPixelValue(typography.fontSize);
163342
+ if (fontSize === null || fontSize <= 22) {
163343
+ return typography;
163344
+ }
163345
+ return {
163346
+ ...typography,
163347
+ fontSize: "18px",
163348
+ lineHeight: "1.15"
163349
+ };
163350
+ }
163351
+ function previewSurfaceForText(textRgba, surface) {
163352
+ if (surface.kind === "block-solid" || surface.kind === "image-overlay") {
163353
+ return surface;
163354
+ }
163355
+ const currentContrast = contrastRatio2(textRgba, surface.rgba);
163356
+ if (currentContrast >= MIN_SAMPLE_CONTRAST) {
163357
+ return surface;
163358
+ }
163359
+ return [surface.rgba, ...UNKNOWN_SURFACE_CANDIDATES].map((candidate) => ({
163360
+ color: colorToCss(candidate),
163361
+ rgba: candidate,
163362
+ contrast: contrastRatio2(textRgba, candidate)
163363
+ })).reduce((best, candidate) => candidate.contrast > best.contrast ? candidate : best);
163364
+ }
163365
+ function defaultAccentTextRgbaByTone(fallback2) {
163366
+ return Object.fromEntries(
163367
+ inlineTextAccentTones.map((tone) => [tone, fallback2])
163368
+ );
163369
+ }
163370
+ function readAccentTextRgbaByTone(editable, fallback2) {
163371
+ return Object.fromEntries(
163372
+ inlineTextAccentTones.map((tone) => [
163373
+ tone,
163374
+ resolveCssColor(editable, accentColorValue(tone), "color") ?? fallback2
163375
+ ])
163376
+ );
163377
+ }
163378
+ function readInlineTextSurface(editable, toolbarTone) {
163379
+ const fallback2 = readThemeFallbackSurface(editable) ?? fallbackSurfaceForToolbarTone(toolbarTone);
163380
+ const block = editable.closest("[data-block]") ?? editable.closest(".rb-section");
163381
+ if (!block) return fallback2;
163382
+ const styleLayer = block.querySelector(".background-style");
163383
+ const overlay = block.querySelector(".background-overlay");
163384
+ const hasImage = Boolean(block.querySelector(".background-image"));
163385
+ const overlayColor = overlay ? readVisibleBackgroundColor(overlay) : null;
163386
+ if (hasImage && overlay && overlayColor) {
163387
+ const opacity = readOpacity(overlay);
163388
+ const composited = opacity < 1 || overlayColor.a < 1 ? compositeColors(overlayColor, fallback2.rgba, opacity) : overlayColor;
163389
+ return {
163390
+ kind: "image-overlay",
163391
+ color: colorToCss(composited),
163392
+ rgba: composited
163393
+ };
163394
+ }
163395
+ if (!hasImage && styleLayer) {
163396
+ const styleLayerColor = readVisibleBackgroundColor(styleLayer, { includeElementOpacity: true });
163397
+ if (styleLayerColor) {
163398
+ return {
163399
+ kind: "block-solid",
163400
+ color: colorToCss(styleLayerColor),
163401
+ rgba: styleLayerColor
163402
+ };
163403
+ }
163404
+ }
163405
+ if (!hasImage) {
163406
+ const blockColor = readVisibleBackgroundColor(block, { includeElementOpacity: true });
163407
+ if (blockColor) {
163408
+ return {
163409
+ kind: "block-solid",
163410
+ color: colorToCss(blockColor),
163411
+ rgba: blockColor
163412
+ };
163413
+ }
163414
+ }
163415
+ return fallback2;
163416
+ }
163417
+ function readThemeFallbackSurface(root) {
163418
+ const themeScope = root.closest(".theme-scope") ?? root;
163419
+ const computed = window.getComputedStyle(themeScope);
163420
+ const color = readRgbTripletCustomProperty(computed, "--section-bg-color") ?? readRgbTripletCustomProperty(computed, "--tb-background") ?? readRgbTripletCustomProperty(computed, "--tb-surface");
163421
+ return color ? {
163422
+ kind: "theme-fallback",
163423
+ color: colorToCss(color),
163424
+ rgba: color
163425
+ } : null;
163426
+ }
163427
+ function fallbackSurfaceForToolbarTone(tone) {
163428
+ const rgba = tone === "dark" ? DARK_TOOLBAR_SURFACE : LIGHT_TOOLBAR_SURFACE;
163429
+ return {
163430
+ kind: "toolbar-fallback",
163431
+ color: colorToCss(rgba),
163432
+ rgba
163433
+ };
163434
+ }
163435
+ function fallbackTextColorForTone(tone) {
163436
+ return tone === "dark" ? LIGHT_TEXT : DARK_TEXT;
163437
+ }
163438
+ function readVisibleBackgroundColor(element, options = {}) {
163439
+ const computed = window.getComputedStyle(element);
163440
+ if (computed.display === "none" || computed.visibility === "hidden") return null;
163441
+ const color = parseCssColor(computed.backgroundColor);
163442
+ if (!color || color.a === 0) return null;
163443
+ if (!options.includeElementOpacity) return color;
163444
+ const opacity = readOpacity(element);
163445
+ return opacity < 1 ? { ...color, a: color.a * opacity } : color;
163446
+ }
163447
+ function readOpacity(element) {
163448
+ const opacity = Number.parseFloat(window.getComputedStyle(element).opacity);
163449
+ if (!Number.isFinite(opacity)) return 1;
163450
+ return Math.max(0, Math.min(1, opacity));
163451
+ }
163452
+ function accentColorValue(tone) {
163453
+ switch (tone) {
163454
+ case "accent":
163455
+ return "rgb(var(--tb-accent))";
163456
+ case "brand":
163457
+ return "rgb(var(--tb-primary))";
163458
+ case "contrast":
163459
+ return "var(--section-text-color, rgb(var(--tb-text)))";
163460
+ }
163461
+ }
163462
+ function highlightBackgroundValue(tone) {
163463
+ switch (tone) {
163464
+ case "soft":
163465
+ return "color-mix(in oklab, var(--section-text-color, rgb(var(--tb-text))) 14%, transparent)";
163466
+ case "accent":
163467
+ return "color-mix(in oklab, rgb(var(--tb-accent)) 28%, transparent)";
163468
+ case "brand":
163469
+ return "color-mix(in oklab, rgb(var(--tb-primary)) 24%, transparent)";
163470
+ }
163471
+ }
163472
+ function resolveCssColor(referenceElement, value, property) {
163473
+ if (!referenceElement) return parseCssColor(value);
163474
+ const probe = document.createElement("span");
163475
+ probe.textContent = "";
163476
+ probe.style.position = "absolute";
163477
+ probe.style.pointerEvents = "none";
163478
+ probe.style.visibility = "hidden";
163479
+ probe.style[property] = value;
163480
+ referenceElement.appendChild(probe);
163481
+ const resolved = window.getComputedStyle(probe)[property];
163482
+ probe.remove();
163483
+ return parseCssColor(resolved);
163484
+ }
163485
+ function readRgbTripletCustomProperty(computed, propertyName) {
163486
+ const value = computed.getPropertyValue(propertyName).trim();
163487
+ const parts = value.split(/\s+/).map((part) => Number.parseFloat(part));
163488
+ const [r4, g2, b2] = parts;
163489
+ if (!isValidRgbChannel(r4) || !isValidRgbChannel(g2) || !isValidRgbChannel(b2)) {
163490
+ return null;
163491
+ }
163492
+ return { r: r4, g: g2, b: b2, a: 1 };
163493
+ }
163494
+ function parseCssColor(value) {
163495
+ const trimmed = value.trim().toLowerCase();
163496
+ if (!trimmed || trimmed === "transparent") {
163497
+ return { r: 0, g: 0, b: 0, a: 0 };
163498
+ }
163499
+ const hex = parseHexColor(trimmed);
163500
+ if (hex) return hex;
163501
+ const rgbMatch = trimmed.match(/^rgba?\(([^)]+)\)$/);
163502
+ if (!rgbMatch?.[1]) return null;
163503
+ const normalized = rgbMatch[1].replace(/\s*\/\s*/, ", ");
163504
+ const parts = normalized.split(/[,\s]+/).filter(Boolean);
163505
+ const [rawR, rawG, rawB, rawAlpha] = parts;
163506
+ const r4 = parseRgbChannel(rawR);
163507
+ const g2 = parseRgbChannel(rawG);
163508
+ const b2 = parseRgbChannel(rawB);
163509
+ const alpha2 = rawAlpha === void 0 ? 1 : parseAlphaChannel(rawAlpha);
163510
+ if (!isValidRgbChannel(r4) || !isValidRgbChannel(g2) || !isValidRgbChannel(b2)) {
163511
+ return null;
163512
+ }
163513
+ return {
163514
+ r: r4,
163515
+ g: g2,
163516
+ b: b2,
163517
+ a: isValidAlpha(alpha2) ? alpha2 : 1
163518
+ };
163519
+ }
163520
+ function parseRgbChannel(value) {
163521
+ if (!value) return void 0;
163522
+ return value.endsWith("%") ? Number.parseFloat(value) / 100 * 255 : Number.parseFloat(value);
163523
+ }
163524
+ function parseAlphaChannel(value) {
163525
+ return value.endsWith("%") ? Number.parseFloat(value) / 100 : Number.parseFloat(value);
163526
+ }
163527
+ function parseHexColor(value) {
163528
+ const hex = value.startsWith("#") ? value.slice(1) : value;
163529
+ if (!/^[0-9a-f]{3}([0-9a-f]{3})?$/i.test(hex)) return null;
163530
+ const normalized = hex.length === 3 ? hex.split("").map((part) => `${part}${part}`).join("") : hex;
163531
+ return {
163532
+ r: Number.parseInt(normalized.slice(0, 2), 16),
163533
+ g: Number.parseInt(normalized.slice(2, 4), 16),
163534
+ b: Number.parseInt(normalized.slice(4, 6), 16),
163535
+ a: 1
163536
+ };
163537
+ }
163538
+ function isValidRgbChannel(value) {
163539
+ return typeof value === "number" && Number.isFinite(value) && value >= 0 && value <= 255;
163540
+ }
163541
+ function isValidAlpha(value) {
163542
+ return typeof value === "number" && Number.isFinite(value) && value >= 0 && value <= 1;
163543
+ }
163544
+ function parseCssPixelValue(value) {
163545
+ if (typeof value !== "string") return null;
163546
+ const match2 = value.trim().match(/^(\d+(?:\.\d+)?)px$/);
163547
+ return match2?.[1] ? Number.parseFloat(match2[1]) : null;
163548
+ }
163549
+ function sameRgba(left, right) {
163550
+ return Math.abs(left.r - right.r) < 1 && Math.abs(left.g - right.g) < 1 && Math.abs(left.b - right.b) < 1 && Math.abs(left.a - right.a) < 0.01;
163551
+ }
163552
+ function colorToCss(color) {
163553
+ const r4 = Math.round(color.r);
163554
+ const g2 = Math.round(color.g);
163555
+ const b2 = Math.round(color.b);
163556
+ return color.a < 1 ? `rgba(${r4}, ${g2}, ${b2}, ${color.a})` : `rgb(${r4}, ${g2}, ${b2})`;
163557
+ }
163558
+ function compositeColors(foreground, background, opacity) {
163559
+ const alpha2 = Math.max(0, Math.min(1, foreground.a * opacity));
163560
+ return {
163561
+ r: foreground.r * alpha2 + background.r * (1 - alpha2),
163562
+ g: foreground.g * alpha2 + background.g * (1 - alpha2),
163563
+ b: foreground.b * alpha2 + background.b * (1 - alpha2),
163564
+ a: 1
163565
+ };
163566
+ }
163567
+ function contrastRatio2(foreground, background) {
163568
+ const fg = foreground.a < 1 ? compositeColors(foreground, background, 1) : foreground;
163569
+ const bg = background.a < 1 ? compositeColors(background, LIGHT_TOOLBAR_SURFACE, 1) : background;
163570
+ const lighter = Math.max(relativeLuminance2(fg), relativeLuminance2(bg));
163571
+ const darker = Math.min(relativeLuminance2(fg), relativeLuminance2(bg));
163572
+ return (lighter + 0.05) / (darker + 0.05);
163573
+ }
163574
+ function relativeLuminance2(color) {
163575
+ const r4 = srgbToLinear2(color.r);
163576
+ const g2 = srgbToLinear2(color.g);
163577
+ const b2 = srgbToLinear2(color.b);
163578
+ return 0.2126 * r4 + 0.7152 * g2 + 0.0722 * b2;
163579
+ }
163580
+ function srgbToLinear2(channel) {
163581
+ const normalized = channel / 255;
163582
+ return normalized <= 0.03928 ? normalized / 12.92 : Math.pow((normalized + 0.055) / 1.055, 2.4);
163583
+ }
163584
+ function FloatingToolbar({
163585
+ selection,
163586
+ selectedText,
163587
+ tone,
163588
+ presentationContext,
163589
+ openMenu,
163590
+ setOpenMenu,
163591
+ onToggleStrong,
163592
+ onToggleEmphasis,
163593
+ onApplyAccent,
163594
+ onRemoveAccent,
163595
+ onApplyHighlight,
163596
+ onRemoveHighlight
163597
+ }) {
163598
+ const { style: style2, placement } = toolbarPlacement(selection.rect, openMenu !== null);
163599
+ const clampedSelectedText = selectedText.trim().length > 0 ? selectedText.trim() : "Selected text";
163600
+ const plainPreview = buildPlainTonePreview(presentationContext);
163601
+ const accentPreviews = inlineTextAccentTones.map((toneOption) => ({
163602
+ toneOption,
163603
+ preview: buildAccentTonePreview(toneOption, presentationContext)
163604
+ })).filter(({ preview }) => !inlineTextTonePreviewLooksSame(preview, plainPreview));
163605
+ return /* @__PURE__ */ jsxs(
163606
+ "div",
163607
+ {
163608
+ "data-rb-inline-text-toolbar": true,
163609
+ "data-tone": tone,
163610
+ "data-placement": placement,
163611
+ className: "rb-inline-text-toolbar",
163612
+ style: style2,
163613
+ onMouseDown: (event) => {
163614
+ event.preventDefault();
163615
+ },
163616
+ children: [
163617
+ /* @__PURE__ */ jsx("button", { type: "button", "aria-label": "Bold", title: "Bold", onClick: onToggleStrong, children: /* @__PURE__ */ jsx(Bold, { "aria-hidden": true, size: 16 }) }),
163618
+ /* @__PURE__ */ jsx("button", { type: "button", "aria-label": "Italic", title: "Italic", onClick: onToggleEmphasis, children: /* @__PURE__ */ jsx(Italic, { "aria-hidden": true, size: 16 }) }),
163619
+ /* @__PURE__ */ jsx(
163620
+ "button",
163621
+ {
163622
+ type: "button",
163623
+ "aria-label": "Accent color",
163624
+ title: "Accent color",
163625
+ "data-open": openMenu === "accent" ? "true" : void 0,
163626
+ onClick: () => setOpenMenu(openMenu === "accent" ? null : "accent"),
163627
+ children: /* @__PURE__ */ jsx(Palette, { "aria-hidden": true, size: 16 })
163628
+ }
163629
+ ),
163630
+ /* @__PURE__ */ jsx(
163631
+ "button",
163632
+ {
163633
+ type: "button",
163634
+ "aria-label": "Highlight background",
163635
+ title: "Highlight background",
163636
+ "data-open": openMenu === "highlight" ? "true" : void 0,
163637
+ onClick: () => setOpenMenu(openMenu === "highlight" ? null : "highlight"),
163638
+ children: /* @__PURE__ */ jsx(Highlighter, { "aria-hidden": true, size: 16 })
163639
+ }
163640
+ ),
163641
+ openMenu === "accent" ? /* @__PURE__ */ jsxs(ToneMenu, { label: "Accent color", children: [
163642
+ accentPreviews.map(({ toneOption, preview }) => /* @__PURE__ */ jsx(
163643
+ "button",
163644
+ {
163645
+ type: "button",
163646
+ "aria-label": `Apply ${toneOption} accent color`,
163647
+ title: `Apply ${toneOption} accent color`,
163648
+ onClick: () => onApplyAccent(toneOption),
163649
+ children: /* @__PURE__ */ jsx(
163650
+ TonePreview,
163651
+ {
163652
+ preview,
163653
+ selectedText: clampedSelectedText
163654
+ }
163655
+ )
163656
+ },
163657
+ toneOption
163658
+ )),
163659
+ /* @__PURE__ */ jsx(
163660
+ "button",
163661
+ {
163662
+ type: "button",
163663
+ "aria-label": "Use plain text color",
163664
+ title: "Use plain text color",
163665
+ onClick: onRemoveAccent,
163666
+ children: /* @__PURE__ */ jsx(
163667
+ TonePreview,
163668
+ {
163669
+ preview: plainPreview,
163670
+ selectedText: clampedSelectedText
163671
+ }
163672
+ )
163673
+ }
163674
+ )
163675
+ ] }) : null,
163676
+ openMenu === "highlight" ? /* @__PURE__ */ jsxs(ToneMenu, { label: "Highlight background", children: [
163677
+ inlineTextHighlightTones.map((toneOption) => /* @__PURE__ */ jsx(
163678
+ "button",
163679
+ {
163680
+ type: "button",
163681
+ "aria-label": `Apply ${toneOption} highlight background`,
163682
+ title: `Apply ${toneOption} highlight background`,
163683
+ onClick: () => onApplyHighlight(toneOption),
163684
+ children: /* @__PURE__ */ jsx(
163685
+ TonePreview,
163686
+ {
163687
+ preview: buildHighlightTonePreview(toneOption, presentationContext),
163688
+ selectedText: clampedSelectedText
163689
+ }
163690
+ )
163691
+ },
163692
+ toneOption
163693
+ )),
163694
+ /* @__PURE__ */ jsx(
163695
+ "button",
163696
+ {
163697
+ type: "button",
163698
+ "aria-label": "Remove highlight background",
163699
+ title: "Remove highlight background",
163700
+ onClick: onRemoveHighlight,
163701
+ children: /* @__PURE__ */ jsx(
163702
+ TonePreview,
163703
+ {
163704
+ preview: plainPreview,
163705
+ selectedText: clampedSelectedText
163706
+ }
163707
+ )
163708
+ }
163709
+ )
163710
+ ] }) : null
163711
+ ]
163712
+ }
163713
+ );
163714
+ }
163715
+ function TonePreview({
163716
+ preview,
163717
+ selectedText
163718
+ }) {
163719
+ return /* @__PURE__ */ jsx(
163720
+ "span",
163721
+ {
163722
+ className: "rb-inline-text-toolbar-preview",
163723
+ "data-low-contrast": preview.lowContrast ? "true" : void 0,
163724
+ style: preview.surfaceStyle,
163725
+ children: /* @__PURE__ */ jsx("span", { className: "rb-inline-text-toolbar-preview-text", style: preview.textStyle, children: selectedText })
163726
+ }
163727
+ );
163728
+ }
163729
+ function ToneMenu({ label, children }) {
163730
+ return /* @__PURE__ */ jsx("div", { className: "rb-inline-text-toolbar-menu", role: "menu", "aria-label": label, children });
163731
+ }
163732
+ function toolbarPlacement(rect, hasOpenMenu) {
163733
+ const toolbarWidth = hasOpenMenu ? 340 : 188;
163734
+ const left = Math.min(
163735
+ Math.max(12, rect.left + rect.width / 2 - toolbarWidth / 2),
163736
+ Math.max(12, window.innerWidth - toolbarWidth - 12)
163737
+ );
163738
+ const aboveTop = rect.top - 48;
163739
+ if (aboveTop < 12) {
163740
+ return {
163741
+ placement: "below",
163742
+ style: { left, top: rect.bottom + 10, width: toolbarWidth }
163743
+ };
163744
+ }
163745
+ return {
163746
+ placement: "above",
163747
+ style: { left, top: aboveTop, width: toolbarWidth }
163748
+ };
163749
+ }
163750
+ function InlineTextEditorStyles() {
163751
+ return /* @__PURE__ */ jsx("style", { children: `
163752
+ [data-rb-inline-text-editor] {
163753
+ min-width: 1ch;
163754
+ outline: 1px dashed transparent;
163755
+ outline-offset: 3px;
163756
+ }
163757
+
163758
+ [data-rb-inline-text-editor]:hover,
163759
+ [data-rb-inline-text-editor]:focus-visible {
163760
+ outline-color: rgba(148, 163, 184, 0.76);
163761
+ }
163762
+
163763
+ [data-rb-inline-text-editor][data-rb-inline-text-empty="true"]::before {
163764
+ content: attr(data-placeholder);
163765
+ color: rgba(148, 163, 184, 0.82);
163766
+ }
163767
+
163768
+ [data-rb-inline-text-editor] .rb-inline-text-accent,
163769
+ [data-rb-inline-text-editor] .rb-inline-text-highlight {
163770
+ font: inherit;
163771
+ letter-spacing: inherit;
163772
+ text-transform: inherit;
163773
+ }
163774
+
163775
+ .rb-inline-text-toolbar {
163776
+ align-items: center;
163777
+ background: rgba(15, 23, 42, 0.94);
163778
+ border: 1px solid rgba(255, 255, 255, 0.14);
163779
+ border-radius: 8px;
163780
+ box-shadow: 0 18px 44px rgba(15, 23, 42, 0.28);
163781
+ color: white;
163782
+ display: flex;
163783
+ gap: 3px;
163784
+ justify-content: center;
163785
+ padding: 5px;
163786
+ position: fixed;
163787
+ z-index: 80;
163788
+ }
163789
+
163790
+ .rb-inline-text-toolbar[data-tone="light"] {
163791
+ background: rgba(255, 255, 255, 0.98);
163792
+ border-color: rgba(15, 23, 42, 0.14);
163793
+ color: rgb(15, 23, 42);
163794
+ }
163795
+
163796
+ .rb-inline-text-toolbar > button,
163797
+ .rb-inline-text-toolbar-menu > button {
163798
+ align-items: center;
163799
+ background: transparent;
163800
+ border: 0;
163801
+ border-radius: 6px;
163802
+ color: inherit;
163803
+ cursor: pointer;
163804
+ display: inline-flex;
163805
+ font: inherit;
163806
+ justify-content: center;
163807
+ min-height: 30px;
163808
+ min-width: 30px;
163809
+ padding: 5px 7px;
163810
+ }
163811
+
163812
+ .rb-inline-text-toolbar > button:hover,
163813
+ .rb-inline-text-toolbar > button[data-open="true"],
163814
+ .rb-inline-text-toolbar-menu > button:hover {
163815
+ background: rgba(148, 163, 184, 0.22);
163816
+ }
163817
+
163818
+ .rb-inline-text-toolbar-menu {
163819
+ background: inherit;
163820
+ border: inherit;
163821
+ border-radius: 8px;
163822
+ box-shadow: inherit;
163823
+ display: grid;
163824
+ gap: 2px;
163825
+ left: 0;
163826
+ min-width: 100%;
163827
+ padding: 5px;
163828
+ position: absolute;
163829
+ top: calc(100% + 6px);
163830
+ }
163831
+
163832
+ .rb-inline-text-toolbar[data-placement="below"] .rb-inline-text-toolbar-menu {
163833
+ bottom: calc(100% + 6px);
163834
+ top: auto;
163835
+ }
163836
+
163837
+ .rb-inline-text-toolbar-menu > button {
163838
+ justify-content: flex-start;
163839
+ width: 100%;
163840
+ overflow: hidden;
163841
+ text-align: left;
163842
+ white-space: nowrap;
163843
+ }
163844
+
163845
+ .rb-inline-text-toolbar-preview {
163846
+ align-items: center;
163847
+ border: 1px solid rgba(148, 163, 184, 0.32);
163848
+ border-radius: 5px;
163849
+ display: inline-flex;
163850
+ max-width: 100%;
163851
+ width: 100%;
163852
+ min-height: 28px;
163853
+ overflow: hidden;
163854
+ padding: 3px 7px;
163855
+ }
163856
+
163857
+ .rb-inline-text-toolbar-preview[data-low-contrast="true"] {
163858
+ box-shadow:
163859
+ inset 0 0 0 1px rgba(255, 255, 255, 0.52),
163860
+ 0 0 0 1px rgba(15, 23, 42, 0.26);
163861
+ }
163862
+
163863
+ .rb-inline-text-toolbar-preview-text {
163864
+ display: inline;
163865
+ max-width: 100%;
163866
+ overflow: hidden;
163867
+ text-overflow: ellipsis;
163868
+ white-space: nowrap;
163869
+ }
163870
+ ` });
163871
+ }
163872
+
163873
+ // ../editor/src/inline/selection.ts
163874
+ function readSelection(root) {
163875
+ const range = readSelectionRange(root);
163876
+ if (!range || range.start === range.end) return null;
163877
+ return range;
163878
+ }
163879
+ function readSelectionRange(root) {
163880
+ if (!root) return null;
163881
+ const selection = window.getSelection();
163882
+ if (!selection || selection.rangeCount === 0) return null;
163883
+ const range = selection.getRangeAt(0);
163884
+ if (!root.contains(range.commonAncestorContainer)) return null;
163885
+ const startProbe = document.createRange();
163886
+ startProbe.selectNodeContents(root);
163887
+ startProbe.setEnd(range.startContainer, range.startOffset);
163888
+ const start = startProbe.toString().length;
163889
+ const end = start + range.toString().length;
163890
+ return {
163891
+ start: Math.min(start, end),
163892
+ end: Math.max(start, end),
163893
+ rect: range.getBoundingClientRect()
163894
+ };
163895
+ }
163896
+ function rangeHasMark(value, range, kind) {
163897
+ const start = Math.min(range.start, range.end);
163898
+ const end = Math.max(range.start, range.end);
163899
+ if (start === end) return false;
163900
+ let offset4 = 0;
163901
+ let sawText = false;
163902
+ for (const run3 of normalizeInlineText(value)) {
163903
+ const runStart = offset4;
163904
+ const runEnd = offset4 + run3.text.length;
163905
+ offset4 = runEnd;
163906
+ if (runEnd <= start || runStart >= end) continue;
163907
+ sawText = true;
163908
+ if (!(run3.marks ?? []).some((mark) => mark.kind === kind)) {
163909
+ return false;
163910
+ }
163911
+ }
163912
+ return sawText;
163913
+ }
163914
+ function InlineTextEditor({
163915
+ value,
163916
+ onChange,
163917
+ as: Comp = "span",
163918
+ id,
163919
+ className,
163920
+ placeholder,
163921
+ maxLength,
163922
+ ariaLabel,
163923
+ ariaDescribedBy,
163924
+ toolbarTone = "dark",
163925
+ onFocus,
163926
+ onBlur
163927
+ }) {
163928
+ const editableRef = useRef(null);
163929
+ const initialValue = useMemo(() => truncateInlineText(value, maxLength), [maxLength, value]);
163930
+ const currentValueRef = useRef(initialValue);
163931
+ const [plainText, setPlainText] = useState(() => inlineTextToPlainText(initialValue));
163932
+ const [selection, setSelection] = useState(null);
163933
+ const [presentationContext, setPresentationContext] = useState(() => defaultInlineTextPresentationContext(toolbarTone));
163934
+ const [openMenu, setOpenMenu] = useState(null);
163935
+ const [isFocused, setIsFocused] = useState(false);
163936
+ const syncEditableDom = useCallback((nextValue) => {
163937
+ if (!editableRef.current) return;
163938
+ editableRef.current.innerHTML = inlineTextToEditableHtml(nextValue);
163939
+ }, []);
163940
+ const setEditableRef = useCallback((node) => {
163941
+ if (node && editableRef.current !== node) {
163942
+ node.innerHTML = inlineTextToEditableHtml(currentValueRef.current);
163943
+ }
163944
+ editableRef.current = node;
163945
+ }, []);
163946
+ useEffect(() => {
163947
+ const nextValue = truncateInlineText(value, maxLength);
163948
+ if (inlineTextEqual(nextValue, currentValueRef.current)) return;
163949
+ if (isFocused) return;
163950
+ currentValueRef.current = nextValue;
163951
+ setPlainText(inlineTextToPlainText(nextValue));
163952
+ syncEditableDom(nextValue);
163953
+ }, [isFocused, maxLength, syncEditableDom, value]);
163954
+ const commitValue = useCallback(
163955
+ (nextValue, options = {}) => {
163956
+ const normalized = normalizeInlineText(nextValue);
163957
+ const limited = truncateInlineText(normalized, maxLength);
163958
+ const shouldSyncDom = Boolean(options.syncDom) || !inlineTextEqual(normalized, limited) || limited.length === 0 && (editableRef.current?.innerHTML ?? "").length > 0;
163959
+ const nextPlainText = inlineTextToPlainText(limited);
163960
+ currentValueRef.current = limited;
163961
+ setPlainText((previous) => previous === nextPlainText ? previous : nextPlainText);
163962
+ if (shouldSyncDom) {
163963
+ syncEditableDom(limited);
163964
+ }
163965
+ onChange(limited, nextPlainText);
163966
+ },
163967
+ [maxLength, onChange, syncEditableDom]
163968
+ );
163969
+ const updateSelectionFromDom = useCallback(() => {
163970
+ const editable = editableRef.current;
163971
+ const nextSelection = readSelection(editable);
163972
+ setSelection(nextSelection);
163973
+ if (editable && nextSelection) {
163974
+ setPresentationContext(readInlineTextPresentationContext(editable, toolbarTone));
163975
+ }
163976
+ if (!nextSelection) {
163977
+ setOpenMenu(null);
163978
+ }
163979
+ }, [toolbarTone]);
163980
+ const clearSelectionUi = useCallback(() => {
163981
+ setSelection(null);
163982
+ setOpenMenu(null);
163983
+ }, []);
163984
+ const applyMark = useCallback(
163985
+ (mark) => {
163986
+ if (!selection) return;
163987
+ const nextValue = applyInlineTextMarkToRange(currentValueRef.current, selection, mark);
163988
+ commitValue(nextValue, { syncDom: true });
163989
+ clearSelectionUi();
163990
+ },
163991
+ [clearSelectionUi, commitValue, selection]
163992
+ );
163993
+ const removeMark2 = useCallback(
163994
+ (kind) => {
163995
+ if (!selection) return;
163996
+ const nextValue = removeInlineTextMarkFromRange(currentValueRef.current, selection, kind);
163997
+ commitValue(nextValue, { syncDom: true });
163998
+ clearSelectionUi();
163999
+ },
164000
+ [clearSelectionUi, commitValue, selection]
164001
+ );
164002
+ const toggleMark2 = useCallback(
164003
+ (kind) => {
164004
+ if (!selection) return;
164005
+ if (rangeHasMark(currentValueRef.current, selection, kind)) {
164006
+ removeMark2(kind);
164007
+ return;
164008
+ }
164009
+ applyMark({ kind });
164010
+ },
164011
+ [applyMark, removeMark2, selection]
164012
+ );
164013
+ return /* @__PURE__ */ jsxs("span", { className: "rb-inline-text-editor-root", children: [
164014
+ /* @__PURE__ */ jsx(InlineTextEditorStyles, {}),
164015
+ /* @__PURE__ */ jsx(
164016
+ Comp,
164017
+ {
164018
+ id,
164019
+ ref: setEditableRef,
164020
+ "data-rb-inline-text-editor": true,
164021
+ "data-rb-inline-text-empty": plainText.length === 0 ? "true" : void 0,
164022
+ "data-placeholder": placeholder,
164023
+ contentEditable: true,
164024
+ suppressContentEditableWarning: true,
164025
+ spellCheck: true,
164026
+ role: "textbox",
164027
+ "aria-multiline": "false",
164028
+ "aria-label": ariaLabel,
164029
+ "aria-describedby": ariaDescribedBy,
164030
+ className,
164031
+ onInput: (event) => {
164032
+ commitValue(parseEditableInlineText(event.currentTarget));
164033
+ updateSelectionFromDom();
164034
+ },
164035
+ onKeyDown: (event) => {
164036
+ if (event.key === "Enter") {
164037
+ event.preventDefault();
164038
+ }
164039
+ },
164040
+ onPaste: (event) => {
164041
+ event.preventDefault();
164042
+ const range = readSelectionRange(editableRef.current) ?? selection;
164043
+ const text2 = event.clipboardData.getData("text/plain").replace(/\s+/g, " ");
164044
+ if (!range) {
164045
+ commitValue(plainTextToInlineText(plainText + text2), { syncDom: true });
164046
+ clearSelectionUi();
164047
+ return;
164048
+ }
164049
+ commitValue(
164050
+ replaceInlineTextRange(currentValueRef.current, range, plainTextToInlineText(text2)),
164051
+ { syncDom: true }
164052
+ );
164053
+ clearSelectionUi();
164054
+ },
164055
+ onMouseUp: () => updateSelectionFromDom(),
164056
+ onKeyUp: (event) => {
164057
+ if (event.key === "Escape") {
164058
+ clearSelectionUi();
164059
+ return;
164060
+ }
164061
+ updateSelectionFromDom();
164062
+ },
164063
+ onFocus: () => {
164064
+ setIsFocused(true);
164065
+ onFocus?.();
164066
+ },
164067
+ onBlur: () => {
164068
+ window.setTimeout(() => {
164069
+ const activeElement = document.activeElement;
164070
+ if (activeElement?.closest("[data-rb-inline-text-toolbar]")) return;
164071
+ setIsFocused(false);
164072
+ clearSelectionUi();
164073
+ onBlur?.();
164074
+ }, 0);
164075
+ }
164076
+ }
164077
+ ),
164078
+ selection ? /* @__PURE__ */ jsx(
164079
+ FloatingToolbar,
164080
+ {
164081
+ selection,
164082
+ selectedText: plainText.slice(selection.start, selection.end),
164083
+ tone: toolbarTone,
164084
+ presentationContext,
164085
+ openMenu,
164086
+ setOpenMenu,
164087
+ onToggleStrong: () => toggleMark2("strong"),
164088
+ onToggleEmphasis: () => toggleMark2("emphasis"),
164089
+ onApplyAccent: (tone) => applyMark({ kind: "accent", tone }),
164090
+ onRemoveAccent: () => removeMark2("accent"),
164091
+ onApplyHighlight: (tone) => applyMark({ kind: "highlight", tone }),
164092
+ onRemoveHighlight: () => removeMark2("highlight")
164093
+ }
164094
+ ) : null
164095
+ ] });
164096
+ }
164097
+
162470
164098
  // ../../node_modules/.pnpm/orderedmap@2.1.1/node_modules/orderedmap/dist/index.js
162471
164099
  function OrderedMap(content) {
162472
164100
  this.content = content;
@@ -183074,7 +184702,7 @@ function requireUseSyncExternalStoreShim_development() {
183074
184702
  return x === y2 && (x !== 0 || 1 / x === 1 / y2) || x !== x && y2 !== y2;
183075
184703
  }
183076
184704
  var objectIs = typeof Object.is === "function" ? Object.is : is;
183077
- var useState95 = React$1.useState, useEffect101 = React$1.useEffect, useLayoutEffect11 = React$1.useLayoutEffect, useDebugValue2 = React$1.useDebugValue;
184705
+ var useState97 = React$1.useState, useEffect102 = React$1.useEffect, useLayoutEffect11 = React$1.useLayoutEffect, useDebugValue2 = React$1.useDebugValue;
183078
184706
  var didWarnOld18Alpha = false;
183079
184707
  var didWarnUncachedGetSnapshot = false;
183080
184708
  function useSyncExternalStore7(subscribe, getSnapshot, getServerSnapshot) {
@@ -183096,7 +184724,7 @@ function requireUseSyncExternalStoreShim_development() {
183096
184724
  }
183097
184725
  }
183098
184726
  }
183099
- var _useState = useState95({
184727
+ var _useState = useState97({
183100
184728
  inst: {
183101
184729
  value,
183102
184730
  getSnapshot
@@ -183111,7 +184739,7 @@ function requireUseSyncExternalStoreShim_development() {
183111
184739
  });
183112
184740
  }
183113
184741
  }, [subscribe, value, getSnapshot]);
183114
- useEffect101(function() {
184742
+ useEffect102(function() {
183115
184743
  if (checkIfSnapshotChanged(inst)) {
183116
184744
  forceUpdate({
183117
184745
  inst
@@ -183376,9 +185004,9 @@ function requireWithSelector_development() {
183376
185004
  }
183377
185005
  var objectIs = typeof Object.is === "function" ? Object.is : is;
183378
185006
  var useSyncExternalStore7 = shim2.useSyncExternalStore;
183379
- var useRef83 = React$1.useRef, useEffect101 = React$1.useEffect, useMemo92 = React$1.useMemo, useDebugValue2 = React$1.useDebugValue;
185007
+ var useRef84 = React$1.useRef, useEffect102 = React$1.useEffect, useMemo95 = React$1.useMemo, useDebugValue2 = React$1.useDebugValue;
183380
185008
  function useSyncExternalStoreWithSelector(subscribe, getSnapshot, getServerSnapshot, selector, isEqual) {
183381
- var instRef = useRef83(null);
185009
+ var instRef = useRef84(null);
183382
185010
  var inst;
183383
185011
  if (instRef.current === null) {
183384
185012
  inst = {
@@ -183389,7 +185017,7 @@ function requireWithSelector_development() {
183389
185017
  } else {
183390
185018
  inst = instRef.current;
183391
185019
  }
183392
- var _useMemo = useMemo92(function() {
185020
+ var _useMemo = useMemo95(function() {
183393
185021
  var hasMemo = false;
183394
185022
  var memoizedSnapshot;
183395
185023
  var memoizedSelection;
@@ -183433,7 +185061,7 @@ function requireWithSelector_development() {
183433
185061
  return [getSnapshotWithSelector, getServerSnapshotWithSelector];
183434
185062
  }, [getSnapshot, getServerSnapshot, selector, isEqual]), getSelection2 = _useMemo[0], getServerSelection = _useMemo[1];
183435
185063
  var value = useSyncExternalStore7(subscribe, getSelection2, getServerSelection);
183436
- useEffect101(function() {
185064
+ useEffect102(function() {
183437
185065
  inst.hasValue = true;
183438
185066
  inst.value = value;
183439
185067
  }, [value]);
@@ -184428,6 +186056,52 @@ function moveCaretToEnd(element) {
184428
186056
  selection.removeAllRanges();
184429
186057
  selection.addRange(range);
184430
186058
  }
186059
+ function PreviewInlineTextEditor({
186060
+ path,
186061
+ plainTextPath,
186062
+ fallbackPlainText = "",
186063
+ onBlockFieldFocus,
186064
+ className,
186065
+ maxLength,
186066
+ as: Comp = "span"
186067
+ }) {
186068
+ const { isEditingMode } = useEditor();
186069
+ const { value, setValue } = useStoreBinding(path);
186070
+ const { value: plainTextValue, setValue: setPlainTextValue } = useStoreBinding(plainTextPath);
186071
+ const [isFocused, setIsFocused] = useState(false);
186072
+ const isLinkedSidebarFocus = useEditorUiStore(
186073
+ (state) => path ? isLinkedSidebarField(path, state.activePreviewField) : false
186074
+ );
186075
+ const editorValue = useMemo(
186076
+ () => coerceInlineTextWithFallback(value, typeof plainTextValue === "string" ? plainTextValue : fallbackPlainText),
186077
+ [fallbackPlainText, plainTextValue, value]
186078
+ );
186079
+ const handleChange = useCallback(
186080
+ (nextValue, plainText) => {
186081
+ setValue(nextValue);
186082
+ setPlainTextValue(plainText);
186083
+ },
186084
+ [setPlainTextValue, setValue]
186085
+ );
186086
+ if (!isEditingMode) return null;
186087
+ return /* @__PURE__ */ jsx(
186088
+ InlineTextEditor,
186089
+ {
186090
+ value: editorValue,
186091
+ onChange: handleChange,
186092
+ as: Comp,
186093
+ maxLength,
186094
+ placeholder: "Add a headline",
186095
+ toolbarTone: "dark",
186096
+ className: `rounded px-1 transition-colors focus:bg-white/10 focus-visible:bg-white/10 ${isLinkedSidebarFocus || isFocused ? "bg-white/5" : ""} ${className ?? ""}`,
186097
+ onFocus: () => {
186098
+ setIsFocused(true);
186099
+ onBlockFieldFocus?.(path);
186100
+ },
186101
+ onBlur: () => setIsFocused(false)
186102
+ }
186103
+ );
186104
+ }
184431
186105
  var PreviewRichTextEditorInner = ({
184432
186106
  path,
184433
186107
  linkedEntryField,
@@ -189303,4 +190977,4 @@ lucide-react/dist/esm/lucide-react.mjs:
189303
190977
  *)
189304
190978
  */
189305
190979
 
189306
- export { AMBIENT_BACKGROUND_ROLES2 as AMBIENT_BACKGROUND_ROLES, ArrowDown, ArrowUp, BackgroundColorField, BackgroundGradientField, Badge2 as Badge, BlockApiProvider, Box, Button, CSS2 as CSS, Callout, CalloutDescription, CalloutTitle, Card, CardContent, CardHeader, CardTitle, Check, ChevronDown, ChevronLeft, ChevronRight, Collapsible2 as Collapsible, CollapsibleContent2 as CollapsibleContent, CollapsibleTrigger2 as CollapsibleTrigger, ColorPicker, Combobox, CommandMultiSelect, Content, ContentFieldsForm, ContentSpinner, Copy, DEFAULT_LAUNCH_READINESS_INPUT, Dialog2 as Dialog, DialogClose2 as DialogClose, DialogContent2 as DialogContent, DialogDescription2 as DialogDescription, DialogFooter, DialogHeader, DialogTitle2 as DialogTitle, DndContext, DropdownMenu2 as DropdownMenu, DropdownMenuContent2 as DropdownMenuContent, DropdownMenuItem2 as DropdownMenuItem, DropdownMenuLabel2 as DropdownMenuLabel, DropdownMenuSeparator2 as DropdownMenuSeparator, DropdownMenuTrigger2 as DropdownMenuTrigger, EDITABLE_SURFACE_FORWARDING_PROP, EMPTY_DOC, EditableBlockProvider, EditorChrome, EditorProvider, EllipsisVertical, EmptyState2 as EmptyState, EntryControllerProvider, EyeOff, FieldFrame, FixedBottomSurface, FormRenderer, GRADIENT_PRESETS, GripVertical, Image, ImagePlus, Input, KeyboardCode, LINKED_CONTENT_ENTRY_META_KEY, Label4 as Label, List2 as List, LoaderCircle, ManifestForm, Maximize2, MediaEditor, MediaEditorProvider, MediaPickerDialog, MediaPickerMini, Monitor, PAGE_DESIGN_EDITOR_STATE_FETCH_ERROR_MESSAGE, PUBLIC_FILE_FIELD_KINDS, PageRenderer, Palette, PaletteProvider, Pencil, Plus, PointerSensor, PreviewDesignCoordinatorProvider, PreviewDesignHistoryOrderProvider, PreviewRichTextEditor, PreviewTextEditor, PreviewThemeOverlayProvider, ResizableSplitPane, ResponsiveScope, RichText2 as RichText, RichTextEditorSurface, Root2, RotateCcw, SECTION_BACKGROUND_MIN_SOURCE_HEIGHT, SECTION_BACKGROUND_MIN_SOURCE_WIDTH, SITE_CHROME_CLASS_NAMES, SITE_CHROME_VISIBLE_HEADER_SELECTOR, SUBROUTE_KINDS, ScrollableDialogContent, SdkConfigProvider, Search, Select2 as Select, SelectContent2 as SelectContent, SelectItem2 as SelectItem, SelectTrigger2 as SelectTrigger, SelectValue2 as SelectValue, Separator2 as Separator, Settings, SiteChromeCustomizeProvider, SiteDocumentLayout, Smartphone, Sparkles, Surface, Tablet, Tabs2 as Tabs, TabsContent2 as TabsContent, TabsList2 as TabsList, TabsTrigger2 as TabsTrigger, Text2 as Text, Textarea, ThemeScope, Trash2, TriangleAlert, Trigger, Upload, X, applyBackgroundOverrideContentPatch, applyCompiledRuntimeFieldsToContent, applyFeatureCardIconSuggestions, applyPageDesignEditorAction, applyResolvedSelections, asDesignBlockId, asRecord, assertNever, assertNever5 as assertNever2, attachRenderableMediaAssetFields, augmentManifestWithStyleGroups, backgroundColorTokens, backgroundOverrideEquals, beginAutosaveBatch, buildApplySiteStyleSelectionBody, buildEditorModelRuntimeFieldsByBlockId, buildSiteChromeLookModels, buildThemeRuntime, buttonPersonalities, canCycleBackgroundOverrideValue, canRedoHistory, canUndoHistory, cancelPreview, classifyHistoryShortcut, classifyKnownMimeType, clearTypographyFontOverrides, clientComponentRegistry, closestCenter, cn, confirmAutosaveBatch, createBlock, createCustomBlockRegistry, createEditorInsertBlockCommand, createEditorRemoveBlockCommand, createEditorReorderBlocksCommand, createEntrySlotBlock, createFeatureCardIconKey, createHistoryState, createManifestFormAdapter, createManifestValidation, createMicrobatcher, createOptimisticActionRunner, createRoutingHelpers, createSnapshotFromPageRecord, createStoreBackend, createStyleConfiguratorState, curatedSiteStyles, cycleSiteChromeLookId, cycleableSiteChromeOptions, decodePublicProductCategorySelectorQuery, defaultBackgroundOverrideForMode, defaultSectionTransitionVariantForFamily, deleteBlock, deleteEntrySlotBlock, deriveLaunchReadiness, deriveRouteMetadataPresentation, deriveStyleConfiguratorCapabilities, deriveTransactionCapabilities, designRuntimeRulesForTheme, dismissNotices, dismissWarnings, emitMediaCropDebug, enabledBackgroundModes, enqueueTransaction, evaluateTypographyFontSlot, evaluateVisibility, expectParsedBrandedId, findButtonPersonality, findFooterLook, findPaletteVariant, findTypographyPreset, foldSubroute, formatSiteChromeBackgroundTokenLabel, getBlockDefinition, getBlockIconSemanticFallbackId, getClientRect, getCuratedSiteStyle, getDirectImageUrlForMediaAsset, getFeatureCardIconCompletion, getFieldIntent, getFooterLayout, getGeneratedBlockIconStyleState, getHeaderLayout, getHeaderStyle, getIconComponent, getIconPickerOptionsForPreset, getLinkedContentEntryMeta, getModalConfig, getPageDesignEditorState, getRichTextImagePositionFromTarget, gradientToCss, idleEditorTransactionQueueState, imagePoolForOverride, inferLegacyOfferingsPreviewGroupOrder, insertOrReplaceRichTextImage, isHeaderField, isIconPickerPreset, isInternalResolvedLinkValue, isKeyboardEvent, isKnownIconName, isNonEmptyValue, isObjectRecord2 as isObjectRecord, isOfferingsPreviewSourceKey, isPreviewingChange, isSupportedLoaderEndpoint, isSvgMimeType, isThemeV2NormalEditorRawStyleFieldName, isThemeV2NormalEditorRawStylePath, listBlockDescriptors, listContentTypes, listEntryPageContentSlots, lucide_react_exports, markApplyFailed, markApplySaved, markApplySaving, mergeBlockDescriptorsWithRegistry, mergeManifestWithSdkOptions, mutateBlockContent, normalEditorCuratedPromotedFieldPaths, normalizeOfferingsPreviewGroupOrder, normalizePickerSearchThreshold, normalizePublicApiLoaderParams, openRow, paletteOverridesSchema, paletteVariants, parseAspectRatioValue, parseBackgroundOverrideFromContent, parseBlockIconValue, parseMediaAssetId, parseSiteIconStyleGuideVersionId, parseSiteId, planBackgroundOverride, planBackgroundTransition, planPageDesignLayoutLookCompatibility, planSiteChromeFooterLayoutSelection, planSiteChromeLookSelection, planSiteDocument, planSiteStylePreviewChange, prefetchBlockData, previewAssistantEnabled, previewButtonPersonality, previewDesignHistoryDomainForCommand, previewFooterLook, previewHeaderLayout, previewHeaderStyle, previewPaletteVariant, previewSiteStyle, previewTypographyPreset, pushHistoryEntry, rankBackgroundImagePoolItems, recoveryConflictCopy, redoHistory, rejectAutosaveBatch, renderBlock, reorderBlocks, reorderEntrySlotBlocks, requireEntriesForCuratedChoices, resolveBackgroundCapability, resolveBlockTitle, resolveContentTitle, resolveIconPickerPreset, resolveImageUrlWithContext, resolveMediaSlotContract, resolveOfferingsPreviewGroupOrderEntries, resolvePageRouteSlug, resolvePickerSelectionLabel, resolvePreviewSidebarTab, resolveStyleConfiguratorInitialSnapshot, resolveVideoSelectionIntentForMediaField, resolveVisiblePromotedFieldPathsForEditorBlock, sectionTransitionFamilies, sectionTransitionFamilyForBoundaryOptionId, sectionTransitionVariantForBoundaryOptionId, selectPreviewDesignHistoryDomain, selectionSnapshotFromApplySiteStyleSelectionResponse, setPaletteOverrides, setTypographyBodyFontOverride, setTypographyHeadingFontOverride, shouldShowPickerSearch, siteFooterManifest, siteHeaderManifest, siteOptionSources, stableSerialize, styleConfiguratorHistoryEntryForPersistedSelection, suggestFeatureCardSemanticIcons, suggestSemanticIconForFeatureCard, surfaceResolutionContextFromTheme, syncStyleConfiguratorState, systemCustomizeFacetAppliesToLayoutVariant, systemCustomizeFacetApplyContentPatch, systemCustomizeFacetCurrentValue, systemCustomizeFacetDefinitionForBlock, systemCustomizeFacetDefinitionsForBlock, systemCustomizeFacetLabelForValue, systemCustomizeFacetNextValue, systemCustomizeFacetRollbackContentPatch, toFeatureCardIconSuggestionInputs, toRoutableLinkPayload, toggleRow, typographyPresets, undoHistory, unfinishedBlockCopy, unsafeAsEditorBlockId, unsafeAsEditorBlockValues, unsafeAsLinkedContentEntryId, useAsyncPickerOptions, useBackendWatch, useBlockContext, useCombinedRefs, useDebouncedLatestSave, useDndContext, useDraggable, useDroppable, useEditor, useEditorUiStore, useEditorUiStoreInstance, useEntryController, useEntryEditorController, useField, useIsomorphicLayoutEffect3 as useIsomorphicLayoutEffect, useMediaEditor, useMediaEditorOptional, useMultiAutosave, useOptionalEditorUiStoreInstance, usePreviewDesignCoordinator, usePreviewDesignHistoryOrder, usePreviewThemeOverlay, useRichTextEditor, useSdkConfig, useSensor, useSensors, useSiteChromeCustomizeOptional, useUISelector, useUniqueId, validateBlockManifestIssues, visibleHeaderClearancePx };
190980
+ export { AMBIENT_BACKGROUND_ROLES2 as AMBIENT_BACKGROUND_ROLES, ArrowDown, ArrowUp, BackgroundColorField, BackgroundGradientField, Badge2 as Badge, BlockApiProvider, Box, Button, CSS2 as CSS, Callout, CalloutDescription, CalloutTitle, Card, CardContent, CardHeader, CardTitle, Check, ChevronDown, ChevronLeft, ChevronRight, Collapsible2 as Collapsible, CollapsibleContent2 as CollapsibleContent, CollapsibleTrigger2 as CollapsibleTrigger, ColorPicker, Combobox, CommandMultiSelect, Content, ContentFieldsForm, ContentSpinner, Copy, DEFAULT_LAUNCH_READINESS_INPUT, Dialog2 as Dialog, DialogClose2 as DialogClose, DialogContent2 as DialogContent, DialogDescription2 as DialogDescription, DialogFooter, DialogHeader, DialogTitle2 as DialogTitle, DndContext, DropdownMenu2 as DropdownMenu, DropdownMenuContent2 as DropdownMenuContent, DropdownMenuItem2 as DropdownMenuItem, DropdownMenuLabel2 as DropdownMenuLabel, DropdownMenuSeparator2 as DropdownMenuSeparator, DropdownMenuTrigger2 as DropdownMenuTrigger, EDITABLE_SURFACE_FORWARDING_PROP, EMPTY_DOC, EditableBlockProvider, EditorChrome, EditorProvider, EllipsisVertical, EmptyState2 as EmptyState, EntryControllerProvider, EyeOff, FieldFrame, FixedBottomSurface, FormRenderer, GRADIENT_PRESETS, GripVertical, Image, ImagePlus, InlineTextEditor, Input, KeyboardCode, LINKED_CONTENT_ENTRY_META_KEY, Label4 as Label, List2 as List, LoaderCircle, ManifestForm, Maximize2, MediaEditor, MediaEditorProvider, MediaPickerDialog, MediaPickerMini, Monitor, PAGE_DESIGN_EDITOR_STATE_FETCH_ERROR_MESSAGE, PUBLIC_FILE_FIELD_KINDS, PageRenderer, Palette, PaletteProvider, Pencil, Plus, PointerSensor, PreviewDesignCoordinatorProvider, PreviewDesignHistoryOrderProvider, PreviewInlineTextEditor, PreviewRichTextEditor, PreviewTextEditor, PreviewThemeOverlayProvider, ResizableSplitPane, ResponsiveScope, RichText2 as RichText, RichTextEditorSurface, Root2, RotateCcw, SECTION_BACKGROUND_MIN_SOURCE_HEIGHT, SECTION_BACKGROUND_MIN_SOURCE_WIDTH, SITE_CHROME_CLASS_NAMES, SITE_CHROME_VISIBLE_HEADER_SELECTOR, SUBROUTE_KINDS, ScrollableDialogContent, SdkConfigProvider, Search, Select2 as Select, SelectContent2 as SelectContent, SelectItem2 as SelectItem, SelectTrigger2 as SelectTrigger, SelectValue2 as SelectValue, Separator2 as Separator, Settings, SiteChromeCustomizeProvider, SiteDocumentLayout, Smartphone, Sparkles, Surface, Tablet, Tabs2 as Tabs, TabsContent2 as TabsContent, TabsList2 as TabsList, TabsTrigger2 as TabsTrigger, Text2 as Text, Textarea, ThemeScope, Trash2, TriangleAlert, Trigger, Upload, X, applyBackgroundOverrideContentPatch, applyCompiledRuntimeFieldsToContent, applyFeatureCardIconSuggestions, applyPageDesignEditorAction, applyResolvedSelections, asDesignBlockId, asRecord, assertNever, assertNever5 as assertNever2, attachRenderableMediaAssetFields, augmentManifestWithStyleGroups, backgroundColorTokens, backgroundOverrideEquals, beginAutosaveBatch, buildApplySiteStyleSelectionBody, buildEditorModelRuntimeFieldsByBlockId, buildSiteChromeLookModels, buildThemeRuntime, buttonPersonalities, canCycleBackgroundOverrideValue, canRedoHistory, canUndoHistory, cancelPreview, classifyHistoryShortcut, classifyKnownMimeType, clearTypographyFontOverrides, clientComponentRegistry, closestCenter, cn, coerceInlineTextWithFallback, confirmAutosaveBatch, createBlock, createCustomBlockRegistry, createEditorInsertBlockCommand, createEditorRemoveBlockCommand, createEditorReorderBlocksCommand, createEntrySlotBlock, createFeatureCardIconKey, createHistoryState, createManifestFormAdapter, createManifestValidation, createMicrobatcher, createOptimisticActionRunner, createRoutingHelpers, createSnapshotFromPageRecord, createStoreBackend, createStyleConfiguratorState, curatedSiteStyles, cycleSiteChromeLookId, cycleableSiteChromeOptions, decodePublicProductCategorySelectorQuery, defaultBackgroundOverrideForMode, defaultSectionTransitionVariantForFamily, deleteBlock, deleteEntrySlotBlock, deriveLaunchReadiness, deriveRouteMetadataPresentation, deriveStyleConfiguratorCapabilities, deriveTransactionCapabilities, designRuntimeRulesForTheme, dismissNotices, dismissWarnings, emitMediaCropDebug, enabledBackgroundModes, enqueueTransaction, evaluateTypographyFontSlot, evaluateVisibility, expectParsedBrandedId, findButtonPersonality, findFooterLook, findPaletteVariant, findTypographyPreset, foldSubroute, formatSiteChromeBackgroundTokenLabel, getAtPath, getBlockDefinition, getBlockIconSemanticFallbackId, getClientRect, getCuratedSiteStyle, getDirectImageUrlForMediaAsset, getFeatureCardIconCompletion, getFieldIntent, getFooterLayout, getGeneratedBlockIconStyleState, getHeaderLayout, getHeaderStyle, getIconComponent, getIconPickerOptionsForPreset, getLinkedContentEntryMeta, getModalConfig, getPageDesignEditorState, getRichTextImagePositionFromTarget, gradientToCss, idleEditorTransactionQueueState, imagePoolForOverride, inferLegacyOfferingsPreviewGroupOrder, inlineTextToPlainText, insertOrReplaceRichTextImage, isHeaderField, isIconPickerPreset, isInlineTextEmpty, isInternalResolvedLinkValue, isKeyboardEvent, isKnownIconName, isNonEmptyValue, isObjectRecord2 as isObjectRecord, isOfferingsPreviewSourceKey, isPreviewingChange, isSupportedLoaderEndpoint, isSvgMimeType, isThemeV2NormalEditorRawStyleFieldName, isThemeV2NormalEditorRawStylePath, listBlockDescriptors, listContentTypes, listEntryPageContentSlots, lucide_react_exports, markApplyFailed, markApplySaved, markApplySaving, mergeBlockDescriptorsWithRegistry, mergeManifestWithSdkOptions, mutateBlockContent, normalEditorCuratedPromotedFieldPaths, normalizeOfferingsPreviewGroupOrder, normalizePickerSearchThreshold, normalizePublicApiLoaderParams, openRow, paletteOverridesSchema, paletteVariants, parseAspectRatioValue, parseBackgroundOverrideFromContent, parseBlockIconValue, parseMediaAssetId, parseSiteIconStyleGuideVersionId, parseSiteId, planBackgroundOverride, planBackgroundTransition, planPageDesignLayoutLookCompatibility, planSiteChromeFooterLayoutSelection, planSiteChromeLookSelection, planSiteDocument, planSiteStylePreviewChange, prefetchBlockData, previewAssistantEnabled, previewButtonPersonality, previewDesignHistoryDomainForCommand, previewFooterLook, previewHeaderLayout, previewHeaderStyle, previewPaletteVariant, previewSiteStyle, previewTypographyPreset, pushHistoryEntry, rankBackgroundImagePoolItems, recoveryConflictCopy, redoHistory, rejectAutosaveBatch, renderBlock, renderInlineText, reorderBlocks, reorderEntrySlotBlocks, requireEntriesForCuratedChoices, resolveBackgroundCapability, resolveBlockTitle, resolveContentTitle, resolveIconPickerPreset, resolveImageUrlWithContext, resolveMediaSlotContract, resolveOfferingsPreviewGroupOrderEntries, resolvePageRouteSlug, resolvePickerSelectionLabel, resolvePreviewSidebarTab, resolveStyleConfiguratorInitialSnapshot, resolveVideoSelectionIntentForMediaField, resolveVisiblePromotedFieldPathsForEditorBlock, sectionTransitionFamilies, sectionTransitionFamilyForBoundaryOptionId, sectionTransitionVariantForBoundaryOptionId, selectPreviewDesignHistoryDomain, selectionSnapshotFromApplySiteStyleSelectionResponse, setPaletteOverrides, setTypographyBodyFontOverride, setTypographyHeadingFontOverride, shouldShowPickerSearch, siblingPath, siteFooterManifest, siteHeaderManifest, siteOptionSources, stableSerialize, styleConfiguratorHistoryEntryForPersistedSelection, suggestFeatureCardSemanticIcons, suggestSemanticIconForFeatureCard, surfaceResolutionContextFromTheme, syncStyleConfiguratorState, systemCustomizeFacetAppliesToLayoutVariant, systemCustomizeFacetApplyContentPatch, systemCustomizeFacetCurrentValue, systemCustomizeFacetDefinitionForBlock, systemCustomizeFacetDefinitionsForBlock, systemCustomizeFacetLabelForValue, systemCustomizeFacetNextValue, systemCustomizeFacetRollbackContentPatch, toFeatureCardIconSuggestionInputs, toRoutableLinkPayload, toggleRow, typographyPresets, undoHistory, unfinishedBlockCopy, unsafeAsEditorBlockId, unsafeAsEditorBlockValues, unsafeAsLinkedContentEntryId, useAsyncPickerOptions, useBackendWatch, useBlockContext, useCombinedRefs, useDebouncedLatestSave, useDndContext, useDraggable, useDroppable, useEditor, useEditorUiStore, useEditorUiStoreInstance, useEntryController, useEntryEditorController, useField, useIsomorphicLayoutEffect3 as useIsomorphicLayoutEffect, useMediaEditor, useMediaEditorOptional, useMultiAutosave, useOptionalEditorUiStoreInstance, usePreviewDesignCoordinator, usePreviewDesignHistoryOrder, usePreviewThemeOverlay, useRichTextEditor, useSdkConfig, useSensor, useSensors, useSiteChromeCustomizeOptional, useUISelector, useUniqueId, validateBlockManifestIssues, visibleHeaderClearancePx };