From bb1b91b6a6fbcee7354335f1e8701fcdf11f71c3 Mon Sep 17 00:00:00 2001 From: KuroSago Date: Thu, 10 Jul 2025 16:09:10 +0800 Subject: [PATCH] no message --- web3/apps/web/src/views/tiptap/index.vue | 3 +- .../tiptap/src/context/useTiptapStore.ts | 88 ++++++ web3/packages/tiptap/src/index.ts | 4 +- web3/packages/tiptap/src/views/index.vue | 61 ++-- web3/packages/tiptap/src/views/initContent.ts | 282 +++++++++++++++++- 5 files changed, 403 insertions(+), 35 deletions(-) create mode 100644 web3/packages/tiptap/src/context/useTiptapStore.ts diff --git a/web3/apps/web/src/views/tiptap/index.vue b/web3/apps/web/src/views/tiptap/index.vue index 19227e97..07da9228 100644 --- a/web3/apps/web/src/views/tiptap/index.vue +++ b/web3/apps/web/src/views/tiptap/index.vue @@ -6,5 +6,6 @@ diff --git a/web3/packages/tiptap/src/context/useTiptapStore.ts b/web3/packages/tiptap/src/context/useTiptapStore.ts new file mode 100644 index 00000000..e07cc249 --- /dev/null +++ b/web3/packages/tiptap/src/context/useTiptapStore.ts @@ -0,0 +1,88 @@ +import { provide, inject, reactive, readonly, type InjectionKey } from "vue"; + +const TiptapStoreKey: InjectionKey = Symbol("TiptapStore"); + +export interface TiptapState { + content: any; + theme: string | null; + hideToolbar: boolean; + hideMenubar: boolean; + disabled: boolean; + minimal: boolean; +} + +export interface TiptapActions { + toggleMinimal: () => void; + updateContent: (newContent: string) => void; + setTheme: (theme: string) => void; + toggleToolbar: () => void; + toggleMenubar: () => void; + toggleEditable: () => void; +} + +export type TiptapStore = { + state: Readonly; + actions: TiptapActions; +}; + +export function useTiptapStore(initialState?: Partial) { + const state = reactive({ + content: "", + theme: null, + hideToolbar: false, + hideMenubar: false, + disabled: false, + minimal: false, + ...initialState, + }); + + const toggleMinimal = () => { + state.minimal = !state.minimal; + }; + + const updateContent = (newContent: string) => { + state.content = newContent; + }; + + const setTheme = (theme: string) => { + state.theme = theme; + }; + + const toggleToolbar = () => { + state.hideToolbar = !state.hideToolbar; + }; + + const toggleMenubar = () => { + state.hideMenubar = !state.hideMenubar; + }; + + const toggleEditable = () => { + state.disabled = !state.disabled; + }; + + const actions: TiptapActions = { + toggleMinimal, + updateContent, + setTheme, + toggleToolbar, + toggleMenubar, + toggleEditable, + }; + + const store: TiptapStore = { + state: readonly(state), + actions, + }; + + provide(TiptapStoreKey, store); + + return store; +} + +export function useTiptapContext() { + const store = inject(TiptapStoreKey); + if (!store) { + throw new Error("useTiptapContext must be used within a TiptapProvider"); + } + return store; +} diff --git a/web3/packages/tiptap/src/index.ts b/web3/packages/tiptap/src/index.ts index 11b98b3d..6db70601 100644 --- a/web3/packages/tiptap/src/index.ts +++ b/web3/packages/tiptap/src/index.ts @@ -1,5 +1,5 @@ import TiptapEditor from "./views/index.vue"; - +import { useTiptapStore, useTiptapContext } from "./context/useTiptapStore"; import { ThemeToggle } from "echo-editor"; -export { TiptapEditor, ThemeToggle }; +export { TiptapEditor, ThemeToggle, useTiptapStore, useTiptapContext }; diff --git a/web3/packages/tiptap/src/views/index.vue b/web3/packages/tiptap/src/views/index.vue index 24791334..f16c622b 100644 --- a/web3/packages/tiptap/src/views/index.vue +++ b/web3/packages/tiptap/src/views/index.vue @@ -1,54 +1,57 @@ diff --git a/web3/packages/tiptap/src/views/initContent.ts b/web3/packages/tiptap/src/views/initContent.ts index 8a838484..bf482e75 100644 --- a/web3/packages/tiptap/src/views/initContent.ts +++ b/web3/packages/tiptap/src/views/initContent.ts @@ -1,3 +1,279 @@ -export const DEMO_CONTENT = ` -

Echo Editor

A modern WYSIWYG AI rich text editor based on tiptap and shadcn ui for Vue.js


Demo

👉Demo

Features

  • Use shadcn ui components

  • Markdown support

  • TypeScript support

  • I18n support

  • Vue 3.x support

  • Slash Command

  • Dark Mode

  • Multi Column

  • AI Power

  • Embed

  • TailwindCss

Installation

pnpm add echo-editor // or or yarn add echo-editor // or or npm i echo-editor -S

install plugin

import { createApp } from 'vue' import App from './App.vue' import EchoEditor from 'echo-editor' import 'echo-editor/style.css' const app = createApp(App) app.use(EchoEditor) app.mount('#app')

-`; +export const DEMO_CONTENT = { + type: "doc", + content: [ + { + type: "heading", + attrs: { textAlign: "center", indent: 0, lineHeight: null, level: 1 }, + content: [{ type: "text", text: "Echo Editor" }], + }, + { + type: "paragraph", + attrs: { textAlign: "left", indent: 0, lineHeight: null }, + content: [ + { + type: "text", + text: "A modern WYSIWYG AI rich text editor based on ", + }, + { + type: "text", + marks: [ + { + type: "link", + attrs: { + href: "https://github.com/scrumpy/tiptap", + target: "_blank", + rel: "noopener noreferrer nofollow", + class: "link", + }, + }, + ], + text: "tiptap", + }, + { type: "text", text: " and " }, + { + type: "text", + marks: [ + { + type: "link", + attrs: { + href: "https://www.shadcn-vue.com/", + target: "_blank", + rel: "noopener noreferrer nofollow", + class: "link", + }, + }, + ], + text: "shadcn ui", + }, + { type: "text", text: " for Vue.js" }, + ], + }, + { + type: "paragraph", + attrs: { textAlign: "left", indent: 0, lineHeight: null }, + }, + { + type: "paragraph", + attrs: { textAlign: "left", indent: 0, lineHeight: null }, + }, + { + type: "paragraph", + attrs: { textAlign: "left", indent: 0, lineHeight: null }, + }, + { + type: "image", + attrs: { + textAlign: "center", + src: "https://picsum.photos/1920/1080.webp?t=1", + alt: null, + title: null, + width: 500, + }, + }, + { + type: "paragraph", + attrs: { textAlign: "left", indent: 0, lineHeight: null }, + }, + { type: "horizontalRule" }, + { + type: "heading", + attrs: { textAlign: "left", indent: 0, lineHeight: null, level: 2 }, + content: [{ type: "text", text: "Demo" }], + }, + { + type: "paragraph", + attrs: { textAlign: "left", indent: 0, lineHeight: null }, + content: [ + { type: "text", text: "👉" }, + { + type: "text", + marks: [ + { + type: "link", + attrs: { + href: "https://echo-editor.jzcloud.site/", + target: "_blank", + rel: "noopener noreferrer nofollow", + class: "link", + }, + }, + ], + text: "Demo", + }, + ], + }, + { + type: "heading", + attrs: { textAlign: "left", indent: 0, lineHeight: null, level: 2 }, + content: [{ type: "text", text: "Features" }], + }, + { + type: "bulletList", + attrs: { listStyleType: "disc" }, + content: [ + { + type: "listItem", + content: [ + { + type: "paragraph", + attrs: { textAlign: "left", indent: 0, lineHeight: null }, + content: [ + { type: "text", text: "Use " }, + { + type: "text", + marks: [ + { + type: "link", + attrs: { + href: "https://www.shadcn-vue.com/", + target: "_blank", + rel: "noopener noreferrer nofollow", + class: "link", + }, + }, + ], + text: "shadcn ui", + }, + { type: "text", text: " components" }, + ], + }, + ], + }, + { + type: "listItem", + content: [ + { + type: "paragraph", + attrs: { textAlign: "left", indent: 0, lineHeight: null }, + content: [{ type: "text", text: "Markdown support" }], + }, + ], + }, + { + type: "listItem", + content: [ + { + type: "paragraph", + attrs: { textAlign: "left", indent: 0, lineHeight: null }, + content: [{ type: "text", text: "TypeScript support" }], + }, + ], + }, + { + type: "listItem", + content: [ + { + type: "paragraph", + attrs: { textAlign: "left", indent: 0, lineHeight: null }, + content: [{ type: "text", text: "I18n support" }], + }, + ], + }, + { + type: "listItem", + content: [ + { + type: "paragraph", + attrs: { textAlign: "left", indent: 0, lineHeight: null }, + content: [{ type: "text", text: "Vue 3.x support" }], + }, + ], + }, + { + type: "listItem", + content: [ + { + type: "paragraph", + attrs: { textAlign: "left", indent: 0, lineHeight: null }, + content: [{ type: "text", text: "Slash Command" }], + }, + ], + }, + { + type: "listItem", + content: [ + { + type: "paragraph", + attrs: { textAlign: "left", indent: 0, lineHeight: null }, + content: [{ type: "text", text: "Dark Mode" }], + }, + ], + }, + { + type: "listItem", + content: [ + { + type: "paragraph", + attrs: { textAlign: "left", indent: 0, lineHeight: null }, + content: [{ type: "text", text: "Multi Column" }], + }, + ], + }, + { + type: "listItem", + content: [ + { + type: "paragraph", + attrs: { textAlign: "left", indent: 0, lineHeight: null }, + content: [{ type: "text", text: "AI Power" }], + }, + ], + }, + { + type: "listItem", + content: [ + { + type: "paragraph", + attrs: { textAlign: "left", indent: 0, lineHeight: null }, + content: [{ type: "text", text: "Embed" }], + }, + ], + }, + { + type: "listItem", + content: [ + { + type: "paragraph", + attrs: { textAlign: "left", indent: 0, lineHeight: null }, + content: [{ type: "text", text: "TailwindCss" }], + }, + ], + }, + ], + }, + { + type: "heading", + attrs: { textAlign: "left", indent: 0, lineHeight: null, level: 2 }, + content: [{ type: "text", text: "Installation" }], + }, + { + type: "codeBlock", + attrs: { language: "bash" }, + content: [ + { + type: "text", + text: "pnpm add echo-editor\n// or\nor yarn add echo-editor\n// or\nor npm i echo-editor -S", + }, + ], + }, + { + type: "heading", + attrs: { textAlign: "left", indent: 0, lineHeight: null, level: 3 }, + content: [{ type: "text", text: "install plugin" }], + }, + { + type: "codeBlock", + attrs: { language: "typescript" }, + content: [ + { + type: "text", + text: "import { createApp } from 'vue'\nimport App from './App.vue'\nimport EchoEditor from 'echo-editor'\nimport 'echo-editor/style.css'\nconst app = createApp(App)\napp.use(EchoEditor)\napp.mount('#app')", + }, + ], + }, + { + type: "paragraph", + attrs: { textAlign: "left", indent: 0, lineHeight: null }, + }, + ], +};