@rathkit/rte-ui 0.1.0-alpha.3 → 0.1.0-alpha.5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/ui.js CHANGED
@@ -1,5 +1,6 @@
1
1
  import { checkFields, createAnnouncer, createDialog, createMenu, createToolbar, createTooltip } from "@rathkit/rte-headless";
2
2
  import { createFindBar } from "./findbar.js";
3
+ import { createFloating } from "./floating.js";
3
4
  import { setIcon } from "./icon.js";
4
5
  import { createShortcuts } from "./shortcuts.js";
5
6
  import { createSourceView } from "./source.js";
@@ -18,7 +19,7 @@ export function createUi(editor, options) {
18
19
  const appliedClasses = new Map();
19
20
  const parts = new Map();
20
21
  const part = (el, name) => {
21
- el.setAttribute("data-rk-part", name);
22
+ el.setAttribute("data-rte-part", name);
22
23
  let set = parts.get(name);
23
24
  if (!set)
24
25
  parts.set(name, (set = new Set()));
@@ -28,7 +29,7 @@ export function createUi(editor, options) {
28
29
  return el;
29
30
  };
30
31
  const message = (key, fallback = "", values = {}) => text(style.messages, key, fallback, values);
31
- root.classList.add("rk-root");
32
+ root.classList.add("rte-root");
32
33
  part(root, "root");
33
34
  const toolbarEl = part(document.createElement("div"), "toolbar");
34
35
  const contentEl = part(document.createElement("div"), "content");
@@ -81,9 +82,9 @@ export function createUi(editor, options) {
81
82
  : given;
82
83
  style = next;
83
84
  const set = (name, value) => (value === undefined ? root.removeAttribute(name) : root.setAttribute(name, value));
84
- set("data-rk-theme", next.theme);
85
- set("data-rk-scheme", next.scheme);
86
- set("data-rk-density", next.density);
85
+ set("data-rte-theme", next.theme);
86
+ set("data-rte-scheme", next.scheme);
87
+ set("data-rte-density", next.density);
87
88
  for (const name of [...appliedTokens])
88
89
  if (!(next.tokens && name in next.tokens)) {
89
90
  root.style.removeProperty(name);
@@ -107,6 +108,7 @@ export function createUi(editor, options) {
107
108
  draw();
108
109
  findBar?.refresh();
109
110
  shortcuts.refresh();
111
+ floating?.refresh();
110
112
  }
111
113
  syncDialogs();
112
114
  }
@@ -114,6 +116,7 @@ export function createUi(editor, options) {
114
116
  return name === undefined ? undefined : style.icons?.[name];
115
117
  }
116
118
  let unbind;
119
+ let floating;
117
120
  function labelOf(item) {
118
121
  return message(`item.${item.id}`, toolbar.state(item.id)?.label ?? item.id);
119
122
  }
@@ -127,7 +130,7 @@ export function createUi(editor, options) {
127
130
  return undefined;
128
131
  if (item.kind === "select") {
129
132
  const select = part(document.createElement("select"), "select");
130
- select.setAttribute("data-rk-item", item.id);
133
+ select.setAttribute("data-rte-item", item.id);
131
134
  for (const o of item.options) {
132
135
  const option = document.createElement("option");
133
136
  option.value = String(o.value);
@@ -141,14 +144,14 @@ export function createUi(editor, options) {
141
144
  const customize = style.parts?.button;
142
145
  if (customize) {
143
146
  const el = customize({ item, state, run: (value) => toolbar.activate(item.id, value) });
144
- el.setAttribute("data-rk-part", "button");
145
- el.setAttribute("data-rk-item", item.id);
147
+ el.setAttribute("data-rte-part", "button");
148
+ el.setAttribute("data-rte-item", item.id);
146
149
  (parts.get("button") ?? parts.set("button", new Set()).get("button"))?.add(el);
147
150
  return el;
148
151
  }
149
152
  const button = part(document.createElement("button"), "button");
150
153
  button.type = "button";
151
- button.setAttribute("data-rk-item", item.id);
154
+ button.setAttribute("data-rte-item", item.id);
152
155
  const icon = part(document.createElement("span"), "icon");
153
156
  icon.setAttribute("aria-hidden", "true");
154
157
  if (setIcon(icon, iconFor(state.icon))) {
@@ -168,7 +171,7 @@ export function createUi(editor, options) {
168
171
  const host = part(document.createElement("span"), "menu-host");
169
172
  const trigger = part(document.createElement("button"), "button");
170
173
  trigger.type = "button";
171
- trigger.setAttribute("data-rk-item", item.id);
174
+ trigger.setAttribute("data-rte-item", item.id);
172
175
  const icon = part(document.createElement("span"), "icon");
173
176
  icon.setAttribute("aria-hidden", "true");
174
177
  if (setIcon(icon, iconFor(state.icon))) {
@@ -197,8 +200,8 @@ export function createUi(editor, options) {
197
200
  menuItems.set(child.id, child);
198
201
  const entry = part(document.createElement("button"), "menu-item");
199
202
  entry.type = "button";
200
- entry.setAttribute("data-rk-menuitem", "");
201
- entry.setAttribute("data-rk-menu-item", child.id);
203
+ entry.setAttribute("data-rte-menuitem", "");
204
+ entry.setAttribute("data-rte-menu-item", child.id);
202
205
  const words = part(document.createElement("span"), "label");
203
206
  const keys = part(document.createElement("span"), "menu-keys");
204
207
  if (child.kind !== "dialog" && child.swatch) {
@@ -222,7 +225,7 @@ export function createUi(editor, options) {
222
225
  popup.style.translate = `${Math.round(dx)}px`;
223
226
  },
224
227
  onSelect: (entry) => {
225
- const id = entry.getAttribute("data-rk-menu-item") ?? "";
228
+ const id = entry.getAttribute("data-rte-menu-item") ?? "";
226
229
  const child = menuItems.get(id);
227
230
  if (child?.kind === "dialog") {
228
231
  openDialog(child, trigger);
@@ -235,25 +238,25 @@ export function createUi(editor, options) {
235
238
  editor.focus();
236
239
  },
237
240
  });
238
- for (const entry of popup.querySelectorAll("[data-rk-menu-item]")) {
239
- if (menuItems.get(entry.getAttribute("data-rk-menu-item") ?? "")?.kind === "toggle")
241
+ for (const entry of popup.querySelectorAll("[data-rte-menu-item]")) {
242
+ if (menuItems.get(entry.getAttribute("data-rte-menu-item") ?? "")?.kind === "toggle")
240
243
  entry.setAttribute("role", "menuitemcheckbox");
241
244
  }
242
245
  menus.push(menu);
243
246
  return host;
244
247
  }
245
248
  function menuEntries() {
246
- for (const entry of toolbarEl.querySelectorAll("[data-rk-menu-item]")) {
247
- const id = entry.getAttribute("data-rk-menu-item") ?? "";
249
+ for (const entry of toolbarEl.querySelectorAll("[data-rte-menu-item]")) {
250
+ const id = entry.getAttribute("data-rte-menu-item") ?? "";
248
251
  const child = menuItems.get(id);
249
252
  const state = toolbar.state(id);
250
253
  if (!child || !state)
251
254
  continue;
252
255
  const label = labelOf(child);
253
- const words = entry.querySelector('[data-rk-part="label"]');
256
+ const words = entry.querySelector('[data-rte-part="label"]');
254
257
  if (words)
255
258
  words.textContent = label;
256
- const keys = entry.querySelector('[data-rk-part="menu-keys"]');
259
+ const keys = entry.querySelector('[data-rte-part="menu-keys"]');
257
260
  if (keys)
258
261
  keys.textContent = state.shortcutLabel ?? "";
259
262
  if (state.shortcut)
@@ -302,17 +305,17 @@ export function createUi(editor, options) {
302
305
  menuEntries();
303
306
  }
304
307
  function names() {
305
- for (const el of toolbarEl.querySelectorAll("[data-rk-item]")) {
306
- const id = el.getAttribute("data-rk-item") ?? "";
308
+ for (const el of toolbarEl.querySelectorAll("[data-rte-item]")) {
309
+ const id = el.getAttribute("data-rte-item") ?? "";
307
310
  const item = toolbar.items.find((i) => i.id === id);
308
311
  const state = toolbar.state(id);
309
312
  if (!item || !state)
310
313
  continue;
311
314
  const label = labelOf(item);
312
315
  el.setAttribute("aria-label", label);
313
- el.setAttribute("data-rk-tip", state.shortcutLabel ? `${label} (${state.shortcutLabel})` : label);
316
+ el.setAttribute("data-rte-tip", state.shortcutLabel ? `${label} (${state.shortcutLabel})` : label);
314
317
  if (el.tagName === "BUTTON") {
315
- const word = el.querySelector('[data-rk-part="label"]');
318
+ const word = el.querySelector('[data-rte-part="label"]');
316
319
  if (word)
317
320
  word.textContent = label;
318
321
  }
@@ -329,10 +332,10 @@ export function createUi(editor, options) {
329
332
  });
330
333
  let drawn = "";
331
334
  const onToolbarClick = (e) => {
332
- const el = e.target?.closest("[data-rk-item]");
335
+ const el = e.target?.closest("[data-rte-item]");
333
336
  if (!el)
334
337
  return;
335
- const item = toolbar.items.find((i) => i.id === el.getAttribute("data-rk-item"));
338
+ const item = toolbar.items.find((i) => i.id === el.getAttribute("data-rte-item"));
336
339
  const state = item ? toolbar.state(item.id) : undefined;
337
340
  if (item?.kind === "toggle" && state && !state.disabled) {
338
341
  const group = item.group === "align" || item.group === "lists";
@@ -353,7 +356,7 @@ export function createUi(editor, options) {
353
356
  let entry = dialogs.get(item.id);
354
357
  if (!entry) {
355
358
  const element = part(document.createElement("dialog"), "dialog");
356
- const titleId = `rk-dialog-title-${++counter}`;
359
+ const titleId = `rte-dialog-title-${++counter}`;
357
360
  element.setAttribute("aria-labelledby", titleId);
358
361
  const form = document.createElement("form");
359
362
  form.noValidate = true;
@@ -361,7 +364,7 @@ export function createUi(editor, options) {
361
364
  title.id = titleId;
362
365
  form.appendChild(title);
363
366
  for (const field of item.fields) {
364
- const inputId = `rk-field-${++counter}`;
367
+ const inputId = `rte-field-${++counter}`;
365
368
  const label = part(document.createElement("label"), "field-label");
366
369
  label.htmlFor = inputId;
367
370
  label.textContent = field.label;
@@ -385,7 +388,7 @@ export function createUi(editor, options) {
385
388
  if (field.required)
386
389
  input.required = true;
387
390
  const error = part(document.createElement("span"), "field-error");
388
- error.setAttribute("data-rk-error", field.name);
391
+ error.setAttribute("data-rte-error", field.name);
389
392
  if (field.type === "checkbox") {
390
393
  const row = part(document.createElement("div"), "field-check");
391
394
  row.append(input, label);
@@ -433,7 +436,7 @@ export function createUi(editor, options) {
433
436
  for (const f of item.fields) {
434
437
  const bad = entry.form.querySelector(`[name="${f.name}"]`);
435
438
  bad?.removeAttribute("aria-invalid");
436
- const err = entry.form.querySelector(`[data-rk-error="${f.name}"]`);
439
+ const err = entry.form.querySelector(`[data-rte-error="${f.name}"]`);
437
440
  if (err)
438
441
  err.textContent = "";
439
442
  }
@@ -442,6 +445,13 @@ export function createUi(editor, options) {
442
445
  }
443
446
  drawn = toolbar.items.map((i) => i.id).join("\u0000");
444
447
  applyStyle(options.style ?? {});
448
+ floating = options.selectionToolbar || options.contextMenu
449
+ ? createFloating({
450
+ editor, root, selectionToolbar: options.selectionToolbar === true, contextMenu: options.contextMenu === true,
451
+ part: (el, name) => part(el, name), message: (key, fallback) => message(key, fallback), icon: (name) => iconFor(name),
452
+ openDialog,
453
+ })
454
+ : undefined;
445
455
  if (stopStatus)
446
456
  showStatus();
447
457
  return {
@@ -456,6 +466,7 @@ export function createUi(editor, options) {
456
466
  tipEl.remove();
457
467
  stopStatus?.();
458
468
  findBar?.destroy();
469
+ floating?.destroy();
459
470
  sourceView?.destroy();
460
471
  removeSourceItem?.();
461
472
  shortcuts.destroy();
@@ -472,8 +483,9 @@ export function createUi(editor, options) {
472
483
  announcer.destroy();
473
484
  toolbar.destroy();
474
485
  toolbarEl.remove();
475
- root.classList.remove("rk-root");
476
- for (const name of ["data-rk-theme", "data-rk-scheme", "data-rk-density", "data-rk-part"])
486
+ contentEl.replaceWith(...contentEl.childNodes);
487
+ root.classList.remove("rte-root");
488
+ for (const name of ["data-rte-theme", "data-rte-scheme", "data-rte-density", "data-rte-part"])
477
489
  root.removeAttribute(name);
478
490
  for (const t of appliedTokens)
479
491
  root.style.removeProperty(t);
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@rathkit/rte-ui",
3
- "version": "0.1.0-alpha.3",
3
+ "version": "0.1.0-alpha.5",
4
4
  "description": "The styled editor interface: a toolbar and dialogs on the headless layer, themeable with tokens, presets, icons and messages.",
5
5
  "keywords": [
6
6
  "rich-text",
@@ -24,7 +24,8 @@
24
24
  },
25
25
  "type": "module",
26
26
  "sideEffects": [
27
- "*.css"
27
+ "*.css",
28
+ "./dist/element-define.js"
28
29
  ],
29
30
  "engines": {
30
31
  "node": ">=22.14.0"
@@ -49,13 +50,21 @@
49
50
  "types": "./dist/standard.d.ts",
50
51
  "default": "./dist/standard.js"
51
52
  },
53
+ "./element": {
54
+ "types": "./dist/element.d.ts",
55
+ "default": "./dist/element.js"
56
+ },
57
+ "./element/define": {
58
+ "types": "./dist/element-define.d.ts",
59
+ "default": "./dist/element-define.js"
60
+ },
52
61
  "./base.css": "./css/base.css"
53
62
  },
54
63
  "peerDependencies": {
55
- "@rathkit/rte-core": ">=0.1.0-alpha.3 <0.2.0",
56
- "@rathkit/rte-headless": ">=0.1.0-alpha.3 <0.2.0",
57
- "@rathkit/rte-themes": ">=0.1.0-alpha.3 <0.2.0",
58
- "@rathkit/rte-icons": ">=0.1.0-alpha.3 <0.2.0"
64
+ "@rathkit/rte-core": ">=0.1.0-alpha.5 <0.2.0",
65
+ "@rathkit/rte-headless": ">=0.1.0-alpha.5 <0.2.0",
66
+ "@rathkit/rte-themes": ">=0.1.0-alpha.5 <0.2.0",
67
+ "@rathkit/rte-icons": ">=0.1.0-alpha.5 <0.2.0"
59
68
  },
60
69
  "peerDependenciesMeta": {
61
70
  "@rathkit/rte-core": {
@@ -93,6 +102,11 @@
93
102
  "name": "ui with default icons",
94
103
  "entry": "dist/standard.js",
95
104
  "gzipKB": 30
105
+ },
106
+ {
107
+ "name": "ui element",
108
+ "entry": "dist/element.js",
109
+ "gzipKB": 30
96
110
  }
97
111
  ]
98
112
  }