mirror of
https://github.com/keven1024/015.git
synced 2026-05-26 07:08:02 +00:00
Revert "refactor(front): replace MarkdownInputField with RichInputField for improved JSON handling in text uploads, update Tiptap component to support JSONContent, and increment dependency versions for better compatibility"
This reverts commit e959a0bc3e.
This commit is contained in:
13
front/components/Field/MarkdownInputField.vue
Normal file
13
front/components/Field/MarkdownInputField.vue
Normal file
@@ -0,0 +1,13 @@
|
||||
<template>
|
||||
<Tiptap v-model="value" />
|
||||
</template>
|
||||
|
||||
<script setup lang="ts">
|
||||
import Tiptap from '@/components/Tiptap.vue'
|
||||
import type { RuleExpression } from 'vee-validate'
|
||||
const props = defineProps<{
|
||||
name: string
|
||||
rules?: RuleExpression<string>
|
||||
}>()
|
||||
const { value, } = useField<string>(props.name, props.rules)
|
||||
</script>
|
||||
@@ -1,20 +0,0 @@
|
||||
<template>
|
||||
<Tiptap :model-value="jsonValue" @update:model-value="(v) => setValue(JSON.stringify(v))" />
|
||||
</template>
|
||||
|
||||
<script setup lang="ts">
|
||||
import Tiptap from '@/components/Tiptap.vue'
|
||||
import type { RuleExpression } from 'vee-validate'
|
||||
const props = defineProps<{
|
||||
name: string
|
||||
rules?: RuleExpression<string>
|
||||
}>()
|
||||
const { value, setValue } = useField<string>(props.name, props.rules)
|
||||
const jsonValue = computed(() => {
|
||||
try {
|
||||
return value.value ? JSON.parse(value.value) : {}
|
||||
} catch (error) {
|
||||
return {}
|
||||
}
|
||||
})
|
||||
</script>
|
||||
@@ -1,92 +1,74 @@
|
||||
<script lang="ts" setup>
|
||||
import RichInputField from '@/components/Field/RichInputField.vue'
|
||||
import FormButton from '@/components/Field/FormButton.vue'
|
||||
import Button from '@/components/ui/button/Button.vue'
|
||||
import showDrawer from '@/lib/showDrawer'
|
||||
import { h } from 'vue'
|
||||
import TextShareDrawer from '@/components/Drawer/TextShareDrawer.vue'
|
||||
import { cx } from 'class-variance-authority'
|
||||
import PickupShareBtn from '@/components/PickupShareBtn.vue'
|
||||
import { isEmpty } from 'lodash-es'
|
||||
const form = useFormContext()
|
||||
const { t } = useI18n()
|
||||
|
||||
const isEmptyRichText = (value: string) => {
|
||||
if (isEmpty(value)) return true
|
||||
try {
|
||||
const { content } = JSON.parse(value) || {}
|
||||
return (
|
||||
content?.reduce((acc: boolean, item: any) => {
|
||||
const { type, content } = item || {}
|
||||
if (!type || !['paragraph'].includes(type)) {
|
||||
return acc
|
||||
}
|
||||
return acc + (content?.length ?? 0)
|
||||
}, 0) == 0
|
||||
)
|
||||
} catch (error) {
|
||||
return true
|
||||
}
|
||||
}
|
||||
const isEmptyText = computed(() => isEmptyRichText(form?.values.text))
|
||||
import MarkdownInputField from "@/components/Field/MarkdownInputField.vue";
|
||||
import FormButton from "@/components/Field/FormButton.vue";
|
||||
import Button from "@/components/ui/button/Button.vue";
|
||||
import showDrawer from "@/lib/showDrawer";
|
||||
import { h } from "vue";
|
||||
import TextShareDrawer from "@/components/Drawer/TextShareDrawer.vue";
|
||||
import { cx } from "class-variance-authority";
|
||||
import PickupShareBtn from "@/components/PickupShareBtn.vue";
|
||||
const form = useFormContext();
|
||||
const { t } = useI18n();
|
||||
|
||||
const emit = defineEmits<{
|
||||
(e: 'change', key: string): void
|
||||
}>()
|
||||
(e: "change", key: string): void;
|
||||
}>();
|
||||
|
||||
const handleTextShare = ({ type, config }: { type: string; config: any }) => {
|
||||
form?.setFieldValue('handle_type', type)
|
||||
form?.setFieldValue('config', config)
|
||||
emit('change', 'result')
|
||||
}
|
||||
form?.setFieldValue("handle_type", type);
|
||||
form?.setFieldValue("config", config);
|
||||
emit("change", "result");
|
||||
};
|
||||
</script>
|
||||
<template>
|
||||
<div class="gap-5 flex flex-col">
|
||||
<div class="text-xl font-normal">{{ t('text.uploadText') }}</div>
|
||||
<div class="relative">
|
||||
<RichInputField
|
||||
name="text"
|
||||
:placeholder="t('text.uploadTextPlaceholder')"
|
||||
class="max-h-[50vh] min-h-40 overflow-y-auto max-w-full [&>*]:pr-10"
|
||||
:rules="(v) => !isEmptyRichText(v)"
|
||||
/>
|
||||
<Button
|
||||
variant="ghost"
|
||||
size="icon"
|
||||
:class="
|
||||
cx(
|
||||
'absolute right-2 top-2 hover:bg-black/10 transition-all duration-300',
|
||||
!isEmptyText ? 'opacity-100' : 'opacity-0 pointer-events-none'
|
||||
)
|
||||
"
|
||||
@click="
|
||||
() => {
|
||||
form?.setValues({ text: '' })
|
||||
}
|
||||
"
|
||||
>
|
||||
<LucideX />
|
||||
</Button>
|
||||
</div>
|
||||
<div class="flex flex-row gap-3">
|
||||
<FormButton
|
||||
@click="
|
||||
async (form) => {
|
||||
const { text } = form?.values || {}
|
||||
showDrawer({
|
||||
render: ({ hide }) =>
|
||||
h(TextShareDrawer, {
|
||||
hide,
|
||||
text,
|
||||
onTextHandle: handleTextShare,
|
||||
}),
|
||||
})
|
||||
}
|
||||
"
|
||||
>
|
||||
<LucideShare class="size-4" />{{ t('btn.submit') }}
|
||||
</FormButton>
|
||||
<PickupShareBtn />
|
||||
</div>
|
||||
<div class="gap-5 flex flex-col">
|
||||
<div class="text-xl font-normal">{{ t("text.uploadText") }}</div>
|
||||
<div class="relative">
|
||||
<MarkdownInputField
|
||||
name="text"
|
||||
:placeholder="t('text.uploadTextPlaceholder')"
|
||||
class="max-h-[50vh] min-h-40 overflow-y-auto max-w-full [&>*]:pr-10"
|
||||
rules="required"
|
||||
/>
|
||||
<Button
|
||||
variant="ghost"
|
||||
size="icon"
|
||||
:class="
|
||||
cx(
|
||||
'absolute right-2 top-2 hover:bg-black/10 transition-all duration-300',
|
||||
form?.values.text?.length > 0
|
||||
? 'opacity-100'
|
||||
: 'opacity-0 pointer-events-none',
|
||||
)
|
||||
"
|
||||
@click="
|
||||
() => {
|
||||
form?.setValues({ text: '' });
|
||||
}
|
||||
"
|
||||
>
|
||||
<LucideX />
|
||||
</Button>
|
||||
</div>
|
||||
<div class="flex flex-row gap-3">
|
||||
<FormButton
|
||||
@click="
|
||||
async (form) => {
|
||||
const { text } = form?.values || {};
|
||||
showDrawer({
|
||||
render: ({ hide }) =>
|
||||
h(TextShareDrawer, {
|
||||
hide,
|
||||
text,
|
||||
onTextHandle: handleTextShare,
|
||||
}),
|
||||
});
|
||||
}
|
||||
"
|
||||
>
|
||||
<LucideShare class="size-4" />{{ t("btn.submit") }}
|
||||
</FormButton>
|
||||
<PickupShareBtn />
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
@@ -1,13 +1,14 @@
|
||||
<script setup lang="ts">
|
||||
import { Editor, EditorContent, type JSONContent } from '@tiptap/vue-3'
|
||||
import { Editor, EditorContent } from '@tiptap/vue-3'
|
||||
import StarterKit from '@tiptap/starter-kit'
|
||||
import { Markdown } from 'tiptap-markdown'
|
||||
import Placeholder from '@tiptap/extension-placeholder'
|
||||
const props = defineProps<{
|
||||
modelValue?: JSONContent
|
||||
modelValue?: string
|
||||
placeholder?: string
|
||||
}>()
|
||||
const emit = defineEmits<{
|
||||
(e: 'update:modelValue', value?: JSONContent): void
|
||||
(e: 'update:modelValue', value: string): void
|
||||
}>()
|
||||
|
||||
const editor = ref<Editor | undefined>(undefined)
|
||||
@@ -16,20 +17,24 @@ onMounted(() => {
|
||||
content: props.modelValue,
|
||||
extensions: [
|
||||
StarterKit,
|
||||
Markdown.configure({
|
||||
transformPastedText: true,
|
||||
transformCopiedText: true,
|
||||
}),
|
||||
Placeholder.configure({
|
||||
placeholder: props.placeholder ?? '',
|
||||
}),
|
||||
// CommandsPlugin,
|
||||
],
|
||||
onUpdate: (v) => {
|
||||
emit('update:modelValue', editor.value?.getJSON?.())
|
||||
onUpdate: () => {
|
||||
emit('update:modelValue', editor.value?.storage?.markdown?.getMarkdown() ?? '')
|
||||
},
|
||||
})
|
||||
})
|
||||
watch(
|
||||
() => props.modelValue,
|
||||
(value) => {
|
||||
if (value !== editor.value?.getJSON?.()) {
|
||||
if (value !== editor.value?.storage?.markdown?.getMarkdown()) {
|
||||
editor.value?.commands.setContent(value ?? '')
|
||||
}
|
||||
}
|
||||
|
||||
@@ -13,20 +13,20 @@
|
||||
"@nuxt/image": "1.10.0",
|
||||
"@nuxtjs/i18n": "9.5.5",
|
||||
"@pinia/nuxt": "^0.11.2",
|
||||
"@tailwindcss/postcss": "^4.1.14",
|
||||
"@tailwindcss/vite": "^4.1.14",
|
||||
"@tanstack/vue-query": "^5.90.2",
|
||||
"@tiptap/extension-blockquote": "^3.6.6",
|
||||
"@tiptap/extension-bold": "^3.6.6",
|
||||
"@tiptap/extension-heading": "^3.6.6",
|
||||
"@tiptap/extension-italic": "^3.6.6",
|
||||
"@tiptap/extension-paragraph": "^3.6.6",
|
||||
"@tiptap/extension-placeholder": "^3.6.6",
|
||||
"@tiptap/extension-strike": "^3.6.6",
|
||||
"@tiptap/extension-text": "^3.6.6",
|
||||
"@tiptap/pm": "^3.6.6",
|
||||
"@tiptap/starter-kit": "^3.6.6",
|
||||
"@tiptap/vue-3": "^3.6.6",
|
||||
"@tailwindcss/postcss": "^4.1.13",
|
||||
"@tailwindcss/vite": "^4.1.13",
|
||||
"@tanstack/vue-query": "^5.90.1",
|
||||
"@tiptap/extension-blockquote": "^2.26.1",
|
||||
"@tiptap/extension-bold": "^2.26.1",
|
||||
"@tiptap/extension-heading": "^2.26.1",
|
||||
"@tiptap/extension-italic": "^2.26.1",
|
||||
"@tiptap/extension-paragraph": "^2.26.1",
|
||||
"@tiptap/extension-placeholder": "^2.26.1",
|
||||
"@tiptap/extension-strike": "^2.26.1",
|
||||
"@tiptap/extension-text": "^2.26.1",
|
||||
"@tiptap/pm": "^2.26.1",
|
||||
"@tiptap/starter-kit": "^2.26.1",
|
||||
"@tiptap/vue-3": "^2.26.1",
|
||||
"@unovis/ts": "^1.6.1",
|
||||
"@unovis/vue": "^1.6.1",
|
||||
"@vee-validate/nuxt": "^4.15.1",
|
||||
@@ -39,22 +39,22 @@
|
||||
"lodash-es": "^4.17.21",
|
||||
"lucide-vue-next": "^0.542.0",
|
||||
"markdown-it": "^14.1.0",
|
||||
"motion-v": "^1.7.2",
|
||||
"motion-v": "^1.7.1",
|
||||
"nanoid": "^5.1.6",
|
||||
"nuxt": "4.1.2",
|
||||
"nuxt-lucide-icons": "1.0.5",
|
||||
"pinia": "^3.0.3",
|
||||
"pixi.js": "^8.14.0",
|
||||
"pixi.js": "^8.13.2",
|
||||
"qrcode": "^1.5.4",
|
||||
"reka-ui": "^2.5.1",
|
||||
"reka-ui": "^2.5.0",
|
||||
"shadcn-nuxt": "2.0.1",
|
||||
"spark-md5": "^3.0.2",
|
||||
"tailwind-merge": "^3.3.1",
|
||||
"tailwindcss": "^4.1.14",
|
||||
"tailwindcss": "^4.1.13",
|
||||
"tiptap-markdown": "^0.8.10",
|
||||
"tw-animate-css": "^1.4.0",
|
||||
"tw-animate-css": "^1.3.8",
|
||||
"vaul-vue": "^0.4.1",
|
||||
"vue": "^3.5.22",
|
||||
"vue": "^3.5.21",
|
||||
"vue-router": "^4.5.1",
|
||||
"vue-sonner": "^1.3.2",
|
||||
"vue3-pixi": "1.0.0-beta.2"
|
||||
@@ -64,7 +64,7 @@
|
||||
"esbuild": "0.25.6"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@tailwindcss/typography": "^0.5.19",
|
||||
"@tailwindcss/typography": "^0.5.18",
|
||||
"@types/lodash-es": "^4.17.12",
|
||||
"@types/markdown-it": "^14.1.2",
|
||||
"@types/qrcode": "^1.5.5",
|
||||
|
||||
Reference in New Issue
Block a user