@dotvoid/textbit-plugins 0.0.0-stage → 0.1.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (91) hide show
  1. package/LICENSE +7 -0
  2. package/README.md +194 -2
  3. package/dist/Audio/audioNode.cjs +1 -0
  4. package/dist/Audio/audioNode.d.ts +8 -0
  5. package/dist/Audio/audioNode.d.ts.map +1 -0
  6. package/dist/Audio/audioNode.js +15 -0
  7. package/dist/Audio/index.cjs +1 -0
  8. package/dist/Audio/index.d.ts +22 -0
  9. package/dist/Audio/index.d.ts.map +1 -0
  10. package/dist/Audio/index.js +63 -0
  11. package/dist/Blockquote/index.cjs +1 -0
  12. package/dist/Blockquote/index.d.ts +15 -0
  13. package/dist/Blockquote/index.d.ts.map +1 -0
  14. package/dist/Blockquote/index.js +56 -0
  15. package/dist/CodeBlock/index.cjs +1 -0
  16. package/dist/CodeBlock/index.d.ts +14 -0
  17. package/dist/CodeBlock/index.d.ts.map +1 -0
  18. package/dist/CodeBlock/index.js +65 -0
  19. package/dist/Image/imageNode.cjs +1 -0
  20. package/dist/Image/imageNode.d.ts +11 -0
  21. package/dist/Image/imageNode.d.ts.map +1 -0
  22. package/dist/Image/imageNode.js +16 -0
  23. package/dist/Image/index.cjs +1 -0
  24. package/dist/Image/index.d.ts +37 -0
  25. package/dist/Image/index.d.ts.map +1 -0
  26. package/dist/Image/index.js +92 -0
  27. package/dist/Leafs/index.cjs +1 -0
  28. package/dist/Leafs/index.d.ts +13 -0
  29. package/dist/Leafs/index.d.ts.map +1 -0
  30. package/dist/Leafs/index.js +66 -0
  31. package/dist/Link/index.cjs +1 -0
  32. package/dist/Link/index.d.ts +25 -0
  33. package/dist/Link/index.d.ts.map +1 -0
  34. package/dist/Link/index.js +148 -0
  35. package/dist/Link/isValidLink.cjs +1 -0
  36. package/dist/Link/isValidLink.d.ts +3 -0
  37. package/dist/Link/isValidLink.d.ts.map +1 -0
  38. package/dist/Link/isValidLink.js +35 -0
  39. package/dist/List/index.cjs +1 -0
  40. package/dist/List/index.d.ts +17 -0
  41. package/dist/List/index.d.ts.map +1 -0
  42. package/dist/List/index.js +151 -0
  43. package/dist/LocalizedQuotationMarks/consume.cjs +1 -0
  44. package/dist/LocalizedQuotationMarks/consume.d.ts +3 -0
  45. package/dist/LocalizedQuotationMarks/consume.d.ts.map +1 -0
  46. package/dist/LocalizedQuotationMarks/consume.js +115 -0
  47. package/dist/LocalizedQuotationMarks/consumes.cjs +1 -0
  48. package/dist/LocalizedQuotationMarks/consumes.d.ts +3 -0
  49. package/dist/LocalizedQuotationMarks/consumes.d.ts.map +1 -0
  50. package/dist/LocalizedQuotationMarks/consumes.js +7 -0
  51. package/dist/LocalizedQuotationMarks/index.cjs +1 -0
  52. package/dist/LocalizedQuotationMarks/index.d.ts +9 -0
  53. package/dist/LocalizedQuotationMarks/index.d.ts.map +1 -0
  54. package/dist/LocalizedQuotationMarks/index.js +13 -0
  55. package/dist/Table/index.cjs +1 -0
  56. package/dist/Table/index.d.ts +16 -0
  57. package/dist/Table/index.d.ts.map +1 -0
  58. package/dist/Table/index.js +179 -0
  59. package/dist/Text/index.cjs +1 -0
  60. package/dist/Text/index.d.ts +25 -0
  61. package/dist/Text/index.d.ts.map +1 -0
  62. package/dist/Text/index.js +64 -0
  63. package/dist/index.cjs +1 -0
  64. package/dist/index.d.ts +13 -0
  65. package/dist/index.d.ts.map +1 -0
  66. package/dist/index.js +31 -0
  67. package/dist/shared/ChildPlaceholder.cjs +1 -0
  68. package/dist/shared/ChildPlaceholder.d.ts +12 -0
  69. package/dist/shared/ChildPlaceholder.d.ts.map +1 -0
  70. package/dist/shared/ChildPlaceholder.js +17 -0
  71. package/dist/shared/Field.cjs +1 -0
  72. package/dist/shared/Field.d.ts +14 -0
  73. package/dist/shared/Field.d.ts.map +1 -0
  74. package/dist/shared/Field.js +28 -0
  75. package/dist/shared/hotkey.cjs +1 -0
  76. package/dist/shared/hotkey.d.ts +3 -0
  77. package/dist/shared/hotkey.d.ts.map +1 -0
  78. package/dist/shared/hotkey.js +6 -0
  79. package/dist/shared/icons.cjs +1 -0
  80. package/dist/shared/icons.d.ts +62 -0
  81. package/dist/shared/icons.d.ts.map +1 -0
  82. package/dist/shared/icons.js +153 -0
  83. package/dist/shared/insertBlock.cjs +1 -0
  84. package/dist/shared/insertBlock.d.ts +5 -0
  85. package/dist/shared/insertBlock.d.ts.map +1 -0
  86. package/dist/shared/insertBlock.js +13 -0
  87. package/dist/shared/media.cjs +1 -0
  88. package/dist/shared/media.d.ts +25 -0
  89. package/dist/shared/media.d.ts.map +1 -0
  90. package/dist/shared/media.js +43 -0
  91. package/package.json +67 -4
@@ -0,0 +1,115 @@
1
+ import { Editor as d, Text as T, Transforms as p, Path as g, Node as y } from "slate";
2
+ const O = {
3
+ sv: ["’", "’", "”", "”"],
4
+ fi: ["’", "’", "”", "”"],
5
+ hu: ["’", "’", "„", "”"],
6
+ pl: ["‚", "’", "„", "”"],
7
+ no: ["‹", "›", "«", "»"],
8
+ en: ["‘", "’", "“", "”"],
9
+ da: ["„", "“", "„", "“"],
10
+ de: ["‚", "‘", "„", "“"],
11
+ fr: ["‹ ", " ›", "« ", " »"]
12
+ }, b = {
13
+ sv: "–"
14
+ }, I = [
15
+ 9,
16
+ // tab
17
+ 32,
18
+ // space
19
+ 60,
20
+ // non breaking space
21
+ 33,
22
+ // !
23
+ 40,
24
+ // (
25
+ 41,
26
+ // )
27
+ 43,
28
+ // +
29
+ 44,
30
+ // ,
31
+ 45,
32
+ // -
33
+ 46,
34
+ // .
35
+ 47,
36
+ // /
37
+ 58,
38
+ // :
39
+ 59,
40
+ // ;
41
+ 60,
42
+ // <
43
+ 61,
44
+ // =
45
+ 62,
46
+ // >
47
+ 63
48
+ // ?
49
+ ], m = async ({ editor: e, input: r }) => {
50
+ const { selection: t } = e, f = e.lang.substring(0, 2).toLowerCase();
51
+ if (Array.isArray(r) || typeof r.data != "string" || !t || t.anchor.path.length < 2)
52
+ return;
53
+ const { data: s } = r;
54
+ if (s[0] === "-" && b[f] && L(e, t))
55
+ return {
56
+ ...r,
57
+ data: b[f] + s.slice(1)
58
+ };
59
+ if (s[0] === "-") {
60
+ const { anchor: o } = t, n = d.before(e, o, { unit: "character" });
61
+ if (n) {
62
+ const [l] = d.node(e, n.path);
63
+ if (T.isText(l) && l.text[n.offset] === "-")
64
+ return p.delete(e, { at: n }), {
65
+ ...r,
66
+ data: "–"
67
+ };
68
+ }
69
+ }
70
+ const x = g.parent(t.anchor.path), u = t.anchor.path[t.anchor.path.length - 1];
71
+ let C = t.anchor.offset, c, E = "";
72
+ for (let o = u; o >= 0; o--) {
73
+ const [n, l] = d.node(e, [...x, o]);
74
+ if (T.isText(n)) {
75
+ for (let a = C || n.text.length - 1; a >= 0; a--) {
76
+ if (c) {
77
+ const A = n.text[a];
78
+ if (!isNaN(parseInt(A)) && I.includes(E.charCodeAt(0)))
79
+ return r;
80
+ o = -1;
81
+ break;
82
+ }
83
+ n.text[a] === s ? c = { path: l, offset: a } : E = n.text[a];
84
+ }
85
+ C = 0;
86
+ }
87
+ }
88
+ if (!c)
89
+ return r;
90
+ const h = O[f] || O.en;
91
+ let i = [];
92
+ if (s === "'")
93
+ i = [h[0], h[1]];
94
+ else if (s === '"')
95
+ i = [h[2], h[3]];
96
+ else
97
+ return r;
98
+ return p.delete(e, { at: c }), p.insertText(e, i[0], { at: c }), {
99
+ ...r,
100
+ data: i[1]
101
+ };
102
+ };
103
+ function L(e, r) {
104
+ const { anchor: t } = r;
105
+ if (t.path.length < 2)
106
+ return !1;
107
+ const f = g.parent(t.path), s = y.first(e, f);
108
+ if (!s)
109
+ return !1;
110
+ const [x, u] = s;
111
+ return T.isText(x) ? g.equals(t.path, u) && t.offset === 0 : !1;
112
+ }
113
+ export {
114
+ m as consume
115
+ };
@@ -0,0 +1 @@
1
+ "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const r=({input:t})=>{const{data:e,type:n}=t;return n!=="text/plain"?[!1]:e!=="'"&&e!=='"'&&e!=="-"?[!1]:[!0,"text/plain"]};exports.consumes=r;
@@ -0,0 +1,3 @@
1
+ import { TBConsumesFunction } from '@dotvoid/textbit';
2
+ export declare const consumes: TBConsumesFunction;
3
+ //# sourceMappingURL=consumes.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"consumes.d.ts","sourceRoot":"","sources":["../../lib/LocalizedQuotationMarks/consumes.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,kBAAkB,CAAA;AAE1D,eAAO,MAAM,QAAQ,EAAE,kBAYtB,CAAA"}
@@ -0,0 +1,7 @@
1
+ const r = ({ input: e }) => {
2
+ const { data: t, type: n } = e;
3
+ return n !== "text/plain" ? [!1] : t !== "'" && t !== '"' && t !== "-" ? [!1] : [!0, "text/plain"];
4
+ };
5
+ export {
6
+ r as consumes
7
+ };
@@ -0,0 +1 @@
1
+ "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const e=require("./consumes.cjs"),o=require("./consume.cjs"),s=()=>({class:"generic",name:"base/localized-quotation-marks",consumer:{consumes:e.consumes,consume:o.consume}});exports.LocalizedQuotationMarks=s;
@@ -0,0 +1,9 @@
1
+ import { TBPluginDefinition } from '@dotvoid/textbit';
2
+ /**
3
+ * Typographic quotation marks and dashes as you type, following the editor's
4
+ * language: "..." becomes “...” in English, ”...” in Swedish, «...» in Norwegian.
5
+ * Two hyphens become an en dash. Quotes inserted by commands, like the special
6
+ * characters picker, are left as they are.
7
+ */
8
+ export declare const LocalizedQuotationMarks: () => TBPluginDefinition;
9
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../lib/LocalizedQuotationMarks/index.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,kBAAkB,CAAA;AAI1D;;;;;GAKG;AACH,eAAO,MAAM,uBAAuB,QAAO,kBAOzC,CAAA"}
@@ -0,0 +1,13 @@
1
+ import { consumes as o } from "./consumes.js";
2
+ import { consume as e } from "./consume.js";
3
+ const m = () => ({
4
+ class: "generic",
5
+ name: "base/localized-quotation-marks",
6
+ consumer: {
7
+ consumes: o,
8
+ consume: e
9
+ }
10
+ });
11
+ export {
12
+ m as LocalizedQuotationMarks
13
+ };
@@ -0,0 +1 @@
1
+ "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const c=require("react/jsx-runtime"),T=require("@dotvoid/textbit"),s=require("slate"),m=require("../shared/icons.cjs"),g=require("../shared/insertBlock.cjs"),u="base/table",h=`${u}/row`,y=`${u}/row/cell`,p={insert:"Table","row-above":"Insert row above","row-below":"Insert row below","delete-row":"Delete row","column-left":"Insert column left","column-right":"Insert column right","delete-column":"Delete column"},N=(o={})=>{const r=e=>o.titles?.[e]??p[e],n=(e,t)=>{const l=t??e,a=[u,h,y].includes(l.type);return[a,a,!1]};return{class:"block",name:u,actions:[{name:"insert",title:r("insert"),tool:()=>c.jsx(m.TableIcon,{}),visibility:e=>[!0,!0,e.type===u],handler:({editor:e})=>{const t=Math.max(1,o.columns??2);g.insertBlockAfterCaret(e,{id:crypto.randomUUID(),class:"block",type:u,children:Array.from({length:Math.max(1,o.rows??2)},()=>b(t))})}},f("row-above",r("row-above"),()=>c.jsx(m.RowAboveIcon,{}),n,(e,t)=>{s.Transforms.insertNodes(e,b(t.columns),{at:[...t.tablePath,t.row]})}),f("row-below",r("row-below"),()=>c.jsx(m.RowBelowIcon,{}),n,(e,t)=>{s.Transforms.insertNodes(e,b(t.columns),{at:[...t.tablePath,t.row+1]})}),f("delete-row",r("delete-row"),()=>c.jsx(m.DeleteRowIcon,{}),n,(e,t)=>{t.rows>1&&s.Transforms.removeNodes(e,{at:[...t.tablePath,t.row]})}),f("column-left",r("column-left"),()=>c.jsx(m.ColLeftIcon,{}),n,(e,t)=>{E(e,t,t.column)}),f("column-right",r("column-right"),()=>c.jsx(m.ColRightIcon,{}),n,(e,t)=>{E(e,t,t.column+1)}),f("delete-column",r("delete-column"),()=>c.jsx(m.DeleteColIcon,{}),n,(e,t)=>{t.columns<=1||s.Editor.withoutNormalizing(e,()=>{for(let l=t.rows-1;l>=0;l--)s.Transforms.removeNodes(e,{at:[...t.tablePath,l,t.column]})})}),{name:"next-cell",hotkey:"tab",when:e=>!!d(e),visibility:()=>[!1,!1,!1],handler:({editor:e,event:t})=>{t?.preventDefault(),v(e,1)}},{name:"previous-cell",hotkey:"shift+tab",when:e=>!!d(e),visibility:()=>[!1,!1,!1],handler:({editor:e,event:t})=>{t?.preventDefault(),v(e,-1)}}],componentEntry:{class:"block",component:({children:e})=>c.jsx("table",{className:"tb-table",children:c.jsx("tbody",{children:e})}),constraints:{normalizeNode:I},children:[{type:"row",class:"block",asOwnElement:!0,component:({children:e,attributes:t})=>c.jsx("tr",{...t,className:"tb-table-row",children:e}),children:[{type:"cell",class:"text",asOwnElement:!0,component:({children:e,attributes:t})=>c.jsx("td",{...t,className:"tb-table-cell",children:e}),constraints:{allowBreak:!1}}]}]}}};function f(o,r,n,e,t){return{name:o,title:r,tool:n,visibility:e,handler:({editor:l})=>{const a=d(l);a&&t(l,a)}}}function d(o){const{selection:r}=o;if(!r)return;const[n]=s.Editor.nodes(o,{at:r.anchor,match:i=>s.Element.isElement(i)&&i.type===y});if(!n)return;const e=n[1],t=e.slice(0,-2),l=s.Node.get(o,t),a=s.Node.get(o,e.slice(0,-1));if(!(!s.Element.isElement(l)||l.type!==u||!s.Element.isElement(a)))return{tablePath:t,row:e[e.length-2],column:e[e.length-1],rows:l.children.length,columns:a.children.length}}function v(o,r){const n=d(o);if(!n)return;let{row:e,column:t}=n;t+=r,t>=n.columns?(t=0,e+=1):t<0&&(t=n.columns-1,e-=1),!(e<0)&&(e>=n.rows&&s.Transforms.insertNodes(o,b(n.columns),{at:[...n.tablePath,e]}),s.Transforms.select(o,s.Editor.start(o,[...n.tablePath,e,t])))}function E(o,r,n){s.Editor.withoutNormalizing(o,()=>{for(let e=0;e<r.rows;e++)s.Transforms.insertNodes(o,x(),{at:[...r.tablePath,e,n]})})}function b(o){return{id:crypto.randomUUID(),class:"block",type:h,children:Array.from({length:o},x)}}function x(){return{id:crypto.randomUUID(),class:"text",type:y,children:[{text:""}]}}function I(o,[r,n]){if(!s.Element.isElement(r))return;if(r.children.length===0)return s.Transforms.removeNodes(o,{at:n}),!0;for(const[i,w]of r.children.entries())if(T.TextbitElement.isElement(w)&&w.class==="block"&&w.type!==h)return s.Transforms.setNodes(o,{type:h},{at:[...n,i]}),!0;const e=r.children.map(i=>s.Element.isElement(i)?i.children.length:0),t=e.indexOf(0);if(t!==-1)return s.Transforms.removeNodes(o,{at:[...n,t]}),!0;const l=Math.max(...e),a=e.findIndex(i=>i<l);if(a!==-1)return s.Transforms.insertNodes(o,Array.from({length:l-e[a]},x),{at:[...n,a,e[a]]}),!0}exports.Table=N;
@@ -0,0 +1,16 @@
1
+ import { TBPluginDefinition } from '@dotvoid/textbit';
2
+ type TableAction = 'insert' | 'row-above' | 'row-below' | 'delete-row' | 'column-left' | 'column-right' | 'delete-column';
3
+ export type TableOptions = {
4
+ /** Size of a new table. Default: 2 by 2. */
5
+ rows?: number;
6
+ columns?: number;
7
+ /** Action names in menus and for screen readers, e.g. translations */
8
+ titles?: Partial<Record<TableAction, string>>;
9
+ };
10
+ /**
11
+ * A simple table of text cells. Tab and Shift+Tab move between cells; Tab in
12
+ * the last cell adds a row.
13
+ */
14
+ export declare const Table: (options?: TableOptions) => TBPluginDefinition;
15
+ export {};
16
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../lib/Table/index.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAgD,kBAAkB,EAAE,MAAM,kBAAkB,CAAA;AAkBxG,KAAK,WAAW,GAAG,QAAQ,GAAG,WAAW,GAAG,WAAW,GAAG,YAAY,GAAG,aAAa,GAAG,cAAc,GAAG,eAAe,CAAA;AAEzH,MAAM,MAAM,YAAY,GAAG;IACzB,4CAA4C;IAC5C,IAAI,CAAC,EAAE,MAAM,CAAA;IACb,OAAO,CAAC,EAAE,MAAM,CAAA;IAChB,sEAAsE;IACtE,MAAM,CAAC,EAAE,OAAO,CAAC,MAAM,CAAC,WAAW,EAAE,MAAM,CAAC,CAAC,CAAA;CAC9C,CAAA;AAYD;;;GAGG;AACH,eAAO,MAAM,KAAK,GAAI,UAAS,YAAiB,KAAG,kBAwGlD,CAAA"}
@@ -0,0 +1,179 @@
1
+ import { jsx as c } from "react/jsx-runtime";
2
+ import { TextbitElement as E } from "@dotvoid/textbit";
3
+ import { Element as f, Transforms as a, Editor as d, Node as g } from "slate";
4
+ import { TableIcon as x, RowAboveIcon as k, RowBelowIcon as P, DeleteRowIcon as T, ColLeftIcon as C, ColRightIcon as D, DeleteColIcon as A } from "../shared/icons.js";
5
+ import { insertBlockAfterCaret as R } from "../shared/insertBlock.js";
6
+ const m = "base/table", b = `${m}/row`, p = `${m}/row/cell`, U = {
7
+ insert: "Table",
8
+ "row-above": "Insert row above",
9
+ "row-below": "Insert row below",
10
+ "delete-row": "Delete row",
11
+ "column-left": "Insert column left",
12
+ "column-right": "Insert column right",
13
+ "delete-column": "Delete column"
14
+ }, j = (o = {}) => {
15
+ const l = (e) => o.titles?.[e] ?? U[e], n = (e, t) => {
16
+ const r = t ?? e, s = [m, b, p].includes(r.type);
17
+ return [s, s, !1];
18
+ };
19
+ return {
20
+ class: "block",
21
+ name: m,
22
+ actions: [
23
+ {
24
+ name: "insert",
25
+ title: l("insert"),
26
+ tool: () => /* @__PURE__ */ c(x, {}),
27
+ visibility: (e) => [!0, !0, e.type === m],
28
+ handler: ({ editor: e }) => {
29
+ const t = Math.max(1, o.columns ?? 2);
30
+ R(e, {
31
+ id: crypto.randomUUID(),
32
+ class: "block",
33
+ type: m,
34
+ children: Array.from({ length: Math.max(1, o.rows ?? 2) }, () => h(t))
35
+ });
36
+ }
37
+ },
38
+ u("row-above", l("row-above"), () => /* @__PURE__ */ c(k, {}), n, (e, t) => {
39
+ a.insertNodes(e, h(t.columns), { at: [...t.tablePath, t.row] });
40
+ }),
41
+ u("row-below", l("row-below"), () => /* @__PURE__ */ c(P, {}), n, (e, t) => {
42
+ a.insertNodes(e, h(t.columns), { at: [...t.tablePath, t.row + 1] });
43
+ }),
44
+ u("delete-row", l("delete-row"), () => /* @__PURE__ */ c(T, {}), n, (e, t) => {
45
+ t.rows > 1 && a.removeNodes(e, { at: [...t.tablePath, t.row] });
46
+ }),
47
+ u("column-left", l("column-left"), () => /* @__PURE__ */ c(C, {}), n, (e, t) => {
48
+ I(e, t, t.column);
49
+ }),
50
+ u("column-right", l("column-right"), () => /* @__PURE__ */ c(D, {}), n, (e, t) => {
51
+ I(e, t, t.column + 1);
52
+ }),
53
+ u("delete-column", l("delete-column"), () => /* @__PURE__ */ c(A, {}), n, (e, t) => {
54
+ t.columns <= 1 || d.withoutNormalizing(e, () => {
55
+ for (let r = t.rows - 1; r >= 0; r--)
56
+ a.removeNodes(e, { at: [...t.tablePath, r, t.column] });
57
+ });
58
+ }),
59
+ {
60
+ name: "next-cell",
61
+ hotkey: "tab",
62
+ when: (e) => !!w(e),
63
+ visibility: () => [!1, !1, !1],
64
+ handler: ({ editor: e, event: t }) => {
65
+ t?.preventDefault(), N(e, 1);
66
+ }
67
+ },
68
+ {
69
+ name: "previous-cell",
70
+ hotkey: "shift+tab",
71
+ when: (e) => !!w(e),
72
+ visibility: () => [!1, !1, !1],
73
+ handler: ({ editor: e, event: t }) => {
74
+ t?.preventDefault(), N(e, -1);
75
+ }
76
+ }
77
+ ],
78
+ componentEntry: {
79
+ class: "block",
80
+ component: ({ children: e }) => /* @__PURE__ */ c("table", { className: "tb-table", children: /* @__PURE__ */ c("tbody", { children: e }) }),
81
+ constraints: {
82
+ normalizeNode: z
83
+ },
84
+ // Rows and cells render the <tr> and <td> themselves: a wrapping <div> is
85
+ // not allowed inside a table
86
+ children: [{
87
+ type: "row",
88
+ class: "block",
89
+ asOwnElement: !0,
90
+ component: ({ children: e, attributes: t }) => /* @__PURE__ */ c("tr", { ...t, className: "tb-table-row", children: e }),
91
+ children: [{
92
+ type: "cell",
93
+ class: "text",
94
+ asOwnElement: !0,
95
+ component: ({ children: e, attributes: t }) => /* @__PURE__ */ c("td", { ...t, className: "tb-table-cell", children: e }),
96
+ constraints: { allowBreak: !1 }
97
+ }]
98
+ }]
99
+ }
100
+ };
101
+ };
102
+ function u(o, l, n, e, t) {
103
+ return {
104
+ name: o,
105
+ title: l,
106
+ tool: n,
107
+ visibility: e,
108
+ handler: ({ editor: r }) => {
109
+ const s = w(r);
110
+ s && t(r, s);
111
+ }
112
+ };
113
+ }
114
+ function w(o) {
115
+ const { selection: l } = o;
116
+ if (!l)
117
+ return;
118
+ const [n] = d.nodes(o, {
119
+ at: l.anchor,
120
+ match: (i) => f.isElement(i) && i.type === p
121
+ });
122
+ if (!n)
123
+ return;
124
+ const e = n[1], t = e.slice(0, -2), r = g.get(o, t), s = g.get(o, e.slice(0, -1));
125
+ if (!(!f.isElement(r) || r.type !== m || !f.isElement(s)))
126
+ return {
127
+ tablePath: t,
128
+ row: e[e.length - 2],
129
+ column: e[e.length - 1],
130
+ rows: r.children.length,
131
+ columns: s.children.length
132
+ };
133
+ }
134
+ function N(o, l) {
135
+ const n = w(o);
136
+ if (!n)
137
+ return;
138
+ let { row: e, column: t } = n;
139
+ t += l, t >= n.columns ? (t = 0, e += 1) : t < 0 && (t = n.columns - 1, e -= 1), !(e < 0) && (e >= n.rows && a.insertNodes(o, h(n.columns), { at: [...n.tablePath, e] }), a.select(o, d.start(o, [...n.tablePath, e, t])));
140
+ }
141
+ function I(o, l, n) {
142
+ d.withoutNormalizing(o, () => {
143
+ for (let e = 0; e < l.rows; e++)
144
+ a.insertNodes(o, v(), { at: [...l.tablePath, e, n] });
145
+ });
146
+ }
147
+ function h(o) {
148
+ return {
149
+ id: crypto.randomUUID(),
150
+ class: "block",
151
+ type: b,
152
+ children: Array.from({ length: o }, v)
153
+ };
154
+ }
155
+ function v() {
156
+ return { id: crypto.randomUUID(), class: "text", type: p, children: [{ text: "" }] };
157
+ }
158
+ function z(o, [l, n]) {
159
+ if (!f.isElement(l))
160
+ return;
161
+ if (l.children.length === 0)
162
+ return a.removeNodes(o, { at: n }), !0;
163
+ for (const [i, y] of l.children.entries())
164
+ if (E.isElement(y) && y.class === "block" && y.type !== b)
165
+ return a.setNodes(o, { type: b }, { at: [...n, i] }), !0;
166
+ const e = l.children.map((i) => f.isElement(i) ? i.children.length : 0), t = e.indexOf(0);
167
+ if (t !== -1)
168
+ return a.removeNodes(o, { at: [...n, t] }), !0;
169
+ const r = Math.max(...e), s = e.findIndex((i) => i < r);
170
+ if (s !== -1)
171
+ return a.insertNodes(
172
+ o,
173
+ Array.from({ length: r - e[s] }, v),
174
+ { at: [...n, s, e[s]] }
175
+ ), !0;
176
+ }
177
+ export {
178
+ j as Table
179
+ };
@@ -0,0 +1 @@
1
+ "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const n=require("react/jsx-runtime"),s=require("@dotvoid/textbit"),i=require("../shared/icons.cjs"),d=require("../shared/hotkey.cjs"),u={paragraph:()=>n.jsx(i.ParagraphIcon,{}),preamble:()=>n.jsx(i.PreambleIcon,{}),"heading-1":()=>n.jsx(i.Heading1Icon,{}),"heading-2":()=>n.jsx(i.Heading2Icon,{}),"heading-3":()=>n.jsx(i.Heading3Icon,{}),"heading-4":()=>n.jsx(i.Heading4Icon,{})},T=(e={})=>{const{headings:a=[1,2,3,4],preamble:r=!0,singleLine:o=!1}=e,l=["paragraph",...a.map(t=>`heading-${t}`),...r?["preamble"]:[]];return{class:"text",name:s.TEXT_TYPE,componentEntry:{class:"text",component:m,placeholder:t=>e.placeholders?.[g(t)]??"",constraints:{allowBreak:!o,allowSoftBreak:!o}},actions:l.map(t=>({name:t==="paragraph"?"set-paragraph":`set-${t}`,title:e.titles?.[t]??x(t),tool:u[t],hotkey:d.hotkeyOption(e.hotkeys?.[t],b(t)),visibility:(p,h)=>{const c=h??p;return[c.type===s.TEXT_TYPE,!0,c.type===s.TEXT_TYPE&&g(c)===t]},handler:({editor:p})=>{s.TextbitEditor.convertToTextNode(p,s.TEXT_TYPE,t==="paragraph"?void 0:t)}}))}};function m({element:e,children:a}){const r=g(e),o=r==="paragraph"||r==="preamble"?"p":`h${r.slice(-1)}`;return n.jsx(o,{className:`tb-text tb-${r}`,children:a})}function g(e){const a=e.properties?.role;return typeof a=="string"&&/^(heading-[1-6]|preamble)$/.test(a)?a:"paragraph"}function x(e){return e==="paragraph"?"Paragraph":e==="preamble"?"Lead-in":`Heading ${e.slice(-1)}`}function b(e){if(e!=="preamble")return`mod+alt+${e==="paragraph"?0:e.slice(-1)}`}exports.Text=T;
@@ -0,0 +1,25 @@
1
+ import { TBPluginDefinition } from '@dotvoid/textbit';
2
+ export type HeadingLevel = 1 | 2 | 3 | 4 | 5 | 6;
3
+ export type TextRole = 'paragraph' | 'preamble' | `heading-${HeadingLevel}`;
4
+ export type TextOptions = {
5
+ /** Heading levels to offer. Default: 1 to 4. */
6
+ headings?: HeadingLevel[];
7
+ /** Offer a lead-in: the larger opening paragraph of an article. Default: true. */
8
+ preamble?: boolean;
9
+ /** Single line text, like a title field: no Enter, no soft breaks */
10
+ singleLine?: boolean;
11
+ /** Action names in menus and for screen readers, e.g. translations */
12
+ titles?: Partial<Record<TextRole, string>>;
13
+ /** Hint shown in an empty block, per role */
14
+ placeholders?: Partial<Record<TextRole, string>>;
15
+ /** Replace a role's shortcut, or remove it with `false` */
16
+ hotkeys?: Partial<Record<TextRole, string | false>>;
17
+ };
18
+ /**
19
+ * Paragraphs, headings and a lead-in. Replaces the editor's built-in `base/text`
20
+ * plugin and keeps its document format: a paragraph has no role, a heading has
21
+ * the role `heading-1` to `heading-6` and renders as the matching h1 to h6, and
22
+ * a lead-in has the role `preamble` and renders as a paragraph.
23
+ */
24
+ export declare const Text: (options?: TextOptions) => TBPluginDefinition;
25
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../lib/Text/index.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,kBAAkB,EAAoB,MAAM,kBAAkB,CAAA;AAa5E,MAAM,MAAM,YAAY,GAAG,CAAC,GAAG,CAAC,GAAG,CAAC,GAAG,CAAC,GAAG,CAAC,GAAG,CAAC,CAAA;AAChD,MAAM,MAAM,QAAQ,GAAG,WAAW,GAAG,UAAU,GAAG,WAAW,YAAY,EAAE,CAAA;AAE3E,MAAM,MAAM,WAAW,GAAG;IACxB,gDAAgD;IAChD,QAAQ,CAAC,EAAE,YAAY,EAAE,CAAA;IACzB,kFAAkF;IAClF,QAAQ,CAAC,EAAE,OAAO,CAAA;IAClB,qEAAqE;IACrE,UAAU,CAAC,EAAE,OAAO,CAAA;IACpB,sEAAsE;IACtE,MAAM,CAAC,EAAE,OAAO,CAAC,MAAM,CAAC,QAAQ,EAAE,MAAM,CAAC,CAAC,CAAA;IAC1C,6CAA6C;IAC7C,YAAY,CAAC,EAAE,OAAO,CAAC,MAAM,CAAC,QAAQ,EAAE,MAAM,CAAC,CAAC,CAAA;IAChD,2DAA2D;IAC3D,OAAO,CAAC,EAAE,OAAO,CAAC,MAAM,CAAC,QAAQ,EAAE,MAAM,GAAG,KAAK,CAAC,CAAC,CAAA;CACpD,CAAA;AAWD;;;;;GAKG;AACH,eAAO,MAAM,IAAI,GAAI,UAAS,WAAgB,KAAG,kBAoChD,CAAA"}
@@ -0,0 +1,64 @@
1
+ import { jsx as r } from "react/jsx-runtime";
2
+ import { TEXT_TYPE as o, TextbitEditor as l } from "@dotvoid/textbit";
3
+ import { Heading4Icon as m, Heading3Icon as d, Heading2Icon as f, Heading1Icon as u, PreambleIcon as b, ParagraphIcon as T } from "../shared/icons.js";
4
+ import { hotkeyOption as x } from "../shared/hotkey.js";
5
+ const y = {
6
+ paragraph: () => /* @__PURE__ */ r(T, {}),
7
+ preamble: () => /* @__PURE__ */ r(b, {}),
8
+ "heading-1": () => /* @__PURE__ */ r(u, {}),
9
+ "heading-2": () => /* @__PURE__ */ r(f, {}),
10
+ "heading-3": () => /* @__PURE__ */ r(d, {}),
11
+ "heading-4": () => /* @__PURE__ */ r(m, {})
12
+ }, N = (e = {}) => {
13
+ const { headings: t = [1, 2, 3, 4], preamble: n = !0, singleLine: p = !1 } = e, g = [
14
+ "paragraph",
15
+ ...t.map((a) => `heading-${a}`),
16
+ ...n ? ["preamble"] : []
17
+ ];
18
+ return {
19
+ class: "text",
20
+ name: o,
21
+ componentEntry: {
22
+ class: "text",
23
+ component: I,
24
+ placeholder: (a) => e.placeholders?.[s(a)] ?? "",
25
+ constraints: {
26
+ allowBreak: !p,
27
+ allowSoftBreak: !p
28
+ }
29
+ },
30
+ actions: g.map((a) => ({
31
+ name: a === "paragraph" ? "set-paragraph" : `set-${a}`,
32
+ title: e.titles?.[a] ?? $(a),
33
+ tool: y[a],
34
+ // Ctrl+Alt+digit as in Google Docs; Cmd+Option+digit on macOS. The lead-in
35
+ // has none by default: no free key is an obvious fit.
36
+ hotkey: x(e.hotkeys?.[a], k(a)),
37
+ visibility: (i, h) => {
38
+ const c = h ?? i;
39
+ return [c.type === o, !0, c.type === o && s(c) === a];
40
+ },
41
+ handler: ({ editor: i }) => {
42
+ l.convertToTextNode(i, o, a === "paragraph" ? void 0 : a);
43
+ }
44
+ }))
45
+ };
46
+ };
47
+ function I({ element: e, children: t }) {
48
+ const n = s(e), p = n === "paragraph" || n === "preamble" ? "p" : `h${n.slice(-1)}`;
49
+ return /* @__PURE__ */ r(p, { className: `tb-text tb-${n}`, children: t });
50
+ }
51
+ function s(e) {
52
+ const t = e.properties?.role;
53
+ return typeof t == "string" && /^(heading-[1-6]|preamble)$/.test(t) ? t : "paragraph";
54
+ }
55
+ function $(e) {
56
+ return e === "paragraph" ? "Paragraph" : e === "preamble" ? "Lead-in" : `Heading ${e.slice(-1)}`;
57
+ }
58
+ function k(e) {
59
+ if (e !== "preamble")
60
+ return `mod+alt+${e === "paragraph" ? 0 : e.slice(-1)}`;
61
+ }
62
+ export {
63
+ N as Text
64
+ };
package/dist/index.cjs ADDED
@@ -0,0 +1 @@
1
+ "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const e=require("./Leafs/index.cjs"),o=require("./Text/index.cjs"),i=require("./List/index.cjs"),r=require("./CodeBlock/index.cjs"),d=require("./Table/index.cjs"),t=require("./Link/index.cjs"),n=require("./LocalizedQuotationMarks/index.cjs"),u=require("./Image/index.cjs"),c=require("./Image/imageNode.cjs"),a=require("./Audio/index.cjs"),s=require("./Audio/audioNode.cjs"),l=require("./Blockquote/index.cjs");exports.Bold=e.Bold;exports.Code=e.Code;exports.Italic=e.Italic;exports.Strikethrough=e.Strikethrough;exports.Underline=e.Underline;exports.Text=o.Text;exports.OrderedList=i.OrderedList;exports.UnorderedList=i.UnorderedList;exports.CodeBlock=r.CodeBlock;exports.Table=d.Table;exports.Link=t.Link;exports.LocalizedQuotationMarks=n.LocalizedQuotationMarks;exports.Image=u.Image;exports.imageNode=c.imageNode;exports.Audio=a.Audio;exports.audioNode=s.audioNode;exports.Blockquote=l.Blockquote;
@@ -0,0 +1,13 @@
1
+ export { Bold, Italic, Underline, Strikethrough, Code, type LeafOptions } from './Leafs';
2
+ export { Text, type TextOptions, type TextRole, type HeadingLevel } from './Text';
3
+ export { UnorderedList, OrderedList, type ListOptions } from './List';
4
+ export { CodeBlock, type CodeBlockOptions } from './CodeBlock';
5
+ export { Table, type TableOptions } from './Table';
6
+ export { Link, type LinkOptions, type LinkLabels } from './Link';
7
+ export { LocalizedQuotationMarks } from './LocalizedQuotationMarks';
8
+ export { Image, type ImageOptions, type ImageLabels } from './Image';
9
+ export { imageNode, type ImageUpload } from './Image/imageNode';
10
+ export { Audio, type AudioOptions, type AudioLabels } from './Audio';
11
+ export { audioNode, type AudioUpload } from './Audio/audioNode';
12
+ export { Blockquote, type BlockquoteOptions, type BlockquoteLabels } from './Blockquote';
13
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../lib/index.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,IAAI,EAAE,MAAM,EAAE,SAAS,EAAE,aAAa,EAAE,IAAI,EAAE,KAAK,WAAW,EAAE,MAAM,SAAS,CAAA;AACxF,OAAO,EAAE,IAAI,EAAE,KAAK,WAAW,EAAE,KAAK,QAAQ,EAAE,KAAK,YAAY,EAAE,MAAM,QAAQ,CAAA;AACjF,OAAO,EAAE,aAAa,EAAE,WAAW,EAAE,KAAK,WAAW,EAAE,MAAM,QAAQ,CAAA;AACrE,OAAO,EAAE,SAAS,EAAE,KAAK,gBAAgB,EAAE,MAAM,aAAa,CAAA;AAC9D,OAAO,EAAE,KAAK,EAAE,KAAK,YAAY,EAAE,MAAM,SAAS,CAAA;AAClD,OAAO,EAAE,IAAI,EAAE,KAAK,WAAW,EAAE,KAAK,UAAU,EAAE,MAAM,QAAQ,CAAA;AAChE,OAAO,EAAE,uBAAuB,EAAE,MAAM,2BAA2B,CAAA;AACnE,OAAO,EAAE,KAAK,EAAE,KAAK,YAAY,EAAE,KAAK,WAAW,EAAE,MAAM,SAAS,CAAA;AACpE,OAAO,EAAE,SAAS,EAAE,KAAK,WAAW,EAAE,MAAM,mBAAmB,CAAA;AAC/D,OAAO,EAAE,KAAK,EAAE,KAAK,YAAY,EAAE,KAAK,WAAW,EAAE,MAAM,SAAS,CAAA;AACpE,OAAO,EAAE,SAAS,EAAE,KAAK,WAAW,EAAE,MAAM,mBAAmB,CAAA;AAC/D,OAAO,EAAE,UAAU,EAAE,KAAK,iBAAiB,EAAE,KAAK,gBAAgB,EAAE,MAAM,cAAc,CAAA"}
package/dist/index.js ADDED
@@ -0,0 +1,31 @@
1
+ import { Bold as e, Code as t, Italic as m, Strikethrough as d, Underline as x } from "./Leafs/index.js";
2
+ import { Text as p } from "./Text/index.js";
3
+ import { OrderedList as a, UnorderedList as l } from "./List/index.js";
4
+ import { CodeBlock as n } from "./CodeBlock/index.js";
5
+ import { Table as c } from "./Table/index.js";
6
+ import { Link as g } from "./Link/index.js";
7
+ import { LocalizedQuotationMarks as B } from "./LocalizedQuotationMarks/index.js";
8
+ import { Image as C } from "./Image/index.js";
9
+ import { imageNode as N } from "./Image/imageNode.js";
10
+ import { Audio as U } from "./Audio/index.js";
11
+ import { audioNode as q } from "./Audio/audioNode.js";
12
+ import { Blockquote as A } from "./Blockquote/index.js";
13
+ export {
14
+ U as Audio,
15
+ A as Blockquote,
16
+ e as Bold,
17
+ t as Code,
18
+ n as CodeBlock,
19
+ C as Image,
20
+ m as Italic,
21
+ g as Link,
22
+ B as LocalizedQuotationMarks,
23
+ a as OrderedList,
24
+ d as Strikethrough,
25
+ c as Table,
26
+ p as Text,
27
+ x as Underline,
28
+ l as UnorderedList,
29
+ q as audioNode,
30
+ N as imageNode
31
+ };
@@ -0,0 +1 @@
1
+ "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const n=require("react/jsx-runtime"),l=require("slate");function r({element:t,children:e}){return!e||l.Node.string(t).length>0?null:n.jsx("span",{contentEditable:!1,"aria-hidden":"true",className:"tb-child-placeholder",style:{position:"absolute",inset:0,pointerEvents:"none",userSelect:"none"},children:e})}exports.ChildPlaceholder=r;
@@ -0,0 +1,12 @@
1
+ import { Element } from 'slate';
2
+ /**
3
+ * Hint text over an empty nested text element: a code block body, a caption, a
4
+ * list item. Textbit's own placeholders only cover top-level text. Positioned
5
+ * over the element and ignored by pointer and screen reader; style the text
6
+ * with .tb-child-placeholder.
7
+ */
8
+ export declare function ChildPlaceholder({ element, children }: {
9
+ element: Element;
10
+ children?: React.ReactNode;
11
+ }): import("react").JSX.Element | null;
12
+ //# sourceMappingURL=ChildPlaceholder.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ChildPlaceholder.d.ts","sourceRoot":"","sources":["../../lib/shared/ChildPlaceholder.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAQ,KAAK,OAAO,EAAE,MAAM,OAAO,CAAA;AAE1C;;;;;GAKG;AACH,wBAAgB,gBAAgB,CAAC,EAAE,OAAO,EAAE,QAAQ,EAAE,EAAE;IACtD,OAAO,EAAE,OAAO,CAAA;IAChB,QAAQ,CAAC,EAAE,KAAK,CAAC,SAAS,CAAA;CAC3B,sCAeA"}
@@ -0,0 +1,17 @@
1
+ import { jsx as n } from "react/jsx-runtime";
2
+ import { Node as o } from "slate";
3
+ function i({ element: t, children: e }) {
4
+ return !e || o.string(t).length > 0 ? null : /* @__PURE__ */ n(
5
+ "span",
6
+ {
7
+ contentEditable: !1,
8
+ "aria-hidden": "true",
9
+ className: "tb-child-placeholder",
10
+ style: { position: "absolute", inset: 0, pointerEvents: "none", userSelect: "none" },
11
+ children: e
12
+ }
13
+ );
14
+ }
15
+ export {
16
+ i as ChildPlaceholder
17
+ };
@@ -0,0 +1 @@
1
+ "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const e=require("react/jsx-runtime"),l=require("slate"),s=require("slate-react"),c=require("./ChildPlaceholder.cjs");function d({element:n,label:r,hint:i,children:o}){const t=s.useSlateStatic();return e.jsxs(e.Fragment,{children:[e.jsx("span",{contentEditable:!1,className:"tb-field-label",style:{userSelect:"none"},onMouseDown:a=>{a.preventDefault(),l.Transforms.select(t,l.Editor.end(t,s.ReactEditor.findPath(t,n))),s.ReactEditor.focus(t)},children:r}),e.jsxs("span",{className:"tb-field-text",style:{position:"relative"},children:[e.jsx(c.ChildPlaceholder,{element:n,children:i}),o]})]})}exports.FieldContent=d;
@@ -0,0 +1,14 @@
1
+ import { Element } from 'slate';
2
+ /**
3
+ * The inside of a labelled text field in a block, such as an image's caption.
4
+ * The field is a text element, so the caret moves in and out of it like any
5
+ * other text. The label is not editable; a click on it puts the caret in the
6
+ * field, like a <label>. Style with .tb-field-label and .tb-field-text.
7
+ */
8
+ export declare function FieldContent({ element, label, hint, children }: {
9
+ element: Element;
10
+ label: string;
11
+ hint?: string;
12
+ children: React.ReactNode;
13
+ }): import("react").JSX.Element;
14
+ //# sourceMappingURL=Field.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"Field.d.ts","sourceRoot":"","sources":["../../lib/shared/Field.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAsB,KAAK,OAAO,EAAE,MAAM,OAAO,CAAA;AAIxD;;;;;GAKG;AACH,wBAAgB,YAAY,CAAC,EAAE,OAAO,EAAE,KAAK,EAAE,IAAI,EAAE,QAAQ,EAAE,EAAE;IAC/D,OAAO,EAAE,OAAO,CAAA;IAChB,KAAK,EAAE,MAAM,CAAA;IACb,IAAI,CAAC,EAAE,MAAM,CAAA;IACb,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAA;CAC1B,+BAuBA"}
@@ -0,0 +1,28 @@
1
+ import { jsxs as o, Fragment as c, jsx as r } from "react/jsx-runtime";
2
+ import { Transforms as d, Editor as f } from "slate";
3
+ import { useSlateStatic as m, ReactEditor as n } from "slate-react";
4
+ import { ChildPlaceholder as p } from "./ChildPlaceholder.js";
5
+ function E({ element: t, label: i, hint: l, children: s }) {
6
+ const e = m();
7
+ return /* @__PURE__ */ o(c, { children: [
8
+ /* @__PURE__ */ r(
9
+ "span",
10
+ {
11
+ contentEditable: !1,
12
+ className: "tb-field-label",
13
+ style: { userSelect: "none" },
14
+ onMouseDown: (a) => {
15
+ a.preventDefault(), d.select(e, f.end(e, n.findPath(e, t))), n.focus(e);
16
+ },
17
+ children: i
18
+ }
19
+ ),
20
+ /* @__PURE__ */ o("span", { className: "tb-field-text", style: { position: "relative" }, children: [
21
+ /* @__PURE__ */ r(p, { element: t, children: l }),
22
+ s
23
+ ] })
24
+ ] });
25
+ }
26
+ export {
27
+ E as FieldContent
28
+ };
@@ -0,0 +1 @@
1
+ "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});function o(e,t){return e===!1?void 0:e??t}exports.hotkeyOption=o;
@@ -0,0 +1,3 @@
1
+ /** An option's shortcut: a replacement, `false` to remove it, or the default */
2
+ export declare function hotkeyOption(option: string | false | undefined, fallback?: string): string | undefined;
3
+ //# sourceMappingURL=hotkey.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"hotkey.d.ts","sourceRoot":"","sources":["../../lib/shared/hotkey.ts"],"names":[],"mappings":"AAAA,gFAAgF;AAChF,wBAAgB,YAAY,CAAC,MAAM,EAAE,MAAM,GAAG,KAAK,GAAG,SAAS,EAAE,QAAQ,CAAC,EAAE,MAAM,GAAG,MAAM,GAAG,SAAS,CAEtG"}
@@ -0,0 +1,6 @@
1
+ function n(e, t) {
2
+ return e === !1 ? void 0 : e ?? t;
3
+ }
4
+ export {
5
+ n as hotkeyOption
6
+ };