From 6075a4504ef234c5067070c4cb7462a964f533d1 Mon Sep 17 00:00:00 2001 From: "Samuel M. Bednarz" Date: Sun, 22 Dec 2024 21:00:23 +0100 Subject: [PATCH] adds blur --- apps/hub/app/components/RichArtickle.vue | 75 ------------ .../useTiptap/extensions/DisplayHeader.ts | 14 --- .../useTiptap/extensions/Overflow.ts | 48 -------- .../useTiptap/extensions/Slugline.ts | 23 ---- apps/hub/app/composables/useTiptap/index.ts | 97 --------------- apps/hub/app/layouts/default.vue | 112 ++++++++++++++++++ 6 files changed, 112 insertions(+), 257 deletions(-) delete mode 100644 apps/hub/app/components/RichArtickle.vue delete mode 100644 apps/hub/app/composables/useTiptap/extensions/DisplayHeader.ts delete mode 100644 apps/hub/app/composables/useTiptap/extensions/Overflow.ts delete mode 100644 apps/hub/app/composables/useTiptap/extensions/Slugline.ts delete mode 100644 apps/hub/app/composables/useTiptap/index.ts diff --git a/apps/hub/app/components/RichArtickle.vue b/apps/hub/app/components/RichArtickle.vue deleted file mode 100644 index 7c93cf6..0000000 --- a/apps/hub/app/components/RichArtickle.vue +++ /dev/null @@ -1,75 +0,0 @@ - - - - - diff --git a/apps/hub/app/composables/useTiptap/extensions/DisplayHeader.ts b/apps/hub/app/composables/useTiptap/extensions/DisplayHeader.ts deleted file mode 100644 index 205347f..0000000 --- a/apps/hub/app/composables/useTiptap/extensions/DisplayHeader.ts +++ /dev/null @@ -1,14 +0,0 @@ -import Heading from '@tiptap/extension-heading' -import { mergeAttributes } from '@tiptap/core' - -export const DisplayHeader = Heading.extend({ - renderHTML({ HTMLAttributes }) { - return [ - `h1`, - mergeAttributes(this.options.HTMLAttributes, HTMLAttributes, { - class: `display`, - }), - 0, - ] - }, -}) diff --git a/apps/hub/app/composables/useTiptap/extensions/Overflow.ts b/apps/hub/app/composables/useTiptap/extensions/Overflow.ts deleted file mode 100644 index a6aa881..0000000 --- a/apps/hub/app/composables/useTiptap/extensions/Overflow.ts +++ /dev/null @@ -1,48 +0,0 @@ -import Bold from '@tiptap/extension-bold' -import { mergeAttributes } from '@tiptap/core' -import type { Editor, Mark } from '@tiptap/core' - -export const Overflow = Bold.extend({ - name: 'overflow', - renderHTML({ HTMLAttributes }) { - return ['span', mergeAttributes(HTMLAttributes, { class: 'overflow' }), 0] - }, -}) - -export function getCurrentBlock(editor: Editor) { - const { state } = editor - return { - start: state.selection.$from.before(), - node: state.doc.nodeAt(state.selection.$from.before()), - size: state.doc.nodeAt(state.selection.$from.before())?.content.size || 0, - end: 0, - } -} - -export function validateOverflow(editor: Editor, props: { limit: number }) { - const { state, view, schema } = editor - const dispatch = view.dispatch - const transaction = state.tr - - function removeMark(from: number, to: number, mark: Mark) { - return dispatch(transaction.removeMark(from, to, mark)) - } - - function addMark(from: number, to: number, mark: Mark) { - return dispatch(transaction.addMark(from, to, mark)) - } - - const current = getCurrentBlock(editor) - - current.end = current.start + current.size + 1 - const atLimit = current.size >= props.limit - const limit = current.start + props.limit - const inner = Math.min(current.end, limit) - - console.log('current', schema.marks) - - const overflowMark = schema.marks.overflow.create() - - removeMark(current.start, inner, overflowMark) - atLimit && addMark(limit, current.end, overflowMark) -} diff --git a/apps/hub/app/composables/useTiptap/extensions/Slugline.ts b/apps/hub/app/composables/useTiptap/extensions/Slugline.ts deleted file mode 100644 index ee1819d..0000000 --- a/apps/hub/app/composables/useTiptap/extensions/Slugline.ts +++ /dev/null @@ -1,23 +0,0 @@ -import Paragraph from '@tiptap/extension-paragraph' - -// slugline is just a paragraph with a slugline class -export const Slugline = Paragraph.extend({ - name: 'slugline', - addAttributes() { - return { - class: { - default: 'slugline', - parseHTML: (element) => { - return { - class: element.getAttribute('class'), - } - }, - renderHTML: (attributes) => { - return { - class: attributes.class, - } - }, - }, - } - }, -}) diff --git a/apps/hub/app/composables/useTiptap/index.ts b/apps/hub/app/composables/useTiptap/index.ts deleted file mode 100644 index 464ec0e..0000000 --- a/apps/hub/app/composables/useTiptap/index.ts +++ /dev/null @@ -1,97 +0,0 @@ -import { useEditor as useTiptap } from '@tiptap/vue-3' -import type { Editor } from '@tiptap/core' -import Document from '@tiptap/extension-document' -import Text from '@tiptap/extension-text' -import Paragraph from '@tiptap/extension-paragraph' -import Bold from '@tiptap/extension-bold' -import Italic from '@tiptap/extension-italic' -import Heading from '@tiptap/extension-heading' -import History from '@tiptap/extension-history' -import CharacterCount from '@tiptap/extension-character-count' -import Placeholder from '@tiptap/extension-placeholder' -import { Overflow, validateOverflow } from './extensions/Overflow' -import { Slugline } from './extensions/Slugline' -import { DisplayHeader } from './extensions/DisplayHeader' - -interface useTiptapProps { - limit?: number - placeholder?: string - content?: string - onChange?: (editor: Editor) => void -} - -export function useTitleEditor({ - limit = 120, - placeholder = 'Write a title...', - content, - onChange = () => {}, -}: useTiptapProps) { - const editor = useTiptap({ - content, - onUpdate: ({ editor }) => onChange(editor), - extensions: [ - Document, - Text, - Heading, - DisplayHeader, - CharacterCount.configure({ limit }), - Placeholder.configure({ - placeholder: placeholder, - }), - ], - }) - - onBeforeUnmount(() => { - if (!editor.value) return - editor.value.destroy() - }) - - return editor -} - -export function useEditor({ - limit = 4000, - placeholder = 'Write something...', - content, - onChange = () => {}, -}: useTiptapProps) { - const editor = useTiptap({ - content, - onUpdate, - extensions: [ - Document, - Text, - Bold, - Italic, - Heading, - Paragraph, - Slugline, - History, - Overflow, - Placeholder.configure({ placeholder }), - CharacterCount.configure({ limit }), - ], - }) - - const currentNodeLength = ref(0) - function countNodeLength(editor: Editor) { - const { $head } = editor.state.selection - const nodeSize = $head.parent.content.size - currentNodeLength.value = nodeSize - } - - function onUpdate({ editor }: { editor: Editor }) { - onChange(editor) - countNodeLength(editor) - validateOverflow(editor, { - limit: 280, - }) - } - - onBeforeUnmount(() => { - if (!editor.value) return - editor.value.destroy() - }) - - return editor -} diff --git a/apps/hub/app/layouts/default.vue b/apps/hub/app/layouts/default.vue index 7f67d72..35b4cba 100644 --- a/apps/hub/app/layouts/default.vue +++ b/apps/hub/app/layouts/default.vue @@ -17,6 +17,14 @@ onKeyStroke('Escape', () => {