efficient-easel 21.1.0 → 22.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 +27 -34
- package/dist/{CanvasDragLayer-CFUcBbgc.d.ts → CanvasDragLayer-B6Yn9S8T.d.ts} +4 -4
- package/dist/{ScreenDocumentContext-1RgtGKWR.d.ts → ScreenDocumentContext-BIK3uWtF.d.ts} +4 -4
- package/dist/blocks/index.d.ts +16 -18
- package/dist/{buckets-Sw94ll9I.d.ts → buckets-_MGDYJlb.d.ts} +1 -1
- package/dist/canvas/index.d.ts +8 -10
- package/dist/canvas/index.js +1 -1
- package/dist/{chunk-2L6KWUBC.js → chunk-4LGROS5L.js} +1 -1
- package/dist/{chunk-WJJ7H42G.js → chunk-CUZQ2HMA.js} +15 -15
- package/dist/chunk-GHBK7BKL.js +1 -0
- package/dist/{chunk-MLQKNED6.js → chunk-IROEWITG.js} +1 -1
- package/dist/{chunk-YVFYWAYU.js → chunk-IYYE7VJN.js} +30 -30
- package/dist/chunk-KN2TIXUT.js +1 -0
- package/dist/{chunk-GWYNMSIP.js → chunk-RY5AWQ63.js} +1 -1
- package/dist/chunk-SJMS247S.js +5 -0
- package/dist/{chunk-DNQ7AF6K.js → chunk-TLN5ZT76.js} +1 -1
- package/dist/chunk-TXR7GC5A.js +8 -0
- package/dist/{chunk-U5DNBT63.js → chunk-UMBNBCL4.js} +1 -1
- package/dist/{chunk-TUXLORVR.js → chunk-WJSEWAWK.js} +13 -13
- package/dist/{chunk-I67UW5UG.js → chunk-XWKQP6AE.js} +1 -1
- package/dist/{chunk-U7TFWHST.js → chunk-YC6KLSW3.js} +1 -1
- package/dist/{chunk-PFFH7ASD.js → chunk-YHFKWV7H.js} +13 -13
- package/dist/copy/index.d.ts +2 -2
- package/dist/copy/index.js +11 -11
- package/dist/data/index.d.ts +21 -21
- package/dist/drag/index.d.ts +5 -5
- package/dist/drag/index.js +1 -1
- package/dist/draw/index.d.ts +1 -1
- package/dist/easel/easel.css +5 -7
- package/dist/easel/index.d.ts +57 -57
- package/dist/easel/index.js +1 -1
- package/dist/edit-lock/index.d.ts +5 -5
- package/dist/fields/fields.css +1 -1
- package/dist/fields/index.d.ts +17 -17
- package/dist/fields/index.js +1 -1
- package/dist/node-ops/index.d.ts +3 -3
- package/dist/panel/index.d.ts +4 -4
- package/dist/panel/panel.css +1 -1
- package/dist/{plan-CZS902DV.d.ts → plan-CRUh2kVK.d.ts} +5 -5
- package/dist/render/index.d.ts +19 -19
- package/dist/render/index.js +5 -5
- package/dist/{repeat-BNgSq2Nw.d.ts → repeat-D65bJS8d.d.ts} +1 -1
- package/dist/{resolve-D68pb3Bx.d.ts → resolve-AJ6WF4EL.d.ts} +5 -5
- package/dist/screen/components/AddBlockRow.js +1 -1
- package/dist/screen/components/AddSidePanel.d.ts +2 -2
- package/dist/screen/components/AddSidePanel.js +1 -1
- package/dist/screen/components/NodeContextMenu.d.ts +11 -11
- package/dist/screen/components/NodeContextMenu.js +1 -1
- package/dist/screen/components/PreviewDeviceContext.d.ts +1 -1
- package/dist/screen/components/PreviewPartsContext.d.ts +2 -2
- package/dist/screen/components/SaveControls.d.ts +8 -8
- package/dist/screen/components/ScreenChrome.js +1 -1
- package/dist/screen/components/ScreenDocumentContext.d.ts +5 -5
- package/dist/screen/components/ScreenMount.d.ts +8 -8
- package/dist/screen/components/ScreenMount.js +1 -1
- package/dist/screen/components/ScreenStoreProvider.d.ts +12 -12
- package/dist/screen/components/ScreenStoreProvider.js +1 -1
- package/dist/screen/components/SectionScreenShell.js +17 -17
- package/dist/screen/components/usePartBridge.d.ts +10 -10
- package/dist/screen/components/usePartBridge.js +1 -1
- package/dist/screen/index.d.ts +8 -8
- package/dist/screen/index.js +1 -1
- package/dist/screen/lib/admin-bridge.d.ts +4 -4
- package/dist/screen/lib/document/add-target-types.js +0 -1
- package/dist/screen/lib/document/content-tree.d.ts +7 -7
- package/dist/screen/lib/document/device-fields.d.ts +7 -7
- package/dist/screen/lib/document/field-buckets.d.ts +1 -1
- package/dist/screen/lib/document/field-markers.d.ts +5 -5
- package/dist/screen/lib/document/palette-sections.d.ts +5 -5
- package/dist/screen/lib/document/panel-fields.d.ts +6 -6
- package/dist/screen/lib/document/panel-no-control-mark.d.ts +4 -5
- package/dist/screen/lib/document/part-id.d.ts +1 -1
- package/dist/screen/lib/document/preview-events.d.ts +2 -2
- package/dist/screen/lib/document/preview-selection-context.d.ts +2 -2
- package/dist/screen/lib/document/section-doc.d.ts +5 -5
- package/dist/screen/lib/document/slot-child-name.d.ts +1 -1
- package/dist/screen/lib/document/slot-section-spec.d.ts +1 -1
- package/dist/screen/lib/document/slot-section-spec.js +0 -1
- package/dist/screen/lib/document/style-clipboard.d.ts +8 -8
- package/dist/screen/lib/document/tree-reveal.d.ts +6 -6
- package/dist/screen/lib/document/tree-reveal.js +1 -1
- package/dist/screen/lib/document/use-section-ops.d.ts +6 -6
- package/dist/screen/lib/document/use-section-ops.js +1 -1
- package/dist/screen/lib/document-addressing.d.ts +5 -5
- package/dist/screen/lib/document-hooks.d.ts +4 -4
- package/dist/screen/lib/host.d.ts +5 -5
- package/dist/screen/lib/key-scope.d.ts +1 -1
- package/dist/screen/lib/key-scope.js +1 -1
- package/dist/screen/lib/media-panel.d.ts +5 -5
- package/dist/screen/lib/media-picker.d.ts +6 -6
- package/dist/screen/lib/page-lock.d.ts +4 -4
- package/dist/screen/lib/screen-parts.d.ts +13 -16
- package/dist/screen/lib/screen-parts.js +1 -1
- package/dist/screen/lib/section-templates.d.ts +4 -4
- package/dist/screen/lib/session-context.d.ts +4 -4
- package/dist/screen/lib/session.d.ts +5 -5
- package/dist/screen/lib/shared-sections.d.ts +4 -4
- package/dist/screen/screen.css +15 -15
- package/dist/{session-DSQFmIvx.d.ts → session-CrWwDt7Z.d.ts} +1 -1
- package/dist/strings/index.d.ts +2 -2
- package/dist/strings/index.js +1 -1
- package/dist/style-clipboard/index.d.ts +2 -2
- package/dist/text-styles/index.js +21 -21
- package/dist/{types-B8NwXKlE.d.ts → types-BFd8FqQw.d.ts} +3 -3
- package/dist/{types-Cq53lL8d.d.ts → types-DFxBChE3.d.ts} +18 -18
- package/dist/{types-41704JE4.d.ts → types-DlQIM1YO.d.ts} +8 -8
- package/dist/{useNodeOps-fIDWzftn.d.ts → useNodeOps-C_nisDHh.d.ts} +2 -2
- package/dist/{watch-D8xZow3y.d.ts → watch-D0bNZRtU.d.ts} +3 -3
- package/dist/{words-CmEnDoOe.d.ts → words-fbR9IwxH.d.ts} +1 -1
- package/package.json +3 -147
- package/dist/chunk-2C7W64S5.js +0 -8
- package/dist/chunk-4FD7TAOE.js +0 -1
- package/dist/chunk-67HCYOW4.js +0 -1
- package/dist/chunk-A2VVB4RH.js +0 -0
- package/dist/chunk-OHZHYROJ.js +0 -5
- package/dist/chunk-PRHBWA5V.js +0 -0
- package/dist/chunk-YIUE4US7.js +0 -0
- package/dist/screen/lib/puck/add-target-types.d.ts +0 -3
- package/dist/screen/lib/puck/add-target-types.js +0 -1
- package/dist/screen/lib/puck/block-choice.d.ts +0 -1
- package/dist/screen/lib/puck/block-choice.js +0 -1
- package/dist/screen/lib/puck/block-types-in.d.ts +0 -1
- package/dist/screen/lib/puck/block-types-in.js +0 -1
- package/dist/screen/lib/puck/content-tree.d.ts +0 -1
- package/dist/screen/lib/puck/content-tree.js +0 -1
- package/dist/screen/lib/puck/device-fields.d.ts +0 -4
- package/dist/screen/lib/puck/device-fields.js +0 -1
- package/dist/screen/lib/puck/field-buckets.d.ts +0 -2
- package/dist/screen/lib/puck/field-buckets.js +0 -1
- package/dist/screen/lib/puck/field-markers.d.ts +0 -2
- package/dist/screen/lib/puck/field-markers.js +0 -1
- package/dist/screen/lib/puck/hidable.d.ts +0 -1
- package/dist/screen/lib/puck/hidable.js +0 -1
- package/dist/screen/lib/puck/palette-sections.d.ts +0 -8
- package/dist/screen/lib/puck/palette-sections.js +0 -1
- package/dist/screen/lib/puck/panel-fields.d.ts +0 -1
- package/dist/screen/lib/puck/panel-fields.js +0 -1
- package/dist/screen/lib/puck/panel-no-control-mark.d.ts +0 -2
- package/dist/screen/lib/puck/panel-no-control-mark.js +0 -1
- package/dist/screen/lib/puck/part-id.d.ts +0 -1
- package/dist/screen/lib/puck/part-id.js +0 -1
- package/dist/screen/lib/puck/preview-click.d.ts +0 -1
- package/dist/screen/lib/puck/preview-click.js +0 -1
- package/dist/screen/lib/puck/preview-dom.d.ts +0 -1
- package/dist/screen/lib/puck/preview-dom.js +0 -1
- package/dist/screen/lib/puck/preview-events.d.ts +0 -1
- package/dist/screen/lib/puck/preview-events.js +0 -1
- package/dist/screen/lib/puck/preview-selection-context.d.ts +0 -2
- package/dist/screen/lib/puck/preview-selection-context.js +0 -1
- package/dist/screen/lib/puck/section-doc.d.ts +0 -9
- package/dist/screen/lib/puck/section-doc.js +0 -1
- package/dist/screen/lib/puck/slot-child-name.d.ts +0 -1
- package/dist/screen/lib/puck/slot-child-name.js +0 -1
- package/dist/screen/lib/puck/slot-heal.d.ts +0 -2
- package/dist/screen/lib/puck/slot-heal.js +0 -1
- package/dist/screen/lib/puck/slot-section-spec.d.ts +0 -1
- package/dist/screen/lib/puck/slot-section-spec.js +0 -1
- package/dist/screen/lib/puck/style-clipboard.d.ts +0 -42
- package/dist/screen/lib/puck/style-clipboard.js +0 -1
- package/dist/screen/lib/puck/text-control-kinds.d.ts +0 -1
- package/dist/screen/lib/puck/text-control-kinds.js +0 -1
- package/dist/screen/lib/puck/tree-reveal.d.ts +0 -1
- package/dist/screen/lib/puck/tree-reveal.js +0 -1
- package/dist/screen/lib/puck/use-section-ops.d.ts +0 -9
- package/dist/screen/lib/puck/use-section-ops.js +0 -1
package/README.md
CHANGED
|
@@ -7,7 +7,7 @@ what a section is, and each editor brings its own blocks and its own data.
|
|
|
7
7
|
The EFFICIENT editors' shared engine and chrome — the campaign designer
|
|
8
8
|
(`efficient-admin-portal`) and the website editor (`efficient-storefront`) draw from
|
|
9
9
|
one source instead of hand-rolling and drifting — and the engine both run on,
|
|
10
|
-
which replaced
|
|
10
|
+
which replaced the open-source editor library the two editors began on, layer by layer, and has carried none of
|
|
11
11
|
it since 0.93.0.
|
|
12
12
|
|
|
13
13
|
> **Published as `efficient-easel`** on public npm from 0.96.0 (it was
|
|
@@ -61,7 +61,7 @@ down too.
|
|
|
61
61
|
|
|
62
62
|
## Why
|
|
63
63
|
|
|
64
|
-
The storefront editor (`efficient-storefront`, Next 16
|
|
64
|
+
The storefront editor (`efficient-storefront`, Next 16) and the campaign
|
|
65
65
|
designer (`efficient-admin-portal`, Vite/React) each hand-rolled their own narrow
|
|
66
66
|
left icon-rail. They had already drifted — button 34px vs 36px, icon 18px vs
|
|
67
67
|
20px, radius 9 vs 8, a CSS-var accent vs a Tailwind one. `EaselRail` is the one
|
|
@@ -425,14 +425,14 @@ unknown pastes only between two components of the same type. An empty
|
|
|
425
425
|
## The document — `efficient-easel/data`
|
|
426
426
|
|
|
427
427
|
`efficient-easel/data` (added in 0.67.0) is the bottom layer of the engine that
|
|
428
|
-
replaces
|
|
428
|
+
replaces the old editor (the blueprint's step 1.1): the saved document as pure
|
|
429
429
|
functions. It imports nothing and touches no browser global, so the editor's
|
|
430
430
|
store, a Next server component, a Node script and a test all call the same
|
|
431
431
|
code.
|
|
432
432
|
|
|
433
433
|
**The format does not change.** A document is exactly what Puck 0.20 saves —
|
|
434
434
|
`{ root: { props }, content: [...], zones: {} }`, with a block's children
|
|
435
|
-
inline in its slot props — so no campaign or page migrates when
|
|
435
|
+
inline in its slot props — so no campaign or page migrates when the old editor goes.
|
|
436
436
|
|
|
437
437
|
```ts
|
|
438
438
|
import { normalizeData, find, insert, move, remove, duplicate, setProps, setRoot, createNode, walk, ROOT_LIST } from 'efficient-easel/data';
|
|
@@ -447,15 +447,15 @@ next = setProps(next, config, id, { level: 3 });
|
|
|
447
447
|
|
|
448
448
|
| Export | Notes |
|
|
449
449
|
|---|---|
|
|
450
|
-
| `normalizeData(data, config)` |
|
|
450
|
+
| `normalizeData(data, config)` | the old editor's load: missing top-level slots become `[]`, `zones` becomes `{}`, the root's `defaultProps` fill what is missing. Older formats (props written on `root`, children parked in `zones`) are converted the way the old editor's `migrate()` converts them. **A document already in shape comes back as the same object.** |
|
|
451
451
|
| `find`, `walk`, `slotsOf`, `getList` | Read. `walk` visits parent before children, slots in declaration order; returning a node from the visitor replaces it. |
|
|
452
|
-
| `insert`, `move`, `remove`, `duplicate` | Change the tree. `move` within one list takes the index AFTER the move (
|
|
452
|
+
| `insert`, `move`, `remove`, `duplicate` | Change the tree. `move` within one list takes the index AFTER the move (the old editor's rule). |
|
|
453
453
|
| `setProps`, `setRoot` | Merge props. A key keeps its place; a patch that changes nothing returns the same document. |
|
|
454
454
|
| `createNode(config, type, props?)`, `newId(type)` | A new block the way the Add panel makes one: `{ ...defaultProps, id }`, ids `<Type>-<uuid>`. |
|
|
455
|
-
| `zoneKey`, `parseZoneKey`, `ROOT_LIST` | A place is `{ parentId, slot, index }`; the top-level list is `{ parentId: 'root', slot: 'default-zone' }` — the two halves of
|
|
455
|
+
| `zoneKey`, `parseZoneKey`, `ROOT_LIST` | A place is `{ parentId, slot, index }`; the top-level list is `{ parentId: 'root', slot: 'default-zone' }` — the two halves of the old editor's zone key. |
|
|
456
456
|
|
|
457
457
|
`config` is the app's block config: only `fields` (which props are slots, including
|
|
458
|
-
slots inside `object` / `array` fields) and `defaultProps` are read, so
|
|
458
|
+
slots inside `object` / `array` fields) and `defaultProps` are read, so an old editor
|
|
459
459
|
`Config` works as it is. A type the config does not know is kept whole.
|
|
460
460
|
|
|
461
461
|
Every edit copies only the path to the change, so an untouched block is the
|
|
@@ -566,11 +566,11 @@ base words under a translation, markers on untranslated rows). Routing and
|
|
|
566
566
|
`efficient-easel/blocks` (added in 0.92.0) holds the types a block is written
|
|
567
567
|
with: Puck 0.20's `Config`, `ComponentConfig`, `Fields`, `Field`,
|
|
568
568
|
`CustomField`, `ComponentData`, `Data`, `Slot` and `SlotComponent`, with the
|
|
569
|
-
same generics. An app that typed its blocks with
|
|
569
|
+
same generics. An app that typed its blocks with the old editor's imports them from here
|
|
570
570
|
instead, and no block changes. It is types only: nothing in it exists at
|
|
571
571
|
runtime. One key is the engine's own: `translatable` on a field (0.97.0),
|
|
572
572
|
which says whether the prop is written again per language (the translation
|
|
573
|
-
overlay, above). It is optional, so a field written for
|
|
573
|
+
overlay, above). It is optional, so a field written for the old editor is still a field.
|
|
574
574
|
|
|
575
575
|
```ts
|
|
576
576
|
import type { Config, CustomField, Slot } from 'efficient-easel/blocks';
|
|
@@ -591,9 +591,9 @@ const config: Config<{ Hero: HeroProps }> = {
|
|
|
591
591
|
## The published renderer — `efficient-easel/render`
|
|
592
592
|
|
|
593
593
|
`efficient-easel/render` (added in 0.68.0) draws a saved document the way the
|
|
594
|
-
published site does — the drop-in for
|
|
594
|
+
published site does — the drop-in for the old editor's `<Render>` (the blueprint's step
|
|
595
595
|
1.2). Same config, same document, **the same HTML**: the specs hold it to
|
|
596
|
-
Puck 0.20.2's markup, recorded from
|
|
596
|
+
Puck 0.20.2's markup, recorded from the old editor's own `<Render>`, byte for byte.
|
|
597
597
|
|
|
598
598
|
```tsx
|
|
599
599
|
import { Render } from 'efficient-easel/render';
|
|
@@ -603,28 +603,21 @@ import { Render } from 'efficient-easel/render';
|
|
|
603
603
|
|
|
604
604
|
It is a plain function: **no hook, no context, no `'use client'`**. It runs in a
|
|
605
605
|
server component, a client component or a script, and `Render(props)` called
|
|
606
|
-
directly returns the element tree. (
|
|
606
|
+
directly returns the element tree. (The old editor's reads the document from a context
|
|
607
607
|
and builds props in hooks, so it only runs as a client component.) Whether the
|
|
608
608
|
blocks themselves can run on the server is up to the blocks.
|
|
609
609
|
|
|
610
|
-
The block authoring shape is
|
|
611
|
-
block's `render` gets its props, `editor
|
|
612
|
-
value), and each slot as a component —
|
|
610
|
+
The block authoring shape is the old editor's, so an app passes the config it has: a
|
|
611
|
+
block's `render` gets its props, `editor`, and each slot as a component —
|
|
613
612
|
`render: ({ content: Content }) => <Content className="grid" />` — which draws
|
|
614
613
|
`<div className style>` around its blocks. The top-level list is wrapped in one
|
|
615
|
-
plain `<div>`, and `editor` carries exactly what
|
|
616
|
-
|
|
614
|
+
plain `<div>`, and `editor` carries exactly what the old editor's client `<Render>` gave
|
|
615
|
+
a block at each level. A type the config does not know draws nothing.
|
|
617
616
|
|
|
618
|
-
**
|
|
619
|
-
|
|
620
|
-
|
|
621
|
-
|
|
622
|
-
|---|---|
|
|
623
|
-
| block prop `puck` (types: `WithBlockProps`) | `editor` — the same value |
|
|
624
|
-
| `efficient-easel/screen/lib/puck/*` (24 subpaths) | `efficient-easel/screen/lib/document/*` — the old ones re-export the new |
|
|
625
|
-
| `data-puck-component`, `data-puck-dropzone`, `data-puck-entry`, `data-puck-dnd`, `data-puck-preview` | `data-easel-block`, `data-easel-dropzone`, `data-easel-entry`, `data-easel-dnd`, `data-easel-preview` — both are drawn; easel's own reads and `BLOCK_ATTRIBUTE`, `BLOCK_SELECTOR`, `LIST_SELECTOR` use the new (`LEGACY_BLOCK_ATTRIBUTE` names the old) |
|
|
626
|
-
| inspector mode `{ kind: "puck" }` | `SELECTION_MODE`, now `{ kind: "selection" }`; `isSelectionMode(mode)` accepts both spellings |
|
|
627
|
-
| the root's `id: "puck-root"` | `page-root`, in easel 22 (the recorded fixtures hold the old id until then) |
|
|
617
|
+
**The old editor's name is gone (22.0.0).** The block prop is `editor`, the
|
|
618
|
+
canvas markup `data-easel-*`, the subpaths `screen/lib/document/*`, the
|
|
619
|
+
inspector mode `{ kind: "selection" }` and the root's id `page-root`. What was
|
|
620
|
+
removed, and what replaces each name, is in the CHANGELOG under 22.0.0.
|
|
628
621
|
|
|
629
622
|
**A slot says how many blocks it holds** (Unreleased). Each slot component
|
|
630
623
|
has a read-only `blockCount`: the blocks it draws. A block of a type the
|
|
@@ -645,7 +638,7 @@ always has it.
|
|
|
645
638
|
|
|
646
639
|
`className` (0.95.0) is an opt-in class for that top-level wrapper, for a host
|
|
647
640
|
whose stylesheet has to reach it: `<Render … className="page" />`. Left out,
|
|
648
|
-
the wrapper is bare and the markup is
|
|
641
|
+
the wrapper is bare and the markup is the old editor's.
|
|
649
642
|
|
|
650
643
|
## What a block draws with — `efficient-easel/draw`, `efficient-easel/draw/client`
|
|
651
644
|
|
|
@@ -697,7 +690,7 @@ graph to an exact list of files and imports.
|
|
|
697
690
|
|
|
698
691
|
`efficient-easel/canvas` (added in 0.70.0, blueprint step 2.1) is the one way
|
|
699
692
|
into the editor's canvas iframe — `#preview-frame`, the engine's own
|
|
700
|
-
same-origin canvas frame (
|
|
693
|
+
same-origin canvas frame (the old editor's, until the editors left it). It replaces the
|
|
701
694
|
editors' own polling loops, host-head style injection and hand-written
|
|
702
695
|
coordinate maths.
|
|
703
696
|
|
|
@@ -714,7 +707,7 @@ const tick = useCanvasLayout(canvas); // re-m
|
|
|
714
707
|
|---|---|
|
|
715
708
|
| `useCanvasFrame(rootRef, { selector?, readySelector? })` | `{ frame, document, window }` or `null`. Found by a MutationObserver and the frame's `load` event — never a timer. `readySelector` waits for the canvas to be drawn in a loaded-but-empty document. |
|
|
716
709
|
| `useCanvasEvent(canvas, type, handler, { on?, capture? })` | A listener on the canvas document (or window) that moves to a replacement document and always calls the latest handler, without re-binding on every render. |
|
|
717
|
-
| `useCanvasStyle(canvas, key, css)` | A `<style>` in the canvas document's head only — re-injected into a replacement, put back if something empties the head (
|
|
710
|
+
| `useCanvasStyle(canvas, key, css)` | A `<style>` in the canvas document's head only — re-injected into a replacement, put back if something empties the head (the old editor's AutoFrame does, once), removed on unmount, never written to the host page. |
|
|
718
711
|
| `useCanvasLayout(canvas)` | A number that changes when the canvas scrolls, resizes, is replaced, or the host scrolls or resizes (plus two settle passes). |
|
|
719
712
|
| `frameRectToHost`, `framePointToHost`, `frameScale` | A box or point measured inside the frame, on the host page — through the frame's SCALE (a phone view drawn small). |
|
|
720
713
|
| `fitCanvas({ available, width, maxScale })` | The canvas width and the scale that fits it into the pane. |
|
|
@@ -1004,7 +997,7 @@ const easel = createEasel<EaselConfig>({ config, data, onChange: (doc) => autosa
|
|
|
1004
997
|
- `bindUndoKeys(target, editor, { leaveTyping: true })` (0.106.0) leaves a
|
|
1005
998
|
press where a person types — a text field, a textarea, an editable
|
|
1006
999
|
region — to that field's own undo. Left out, a press there undoes the
|
|
1007
|
-
easel's step, as
|
|
1000
|
+
easel's step, as the old editor's did; the provider and the canvas bind so.
|
|
1008
1001
|
- **Two tabs since 4.0.0: Design and Animation.** A field's `bucket` is one
|
|
1009
1002
|
of `SETTINGS_BUCKETS`; anything else (the 3.x `Content`, `Style`, `Layout`)
|
|
1010
1003
|
is ignored, so the rows stay in the tab above them. Inside Design the host
|
|
@@ -1033,8 +1026,8 @@ const easel = createEasel<EaselConfig>({ config, data, onChange: (doc) => autosa
|
|
|
1033
1026
|
the slot's name has a bucket. Filter `row.field.type !== 'slot'` before
|
|
1034
1027
|
drawing or counting rows of your own.
|
|
1035
1028
|
- **Inserting a block runs no resolver; `easel.resolveNode` does.** The
|
|
1036
|
-
`insert` action puts the block in with its `defaultProps`, as
|
|
1037
|
-
did. What ran a new block's `resolveData` in
|
|
1029
|
+
`insert` action puts the block in with its `defaultProps`, as the old editor's reducer
|
|
1030
|
+
did. What ran a new block's `resolveData` in the old editor was its own drop from the
|
|
1038
1031
|
component list, and the engine has no drop of its own: the Add list's click
|
|
1039
1032
|
and the drag's drop are the host's. So follow an insert with it:
|
|
1040
1033
|
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import * as react from 'react';
|
|
2
|
-
import { C as CanvasTarget$1 } from './watch-
|
|
3
|
-
import { S as SlotAddress, P as Place } from './types-
|
|
4
|
-
import { D as DragSession } from './session-
|
|
2
|
+
import { C as CanvasTarget$1 } from './watch-D0bNZRtU.js';
|
|
3
|
+
import { S as SlotAddress, P as Place } from './types-DlQIM1YO.js';
|
|
4
|
+
import { D as DragSession } from './session-CrWwDt7Z.js';
|
|
5
5
|
import { D as DragWords } from './words-SD4neL0n.js';
|
|
6
6
|
|
|
7
7
|
/**
|
|
@@ -207,7 +207,7 @@ type CanvasDragLayerProps<I> = {
|
|
|
207
207
|
readOnly?: boolean;
|
|
208
208
|
/** Re-measure when this changes — the document's revision. Layout changes re-measure by themselves. */
|
|
209
209
|
revision?: unknown;
|
|
210
|
-
/** How the canvas is measured. Default:
|
|
210
|
+
/** How the canvas is measured. Default: the old editor's markers (./measure). */
|
|
211
211
|
measure?: (canvas: CanvasTarget$1, layer: Element) => MeasuredCanvas;
|
|
212
212
|
/**
|
|
213
213
|
* The layer's own words in the host's language:
|
|
@@ -621,15 +621,15 @@ type ScreenDocumentValue = {
|
|
|
621
621
|
* editing right now. Null while loading and between retargets, so it also
|
|
622
622
|
* keys any once-per-document work (e.g. the pinned-chrome seed). */
|
|
623
623
|
docId: string | null;
|
|
624
|
-
/** The document exactly as it was LOADED from the backend:
|
|
624
|
+
/** The document exactly as it was LOADED from the backend: the old editor's initial
|
|
625
625
|
* state, and the persisted snapshot a load-time seed must measure itself
|
|
626
|
-
* against. Null while loading. Edits live in
|
|
626
|
+
* against. Null while loading. Edits live in the old editor's own store, so this does
|
|
627
627
|
* NOT track them — it stays the last-loaded layout for the whole session. */
|
|
628
628
|
data: Data | null;
|
|
629
629
|
/** The freshest layout the merchant is actually viewing — the latest edit made
|
|
630
630
|
* since load (tracked on every onChange, even after the autosave settles), else
|
|
631
631
|
* the last-loaded `data`. Lets a feature snapshot the live view (e.g. the
|
|
632
|
-
* read-only origin backdrop in footer focus) without reaching into
|
|
632
|
+
* read-only origin backdrop in footer focus) without reaching into the old editor's store.
|
|
633
633
|
* Lean accessor (ISP) — never exposes the ref. */
|
|
634
634
|
getLiveData: () => Data | null;
|
|
635
635
|
error: string | null;
|
|
@@ -659,7 +659,7 @@ type ScreenDocumentValue = {
|
|
|
659
659
|
/** "Retry now": a failed save goes again at once instead of waiting out its
|
|
660
660
|
* backoff. */
|
|
661
661
|
retrySave: () => void;
|
|
662
|
-
/** Autosave — hand every
|
|
662
|
+
/** Autosave — hand every the old editor onChange to this. */
|
|
663
663
|
onChange: (next: Data) => void;
|
|
664
664
|
/** Persist the pending edit immediately; resolves to whether nothing is left
|
|
665
665
|
* unsaved. */
|
package/dist/blocks/index.d.ts
CHANGED
|
@@ -1,17 +1,17 @@
|
|
|
1
1
|
import { ReactElement, FC, CSSProperties, ReactNode, JSX } from 'react';
|
|
2
|
-
import { P as Permissions, A as AppState } from '../types-
|
|
2
|
+
import { P as Permissions, A as AppState } from '../types-DFxBChE3.js';
|
|
3
3
|
import '../data/index.js';
|
|
4
|
-
import '../types-
|
|
5
|
-
import '../resolve-
|
|
6
|
-
import '../plan-
|
|
4
|
+
import '../types-DlQIM1YO.js';
|
|
5
|
+
import '../resolve-AJ6WF4EL.js';
|
|
6
|
+
import '../plan-CRUh2kVK.js';
|
|
7
7
|
|
|
8
8
|
/**
|
|
9
9
|
* efficient-easel/blocks — how a block is WRITTEN: its config, its fields, the
|
|
10
10
|
* props its `render` receives and the document it lands in.
|
|
11
11
|
*
|
|
12
|
-
* Blueprint default #3 keeps
|
|
12
|
+
* Blueprint default #3 keeps the old editor's block writing, so the ~119 blocks both apps
|
|
13
13
|
* wrote move onto the engine without a line changed. Until 6.1 those blocks were
|
|
14
|
-
* typed by importing
|
|
14
|
+
* typed by importing the old editor's own types, which kept the old editor package in both apps'
|
|
15
15
|
* dependencies after nothing ran it any more. These are the same shapes, written
|
|
16
16
|
* here — Puck 0.20's `Config`, `ComponentConfig`, `Fields`, `Field`,
|
|
17
17
|
* `CustomField`, `ComponentData`, `Data`, `Slot` and `SlotComponent` — so an app
|
|
@@ -20,11 +20,11 @@ import '../plan-CZS902DV.js';
|
|
|
20
20
|
* WHAT IS LEFT OUT, ON PURPOSE:
|
|
21
21
|
* - the `ConfigParams` form of `Config<{ components, root, fields }>` and the
|
|
22
22
|
* user field-type extension it carries (neither app uses it);
|
|
23
|
-
* - everything about
|
|
23
|
+
* - everything about the old editor's own app — its store, overrides, plugins and
|
|
24
24
|
* history. Those are the engine's now (`efficient-easel/easel`).
|
|
25
25
|
*
|
|
26
|
-
* The `
|
|
27
|
-
* (`
|
|
26
|
+
* The `editor` prop is what every block's `render` destructures
|
|
27
|
+
* (`editor.isEditing`, `editor.renderDropZone`), and renaming it is the block rewrite
|
|
28
28
|
* default #3 rules out. Its type is `BlockContext`.
|
|
29
29
|
*
|
|
30
30
|
* TYPES ONLY — nothing here exists at runtime, so a server component, a test
|
|
@@ -49,7 +49,7 @@ type BaseField = {
|
|
|
49
49
|
metadata?: Metadata;
|
|
50
50
|
visible?: boolean;
|
|
51
51
|
/**
|
|
52
|
-
* NOT
|
|
52
|
+
* NOT THE OLD EDITOR'S — the engine's (0.97.0). Whether this prop is written again in
|
|
53
53
|
* each language of a multilingual page (`efficient-easel/data`, the
|
|
54
54
|
* translation overlay). Left out, a `text` or `textarea` field is and every
|
|
55
55
|
* other type is not, so a `custom` field that edits words, or a picture with
|
|
@@ -104,7 +104,7 @@ type ObjectField<Props = AnyRecord> = BaseField & {
|
|
|
104
104
|
[SubPropName in keyof Props]: Field<Props[SubPropName]>;
|
|
105
105
|
};
|
|
106
106
|
};
|
|
107
|
-
/** A custom field's drawing: called with
|
|
107
|
+
/** A custom field's drawing: called with the old editor's six props, as both apps wrote them. */
|
|
108
108
|
type CustomFieldRender<Value> = (props: {
|
|
109
109
|
field: CustomField<Value>;
|
|
110
110
|
name: string;
|
|
@@ -124,9 +124,9 @@ type SlotField = BaseField & {
|
|
|
124
124
|
disallow?: string[];
|
|
125
125
|
};
|
|
126
126
|
/**
|
|
127
|
-
*
|
|
127
|
+
* The old editor's `external` field: a value picked from a list the app fetches. Neither
|
|
128
128
|
* app has one and the Inspector does not draw it — it is in the union only so
|
|
129
|
-
* the union is
|
|
129
|
+
* the union is the old editor's, and a function that takes `Fields` takes the old editor's too.
|
|
130
130
|
*/
|
|
131
131
|
type ExternalField<Props = AnyRecord> = BaseField & {
|
|
132
132
|
type: 'external';
|
|
@@ -240,7 +240,7 @@ type DropZoneProps = {
|
|
|
240
240
|
type SlotComponent = ((props?: Omit<DropZoneProps, 'zone'>) => ReactNode) & {
|
|
241
241
|
readonly blockCount?: number;
|
|
242
242
|
};
|
|
243
|
-
/** The `editor` prop every block's `render` receives
|
|
243
|
+
/** The `editor` prop every block's `render` receives. */
|
|
244
244
|
type BlockContext = {
|
|
245
245
|
renderDropZone: FC<DropZoneProps>;
|
|
246
246
|
metadata: Metadata;
|
|
@@ -249,15 +249,13 @@ type BlockContext = {
|
|
|
249
249
|
};
|
|
250
250
|
type WithBlockProps<Props> = Props & {
|
|
251
251
|
editor: BlockContext;
|
|
252
|
-
/** @deprecated The same value as `editor`; removed in easel 22. */
|
|
253
|
-
puck: BlockContext;
|
|
254
252
|
editMode?: boolean;
|
|
255
253
|
};
|
|
256
254
|
type WithChildren<Props> = Props & {
|
|
257
255
|
children: ReactNode;
|
|
258
256
|
};
|
|
259
|
-
type AsFieldProps<Props> = Omit<Props, 'children' | 'editor' | '
|
|
260
|
-
/** A block's `render`: its own props with slots as `SlotComponent`s, its id
|
|
257
|
+
type AsFieldProps<Props> = Omit<Props, 'children' | 'editor' | 'editMode'>;
|
|
258
|
+
/** A block's `render`: its own props with slots as `SlotComponent`s, its id and `editor`. */
|
|
261
259
|
type BlockComponent<Props> = (props: WithId<WithBlockProps<{
|
|
262
260
|
[K in keyof Props]: WithDeepSlots<Props[K], SlotComponent>;
|
|
263
261
|
}>>) => JSX.Element;
|
|
@@ -6,7 +6,7 @@
|
|
|
6
6
|
* tabs that hold a setting — an empty tab is hidden, never drawn.
|
|
7
7
|
*
|
|
8
8
|
* ONE list for both editors. The website editor wrote the first one in
|
|
9
|
-
*
|
|
9
|
+
* the storefront's old field-groups module (`BUCKETS`); from 0.43.0 it
|
|
10
10
|
* lives here, so the campaign editor spells its panel with the same words in
|
|
11
11
|
* the same order instead of keeping a second list.
|
|
12
12
|
*/
|
package/dist/canvas/index.d.ts
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { RefObject } from 'react';
|
|
2
|
-
import { C as CanvasTarget, W as WatchOptions } from '../watch-
|
|
3
|
-
export { B as BLOCK_SELECTOR, a as CANVAS_SELECTOR, L as LIST_SELECTOR, i as isFrameReady, w as watchCanvasFrame } from '../watch-
|
|
4
|
-
export { R as REPEAT_ATTRIBUTE, a as REPEAT_INDEX_ATTRIBUTE, i as isRepeatCopy, m as mainCopyOf, q as queryAllCopies, b as queryMainCopy } from '../repeat-
|
|
2
|
+
import { C as CanvasTarget, W as WatchOptions } from '../watch-D0bNZRtU.js';
|
|
3
|
+
export { B as BLOCK_SELECTOR, a as CANVAS_SELECTOR, L as LIST_SELECTOR, i as isFrameReady, w as watchCanvasFrame } from '../watch-D0bNZRtU.js';
|
|
4
|
+
export { R as REPEAT_ATTRIBUTE, a as REPEAT_INDEX_ATTRIBUTE, i as isRepeatCopy, m as mainCopyOf, q as queryAllCopies, b as queryMainCopy } from '../repeat-D65bJS8d.js';
|
|
5
5
|
|
|
6
6
|
/**
|
|
7
7
|
* The small facts every canvas surface needs, written once — pure DOM, no
|
|
@@ -27,8 +27,6 @@ export { R as REPEAT_ATTRIBUTE, a as REPEAT_INDEX_ATTRIBUTE, i as isRepeatCopy,
|
|
|
27
27
|
declare function isTypingTarget(target: EventTarget | null): boolean;
|
|
28
28
|
/** The attribute on every block the canvas draws. */
|
|
29
29
|
declare const BLOCK_ATTRIBUTE = "data-easel-block";
|
|
30
|
-
/** @deprecated Puck 0.20's name for {@link BLOCK_ATTRIBUTE}, still drawn beside it; removed in easel 22. */
|
|
31
|
-
declare const LEGACY_BLOCK_ATTRIBUTE = "data-puck-component";
|
|
32
30
|
|
|
33
31
|
/**
|
|
34
32
|
* The id of the block a pointer event landed on: the NEAREST ancestor (or the
|
|
@@ -136,10 +134,10 @@ declare function removeCanvasStyle(doc: Document, key: string): void;
|
|
|
136
134
|
/**
|
|
137
135
|
* efficient-easel/canvas — the one way into the editor's canvas frame.
|
|
138
136
|
*
|
|
139
|
-
* Step 2.1 of the engine that replaces
|
|
137
|
+
* Step 2.1 of the engine that replaces the old editor (blueprint "From The Ground Up
|
|
140
138
|
* For Efficient Editor", 2026-09-29). Both editors draw their canvas in an
|
|
141
|
-
* iframe —
|
|
142
|
-
* CanvasFrame once the editors leave
|
|
139
|
+
* iframe — the old editor's `#preview-frame` today, the engine's own same-origin
|
|
140
|
+
* CanvasFrame once the editors leave the old editor — and each reached into it its own
|
|
143
141
|
* way: eight polling loops with eight intervals, stylesheets pushed into the
|
|
144
142
|
* host `<head>` hoping to be mirrored, key listeners re-bound on a one-second
|
|
145
143
|
* timer, coordinate conversions that forgot the frame's scale. This module is
|
|
@@ -214,7 +212,7 @@ declare function useCanvasTyping(canvas: CanvasTarget | null): boolean;
|
|
|
214
212
|
* back in a replacement document, and take it out on unmount. An empty string
|
|
215
213
|
* removes it. Nothing is written to the host page.
|
|
216
214
|
*
|
|
217
|
-
* "Keep" means it comes back if something else takes it out.
|
|
215
|
+
* "Keep" means it comes back if something else takes it out. The old editor's AutoFrame
|
|
218
216
|
* empties the frame's `<head>` once, when the host styles it mirrors have
|
|
219
217
|
* loaded (`doc.head.innerHTML = ""` in CopyHostStyles), and nothing orders that
|
|
220
218
|
* after the canvas is published — so a sheet written first would silently go.
|
|
@@ -236,4 +234,4 @@ declare function useCanvasLayout(canvas: CanvasTarget | null, { settle }?: {
|
|
|
236
234
|
settle?: readonly number[];
|
|
237
235
|
}): number;
|
|
238
236
|
|
|
239
|
-
export { BLOCK_ATTRIBUTE, type Box, CANVAS_TYPABLE_EVENT, CANVAS_TYPING_EVENT, type CanvasFit, CanvasTarget, type CanvasTypableEvent, type CanvasTypingEvent,
|
|
237
|
+
export { BLOCK_ATTRIBUTE, type Box, CANVAS_TYPABLE_EVENT, CANVAS_TYPING_EVENT, type CanvasFit, CanvasTarget, type CanvasTypableEvent, type CanvasTypingEvent, WatchOptions, clientPointToLayer, drawnBox, elementScale, fitCanvas, framePointToHost, frameRectToHost, frameRectToLayer, frameScale, isTypingTarget, nodeIdAt, removeCanvasStyle, setCanvasNonce, upsertCanvasStyle, useCanvasEvent, useCanvasFrame, useCanvasLayout, useCanvasStyle, useCanvasTyping };
|
package/dist/canvas/index.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
export{BLOCK_ATTRIBUTE,BLOCK_SELECTOR,CANVAS_SELECTOR,CANVAS_TYPABLE_EVENT,CANVAS_TYPING_EVENT,
|
|
1
|
+
export{BLOCK_ATTRIBUTE,BLOCK_SELECTOR,CANVAS_SELECTOR,CANVAS_TYPABLE_EVENT,CANVAS_TYPING_EVENT,LIST_SELECTOR,clientPointToLayer,drawnBox,elementScale,fitCanvas,framePointToHost,frameRectToHost,frameRectToLayer,frameScale,isFrameReady,isTypingTarget,nodeIdAt,removeCanvasStyle,setCanvasNonce,upsertCanvasStyle,useCanvasEvent,useCanvasFrame,useCanvasLayout,useCanvasStyle,useCanvasTyping,watchCanvasFrame}from"../chunk-GHBK7BKL.js";export{REPEAT_ATTRIBUTE,REPEAT_INDEX_ATTRIBUTE,isRepeatCopy,mainCopyOf,queryAllCopies,queryMainCopy}from"../chunk-LF3FUSCQ.js";
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{useEaselSession as e}from"./chunk-YM4UEGBV.js";import{useHostEscape as n}from"./chunk-MQA7OFRA.js";import{DEFAULT_SCREEN_WORDS as t}from"./chunk-EB6NI2VK.js";import{styleMenuItems as o}from"./chunk-V7U33NF2.js";import{ROOT_ZONE as l}from"./chunk-TCAAOYQY.js";import{easelMenuEntries as r,menuLabel as i}from"./chunk-FIVU2COQ.js";import{createNodeClipboard as c,nodeMenuItems as s}from"./chunk-P5VYGWYO.js";import{DEFAULT_NODE_MENU_WORDS as a}from"./chunk-WK3AFPXY.js";import{isTypingTarget as u,useCanvasEvent as d,framePointToHost as p}from"./chunk-
|
|
1
|
+
import{useEaselSession as e}from"./chunk-YM4UEGBV.js";import{useHostEscape as n}from"./chunk-MQA7OFRA.js";import{DEFAULT_SCREEN_WORDS as t}from"./chunk-EB6NI2VK.js";import{styleMenuItems as o}from"./chunk-V7U33NF2.js";import{ROOT_ZONE as l}from"./chunk-TCAAOYQY.js";import{easelMenuEntries as r,menuLabel as i}from"./chunk-FIVU2COQ.js";import{createNodeClipboard as c,nodeMenuItems as s}from"./chunk-P5VYGWYO.js";import{DEFAULT_NODE_MENU_WORDS as a}from"./chunk-WK3AFPXY.js";import{isTypingTarget as u,useCanvasEvent as d,framePointToHost as p}from"./chunk-GHBK7BKL.js";import{zoneKey as f,ROOT_SLOT as m,ROOT_ID as h}from"./chunk-K7BTCBWD.js";import{useState as y,useCallback as k,useRef as b,useEffect as g}from"react";import{ContextMenu as v}from"efficient-shell/ui";import{UndoIcon as w,RedoIcon as x,PasteIcon as C,SettingsIcon as O,LayersIcon as z,CopyIcon as A}from"efficient-shell/icons/efficient";import{jsx as P}from"react/jsx-runtime";function K(e,n){const t=[],o=/* @__PURE__ */new Set;let r={zone:n.zone,index:n.index};for(;r;){const n=e.nodeAt(r.zone,r.index);if(!n||o.has(n.props.id))break;if(o.add(n.props.id),t.push({zone:r.zone,index:r.index,node:n,parentType:null}),r.zone===l)break;const i=r.zone.lastIndexOf(":");if(i<=0)break;r=e.locate(r.zone.slice(0,i))}for(let e=0;e<t.length-1;e+=1)t[e].parentType=t[e+1].node.type;return t}var j=c(),B=/* @__PURE__ */new WeakMap;function D(e){if(e.claimsPage)return j;const n=e.registry;if(!n)return e.cache("easel:node-clipboard",c);let t=B.get(n);return t||(t=c(),B.set(n,t)),t}function M(){return D(e())}function T(e,n,t){if(n===l){const{floor:n,cap:o}=e.sectionBand();return{parentId:h,slot:m,index:Math.min(Math.max(t,n),o)}}const o=n.lastIndexOf(":");return{parentId:n.slice(0,o),slot:n.slice(o+1),index:t}}function Y(e,n,t){const o=e.isPinned(n,t),l=!o&&!e.isLocked(n)&&!e.duplicateBlocked(n),r=e.permits?.(n)??{duplicate:!0,delete:!0};return{copy:!o&&r.duplicate,cut:l&&r.duplicate&&r.delete,delete:l&&r.delete}}function E(e,n,t){const o=e.canPasteAt;if(!o)return f(n.from)===t.zone?T(e,t.zone,t.index+1):null;for(const l of K(e,t)){const t=T(e,l.zone,l.index+1);if(o(n,t))return t}return null}function I(e){if(e.defaultPrevented||e.altKey||e.shiftKey)return null;if(u(e.target))return null;const n=e.target,t=n&&"ownerDocument"in n?n.ownerDocument??n:null,o=t?.getSelection?.();if(o&&!o.isCollapsed&&o.toString().trim())return null;if(!e.metaKey&&!e.ctrlKey)return"Delete"===e.key?"delete":null;const l=e.code||(1===e.key.length?`Key${e.key.toUpperCase()}`:"");return"KeyC"===l?"copy":"KeyX"===l?"cut":"KeyV"===l?"paste":null}function S(e,n,t,o){const l=e.nodeAt(t.zone,t.index);if(!l)return null;const r=l.props.id,i=e.labelOf(l.type,t.zone),c=Y(e,l,t.zone);if("copy"===n)return c.copy?(e.nodeOps.copy(r,i),{done:"copied",name:i}):null;if(o.readOnly)return null;if("cut"===n)return c.cut?(e.nodeOps.cut(r,i),{done:"cut",name:i}):null;if("delete"===n)return c.delete?(e.nodeOps.remove(r),{done:"deleted",name:i}):null;const s=o.held;if(!s)return null;const a=e.isPinned(l,t.zone)?null:E(e,s,t);return a?(e.nodeOps.paste(a),{done:"pasted",name:s.label}):(e.onPasteRefused(s),{done:"refused",name:s.label})}function V(e,n){const{zone:t,index:r}=n,i=e.nodeAt(t,r);if(!i)return[];const c=i.props.id,a=e.labelOf(i.type,t),u=Boolean(i.props._hidden),d=e.nodeOps,p=e.isPinned(i,t),f=e.isLocked(i),m=!p&&!f&&!e.duplicateBlocked(i),h=e.permits?.(i)??{duplicate:!0,delete:!0},y=Y(e,i,t),k=K(e,n),b=d.held,g=b&&!p?E(e,b,n):null,v=!e.readOnly,w=e.style?o({held:v?e.style.held():null,canCopy:e.style.canCopy(i,t),onCopy:()=>e.style?.copy(i,t),onPaste:()=>e.style?.paste(t,r,i),words:e.words?.styleClipboard}):[];return s({title:a,words:e.words?.menu,layer:{group:"pick",items:k.flatMap((n,t)=>{const o={label:e.rowNameOf(n.node,n.zone),checked:0===t,onClick:()=>e.selectAt(n.zone,n.index,n.node.props.id,n.parentType)},r=n.zone===l?null:e.slotRung?.(n.zone)??null;return r?[o,{label:r.label,checked:!1,onClick:r.select}]:[o]})},actions:{duplicate:v&&m&&h.duplicate?()=>d.duplicate(c):void 0,...L(v&&!p,e=>d.canStep(c,e),e=>d.step(c,e)),copy:y.copy?()=>d.copy(c,a):void 0,cut:v&&y.cut?()=>d.cut(c,a):void 0,paste:v&&b&&g?{label:b.label,run:()=>d.paste(g)}:void 0,rename:v&&e.renamePropOf(i,t)?()=>e.beginRename(t,r):void 0,hide:!v||f||p?void 0:{hidden:u,run:()=>d.setProps(c,{_hidden:!u})},delete:v&&m&&h.delete?()=>d.remove(c):void 0},style:w,extras:e.menuRows?.(i,t,r)??void 0,pinnedLine:p?R(e).pinned:void 0})}function L(e,n,t){return e?{moveUp:n(-1)?()=>t(-1):null,moveDown:n(1)?()=>t(1):null}:{}}var R=e=>e.words?.screen??t.menu;function X(e){const n=R(e),o=!e.readOnly,r=[];o&&e.history.hasPast&&r.push({label:n.undo,icon:/* @__PURE__ */P(w,{}),shortcut:"⌘Z",onClick:e.history.back}),o&&e.history.hasFuture&&r.push({label:n.redo,icon:/* @__PURE__ */P(x,{}),shortcut:"⇧⌘Z",onClick:e.history.forward});const i=[],c=e.nodeOps.held,s=T(e,l,e.sectionBand().cap);if(o&&c&&(e.canPasteAt?e.canPasteAt(c,s):f(c.from)===l)){const n=s,t=e.words?.menu??a;i.push({label:t.pasteNamed({paste:t.paste,label:c.label}),icon:/* @__PURE__ */P(C,{}),shortcut:"⌘V",onClick:()=>e.nodeOps.paste(n)})}const u=[r,i,[{label:e.pageSettingsLabel??t.pageSettings,icon:/* @__PURE__ */P(O,{}),onClick:e.openPageSettings},{label:n.collapseAll,icon:/* @__PURE__ */P(z,{}),onClick:e.collapseAll}]].filter(e=>e.length>0),d={label:"—",onClick:()=>{}};return u.flatMap((e,n)=>n?[d,...e]:e)}function N(e,n){const t=n.selectionStart??0,o=n.selectionEnd??0,l=n.value.slice(t,o),r=e=>{n.focus(),n.setRangeText(e,t,o,"end"),n.dispatchEvent(new Event("input",{bubbles:!0}))},i=e.words?.menu??a,c=R(e),s=[];l&&(s.push({label:i.copy,icon:/* @__PURE__ */P(A,{}),shortcut:"⌘C",onClick:()=>navigator.clipboard?.writeText(l)}),s.push({label:i.cut,icon:/* @__PURE__ */P(A,{}),shortcut:"⌘X",onClick:()=>{navigator.clipboard?.writeText(l),r("")}})),s.push({label:i.paste,icon:/* @__PURE__ */P(C,{}),shortcut:"⌘V",onClick:()=>{navigator.clipboard?.readText().then(e=>{e&&r(e)}).catch(()=>e.onPasteRefused())}});const u=[s,n.value?[{label:c.selectAll,shortcut:"⌘A",onClick:()=>{n.focus(),n.select()}}]:[]].filter(e=>e.length>0),d={label:"—",onClick:()=>{}};return u.flatMap((e,n)=>n?[d,...e]:e)}function U(e){return e.shiftKey}function F(e,t){const[o,l]=y(null),r=k(()=>l(null),[]);n(null!==o,r);const i=b(e);i.current=e;const c=k(e=>{const n=i.current,t=n.keys;if(!t)return;const o=I(e);if(!o)return;const l=t.selected();if(!l)return;const r=S(n,o,l,{readOnly:t.readOnly,held:t.held()});r&&(e.preventDefault(),t.onDone?.(r))},[]),s=e.keys?.target??null;g(()=>{if(!s)return;const e=e=>c(e);return s.addEventListener("keydown",e),()=>s.removeEventListener("keydown",e)},[s,c]),d(t,"keydown",c);const a=k(n=>{if(U(n))return;const t=n.target;if(t?.closest?.("[data-slot-zone]"))return n.preventDefault(),void l(null);const o=function(e){const n=e?.closest?.("input, textarea");return n&&("INPUT"!==n.tagName||["text","search","url","email","tel","number",""].includes(n.type))?n:null}(t);if(o)return n.preventDefault(),void l({kind:"input",x:n.clientX,y:n.clientY,el:o,owner:t});const r=t?.closest?.("[data-node-id]")?.getAttribute("data-node-id"),i=r?e.locate(r):null;n.preventDefault(),l(i?{kind:"node",x:n.clientX,y:n.clientY,...i,owner:t}:{kind:"empty",x:n.clientX,y:n.clientY,owner:t})},[e]);d(t,"contextmenu",n=>{if(U(n)||!t)return;const o=n.target?.closest?.("[data-easel-block]")??null,r=o?.getAttribute("data-easel-block"),i=r?e.locate(r):null;n.preventDefault();const c=p(t.frame,n.clientX,n.clientY),s=t.frame;l(i?{kind:"node",...c,...i,owner:s}:{kind:"empty",...c,owner:s})}),d(t,"mousedown",r),d(t,"scroll",r,{on:"window"});return{onEditorContextMenu:a,menu:o?/* @__PURE__ */P(W,{host:e,target:o,onClose:r}):null,closeMenu:r}}function W({host:e,target:n,onClose:t}){const o="node"===n.kind?V(e,n):"input"===n.kind?N(e,n.el):X(e);return 0===o.length?null:/* @__PURE__ */P(v,{at:{x:n.x,y:n.y},owner:n.owner??null,onClose:t,"aria-label":i(o),items:r(o)})}export{j as EASEL_NODE_CLIPBOARD,K as ancestorChain,D as nodeClipboardOf,Y as nodeClipboardRules,V as nodeMenuItems,I as nodeShortcut,X as pageMenuItems,E as pastePlace,S as runNodeShortcut,N as textMenuItems,M as useNodeClipboard,F as useNodeContextMenu};
|
|
@@ -1,18 +1,18 @@
|
|
|
1
|
-
import{DEFAULT_DRAG_WORDS as e}from"./chunk-TQ5Y6S2X.js";import{dropEffectFor as t,scrollBoxOf as n,frameScrollBox as l,startAutoScroll as a,isNoOpDrop as r}from"./chunk-3S5N4HLJ.js";import{withTip as o}from"./chunk-P2VEMZH5.js";import{useCanvasLayout as s,useCanvasTyping as i,useCanvasEvent as c,CANVAS_TYPABLE_EVENT as d,framePointToHost as u,elementScale as h,frameRectToLayer as f,clientPointToLayer as p}from"./chunk-
|
|
1
|
+
import{DEFAULT_DRAG_WORDS as e}from"./chunk-TQ5Y6S2X.js";import{dropEffectFor as t,scrollBoxOf as n,frameScrollBox as l,startAutoScroll as a,isNoOpDrop as r}from"./chunk-3S5N4HLJ.js";import{withTip as o}from"./chunk-P2VEMZH5.js";import{useCanvasLayout as s,useCanvasTyping as i,useCanvasEvent as c,CANVAS_TYPABLE_EVENT as d,framePointToHost as u,elementScale as h,frameRectToLayer as f,clientPointToLayer as p}from"./chunk-GHBK7BKL.js";import{isRepeatCopy as m}from"./chunk-LF3FUSCQ.js";import{parseZoneKey as g,ROOT_ID as b}from"./chunk-K7BTCBWD.js";import{useRef as x,useEffect as y,useState as v,useCallback as w,useMemo as k,useSyncExternalStore as N,useId as D,useLayoutEffect as A}from"react";import{Tooltip as z,IconButton as T,solidSurfaceStyle as M,Input as C,ItemCount as S}from"efficient-shell/ui";import{AddIcon as $,CloseIcon as B,SearchIcon as E}from"efficient-shell/icons/efficient";import{jsxs as L,jsx as j}from"react/jsx-runtime";function K({label:e,onInsert:t,style:n,axis:l="y",className:a,index:r}){const o=["es-canvas-insert","x"===l?"is-x":"",a??""].filter(Boolean).join(" ");/* @__PURE__ */
|
|
2
2
|
return L("div",{className:o,style:n,"data-index":r,children:[
|
|
3
|
-
/* @__PURE__ */
|
|
4
|
-
/* @__PURE__ */
|
|
5
|
-
/* @__PURE__ */
|
|
6
|
-
/* @__PURE__ */
|
|
7
|
-
/* @__PURE__ */
|
|
3
|
+
/* @__PURE__ */j("span",{className:"es-canvas-insert-line","aria-hidden":"true"}),
|
|
4
|
+
/* @__PURE__ */j("span",{className:"es-canvas-insert-chip",children:/* @__PURE__ */j(z,{content:e,children:/* @__PURE__ */j(T,{variant:"ghost",size:"sm","aria-label":e,onClick:t,children:/* @__PURE__ */j($,{})})})})]})}var O=(e,t,n)=>t>=e.left&&t<=e.left+e.width&&n>=e.top&&n<=e.top+e.height,I=e=>e.width*e.height;function q(e,t,n){return e.map((e,t)=>({s:e,at:t})).filter(({s:e})=>O(e.box,t,n)).sort((e,t)=>I(t.s.box)-I(e.s.box)||e.at-t.at).map(({s:e})=>e)}function X(e,t,n){return q(e,t,n).at(-1)??null}function Y(e,t,n){const l="x"===e.axis?t:n;let a=0;for(const t of e.children){l>("x"===e.axis?t.left+t.width/2:t.top+t.height/2)&&(a+=1)}return a}function H(e,t){const n=e.children;if("x"===e.axis){const l=n[t-1],a=n[t],r=l&&a?(l.left+l.width+a.left)/2:l?l.left+l.width:a?a.left:e.box.left,o=a??l??e.box;return{left:r-1,top:o.top,width:2,height:o.height}}const l=n[t-1],a=n[t],r=l&&a?(l.top+l.height+a.top)/2:l?l.top+l.height:a?a.top:e.box.top;return{left:e.box.left,top:r-1,width:e.box.width,height:2}}function F(e,t,n,l,a=()=>!1,r=()=>!0){const o=e.filter(e=>O(e.box,t,n)).sort((e,t)=>I(e.box)-I(t.box));for(const e of o){const o=Y(e,t,n),s={...e.list,index:o};if(a(s))return null;if(l(s))return{zone:e,to:s,line:H(e,o)};if(!r(s))return null}return null}function P(e,t,n=12){const l=e.children;if(0===l.length)return[];const a=e.box,r="x"===e.axis,o=r?a.left:a.top,s=o+(r?a.width:a.height),i=e=>r?e.left:e.top,c=e=>r?e.left+e.width:e.top+e.height,d=[];for(let a=0;a<=l.length;a++){const u=l[a-1],h=l[a];let f,p;if(u&&h)f=c(u),p=Math.max(i(h)-f,0);else{const e=u?(c(u)+s)/2:(o+i(h))/2,t=Math.min(Math.max(e,o+n),s-n);f=u?Math.max(t,c(u)):Math.min(t,i(h)),p=0}const m=[u,h].filter(e=>Boolean(e)),g=Math.min(...m.map(e=>r?e.top:e.left)),b=Math.max(...m.map(e=>r?e.top+e.height:e.left+e.width)),x=r?{left:f,top:g,width:p,height:b-g}:{left:g,top:f,width:b-g,height:p};d.push({key:`${e.key}:+${a}`,place:{...e.list,index:a},box:x,axis:e.axis,label:t})}return d}function Z(e,t=e.key){const n=[];for(let l=1;l<e.children.length;l++){const a=e.children[l-1],r=e.children[l],o=a.top+a.height;n.push({key:`${t}:${l}`,place:{...e.list,index:l},box:{left:e.box.left,top:o,width:e.box.width,height:Math.max(r.top-o,0)}})}return n}var Q={nodes:[],zones:[]},R="data-easel-dropzone",V="data-easel-block";function W(e,t){if(e.length>=2){const[t,n]=e;return Math.abs(n.top-t.top)<Math.min(t.height,n.height)/2&&n.left>t.left?"x":"y"}const n=t.ownerDocument.defaultView?.getComputedStyle(t);return n&&n.display.includes("flex")&&n.flexDirection.startsWith("row")?"x":"y"}function G(e,t){const{frame:n,document:l}=e,a=e=>f(n,function(e){const t=e.getBoundingClientRect();return{left:t.left,top:t.top,width:t.width,height:t.height}}(e),t),r=[],o=[];for(const e of l.querySelectorAll(`[${R}]`)){if(m(e))continue;const t=e.getAttribute(R)??"";let n;try{n=g(t)}catch{continue}const l=[...e.querySelectorAll(`[${V}]`)].filter(t=>t.parentElement?.closest(`[${R}]`)===e&&!m(t)),s=l.map(a);o.push({key:t,list:n,box:a(e),axis:W(s,e),children:s}),l.forEach((e,t)=>{const l=e.getAttribute(V);l&&r.push({id:l,place:{...n,index:t},box:s[t]})})}return{nodes:r,zones:o}}var J="data-es-empty-cell",U="data-easel-dropzone",_=140;var ee=e=>({left:e.left,top:e.top,width:e.width,height:e.height});function te(o){const{canvas:f,session:m,readOnly:g,words:D=e.canvas}=o,T=x(o);y(()=>{T.current=o});const C=x(null),S=s(f),[$,B]=v(0),E=w(()=>B(e=>e+1),[]),[O,I]=v(Q);y(()=>{const e=C.current;f&&e&&I((T.current.measure??G)(f,e))},[f,S,o.revision,$]);const X=o.model,Y=k(()=>X(O),[X,O]),H=N(m.subscribe,m.shown,m.shown),P=o.choose,Z=(e,t)=>{const n=q(Y.sources,e,t);return 0===n.length?null:P?P(n):n[n.length-1]},[R,V]=v(null),[W,_]=v(null),[te,ne]=v(null),le=x(null),ae=()=>{le.current&&clearTimeout(le.current),le.current=null},re=()=>{ae(),le.current=setTimeout(()=>{m.get()||V(null)},140)};y(()=>ae,[]);const oe=x(null),se=i(f),ie=x(!1);ie.current=se,y(()=>{se&&(ae(),V(null))},[se]);const[ce,de]=v(null);c(f,d,e=>de(e.detail?.id??null));const ue=!ce||se||g||H?null:O.nodes.find(e=>e.id===ce)?.box??null;c(f,"mousemove",e=>{const t=C.current;if(!f||!t)return;const n=u(f.frame,e.clientX,e.clientY,t),l=h(t),a={x:n.x/l,y:n.y/l};if(oe.current=a,T.current.readOnly||m.get()||ie.current)return;ae();const r=Z(a.x,a.y);V(e=>e?.key===r?.key&&e?.box===r?.box?e:r)}),c(f,"mouseout",e=>{e.relatedTarget||(oe.current=null,re())}),c(f,"mouseover",e=>{e.relatedTarget||E()});const he=x(null),fe=w(()=>{he.current?.(),he.current=null,_(null),ne(null)},[]);y(()=>m.subscribe(()=>{m.get()?E():fe()}),[m,fe,E]),y(()=>fe,[fe]),("undefined"==typeof document?y:A)(()=>{if(m.get())return;const e=oe.current;V(t=>g||ie.current?null:e?Z(e.x,e.y):t?Y.sources.find(e=>e.key===t.key)??null:null)},[Y,H,m,g,P]);const pe=e=>{const t=m.get(),n=C.current,l=T.current.dropOn;if(!t||!n||!l)return null;const a=p(n,e.clientX,e.clientY);oe.current=a;const r=q(Y.sources,a.x,a.y);for(let e=r.length-1;e>=0;e-=1)if(l.accepts(t.item,r[e]))return{h:t,source:r[e]};return null},me=e=>{const t=m.get(),n=C.current;if(!t||!n)return null;const l=p(n,e.clientX,e.clientY);oe.current=l;const a=F(Y.zones,l.x,l.y,e=>T.current.canDrop(t.item,e),e=>!!t.from&&r(t.from,e),e=>T.current.fallThrough?.(t.item,e,t.from)??!0);return a?{h:t,t:a}:null},ge={onDragEnter:e=>{if(he.current)return;const t=n(e.currentTarget.parentElement?.parentElement??null),r=f?l(f.document):null,o=[];t&&o.push(a(t)),r&&f&&o.push(a(r,f.frame)),he.current=o.length?()=>o.forEach(e=>e()):null},onDragOver:e=>{const n=pe(e);if(n)return e.preventDefault(),e.dataTransfer.dropEffect=t(e.dataTransfer.effectAllowed),_(null),void ne(e=>e&&e.key===n.source.key&&e.box===n.source.box?e:n.source);ne(null);const l=me(e);if(!l)return void _(null);e.preventDefault(),e.dataTransfer.dropEffect=t(e.dataTransfer.effectAllowed);const a={zoneKey:l.t.zone.key,line:l.t.line,axis:l.t.zone.axis};_(e=>e&&e.zoneKey===a.zoneKey&&e.line.left===a.line.left&&e.line.top===a.line.top?e:a)},onDragLeave:e=>{const t=e.relatedTarget;t&&e.currentTarget.contains(t)||(oe.current=null,_(null),ne(null))},onDrop:e=>{const t=pe(e);if(t)return e.preventDefault(),m.end(),fe(),void T.current.dropOn.onDrop(t.h.item,t.source);const n=me(e);n&&(e.preventDefault(),m.end(),fe(),T.current.onDrop(n.h.item,n.t.to))}},be={draggable:!g&&!!R,onMouseEnter:ae,onMouseLeave:()=>!m.get()&&re(),onDragStart:e=>{if(R&&!g){m.start({key:R.key,item:R.item,from:R.from}),e.dataTransfer.effectAllowed="move";try{e.dataTransfer.setData("text/plain",R.key)}catch{}}else e.preventDefault()},onDragEnd:()=>{m.end(),fe()},onClick:()=>{R&&!g&&T.current.onPick?.(R.item)}},{seams:xe=[]}=Y,ye=Y.zones.filter(e=>0===e.children.length),ve=!o.onZoneAdd||g||se?[]:ye,we=ve.map(e=>e.key).join("\n");return y(()=>{const e=f?.document;if(!e)return;const t=new Set(we?we.split("\n"):[]);for(const n of e.querySelectorAll(`[${U}]`))n.toggleAttribute(J,t.has(n.getAttribute(U)??""));return()=>{for(const t of e.querySelectorAll(`[${J}]`))t.removeAttribute(J)}},[f,we,O,S,$]),/* @__PURE__ */L("div",{ref:C,className:"es-canvas-layer",children:[H||!o.onSeamAdd||g||se?null:xe.map(e=>
|
|
5
|
+
/* @__PURE__ */j(K,{className:"es-canvas-seam",axis:e.axis,index:e.place.index,label:e.label??o.seamLabel??D.addSection,onInsert:()=>o.onSeamAdd?.(e.place),style:"x"===e.axis?{left:e.box.left+e.box.width/2-12,top:e.box.top,width:24,height:e.box.height}:{left:e.box.left,top:e.box.top+e.box.height/2-12,width:e.box.width,height:24}},e.key)),ve.length?ve.map(e=>/* @__PURE__ */j("button",{type:"button",className:["es-canvas-empty",e.addAlways?"is-always":"",W?.zoneKey===e.key?"is-over":""].filter(Boolean).join(" "),style:ee(e.box),"data-node-id":e.list.parentId===b?void 0:e.list.parentId,onClick:()=>o.onZoneAdd?.({...e.list,index:0}),children:/* @__PURE__ */j("span",{className:"es-canvas-empty-add",children:D.addButton({label:e.addLabel??o.zoneAddLabel??D.addBlock})})},e.key)):null,H?/* @__PURE__ */j("div",{className:"es-canvas-catch",...ge}):null,te&&H?/* @__PURE__ */j("div",{className:"es-canvas-target",style:ee(te.box),children:o.dropOn?.label?/* @__PURE__ */j("span",{className:"es-canvas-target-label",style:M(),children:o.dropOn.label(H.item,te)}):null}):null,W&&!ye.some(e=>e.key===W.zoneKey)?/* @__PURE__ */j("div",{className:`es-canvas-line is-${W.axis}`,style:ee(W.line)}):null,ue?/* @__PURE__ */j("span",{className:"es-canvas-hint"+(ue.width<200?" is-below":""),style:{...M(),left:ue.left+ue.width,top:ue.width<200?ue.top+ue.height:ue.top},children:D.typeHint}):null,
|
|
6
|
+
/* @__PURE__ */j("div",{className:"es-canvas-handle-spot",style:R?{"--es-handle-x":`${R.box.left+2}px`,"--es-handle-y":`${Math.max(R.box.top-11,0)}px`}:void 0,children:/* @__PURE__ */j(z,{className:"es-canvas-handle-tip",side:"top",content:!R||g||H?null:R.title??D.handle({label:R.label}),children:/* @__PURE__ */L("div",{className:["es-canvas-handle",R&&!g?"is-shown":"",H?"is-dragging":""].filter(Boolean).join(" "),...be,children:[
|
|
7
|
+
/* @__PURE__ */j("span",{className:"es-canvas-grip","aria-hidden":"true",children:"⋮⋮"}),R?.label]})})})]})}var ne=e=>e.tiles.length>0&&e.tiles.every(e=>null!=e.cover);function le({groups:t,session:n,itemFor:l,onInsert:a,onTileMenu:r,at:s,hint:i,searchLabel:c,readOnly:d,words:u=e.add}){const h=i??u.hint,f=c??u.search,[p,m]=v(""),g=D(),b=p.trim().toLowerCase(),x=function(e){const t=/* @__PURE__ */new Map;return e.map(e=>{const n=e.key??e.title,l=t.get(n)??0;return t.set(n,l+1),0===l?n:`${n}\0${l}`})}(t),y=t.map((e,t)=>({...e,key:x[t],tiles:b?e.tiles.filter(e=>((e,t)=>e.label.toLowerCase().includes(t)||(e.keywords??[]).some(e=>e.toLowerCase().includes(t)))(e,b)):e.tiles})).filter(e=>e.tiles.length>0),w=(e,t)=>a=>{if(t)a.preventDefault();else{n.start({key:`new:${e}`,item:l(e)}),a.dataTransfer.effectAllowed="copy";try{a.dataTransfer.setData("text/plain",e)}catch{}}};/* @__PURE__ */
|
|
8
8
|
return L("div",{className:"es-add",children:[s?/* @__PURE__ */L("div",{className:"es-add-at",role:"status",children:[
|
|
9
|
-
/* @__PURE__ */
|
|
10
|
-
/* @__PURE__ */
|
|
11
|
-
/* @__PURE__ */
|
|
12
|
-
/* @__PURE__ */
|
|
13
|
-
/* @__PURE__ */
|
|
9
|
+
/* @__PURE__ */j("span",{children:s.label}),o(u.stop,/* @__PURE__ */j("button",{type:"button",className:"es-add-at-clear","aria-label":u.stop,onClick:s.onClear,children:/* @__PURE__ */j(B,{size:12,"aria-hidden":"true"})}))]}):null,
|
|
10
|
+
/* @__PURE__ */j("p",{className:"es-add-hint",children:h}),
|
|
11
|
+
/* @__PURE__ */j("div",{className:"es-add-find",children:/* @__PURE__ */j(C,{id:g,type:"search","aria-label":f,placeholder:u.searchPlaceholder({label:f}),value:p,onChange:e=>m(e.target.value),leftIcon:/* @__PURE__ */j(E,{size:16,"aria-hidden":"true"}),rightAdornment:p?/* @__PURE__ */j(T,{size:"sm","aria-label":u.clearSearch,onClick:()=>m(""),children:/* @__PURE__ */j(B,{size:12,"aria-hidden":"true"})}):void 0})}),0===y.length?/* @__PURE__ */L("div",{className:"es-add-empty",role:"status",children:[
|
|
12
|
+
/* @__PURE__ */j("div",{className:"es-add-empty-title",children:u.nothing({query:p.trim()})}),
|
|
13
|
+
/* @__PURE__ */j("div",{className:"es-add-empty-sub",children:u.tryAnother})]}):y.map(e=>/* @__PURE__ */L("section",{className:"es-add-group","aria-label":e.title,children:[
|
|
14
14
|
/* @__PURE__ */L("div",{className:"es-add-group-head",children:[
|
|
15
|
-
/* @__PURE__ */
|
|
16
|
-
/* @__PURE__ */
|
|
17
|
-
/* @__PURE__ */
|
|
18
|
-
/* @__PURE__ */L("span",{className:"es-add-tile-label",children:[e.label,null!=e.mark?/* @__PURE__ */
|
|
15
|
+
/* @__PURE__ */j("span",{className:"es-add-group-title",children:e.title}),
|
|
16
|
+
/* @__PURE__ */j(S,{count:e.tiles.length,label:u.count({count:e.tiles.length,sections:ne(e)}),className:"ml-auto"})]}),
|
|
17
|
+
/* @__PURE__ */j("div",{className:ne(e)?"es-add-grid is-cards":"es-add-grid",children:e.tiles.map(e=>{const t=Boolean(d||e.disabled),l=d?void 0:e.disabled?e.disabledReason:e.title??u.tile({label:e.label});return o(l,/* @__PURE__ */L("button",{type:"button",className:null!=e.cover?"es-add-tile has-cover":"es-add-tile",draggable:!t,"aria-disabled":t||void 0,"aria-label":u.tile({label:e.label}),onDragStart:w(e.type,t),onDragEnd:()=>n.end(),onClick:()=>!t&&a?.(e.type),onContextMenu:r?t=>{r(e.type,{x:t.clientX,y:t.clientY,owner:t.currentTarget})&&t.preventDefault()}:void 0,children:[null!=e.cover?/* @__PURE__ */j("span",{className:"es-add-tile-cover","aria-hidden":"true",children:e.cover}):e.icon?/* @__PURE__ */j("span",{className:"es-add-tile-glyph","aria-hidden":"true",children:e.icon}):null,
|
|
18
|
+
/* @__PURE__ */L("span",{className:"es-add-tile-label",children:[e.label,null!=e.mark?/* @__PURE__ */j("span",{className:"es-add-tile-mark","aria-hidden":"true",children:e.mark}):null]})]},e.type))})})]},e.key))]})}export{le as AddPanel,te as CanvasDragLayer,K as CanvasInsert,Q as EMPTY_MEASURE,_ as HANDLE_GRACE_MS,F as canvasTarget,O as contains,Y as gapInZone,H as gapLine,P as insertSeams,G as measureCanvas,X as pickSource,Z as seamsBetween,q as sourcesAt};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
import{useState as t,useEffect as e,useRef as n}from"react";var o=/* @__PURE__ */new Set(["button","checkbox","color","file","hidden","image","radio","range","reset","submit"]);function r(t){const e=t;if(!e||"string"!=typeof e.tagName)return!1;const n=e.tagName.toUpperCase();if("TEXTAREA"===n||"SELECT"===n)return!0;if("INPUT"===n)return!o.has(String(e.type??"text").toLowerCase());if(e.isContentEditable)return!0;const r=e.closest?.("[contenteditable]");return!(!r||"false"===r.getAttribute("contenteditable"))||null!=e.closest?.('[role="textbox"]')}var i="data-easel-block";function c(t,e=i){const n=t;return n&&"function"==typeof n.closest?n.closest(`[${e}]`)?.getAttribute(e)??null:null}function u(t){const e=t.getBoundingClientRect();if(e.width>0&&e.height>0)return{left:e.left,top:e.top,width:e.width,height:e.height};let n=1/0,o=1/0,r=-1/0,i=-1/0;for(const e of Array.from(t.children)){const t=e.getBoundingClientRect();t.width<=0||t.height<=0||(n=Math.min(n,t.left),o=Math.min(o,t.top),r=Math.max(r,t.right??t.left+t.width),i=Math.max(i,t.bottom??t.top+t.height))}return n===1/0?{left:e.left,top:e.top,width:e.width,height:e.height}:{left:n,top:o,width:r-n,height:i-o}}function l(t){const e=t.offsetWidth;if(!e)return 1;const n=t.getBoundingClientRect().width;return n>0?n/e:1}function s(t,e,n){const o=t.getBoundingClientRect(),r=n?.getBoundingClientRect()??{left:0,top:0},i=l(t);return{left:o.left-r.left+e.left*i,top:o.top-r.top+e.top*i,width:e.width*i,height:e.height*i}}function a(t){const e=t.offsetWidth;if(!e)return 1;const n=t.getBoundingClientRect().width;return n>0?n/e:1}function d(t,e,n){const o=s(t,e,n),r=a(n);return{left:o.left/r,top:o.top/r,width:o.width/r,height:o.height/r}}function f(t,e,n){const o=t.getBoundingClientRect(),r=a(t);return{x:(e-o.left)/r,y:(n-o.top)/r}}function h(t,e,n,o){const{left:r,top:i}=s(t,{left:e,top:n,width:0,height:0},o);return{x:r,y:i}}function m({available:t,width:e,maxScale:n=1}){const o=Math.max(0,t);if(!e||e<=0)return{width:o,scale:1,shownWidth:o};const r=o>0?Math.min(o/e,n):1;return{width:e,scale:r,shownWidth:e*r}}var w="data-es-canvas-style",g=/* @__PURE__ */new WeakMap;function b(t,e){e?g.set(t,e):g.delete(t)}function p(t,e,n){const o=t.head??t.documentElement;let r=y(t,e);if(!r){r=t.createElement("style"),r.setAttribute(w,e);const n=g.get(t);n&&r.setAttribute("nonce",n),o.appendChild(r)}return r.textContent!==n&&(r.textContent=n),r}function v(t,e){y(t,e)?.remove()}function y(t,e){for(const n of Array.from(t.querySelectorAll(`style[${w}]`)))if(n.getAttribute(w)===e)return n;return null}var E="[data-easel-block]",A="[data-easel-dropzone]",C="iframe#preview-frame";function L(t){const e=t.contentDocument;if(!e||!t.contentWindow||"loading"===e.readyState||!e.body)return!1;if(t.hasAttribute("srcdoc"))return"about:srcdoc"===e.URL;const n=t.getAttribute("src");return!n||"about:blank"===n||"about:blank"!==e.URL}function x(t,e,{selector:n=C,readySelector:o}={}){let r=null,i=null,c=!1,u=!1,l=null;const s=()=>{l?.observer.disconnect(),l=null},a=()=>{if(u)return;let t=null;if(r&&L(r)){const e=r.contentDocument;(t=>{if(!o||t.querySelector(o))return s(),!0;if(l?.doc!==t){s();const e=t.defaultView?.MutationObserver;if(e){const n=new e(()=>a());n.observe(t,{childList:!0,subtree:!0}),l={doc:t,observer:n}}}return!1})(e)&&(t={frame:r,document:e,window:r.contentWindow})}else s();(t===i||!!t&&!!i&&t.frame===i.frame&&t.document===i.document)&&c||(c=!0,i=t,e(i))},d=()=>a(),f=()=>{const e=t.querySelector?.(n);e!==r?(r?.removeEventListener("load",d),r=e,r?.addEventListener("load",d),a()):a()},h=t.ownerDocument?.defaultView??t.defaultView,m=h?.MutationObserver,w=m?new m(t=>(t=>null!==r&&!r.isConnected||t.some(t=>[...t.addedNodes,...t.removedNodes].some(t=>"IFRAME"===t.nodeName||!!t.querySelector?.("iframe"))))(t)&&f()):null;return w?.observe(t,{childList:!0,subtree:!0}),f(),()=>{u=!0,w?.disconnect(),s(),r?.removeEventListener("load",d),r=null}}function M(n,{selector:o,readySelector:r}={}){const[i,c]=t(null);return e(()=>{const t=n.current;if(!t)return;const e=x(t,c,{selector:o,readySelector:r});return()=>{e(),c(null)}},[n,o,r]),i}var R="easel:canvas-typing",S="easel:canvas-typable";function B(t,o,r,{on:i="document",capture:c=!1}={}){const u=n(r);u.current=r;const l=t?.document??null,s=t?.window??null;e(()=>{const t="window"===i?s:l;if(!t)return;const e=t=>u.current(t);return t.addEventListener(o,e,c),()=>t.removeEventListener(o,e,c)},[l,s,o,i,c])}function W(e){const[n,o]=t(!1);return B(e,R,t=>o(Boolean(t.detail?.typing))),n}function k(t,n,o){const r=t?.document??null;e(()=>{if(!r)return;if(!o)return void v(r,n);const t=p(r,n,o),e=r.defaultView?.MutationObserver,i=e?new e(()=>{t.isConnected||p(r,n,o)}):null;return i?.observe(r.head??r.documentElement,{childList:!0}),()=>{i?.disconnect(),v(r,n)}},[r,n,o])}function q(n,{settle:o=[150,450]}={}){const[r,i]=t(0),c=n?.frame??null,u=n?.document??null,l=n?.window??null,s=o.join(",");return e(()=>{if(!c||!u||!l)return;const t=c.ownerDocument.defaultView;let e=!1,n=0;const r=()=>{if(e)return;e=!0;const o=()=>{e=!1,i(t=>t+1)};t?.requestAnimationFrame?n=t.requestAnimationFrame(o):o()},s=[],a=(t,e)=>{t.addEventListener(e,r,!0),s.push(()=>t.removeEventListener(e,r,!0))};a(u,"scroll"),a(l,"resize"),t&&(a(t,"scroll"),a(t,"resize"));const d=t?.ResizeObserver;if(d){const t=new d(r);t.observe(c),u.documentElement&&t.observe(u.documentElement),s.push(()=>t.disconnect())}const f=u.defaultView?.MutationObserver,h=u.body??u.documentElement;if(f&&h){const t=new f(r);t.observe(u===c.ownerDocument?c:h,{childList:!0,subtree:!0}),s.push(()=>t.disconnect())}const m=u.fonts;m&&a(m,"loadingdone");const w=o.map(t=>setTimeout(r,t));return r(),()=>{for(const t of s)t();for(const t of w)clearTimeout(t);n&&t?.cancelAnimationFrame&&t.cancelAnimationFrame(n)}},[c,u,l,s]),r}export{i as BLOCK_ATTRIBUTE,E as BLOCK_SELECTOR,C as CANVAS_SELECTOR,S as CANVAS_TYPABLE_EVENT,R as CANVAS_TYPING_EVENT,A as LIST_SELECTOR,f as clientPointToLayer,u as drawnBox,a as elementScale,m as fitCanvas,h as framePointToHost,s as frameRectToHost,d as frameRectToLayer,l as frameScale,L as isFrameReady,r as isTypingTarget,c as nodeIdAt,v as removeCanvasStyle,b as setCanvasNonce,p as upsertCanvasStyle,B as useCanvasEvent,M as useCanvasFrame,q as useCanvasLayout,k as useCanvasStyle,W as useCanvasTyping,x as watchCanvasFrame};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{useScreenBlockRules as e}from"./chunk-
|
|
1
|
+
import{useScreenBlockRules as e}from"./chunk-SJMS247S.js";import{newNodeId as t,ROOT_ZONE as n}from"./chunk-TCAAOYQY.js";import{useEasel as o,useEaselApi as r}from"./chunk-WJSEWAWK.js";import{useMemo as s}from"react";function i(i={}){const{dispatch:p}=o(e=>e),d=r(),c=!0===i.readOnly,a=e().resolveOnInsert,l=!0===(i.resolveOnInsert??a),m=!0===i.foldIntoHistory;return s(()=>{const e=m?e=>p({...e,recordHistory:!1}):p,o=(n,o,r)=>{const s=t(o);return c||e({type:"insert",componentType:o,destinationZone:n,destinationIndex:r,id:s}),s},r=e=>(l&&!c&&d.resolveNode(e,{trigger:"insert"}),e),s=(t,n,o)=>{c||e({type:"replace",destinationZone:t,destinationIndex:n,data:o})},i=(e,t,n)=>r(o(e,t,n));return{insertComponent:i,insertSection:(e,t)=>i(n,e,t),replaceComponent:s,seedChild:(e,t,n,i)=>{const p=o(e,n,t);s(e,t,{type:n,props:{id:p,...i}}),r(p)},insertNode:(e,t,n)=>{const i=o(e,n.type,t);return s(e,t,{type:n.type,props:{...n.props,id:i}}),r(i)},removeComponent:(t,n)=>{c||e({type:"remove",index:n,zone:t})},reorderComponent:(t,n,o)=>{c||e({type:"reorder",sourceIndex:n,destinationIndex:o,destinationZone:t})},duplicateComponent:(t,n)=>{c||e({type:"duplicate",sourceIndex:n,sourceZone:t})},select:e=>p({type:"setUi",ui:{itemSelector:e}}),setDocument:t=>{c||e({type:"setData",data:t})},commitDocument:(t,n)=>{c||(m?d.batch(()=>{e({type:"setData",data:t}),void 0!==n&&("slot"===n?.kind?d.selectSlot({parentId:n.parentId,slot:n.slot}):d.select(n?n.id:null))}):d.run({data:t,select:n}))}}},[p,c,l,d,m])}export{i as useSectionOps};
|