erl-mathtextx-editor 0.1.7 → 0.1.9

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 (30) hide show
  1. package/CHANGELOG.md +157 -0
  2. package/README.md +268 -253
  3. package/dist/{CellPropertiesDialogImpl-HPT77uxM.js → CellPropertiesDialogImpl-DBgs-7H9.js} +1 -1
  4. package/dist/{ContentViewer-CWZ30KYR.js → ContentViewer-CsFSAN_B.js} +15 -15
  5. package/dist/ImageInsertDialog-B24KHrgt.js +238 -0
  6. package/dist/{InsertTableDialogImpl-DZrLgDKN.js → InsertTableDialogImpl-B6_PRu5m.js} +1 -1
  7. package/dist/{LinkDialogImpl-DTHugWZM.js → LinkDialogImpl-BTA8u_qQ.js} +60 -45
  8. package/dist/TablePropertiesDialogImpl-CuRRWS4H.js +56 -0
  9. package/dist/{TableTemplatesDialogImpl-D0sFSAKl.js → TableTemplatesDialogImpl-CU8seEdV.js} +1 -1
  10. package/dist/assets/erl-mathtextx-editor.css +1 -1
  11. package/dist/assets/viewer.css +1 -1
  12. package/dist/components/TablePropertiesDialog.d.ts +4 -0
  13. package/dist/components/TablePropertiesDialogImpl.d.ts +11 -0
  14. package/dist/core/extensions.d.ts +6 -0
  15. package/dist/erl-mathtextx-editor.js +14 -13
  16. package/dist/erl-mathtextx-editor.umd.cjs +163 -153
  17. package/dist/extensions/CustomIndent.d.ts +10 -0
  18. package/dist/extensions/IndentBackspace.d.ts +2 -0
  19. package/dist/extensions/SlashGraph.d.ts +2 -0
  20. package/dist/extensions/TableAlignPlugin.d.ts +7 -0
  21. package/dist/{index-CLGg8QXp.js → index-CB1g0gXh.js} +177 -199
  22. package/dist/index-UCSefQk0.js +53830 -0
  23. package/dist/index.d.ts +2 -0
  24. package/dist/math/MathFieldView.d.ts +5 -0
  25. package/dist/{tiptap-Bc1mIOtx.js → tiptap-K3rU-Wjn.js} +4325 -3155
  26. package/dist/utils/logger.d.ts +40 -0
  27. package/dist/viewer.js +1 -1
  28. package/package.json +7 -18
  29. package/dist/ImageInsertDialog-DzLFhSDK.js +0 -217
  30. package/dist/index-Ci20X1Rj.js +0 -5281
@@ -0,0 +1,40 @@
1
+ /**
2
+ * Logger utility for the editor package.
3
+ * Logs only in development mode to avoid information disclosure in production.
4
+ * TODO: Add integration with error tracking service (Sentry, etc.) for production
5
+ */
6
+ /**
7
+ * Logger object with methods for different log levels.
8
+ * In production, these are no-ops to prevent console noise and info disclosure.
9
+ */
10
+ export declare const logger: {
11
+ /**
12
+ * Log error messages. In production, consider sending to error tracking service.
13
+ */
14
+ error: (message: string, error?: unknown) => void;
15
+ /**
16
+ * Log warning messages.
17
+ */
18
+ warn: (message: string, data?: unknown) => void;
19
+ /**
20
+ * Log informational messages (uses warn in dev to comply with ESLint rules).
21
+ */
22
+ info: (message: string, data?: unknown) => void;
23
+ /**
24
+ * Log debug messages (verbose logging for development, uses warn in dev).
25
+ */
26
+ debug: (message: string, data?: unknown) => void;
27
+ };
28
+ /**
29
+ * Type-safe error handler that captures both message and error object.
30
+ * Use this for async operations where you need to handle errors.
31
+ */
32
+ export declare function handleError(context: string, error: unknown, options?: {
33
+ silent?: boolean;
34
+ fallbackMessage?: string;
35
+ }): void;
36
+ /**
37
+ * Wrap a function with error logging.
38
+ * Useful for event handlers and callbacks.
39
+ */
40
+ export declare function withErrorLogging<T extends (...args: unknown[]) => unknown>(fn: T, context: string): (...args: Parameters<T>) => ReturnType<T> | undefined;
package/dist/viewer.js CHANGED
@@ -1,4 +1,4 @@
1
- import { C as r } from "./ContentViewer-CWZ30KYR.js";
1
+ import { C as r } from "./ContentViewer-CsFSAN_B.js";
2
2
  export {
3
3
  r as ContentViewer
4
4
  };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "erl-mathtextx-editor",
3
- "version": "0.1.7",
3
+ "version": "0.1.9",
4
4
  "description": "Visual math editor component for solutest.id — CKEditor replacement with zero-LaTeX approach",
5
5
  "type": "module",
6
6
  "main": "./dist/erl-mathtextx-editor.umd.cjs",
@@ -20,7 +20,10 @@
20
20
  "./viewer/styles": "./dist/viewer-styles.js"
21
21
  },
22
22
  "files": [
23
- "dist"
23
+ "dist",
24
+ "README.md",
25
+ "CHANGELOG.md",
26
+ "LICENSE"
24
27
  ],
25
28
  "scripts": {
26
29
  "dev": "vite",
@@ -37,27 +40,13 @@
37
40
  },
38
41
  "dependencies": {
39
42
  "@tiptap/core": "^2.11.0",
40
- "@tiptap/extension-bold": "^2.11.0",
41
- "@tiptap/extension-bullet-list": "^2.11.0",
42
- "@tiptap/extension-code-block": "^2.11.0",
43
+ "@tiptap/extension-code-block-lowlight": "^2.11.0",
43
44
  "@tiptap/extension-color": "^2.27.2",
44
- "@tiptap/extension-document": "^2.11.0",
45
- "@tiptap/extension-dropcursor": "^2.11.0",
46
45
  "@tiptap/extension-font-family": "^2.27.2",
47
- "@tiptap/extension-gapcursor": "^2.11.0",
48
- "@tiptap/extension-hard-break": "^2.11.0",
49
- "@tiptap/extension-heading": "^2.11.0",
50
46
  "@tiptap/extension-highlight": "^2.27.2",
51
- "@tiptap/extension-history": "^2.11.0",
52
- "@tiptap/extension-horizontal-rule": "^2.11.0",
53
47
  "@tiptap/extension-image": "^2.11.0",
54
- "@tiptap/extension-italic": "^2.11.0",
55
48
  "@tiptap/extension-link": "^2.11.0",
56
- "@tiptap/extension-list-item": "^2.11.0",
57
- "@tiptap/extension-ordered-list": "^2.11.0",
58
- "@tiptap/extension-paragraph": "^2.11.0",
59
49
  "@tiptap/extension-placeholder": "^2.11.0",
60
- "@tiptap/extension-strike": "^2.11.0",
61
50
  "@tiptap/extension-subscript": "^2.11.0",
62
51
  "@tiptap/extension-superscript": "^2.11.0",
63
52
  "@tiptap/extension-table": "^2.11.0",
@@ -66,7 +55,6 @@
66
55
  "@tiptap/extension-table-row": "^2.11.0",
67
56
  "@tiptap/extension-task-item": "^2.11.0",
68
57
  "@tiptap/extension-task-list": "^2.11.0",
69
- "@tiptap/extension-text": "^2.11.0",
70
58
  "@tiptap/extension-text-align": "^2.27.2",
71
59
  "@tiptap/extension-text-style": "^2.27.2",
72
60
  "@tiptap/extension-typography": "^2.27.2",
@@ -80,6 +68,7 @@
80
68
  "html2canvas": "^1.4.1",
81
69
  "jspdf": "^4.1.0",
82
70
  "katex": "^0.16.33",
71
+ "lowlight": "^3.3.0",
83
72
  "mathlive": "^0.101.0"
84
73
  },
85
74
  "devDependencies": {
@@ -1,217 +0,0 @@
1
- import { jsxs as l, Fragment as E, jsx as e } from "react/jsx-runtime";
2
- import { useId as I, useRef as P, useState as c, useCallback as n } from "react";
3
- import { u as W } from "./index-Ci20X1Rj.js";
4
- function O({
5
- isOpen: f,
6
- onClose: x,
7
- onInsert: m,
8
- onImageUpload: p
9
- }) {
10
- const k = I(), N = P(null), [g, y] = c(p ? "upload" : "url"), [t, U] = c(""), [d, w] = c(""), [F, h] = c(!1), [G, b] = c(!1), [v, s] = c(null), [D, i] = c(""), R = P(null), C = n(() => {
11
- U(""), w(""), s(null), i(""), b(!1), h(!1);
12
- }, []), r = n(() => {
13
- C(), x();
14
- }, [x, C]);
15
- W({ isOpen: f, dialogRef: N, onClose: r });
16
- const _ = n(
17
- async (a) => {
18
- if (!a.type.startsWith("image/")) {
19
- i("File harus berupa gambar (jpg, png, gif, webp)");
20
- return;
21
- }
22
- if (a.size > 10 * 1024 * 1024) {
23
- i("Ukuran file maksimal 10MB");
24
- return;
25
- }
26
- i("");
27
- const o = URL.createObjectURL(a);
28
- if (s(o), p) {
29
- b(!0);
30
- try {
31
- const u = await p(a);
32
- m(u, d || a.name), r();
33
- } catch {
34
- i("Upload gagal. Silakan coba lagi."), s(null);
35
- } finally {
36
- b(!1);
37
- }
38
- } else {
39
- const u = new FileReader();
40
- u.onload = () => {
41
- const T = u.result;
42
- m(T, d || a.name), r();
43
- }, u.readAsDataURL(a);
44
- }
45
- },
46
- [p, m, d, r]
47
- ), M = n(
48
- (a) => {
49
- const o = a.target.files?.[0];
50
- o && _(o);
51
- },
52
- [_]
53
- ), S = n((a) => {
54
- a.preventDefault(), a.stopPropagation(), h(!0);
55
- }, []), j = n((a) => {
56
- a.preventDefault(), a.stopPropagation(), h(!1);
57
- }, []), A = n(
58
- (a) => {
59
- a.preventDefault(), a.stopPropagation(), h(!1);
60
- const o = a.dataTransfer.files?.[0];
61
- o && _(o);
62
- },
63
- [_]
64
- ), L = n(() => {
65
- if (!t.trim()) {
66
- i("Masukkan URL gambar");
67
- return;
68
- }
69
- try {
70
- new URL(t);
71
- } catch {
72
- i("URL tidak valid");
73
- return;
74
- }
75
- m(t.trim(), d || void 0), r();
76
- }, [t, d, m, r]), B = n(() => {
77
- if (t.trim())
78
- try {
79
- new URL(t), s(t.trim()), i("");
80
- } catch {
81
- i("URL tidak valid");
82
- }
83
- }, [t]);
84
- return f ? /* @__PURE__ */ l(E, { children: [
85
- /* @__PURE__ */ e("div", { className: "mtx-dialog-overlay", onClick: r }),
86
- /* @__PURE__ */ l("div", { className: "mtx-image-dialog", ref: N, role: "dialog", "aria-modal": "true", "aria-labelledby": k, tabIndex: -1, children: [
87
- /* @__PURE__ */ l("div", { className: "mtx-image-dialog__header", children: [
88
- /* @__PURE__ */ e("h3", { id: k, children: "Sisipkan Gambar" }),
89
- /* @__PURE__ */ e(
90
- "button",
91
- {
92
- className: "mtx-image-dialog__close",
93
- onClick: r,
94
- "aria-label": "Tutup",
95
- children: "✕"
96
- }
97
- )
98
- ] }),
99
- /* @__PURE__ */ l("div", { className: "mtx-image-dialog__tabs", children: [
100
- /* @__PURE__ */ e(
101
- "button",
102
- {
103
- className: `mtx-image-dialog__tab ${g === "upload" ? "is-active" : ""}`,
104
- onClick: () => {
105
- y("upload"), i(""), s(null);
106
- },
107
- children: "📁 Upload File"
108
- }
109
- ),
110
- /* @__PURE__ */ e(
111
- "button",
112
- {
113
- className: `mtx-image-dialog__tab ${g === "url" ? "is-active" : ""}`,
114
- onClick: () => {
115
- y("url"), i(""), s(null);
116
- },
117
- children: "🔗 URL"
118
- }
119
- )
120
- ] }),
121
- /* @__PURE__ */ l("div", { className: "mtx-image-dialog__body", children: [
122
- g === "upload" && /* @__PURE__ */ l(
123
- "div",
124
- {
125
- className: `mtx-image-dialog__dropzone ${F ? "is-dragging" : ""}`,
126
- onDragOver: S,
127
- onDragLeave: j,
128
- onDrop: A,
129
- onClick: () => R.current?.click(),
130
- children: [
131
- /* @__PURE__ */ e(
132
- "input",
133
- {
134
- ref: R,
135
- type: "file",
136
- accept: "image/*",
137
- onChange: M,
138
- style: { display: "none" }
139
- }
140
- ),
141
- G ? /* @__PURE__ */ l("div", { className: "mtx-image-dialog__uploading", children: [
142
- /* @__PURE__ */ e("div", { className: "mtx-spinner" }),
143
- /* @__PURE__ */ e("p", { children: "Mengupload gambar..." })
144
- ] }) : v ? /* @__PURE__ */ e("div", { className: "mtx-image-dialog__preview", children: /* @__PURE__ */ e("img", { src: v, alt: "Preview" }) }) : /* @__PURE__ */ l("div", { className: "mtx-image-dialog__placeholder", children: [
145
- /* @__PURE__ */ l("svg", { width: "48", height: "48", viewBox: "0 0 48 48", fill: "none", stroke: "currentColor", strokeWidth: "1.5", children: [
146
- /* @__PURE__ */ e("rect", { x: "4", y: "8", width: "40", height: "32", rx: "4" }),
147
- /* @__PURE__ */ e("circle", { cx: "16", cy: "20", r: "4" }),
148
- /* @__PURE__ */ e("path", { d: "M4 36l10-10 6 6 8-10 16 14" })
149
- ] }),
150
- /* @__PURE__ */ l("p", { children: [
151
- /* @__PURE__ */ e("strong", { children: "Klik untuk pilih file" }),
152
- " atau drag & drop ke sini"
153
- ] }),
154
- /* @__PURE__ */ e("span", { children: "JPG, PNG, GIF, WebP — Maks 10MB" })
155
- ] })
156
- ]
157
- }
158
- ),
159
- g === "url" && /* @__PURE__ */ l("div", { className: "mtx-image-dialog__url-form", children: [
160
- /* @__PURE__ */ e("label", { children: "URL Gambar" }),
161
- /* @__PURE__ */ e("div", { className: "mtx-image-dialog__url-row", children: /* @__PURE__ */ e(
162
- "input",
163
- {
164
- type: "url",
165
- value: t,
166
- onChange: (a) => U(a.target.value),
167
- placeholder: "https://example.com/gambar.jpg",
168
- onKeyDown: (a) => {
169
- a.key === "Enter" && L();
170
- },
171
- onBlur: B,
172
- autoFocus: !0
173
- }
174
- ) }),
175
- v && /* @__PURE__ */ e("div", { className: "mtx-image-dialog__url-preview", children: /* @__PURE__ */ e(
176
- "img",
177
- {
178
- src: v,
179
- alt: "Preview",
180
- onError: () => {
181
- s(null), i("Gambar tidak dapat dimuat dari URL ini");
182
- }
183
- }
184
- ) })
185
- ] }),
186
- /* @__PURE__ */ l("div", { className: "mtx-image-dialog__alt", children: [
187
- /* @__PURE__ */ e("label", { children: "Teks Alternatif (opsional)" }),
188
- /* @__PURE__ */ e(
189
- "input",
190
- {
191
- type: "text",
192
- value: d,
193
- onChange: (a) => w(a.target.value),
194
- placeholder: "Deskripsi gambar untuk aksesibilitas"
195
- }
196
- )
197
- ] }),
198
- D && /* @__PURE__ */ e("div", { className: "mtx-image-dialog__error", children: D })
199
- ] }),
200
- /* @__PURE__ */ l("div", { className: "mtx-image-dialog__footer", children: [
201
- /* @__PURE__ */ e("button", { className: "mtx-image-dialog__btn mtx-image-dialog__btn--cancel", onClick: r, children: "Batal" }),
202
- g === "url" && /* @__PURE__ */ e(
203
- "button",
204
- {
205
- className: "mtx-image-dialog__btn mtx-image-dialog__btn--insert",
206
- onClick: L,
207
- disabled: !t.trim(),
208
- children: "Sisipkan"
209
- }
210
- )
211
- ] })
212
- ] })
213
- ] }) : null;
214
- }
215
- export {
216
- O as ImageInsertDialog
217
- };