@bettercms-ai/kit 0.1.1 → 2.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +22 -16
- package/dist/_virtual/_rolldown/runtime.js +13 -0
- package/dist/adapters/dock-values.d.ts +28 -0
- package/dist/adapters/dock-values.js +41 -0
- package/dist/adapters/dock-values.js.map +1 -0
- package/dist/adapters/icons.d.ts +15 -0
- package/dist/adapters/icons.js +27 -0
- package/dist/adapters/icons.js.map +1 -0
- package/dist/adapters/lossy.d.ts +326 -0
- package/dist/adapters/lossy.js +414 -0
- package/dist/adapters/lossy.js.map +1 -0
- package/dist/adapters/prod-types.d.ts +546 -0
- package/dist/adapters/prod-types.js +714 -0
- package/dist/adapters/prod-types.js.map +1 -0
- package/dist/adapters/schema.d.ts +154 -0
- package/dist/adapters/schema.js +3020 -0
- package/dist/adapters/schema.js.map +1 -0
- package/dist/adapters/values.d.ts +221 -0
- package/dist/adapters/values.js +623 -0
- package/dist/adapters/values.js.map +1 -0
- package/dist/brand/logo.d.ts +17 -0
- package/dist/brand/logo.js +96 -0
- package/dist/brand/logo.js.map +1 -0
- package/dist/context.d.ts +359 -0
- package/dist/context.js +217 -0
- package/dist/context.js.map +1 -0
- package/dist/controls/button.d.ts +72 -0
- package/dist/controls/button.js +578 -0
- package/dist/controls/button.js.map +1 -0
- package/dist/controls/c1.d.ts +11 -0
- package/dist/controls/c1.js +24 -0
- package/dist/controls/c1.js.map +1 -0
- package/dist/controls/c2.d.ts +10 -0
- package/dist/controls/c2.js +19 -0
- package/dist/controls/c2.js.map +1 -0
- package/dist/controls/choice.d.ts +44 -0
- package/dist/controls/choice.js +463 -0
- package/dist/controls/choice.js.map +1 -0
- package/dist/controls/code-register.d.ts +1 -0
- package/dist/controls/code-register.js +8 -0
- package/dist/controls/code-register.js.map +1 -0
- package/dist/controls/code.d.ts +42 -0
- package/dist/controls/code.js +397 -0
- package/dist/controls/code.js.map +1 -0
- package/dist/controls/color.d.ts +5 -0
- package/dist/controls/color.js +130 -0
- package/dist/controls/color.js.map +1 -0
- package/dist/controls/component-services.d.ts +156 -0
- package/dist/controls/component-services.js +7 -0
- package/dist/controls/component-services.js.map +1 -0
- package/dist/controls/date-register.d.ts +1 -0
- package/dist/controls/date-register.js +9 -0
- package/dist/controls/date-register.js.map +1 -0
- package/dist/controls/date-zone.d.ts +104 -0
- package/dist/controls/date-zone.js +278 -0
- package/dist/controls/date-zone.js.map +1 -0
- package/dist/controls/date.d.ts +7 -0
- package/dist/controls/date.js +466 -0
- package/dist/controls/date.js.map +1 -0
- package/dist/controls/form-picker-register.d.ts +1 -0
- package/dist/controls/form-picker-register.js +19 -0
- package/dist/controls/form-picker-register.js.map +1 -0
- package/dist/controls/form-picker.d.ts +43 -0
- package/dist/controls/form-picker.js +85 -0
- package/dist/controls/form-picker.js.map +1 -0
- package/dist/controls/icon-register.d.ts +1 -0
- package/dist/controls/icon-register.js +8 -0
- package/dist/controls/icon-register.js.map +1 -0
- package/dist/controls/icon.d.ts +40 -0
- package/dist/controls/icon.js +360 -0
- package/dist/controls/icon.js.map +1 -0
- package/dist/controls/index.d.ts +5 -0
- package/dist/controls/index.js +38 -0
- package/dist/controls/index.js.map +1 -0
- package/dist/controls/json-register.d.ts +1 -0
- package/dist/controls/json-register.js +8 -0
- package/dist/controls/json-register.js.map +1 -0
- package/dist/controls/json.d.ts +2 -0
- package/dist/controls/json.js +82 -0
- package/dist/controls/json.js.map +1 -0
- package/dist/controls/link.d.ts +260 -0
- package/dist/controls/link.js +1186 -0
- package/dist/controls/link.js.map +1 -0
- package/dist/controls/location-register.d.ts +1 -0
- package/dist/controls/location-register.js +8 -0
- package/dist/controls/location-register.js.map +1 -0
- package/dist/controls/location.d.ts +16 -0
- package/dist/controls/location.js +221 -0
- package/dist/controls/location.js.map +1 -0
- package/dist/controls/media-register.d.ts +1 -0
- package/dist/controls/media-register.js +12 -0
- package/dist/controls/media-register.js.map +1 -0
- package/dist/controls/media-services.d.ts +46 -0
- package/dist/controls/media-services.js +0 -0
- package/dist/controls/media.d.ts +104 -0
- package/dist/controls/media.js +1396 -0
- package/dist/controls/media.js.map +1 -0
- package/dist/controls/number.d.ts +22 -0
- package/dist/controls/number.js +196 -0
- package/dist/controls/number.js.map +1 -0
- package/dist/controls/reference-register.d.ts +1 -0
- package/dist/controls/reference-register.js +10 -0
- package/dist/controls/reference-register.js.map +1 -0
- package/dist/controls/reference-services.d.ts +58 -0
- package/dist/controls/reference-services.js +0 -0
- package/dist/controls/reference.d.ts +23 -0
- package/dist/controls/reference.js +777 -0
- package/dist/controls/reference.js.map +1 -0
- package/dist/controls/rich-text/blocks.d.ts +49 -0
- package/dist/controls/rich-text/blocks.js +1859 -0
- package/dist/controls/rich-text/blocks.js.map +1 -0
- package/dist/controls/rich-text/catalog.d.ts +101 -0
- package/dist/controls/rich-text/catalog.js +623 -0
- package/dist/controls/rich-text/catalog.js.map +1 -0
- package/dist/controls/rich-text/codec.d.ts +64 -0
- package/dist/controls/rich-text/codec.js +34 -0
- package/dist/controls/rich-text/codec.js.map +1 -0
- package/dist/controls/rich-text/component-card.d.ts +14 -0
- package/dist/controls/rich-text/component-card.js +1024 -0
- package/dist/controls/rich-text/component-card.js.map +1 -0
- package/dist/controls/rich-text/component-panel.d.ts +47 -0
- package/dist/controls/rich-text/component-panel.js +141 -0
- package/dist/controls/rich-text/component-panel.js.map +1 -0
- package/dist/controls/rich-text/control.d.ts +20 -0
- package/dist/controls/rich-text/control.js +296 -0
- package/dist/controls/rich-text/control.js.map +1 -0
- package/dist/controls/rich-text/dom.d.ts +233 -0
- package/dist/controls/rich-text/dom.js +1019 -0
- package/dist/controls/rich-text/dom.js.map +1 -0
- package/dist/controls/rich-text/editor.d.ts +57 -0
- package/dist/controls/rich-text/editor.js +1630 -0
- package/dist/controls/rich-text/editor.js.map +1 -0
- package/dist/controls/rich-text/floating.d.ts +28 -0
- package/dist/controls/rich-text/floating.js +154 -0
- package/dist/controls/rich-text/floating.js.map +1 -0
- package/dist/controls/rich-text/index.d.ts +1 -0
- package/dist/controls/rich-text/index.js +12 -0
- package/dist/controls/rich-text/index.js.map +1 -0
- package/dist/controls/rich-text/link-form.d.ts +13 -0
- package/dist/controls/rich-text/link-form.js +147 -0
- package/dist/controls/rich-text/link-form.js.map +1 -0
- package/dist/controls/rich-text/markdown.d.ts +6 -0
- package/dist/controls/rich-text/markdown.js +181 -0
- package/dist/controls/rich-text/markdown.js.map +1 -0
- package/dist/controls/rich-text/ops.d.ts +35 -0
- package/dist/controls/rich-text/ops.js +316 -0
- package/dist/controls/rich-text/ops.js.map +1 -0
- package/dist/controls/rich-text/plain.d.ts +17 -0
- package/dist/controls/rich-text/plain.js +44 -0
- package/dist/controls/rich-text/plain.js.map +1 -0
- package/dist/controls/rich-text/toolbar.d.ts +89 -0
- package/dist/controls/rich-text/toolbar.js +343 -0
- package/dist/controls/rich-text/toolbar.js.map +1 -0
- package/dist/controls/scale.d.ts +56 -0
- package/dist/controls/scale.js +563 -0
- package/dist/controls/scale.js.map +1 -0
- package/dist/controls/slot-register.d.ts +1 -0
- package/dist/controls/slot-register.js +16 -0
- package/dist/controls/slot-register.js.map +1 -0
- package/dist/controls/slot-services.d.ts +122 -0
- package/dist/controls/slot-services.js +155 -0
- package/dist/controls/slot-services.js.map +1 -0
- package/dist/controls/slot.d.ts +33 -0
- package/dist/controls/slot.js +366 -0
- package/dist/controls/slot.js.map +1 -0
- package/dist/controls/table/index.d.ts +1 -0
- package/dist/controls/table/index.js +12 -0
- package/dist/controls/table/index.js.map +1 -0
- package/dist/controls/table/prod.d.ts +21 -0
- package/dist/controls/table/prod.js +79 -0
- package/dist/controls/table/prod.js.map +1 -0
- package/dist/controls/table/refs.d.ts +50 -0
- package/dist/controls/table/refs.js +79 -0
- package/dist/controls/table/refs.js.map +1 -0
- package/dist/controls/table/stored.d.ts +15 -0
- package/dist/controls/table/stored.js +44 -0
- package/dist/controls/table/stored.js.map +1 -0
- package/dist/controls/table/table-editor.d.ts +103 -0
- package/dist/controls/table/table-editor.js +2725 -0
- package/dist/controls/table/table-editor.js.map +1 -0
- package/dist/controls/table/table-link.d.ts +24 -0
- package/dist/controls/table/table-link.js +180 -0
- package/dist/controls/table/table-link.js.map +1 -0
- package/dist/controls/table/table.d.ts +9 -0
- package/dist/controls/table/table.js +103 -0
- package/dist/controls/table/table.js.map +1 -0
- package/dist/controls/text.d.ts +17 -0
- package/dist/controls/text.js +322 -0
- package/dist/controls/text.js.map +1 -0
- package/dist/controls/unknown-value.d.ts +17 -0
- package/dist/controls/unknown-value.js +66 -0
- package/dist/controls/unknown-value.js.map +1 -0
- package/dist/core/core.d.ts +63 -0
- package/dist/core/core.js +171 -0
- package/dist/core/core.js.map +1 -0
- package/dist/core/facets.d.ts +347 -0
- package/dist/core/facets.js +334 -0
- package/dist/core/facets.js.map +1 -0
- package/dist/core/index.d.ts +3 -0
- package/dist/core/index.js +3 -0
- package/dist/engine/array.d.ts +101 -0
- package/dist/engine/array.js +906 -0
- package/dist/engine/array.js.map +1 -0
- package/dist/engine/bits.d.ts +24 -0
- package/dist/engine/bits.js +60 -0
- package/dist/engine/bits.js.map +1 -0
- package/dist/engine/breadcrumb.d.ts +45 -0
- package/dist/engine/breadcrumb.js +63 -0
- package/dist/engine/breadcrumb.js.map +1 -0
- package/dist/engine/expand.d.ts +66 -0
- package/dist/engine/expand.js +153 -0
- package/dist/engine/expand.js.map +1 -0
- package/dist/engine/field-list.d.ts +20 -0
- package/dist/engine/field-list.js +19 -0
- package/dist/engine/field-list.js.map +1 -0
- package/dist/engine/field-shell.d.ts +49 -0
- package/dist/engine/field-shell.js +988 -0
- package/dist/engine/field-shell.js.map +1 -0
- package/dist/engine/frame.d.ts +122 -0
- package/dist/engine/frame.js +601 -0
- package/dist/engine/frame.js.map +1 -0
- package/dist/engine/group-summary.d.ts +5 -0
- package/dist/engine/group-summary.js +70 -0
- package/dist/engine/group-summary.js.map +1 -0
- package/dist/engine/grouping.d.ts +238 -0
- package/dist/engine/grouping.js +996 -0
- package/dist/engine/grouping.js.map +1 -0
- package/dist/engine/item-list.d.ts +99 -0
- package/dist/engine/item-list.js +725 -0
- package/dist/engine/item-list.js.map +1 -0
- package/dist/engine/kit-field.d.ts +72 -0
- package/dist/engine/kit-field.js +558 -0
- package/dist/engine/kit-field.js.map +1 -0
- package/dist/engine/schema-form.d.ts +116 -0
- package/dist/engine/schema-form.js +462 -0
- package/dist/engine/schema-form.js.map +1 -0
- package/dist/engine/slot.d.ts +13 -0
- package/dist/engine/slot.js +216 -0
- package/dist/engine/slot.js.map +1 -0
- package/dist/index.d.ts +45 -3139
- package/dist/index.js +47 -2036
- package/dist/index.js.map +1 -0
- package/dist/kit.css +75 -0
- package/dist/lib/cn.d.ts +4 -0
- package/dist/lib/cn.js +56 -0
- package/dist/lib/cn.js.map +1 -0
- package/dist/lib/columns.d.ts +14 -0
- package/dist/lib/columns.js +30 -0
- package/dist/lib/columns.js.map +1 -0
- package/dist/lib/frames.d.ts +36 -0
- package/dist/lib/frames.js +214 -0
- package/dist/lib/frames.js.map +1 -0
- package/dist/lib/icon-image.d.ts +10 -0
- package/dist/lib/icon-image.js +8 -0
- package/dist/lib/icon-image.js.map +1 -0
- package/dist/lib/icons.d.ts +16 -0
- package/dist/lib/icons.js +173 -0
- package/dist/lib/icons.js.map +1 -0
- package/dist/lib/input-modality.d.ts +11 -0
- package/dist/lib/input-modality.js +47 -0
- package/dist/lib/input-modality.js.map +1 -0
- package/dist/lib/key-event.d.ts +11 -0
- package/dist/lib/key-event.js +16 -0
- package/dist/lib/key-event.js.map +1 -0
- package/dist/lib/path.d.ts +29 -0
- package/dist/lib/path.js +66 -0
- package/dist/lib/path.js.map +1 -0
- package/dist/lib/schema.d.ts +80 -0
- package/dist/lib/schema.js +384 -0
- package/dist/lib/schema.js.map +1 -0
- package/dist/lib/utils.d.ts +7 -0
- package/dist/lib/utils.js +37 -0
- package/dist/lib/utils.js.map +1 -0
- package/dist/lib/validate.d.ts +30 -0
- package/dist/lib/validate.js +224 -0
- package/dist/lib/validate.js.map +1 -0
- package/dist/library/analysis.d.ts +23 -0
- package/dist/library/analysis.js +160 -0
- package/dist/library/analysis.js.map +1 -0
- package/dist/library/catalog.d.ts +57 -0
- package/dist/library/catalog.js +307 -0
- package/dist/library/catalog.js.map +1 -0
- package/dist/library/coreNotes.d.ts +8 -0
- package/dist/library/coreNotes.js +111 -0
- package/dist/library/coreNotes.js.map +1 -0
- package/dist/library/coverage.d.ts +40 -0
- package/dist/library/coverage.js +59 -0
- package/dist/library/coverage.js.map +1 -0
- package/dist/library/entries/advanced.entries.d.ts +2 -0
- package/dist/library/entries/advanced.entries.js +6579 -0
- package/dist/library/entries/advanced.entries.js.map +1 -0
- package/dist/library/entries/commerce.entries.d.ts +2 -0
- package/dist/library/entries/commerce.entries.js +4140 -0
- package/dist/library/entries/commerce.entries.js.map +1 -0
- package/dist/library/entries/company.entries.d.ts +2 -0
- package/dist/library/entries/company.entries.js +2731 -0
- package/dist/library/entries/company.entries.js.map +1 -0
- package/dist/library/entries/conversion.entries.d.ts +2 -0
- package/dist/library/entries/conversion.entries.js +3707 -0
- package/dist/library/entries/conversion.entries.js.map +1 -0
- package/dist/library/entries/data.entries.d.ts +7 -0
- package/dist/library/entries/data.entries.js +4613 -0
- package/dist/library/entries/data.entries.js.map +1 -0
- package/dist/library/entries/events.entries.d.ts +2 -0
- package/dist/library/entries/events.entries.js +3428 -0
- package/dist/library/entries/events.entries.js.map +1 -0
- package/dist/library/entries/features.entries.d.ts +2 -0
- package/dist/library/entries/features.entries.js +3157 -0
- package/dist/library/entries/features.entries.js.map +1 -0
- package/dist/library/entries/heroes.entries.d.ts +2 -0
- package/dist/library/entries/heroes.entries.js +3401 -0
- package/dist/library/entries/heroes.entries.js.map +1 -0
- package/dist/library/entries/index.d.ts +3 -0
- package/dist/library/entries/index.js +35 -0
- package/dist/library/entries/index.js.map +1 -0
- package/dist/library/entries/listings.entries.d.ts +2 -0
- package/dist/library/entries/listings.entries.js +2976 -0
- package/dist/library/entries/listings.entries.js.map +1 -0
- package/dist/library/entries/longform.entries.d.ts +2 -0
- package/dist/library/entries/longform.entries.js +4227 -0
- package/dist/library/entries/longform.entries.js.map +1 -0
- package/dist/library/entries/media.entries.d.ts +2 -0
- package/dist/library/entries/media.entries.js +2781 -0
- package/dist/library/entries/media.entries.js.map +1 -0
- package/dist/library/entries/navigation.entries.d.ts +2 -0
- package/dist/library/entries/navigation.entries.js +4011 -0
- package/dist/library/entries/navigation.entries.js.map +1 -0
- package/dist/library/entries/pricing.entries.d.ts +2 -0
- package/dist/library/entries/pricing.entries.js +2383 -0
- package/dist/library/entries/pricing.entries.js.map +1 -0
- package/dist/library/entries/social-proof.entries.d.ts +2 -0
- package/dist/library/entries/social-proof.entries.js +2297 -0
- package/dist/library/entries/social-proof.entries.js.map +1 -0
- package/dist/library/examples/bento.d.ts +92 -0
- package/dist/library/examples/bento.js +201 -0
- package/dist/library/examples/bento.js.map +1 -0
- package/dist/library/examples/blocks.d.ts +14 -0
- package/dist/library/examples/blocks.js +313 -0
- package/dist/library/examples/blocks.js.map +1 -0
- package/dist/library/examples/faq.d.ts +28 -0
- package/dist/library/examples/faq.js +230 -0
- package/dist/library/examples/faq.js.map +1 -0
- package/dist/library/examples/hero.d.ts +43 -0
- package/dist/library/examples/hero.js +222 -0
- package/dist/library/examples/hero.js.map +1 -0
- package/dist/library/examples/index.d.ts +36 -0
- package/dist/library/examples/index.js +109 -0
- package/dist/library/examples/index.js.map +1 -0
- package/dist/library/examples/journalStory.d.ts +93 -0
- package/dist/library/examples/journalStory.js +338 -0
- package/dist/library/examples/journalStory.js.map +1 -0
- package/dist/library/examples/megaMenu.d.ts +134 -0
- package/dist/library/examples/megaMenu.js +442 -0
- package/dist/library/examples/megaMenu.js.map +1 -0
- package/dist/library/examples/pricing.d.ts +103 -0
- package/dist/library/examples/pricing.js +479 -0
- package/dist/library/examples/pricing.js.map +1 -0
- package/dist/library/examples/tabs.d.ts +87 -0
- package/dist/library/examples/tabs.js +180 -0
- package/dist/library/examples/tabs.js.map +1 -0
- package/dist/library/export.d.ts +42 -0
- package/dist/library/export.js +80 -0
- package/dist/library/export.js.map +1 -0
- package/dist/library/index.d.ts +13 -0
- package/dist/library/index.js +6 -0
- package/dist/library/kit-catalog.json +1510 -0
- package/dist/library/types.d.ts +42 -0
- package/dist/library/types.js +0 -0
- package/dist/schema/adapters.d.ts +28 -0
- package/dist/schema/adapters.js +492 -0
- package/dist/schema/adapters.js.map +1 -0
- package/dist/schema/help.d.ts +27 -0
- package/dist/schema/help.js +56 -0
- package/dist/schema/help.js.map +1 -0
- package/dist/schema/scale.d.ts +69 -0
- package/dist/schema/scale.js +250 -0
- package/dist/schema/scale.js.map +1 -0
- package/dist/schema/sources.d.ts +103 -0
- package/dist/schema/sources.js +65 -0
- package/dist/schema/sources.js.map +1 -0
- package/dist/schema/table.d.ts +319 -0
- package/dist/schema/table.js +1199 -0
- package/dist/schema/table.js.map +1 -0
- package/dist/schema/types.d.ts +297 -0
- package/dist/schema/types.js +14 -0
- package/dist/schema/types.js.map +1 -0
- package/dist/styles.css +2 -0
- package/dist/table/table-view.d.ts +14 -0
- package/dist/table/table-view.js +140 -0
- package/dist/table/table-view.js.map +1 -0
- package/dist/table/table.css +73 -0
- package/dist/testing/corpus.d.ts +63 -0
- package/dist/testing/corpus.js +129 -0
- package/dist/testing/corpus.js.map +1 -0
- package/dist/testing/test-form.d.ts +11 -0
- package/dist/testing/test-form.js +38 -0
- package/dist/testing/test-form.js.map +1 -0
- package/dist/theme.css +345 -0
- package/dist/theme.d.ts +20 -1504
- package/dist/theme.js +43 -4126
- package/dist/theme.js.map +1 -0
- package/dist/tokens.css +542 -0
- package/dist/types.d.ts +17 -0
- package/dist/types.js +0 -0
- package/dist/ui/action-tray.d.ts +54 -0
- package/dist/ui/action-tray.js +154 -0
- package/dist/ui/action-tray.js.map +1 -0
- package/dist/ui/autocomplete.d.ts +30 -0
- package/dist/ui/autocomplete.js +139 -0
- package/dist/ui/autocomplete.js.map +1 -0
- package/dist/ui/button.d.ts +57 -0
- package/dist/ui/button.js +201 -0
- package/dist/ui/button.js.map +1 -0
- package/dist/ui/choice-switch.d.ts +36 -0
- package/dist/ui/choice-switch.js +57 -0
- package/dist/ui/choice-switch.js.map +1 -0
- package/dist/ui/controls.d.ts +83 -0
- package/dist/ui/controls.js +331 -0
- package/dist/ui/controls.js.map +1 -0
- package/dist/ui/display.d.ts +163 -0
- package/dist/ui/display.js +455 -0
- package/dist/ui/display.js.map +1 -0
- package/dist/ui/expanded-editor-modal.d.ts +26 -0
- package/dist/ui/expanded-editor-modal.js +140 -0
- package/dist/ui/expanded-editor-modal.js.map +1 -0
- package/dist/ui/field-context.d.ts +12 -0
- package/dist/ui/field-context.js +23 -0
- package/dist/ui/field-context.js.map +1 -0
- package/dist/ui/floating-panel.d.ts +152 -0
- package/dist/ui/floating-panel.js +928 -0
- package/dist/ui/floating-panel.js.map +1 -0
- package/dist/ui/index.d.ts +16 -0
- package/dist/ui/index.js +18 -0
- package/dist/ui/input.d.ts +78 -0
- package/dist/ui/input.js +250 -0
- package/dist/ui/input.js.map +1 -0
- package/dist/ui/mode-bar.d.ts +31 -0
- package/dist/ui/mode-bar.js +65 -0
- package/dist/ui/mode-bar.js.map +1 -0
- package/dist/ui/overlay.d.ts +195 -0
- package/dist/ui/overlay.js +697 -0
- package/dist/ui/overlay.js.map +1 -0
- package/dist/ui/path-crumbs.d.ts +90 -0
- package/dist/ui/path-crumbs.js +566 -0
- package/dist/ui/path-crumbs.js.map +1 -0
- package/dist/ui/presence.d.ts +16 -0
- package/dist/ui/presence.js +65 -0
- package/dist/ui/presence.js.map +1 -0
- package/dist/ui/select.d.ts +66 -0
- package/dist/ui/select.js +407 -0
- package/dist/ui/select.js.map +1 -0
- package/dist/ui/shortcut-hint.d.ts +14 -0
- package/dist/ui/shortcut-hint.js +35 -0
- package/dist/ui/shortcut-hint.js.map +1 -0
- package/dist/ui/spinner.d.ts +24 -0
- package/dist/ui/spinner.js +42 -0
- package/dist/ui/spinner.js.map +1 -0
- package/dist/ui/split-button.d.ts +32 -0
- package/dist/ui/split-button.js +60 -0
- package/dist/ui/split-button.js.map +1 -0
- package/dist/ui/surfaces.d.ts +23 -0
- package/dist/ui/surfaces.js +26 -0
- package/dist/ui/surfaces.js.map +1 -0
- package/dist/ui/tab.d.ts +38 -0
- package/dist/ui/tab.js +87 -0
- package/dist/ui/tab.js.map +1 -0
- package/dist/ui/toast.d.ts +20 -0
- package/dist/ui/toast.js +115 -0
- package/dist/ui/toast.js.map +1 -0
- package/dist/ui/tooltip-root.d.ts +13 -0
- package/dist/ui/tooltip-root.js +77 -0
- package/dist/ui/tooltip-root.js.map +1 -0
- package/dist/ui/variants.d.ts +15 -0
- package/dist/ui/variants.js +14 -0
- package/dist/ui/variants.js.map +1 -0
- package/package.json +76 -50
- package/LICENSE +0 -21
- package/dist/_chunks-cjs/_visual-editing.js +0 -5898
- package/dist/_chunks-cjs/refractor.js +0 -22
- package/dist/_chunks-es/_visual-editing.mjs +0 -5904
- package/dist/_chunks-es/refractor.mjs +0 -25
- package/dist/_color.d.mts +0 -119
- package/dist/_color.d.ts +0 -119
- package/dist/_color.js +0 -1412
- package/dist/_color.mjs +0 -1411
- package/dist/_visual-editing.d.mts +0 -1126
- package/dist/_visual-editing.d.ts +0 -1126
- package/dist/_visual-editing.js +0 -30
- package/dist/_visual-editing.mjs +0 -30
- package/dist/index.d.mts +0 -3140
- package/dist/index.mjs +0 -2044
- package/dist/theme.d.mts +0 -1506
- package/dist/theme.mjs +0 -4126
- package/exports/_visual-editing.ts +0 -31
- package/exports/index.ts +0 -1
- package/exports/theme.ts +0 -1
- package/src/color/index.d.mts +0 -119
- package/src/color/index.mjs +0 -1411
- package/src/core/__workshop__/constants.ts +0 -293
- package/src/core/_compat.ts +0 -264
- package/src/core/components/autocomplete/__mocks__/apiStore.ts +0 -49
- package/src/core/components/autocomplete/__mocks__/countries.ts +0 -245
- package/src/core/components/autocomplete/__workshop__/async.tsx +0 -156
- package/src/core/components/autocomplete/__workshop__/constrainedHeight.tsx +0 -137
- package/src/core/components/autocomplete/__workshop__/custom.tsx +0 -89
- package/src/core/components/autocomplete/__workshop__/example.tsx +0 -79
- package/src/core/components/autocomplete/__workshop__/focusAndBlur.tsx +0 -36
- package/src/core/components/autocomplete/__workshop__/fullscreen.tsx +0 -294
- package/src/core/components/autocomplete/__workshop__/index.ts +0 -39
- package/src/core/components/autocomplete/__workshop__/types.ts +0 -4
- package/src/core/components/autocomplete/autocomplete.styles.tsx +0 -39
- package/src/core/components/autocomplete/autocomplete.tsx +0 -767
- package/src/core/components/autocomplete/autocompleteOption.tsx +0 -45
- package/src/core/components/autocomplete/autocompleteReducer.ts +0 -47
- package/src/core/components/autocomplete/constants.ts +0 -28
- package/src/core/components/autocomplete/index.ts +0 -2
- package/src/core/components/autocomplete/types.ts +0 -108
- package/src/core/components/breadcrumbs/__workshop__/example.tsx +0 -62
- package/src/core/components/breadcrumbs/__workshop__/index.ts +0 -14
- package/src/core/components/breadcrumbs/breadcrumbs.styles.ts +0 -18
- package/src/core/components/breadcrumbs/breadcrumbs.test.tsx +0 -51
- package/src/core/components/breadcrumbs/breadcrumbs.tsx +0 -133
- package/src/core/components/breadcrumbs/index.ts +0 -1
- package/src/core/components/dialog/__workshop__/activate.tsx +0 -134
- package/src/core/components/dialog/__workshop__/autoFocus.tsx +0 -29
- package/src/core/components/dialog/__workshop__/index.ts +0 -19
- package/src/core/components/dialog/__workshop__/layering.tsx +0 -41
- package/src/core/components/dialog/__workshop__/nested.tsx +0 -72
- package/src/core/components/dialog/__workshop__/onScroll.tsx +0 -39
- package/src/core/components/dialog/__workshop__/panes.tsx +0 -82
- package/src/core/components/dialog/__workshop__/position.tsx +0 -30
- package/src/core/components/dialog/__workshop__/props.tsx +0 -75
- package/src/core/components/dialog/__workshop__/provider.tsx +0 -11
- package/src/core/components/dialog/__workshop__/wrapped.tsx +0 -76
- package/src/core/components/dialog/dialog.tsx +0 -430
- package/src/core/components/dialog/dialogContext.ts +0 -20
- package/src/core/components/dialog/dialogProvider.tsx +0 -35
- package/src/core/components/dialog/index.ts +0 -4
- package/src/core/components/dialog/styles.ts +0 -77
- package/src/core/components/dialog/useDialog.ts +0 -11
- package/src/core/components/hotkeys/__workshop__/index.ts +0 -14
- package/src/core/components/hotkeys/__workshop__/plain.tsx +0 -9
- package/src/core/components/hotkeys/hotkeys.test.tsx +0 -42
- package/src/core/components/hotkeys/hotkeys.tsx +0 -66
- package/src/core/components/hotkeys/index.ts +0 -1
- package/src/core/components/index.ts +0 -9
- package/src/core/components/menu/__workshop__/asComponent.tsx +0 -45
- package/src/core/components/menu/__workshop__/avatarMenu.tsx +0 -51
- package/src/core/components/menu/__workshop__/closableMenuButton.tsx +0 -46
- package/src/core/components/menu/__workshop__/constrainedInBoundary.tsx +0 -134
- package/src/core/components/menu/__workshop__/customMenuItem.tsx +0 -45
- package/src/core/components/menu/__workshop__/customSelectedState.tsx +0 -39
- package/src/core/components/menu/__workshop__/disableFocusOnClose.tsx +0 -40
- package/src/core/components/menu/__workshop__/groups.tsx +0 -156
- package/src/core/components/menu/__workshop__/index.ts +0 -89
- package/src/core/components/menu/__workshop__/menuButton.tsx +0 -80
- package/src/core/components/menu/__workshop__/menuGroupRight.tsx +0 -58
- package/src/core/components/menu/__workshop__/nestedMenu.tsx +0 -22
- package/src/core/components/menu/__workshop__/onCloseMenuButton.tsx +0 -41
- package/src/core/components/menu/__workshop__/selectedItem.tsx +0 -69
- package/src/core/components/menu/__workshop__/shouldFocus.tsx +0 -47
- package/src/core/components/menu/__workshop__/tones.tsx +0 -25
- package/src/core/components/menu/__workshop__/withoutArrow.tsx +0 -32
- package/src/core/components/menu/helpers.ts +0 -82
- package/src/core/components/menu/index.ts +0 -5
- package/src/core/components/menu/menu.spacing.test.tsx +0 -63
- package/src/core/components/menu/menu.test.tsx +0 -125
- package/src/core/components/menu/menu.tsx +0 -178
- package/src/core/components/menu/menuButton.tsx +0 -268
- package/src/core/components/menu/menuContext.ts +0 -18
- package/src/core/components/menu/menuDivider.ts +0 -23
- package/src/core/components/menu/menuGroup.spacing.test.tsx +0 -63
- package/src/core/components/menu/menuGroup.tsx +0 -233
- package/src/core/components/menu/menuItem.spacing.test.tsx +0 -59
- package/src/core/components/menu/menuItem.tsx +0 -197
- package/src/core/components/menu/useMenu.ts +0 -21
- package/src/core/components/menu/useMenuController.ts +0 -231
- package/src/core/components/skeleton/__workshop__/delay.tsx +0 -70
- package/src/core/components/skeleton/__workshop__/index.ts +0 -11
- package/src/core/components/skeleton/__workshop__/skeleton.tsx +0 -64
- package/src/core/components/skeleton/index.ts +0 -2
- package/src/core/components/skeleton/skeleton.tsx +0 -57
- package/src/core/components/skeleton/styles.ts +0 -50
- package/src/core/components/skeleton/textSkeleton.tsx +0 -122
- package/src/core/components/tab/__workshop__/example.tsx +0 -79
- package/src/core/components/tab/__workshop__/index.ts +0 -14
- package/src/core/components/tab/index.ts +0 -3
- package/src/core/components/tab/tab.tsx +0 -101
- package/src/core/components/tab/tabList.test.tsx +0 -48
- package/src/core/components/tab/tabList.tsx +0 -70
- package/src/core/components/tab/tabPanel.tsx +0 -39
- package/src/core/components/toast/__workshop__/hook.tsx +0 -71
- package/src/core/components/toast/__workshop__/index.ts +0 -19
- package/src/core/components/toast/__workshop__/toast.tsx +0 -26
- package/src/core/components/toast/index.ts +0 -4
- package/src/core/components/toast/styles.ts +0 -77
- package/src/core/components/toast/toast.test.tsx +0 -101
- package/src/core/components/toast/toast.tsx +0 -198
- package/src/core/components/toast/toastContext.ts +0 -7
- package/src/core/components/toast/toastLayer.tsx +0 -51
- package/src/core/components/toast/toastProvider.tsx +0 -113
- package/src/core/components/toast/toastState.ts +0 -6
- package/src/core/components/toast/types.ts +0 -26
- package/src/core/components/toast/useToast.ts +0 -25
- package/src/core/components/tree/__workshop__/basic.perf.ts +0 -19
- package/src/core/components/tree/__workshop__/basic.tsx +0 -105
- package/src/core/components/tree/__workshop__/index.ts +0 -21
- package/src/core/components/tree/__workshop__/tabFromElement.tsx +0 -84
- package/src/core/components/tree/helpers.ts +0 -105
- package/src/core/components/tree/index.ts +0 -4
- package/src/core/components/tree/style.ts +0 -105
- package/src/core/components/tree/tree.test.tsx +0 -55
- package/src/core/components/tree/tree.tsx +0 -240
- package/src/core/components/tree/treeContext.ts +0 -10
- package/src/core/components/tree/treeGroup.tsx +0 -28
- package/src/core/components/tree/treeItem.test.tsx +0 -65
- package/src/core/components/tree/treeItem.tsx +0 -224
- package/src/core/components/tree/types.ts +0 -25
- package/src/core/components/tree/useTree.ts +0 -17
- package/src/core/constants.ts +0 -79
- package/src/core/helpers/animation.ts +0 -27
- package/src/core/helpers/element.ts +0 -55
- package/src/core/helpers/focus.ts +0 -100
- package/src/core/helpers/index.ts +0 -4
- package/src/core/helpers/scroll.ts +0 -15
- package/src/core/hooks/index.ts +0 -12
- package/src/core/hooks/useArrayProp.ts +0 -17
- package/src/core/hooks/useClickOutside.test.tsx +0 -482
- package/src/core/hooks/useClickOutside.ts +0 -118
- package/src/core/hooks/useClickOutsideEvent.test.tsx +0 -115
- package/src/core/hooks/useClickOutsideEvent.ts +0 -73
- package/src/core/hooks/useCustomValidity.ts +0 -13
- package/src/core/hooks/useDelayed.test.ts +0 -88
- package/src/core/hooks/useDelayedState.ts +0 -36
- package/src/core/hooks/useElementRect/__workshop__/example.tsx +0 -32
- package/src/core/hooks/useElementRect/__workshop__/index.ts +0 -14
- package/src/core/hooks/useElementRect/index.ts +0 -1
- package/src/core/hooks/useElementRect/useElementRect.ts +0 -13
- package/src/core/hooks/useElementSize.ts +0 -19
- package/src/core/hooks/useForwardedRef.ts +0 -19
- package/src/core/hooks/useGlobalKeyDown.ts +0 -24
- package/src/core/hooks/useIsomorphicEffect.ts +0 -7
- package/src/core/hooks/useMatchMedia.ts +0 -28
- package/src/core/hooks/useMediaIndex/__workshop__/index.ts +0 -14
- package/src/core/hooks/useMediaIndex/__workshop__/test.tsx +0 -14
- package/src/core/hooks/useMediaIndex/index.ts +0 -1
- package/src/core/hooks/useMediaIndex/useMediaIndex.test.tsx +0 -36
- package/src/core/hooks/useMediaIndex/useMediaIndex.ts +0 -102
- package/src/core/hooks/useMounted.ts +0 -15
- package/src/core/hooks/usePrefersDark.hydration.test.tsx +0 -56
- package/src/core/hooks/usePrefersDark.test.tsx +0 -19
- package/src/core/hooks/usePrefersDark.ts +0 -16
- package/src/core/hooks/usePrefersReducedMotion.hydration.test.tsx +0 -56
- package/src/core/hooks/usePrefersReducedMotion.test.tsx +0 -19
- package/src/core/hooks/usePrefersReducedMotion.ts +0 -16
- package/src/core/index.ts +0 -10
- package/src/core/lib/createGlobalScopedContext.ts +0 -36
- package/src/core/lib/globalScope.ts +0 -19
- package/src/core/lib/isRecord.ts +0 -3
- package/src/core/middleware/origin.ts +0 -47
- package/src/core/observers/elementSizeObserver.ts +0 -116
- package/src/core/observers/index.ts +0 -2
- package/src/core/observers/resizeObserver.ts +0 -9
- package/src/core/primitives/_selectable/index.ts +0 -1
- package/src/core/primitives/_selectable/selectable.tsx +0 -15
- package/src/core/primitives/_selectable/style.ts +0 -115
- package/src/core/primitives/avatar/__workshop__/asButton.tsx +0 -14
- package/src/core/primitives/avatar/__workshop__/index.ts +0 -29
- package/src/core/primitives/avatar/__workshop__/stack.tsx +0 -25
- package/src/core/primitives/avatar/__workshop__/withinButton.tsx +0 -63
- package/src/core/primitives/avatar/__workshop__/withinMenuItem.tsx +0 -70
- package/src/core/primitives/avatar/avatar.tsx +0 -200
- package/src/core/primitives/avatar/avatarCounter.tsx +0 -91
- package/src/core/primitives/avatar/avatarStack.tsx +0 -100
- package/src/core/primitives/avatar/index.ts +0 -4
- package/src/core/primitives/avatar/styles.ts +0 -167
- package/src/core/primitives/avatar/types.ts +0 -17
- package/src/core/primitives/badge/__workshop__/index.ts +0 -19
- package/src/core/primitives/badge/__workshop__/props.tsx +0 -30
- package/src/core/primitives/badge/__workshop__/tones.tsx +0 -21
- package/src/core/primitives/badge/badge.test.tsx +0 -16
- package/src/core/primitives/badge/badge.tsx +0 -70
- package/src/core/primitives/badge/index.ts +0 -1
- package/src/core/primitives/badge/styles.ts +0 -20
- package/src/core/primitives/badge/types.ts +0 -8
- package/src/core/primitives/box/__workshop__/asComponent.tsx +0 -31
- package/src/core/primitives/box/__workshop__/index.ts +0 -24
- package/src/core/primitives/box/__workshop__/props.tsx +0 -20
- package/src/core/primitives/box/__workshop__/responsive.tsx +0 -20
- package/src/core/primitives/box/box.test.tsx +0 -142
- package/src/core/primitives/box/box.tsx +0 -154
- package/src/core/primitives/box/index.ts +0 -1
- package/src/core/primitives/button/__workshop__/custom.tsx +0 -51
- package/src/core/primitives/button/__workshop__/customIcons.tsx +0 -30
- package/src/core/primitives/button/__workshop__/disabled.tsx +0 -74
- package/src/core/primitives/button/__workshop__/index.ts +0 -59
- package/src/core/primitives/button/__workshop__/labelUploadButton.tsx +0 -36
- package/src/core/primitives/button/__workshop__/mixedChildren.tsx +0 -12
- package/src/core/primitives/button/__workshop__/props.tsx +0 -55
- package/src/core/primitives/button/__workshop__/stacked.tsx +0 -58
- package/src/core/primitives/button/__workshop__/styled1.tsx +0 -17
- package/src/core/primitives/button/__workshop__/styled2.tsx +0 -19
- package/src/core/primitives/button/__workshop__/uploadButton.tsx +0 -28
- package/src/core/primitives/button/button.test.tsx +0 -82
- package/src/core/primitives/button/button.tsx +0 -210
- package/src/core/primitives/button/index.ts +0 -1
- package/src/core/primitives/button/styles.ts +0 -117
- package/src/core/primitives/card/__workshop__/allTones.tsx +0 -25
- package/src/core/primitives/card/__workshop__/asButton.tsx +0 -107
- package/src/core/primitives/card/__workshop__/asComponent.tsx +0 -27
- package/src/core/primitives/card/__workshop__/checkered.tsx +0 -26
- package/src/core/primitives/card/__workshop__/index.ts +0 -18
- package/src/core/primitives/card/__workshop__/interactive.tsx +0 -30
- package/src/core/primitives/card/__workshop__/listNavigation.tsx +0 -80
- package/src/core/primitives/card/__workshop__/props.tsx +0 -53
- package/src/core/primitives/card/__workshop__/selected.tsx +0 -94
- package/src/core/primitives/card/__workshop__/styled.tsx +0 -14
- package/src/core/primitives/card/card.tsx +0 -128
- package/src/core/primitives/card/index.ts +0 -2
- package/src/core/primitives/card/styles.ts +0 -147
- package/src/core/primitives/card/types.ts +0 -11
- package/src/core/primitives/checkbox/__workshop__/example.tsx +0 -25
- package/src/core/primitives/checkbox/__workshop__/index.ts +0 -13
- package/src/core/primitives/checkbox/__workshop__/props.tsx +0 -33
- package/src/core/primitives/checkbox/__workshop__/readOnly.tsx +0 -16
- package/src/core/primitives/checkbox/__workshop__/tones.tsx +0 -28
- package/src/core/primitives/checkbox/checkbox.tsx +0 -73
- package/src/core/primitives/checkbox/index.ts +0 -1
- package/src/core/primitives/checkbox/styles.ts +0 -128
- package/src/core/primitives/code/__workshop__/index.ts +0 -19
- package/src/core/primitives/code/__workshop__/opticalAlignment.tsx +0 -48
- package/src/core/primitives/code/__workshop__/props.tsx +0 -21
- package/src/core/primitives/code/code.tsx +0 -55
- package/src/core/primitives/code/index.ts +0 -1
- package/src/core/primitives/code/refractor.tsx +0 -20
- package/src/core/primitives/code/styles.ts +0 -77
- package/src/core/primitives/container/__workshop__/example.tsx +0 -20
- package/src/core/primitives/container/__workshop__/index.ts +0 -8
- package/src/core/primitives/container/container.tsx +0 -54
- package/src/core/primitives/container/index.ts +0 -2
- package/src/core/primitives/container/styles.ts +0 -23
- package/src/core/primitives/container/types.ts +0 -6
- package/src/core/primitives/flex/__workshop__/example.tsx +0 -34
- package/src/core/primitives/flex/__workshop__/gap.tsx +0 -25
- package/src/core/primitives/flex/__workshop__/index.ts +0 -11
- package/src/core/primitives/flex/flex.tsx +0 -64
- package/src/core/primitives/flex/index.ts +0 -1
- package/src/core/primitives/grid/__workshop__/index.ts +0 -10
- package/src/core/primitives/grid/__workshop__/responsive.tsx +0 -54
- package/src/core/primitives/grid/grid.test.tsx +0 -80
- package/src/core/primitives/grid/grid.tsx +0 -74
- package/src/core/primitives/grid/index.ts +0 -1
- package/src/core/primitives/heading/__workshop__/index.ts +0 -19
- package/src/core/primitives/heading/__workshop__/opticalAlignment.tsx +0 -54
- package/src/core/primitives/heading/__workshop__/plain.tsx +0 -32
- package/src/core/primitives/heading/heading.tsx +0 -88
- package/src/core/primitives/heading/index.ts +0 -1
- package/src/core/primitives/heading/styles.ts +0 -64
- package/src/core/primitives/heading/types.ts +0 -7
- package/src/core/primitives/index.ts +0 -27
- package/src/core/primitives/inline/__workshop__/index.ts +0 -8
- package/src/core/primitives/inline/__workshop__/plain.tsx +0 -27
- package/src/core/primitives/inline/index.ts +0 -1
- package/src/core/primitives/inline/inline.test.tsx +0 -51
- package/src/core/primitives/inline/inline.tsx +0 -63
- package/src/core/primitives/inline/styles.ts +0 -32
- package/src/core/primitives/inline/types.ts +0 -6
- package/src/core/primitives/kbd/__workshop__/index.ts +0 -8
- package/src/core/primitives/kbd/__workshop__/plain.tsx +0 -9
- package/src/core/primitives/kbd/index.ts +0 -1
- package/src/core/primitives/kbd/kbd.tsx +0 -69
- package/src/core/primitives/label/__workshop__/index.ts +0 -19
- package/src/core/primitives/label/__workshop__/opticalAlignment.tsx +0 -48
- package/src/core/primitives/label/__workshop__/plain.tsx +0 -24
- package/src/core/primitives/label/index.ts +0 -1
- package/src/core/primitives/label/label.tsx +0 -87
- package/src/core/primitives/label/styles.ts +0 -45
- package/src/core/primitives/popover/__workshop__/AlignedStory.tsx +0 -77
- package/src/core/primitives/popover/__workshop__/MarginsStory.tsx +0 -31
- package/src/core/primitives/popover/__workshop__/MatchReferenceWidthStory.tsx +0 -32
- package/src/core/primitives/popover/__workshop__/OpenOnMountStory.tsx +0 -11
- package/src/core/primitives/popover/__workshop__/PlainStory.tsx +0 -71
- package/src/core/primitives/popover/__workshop__/RecursiveStory.tsx +0 -71
- package/src/core/primitives/popover/__workshop__/SidePanelStory.tsx +0 -89
- package/src/core/primitives/popover/__workshop__/TestStory.tsx +0 -97
- package/src/core/primitives/popover/__workshop__/index.ts +0 -49
- package/src/core/primitives/popover/constants.ts +0 -22
- package/src/core/primitives/popover/floating-ui/size.ts +0 -99
- package/src/core/primitives/popover/helpers.ts +0 -31
- package/src/core/primitives/popover/index.ts +0 -2
- package/src/core/primitives/popover/popover.tsx +0 -511
- package/src/core/primitives/popover/popoverCard.tsx +0 -166
- package/src/core/primitives/popover/types.ts +0 -7
- package/src/core/primitives/radio/__workshop__/example.tsx +0 -63
- package/src/core/primitives/radio/__workshop__/index.ts +0 -11
- package/src/core/primitives/radio/__workshop__/plain.tsx +0 -28
- package/src/core/primitives/radio/index.ts +0 -1
- package/src/core/primitives/radio/radio.tsx +0 -51
- package/src/core/primitives/radio/styles.ts +0 -117
- package/src/core/primitives/select/__workshop__/index.ts +0 -11
- package/src/core/primitives/select/__workshop__/plain.tsx +0 -27
- package/src/core/primitives/select/__workshop__/readOnly.tsx +0 -23
- package/src/core/primitives/select/index.ts +0 -1
- package/src/core/primitives/select/select.test.tsx +0 -52
- package/src/core/primitives/select/select.tsx +0 -94
- package/src/core/primitives/select/styles.ts +0 -166
- package/src/core/primitives/spinner/__workshop__/Props.tsx +0 -15
- package/src/core/primitives/spinner/__workshop__/index.ts +0 -14
- package/src/core/primitives/spinner/index.ts +0 -1
- package/src/core/primitives/spinner/spinner.tsx +0 -46
- package/src/core/primitives/stack/__workshop__/index.ts +0 -14
- package/src/core/primitives/stack/__workshop__/plain.tsx +0 -32
- package/src/core/primitives/stack/index.ts +0 -1
- package/src/core/primitives/stack/stack.test.tsx +0 -57
- package/src/core/primitives/stack/stack.tsx +0 -57
- package/src/core/primitives/stack/styles.ts +0 -32
- package/src/core/primitives/switch/__workshop__/example.tsx +0 -23
- package/src/core/primitives/switch/__workshop__/index.ts +0 -11
- package/src/core/primitives/switch/__workshop__/props.tsx +0 -21
- package/src/core/primitives/switch/index.ts +0 -1
- package/src/core/primitives/switch/styles.ts +0 -173
- package/src/core/primitives/switch/switch.tsx +0 -68
- package/src/core/primitives/text/__workshop__/colored.tsx +0 -30
- package/src/core/primitives/text/__workshop__/example.tsx +0 -39
- package/src/core/primitives/text/__workshop__/index.ts +0 -24
- package/src/core/primitives/text/__workshop__/opticalAlignment.tsx +0 -48
- package/src/core/primitives/text/index.ts +0 -1
- package/src/core/primitives/text/styles.ts +0 -74
- package/src/core/primitives/text/text.tsx +0 -89
- package/src/core/primitives/textArea/__workshop__/index.ts +0 -14
- package/src/core/primitives/textArea/__workshop__/plain.tsx +0 -50
- package/src/core/primitives/textArea/index.ts +0 -1
- package/src/core/primitives/textArea/textArea.tsx +0 -120
- package/src/core/primitives/textInput/__workshop__/clearButton.tsx +0 -30
- package/src/core/primitives/textInput/__workshop__/customValidity.tsx +0 -17
- package/src/core/primitives/textInput/__workshop__/index.ts +0 -44
- package/src/core/primitives/textInput/__workshop__/plain.tsx +0 -98
- package/src/core/primitives/textInput/__workshop__/readOnly.tsx +0 -9
- package/src/core/primitives/textInput/__workshop__/states.tsx +0 -53
- package/src/core/primitives/textInput/__workshop__/tones.tsx +0 -277
- package/src/core/primitives/textInput/__workshop__/typed.tsx +0 -23
- package/src/core/primitives/textInput/index.ts +0 -1
- package/src/core/primitives/textInput/textInput.test.tsx +0 -48
- package/src/core/primitives/textInput/textInput.tsx +0 -395
- package/src/core/primitives/tooltip/__workshop__/customPortal.tsx +0 -102
- package/src/core/primitives/tooltip/__workshop__/index.ts +0 -29
- package/src/core/primitives/tooltip/__workshop__/overflowingBoundary.tsx +0 -74
- package/src/core/primitives/tooltip/__workshop__/props.tsx +0 -107
- package/src/core/primitives/tooltip/__workshop__/resizableBoundary.tsx +0 -86
- package/src/core/primitives/tooltip/constants.ts +0 -23
- package/src/core/primitives/tooltip/index.ts +0 -2
- package/src/core/primitives/tooltip/tooltip.test.tsx +0 -452
- package/src/core/primitives/tooltip/tooltip.tsx +0 -495
- package/src/core/primitives/tooltip/tooltipCard.tsx +0 -109
- package/src/core/primitives/tooltip/tooltipDelayGroup/index.ts +0 -4
- package/src/core/primitives/tooltip/tooltipDelayGroup/tooltipDelayGroupContext.tsx +0 -11
- package/src/core/primitives/tooltip/tooltipDelayGroup/tooltipDelayGroupProvider.tsx +0 -57
- package/src/core/primitives/tooltip/tooltipDelayGroup/types.ts +0 -10
- package/src/core/primitives/tooltip/tooltipDelayGroup/useTooltipDelayGroup.ts +0 -13
- package/src/core/primitives/types.ts +0 -179
- package/src/core/styles/border/borderStyle.ts +0 -56
- package/src/core/styles/border/index.ts +0 -2
- package/src/core/styles/border/types.ts +0 -10
- package/src/core/styles/box/boxStyle.ts +0 -69
- package/src/core/styles/box/index.ts +0 -2
- package/src/core/styles/box/types.ts +0 -11
- package/src/core/styles/card/_cardColorStyle.ts +0 -108
- package/src/core/styles/card/index.ts +0 -1
- package/src/core/styles/flex/flexItemStyle.ts +0 -27
- package/src/core/styles/flex/flexStyle.ts +0 -70
- package/src/core/styles/flex/index.ts +0 -3
- package/src/core/styles/flex/types.ts +0 -25
- package/src/core/styles/focusRing/index.ts +0 -25
- package/src/core/styles/font/codeFontStyle.ts +0 -13
- package/src/core/styles/font/headingFontStyle.ts +0 -13
- package/src/core/styles/font/index.ts +0 -6
- package/src/core/styles/font/labelFontStyle.ts +0 -13
- package/src/core/styles/font/responsiveFont.ts +0 -103
- package/src/core/styles/font/textAlignStyle.ts +0 -19
- package/src/core/styles/font/textFontStyle.ts +0 -13
- package/src/core/styles/font/types.ts +0 -35
- package/src/core/styles/grid/gridItemStyle.ts +0 -82
- package/src/core/styles/grid/gridStyle.ts +0 -108
- package/src/core/styles/grid/index.ts +0 -3
- package/src/core/styles/grid/types.ts +0 -37
- package/src/core/styles/helpers.ts +0 -72
- package/src/core/styles/index.ts +0 -5
- package/src/core/styles/input/index.ts +0 -2
- package/src/core/styles/input/responsiveInputPaddingStyle.ts +0 -78
- package/src/core/styles/input/textInputStyle.ts +0 -263
- package/src/core/styles/internal.ts +0 -12
- package/src/core/styles/margin/index.ts +0 -2
- package/src/core/styles/margin/marginStyle.ts +0 -21
- package/src/core/styles/margin/marginsStyle.test.ts +0 -33
- package/src/core/styles/margin/types.ts +0 -9
- package/src/core/styles/padding/index.ts +0 -2
- package/src/core/styles/padding/paddingStyle.test.ts +0 -33
- package/src/core/styles/padding/paddingStyle.ts +0 -21
- package/src/core/styles/padding/types.ts +0 -12
- package/src/core/styles/radius/index.ts +0 -2
- package/src/core/styles/radius/radiusStyle.ts +0 -23
- package/src/core/styles/radius/types.ts +0 -8
- package/src/core/styles/shadow/index.ts +0 -2
- package/src/core/styles/shadow/shadowStyle.ts +0 -29
- package/src/core/styles/shadow/types.ts +0 -6
- package/src/core/styles/types.ts +0 -8
- package/src/core/theme/__workshop__/build/Root.tsx +0 -367
- package/src/core/theme/__workshop__/build/helpers.ts +0 -46
- package/src/core/theme/__workshop__/build/story.tsx +0 -465
- package/src/core/theme/__workshop__/canvas.tsx +0 -352
- package/src/core/theme/__workshop__/color.tsx +0 -62
- package/src/core/theme/__workshop__/debug/story.tsx +0 -408
- package/src/core/theme/__workshop__/index.ts +0 -39
- package/src/core/theme/__workshop__/layer.tsx +0 -78
- package/src/core/theme/__workshop__/nestedProvider.tsx +0 -15
- package/src/core/theme/index.ts +0 -5
- package/src/core/theme/theme.test.tsx +0 -73
- package/src/core/theme/themeColorProvider.tsx +0 -29
- package/src/core/theme/themeContext.ts +0 -10
- package/src/core/theme/themeProvider.tsx +0 -62
- package/src/core/theme/types.ts +0 -12
- package/src/core/theme/useRootTheme.ts +0 -17
- package/src/core/theme/useTheme.ts +0 -16
- package/src/core/types/avatar.ts +0 -14
- package/src/core/types/badge.ts +0 -12
- package/src/core/types/box.ts +0 -19
- package/src/core/types/button.ts +0 -21
- package/src/core/types/card.ts +0 -6
- package/src/core/types/component.ts +0 -32
- package/src/core/types/dialog.ts +0 -4
- package/src/core/types/flex.ts +0 -30
- package/src/core/types/grid.ts +0 -14
- package/src/core/types/gridItem.ts +0 -29
- package/src/core/types/index.ts +0 -15
- package/src/core/types/placement.ts +0 -18
- package/src/core/types/popover.ts +0 -4
- package/src/core/types/radius.ts +0 -4
- package/src/core/types/selectable.ts +0 -6
- package/src/core/types/text.ts +0 -4
- package/src/core/utils/arrow/arrow.tsx +0 -123
- package/src/core/utils/arrow/cmds.ts +0 -91
- package/src/core/utils/arrow/index.ts +0 -1
- package/src/core/utils/boundaryElement/__workshop__/index.ts +0 -14
- package/src/core/utils/boundaryElement/__workshop__/plain.tsx +0 -19
- package/src/core/utils/boundaryElement/boundaryElement.test.tsx +0 -100
- package/src/core/utils/boundaryElement/boundaryElementContext.ts +0 -7
- package/src/core/utils/boundaryElement/boundaryElementProvider.tsx +0 -24
- package/src/core/utils/boundaryElement/index.ts +0 -3
- package/src/core/utils/boundaryElement/types.ts +0 -7
- package/src/core/utils/boundaryElement/useBoundaryElement.ts +0 -26
- package/src/core/utils/conditionalWrapper/conditionalWrapper.tsx +0 -21
- package/src/core/utils/conditionalWrapper/index.ts +0 -1
- package/src/core/utils/elementQuery/__workshop__/customMedia.tsx +0 -30
- package/src/core/utils/elementQuery/__workshop__/index.ts +0 -14
- package/src/core/utils/elementQuery/elementQuery.tsx +0 -53
- package/src/core/utils/elementQuery/helpers.ts +0 -27
- package/src/core/utils/elementQuery/index.ts +0 -1
- package/src/core/utils/errorBoundary.tsx +0 -48
- package/src/core/utils/getElementRef.ts +0 -26
- package/src/core/utils/index.ts +0 -9
- package/src/core/utils/layer/__workshop__/_debug.tsx +0 -17
- package/src/core/utils/layer/__workshop__/index.ts +0 -24
- package/src/core/utils/layer/__workshop__/multipleRoots.tsx +0 -49
- package/src/core/utils/layer/__workshop__/nested.tsx +0 -98
- package/src/core/utils/layer/__workshop__/responsiveZOffset.tsx +0 -13
- package/src/core/utils/layer/getLayerContext.test.ts +0 -30
- package/src/core/utils/layer/getLayerContext.ts +0 -21
- package/src/core/utils/layer/index.ts +0 -4
- package/src/core/utils/layer/layer.test.tsx +0 -108
- package/src/core/utils/layer/layer.tsx +0 -98
- package/src/core/utils/layer/layerContext.ts +0 -7
- package/src/core/utils/layer/layerProvider.tsx +0 -111
- package/src/core/utils/layer/types.ts +0 -9
- package/src/core/utils/layer/useLayer.ts +0 -26
- package/src/core/utils/portal/__workshop__/index.ts +0 -14
- package/src/core/utils/portal/__workshop__/named.tsx +0 -63
- package/src/core/utils/portal/index.ts +0 -4
- package/src/core/utils/portal/portal.test.tsx +0 -103
- package/src/core/utils/portal/portal.ts +0 -32
- package/src/core/utils/portal/portalContext.ts +0 -31
- package/src/core/utils/portal/portalProvider.tsx +0 -47
- package/src/core/utils/portal/types.ts +0 -9
- package/src/core/utils/portal/usePortal.ts +0 -25
- package/src/core/utils/spanWithTextOverflow.tsx +0 -10
- package/src/core/utils/srOnly/index.ts +0 -1
- package/src/core/utils/srOnly/srOnly.tsx +0 -36
- package/src/core/utils/virtualList/__workshop__/changingProps.tsx +0 -36
- package/src/core/utils/virtualList/__workshop__/elementScroll.tsx +0 -24
- package/src/core/utils/virtualList/__workshop__/index.ts +0 -29
- package/src/core/utils/virtualList/__workshop__/infiniteList.tsx +0 -48
- package/src/core/utils/virtualList/__workshop__/windowScrolll.tsx +0 -22
- package/src/core/utils/virtualList/index.ts +0 -1
- package/src/core/utils/virtualList/virtualList.tsx +0 -200
- package/src/theme/build/_deprecated/color/_selectable/createSelectableTones.ts +0 -76
- package/src/theme/build/_deprecated/color/_solid/createSolidTones.ts +0 -54
- package/src/theme/build/_deprecated/color/button/createButtonModes.ts +0 -22
- package/src/theme/build/_deprecated/color/button/createButtonTones.ts +0 -55
- package/src/theme/build/_deprecated/color/card/createCardStates.ts +0 -60
- package/src/theme/build/_deprecated/color/color.test.ts +0 -63
- package/src/theme/build/_deprecated/color/defaults.ts +0 -390
- package/src/theme/build/_deprecated/color/factory.ts +0 -142
- package/src/theme/build/_deprecated/color/index.ts +0 -1
- package/src/theme/build/_deprecated/color/input/createInputModes.ts +0 -81
- package/src/theme/build/_deprecated/color/muted/createMuted.ts +0 -54
- package/src/theme/build/_deprecated/color/spot/createSpot.ts +0 -20
- package/src/theme/build/buildColorTheme.test.ts +0 -183
- package/src/theme/build/buildColorTheme.ts +0 -499
- package/src/theme/build/buildTheme.test.ts +0 -87
- package/src/theme/build/buildTheme.ts +0 -36
- package/src/theme/build/colorToken/colorToken.ts +0 -19
- package/src/theme/build/colorToken/compileColorToken.ts +0 -21
- package/src/theme/build/colorToken/index.ts +0 -2
- package/src/theme/build/colorToken/types.ts +0 -6
- package/src/theme/build/index.ts +0 -3
- package/src/theme/build/lib/color-fns/blend/index.ts +0 -3
- package/src/theme/build/lib/color-fns/blend/mix.ts +0 -21
- package/src/theme/build/lib/color-fns/blend/multiply.ts +0 -18
- package/src/theme/build/lib/color-fns/blend/screen.ts +0 -18
- package/src/theme/build/lib/color-fns/color-fns.test.ts +0 -68
- package/src/theme/build/lib/color-fns/contrastRatio.ts +0 -31
- package/src/theme/build/lib/color-fns/convert.ts +0 -150
- package/src/theme/build/lib/color-fns/index.ts +0 -6
- package/src/theme/build/lib/color-fns/parse.ts +0 -60
- package/src/theme/build/lib/color-fns/rgba.ts +0 -10
- package/src/theme/build/lib/color-fns/types.ts +0 -28
- package/src/theme/build/lib/isRecord.ts +0 -3
- package/src/theme/build/lib/lazy.ts +0 -30
- package/src/theme/build/lib/utils.ts +0 -19
- package/src/theme/build/merge.ts +0 -26
- package/src/theme/build/mixThemeColor.test.ts +0 -21
- package/src/theme/build/mixThemeColor.ts +0 -53
- package/src/theme/build/renderColorTheme.ts +0 -532
- package/src/theme/build/renderColorValue.ts +0 -85
- package/src/theme/build/resolveColorTokens.ts +0 -268
- package/src/theme/build/theme.test.ts +0 -27
- package/src/theme/config/helpers.ts +0 -55
- package/src/theme/config/index.ts +0 -4
- package/src/theme/config/system.ts +0 -115
- package/src/theme/config/tokens/color/index.ts +0 -1
- package/src/theme/config/tokens/color/types.ts +0 -133
- package/src/theme/config/tokens/index.ts +0 -4
- package/src/theme/config/tokens/parseTokenKey.test.ts +0 -64
- package/src/theme/config/tokens/parseTokenKey.ts +0 -67
- package/src/theme/config/tokens/parseTokenValue.test.ts +0 -42
- package/src/theme/config/tokens/parseTokenValue.ts +0 -133
- package/src/theme/config/tokens/types.ts +0 -53
- package/src/theme/config/types.ts +0 -46
- package/src/theme/defaults/colorPalette.ts +0 -5
- package/src/theme/defaults/colorTokens.ts +0 -648
- package/src/theme/defaults/config.ts +0 -84
- package/src/theme/defaults/fonts.ts +0 -227
- package/src/theme/getScopedTheme.ts +0 -98
- package/src/theme/index.ts +0 -5
- package/src/theme/system/avatar.ts +0 -14
- package/src/theme/system/color/_constants.ts +0 -45
- package/src/theme/system/color/_helpers.ts +0 -24
- package/src/theme/system/color/_system.ts +0 -40
- package/src/theme/system/color/avatar.ts +0 -15
- package/src/theme/system/color/badge.ts +0 -16
- package/src/theme/system/color/button.ts +0 -17
- package/src/theme/system/color/color.ts +0 -34
- package/src/theme/system/color/index.ts +0 -13
- package/src/theme/system/color/input.ts +0 -25
- package/src/theme/system/color/kbd.ts +0 -8
- package/src/theme/system/color/selectable.ts +0 -12
- package/src/theme/system/color/shadow.ts +0 -7
- package/src/theme/system/color/state.ts +0 -43
- package/src/theme/system/color/syntax.ts +0 -41
- package/src/theme/system/css.ts +0 -14
- package/src/theme/system/focusRing.ts +0 -7
- package/src/theme/system/font.ts +0 -52
- package/src/theme/system/index.ts +0 -11
- package/src/theme/system/input.ts +0 -33
- package/src/theme/system/layer.ts +0 -8
- package/src/theme/system/shadow.ts +0 -19
- package/src/theme/system/styles.ts +0 -13
- package/src/theme/system/theme.ts +0 -138
- package/src/theme/system/v0/avatar.ts +0 -10
- package/src/theme/system/v0/color/_generic.ts +0 -35
- package/src/theme/system/v0/color/_system.ts +0 -17
- package/src/theme/system/v0/color/base.ts +0 -21
- package/src/theme/system/v0/color/button.ts +0 -42
- package/src/theme/system/v0/color/card.ts +0 -19
- package/src/theme/system/v0/color/color.ts +0 -40
- package/src/theme/system/v0/color/index.ts +0 -11
- package/src/theme/system/v0/color/input.ts +0 -34
- package/src/theme/system/v0/color/muted.ts +0 -26
- package/src/theme/system/v0/color/selectable.ts +0 -31
- package/src/theme/system/v0/color/solid.ts +0 -26
- package/src/theme/system/v0/color/spot.ts +0 -13
- package/src/theme/system/v0/index.ts +0 -3
- package/src/theme/system/v0/input.ts +0 -23
- package/src/theme/versioning/getTheme_v2.ts +0 -57
- package/src/theme/versioning/index.ts +0 -5
- package/src/theme/versioning/is_v0.ts +0 -6
- package/src/theme/versioning/is_v2.ts +0 -6
- package/src/theme/versioning/themeColor_v0_v2.ts +0 -243
- package/src/theme/versioning/themeColor_v2_v2_9.ts +0 -49
- package/src/theme/versioning/v0_v2.ts +0 -94
- package/src/theme/versioning/v2_v0.ts +0 -135
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"editor.js","names":[],"sources":["../../../src/controls/rich-text/editor.tsx"],"sourcesContent":["/**\n * RICH TEXT — the boxed rich-text editor (V2 HEAD controls/rich-text-editor.tsx, Figma 60995-5431, CPO D49 / D54 / D55).\n *\n * contentEditable + execCommand keeps it dependency-free; the value is clean HTML, which the field's control turns into\n * the stored value through the host's codec (./codec.ts). Rich blocks (an image) are React \"islands\" rendered into\n * contenteditable=false nodes and written back as static HTML, so a re-mount restores them (./dom.ts).\n *\n * ./toolbar.tsx the field toolbar (no room at rest, folds into the chevron by width)\n * ./catalog.tsx Insert menu, slash menu and the shared block catalogue\n * ./blocks.tsx the rich blocks (an image)\n * ./markdown.ts HTML ⇄ Markdown for the Markdown toggle and pasting\n * ./ops.ts pure DOM block operations (insert, turn into, move, duplicate, live Markdown, field rules)\n * ./floating.tsx the selection bubble\n * ./dom.ts hydrate / serialize / sanitize and selection helpers\n *\n * Everything the editor offers is limited to what the field accepts (`features`): a toolbar button, a slash command, a\n * Markdown shortcut or pasted markup the field cannot hold is not offered, or is turned into what it can hold and said so.\n */\nimport * as React from \"react\";\nimport { createPortal, flushSync } from \"react-dom\";\nimport { AnimatePresence, motion, useReducedMotion } from \"framer-motion\";\nimport { IconArrowBarToDown, IconArrowBarToUp, IconCopy, IconGripVertical, IconPlus, IconTransform, IconTrash } from \"@tabler/icons-react\";\nimport { cn } from \"../../lib/cn\";\nimport { eventKey } from \"../../lib/key-event\";\nimport { useKitEnv, useKitServices, type AiPreset } from \"../../context\";\nimport { Button } from \"../../ui/button\";\nimport { Textarea } from \"../../ui/input\";\nimport { ExpandedEditorModal } from \"../../ui/expanded-editor-modal\";\nimport { Menu, MenuContent, MenuItem, MenuSeparator, MenuSub, MenuSubContent, MenuSubTrigger, MenuTrigger, Popover, PopoverAnchor, PopoverContent, PopoverTrigger, Tooltip } from \"../../ui/overlay\";\nimport { shortcutHintsOn } from \"../../ui/shortcut-hint\";\nimport { ALL_FEATURES, type RichTextFeature } from \"./codec\";\nimport { COMPONENT_INSERT_TOAST, type KitHistoryStep } from \"../component-services\";\nimport { Island, type IslandCtx } from \"./blocks\";\nimport { openComponentPanel } from \"./component-panel\";\nimport { CatalogComponentsProvider, InsertMenuContent, SlashMenuPanel, blockAllowed, catalogKey, noteRecent, useCatalog, type CatalogComponents, type CatalogItem } from \"./catalog\";\nimport {\n closestBlock, createIsland, defaultModel, editingHost, esc, hydrate, isEmptyHtml, placeCaret, rangeRect, rid, sanitize,\n serialize, textBeforeCaret, topBlock, type IslandEl, type IslandModels, type IslandKind,\n} from \"./dom\";\nimport { htmlToMarkdown, looksLikeMarkdown, markdownToHtml } from \"./markdown\";\nimport * as ops from \"./ops\";\nimport { SelectionBubble } from \"./floating\";\nimport { LinkForm, type TextLink } from \"./link-form\";\nimport { EMPTY_FMT, FormatToolbar, MARK_FEATURE, stylesFor, type Fmt, type MarkCmd } from \"./toolbar\";\n\n/* ── Prose styles for the editable surface (kit tokens only) ──\n * Every descendant rule skips `[data-rt-isolate]` subtrees, as V2's (rich-text-editor.tsx:46-58): a block's own UI inside\n * the writing surface (a table island's column headers, a component card's form) is app UI, not prose. */\nexport const RT_PROSE =\n \"text-kit-base leading-[1.6] text-kit-fg [&>*+*]:mt-3 \" +\n // BUG-7: a styled run keeps the SITE's class (the stored design), but the site's stylesheet is not here. Only the\n // utilities the dashboard happens to build apply: `text-transparent` without its `bg-clip-text` gradient drew the\n // words invisible. The run's text is drawn as text; the class itself is kept, so a save writes it back unchanged.\n \"[&_span[class]:not([data-rt-isolate]_*)]:!text-inherit [&_span[class]:not([data-rt-isolate]_*)]:![-webkit-text-fill-color:currentColor] [&_span[class]:not([data-rt-isolate]_*)]:!bg-none [&_span[class]:not([data-rt-isolate]_*)]:!opacity-100 [&_span[class]:not([data-rt-isolate]_*)]:!visible \" +\n \"[&_h1:not([data-rt-isolate]_*)]:text-[28px] [&_h1:not([data-rt-isolate]_*)]:font-semibold [&_h1:not([data-rt-isolate]_*)]:leading-9 [&_h1:not([data-rt-isolate]_*)]:tracking-[-0.01em] [&_h2:not([data-rt-isolate]_*)]:text-[22px] [&_h2:not([data-rt-isolate]_*)]:font-semibold [&_h2:not([data-rt-isolate]_*)]:leading-8 [&_h2:not([data-rt-isolate]_*)]:tracking-[-0.01em] \" +\n \"[&_h3:not([data-rt-isolate]_*)]:text-kit-lg [&_h3:not([data-rt-isolate]_*)]:font-semibold [&_h4:not([data-rt-isolate]_*)]:text-kit-md [&_h4:not([data-rt-isolate]_*)]:font-semibold [&_h5:not([data-rt-isolate]_*)]:text-kit-base [&_h5:not([data-rt-isolate]_*)]:font-semibold [&_h6:not([data-rt-isolate]_*)]:text-kit-sm [&_h6:not([data-rt-isolate]_*)]:font-semibold [&_h6:not([data-rt-isolate]_*)]:uppercase [&_h6:not([data-rt-isolate]_*)]:tracking-wide [&_h6:not([data-rt-isolate]_*)]:text-kit-fg-2 [&>h1]:mt-6 [&>h2]:mt-6 [&>h3]:mt-5 [&>*:first-child]:mt-0 \" +\n // a block's own list (key takeaways, V2 data-rt-isolate) is app UI, not body prose: V2 rich-text-editor.tsx skips it\n \"[&_ul:not([data-rt-isolate]_*)]:list-disc [&_ul:not([data-rt-isolate]_*)]:pl-5 [&_ol:not([data-rt-isolate]_*)]:list-decimal [&_ol:not([data-rt-isolate]_*)]:pl-5 [&_li:not([data-rt-isolate]_*)]:pl-1 [&_li+li:not([data-rt-isolate]_*)]:mt-1 [&_li:not([data-rt-isolate]_*)]:marker:text-kit-fg-3 \" +\n \"[&_ul[data-task]:not([data-rt-isolate]_*)]:list-none [&_ul[data-task]:not([data-rt-isolate]_*)]:pl-0 [&_ul[data-task]>li:not([data-rt-isolate]_*)]:relative [&_ul[data-task]>li:not([data-rt-isolate]_*)]:pl-7 [&_ul[data-task]>li:not([data-rt-isolate]_*)]:before:absolute [&_ul[data-task]>li:not([data-rt-isolate]_*)]:before:left-0 [&_ul[data-task]>li:not([data-rt-isolate]_*)]:before:top-[0.2em] [&_ul[data-task]>li:not([data-rt-isolate]_*)]:before:flex [&_ul[data-task]>li:not([data-rt-isolate]_*)]:before:size-4 [&_ul[data-task]>li:not([data-rt-isolate]_*)]:before:items-center [&_ul[data-task]>li:not([data-rt-isolate]_*)]:before:justify-center [&_ul[data-task]>li:not([data-rt-isolate]_*)]:before:rounded-kit-md [&_ul[data-task]>li:not([data-rt-isolate]_*)]:before:border [&_ul[data-task]>li:not([data-rt-isolate]_*)]:before:border-kit-line-strong [&_ul[data-task]>li:not([data-rt-isolate]_*)]:before:bg-kit-surface [&_ul[data-task]>li:not([data-rt-isolate]_*)]:before:text-[11px] [&_ul[data-task]>li:not([data-rt-isolate]_*)]:before:font-semibold [&_ul[data-task]>li:not([data-rt-isolate]_*)]:before:leading-none [&_ul[data-task]>li:not([data-rt-isolate]_*)]:before:content-[''] \" +\n \"[&_ul[data-task]>li[data-checked=true]:not([data-rt-isolate]_*)]:text-kit-fg-3 [&_ul[data-task]>li[data-checked=true]:not([data-rt-isolate]_*)]:line-through [&_ul[data-task]>li[data-checked=true]:not([data-rt-isolate]_*)]:before:border-kit-inverse [&_ul[data-task]>li[data-checked=true]:not([data-rt-isolate]_*)]:before:bg-kit-inverse [&_ul[data-task]>li[data-checked=true]:not([data-rt-isolate]_*)]:before:text-kit-fg-inverse [&_ul[data-task]>li[data-checked=true]:not([data-rt-isolate]_*)]:before:content-['✓'] \" +\n \"[&_blockquote:not([data-rt-isolate]_*)]:border-l-2 [&_blockquote:not([data-rt-isolate]_*)]:border-kit-line-strong [&_blockquote:not([data-rt-isolate]_*)]:pl-4 [&_blockquote:not([data-rt-isolate]_*)]:text-kit-fg-2 [&_blockquote:not([data-rt-isolate]_*)]:italic \" +\n \"[&_a:not([data-rt-isolate]_*)]:text-kit-accent-fg [&_a:not([data-rt-isolate]_*)]:underline [&_a:not([data-rt-isolate]_*)]:decoration-kit-accent-line [&_a:not([data-rt-isolate]_*)]:underline-offset-2 \" +\n \"[&_a[data-button]:not([data-rt-isolate]_*)]:inline-flex [&_a[data-button]:not([data-rt-isolate]_*)]:h-9 [&_a[data-button]:not([data-rt-isolate]_*)]:items-center [&_a[data-button]:not([data-rt-isolate]_*)]:rounded-kit-md [&_a[data-button]:not([data-rt-isolate]_*)]:bg-kit-inverse [&_a[data-button]:not([data-rt-isolate]_*)]:px-3.5 [&_a[data-button]:not([data-rt-isolate]_*)]:text-kit-sm [&_a[data-button]:not([data-rt-isolate]_*)]:font-medium [&_a[data-button]:not([data-rt-isolate]_*)]:text-kit-fg-inverse [&_a[data-button]:not([data-rt-isolate]_*)]:no-underline \" +\n // a glossary term (`<abbr data-term title>`) reads as a dotted underline; a footnote marker as a small superscript\n \"[&_abbr:not([data-rt-isolate]_*)]:cursor-help [&_abbr:not([data-rt-isolate]_*)]:underline [&_abbr:not([data-rt-isolate]_*)]:decoration-dotted [&_abbr:not([data-rt-isolate]_*)]:underline-offset-2 [&_sup:not([data-rt-isolate]_*)]:text-[0.7em] [&_sup:not([data-rt-isolate]_*)]:leading-none \" +\n \"[&_code:not([data-rt-isolate]_*)]:rounded-kit-md [&_code:not([data-rt-isolate]_*)]:bg-kit-muted [&_code:not([data-rt-isolate]_*)]:px-1 [&_code:not([data-rt-isolate]_*)]:py-px [&_code:not([data-rt-isolate]_*)]:font-kit-mono [&_code:not([data-rt-isolate]_*)]:text-[0.9em] \" +\n \"[&_pre:not([data-rt-isolate]_*)]:overflow-x-auto [&_pre:not([data-rt-isolate]_*)]:whitespace-pre-wrap [&_pre:not([data-rt-isolate]_*)]:rounded-kit-lg [&_pre:not([data-rt-isolate]_*)]:bg-kit-code [&_pre:not([data-rt-isolate]_*)]:text-kit-code-fg [&_pre:not([data-rt-isolate]_*)]:p-3 [&_pre:not([data-rt-isolate]_*)]:font-kit-mono [&_pre:not([data-rt-isolate]_*)]:text-kit-sm [&_pre:not([data-rt-isolate]_*)]:border [&_pre:not([data-rt-isolate]_*)]:border-kit-line \" +\n \"[&_pre_code:not([data-rt-isolate]_*)]:rounded-none [&_pre_code:not([data-rt-isolate]_*)]:bg-transparent [&_pre_code:not([data-rt-isolate]_*)]:p-0 [&_pre_code:not([data-rt-isolate]_*)]:text-[1em] \" +\n \"[&_hr:not([data-rt-isolate]_*)]:my-6 [&_hr:not([data-rt-isolate]_*)]:border-kit-line \" +\n // V2 rich-text-editor.tsx 64-65: an image's figure sits 16px off its neighbours (my-4), the picture framed\n \"[&_figure:not([data-rt-isolate]_*)]:my-4 [&_img:not([data-rt-isolate]_*)]:rounded-kit-lg [&_img:not([data-rt-isolate]_*)]:border [&_img:not([data-rt-isolate]_*)]:border-kit-line [&_figcaption:not([data-rt-isolate]_*)]:mt-1.5 [&_figcaption:not([data-rt-isolate]_*)]:text-center [&_figcaption:not([data-rt-isolate]_*)]:text-kit-sm [&_figcaption:not([data-rt-isolate]_*)]:text-kit-fg-3 \" +\n \"[&_figure_img:not([data-rt-isolate]_*)]:block [&_figure[data-size=s]_img:not([data-rt-isolate]_*)]:w-1/3 [&_figure[data-size=m]_img:not([data-rt-isolate]_*)]:w-1/2 [&_figure[data-size=l]_img:not([data-rt-isolate]_*)]:w-3/4 [&_figure[data-align=center]_img:not([data-rt-isolate]_*)]:mx-auto [&_figure[data-align=right]_img:not([data-rt-isolate]_*)]:ml-auto [&_figure[data-align=full]_img:not([data-rt-isolate]_*)]:w-full \" +\n \"[&_div[data-callout]:not([data-rt-isolate]_*)]:rounded-kit-lg [&_div[data-callout]:not([data-rt-isolate]_*)]:border [&_div[data-callout]:not([data-rt-isolate]_*)]:border-kit-info-line [&_div[data-callout]:not([data-rt-isolate]_*)]:bg-kit-info-soft [&_div[data-callout]:not([data-rt-isolate]_*)]:px-4 [&_div[data-callout]:not([data-rt-isolate]_*)]:py-3 [&_div[data-callout]:not([data-rt-isolate]_*)]:text-kit-fg \" +\n \"[&_div[data-callout=tip]:not([data-rt-isolate]_*)]:border-kit-success-line [&_div[data-callout=tip]:not([data-rt-isolate]_*)]:bg-kit-success-soft [&_div[data-callout=warning]:not([data-rt-isolate]_*)]:border-kit-warning-line [&_div[data-callout=warning]:not([data-rt-isolate]_*)]:bg-kit-warning-soft [&_div[data-callout]>p[data-title]:not([data-rt-isolate]_*)]:font-medium \" +\n \"[&_details:not([data-rt-isolate]_*)]:rounded-kit-md [&_summary:not([data-rt-isolate]_*)]:cursor-pointer [&_summary:not([data-rt-isolate]_*)]:font-medium [&_details>div:not([data-rt-isolate]_*)]:mt-1 [&_details>div:not([data-rt-isolate]_*)]:border-l [&_details>div:not([data-rt-isolate]_*)]:border-kit-line [&_details>div:not([data-rt-isolate]_*)]:pl-4 [&_details>div:not([data-rt-isolate]_*)]:ml-1 \" +\n \"[&_div[data-rt=columns]:not([data-rt-isolate]_*)]:grid [&_div[data-rt=columns]:not([data-rt-isolate]_*)]:gap-4 [&_div[data-cols='2']:not([data-rt-isolate]_*)]:grid-cols-2 [&_div[data-cols='3']:not([data-rt-isolate]_*)]:grid-cols-3 [&_div[data-cols='4']:not([data-rt-isolate]_*)]:grid-cols-4 [&_div[data-gap=s]:not([data-rt-isolate]_*)]:gap-2 [&_div[data-gap=l]:not([data-rt-isolate]_*)]:gap-7 \" +\n \"[&_div[data-rt=file]:not([data-rt-isolate]_*)]:rounded-kit-lg [&_div[data-rt=file]:not([data-rt-isolate]_*)]:border [&_div[data-rt=file]:not([data-rt-isolate]_*)]:border-kit-line [&_div[data-rt=file]:not([data-rt-isolate]_*)]:px-3 [&_div[data-rt=file]:not([data-rt-isolate]_*)]:py-2.5 [&_div[data-rt=file]:not([data-rt-isolate]_*)]:text-kit-sm \" +\n \"[&_div[data-embed]:not([data-rt-isolate]_*)]:flex [&_div[data-embed]:not([data-rt-isolate]_*)]:aspect-video [&_div[data-embed]:not([data-rt-isolate]_*)]:items-center [&_div[data-embed]:not([data-rt-isolate]_*)]:justify-center [&_div[data-embed]:not([data-rt-isolate]_*)]:rounded-kit-lg [&_div[data-embed]:not([data-rt-isolate]_*)]:border [&_div[data-embed]:not([data-rt-isolate]_*)]:border-kit-line [&_div[data-embed]:not([data-rt-isolate]_*)]:bg-kit-subtle [&_div[data-embed]:not([data-rt-isolate]_*)]:text-kit-sm [&_div[data-embed]:not([data-rt-isolate]_*)]:text-kit-fg-3 \" +\n \"[&_div[data-block]:not([data-rt-isolate]_*)]:flex [&_div[data-block]:not([data-rt-isolate]_*)]:items-center [&_div[data-block]:not([data-rt-isolate]_*)]:gap-2 [&_div[data-block]:not([data-rt-isolate]_*)]:rounded-kit-lg [&_div[data-block]:not([data-rt-isolate]_*)]:border [&_div[data-block]:not([data-rt-isolate]_*)]:border-dashed [&_div[data-block]:not([data-rt-isolate]_*)]:border-kit-accent-line [&_div[data-block]:not([data-rt-isolate]_*)]:bg-kit-accent-softer [&_div[data-block]:not([data-rt-isolate]_*)]:px-3 [&_div[data-block]:not([data-rt-isolate]_*)]:py-3 [&_div[data-block]:not([data-rt-isolate]_*)]:text-kit-sm [&_div[data-block]:not([data-rt-isolate]_*)]:text-kit-accent-fg \" +\n \"[&_table:not([data-rt-isolate]_*)]:w-full [&_table:not([data-rt-isolate]_*)]:border-collapse [&_table:not([data-rt-isolate]_*)]:text-kit-sm [&_td:not([data-rt-isolate]_*)]:border [&_td:not([data-rt-isolate]_*)]:border-kit-line [&_td:not([data-rt-isolate]_*)]:px-2.5 [&_td:not([data-rt-isolate]_*)]:py-1.5 [&_td:not([data-rt-isolate]_*)]:align-top [&_th:not([data-rt-isolate]_*)]:border [&_th:not([data-rt-isolate]_*)]:border-kit-line [&_th:not([data-rt-isolate]_*)]:bg-kit-subtle [&_th:not([data-rt-isolate]_*)]:px-2.5 [&_th:not([data-rt-isolate]_*)]:py-1.5 [&_th:not([data-rt-isolate]_*)]:text-left [&_th:not([data-rt-isolate]_*)]:align-top [&_th:not([data-rt-isolate]_*)]:font-medium\";\n\n/** Panel density (≈340px inspector): 13px text, smaller headings. */\nexport const RT_PANEL = \"text-kit-sm leading-[1.6] [&_h1:not([data-rt-isolate]_*)]:text-kit-xl [&_h1:not([data-rt-isolate]_*)]:leading-7 [&_h2:not([data-rt-isolate]_*)]:text-kit-lg [&_h2:not([data-rt-isolate]_*)]:leading-7 [&_h3:not([data-rt-isolate]_*)]:text-kit-md [&_h4:not([data-rt-isolate]_*)]:text-kit-base [&_h5:not([data-rt-isolate]_*)]:text-kit-sm [&_h6:not([data-rt-isolate]_*)]:text-kit-xs\";\n\n/** execCommand, where the engine has it (it returns false where it does not). */\nconst exec = (cmd: string, arg?: string): boolean => {\n try {\n return typeof document.execCommand === \"function\" && document.execCommand(cmd, false, arg);\n } catch {\n return false;\n }\n};\n/** A footnote marker (`<sup data-footnote>`, or the table's `<sup><a href=\"#…-fn-n\">`): never an x² mark. */\nconst FOOTNOTE_SUP = \"sup[data-footnote], sup:has(> a[href*='-fn-'])\";\n/** x² / x₂ (V2): on inside the same mark takes it off (unwrap, keeping the words selected); inside the other one swaps;\n * otherwise the browser wraps the selection. Footnote markers are never touched. */\nfunction toggleScript(root: HTMLElement, tag: \"sup\" | \"sub\") {\n const s = window.getSelection();\n if (!s || !s.rangeCount) return;\n const at = (n: Node | null) => (n?.nodeType === 1 ? (n as HTMLElement) : (n?.parentElement ?? null));\n const find = (t: \"sup\" | \"sub\") => {\n const el = at(s.anchorNode)?.closest<HTMLElement>(t === \"sup\" ? `sup:not(${FOOTNOTE_SUP})` : \"sub\");\n return el && root.contains(el) ? el : null;\n };\n const unwrap = (el: HTMLElement) => {\n const first = el.firstChild;\n const last = el.lastChild;\n el.replaceWith(...Array.from(el.childNodes));\n if (first && last) {\n const r = document.createRange();\n r.setStartBefore(first);\n r.setEndAfter(last);\n s.removeAllRanges();\n s.addRange(r);\n }\n };\n const same = find(tag);\n if (same) return unwrap(same);\n const other = find(tag === \"sup\" ? \"sub\" : \"sup\");\n if (other) unwrap(other);\n exec(tag === \"sup\" ? \"superscript\" : \"subscript\");\n}\n\n/** Focus is in another text field (the comment composer, a link input) while the page's selection stays in this editor. */\nconst typingElsewhere = (el: HTMLElement | null) => {\n const ae = document.activeElement;\n return !!el && !!ae && ae !== el && !el.contains(ae) && ae.matches(\"input, textarea, [contenteditable='true']\");\n};\nconst queryState = (c: string) => {\n try {\n return typeof document.queryCommandState === \"function\" && document.queryCommandState(c);\n } catch {\n return false;\n }\n};\n/** Insert HTML at the caret: the browser's own insert (undoable), else by hand. */\nfunction insertHtmlAtCaret(html: string) {\n if (exec(\"insertHTML\", html)) return;\n const s = window.getSelection();\n if (!s || !s.rangeCount) return;\n const r = s.getRangeAt(0);\n r.deleteContents();\n const tpl = document.createElement(\"template\");\n tpl.innerHTML = sanitize(html);\n const last = tpl.content.lastChild;\n r.insertNode(tpl.content);\n if (last) {\n r.setStartAfter(last);\n r.collapse(true);\n s.removeAllRanges();\n s.addRange(r);\n }\n}\n/* ── Word count (V2 rich-text-editor.tsx:115-128 + article.ts countWords, CPO D54 / D55) ──\n * Words = what the writer wrote once, in the flow a reader follows: text, headings, lists, quotes, callouts, toggles,\n * table cells and image captions. Not counted: components (counted apart), a pull quote (it repeats a line of the\n * story), key takeaways (they restate it), embeds, video and file links. */\nconst NOT_COUNTED = \"[data-rt=component],[data-rt=pullquote],[data-rt=takeaways],[data-rt=embed],[data-rt=video],[data-rt=file]\";\nconst WORDS = (s: string) => s.replace(/\\u200b/g, \"\").trim().split(/\\s+/).filter(Boolean).length;\nexport function countWords(html: string): number {\n if (!html) return 0;\n if (!/data-rt=\"(?:component|pullquote|takeaways|embed|video|file)\"/.test(html) || typeof DOMParser === \"undefined\")\n // A block's end and a line break part words; any other tag is a mark inside one (\"<strong>Screw</strong>Fast,\").\n return WORDS(html.replace(/<\\/(p|li|h[1-6]|blockquote|pre|figcaption|td|th|summary|div)>|<br\\s*\\/?>/g, \" \").replace(/<[^>]+>/g, \"\").replace(/ |&[a-z]+;/g, \" \"));\n const doc = new DOMParser().parseFromString(`<body>${html}</body>`, \"text/html\");\n doc.body.querySelectorAll(NOT_COUNTED).forEach((n) => n.remove());\n doc.body.querySelectorAll(\"p,li,h1,h2,h3,h4,h5,h6,td,th,figcaption,summary,pre,blockquote,div\").forEach((n) => n.append(\" \"));\n return WORDS(doc.body.textContent ?? \"\");\n}\n/** Linked component instances in the body. */\nexport const countComponents = (html: string) => (html.match(/data-rt=\"component\"/g) ?? []).length;\n/** \"1,840 words · 3 components\" */\nexport const bodyCountLabel = (html: string) => {\n const w = countWords(html);\n const c = countComponents(html);\n return `${w.toLocaleString(\"en-US\")} ${w === 1 ? \"word\" : \"words\"}${c ? ` · ${c} ${c === 1 ? \"block\" : \"blocks\"}` : \"\"}`;\n};\n\nfunction insertTextAtCaret(text: string) {\n if (exec(\"insertText\", text)) return;\n const s = window.getSelection();\n if (!s || !s.rangeCount) return;\n const r = s.getRangeAt(0);\n r.deleteContents();\n const t = document.createTextNode(text);\n r.insertNode(t);\n r.setStartAfter(t);\n r.collapse(true);\n s.removeAllRanges();\n s.addRange(r);\n}\n\n/** The slash menu at full height (header 32, list 300, footer 28, borders), the least it shrinks to, and the gap it keeps from the window's edge. */\nconst SLASH_MENU_H = 362;\nconst SLASH_MIN_H = 160;\nconst SLASH_EDGE = 8;\n\n/**\n * Where the slash menu goes, collision-aware: below the caret when the whole menu fits there, else on the side with\n * more room, and never taller than that room (its list scrolls), so the last row (More components) stays reachable in\n * a short window.\n */\nexport function slashPlacement(caret: { top: number; bottom: number }, viewportH: number): { flipUp: boolean; maxHeight: number } {\n const below = viewportH - caret.bottom - 6 - SLASH_EDGE;\n const above = caret.top - 6 - SLASH_EDGE;\n const flipUp = below < SLASH_MENU_H && above > below;\n return { flipUp, maxHeight: Math.max(SLASH_MIN_H, Math.min(SLASH_MENU_H, flipUp ? above : below)) };\n}\n\ntype IslandStep = { el: IslandEl; before: IslandModels[IslandKind]; label: string; at: number };\n/** A step the host's history holds (KitServices.historyStep); its undo and redo are the host's, while it is next. */\ntype HostStep = { label: string; step: KitHistoryStep };\ntype GutterState = { el: HTMLElement; top: number; height: number };\ntype SlashState = { rect: DOMRect; node: Text; offset: number; query: string; folder: boolean; active: number };\ntype LinkState = { rect: DOMRect; initial: TextLink; existing: HTMLAnchorElement | null };\ntype Notice = { message: string; description?: string; action?: { label: string; onClick: () => void } };\n\nexport interface RichTextEditorProps {\n value: string;\n onChange: (html: string) => void;\n readOnly?: boolean;\n placeholder?: string;\n docKey: string;\n /** what the field accepts; the editor offers nothing else (default: everything) */\n features?: readonly RichTextFeature[];\n /** a one-paragraph field: Enter starts no new block */\n single?: boolean;\n /** links may open in a new tab */\n allowNewTab?: boolean;\n /** the writing surface's id (the field label's `for`; its label is `${id}-label`) */\n id?: string;\n invalid?: boolean;\n /** panel = narrow (~340px) inspector, document = the full editor column. */\n variant?: \"panel\" | \"document\";\n /** CPO D49: the expanded editor's breadcrumb, root → this field (\"Alternating feature rows\", \"Thin walls\", \"Body\"). */\n expandCrumbs?: string[];\n /** Controlled expanded modal (a host's label-row action opens it too). */\n expandedOpen?: boolean;\n onExpandedOpenChange?: (open: boolean) => void;\n /** This editor IS the body of the expanded modal: toolbar always shown, tall writing surface. */\n inModal?: boolean;\n /** Already the full editor: no Expand button. */\n hideFullscreen?: boolean;\n /** Scroll the writing surface beyond this height (px). */\n maxHeight?: number;\n autoFocus?: boolean;\n /** Shows the toolbar Comment button. */\n onComment?: (quote: string) => void;\n /** the components this field may embed (the insert menus' More components); absent → none offered */\n components?: CatalogComponents;\n}\n\n/* ── Editor ────────────────────────────────────────────────────────── */\nexport function RichTextEditor({\n value,\n onChange,\n readOnly,\n placeholder,\n docKey,\n features = ALL_FEATURES,\n single,\n allowNewTab = true,\n id,\n invalid,\n variant = \"document\",\n expandCrumbs,\n expandedOpen,\n onExpandedOpenChange,\n inModal,\n hideFullscreen,\n maxHeight,\n autoFocus,\n onComment,\n components,\n}: RichTextEditorProps) {\n const hints = shortcutHintsOn();\n const ph = placeholder ?? (hints ? \"Type '/' for commands\" : \"Write something…\");\n const dense = variant === \"panel\";\n const ref = React.useRef<HTMLDivElement>(null);\n const wrap = React.useRef<HTMLDivElement>(null);\n const scroller = React.useRef<HTMLDivElement>(null);\n const saved = React.useRef<Range | null>(null);\n const known = React.useRef<string | null>(null);\n const pending = React.useRef<string | null>(null);\n /** a host undo just ran: its value is loaded even while the editor has focus (⌘Z here) */\n const forceLoad = React.useRef(false);\n const prevDoc = React.useRef<string | null>(null);\n const onChangeRef = React.useRef(onChange);\n onChangeRef.current = onChange;\n const valueRef = React.useRef(value);\n valueRef.current = value;\n const services = useKitServices();\n const env = useKitEnv();\n const featureKey = features.join(\",\");\n // eslint-disable-next-line react-hooks/exhaustive-deps\n const allows = React.useCallback((f: RichTextFeature) => features.includes(f), [featureKey]);\n\n const [empty, setEmpty] = React.useState(isEmptyHtml(value));\n const [words, setWords] = React.useState(() => countWords(value));\n const [comps, setComps] = React.useState(() => countComponents(value));\n const [fmt, setFmt] = React.useState<Fmt>(EMPTY_FMT);\n const [modalOwn, setModalOwn] = React.useState(false);\n const modalOpen = expandedOpen ?? modalOwn;\n const setModalOpen = (o: boolean) => (onExpandedOpenChange ? onExpandedOpenChange(o) : setModalOwn(o));\n const [md, setMd] = React.useState<{ text: string; original: string } | null>(null);\n const [mdConfirm, setMdConfirm] = React.useState(false);\n // Reduced motion: the Markdown confirm fades only (no slide).\n const reduceMotion = useReducedMotion();\n const [bubble, setBubble] = React.useState<DOMRect | null>(null);\n /** Comment was picked: the toolbar stays away until the next click or key inside this editor */\n const [quiet, setQuiet] = React.useState(false);\n React.useEffect(() => {\n const el = ref.current;\n if (!quiet || !el) return;\n const wake = () => setQuiet(false);\n el.addEventListener(\"mousedown\", wake);\n el.addEventListener(\"keydown\", wake);\n return () => {\n el.removeEventListener(\"mousedown\", wake);\n el.removeEventListener(\"keydown\", wake);\n };\n }, [quiet]);\n const [slash, setSlash] = React.useState<SlashState | null>(null);\n const [gutter, setGutter] = React.useState<GutterState | null>(null);\n const [blockMenu, setBlockMenu] = React.useState(false);\n const [gutterInsert, setGutterInsert] = React.useState(false);\n const gutterTarget = React.useRef<HTMLElement | null>(null);\n // D58: AI writing help follows ai.use and needs the host's AI service; without both no AI entry point is drawn.\n const canAI = env.can(\"ai.use\") && !!services.aiRewrite;\n const aiAttempt = React.useRef(0);\n const [link, setLink] = React.useState<LinkState | null>(null);\n const [drag, setDrag] = React.useState<{ from: HTMLElement; line: number | null; target: Element | null } | null>(null);\n const [focused, setFocused] = React.useState(false);\n const [menus, setMenus] = React.useState({ style: false, more: false });\n const [insertOpen, setInsertOpen] = React.useState(false);\n const inserted = React.useRef(false);\n const [islands, setIslands] = React.useState<{ id: string; el: IslandEl }[]>([]);\n const hist = React.useRef<{ past: IslandStep[]; future: IslandStep[]; textAt: number; hosts: HostStep[] }>({ past: [], future: [], textAt: 0, hosts: [] });\n const [width, setWidth] = React.useState(720);\n /* The block gutter (+ / grip) never reserves room inside the field: it floats in the space LEFT of the box when the\n host leaves ≥ 48px there (document columns), and sits in the box's padding otherwise. */\n const [gutterRoom, setGutterRoom] = React.useState(false);\n const blurTimer = React.useRef<number | undefined>(undefined);\n const [notice, setNotice] = React.useState<Notice | null>(null);\n\n const expanded = !!inModal;\n const toolbarOpen = !readOnly && (focused || menus.style || menus.more || insertOpen || expanded || !!md || !!link);\n const scrollable = !!maxHeight && !expanded;\n\n /** A refusal or a result the author must see: the host's toaster, else a line under the editor. Never silent. */\n const notify = React.useCallback(\n (message: string, opts: { description?: string; action?: Notice[\"action\"] } = {}) => {\n if (services.toast) services.toast(message, opts);\n else setNotice({ message, ...opts });\n },\n [services],\n );\n React.useEffect(() => {\n if (!notice) return;\n const t = window.setTimeout(() => setNotice(null), 8000);\n return () => window.clearTimeout(t);\n }, [notice]);\n\n /* ── islands ─────────────────────────────────────────────────────── */\n const syncIslands = React.useCallback(() => {\n const el = ref.current;\n if (!el) return setIslands((p) => (p.length ? [] : p));\n const list = Array.from(el.querySelectorAll<IslandEl>(\":scope > [data-rt-island]\"));\n const seen = new Set<string>();\n for (const x of list) {\n if (!x.__rt) {\n // a copy the browser made (drag/drop, native undo of a clone): start it fresh\n x.innerHTML = \"\";\n x.__rt = defaultModel(x.getAttribute(\"data-rt-island\") as IslandKind);\n delete x.dataset.rtId;\n }\n if (!x.dataset.rtId || seen.has(x.dataset.rtId)) x.dataset.rtId = rid(\"i\");\n seen.add(x.dataset.rtId);\n }\n setIslands((prev) => (prev.length === list.length && prev.every((p, i) => p.el === list[i]) ? prev : list.map((x) => ({ id: x.dataset.rtId!, el: x }))));\n }, []);\n\n /* ── value in / out ──────────────────────────────────────────────── */\n const load = React.useCallback(\n (html: string) => {\n const el = ref.current;\n if (!el) return;\n el.innerHTML = sanitize(html || \"\") || \"<p><br></p>\";\n hydrate(el);\n known.current = html;\n setEmpty(isEmptyHtml(html));\n setWords(countWords(html));\n setComps(countComponents(html));\n syncIslands();\n },\n [syncIslands],\n );\n\n const emit = React.useCallback(() => {\n const el = ref.current;\n if (!el) return;\n syncIslands();\n const html = serialize(el);\n setEmpty(isEmptyHtml(html) && !el.querySelector(\":scope > [data-rt-island], :scope > hr\"));\n setWords(countWords(html));\n setComps(countComponents(html));\n if (html === known.current) return;\n forceLoad.current = false;\n known.current = html;\n onChangeRef.current(html);\n }, [syncIslands]);\n\n React.useLayoutEffect(() => {\n const el = ref.current;\n if (!el) return;\n const docChanged = prevDoc.current !== null && prevDoc.current !== docKey;\n prevDoc.current = docKey;\n if (pending.current !== null) {\n const h = pending.current;\n pending.current = null;\n load(h);\n return;\n }\n if (forceLoad.current && value !== known.current) {\n forceLoad.current = false;\n load(value);\n return;\n }\n if (docChanged || !el.firstChild || (value !== known.current && !wrap.current?.contains(document.activeElement))) load(value);\n }, [value, docKey, md, load]);\n\n React.useEffect(() => {\n setMd(null);\n setMdConfirm(false);\n setSlash(null);\n setLink(null);\n setGutter(null);\n }, [docKey]);\n\n React.useEffect(() => {\n exec(\"defaultParagraphSeparator\", \"p\");\n if (autoFocus && ref.current && !readOnly) {\n ref.current.focus({ preventScroll: true });\n placeCaret(ref.current.lastElementChild ?? ref.current);\n }\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, []);\n\n React.useEffect(() => {\n const w = wrap.current;\n if (!w || typeof ResizeObserver === \"undefined\") return;\n const measureRoom = () => {\n let a = w.parentElement;\n while (a && a !== document.body) {\n const cs = getComputedStyle(a);\n if (cs.overflowX !== \"visible\" || cs.overflowY !== \"visible\") break;\n a = a.parentElement;\n }\n const left = w.getBoundingClientRect().left - (a ? a.getBoundingClientRect().left : 0);\n setGutterRoom(left >= 48);\n };\n const ro = new ResizeObserver(([e]) => {\n setWidth(Math.round(e.contentRect.width));\n measureRoom();\n });\n ro.observe(w);\n return () => ro.disconnect();\n }, []);\n\n /* the toolbar sticks below any sticky header (e.g. field tabs) in the same scroll area */\n const [stickyTop, setStickyTop] = React.useState(0);\n React.useEffect(() => {\n const w = wrap.current;\n if (!toolbarOpen || dense || !w) return;\n let sp = w.parentElement;\n while (sp && !/(auto|scroll)/.test(getComputedStyle(sp).overflowY)) sp = sp.parentElement;\n if (!sp) return setStickyTop(0);\n let top = 0;\n sp.querySelectorAll<HTMLElement>(\".sticky\").forEach((h) => {\n if (h.contains(w) || w.contains(h) || !(h.compareDocumentPosition(w) & Node.DOCUMENT_POSITION_FOLLOWING)) return;\n const cs = getComputedStyle(h);\n if (cs.position !== \"sticky\") return;\n top = Math.max(top, (parseFloat(cs.top) || 0) + h.offsetHeight);\n });\n setStickyTop(top);\n }, [toolbarOpen, dense]);\n\n // the slash menu follows the caret when anything scrolls; it closes only when the caret has left the \"/\" it was opened for\n const hasSlash = !!slash;\n React.useEffect(() => {\n if (!hasSlash) return;\n let raf = 0;\n const on = (e: Event) => {\n if (e.target instanceof Element && e.target.closest(\"[role=listbox]\")) return;\n cancelAnimationFrame(raf);\n raf = requestAnimationFrame(() =>\n setSlash((sl) => {\n const s = window.getSelection();\n if (!sl || !s || !s.rangeCount || s.getRangeAt(0).startContainer !== sl.node) return null;\n const rect = rangeRect(s.getRangeAt(0), sl.node.parentElement ?? ref.current);\n return rect.top === sl.rect.top && rect.left === sl.rect.left ? sl : { ...sl, rect };\n }),\n );\n };\n window.addEventListener(\"scroll\", on, true);\n return () => {\n cancelAnimationFrame(raf);\n window.removeEventListener(\"scroll\", on, true);\n };\n }, [hasSlash]);\n\n // keep the bubble on the selection while anything scrolls (incl. the toolbar sliding open)\n const hasBubble = !!bubble;\n React.useEffect(() => {\n if (!hasBubble) return;\n let raf = 0;\n const on = () => {\n cancelAnimationFrame(raf);\n raf = requestAnimationFrame(() => {\n const s = window.getSelection();\n const ok = s && s.rangeCount && !s.isCollapsed && ref.current?.contains(s.anchorNode) && !typingElsewhere(ref.current);\n setBubble(ok ? rangeRect(s!.getRangeAt(0), ref.current) : null);\n });\n };\n window.addEventListener(\"scroll\", on, true);\n window.addEventListener(\"resize\", on);\n // The toolbar sliding open moves the words without a scroll: the bubble sat on the selected word.\n const box = new ResizeObserver(on);\n if (wrap.current) box.observe(wrap.current);\n return () => {\n cancelAnimationFrame(raf);\n box.disconnect();\n window.removeEventListener(\"scroll\", on, true);\n window.removeEventListener(\"resize\", on);\n };\n }, [hasBubble]);\n\n /* ── selection ───────────────────────────────────────────────────── */\n const saveSel = () => {\n const s = window.getSelection();\n if (s && s.rangeCount && ref.current?.contains(s.anchorNode)) saved.current = s.getRangeAt(0).cloneRange();\n };\n const restoreSel = () => {\n const el = ref.current;\n if (!el) return;\n const r = saved.current;\n const s = window.getSelection();\n if (r && el.contains(r.startContainer) && s) {\n (editingHost(r.startContainer) ?? el).focus({ preventScroll: true });\n s.removeAllRanges();\n s.addRange(r);\n } else {\n el.focus({ preventScroll: true });\n placeCaret(el.lastElementChild ?? el);\n }\n };\n\n const refresh = React.useCallback(() => {\n const el = ref.current;\n const s = window.getSelection();\n if (!el || !s || !s.rangeCount || !el.contains(s.anchorNode)) return;\n // typing somewhere else (the comment composer, a link field) keeps the page's selection here: no toolbar over it\n if (typingElsewhere(el)) {\n setBubble(null);\n return;\n }\n saved.current = s.getRangeAt(0).cloneRange();\n const anchorEl = s.anchorNode?.nodeType === 1 ? (s.anchorNode as HTMLElement) : s.anchorNode?.parentElement;\n const inIsland = !!anchorEl?.closest(\"[data-rt-island]\");\n const tb = topBlock(el, s.anchorNode);\n const r = s.getRangeAt(0);\n const hasSel = !s.isCollapsed && !!r.toString().trim();\n const next: Fmt = {\n bold: queryState(\"bold\") && !/^H[1-6]$/.test(tb?.tagName ?? \"\"),\n italic: queryState(\"italic\"),\n underline: queryState(\"underline\"),\n strike: queryState(\"strikeThrough\"),\n // our own check: the base CSS resets sup/sub alignment, so the browser's own state for them always reads false\n sup: !!anchorEl?.closest(`sup:not(${FOOTNOTE_SUP})`),\n sub: !!anchorEl?.closest(\"sub\"),\n ul: !inIsland && tb?.tagName === \"UL\",\n ol: !inIsland && tb?.tagName === \"OL\",\n block: inIsland ? \"island\" : (tb?.tagName.toLowerCase() ?? \"p\"),\n hasSel,\n onLink: !!anchorEl?.closest(\"a\"),\n };\n setFmt((p) => (JSON.stringify(p) === JSON.stringify(next) ? p : next));\n setBubble(hasSel ? rangeRect(r, el) : null);\n el.querySelectorAll(\":scope > [data-hint]\").forEach((n) => (n !== tb || n.textContent) && n.removeAttribute(\"data-hint\"));\n if (tb && tb.tagName === \"P\" && s.isCollapsed && !tb.textContent && !tb.querySelector(\"img\") && document.activeElement === el && shortcutHintsOn()) tb.setAttribute(\"data-hint\", \"Type '/' for commands\");\n }, []);\n\n React.useEffect(() => {\n const on = () => refresh();\n // focus moving into another text field (the comment composer opening) fires no selectionchange: hide on focusin too\n const away = () => typingElsewhere(ref.current) && setBubble(null);\n document.addEventListener(\"selectionchange\", on);\n document.addEventListener(\"focusin\", away);\n return () => {\n document.removeEventListener(\"selectionchange\", on);\n document.removeEventListener(\"focusin\", away);\n };\n }, [refresh]);\n\n const run = (fn: () => void) => {\n restoreSel();\n fn();\n emit();\n refresh();\n };\n\n /* ── gutter ──────────────────────────────────────────────────────── */\n const placeGutter = (b: HTMLElement | null) => {\n const sc = scroller.current;\n if (!b || !sc) return setGutter(null);\n const sr = sc.getBoundingClientRect();\n const br = b.getBoundingClientRect();\n setGutter((g) => {\n const top = br.top - sr.top + sc.scrollTop;\n return g && g.el === b && g.top === top ? g : { el: b, top, height: br.height };\n });\n };\n const currentBlock = (): HTMLElement | null => {\n const el = ref.current;\n if (!el) return null;\n const s = window.getSelection();\n return topBlock(el, s && s.rangeCount && el.contains(s.anchorNode) ? s.anchorNode : document.activeElement);\n };\n\n /* ── block operations (DOM work lives in ./ops) ─────────── */\n const deleteBlock = (b: HTMLElement) => {\n const el = ref.current;\n if (!el || !el.contains(b)) return;\n const next = b.nextSibling;\n b.remove();\n let filler: HTMLElement | null = null;\n if (!el.firstElementChild) {\n filler = document.createElement(\"p\");\n filler.innerHTML = \"<br>\";\n el.append(filler);\n }\n setGutter(null);\n setBlockMenu(false);\n emit();\n notify(\"Block deleted\", {\n action: {\n label: \"Undo\",\n onClick: () => {\n const root = ref.current;\n if (!root) return;\n if (filler?.isConnected && !filler.textContent) filler.remove();\n if (next && next.parentNode === root) root.insertBefore(b, next);\n else root.append(b);\n emit();\n },\n },\n });\n };\n\n const duplicateBlock = (b: HTMLElement) => {\n const c = ops.duplicateBlock(b);\n emit();\n if (gutter) placeGutter(c);\n };\n\n const moveBlock = (b: HTMLElement, dir: -1 | 1) => {\n if (!ops.moveBlock(b, dir)) return;\n emit();\n if (gutter) requestAnimationFrame(() => placeGutter(b));\n };\n\n const turnInto = (b: HTMLElement | null, tag: string) => {\n const el = ref.current;\n if (el && ops.turnInto(el, b, tag)) emit();\n };\n\n const exitIsland = (x: HTMLElement) => {\n const el = ref.current;\n if (!el || !el.contains(x)) return;\n const next = ops.ensureLineAfter(x);\n el.focus({ preventScroll: true });\n placeCaret(next, false);\n emit();\n };\n\n const insertBlock = (it: CatalogItem) => {\n const el = ref.current;\n if (!el || readOnly) return;\n if (it.kind === \"component\" && it.component) {\n // V2 insert: a fresh linked instance, ONE undo step\n const c = it.component;\n noteRecent(it);\n const made: { el: IslandEl | null } = { el: null };\n oneStep(`Insert ${c.name}`, () => {\n const isl = (made.el = ops.insertIsland(el, \"component\", { ...defaultModel(\"component\"), ref: c.id, name: c.name }));\n emit();\n return isl;\n });\n refresh();\n // V2 insert: its properties open beside it, and the toast says what a shared component is\n if (made.el && services.useComponentInfo) openComponentPanel(made.el);\n services.toast?.(`${c.name} added`, { description: COMPONENT_INSERT_TOAST });\n return;\n }\n if (!it.id || !blockAllowed(it.id, allows)) return;\n noteRecent(it);\n ops.insertBasic(el, it.id);\n emit();\n refresh();\n };\n\n /* ── slash menu ──────────────────────────────────────────────────── */\n const slashCat = useCatalog(slash?.query ?? \"\", allows, slash?.folder ?? false, components ?? null);\n const caretRect = () => {\n const s = window.getSelection();\n if (!s || !s.rangeCount) return null;\n return rangeRect(s.getRangeAt(0), topBlock(ref.current, s.anchorNode) ?? ref.current);\n };\n const pickSlash = (it: CatalogItem) => {\n if (it.kind === \"folder\") return setSlash((s) => s && { ...s, folder: true, active: 1 });\n if (it.kind === \"back\") return setSlash((s) => s && { ...s, folder: false, active: 0 });\n const sl = slash;\n setSlash(null);\n if (sl) {\n try {\n const r = document.createRange();\n r.setStart(sl.node, sl.offset);\n r.setEnd(sl.node, Math.min(sl.node.length, sl.offset + 1 + sl.query.length));\n r.deleteContents();\n const c = document.createRange();\n c.setStart(sl.node, Math.min(sl.offset, sl.node.length));\n c.collapse(true);\n const s = window.getSelection();\n s?.removeAllRanges();\n s?.addRange(c);\n } catch {\n /* the text moved */\n }\n // A component is ONE step of the host's history, recorded from the body as it stands when the step starts: the\n // typed \"/query\" goes first, flushed, so an undo of the insert never brings it back as a paragraph.\n if (it.kind === \"component\") flushSync(() => emit());\n }\n insertBlock(it);\n };\n\n const toggleInlineCode = () => {\n const el = ref.current;\n const s = window.getSelection();\n if (!el || !s || !s.rangeCount || !allows(\"code\")) return;\n const anchorEl = s.anchorNode?.nodeType === 1 ? (s.anchorNode as HTMLElement) : s.anchorNode?.parentElement;\n const code = anchorEl?.closest(\"code\");\n if (code && el.contains(code) && !code.closest(\"pre\")) {\n code.replaceWith(...Array.from(code.childNodes));\n emit();\n return;\n }\n const text = s.toString();\n if (!text) return void notify(\"Select some text first\", { description: \"Or wrap words in backticks to format them as code.\" });\n insertHtmlAtCaret(`<code>${esc(text)}</code>`);\n emit();\n };\n\n /* ── keyboard ────────────────────────────────────────────────────── */\n const onKeyDown = (e: React.KeyboardEvent<HTMLDivElement>) => {\n if (slash) {\n if (e.key === \"Escape\") {\n e.preventDefault();\n e.stopPropagation();\n setSlash(slash.folder ? { ...slash, folder: false, active: 0 } : null);\n return;\n }\n if (catalogKey(e, slashCat.flat, slash.active, (a) => setSlash((s) => s && { ...s, active: a }), pickSlash, false)) {\n e.preventDefault();\n return;\n }\n }\n const mod = e.metaKey || e.ctrlKey;\n const k = eventKey(e);\n if (mod && !e.altKey && k === \"k\") {\n e.preventDefault();\n saveSel();\n openLink();\n return;\n }\n if (mod && !e.altKey && !e.shiftKey && k === \"e\") {\n e.preventDefault();\n toggleInlineCode();\n return;\n }\n // the browser's own mark shortcuts, only for the marks the field keeps\n if (mod && !e.altKey && !e.shiftKey && ((k === \"b\" && !allows(\"bold\")) || (k === \"i\" && !allows(\"italic\")) || (k === \"u\" && !allows(\"underline\")))) {\n e.preventDefault();\n return;\n }\n if (mod && e.altKey && /^Digit[0-6]$/.test(e.code)) {\n e.preventDefault();\n const n = Number(e.code.slice(5));\n const tag = n === 0 ? \"p\" : `h${n}`;\n if (tag === \"p\" || allows(tag as RichTextFeature)) turnInto(currentBlock(), tag);\n return;\n }\n if (e.key === \"Enter\" && !mod && !e.shiftKey) {\n // a one-paragraph field has no second block to start\n if (single) {\n e.preventDefault();\n return;\n }\n // Enter on an empty quote or heading line leaves it for a paragraph\n const cb = currentBlock();\n if (cb && /^(BLOCKQUOTE|H[1-6])$/.test(cb.tagName) && !cb.textContent?.replace(//g, \"\").trim()) {\n e.preventDefault();\n turnInto(cb, \"p\");\n return;\n }\n // Enter at the end of a quote starts a paragraph (not another quote)\n const sel = window.getSelection();\n if (cb?.tagName === \"BLOCKQUOTE\" && sel?.isCollapsed && sel.rangeCount && !cb.querySelector(\"p\")) {\n const rest = document.createRange();\n rest.selectNodeContents(cb);\n rest.setStart(sel.anchorNode!, sel.anchorOffset);\n if (!rest.toString().trim()) {\n e.preventDefault();\n const p = document.createElement(\"p\");\n p.innerHTML = \"<br>\";\n cb.after(p);\n placeCaret(p);\n emit();\n return;\n }\n }\n const s = window.getSelection();\n const pre = s?.anchorNode && (s.anchorNode.nodeType === 1 ? (s.anchorNode as HTMLElement) : s.anchorNode.parentElement)?.closest(\"pre\");\n if (pre && ref.current?.contains(pre)) {\n e.preventDefault();\n exec(\"insertLineBreak\");\n return;\n }\n }\n if (e.key === \"ArrowDown\" && !mod && !e.shiftKey && !single) {\n // leave a trailing heading / quote / code block / list\n const b = currentBlock();\n const s = window.getSelection();\n if (b && !b.nextElementSibling && b.tagName !== \"P\" && !b.hasAttribute(\"data-rt-island\") && s?.isCollapsed && s.rangeCount) {\n const rest = document.createRange();\n rest.selectNodeContents(b);\n rest.setStart(s.anchorNode!, s.anchorOffset);\n if (!rest.toString().trim()) {\n e.preventDefault();\n const p = ops.ensureLineAfter(b);\n placeCaret(p, false);\n emit();\n }\n }\n }\n };\n\n /** Block-level shortcuts; runs for the surface and for text inside rich blocks. */\n const onWrapKeyDown = (e: React.KeyboardEvent<HTMLDivElement>) => {\n if (e.defaultPrevented) return;\n const mod = e.metaKey || e.ctrlKey;\n if (mod && e.key === \"Enter\" && !hideFullscreen) {\n e.preventDefault();\n setModalOpen(true);\n return;\n }\n if (md || readOnly) return;\n const t = e.target as HTMLElement;\n if (!ref.current?.contains(t) || t.tagName === \"INPUT\" || t.tagName === \"TEXTAREA\") return;\n if (undoKey(e)) return;\n if (single) return;\n if (mod && !e.shiftKey && !e.altKey && eventKey(e) === \"d\") {\n e.preventDefault();\n const b = currentBlock();\n if (b) duplicateBlock(b);\n return;\n }\n if (mod && e.shiftKey && (e.key === \"ArrowUp\" || e.key === \"ArrowDown\")) {\n e.preventDefault();\n const b = currentBlock();\n if (b) moveBlock(b, e.key === \"ArrowUp\" ? -1 : 1);\n }\n };\n\n const onInput = (e: React.FormEvent<HTMLDivElement>) => {\n if (e.target !== ref.current) return;\n const ne = e.nativeEvent as InputEvent;\n if (ne.inputType !== \"historyUndo\" && ne.inputType !== \"historyRedo\") {\n hist.current.textAt = Date.now();\n hist.current.future = [];\n }\n if (!single && ne.inputType === \"insertText\" && (ne.data === \" \" || ne.data === \"-\") && ops.liveMarkdown(ref.current!, ne.data, allows)) {\n setSlash(null);\n emit();\n return;\n }\n if (ne.inputType === \"insertText\" && ne.data === \"`\" && allows(\"code\")) ops.liveInlineCode();\n emit();\n const s = window.getSelection();\n if (!s || !s.rangeCount) return setSlash(null);\n const r = s.getRangeAt(0);\n if (!slash) {\n // \"/\" opens the menu only at the very start of a block, and only in a field that takes more than one block\n if (single || ne.inputType !== \"insertText\" || ne.data !== \"/\" || r.startContainer.nodeType !== 3) return;\n const blk = closestBlock(ref.current!, r.startContainer);\n if (!blk || textBeforeCaret(blk) !== \"/\") return;\n const rect = caretRect();\n if (rect) setSlash({ rect, node: r.startContainer as Text, offset: r.startOffset - 1, query: \"\", folder: false, active: 0 });\n return;\n }\n if (r.startContainer !== slash.node || r.startOffset <= slash.offset || slash.node.data[slash.offset] !== \"/\") return setSlash(null);\n const q = slash.node.data.slice(slash.offset + 1, r.startOffset);\n if (/\\s/.test(q) || q.length > 24) return setSlash(null);\n setSlash({ ...slash, query: q, active: slash.folder ? 1 : 0 });\n };\n\n /* ── links ───────────────────────────────────────────────────────── */\n const openLink = () => {\n if (!allows(\"link\")) return;\n restoreSel();\n const s = window.getSelection();\n const anchorEl = s?.anchorNode?.nodeType === 1 ? (s.anchorNode as HTMLElement) : s?.anchorNode?.parentElement;\n const anchor = (anchorEl?.closest(\"a\") as HTMLAnchorElement | null) ?? null;\n if (!anchor && (!s || s.isCollapsed || !s.toString().trim())) {\n notify(\"Select some text first\", { description: hints ? \"Then press ⌘K to link it.\" : \"Then link it.\" });\n return;\n }\n const rect = s && s.rangeCount ? rangeRect(s.getRangeAt(0), ref.current) : ref.current!.getBoundingClientRect();\n setBubble(null);\n setLink({ rect, existing: anchor, initial: anchor ? { href: anchor.getAttribute(\"href\") ?? \"\", newTab: anchor.getAttribute(\"target\") === \"_blank\" } : { href: \"\" } });\n };\n const saveLink = (v: TextLink) => {\n const l = link;\n setLink(null);\n if (!l) return;\n if (l.existing) {\n l.existing.setAttribute(\"href\", v.href);\n if (v.newTab) l.existing.setAttribute(\"target\", \"_blank\");\n else l.existing.removeAttribute(\"target\");\n emit();\n return;\n }\n run(() => {\n const text = window.getSelection()?.toString() || v.href;\n insertHtmlAtCaret(`<a href=\"${esc(v.href).replace(/\"/g, \""\")}\"${v.newTab ? ` target=\"_blank\"` : \"\"}>${esc(text)}</a>`);\n });\n };\n\n /* ── AI rewrite of the selection (the host's service) ────────────── */\n const aiRewrite = (preset: AiPreset) => {\n const rewrite = services.aiRewrite;\n restoreSel();\n const range = saved.current?.cloneRange();\n const text = range?.toString() ?? \"\";\n if (!rewrite || !range || !text.trim()) return;\n setBubble(null);\n Promise.resolve()\n .then(() => rewrite(text, preset, aiAttempt.current++))\n .then(\n (out) => {\n const el = ref.current;\n if (!el || !el.contains(range.startContainer) || range.toString() !== text) {\n notify(\"The text changed before the rewrite came back\", { description: \"Nothing was replaced. Select it again to retry.\" });\n return;\n }\n el.focus({ preventScroll: true });\n const s = window.getSelection();\n s?.removeAllRanges();\n s?.addRange(range);\n insertTextAtCaret(out);\n emit();\n notify(\"Rewritten with AI\", { description: hints ? \"Press ⌘Z to undo\" : undefined });\n },\n (err: unknown) => notify(\"Could not rewrite the selection\", { description: err instanceof Error ? err.message : String(err) }),\n );\n };\n\n /* ── drag to reorder via the grip ────────────────────────────────── */\n const onGripDown = (e: React.PointerEvent) => {\n if (!gutter) return;\n startDrag(gutter.el, e, () => setBlockMenu(true));\n };\n /** Drag a top-level block (the gutter grip) to a new position; a tap calls `onTap`. */\n const startDrag = (from: HTMLElement, e: React.PointerEvent, onTap?: () => void) => {\n if (readOnly || e.button !== 0) return;\n e.preventDefault();\n const start = e.clientY;\n let moved = false;\n const kids = () => Array.from(ref.current?.children ?? []);\n const move = (ev: PointerEvent) => {\n if (!moved && Math.abs(ev.clientY - start) < 4) return;\n moved = true;\n const sc = scroller.current!;\n const sr = sc.getBoundingClientRect();\n let target: Element | null = null;\n let line = 0;\n for (const k of kids()) {\n const r = k.getBoundingClientRect();\n if (ev.clientY < r.top + r.height / 2) {\n target = k;\n line = r.top - sr.top + sc.scrollTop - 4;\n break;\n }\n line = r.bottom - sr.top + sc.scrollTop + 4;\n }\n setDrag({ from, line, target });\n };\n const up = () => {\n window.removeEventListener(\"pointermove\", move);\n window.removeEventListener(\"pointerup\", up);\n if (!moved) {\n onTap?.();\n return;\n }\n setDrag((d) => {\n if (d && d.target !== d.from) {\n if (d.target) d.target.before(d.from);\n else ref.current?.append(d.from);\n setTimeout(emit, 0);\n }\n return null;\n });\n };\n window.addEventListener(\"pointermove\", move);\n window.addEventListener(\"pointerup\", up);\n };\n\n /* ── pasted and converted markup keeps to the field's rules ──────── */\n const conform = (html: string): string => {\n const r = ops.restrictHtml(html, allows);\n if (r.dropped.length) notify(`This field keeps no ${r.dropped.join(\" or \")}`, { description: \"They were left out; the text around them was kept.\" });\n return r.html;\n };\n\n /* ── Markdown mode ───────────────────────────────────────────────── */\n const toggleMarkdown = () => {\n if (!md) {\n const html = ref.current ? serialize(ref.current) : value;\n const text = htmlToMarkdown(html);\n setMd({ text, original: text });\n setSlash(null);\n setGutter(null);\n setBubble(null);\n setLink(null);\n return;\n }\n if (md.text === md.original) {\n setMd(null);\n setMdConfirm(false);\n return;\n }\n setMdConfirm(true);\n };\n const convertMarkdown = () => {\n if (!md) return;\n let html: string;\n try {\n html = conform(markdownToHtml(md.text));\n } catch (err) {\n notify(\"Could not convert this Markdown\", { description: `${err instanceof Error ? err.message : String(err)}. Your rich text is unchanged.` });\n return;\n }\n pending.current = html;\n known.current = html;\n onChangeRef.current(html);\n setMd(null);\n setMdConfirm(false);\n };\n\n /* ── One undo history (CPO D54): typing is the browser's own undo; an island write (an image's address or alt text)\n is a step on this stack. ⌘Z takes whichever happened last. ── */\n /** A host step's undo or redo; its value then loads even here, with the caret in the editor. */\n const runHost = (run: () => true | string): true | string => {\n forceLoad.current = true;\n const r = run();\n if (r !== true) forceLoad.current = false;\n return r;\n };\n /**\n * This body's host step that is the host's next undo (or redo) NOW. The host's toolbar moves these steps too: after\n * its Undo then Redo, the step is the latest change again, so ⌘Z here undoes it. Any later change in this body is a\n * host step of its own (the body's value is the host's), so a host step that is next is the latest change here.\n */\n const hostNext = (way: \"undo\" | \"redo\"): HostStep | null => {\n const hs = hist.current.hosts;\n for (let i = hs.length - 1; i >= 0; i--) if (hs[i].step.next() === way) return hs[i];\n return null;\n };\n const islandUndo = (): boolean => {\n const host = hostNext(\"undo\");\n if (host) {\n const r = runHost(host.step.undo);\n if (r !== true) notify(\"Nothing was undone\", { description: r });\n return true;\n }\n const h = hist.current;\n // a step whose island is gone has nothing to undo\n while (h.past.length && !h.past[h.past.length - 1].el.isConnected) h.past.pop();\n const step = h.past[h.past.length - 1];\n if (!step || step.at < h.textAt) return false;\n if (!step.el.__rtSet) return false;\n h.past.pop();\n h.future.push({ ...step, before: step.el.__rt!, at: Date.now() });\n step.el.__rtSet(step.before);\n return true;\n };\n const islandRedo = (): boolean => {\n const host = hostNext(\"redo\");\n if (host) {\n const r = runHost(host.step.redo);\n if (r !== true) notify(\"Nothing was redone\", { description: r });\n return true;\n }\n const h = hist.current;\n const step = h.future.pop();\n if (!step || !step.el.isConnected || !step.el.__rtSet) return false;\n h.past.push({ ...step, before: step.el.__rt!, at: Date.now() });\n step.el.__rtSet(step.before);\n return true;\n };\n /**\n * One action as ONE undo step (a separate copy, \"use shared version again\", a component inserted): in the host's\n * history when it keeps one (KitServices.historyStep: its toolbar Undo, an Undo toast and ⌘Z here are the same\n * undo), else in this editor's own (`before`: the model the island had; an insert has none, and stays as undoable\n * as any block inserted here). `write` makes the change and answers the island it changed. Answers its undo.\n */\n const oneStep = (label: string, write: () => IslandEl | null, before?: IslandModels[IslandKind]): (() => true | string) => {\n const h = hist.current;\n const made: { el: IslandEl | null } = { el: null };\n const historyStep = services.historyStep;\n const step = historyStep\n ? historyStep(() => {\n made.el = write();\n })\n : ((made.el = write()), null);\n const el = made.el;\n if (step) {\n h.hosts = [...h.hosts, { label, step }].slice(-100);\n return () => runHost(step.undo);\n }\n if (!el || !before) return () => \"This change has no undo step here.\";\n const s: IslandStep = { el, before, label, at: Date.now() };\n h.past = [...h.past, s].slice(-100);\n h.future = [];\n return () => {\n if (!h.past.includes(s)) return \"It was undone already.\";\n if (h.past[h.past.length - 1] !== s || s.at < h.textAt) return \"Changes made after it come first. Press ⌘Z to undo them.\";\n return islandUndo() ? true : \"The block was removed, so there is nothing to undo.\";\n };\n };\n const record = (el: IslandEl, before: IslandModels[IslandKind], label: string, coalesce?: boolean) => {\n const h = hist.current;\n const now = Date.now();\n const top = h.past[h.past.length - 1];\n // typing in one field coalesces (~500ms), unless the text was edited in between\n if (coalesce && top && top.el === el && top.label === label && now - top.at < 500 && top.at > h.textAt) top.at = now;\n else h.past = [...h.past, { el, before, label, at: now }].slice(-100);\n h.future = [];\n };\n const undoKey = (e: React.KeyboardEvent): boolean => {\n const mod = e.metaKey || e.ctrlKey;\n if (!mod || e.altKey || eventKey(e) !== \"z\") return false;\n if (e.shiftKey) {\n if (!islandRedo()) return false;\n e.preventDefault();\n return true;\n }\n if (islandUndo()) {\n e.preventDefault();\n return true;\n }\n if (!hist.current.past.length || !ref.current) return false;\n e.preventDefault();\n const before = ref.current.innerHTML;\n exec(\"undo\");\n if (ref.current.innerHTML === before) {\n hist.current.textAt = 0;\n islandUndo();\n }\n return true;\n };\n\n /* ── API for islands (stable) ────────────────────────────────────── */\n const api = React.useRef({ emit, deleteBlock, exitIsland, record, oneStep, notify, duplicateBlock, moveBlock, islandUndo, islandRedo, startDrag });\n api.current = { emit, deleteBlock, exitIsland, record, oneStep, notify, duplicateBlock, moveBlock, islandUndo, islandRedo, startDrag };\n const islandCtx = React.useMemo<IslandCtx>(\n () => ({\n readOnly,\n dense,\n emit: () => api.current.emit(),\n remove: (x) => api.current.deleteBlock(x),\n exit: (x) => api.current.exitIsland(x),\n record: (x, before, label, coalesce) => api.current.record(x, before, label, coalesce),\n step: (label, write, before) => api.current.oneStep(label, write, before),\n notify: (message, description) => api.current.notify(message, { description }),\n duplicate: (x) => api.current.duplicateBlock(x),\n move: (x, dir) => api.current.moveBlock(x, dir),\n undo: () => api.current.islandUndo(),\n redo: () => api.current.islandRedo(),\n drag: (x, e) => api.current.startDrag(x, e),\n }),\n [readOnly, dense],\n );\n\n const commentSel = onComment\n ? () => {\n restoreSel();\n const q = window.getSelection()?.toString().trim();\n // the comment popover takes over: the selection toolbar steps away so it never sits on the composer\n setBubble(null);\n setQuiet(true);\n if (q) onComment(q);\n }\n : undefined;\n const onMark = (cmd: MarkCmd) =>\n allows(MARK_FEATURE[cmd]) &&\n run(() =>\n cmd === \"superscript\" || cmd === \"subscript\" ? ref.current && toggleScript(ref.current, cmd === \"superscript\" ? \"sup\" : \"sub\") : exec(cmd),\n );\n const onStyle = (tag: string) => {\n restoreSel();\n turnInto(currentBlock(), tag);\n refresh();\n };\n\n /* ── render ──────────────────────────────────────────────────────── */\n const { flipUp, maxHeight: slashMaxH } = slash ? slashPlacement(slash.rect, window.innerHeight) : { flipUp: false, maxHeight: SLASH_MENU_H };\n const gBlock = gutter?.el;\n const gIsText = !!gBlock && !gBlock.hasAttribute(\"data-rt-island\") && gBlock.tagName !== \"HR\";\n const btn = dense ? \"size-5 [&_svg:not([data-rt-isolate]_*)]:size-3.5\" : \"size-[22px] [&_svg:not([data-rt-isolate]_*)]:size-3.5\";\n /* outside: + and grip float left of the box · inset: a slim grip sits in the 16px padding (insert via / or the\n toolbar) · none: compact inspector fields and one-paragraph fields */\n const gutterMode: \"outside\" | \"inset\" | \"none\" = readOnly || dense || single ? \"none\" : gutterRoom ? \"outside\" : \"inset\";\n const showGutter = gutterMode !== \"none\";\n const minH = expanded ? \"min-h-[60vh]\" : single ? \"min-h-9\" : dense ? \"min-h-[120px]\" : \"min-h-[190px]\";\n const turnStyles = stylesFor(allows).filter((s) => [\"p\", \"h1\", \"h2\", \"h3\", \"blockquote\"].includes(s.tag));\n\n return (\n <CatalogComponentsProvider value={components ?? null}>\n <div\n ref={wrap}\n data-rt-editor=\"\"\n className={cn(\n \"relative [--rt-toolbar-h:2rem] pointer-coarse:[--rt-toolbar-h:2.75rem]\",\n \"rounded-kit-lg border transition-colors duration-150\",\n /* the expanded modal is raised: the editor sits level with it, never below (D56) */\n expanded ? \"bg-[var(--kit-surface-raised)]\" : \"bg-kit-surface\",\n /* V2 rich-text-editor.tsx:1152: line at rest, line-strong while the toolbar is open; an invalid value (dash) keeps its edge */\n invalid ? \"border-[var(--kit-field-invalid)]\" : toolbarOpen ? \"border-kit-line-strong\" : \"border-kit-line\",\n )}\n /* what the sticky toolbar covers at the top of the scroll area */\n style={{ \"--rt-sticky-top\": toolbarOpen && !dense ? `calc(${stickyTop}px + var(--rt-toolbar-h))` : \"var(--kit-sticky-top, 0px)\" } as React.CSSProperties}\n onMouseLeave={() => !blockMenu && !gutterInsert && !drag && setGutter(null)}\n onKeyDown={onWrapKeyDown}\n onFocus={() => {\n window.clearTimeout(blurTimer.current);\n setFocused(true);\n }}\n onBlur={() => {\n window.clearTimeout(blurTimer.current);\n blurTimer.current = window.setTimeout(() => {\n const a = document.activeElement;\n if (wrap.current?.contains(a) || a?.closest(\"[role=menu],[role=dialog],[role=listbox],[data-floating-layer]\")) return;\n setFocused(false);\n setBubble(null);\n ref.current?.querySelectorAll(\"[data-hint]\").forEach((n) => n.removeAttribute(\"data-hint\"));\n if (valueRef.current !== known.current && !md) load(valueRef.current);\n }, 400);\n }}\n >\n {readOnly ? null : (\n <FormatToolbar\n open={toolbarOpen}\n sticky={!dense}\n stickyTop={stickyTop}\n width={width}\n dense={dense}\n fmt={fmt}\n md={!!md}\n allows={allows}\n hideFullscreen={hideFullscreen}\n insertOpen={insertOpen}\n setInsertOpen={(o) => {\n if (o) inserted.current = false;\n setInsertOpen(o);\n }}\n onMenuOpen={(name, o) => setMenus((m) => ({ ...m, [name]: o }))}\n onStyle={onStyle}\n onMark={onMark}\n onList={(kind) =>\n allows(kind) &&\n run(() => {\n // Chrome nests the list inside a heading/quote (<h2><ul>…) — turn the line into a paragraph first.\n const b = currentBlock();\n if (b && /^(H[1-6]|BLOCKQUOTE)$/.test(b.tagName)) turnInto(b, \"p\");\n exec(kind === \"ul\" ? \"insertUnorderedList\" : \"insertOrderedList\");\n // …and it can still leave <p><ul>…</ul></p>; lift the list out of any text block.\n ref.current?.querySelectorAll(\":is(p,h1,h2,h3,h4,h5,h6,blockquote) > :is(ul,ol)\").forEach((list) => {\n const host = list.parentElement!;\n host.replaceWith(...Array.from(host.childNodes).filter((n) => n.nodeType === 1 || n.textContent?.trim()));\n });\n })\n }\n onLink={openLink}\n onClear={() =>\n run(() => {\n exec(\"removeFormat\");\n exec(\"unlink\");\n })\n }\n onComment={commentSel}\n onInlineCode={() => {\n restoreSel();\n toggleInlineCode();\n }}\n onCodeBlock={() => {\n restoreSel();\n if (allows(\"pre\")) turnInto(currentBlock(), \"pre\");\n }}\n onInsert={(it) => {\n inserted.current = true;\n restoreSel();\n insertBlock(it);\n setInsertOpen(false);\n }}\n keepFocusOnInsertClose={() => inserted.current}\n onFullscreen={() => setModalOpen(true)}\n onMarkdown={toggleMarkdown}\n saveSel={saveSel}\n />\n )}\n\n {md ? (\n <div className=\"px-3 pb-2.5 pt-2.5\">\n <Textarea\n aria-label=\"Field content as Markdown\"\n spellCheck={false}\n value={md.text}\n readOnly={readOnly}\n onChange={(e) => {\n setMd({ ...md, text: e.target.value });\n setMdConfirm(false);\n }}\n className={cn(\"font-kit-mono text-kit-xs leading-5\", expanded ? \"min-h-[60vh]\" : dense ? \"min-h-[120px]\" : \"min-h-[190px]\")}\n style={scrollable ? { maxHeight } : undefined}\n />\n <p className=\"mt-1.5 text-kit-2xs text-kit-fg-3\">Markdown. Switching back converts it to blocks.</p>\n <AnimatePresence initial={false}>\n {mdConfirm ? (\n <motion.div\n key=\"confirm\"\n initial={{ opacity: 0, y: reduceMotion ? 0 : 4 }}\n animate={{ opacity: 1, y: 0 }}\n exit={{ opacity: 0, y: reduceMotion ? 0 : 4 }}\n transition={{ duration: 0.15 }}\n role=\"alertdialog\"\n aria-label=\"Convert edited Markdown?\"\n className=\"mt-2 flex flex-wrap items-center gap-2 rounded-kit-lg border border-kit-line bg-kit-subtle px-3 py-2\"\n >\n <span className=\"flex-1 text-kit-sm font-medium text-kit-fg\">Convert edited Markdown?</span>\n <Button size=\"xs\" variant=\"ghost\" onClick={() => setMdConfirm(false)}>\n Keep editing Markdown\n </Button>\n <Button size=\"xs\" variant=\"primary\" autoFocus onClick={convertMarkdown}>\n Convert to rich text\n </Button>\n </motion.div>\n ) : null}\n </AnimatePresence>\n </div>\n ) : (\n <div\n ref={scroller}\n className={cn(\"relative\", scrollable && \"overflow-y-auto\")}\n style={scrollable ? { maxHeight } : undefined}\n onMouseMove={(e) => {\n if (drag || blockMenu || gutterInsert || !showGutter) return;\n const t = e.target as HTMLElement;\n if (t.closest(\"[data-rt-gutter]\")) return;\n const b = topBlock(ref.current, t);\n // a component card carries its own handle and ⋯ menu (V2 rich-text-editor.tsx:1297-1298): no second grip beside it\n placeGutter(b?.getAttribute(\"data-rt-island\") === \"component\" ? null : b);\n }}\n >\n <div\n ref={ref}\n id={inModal ? undefined : id}\n role=\"textbox\"\n aria-multiline={!single}\n aria-labelledby={!inModal && id ? `${id}-label` : undefined}\n aria-label=\"Rich text\"\n aria-placeholder={ph}\n aria-readonly={readOnly || undefined}\n aria-invalid={invalid || undefined}\n contentEditable={!readOnly}\n suppressContentEditableWarning\n spellCheck\n tabIndex={readOnly ? 0 : undefined}\n onInput={onInput}\n onKeyDown={onKeyDown}\n onKeyUp={refresh}\n onMouseUp={refresh}\n onPaste={(e) => {\n if (readOnly) return;\n const files = Array.from(e.clipboardData.files).filter((f) => f.type.startsWith(\"image/\"));\n if (files.length) {\n e.preventDefault();\n notify(allows(\"image\") ? \"Add images from the media library\" : \"This field keeps no images\", {\n description: allows(\"image\") ? \"A pasted file has no address the page can show it from. Use Insert › Image.\" : undefined,\n });\n return;\n }\n const text = e.clipboardData.getData(\"text/plain\");\n e.preventDefault();\n if (!text) return;\n if (single || (!/\\n/.test(text.trim()) && !looksLikeMarkdown(text))) {\n insertTextAtCaret(single ? text.replace(/\\s*\\n\\s*/g, \" \") : text);\n emit();\n return;\n }\n let html: string;\n try {\n html = markdownToHtml(text);\n } catch {\n html = text.split(/\\n{2,}/).map((p) => `<p>${esc(p.trim()).replace(/\\n/g, \"<br>\")}</p>`).join(\"\");\n }\n insertHtmlAtCaret(conform(html));\n if (ref.current) hydrate(ref.current);\n emit();\n }}\n onDragOver={(e) => {\n if (e.dataTransfer.types.includes(\"application/x-bcms-asset\") && allows(\"image\")) e.preventDefault();\n }}\n onDrop={(e) => {\n const asset = e.dataTransfer.getData(\"application/x-bcms-asset\");\n if (!asset || readOnly || !allows(\"image\")) return;\n e.preventDefault();\n try {\n const a = JSON.parse(asset) as { url: string; alt?: string; name: string };\n const b = topBlock(ref.current, e.target as Node);\n const isl = createIsland(\"image\", defaultModel(\"image\", { src: a.url, alt: a.alt ?? \"\" }));\n if (b) b.after(isl);\n else ref.current?.append(isl);\n ops.ensureLineAfter(isl);\n emit();\n } catch {\n notify(\"That drop is not an image from the media library\");\n }\n }}\n className={cn(\n RT_PROSE,\n dense && RT_PANEL,\n \"peer relative outline-none focus-visible:shadow-none [&_*:not([data-rt-isolate]_*)]:outline-none\",\n \"[&>p[data-hint]]:before:pointer-events-none [&>p[data-hint]]:before:float-left [&>p[data-hint]]:before:h-0 [&>p[data-hint]]:before:text-kit-fg-4 [&>p[data-hint]]:before:content-[attr(data-hint)]\",\n \"[&_a[data-button]:not([data-rt-isolate]_*)]:cursor-pointer [&_ul[data-task]>li:not([data-rt-isolate]_*)]:before:cursor-pointer\",\n \"[&_sup[data-rt=fn]]:mx-px [&_sup[data-rt=fn]]:cursor-pointer [&_sup[data-rt=fn]]:rounded-kit-sm [&_sup[data-rt=fn]]:px-0.5 [&_sup[data-rt=fn]]:text-[0.72em] [&_sup[data-rt=fn]]:font-semibold [&_sup[data-rt=fn]]:text-kit-accent-fg [&_sup[data-rt=fn]:hover]:bg-kit-accent-soft\",\n dense ? \"px-2.5 py-2\" : \"px-4 py-3.5\",\n minH,\n )}\n />\n {empty ? (\n <div aria-hidden className={cn(\"pointer-events-none absolute text-kit-fg-4 peer-focus:hidden\", dense ? \"text-kit-sm\" : \"text-kit-base\", dense ? \"left-2.5 top-2\" : \"left-4 top-3.5\")}>\n {ph}\n </div>\n ) : null}\n\n {/* Block gutter (+ / grip) */}\n {gutter && showGutter ? (\n <div\n data-rt-gutter=\"\"\n /* z-3: under the sticky toolbar (z-4), so a tall block's grip never paints over it */\n className={cn(\"absolute z-[3] flex items-start\", gutterMode === \"outside\" ? \"-left-12 pr-1\" : \"left-0\")}\n style={{ top: gutter.top + Math.max(-2, Math.min(4, gutter.height / 2 - 12)) }}\n >\n {gutterMode === \"outside\" ? (\n <Popover\n open={gutterInsert}\n onOpenChange={(o) => {\n if (o) {\n gutterTarget.current = gutter.el;\n inserted.current = false;\n }\n setGutterInsert(o);\n }}\n >\n <Tooltip content=\"Add a block below\" disabled={gutterInsert}>\n <PopoverTrigger\n aria-label=\"Add a block below\"\n className={cn(\"flex items-center justify-center rounded-kit-md text-kit-fg-3 hover:bg-kit-hover hover:text-kit-fg data-[popup-open]:bg-kit-hover data-[popup-open]:text-kit-fg\", btn)}\n >\n <IconPlus stroke={1.5} aria-hidden />\n </PopoverTrigger>\n </Tooltip>\n {gutterInsert ? (\n <InsertMenuContent\n side=\"bottom\"\n align=\"start\"\n allows={allows}\n keepFocusOnClose={() => inserted.current}\n onInsert={(it) => {\n const b = gutterTarget.current;\n const el = ref.current;\n inserted.current = true;\n setGutterInsert(false);\n if (!b || !el || !el.contains(b)) return;\n const p = document.createElement(\"p\");\n p.innerHTML = \"<br>\";\n b.after(p);\n el.focus({ preventScroll: true });\n placeCaret(p);\n insertBlock(it);\n }}\n />\n ) : null}\n </Popover>\n ) : null}\n <Menu open={blockMenu} onOpenChange={setBlockMenu}>\n <Tooltip content=\"Drag to move, click for options\" disabled={blockMenu || !!drag}>\n <MenuTrigger\n aria-label=\"Block options\"\n onPointerDown={onGripDown}\n onKeyDown={(e) => {\n if (e.key === \"Enter\" || e.key === \" \") {\n e.preventDefault();\n setBlockMenu(true);\n }\n }}\n className={cn(\n \"flex cursor-grab items-center justify-center rounded-kit-md text-kit-fg-3 hover:bg-kit-hover hover:text-kit-fg active:cursor-grabbing\",\n gutterMode === \"inset\" ? \"h-[22px] w-4 rounded-kit-sm [&_svg:not([data-rt-isolate]_*)]:size-3.5\" : btn,\n (blockMenu || drag) && \"bg-kit-hover text-kit-fg\",\n )}\n >\n <IconGripVertical stroke={1.5} aria-hidden />\n </MenuTrigger>\n </Tooltip>\n <MenuContent className=\"w-56\" align=\"start\" finalFocus={false}>\n {turnStyles.length > 1 ? (\n <MenuSub>\n <MenuSubTrigger icon={<IconTransform stroke={1.5} />} disabled={!gIsText}>\n Turn into\n </MenuSubTrigger>\n <MenuSubContent className=\"w-48\">\n {turnStyles.map((t) => (\n <MenuItem key={t.tag} icon={t.icon} onClick={() => turnInto(gBlock ?? null, t.tag)}>\n {t.label}\n </MenuItem>\n ))}\n </MenuSubContent>\n </MenuSub>\n ) : null}\n <MenuItem icon={<IconCopy stroke={1.5} />} shortcut=\"⌘D\" onClick={() => gBlock && duplicateBlock(gBlock)}>\n Duplicate\n </MenuItem>\n <MenuItem icon={<IconArrowBarToUp stroke={1.5} />} shortcut=\"⌘⇧↑\" disabled={!gBlock?.previousElementSibling} onClick={() => gBlock && moveBlock(gBlock, -1)}>\n Move up\n </MenuItem>\n <MenuItem icon={<IconArrowBarToDown stroke={1.5} />} shortcut=\"⌘⇧↓\" disabled={!gBlock?.nextElementSibling} onClick={() => gBlock && moveBlock(gBlock, 1)}>\n Move down\n </MenuItem>\n <MenuSeparator />\n <MenuItem danger icon={<IconTrash stroke={1.5} />} onClick={() => gBlock && deleteBlock(gBlock)}>\n Delete\n </MenuItem>\n </MenuContent>\n </Menu>\n </div>\n ) : null}\n {drag?.line != null ? <div className=\"pointer-events-none absolute inset-x-3 z-[6] h-0.5 rounded-full bg-kit-info\" style={{ top: drag.line }} /> : null}\n\n {/* Rich blocks render into their contenteditable=false hosts */}\n {islands.map(({ id: key, el }) => createPortal(<Island el={el} ctx={islandCtx} />, el, key))}\n </div>\n )}\n\n {/* Footer meta (V2 rich-text-editor.tsx:1563-1571), and any refusal said in place when the host has no toaster */}\n <div className=\"flex h-7 items-center justify-end gap-3 rounded-b-kit-lg border-t border-kit-line-subtle px-3 text-kit-2xs text-kit-fg-3\">\n {notice ? (\n <span role=\"status\" aria-live=\"polite\" className=\"mr-auto min-w-0 truncate text-kit-fg-2\">\n {notice.message}\n {notice.description ? ` ${notice.description}` : \"\"}\n {notice.action ? (\n <button\n type=\"button\"\n className=\"ml-1.5 font-medium text-kit-fg underline underline-offset-2\"\n onClick={() => {\n notice.action!.onClick();\n setNotice(null);\n }}\n >\n {notice.action.label}\n </button>\n ) : null}\n </span>\n ) : null}\n <span className=\"tabular-nums\">\n {words.toLocaleString(\"en-US\")} {words === 1 ? \"word\" : \"words\"}\n {comps ? ` · ${comps} ${comps === 1 ? \"block\" : \"blocks\"}` : \"\"} · {Math.max(1, Math.round(words / 220))} min read\n </span>\n </div>\n\n {/* Bubble toolbar on selection: a toolbar menu owns the moment, so the bubble steps aside while one is open */}\n {bubble && !quiet && !readOnly && !slash && !link && !md && !menus.style && !menus.more && !insertOpen ? (\n <SelectionBubble\n rect={bubble}\n avoid={toolbarOpen ? wrap.current?.querySelector<HTMLElement>('[role=\"toolbar\"][aria-label=\"Text formatting\"]')?.getBoundingClientRect() : null}\n fmt={fmt}\n allows={allows}\n saveSel={saveSel}\n onAi={canAI ? aiRewrite : undefined}\n onStyle={onStyle}\n onMark={onMark}\n onInlineCode={() => {\n restoreSel();\n toggleInlineCode();\n }}\n onLink={openLink}\n onComment={commentSel}\n />\n ) : null}\n\n {/* Slash menu (opens only at the start of a block; never takes focus) */}\n {slash && !md\n ? createPortal(\n <>\n <div data-floating-layer=\"\" className=\"pointer-events-auto fixed inset-0 z-[var(--kit-z-popover,84)]\" onMouseDown={() => setSlash(null)} />\n <motion.div\n initial={{ opacity: 0, y: flipUp ? -4 : 4 }}\n animate={{ opacity: 1, y: 0 }}\n transition={{ duration: 0.14 }}\n style={{\n left: Math.min(window.innerWidth - 330, Math.max(8, slash.rect.left)),\n ...(flipUp ? { bottom: window.innerHeight - slash.rect.top + 6 } : { top: slash.rect.bottom + 6 }),\n }}\n data-floating-layer=\"\"\n className=\"pointer-events-auto fixed z-[calc(var(--kit-z-popover,84)_+_1)]\"\n >\n <SlashMenuPanel query={slash.query} folder={slash.folder} active={slash.active} allows={allows} setActive={(a) => setSlash((s) => s && { ...s, active: a })} onPick={pickSlash} maxHeight={slashMaxH} />\n </motion.div>\n </>,\n document.body,\n )\n : null}\n\n {/* Link popover anchored to the selection */}\n <Popover open={!!link} onOpenChange={(o) => !o && setLink(null)}>\n <PopoverAnchor\n render={<span className=\"pointer-events-none fixed\" style={link ? { top: link.rect.bottom, left: link.rect.left, width: Math.max(1, link.rect.width), height: 1 } : { top: 0, left: 0 }} />}\n />\n <PopoverContent className=\"w-[340px] rounded-kit-lg p-3\" finalFocus={false}>\n {link ? (\n <div className=\"flex flex-col gap-2\">\n <LinkForm\n initial={link.initial}\n allowNewTab={allowNewTab}\n onSave={saveLink}\n onCancel={() => setLink(null)}\n onDetach={\n link.existing\n ? () => {\n const a = link.existing!;\n a.replaceWith(...Array.from(a.childNodes));\n setLink(null);\n emit();\n }\n : undefined\n }\n />\n </div>\n ) : null}\n </PopoverContent>\n </Popover>\n {!hideFullscreen ? (\n <ExpandedEditorModal open={modalOpen} onOpenChange={setModalOpen} crumbs={expandCrumbs?.length ? expandCrumbs : [\"Text\"]} returnFocus={() => ref.current} meta={bodyCountLabel(value)}>\n {modalOpen ? (\n <RichTextEditor\n value={value}\n onChange={onChange}\n readOnly={readOnly}\n placeholder={placeholder}\n docKey={`${docKey}:expanded`}\n features={features}\n single={single}\n allowNewTab={allowNewTab}\n expandCrumbs={expandCrumbs}\n variant=\"document\"\n hideFullscreen\n inModal\n autoFocus\n onComment={onComment}\n components={components}\n />\n ) : null}\n </ExpandedEditorModal>\n ) : null}\n </div>\n </CatalogComponentsProvider>\n );\n}\n\n"],"mappings":"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"}
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* RICH TEXT · the selection bubble: AI rewrite, style, marks, link (V2 HEAD controls/rich-text/floating.tsx).
|
|
3
|
+
* V2's inline "Ask AI" prompt took free text; the host's AI service rewrites by preset only, so it is not drawn.
|
|
4
|
+
*/
|
|
5
|
+
import * as React from "react";
|
|
6
|
+
import type { AiPreset } from "../../context";
|
|
7
|
+
import type { RichTextFeature } from "./codec";
|
|
8
|
+
import { type Fmt, type MarkCmd } from "./toolbar";
|
|
9
|
+
/** The bubble's rewrite directions (V2: improve, shorter, punchier, grammar), as the host service's presets. */
|
|
10
|
+
export declare const BUBBLE_AI: {
|
|
11
|
+
id: AiPreset;
|
|
12
|
+
label: string;
|
|
13
|
+
}[];
|
|
14
|
+
export declare function SelectionBubble({ rect, fmt, allows, saveSel, onAi, onStyle, onMark, onInlineCode, onLink, onComment, avoid, }: {
|
|
15
|
+
rect: DOMRect;
|
|
16
|
+
/** The editor's own toolbar row (when it is open): the bubble never sits on top of it. */
|
|
17
|
+
avoid?: DOMRect | null;
|
|
18
|
+
fmt: Fmt;
|
|
19
|
+
allows: (f: RichTextFeature) => boolean;
|
|
20
|
+
saveSel: () => void;
|
|
21
|
+
/** Absent when the person has no AI (D58: ai.use) or the host has no AI service: the AI menu and its divider are not drawn. */
|
|
22
|
+
onAi?: (preset: AiPreset) => void;
|
|
23
|
+
onStyle: (tag: string) => void;
|
|
24
|
+
onMark: (cmd: MarkCmd) => void;
|
|
25
|
+
onInlineCode: () => void;
|
|
26
|
+
onLink: () => void;
|
|
27
|
+
onComment?: () => void;
|
|
28
|
+
}): React.ReactPortal;
|
|
@@ -0,0 +1,154 @@
|
|
|
1
|
+
import { Sparkle } from "../../ui/button.js";
|
|
2
|
+
import { Menu, MenuContent, MenuItem, MenuTrigger } from "../../ui/overlay.js";
|
|
3
|
+
import { StyleMenu, ToolButton, stylesFor } from "./toolbar.js";
|
|
4
|
+
import * as React from "react";
|
|
5
|
+
import { Fragment, jsx, jsxs } from "react/jsx-runtime";
|
|
6
|
+
import { IconBold, IconCode, IconItalic, IconLink, IconMessage, IconStrikethrough, IconSubscript, IconSuperscript, IconUnderline } from "@tabler/icons-react";
|
|
7
|
+
import { createPortal } from "react-dom";
|
|
8
|
+
//#region src/controls/rich-text/floating.tsx
|
|
9
|
+
/**
|
|
10
|
+
* RICH TEXT · the selection bubble: AI rewrite, style, marks, link (V2 HEAD controls/rich-text/floating.tsx).
|
|
11
|
+
* V2's inline "Ask AI" prompt took free text; the host's AI service rewrites by preset only, so it is not drawn.
|
|
12
|
+
*/
|
|
13
|
+
/** The bubble's rewrite directions (V2: improve, shorter, punchier, grammar), as the host service's presets. */
|
|
14
|
+
var BUBBLE_AI = [
|
|
15
|
+
{
|
|
16
|
+
id: "improve",
|
|
17
|
+
label: "Improve writing"
|
|
18
|
+
},
|
|
19
|
+
{
|
|
20
|
+
id: "shorter",
|
|
21
|
+
label: "Make shorter"
|
|
22
|
+
},
|
|
23
|
+
{
|
|
24
|
+
id: "simplify",
|
|
25
|
+
label: "Simplify"
|
|
26
|
+
},
|
|
27
|
+
{
|
|
28
|
+
id: "grammar",
|
|
29
|
+
label: "Fix spelling and grammar"
|
|
30
|
+
}
|
|
31
|
+
];
|
|
32
|
+
function SelectionBubble({ rect, fmt, allows, saveSel, onAi, onStyle, onMark, onInlineCode, onLink, onComment, avoid }) {
|
|
33
|
+
const above = rect.top - 44;
|
|
34
|
+
const top = above < 8 || !!avoid && above < avoid.bottom + 4 && above + 36 > avoid.top ? rect.bottom + 8 : above;
|
|
35
|
+
const styles = stylesFor(allows);
|
|
36
|
+
const ref = React.useRef(null);
|
|
37
|
+
const [w, setW] = React.useState(460);
|
|
38
|
+
React.useLayoutEffect(() => {
|
|
39
|
+
if (ref.current) setW(ref.current.offsetWidth);
|
|
40
|
+
}, [
|
|
41
|
+
fmt.block,
|
|
42
|
+
!!onAi,
|
|
43
|
+
!!onComment
|
|
44
|
+
]);
|
|
45
|
+
return createPortal(/* @__PURE__ */ jsxs("div", {
|
|
46
|
+
onMouseDown: (e) => {
|
|
47
|
+
if (!e.target.closest("button")) e.preventDefault();
|
|
48
|
+
},
|
|
49
|
+
ref,
|
|
50
|
+
style: {
|
|
51
|
+
top,
|
|
52
|
+
boxShadow: "var(--kit-shadow-sm)",
|
|
53
|
+
left: Math.min(window.innerWidth - w - 8, Math.max(8, rect.left + rect.width / 2 - w / 2))
|
|
54
|
+
},
|
|
55
|
+
"data-floating-layer": "",
|
|
56
|
+
"data-kit-scope": "",
|
|
57
|
+
className: "glass-strong pointer-events-auto fixed z-[calc(var(--kit-z-popover,84)_+_1)] flex h-9 items-center gap-0.5 rounded-kit-lg border border-kit-line px-1",
|
|
58
|
+
role: "toolbar",
|
|
59
|
+
"aria-label": "Selection formatting",
|
|
60
|
+
children: [
|
|
61
|
+
onAi ? /* @__PURE__ */ jsxs(Fragment, { children: [/* @__PURE__ */ jsxs(Menu, { children: [/* @__PURE__ */ jsxs(MenuTrigger, {
|
|
62
|
+
onMouseDown: (e) => {
|
|
63
|
+
e.preventDefault();
|
|
64
|
+
saveSel();
|
|
65
|
+
},
|
|
66
|
+
className: "flex h-7 items-center gap-1.5 rounded-kit-md px-2 text-kit-sm text-kit-fg hover:bg-kit-hover data-[popup-open]:bg-kit-hover",
|
|
67
|
+
children: [/* @__PURE__ */ jsx(Sparkle, { size: 14 }), " Improve writing"]
|
|
68
|
+
}), /* @__PURE__ */ jsx(MenuContent, {
|
|
69
|
+
className: "w-52",
|
|
70
|
+
finalFocus: false,
|
|
71
|
+
children: BUBBLE_AI.map((p) => /* @__PURE__ */ jsx(MenuItem, {
|
|
72
|
+
icon: /* @__PURE__ */ jsx(Sparkle, { size: 16 }),
|
|
73
|
+
onClick: () => onAi(p.id),
|
|
74
|
+
children: p.label
|
|
75
|
+
}, p.id))
|
|
76
|
+
})] }), /* @__PURE__ */ jsx("span", {
|
|
77
|
+
"aria-hidden": true,
|
|
78
|
+
className: "mx-0.5 h-4 w-px bg-kit-line"
|
|
79
|
+
})] }) : null,
|
|
80
|
+
fmt.block !== "island" && styles.length > 1 ? /* @__PURE__ */ jsxs(Fragment, { children: [/* @__PURE__ */ jsx(StyleMenu, {
|
|
81
|
+
block: fmt.block,
|
|
82
|
+
styles,
|
|
83
|
+
onPick: onStyle
|
|
84
|
+
}), /* @__PURE__ */ jsx("span", {
|
|
85
|
+
"aria-hidden": true,
|
|
86
|
+
className: "mx-0.5 h-4 w-px bg-kit-line"
|
|
87
|
+
})] }) : null,
|
|
88
|
+
allows("bold") ? /* @__PURE__ */ jsx(ToolButton, {
|
|
89
|
+
label: "Bold",
|
|
90
|
+
icon: /* @__PURE__ */ jsx(IconBold, { stroke: 1.5 }),
|
|
91
|
+
shortcut: "⌘B",
|
|
92
|
+
active: fmt.bold,
|
|
93
|
+
onClick: () => onMark("bold")
|
|
94
|
+
}) : null,
|
|
95
|
+
allows("italic") ? /* @__PURE__ */ jsx(ToolButton, {
|
|
96
|
+
label: "Italic",
|
|
97
|
+
icon: /* @__PURE__ */ jsx(IconItalic, { stroke: 1.5 }),
|
|
98
|
+
shortcut: "⌘I",
|
|
99
|
+
active: fmt.italic,
|
|
100
|
+
onClick: () => onMark("italic")
|
|
101
|
+
}) : null,
|
|
102
|
+
allows("underline") ? /* @__PURE__ */ jsx(ToolButton, {
|
|
103
|
+
label: "Underline",
|
|
104
|
+
icon: /* @__PURE__ */ jsx(IconUnderline, { stroke: 1.5 }),
|
|
105
|
+
shortcut: "⌘U",
|
|
106
|
+
active: fmt.underline,
|
|
107
|
+
onClick: () => onMark("underline")
|
|
108
|
+
}) : null,
|
|
109
|
+
allows("strike") ? /* @__PURE__ */ jsx(ToolButton, {
|
|
110
|
+
label: "Strikethrough",
|
|
111
|
+
icon: /* @__PURE__ */ jsx(IconStrikethrough, { stroke: 1.5 }),
|
|
112
|
+
active: fmt.strike,
|
|
113
|
+
onClick: () => onMark("strikeThrough")
|
|
114
|
+
}) : null,
|
|
115
|
+
allows("sup") ? /* @__PURE__ */ jsx(ToolButton, {
|
|
116
|
+
label: "Superscript",
|
|
117
|
+
icon: /* @__PURE__ */ jsx(IconSuperscript, { stroke: 1.5 }),
|
|
118
|
+
active: fmt.sup,
|
|
119
|
+
onClick: () => onMark("superscript")
|
|
120
|
+
}) : null,
|
|
121
|
+
allows("sub") ? /* @__PURE__ */ jsx(ToolButton, {
|
|
122
|
+
label: "Subscript",
|
|
123
|
+
icon: /* @__PURE__ */ jsx(IconSubscript, { stroke: 1.5 }),
|
|
124
|
+
active: fmt.sub,
|
|
125
|
+
onClick: () => onMark("subscript")
|
|
126
|
+
}) : null,
|
|
127
|
+
allows("code") ? /* @__PURE__ */ jsx(ToolButton, {
|
|
128
|
+
label: "Inline code",
|
|
129
|
+
icon: /* @__PURE__ */ jsx(IconCode, { stroke: 1.5 }),
|
|
130
|
+
shortcut: "⌘E",
|
|
131
|
+
onClick: onInlineCode
|
|
132
|
+
}) : null,
|
|
133
|
+
allows("link") ? /* @__PURE__ */ jsx(ToolButton, {
|
|
134
|
+
label: "Link",
|
|
135
|
+
icon: /* @__PURE__ */ jsx(IconLink, { stroke: 1.5 }),
|
|
136
|
+
shortcut: "⌘K",
|
|
137
|
+
active: fmt.onLink,
|
|
138
|
+
onClick: onLink
|
|
139
|
+
}) : null,
|
|
140
|
+
onComment ? /* @__PURE__ */ jsxs(Fragment, { children: [/* @__PURE__ */ jsx("span", {
|
|
141
|
+
"aria-hidden": true,
|
|
142
|
+
className: "mx-0.5 h-4 w-px bg-kit-line"
|
|
143
|
+
}), /* @__PURE__ */ jsx(ToolButton, {
|
|
144
|
+
label: "Comment",
|
|
145
|
+
icon: /* @__PURE__ */ jsx(IconMessage, { stroke: 1.5 }),
|
|
146
|
+
onClick: onComment
|
|
147
|
+
})] }) : null
|
|
148
|
+
]
|
|
149
|
+
}), document.body);
|
|
150
|
+
}
|
|
151
|
+
//#endregion
|
|
152
|
+
export { BUBBLE_AI, SelectionBubble };
|
|
153
|
+
|
|
154
|
+
//# sourceMappingURL=floating.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"floating.js","names":[],"sources":["../../../src/controls/rich-text/floating.tsx"],"sourcesContent":["/**\n * RICH TEXT · the selection bubble: AI rewrite, style, marks, link (V2 HEAD controls/rich-text/floating.tsx).\n * V2's inline \"Ask AI\" prompt took free text; the host's AI service rewrites by preset only, so it is not drawn.\n */\nimport * as React from \"react\";\nimport { createPortal } from \"react-dom\";\nimport { IconBold, IconCode, IconItalic, IconLink, IconMessage, IconStrikethrough, IconSubscript, IconSuperscript, IconUnderline } from \"@tabler/icons-react\";\nimport { Sparkle } from \"../../ui/button\";\nimport { Menu, MenuContent, MenuItem, MenuTrigger } from \"../../ui/overlay\";\nimport type { AiPreset } from \"../../context\";\nimport type { RichTextFeature } from \"./codec\";\nimport { StyleMenu, ToolButton, stylesFor, type Fmt, type MarkCmd } from \"./toolbar\";\n\n/** The bubble's rewrite directions (V2: improve, shorter, punchier, grammar), as the host service's presets. */\nexport const BUBBLE_AI: { id: AiPreset; label: string }[] = [\n { id: \"improve\", label: \"Improve writing\" },\n { id: \"shorter\", label: \"Make shorter\" },\n { id: \"simplify\", label: \"Simplify\" },\n { id: \"grammar\", label: \"Fix spelling and grammar\" },\n];\n\nexport function SelectionBubble({\n rect,\n fmt,\n allows,\n saveSel,\n onAi,\n onStyle,\n onMark,\n onInlineCode,\n onLink,\n onComment,\n avoid,\n}: {\n rect: DOMRect;\n /** The editor's own toolbar row (when it is open): the bubble never sits on top of it. */\n avoid?: DOMRect | null;\n fmt: Fmt;\n allows: (f: RichTextFeature) => boolean;\n saveSel: () => void;\n /** Absent when the person has no AI (D58: ai.use) or the host has no AI service: the AI menu and its divider are not drawn. */\n onAi?: (preset: AiPreset) => void;\n onStyle: (tag: string) => void;\n onMark: (cmd: MarkCmd) => void;\n onInlineCode: () => void;\n onLink: () => void;\n onComment?: () => void;\n}) {\n // Above the selection by default; flips below it when above would cover the editor's toolbar or leave the viewport.\n const above = rect.top - 44;\n const blocked = above < 8 || (!!avoid && above < avoid.bottom + 4 && above + 36 > avoid.top);\n const top = blocked ? rect.bottom + 8 : above;\n const styles = stylesFor(allows);\n // centre on the selection with the bubble's real width (it grows with AI, style and comment), never past either edge\n const ref = React.useRef<HTMLDivElement>(null);\n const [w, setW] = React.useState(460);\n React.useLayoutEffect(() => {\n if (ref.current) setW(ref.current.offsetWidth);\n }, [fmt.block, !!onAi, !!onComment]);\n return createPortal(\n // No entrance motion: the bubble shows on every text selection, a 100+/day action.\n <div\n onMouseDown={(e) => {\n if (!(e.target as HTMLElement).closest(\"button\")) e.preventDefault();\n }}\n ref={ref}\n style={{ top, boxShadow: \"var(--kit-shadow-sm)\", left: Math.min(window.innerWidth - w - 8, Math.max(8, rect.left + rect.width / 2 - w / 2)) }}\n data-floating-layer=\"\"\n data-kit-scope=\"\"\n /* V2 floating.tsx:57-59: glass-strong for the raised fill and hairline; the tight shadow-sm (inline, so it beats the\n glass drop) keeps the shadow off the selected text right under the bubble */\n className=\"glass-strong pointer-events-auto fixed z-[calc(var(--kit-z-popover,84)_+_1)] flex h-9 items-center gap-0.5 rounded-kit-lg border border-kit-line px-1\"\n role=\"toolbar\"\n aria-label=\"Selection formatting\"\n >\n {onAi ? (\n <>\n <Menu>\n <MenuTrigger\n onMouseDown={(e) => {\n e.preventDefault();\n saveSel();\n }}\n className=\"flex h-7 items-center gap-1.5 rounded-kit-md px-2 text-kit-sm text-kit-fg hover:bg-kit-hover data-[popup-open]:bg-kit-hover\"\n >\n <Sparkle size={14} /> Improve writing\n </MenuTrigger>\n <MenuContent className=\"w-52\" finalFocus={false}>\n {BUBBLE_AI.map((p) => (\n <MenuItem key={p.id} icon={<Sparkle size={16} />} onClick={() => onAi(p.id)}>\n {p.label}\n </MenuItem>\n ))}\n </MenuContent>\n </Menu>\n <span aria-hidden className=\"mx-0.5 h-4 w-px bg-kit-line\" />\n </>\n ) : null}\n {fmt.block !== \"island\" && styles.length > 1 ? (\n <>\n <StyleMenu block={fmt.block} styles={styles} onPick={onStyle} />\n <span aria-hidden className=\"mx-0.5 h-4 w-px bg-kit-line\" />\n </>\n ) : null}\n {allows(\"bold\") ? <ToolButton label=\"Bold\" icon={<IconBold stroke={1.5} />} shortcut=\"⌘B\" active={fmt.bold} onClick={() => onMark(\"bold\")} /> : null}\n {allows(\"italic\") ? <ToolButton label=\"Italic\" icon={<IconItalic stroke={1.5} />} shortcut=\"⌘I\" active={fmt.italic} onClick={() => onMark(\"italic\")} /> : null}\n {allows(\"underline\") ? <ToolButton label=\"Underline\" icon={<IconUnderline stroke={1.5} />} shortcut=\"⌘U\" active={fmt.underline} onClick={() => onMark(\"underline\")} /> : null}\n {allows(\"strike\") ? <ToolButton label=\"Strikethrough\" icon={<IconStrikethrough stroke={1.5} />} active={fmt.strike} onClick={() => onMark(\"strikeThrough\")} /> : null}\n {/* x² and x₂: one at a time (picking one inside the other swaps them) */}\n {allows(\"sup\") ? <ToolButton label=\"Superscript\" icon={<IconSuperscript stroke={1.5} />} active={fmt.sup} onClick={() => onMark(\"superscript\")} /> : null}\n {allows(\"sub\") ? <ToolButton label=\"Subscript\" icon={<IconSubscript stroke={1.5} />} active={fmt.sub} onClick={() => onMark(\"subscript\")} /> : null}\n {allows(\"code\") ? <ToolButton label=\"Inline code\" icon={<IconCode stroke={1.5} />} shortcut=\"⌘E\" onClick={onInlineCode} /> : null}\n {allows(\"link\") ? <ToolButton label=\"Link\" icon={<IconLink stroke={1.5} />} shortcut=\"⌘K\" active={fmt.onLink} onClick={onLink} /> : null}\n {onComment ? (\n <>\n <span aria-hidden className=\"mx-0.5 h-4 w-px bg-kit-line\" />\n <ToolButton label=\"Comment\" icon={<IconMessage stroke={1.5} />} onClick={onComment} />\n </>\n ) : null}\n </div>,\n document.body,\n );\n}\n"],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import { ACTIONS, CONTROLS } from "../../engine/kit-field.js";
|
|
2
|
+
import { RichTextControl, RichTextExpandAction } from "./control.js";
|
|
3
|
+
//#region src/controls/rich-text/index.ts
|
|
4
|
+
/**
|
|
5
|
+
* Rich text: registers the control and its label-row action (one line each, so lanes merge cleanly).
|
|
6
|
+
* Imported for its side effect by whatever loads the kit's controls; import the parts themselves by path.
|
|
7
|
+
*/
|
|
8
|
+
CONTROLS.richtext = RichTextControl;
|
|
9
|
+
ACTIONS.richtext = RichTextExpandAction;
|
|
10
|
+
//#endregion
|
|
11
|
+
|
|
12
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","names":[],"sources":["../../../src/controls/rich-text/index.ts"],"sourcesContent":["/**\n * Rich text: registers the control and its label-row action (one line each, so lanes merge cleanly).\n * Imported for its side effect by whatever loads the kit's controls; import the parts themselves by path.\n */\nimport { ACTIONS, CONTROLS } from \"../../engine/kit-field\";\nimport { RichTextControl, RichTextExpandAction } from \"./control\";\n\nCONTROLS.richtext = RichTextControl;\nACTIONS.richtext = RichTextExpandAction;\n"],"mappings":";;;;;;;AAOA,SAAS,WAAW;AACpB,QAAQ,WAAW"}
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
export interface TextLink {
|
|
2
|
+
href: string;
|
|
3
|
+
newTab?: boolean;
|
|
4
|
+
}
|
|
5
|
+
/** An address a link may carry: http(s), mailto, tel, a site path or an in-page anchor. */
|
|
6
|
+
export declare function linkProblem(href: string): string | null;
|
|
7
|
+
export declare function LinkForm({ initial, allowNewTab, onSave, onCancel, onDetach, }: {
|
|
8
|
+
initial: TextLink;
|
|
9
|
+
allowNewTab: boolean;
|
|
10
|
+
onSave: (v: TextLink) => void;
|
|
11
|
+
onCancel: () => void;
|
|
12
|
+
onDetach?: () => void;
|
|
13
|
+
}): import("react/jsx-runtime").JSX.Element;
|