@shadow-garden/bapbong-ui 0.1.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/LICENSE +21 -0
- package/README.md +113 -0
- package/dist/index.cjs +1187 -0
- package/dist/index.d.ts +9 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +1151 -0
- package/dist/lib/cell-properties.d.ts +35 -0
- package/dist/lib/cell-properties.d.ts.map +1 -0
- package/dist/lib/context-menu.d.ts +24 -0
- package/dist/lib/context-menu.d.ts.map +1 -0
- package/dist/lib/dialog.d.ts +55 -0
- package/dist/lib/dialog.d.ts.map +1 -0
- package/dist/lib/find.d.ts +53 -0
- package/dist/lib/find.d.ts.map +1 -0
- package/dist/lib/internal.d.ts +25 -0
- package/dist/lib/internal.d.ts.map +1 -0
- package/dist/lib/menubar.d.ts +56 -0
- package/dist/lib/menubar.d.ts.map +1 -0
- package/dist/lib/table-grid.d.ts +14 -0
- package/dist/lib/table-grid.d.ts.map +1 -0
- package/dist/lib/toolbar.d.ts +73 -0
- package/dist/lib/toolbar.d.ts.map +1 -0
- package/package.json +61 -0
package/LICENSE
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 Le Phuoc Minh
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
package/README.md
ADDED
|
@@ -0,0 +1,113 @@
|
|
|
1
|
+
# @shadow-garden/bapbong-ui
|
|
2
|
+
|
|
3
|
+
**Framework-agnostic editor UI** (L3). Vanilla DOM widgets that mount into a
|
|
4
|
+
host element and bind to `editor.commands` — a host framework only supplies the
|
|
5
|
+
element and calls `mount`/`destroy`. The same lib works in Angular, React,
|
|
6
|
+
Svelte, or plain HTML.
|
|
7
|
+
|
|
8
|
+
- **Scope:** `scope:app`
|
|
9
|
+
- **Depends on:** `@shadow-garden/bapbong-contracts` only. The editor surface is
|
|
10
|
+
a structural `EditorHandle` interface (which `BapbongEditor` satisfies), and
|
|
11
|
+
the editor-state type is derived from the `Command` contract — so this package
|
|
12
|
+
imports neither the editor nor ProseMirror (same decoupling as the plugin
|
|
13
|
+
contract).
|
|
14
|
+
|
|
15
|
+
## Toolbar
|
|
16
|
+
|
|
17
|
+
```ts
|
|
18
|
+
import { mountToolbar } from '@shadow-garden/bapbong-ui';
|
|
19
|
+
|
|
20
|
+
const handle = mountToolbar(hostEl, editor); // renders + wires everything
|
|
21
|
+
// …
|
|
22
|
+
handle.destroy(); // removes DOM + listeners
|
|
23
|
+
```
|
|
24
|
+
|
|
25
|
+
- Renders a button per command from the registry; the lib owns labels/icons
|
|
26
|
+
(the headless `Command` carries none), groups, styling and active state.
|
|
27
|
+
- Click → `command.run(state, dispatch)`; active/disabled tracked via
|
|
28
|
+
`editor.onChange` + `command.isActive`/`isEnabled`.
|
|
29
|
+
- Customise with `{ groups, items }` — groups reference command names; default
|
|
30
|
+
is marks then alignments, derived from the registry.
|
|
31
|
+
- Theme via CSS variables: `--bb-ui-bg`, `--bb-ui-fg`, `--bb-ui-border`,
|
|
32
|
+
`--bb-ui-hover`, `--bb-ui-active-bg`, `--bb-ui-active-fg`.
|
|
33
|
+
|
|
34
|
+
## Menubar
|
|
35
|
+
|
|
36
|
+
```ts
|
|
37
|
+
import { mountMenubar } from '@shadow-garden/bapbong-ui';
|
|
38
|
+
|
|
39
|
+
const handle = mountMenubar(hostEl, editor); // top-level titles → dropdowns
|
|
40
|
+
handle.destroy();
|
|
41
|
+
```
|
|
42
|
+
|
|
43
|
+
- Top-level titles open dropdowns; active toggles show a check. Click-outside /
|
|
44
|
+
Escape close; hovering another title switches; submenus open on hover.
|
|
45
|
+
- Entries are a declarative tree (`{ menus, labels }`). A `MenuEntry` is one of:
|
|
46
|
+
- `'separator'`
|
|
47
|
+
- `{ command, label? }` — runs a registry command (active check + enabled).
|
|
48
|
+
- `{ label, run, isActive?, isEnabled?, shortcut? }` — a **host action**
|
|
49
|
+
(File > Open, View > comment mode, Help…).
|
|
50
|
+
- `{ label, submenu: MenuEntry[] }` — a nested dropdown.
|
|
51
|
+
- `{ label, widget: (close) => HTMLElement }` — custom flyout content.
|
|
52
|
+
- `tableGridPicker({ maxRows, maxCols, onPick })` — a Word/Docs-style size grid
|
|
53
|
+
to drop into a `widget` entry (Insert > Table).
|
|
54
|
+
|
|
55
|
+
## Context menu
|
|
56
|
+
|
|
57
|
+
```ts
|
|
58
|
+
import { showContextMenu } from '@shadow-garden/bapbong-ui';
|
|
59
|
+
|
|
60
|
+
showContextMenu(
|
|
61
|
+
[{ label: 'Cut', run, shortcut: '⌘X' }, 'separator', { label: 'Delete', run, enabled: false }],
|
|
62
|
+
{ x: ev.clientX, y: ev.clientY },
|
|
63
|
+
);
|
|
64
|
+
```
|
|
65
|
+
|
|
66
|
+
- A floating menu at a viewport point (one-shot rows + separators). Viewport-
|
|
67
|
+
clamped; closes on select / outside click / Escape / scroll; only one open at
|
|
68
|
+
a time. The host builds the entries from the editor's `contextmenu` pointer
|
|
69
|
+
event (position + target).
|
|
70
|
+
|
|
71
|
+
## Dialog
|
|
72
|
+
|
|
73
|
+
A generic overlay primitive (built on the native `<dialog>` — modal mode gets
|
|
74
|
+
focus-trap / `Esc` / backdrop for free). Reused by find, prompts, shortcuts, and
|
|
75
|
+
the cell-properties dialog — one primitive, not N bespoke widgets.
|
|
76
|
+
|
|
77
|
+
```ts
|
|
78
|
+
import { Dialog, promptDialog } from '@shadow-garden/bapbong-ui';
|
|
79
|
+
|
|
80
|
+
const dlg = new Dialog({ title: 'Cell properties', modal: true });
|
|
81
|
+
dlg.setContent(myFormElement);
|
|
82
|
+
dlg.open(); // open() / close() / onClose() / destroy()
|
|
83
|
+
|
|
84
|
+
const url = await promptDialog({ title: 'Insert link', placeholder: 'https://…' });
|
|
85
|
+
```
|
|
86
|
+
|
|
87
|
+
Pass `{ anchor: () => el.getBoundingClientRect() }` to pin a non-modal dialog's
|
|
88
|
+
top-right just inside a rect (e.g. the canvas viewport) instead of the screen
|
|
89
|
+
corner; it re-positions on scroll/resize.
|
|
90
|
+
|
|
91
|
+
## Find dialog
|
|
92
|
+
|
|
93
|
+
```ts
|
|
94
|
+
import { createFindDialog } from '@shadow-garden/bapbong-ui';
|
|
95
|
+
|
|
96
|
+
const find = createFindDialog(editor.find); // bound to the find plugin
|
|
97
|
+
find.open(); // e.g. from an Edit ▸ Find menu item / Ctrl+F
|
|
98
|
+
find.destroy();
|
|
99
|
+
```
|
|
100
|
+
|
|
101
|
+
- Find/replace inside a (non-modal) `Dialog`, bound to a structural `FindHandle`
|
|
102
|
+
(the editor's `find` plugin satisfies it), so the package never imports the
|
|
103
|
+
editor. Query input, match count, prev/next, replace + replace-all; closing
|
|
104
|
+
clears the search. i18n via `{ labels }`.
|
|
105
|
+
- Opens on **Ctrl/Cmd+F** (pre-empting the browser's native find); disable with
|
|
106
|
+
`{ shortcut: false }`. Pin it with `{ anchor }` (see Dialog).
|
|
107
|
+
|
|
108
|
+
## Build / test
|
|
109
|
+
|
|
110
|
+
```sh
|
|
111
|
+
pnpm nx build @shadow-garden/bapbong-ui
|
|
112
|
+
pnpm nx test @shadow-garden/bapbong-ui # Node (DOM behaviour verified in-browser)
|
|
113
|
+
```
|