diff --git a/package-lock.json b/package-lock.json index 907e77c..07f3ae0 100644 --- a/package-lock.json +++ b/package-lock.json @@ -11,6 +11,21 @@ "@blocknote/core": "^0.42.0", "@blocknote/react": "^0.42.0", "@blocknote/shadcn": "^0.42.0", + "@editorjs/checklist": "^1.6.0", + "@editorjs/code": "^2.9.3", + "@editorjs/delimiter": "^1.4.2", + "@editorjs/editorjs": "^2.31.0", + "@editorjs/embed": "^2.7.6", + "@editorjs/header": "^2.8.8", + "@editorjs/image": "^2.10.3", + "@editorjs/inline-code": "^1.5.2", + "@editorjs/link": "^2.6.2", + "@editorjs/list": "^2.0.9", + "@editorjs/marker": "^1.4.0", + "@editorjs/paragraph": "^2.11.7", + "@editorjs/quote": "^2.7.6", + "@editorjs/table": "^2.4.5", + "@editorjs/warning": "^1.4.1", "@hello-pangea/dnd": "^18.0.1", "@radix-ui/react-collapsible": "^1.1.12", "@radix-ui/react-dialog": "^1.1.15", @@ -32,7 +47,7 @@ }, "devDependencies": { "@tailwindcss/postcss": "^4", - "@types/node": "^20.19.24", + "@types/node": "^20.19.25", "@types/react": "^19", "@types/react-dom": "^19", "tailwindcss": "^4", @@ -188,6 +203,222 @@ "url": "https://github.com/sponsors/dcastil" } }, + "node_modules/@codexteam/icons": { + "version": "0.3.3", + "resolved": "https://registry.npmjs.org/@codexteam/icons/-/icons-0.3.3.tgz", + "integrity": "sha512-cp7mkZPgmBuSxigTm3Vb+DtVHYeX7qXfQd7o05vcLD8Ag5WvRlol2QSn5P10k0CDAJwmkH9nQGQLBycErS9lsQ==", + "license": "MIT" + }, + "node_modules/@editorjs/caret": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/@editorjs/caret/-/caret-1.0.3.tgz", + "integrity": "sha512-VmgwQJZgL/LQjk049JunzRV1YCa0vDi+BNEpbDmr5cp3lGZllq9QQFO1eI71ZPzvFVn3vvhb+eOif4sAEyGgbw==", + "license": "MIT", + "dependencies": { + "@editorjs/dom": "^1.0.1" + } + }, + "node_modules/@editorjs/checklist": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/@editorjs/checklist/-/checklist-1.6.0.tgz", + "integrity": "sha512-hRNP36DInr73mSK3noHBQeoQb7DA12ANfqTXufEkTgQzx+k4mRJ0HdeGukTIR4JbwjHJ9ecUBnnQqIEGnxCFEg==", + "license": "MIT", + "dependencies": { + "@codexteam/icons": "^0.3.0" + } + }, + "node_modules/@editorjs/code": { + "version": "2.9.3", + "resolved": "https://registry.npmjs.org/@editorjs/code/-/code-2.9.3.tgz", + "integrity": "sha512-nXUrK3CjhpubvShYtcbkpZ9SU15IYwmJOsWZrlWYSzy9unZBRQthii6eABndsCtODzzV0yiSKmTp00RQkFow3Q==", + "license": "MIT", + "dependencies": { + "@codexteam/icons": "^0.3.2" + } + }, + "node_modules/@editorjs/delimiter": { + "version": "1.4.2", + "resolved": "https://registry.npmjs.org/@editorjs/delimiter/-/delimiter-1.4.2.tgz", + "integrity": "sha512-S8q2LpeYdYkVShLp7K8c4HLthDHBevLw+sT+iO0+SH0oMvFmld9SUon3DFzMQ2gG07EOdZGRZ958+sVxyvFjZw==", + "license": "MIT", + "dependencies": { + "@codexteam/icons": "^0.3.2" + } + }, + "node_modules/@editorjs/dom": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/@editorjs/dom/-/dom-1.0.1.tgz", + "integrity": "sha512-yLO+86MYOIUr1Jl7SQw23SYT84ggv6aJW0EIRsI3NTHYgnQzmK7Bt2n5ZFupQlB0GJqmKqA5tCue3NKQb+o7Pw==", + "license": "MIT", + "dependencies": { + "@editorjs/helpers": "^1.0.1" + } + }, + "node_modules/@editorjs/editorjs": { + "version": "2.31.0", + "resolved": "https://registry.npmjs.org/@editorjs/editorjs/-/editorjs-2.31.0.tgz", + "integrity": "sha512-CBcIZXtPlg0dSlC5clO9OfTCmcxelj723jd4d67teFlaFJobjjxU1PmMxFJdhaRep5+nqdD0jr+fdJBqEDqt1g==", + "license": "Apache-2.0", + "dependencies": { + "@editorjs/caret": "^1.0.1", + "codex-notifier": "^1.1.2", + "codex-tooltip": "^1.0.5" + } + }, + "node_modules/@editorjs/embed": { + "version": "2.7.6", + "resolved": "https://registry.npmjs.org/@editorjs/embed/-/embed-2.7.6.tgz", + "integrity": "sha512-L3agW/23mOI0L+oksUE9UOR5VSNCqapxLH5lma+5j+idjKCC31nxbx07x53MSJ4rlOTO1L7cFVhkqptEdOliJA==", + "license": "MIT", + "dependencies": { + "@editorjs/editorjs": "^2.29.1" + } + }, + "node_modules/@editorjs/header": { + "version": "2.8.8", + "resolved": "https://registry.npmjs.org/@editorjs/header/-/header-2.8.8.tgz", + "integrity": "sha512-bsMSs34u2hoi0UBuRoc5EGWXIFzJiwYgkFUYQGVm63y5FU+s8zPBmVx5Ip2sw1xgs0fqfDROqmteMvvmbCy62w==", + "license": "MIT", + "dependencies": { + "@codexteam/icons": "^0.0.5", + "@editorjs/editorjs": "^2.29.1" + } + }, + "node_modules/@editorjs/header/node_modules/@codexteam/icons": { + "version": "0.0.5", + "resolved": "https://registry.npmjs.org/@codexteam/icons/-/icons-0.0.5.tgz", + "integrity": "sha512-s6H2KXhLz2rgbMZSkRm8dsMJvyUNZsEjxobBEg9ztdrb1B2H3pEzY6iTwI4XUPJWJ3c3qRKwV4TrO3J5jUdoQA==", + "license": "MIT" + }, + "node_modules/@editorjs/helpers": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/@editorjs/helpers/-/helpers-1.0.1.tgz", + "integrity": "sha512-Lmr8ImoQvoROXtzhsIJsA1ZtXzH46DmE6O8hMjn9/AvQq62UfjREjn+Ewi6KxjIZMay2PsgDEbLlsVyNJGEaxw==", + "license": "MIT" + }, + "node_modules/@editorjs/image": { + "version": "2.10.3", + "resolved": "https://registry.npmjs.org/@editorjs/image/-/image-2.10.3.tgz", + "integrity": "sha512-ekCsGICZOIdghF/U2T34H7CItqaWAoJDXbkRD+x8l/LIo/7Ozf7KovYm21qz+CluArgV4RurVFHqwlz+O0vfJA==", + "license": "MIT", + "dependencies": { + "@codexteam/icons": "^0.3.0" + } + }, + "node_modules/@editorjs/inline-code": { + "version": "1.5.2", + "resolved": "https://registry.npmjs.org/@editorjs/inline-code/-/inline-code-1.5.2.tgz", + "integrity": "sha512-IpEvwMTP3q89T/6vTi3ACoSMOcTdywtMsci1w19+Z/lxQn/NVuVah++ro93wQ/1ZVTyCr+TPUCchxwzY1/xaMg==", + "license": "MIT", + "dependencies": { + "@codexteam/icons": "^0.3.2" + } + }, + "node_modules/@editorjs/link": { + "version": "2.6.2", + "resolved": "https://registry.npmjs.org/@editorjs/link/-/link-2.6.2.tgz", + "integrity": "sha512-3cPx6M4ZvwDDvsi0E0fvMR3rvveAV/C0GRo1JLeZJ9cG9QgyoNolj4eu5Eqx3/r1XTC/he54qYEIZ/Dc4Lr4Ow==", + "license": "MIT", + "dependencies": { + "@babel/runtime": "^7.10.2", + "@codexteam/icons": "^0.0.4" + } + }, + "node_modules/@editorjs/link/node_modules/@codexteam/icons": { + "version": "0.0.4", + "resolved": "https://registry.npmjs.org/@codexteam/icons/-/icons-0.0.4.tgz", + "integrity": "sha512-V8N/TY2TGyas4wLrPIFq7bcow68b3gu8DfDt1+rrHPtXxcexadKauRJL6eQgfG7Z0LCrN4boLRawR4S9gjIh/Q==", + "license": "MIT" + }, + "node_modules/@editorjs/list": { + "version": "2.0.9", + "resolved": "https://registry.npmjs.org/@editorjs/list/-/list-2.0.9.tgz", + "integrity": "sha512-rUTgDSt5wygD3Dp24bNyp6vvye/Xf4UWju0ZuvWeP13Z4cu2z1Jb5JFSTEhCou72XUGuf4xVhtsd8cm/bwUS1g==", + "license": "MIT", + "dependencies": { + "@codexteam/icons": "^0.3.2" + } + }, + "node_modules/@editorjs/marker": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/@editorjs/marker/-/marker-1.4.0.tgz", + "integrity": "sha512-5ipEXfL44jTTRzgNp/p/YjMO7jT08S5z4V8qA3FFJTfdhKgQyM3mvP1zpdYKw47ZZpVWMCncvk5Nto3BxihEtg==", + "license": "MIT", + "dependencies": { + "@codexteam/icons": "^0.0.5" + } + }, + "node_modules/@editorjs/marker/node_modules/@codexteam/icons": { + "version": "0.0.5", + "resolved": "https://registry.npmjs.org/@codexteam/icons/-/icons-0.0.5.tgz", + "integrity": "sha512-s6H2KXhLz2rgbMZSkRm8dsMJvyUNZsEjxobBEg9ztdrb1B2H3pEzY6iTwI4XUPJWJ3c3qRKwV4TrO3J5jUdoQA==", + "license": "MIT" + }, + "node_modules/@editorjs/paragraph": { + "version": "2.11.7", + "resolved": "https://registry.npmjs.org/@editorjs/paragraph/-/paragraph-2.11.7.tgz", + "integrity": "sha512-qD6bbWvRc4VvP0mXDOm+hOhzzhUYR9ZjcAvgCuKWcCbUMpCvhVF1s8NX40zdjekPi6JEnuHTamCncTrSzVsVhw==", + "license": "MIT", + "dependencies": { + "@codexteam/icons": "^0.0.4" + } + }, + "node_modules/@editorjs/paragraph/node_modules/@codexteam/icons": { + "version": "0.0.4", + "resolved": "https://registry.npmjs.org/@codexteam/icons/-/icons-0.0.4.tgz", + "integrity": "sha512-V8N/TY2TGyas4wLrPIFq7bcow68b3gu8DfDt1+rrHPtXxcexadKauRJL6eQgfG7Z0LCrN4boLRawR4S9gjIh/Q==", + "license": "MIT" + }, + "node_modules/@editorjs/quote": { + "version": "2.7.6", + "resolved": "https://registry.npmjs.org/@editorjs/quote/-/quote-2.7.6.tgz", + "integrity": "sha512-D01KUMSDj2r+6Z+xjDkQqI+y6URpeHCvj0+P4pah+GtkG040lWjFb2H4pgHFXuol2cbfyAoraYSw85fuPheCvw==", + "license": "MIT", + "dependencies": { + "@codexteam/icons": "^0.3.2", + "@editorjs/dom": "^0.0.5" + } + }, + "node_modules/@editorjs/quote/node_modules/@editorjs/dom": { + "version": "0.0.5", + "resolved": "https://registry.npmjs.org/@editorjs/dom/-/dom-0.0.5.tgz", + "integrity": "sha512-SZ78Gwpkp3EUhjBIp0lSojeQ35V9acF8SubJsMeOH/vlOUE40GOnvvwWZnF05lO7bIB0dOHhhJy4N7IIAWxP2w==", + "license": "MIT", + "dependencies": { + "@editorjs/helpers": "^0.0.4" + } + }, + "node_modules/@editorjs/quote/node_modules/@editorjs/helpers": { + "version": "0.0.4", + "resolved": "https://registry.npmjs.org/@editorjs/helpers/-/helpers-0.0.4.tgz", + "integrity": "sha512-ieg3dzo2m1/ELze/RMNADiAiC5amXxIlVXoJ5vvXITOu/p/dPsrF+Oi3h5gBYvtGk9vg5LJUSG5YWU0tBUO1tw==", + "license": "MIT" + }, + "node_modules/@editorjs/table": { + "version": "2.4.5", + "resolved": "https://registry.npmjs.org/@editorjs/table/-/table-2.4.5.tgz", + "integrity": "sha512-pF48R2wc5m0c+N+RjtCLXBGZd23Rl7EjfSFpmcSViwNsu5RwMgYGrEiQ8mzVh98mbvYQwXm/NYBi9DEUUs970A==", + "license": "MIT", + "dependencies": { + "@codexteam/icons": "^0.0.6" + } + }, + "node_modules/@editorjs/table/node_modules/@codexteam/icons": { + "version": "0.0.6", + "resolved": "https://registry.npmjs.org/@codexteam/icons/-/icons-0.0.6.tgz", + "integrity": "sha512-L7Q5PET8PjKcBT5wp7VR+FCjwCi5PUp7rd/XjsgQ0CI5FJz0DphyHGRILMuDUdCW2MQT9NHbVr4QP31vwAkS/A==", + "license": "MIT" + }, + "node_modules/@editorjs/warning": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/@editorjs/warning/-/warning-1.4.1.tgz", + "integrity": "sha512-7A+irJ6gIh6li4DC7qw/NiWCThlBgtoPUeeIVdldVjoATAu+a1GjS+w/5L24ReacgQJNPVQPPCoMaS1nB83agw==", + "license": "MIT", + "dependencies": { + "@codexteam/icons": "^0.3.2", + "@editorjs/editorjs": "^2.30.7" + } + }, "node_modules/@emnapi/runtime": { "version": "1.7.0", "resolved": "https://registry.npmjs.org/@emnapi/runtime/-/runtime-1.7.0.tgz", @@ -2662,9 +2893,9 @@ "license": "MIT" }, "node_modules/@types/node": { - "version": "20.19.24", - "resolved": "https://registry.npmjs.org/@types/node/-/node-20.19.24.tgz", - "integrity": "sha512-FE5u0ezmi6y9OZEzlJfg37mqqf6ZDSF2V/NLjUyGrR9uTZ7Sb9F7bLNZ03S4XVUNRWGA7Ck4c1kK+YnuWjl+DA==", + "version": "20.19.25", + "resolved": "https://registry.npmjs.org/@types/node/-/node-20.19.25.tgz", + "integrity": "sha512-ZsJzA5thDQMSQO788d7IocwwQbI8B5OPzmqNvpf3NY/+MHDAS759Wo0gd2WQeXYt5AAAQjzcrTVC6SKCuYgoCQ==", "dev": true, "license": "MIT", "dependencies": { @@ -2917,6 +3148,18 @@ "react-dom": "^18 || ^19 || ^19.0.0-rc" } }, + "node_modules/codex-notifier": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/codex-notifier/-/codex-notifier-1.1.2.tgz", + "integrity": "sha512-DCp6xe/LGueJ1N5sXEwcBc3r3PyVkEEDNWCVigfvywAkeXcZMk9K41a31tkEFBW0Ptlwji6/JlAb49E3Yrxbtg==", + "license": "MIT" + }, + "node_modules/codex-tooltip": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/codex-tooltip/-/codex-tooltip-1.0.5.tgz", + "integrity": "sha512-IuA8LeyLU5p1B+HyhOsqR6oxyFQ11k3i9e9aXw40CrHFTRO2Y1npNBVU3W1SvhKAbUU7R/YikUBdcYFP0RcJag==", + "license": "MIT" + }, "node_modules/comma-separated-tokens": { "version": "2.0.3", "resolved": "https://registry.npmjs.org/comma-separated-tokens/-/comma-separated-tokens-2.0.3.tgz", diff --git a/package.json b/package.json index 8afa033..f4a4951 100644 --- a/package.json +++ b/package.json @@ -8,9 +8,19 @@ "start": "next start" }, "dependencies": { - "@blocknote/core": "^0.42.0", - "@blocknote/react": "^0.42.0", - "@blocknote/shadcn": "^0.42.0", + "@editorjs/checklist": "^1.6.0", + "@editorjs/code": "^2.9.3", + "@editorjs/delimiter": "^1.4.2", + "@editorjs/editorjs": "^2.31.0", + "@editorjs/embed": "^2.7.6", + "@editorjs/header": "^2.8.8", + "@editorjs/inline-code": "^1.5.2", + "@editorjs/link": "^2.6.2", + "@editorjs/list": "^2.0.9", + "@editorjs/marker": "^1.4.0", + "@editorjs/quote": "^2.7.6", + "@editorjs/table": "^2.4.5", + "@editorjs/warning": "^1.4.1", "@hello-pangea/dnd": "^18.0.1", "@radix-ui/react-collapsible": "^1.1.12", "@radix-ui/react-dialog": "^1.1.15", @@ -32,7 +42,7 @@ }, "devDependencies": { "@tailwindcss/postcss": "^4", - "@types/node": "^20.19.24", + "@types/node": "^20.19.25", "@types/react": "^19", "@types/react-dom": "^19", "tailwindcss": "^4", diff --git a/src/components/view/Doc.tsx b/src/components/view/Doc.tsx index eb62f09..90e3b8e 100644 --- a/src/components/view/Doc.tsx +++ b/src/components/view/Doc.tsx @@ -1,37 +1,60 @@ -import { SetState } from "@/lib/types"; -import { useCreateBlockNote } from "@blocknote/react"; -import { BlockNoteView } from "@blocknote/shadcn"; -import { useEffect } from "react"; +"use client"; -export default function DocView({ - doc, - setDoc, -}: { - doc: string; - setDoc: SetState; -}) { - const editor = useCreateBlockNote(); +import { useEffect, useRef, useState } from "react"; + +import Header from "@editorjs/header"; +import List from "@editorjs/list"; +import Quote from "@editorjs/quote"; +import Code from "@editorjs/code"; +import Table from "@editorjs/table"; +import Delimiter from "@editorjs/delimiter"; +import Warning from "@editorjs/warning"; +import InlineCode from "@editorjs/inline-code"; + +export default function DocView() { + const holderRef = useRef(null); + const [doc, setDoc] = useState({ blocks: [] }); useEffect(() => { - if (editor && doc) { - editor.tryParseMarkdownToBlocks(doc); - } - }, [editor]); + let editor: any; + let isMounted = true; + + (async () => { + const EditorJS = (await import("@editorjs/editorjs")).default; + + if (!isMounted || !holderRef.current) return; + + editor = new EditorJS({ + holder: holderRef.current, + placeholder: "Start writing here...", + autofocus: true, + tools: { + list: { class: List, inlineToolbar: true }, + quote: { class: Quote, inlineToolbar: true }, + code: Code, + table: Table, + header: Header, + delimiter: Delimiter, + warning: Warning, + inlineCode: InlineCode, + }, + data: doc, + async onChange() { + const savedData = await editor.save(); + setDoc(savedData); + }, + }); + })(); + + return () => { + isMounted = false; + if (editor) editor.destroy(); + }; + }, []); return ( -
editor.focus()}> - { - if (editor) { - console.log(editor.blocksToMarkdownLossy(editor.document)); - setDoc(editor.blocksToMarkdownLossy(editor.document)); - } - }} - /> +
+
); }