Skip to content

fix: prop types to handle null and undefined values #327

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Mar 8, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 1 addition & 3 deletions demo/src/examples/BasicExample.vue
Original file line number Diff line number Diff line change
Expand Up @@ -12,9 +12,7 @@ export default defineComponent({
QuillEditor,
},
setup: () => {
const content = ref<Delta>(
new Delta()
)
const content = ref<Delta | null>(null)

return { content }
},
Expand Down
33 changes: 22 additions & 11 deletions packages/vue-quill/src/components/QuillEditor.ts
Original file line number Diff line number Diff line change
Expand Up @@ -22,13 +22,14 @@ import { toolbarOptions, ToolbarOptions } from './options'

export type Module = { name: string; module: unknown; options?: object }

type ContentPropType = string | Delta | undefined | null

export const QuillEditor = defineComponent({
name: 'QuillEditor',
inheritAttrs: false,
props: {
content: {
type: [String, Object] as PropType<string | Delta>,
default: () => {},
type: [String, Object] as PropType<ContentPropType>,
},
contentType: {
type: String as PropType<'delta' | 'html' | 'text'>,
Expand Down Expand Up @@ -185,8 +186,8 @@ export const QuillEditor = defineComponent({
)
}

const maybeClone = (delta: Delta | string) => {
return typeof delta === 'object' ? delta.slice() : delta
const maybeClone = (delta: ContentPropType) => {
return typeof delta === 'object' && delta ? delta.slice() : delta
}

const deltaHasValuesOtherThanRetain = (delta: Delta): boolean => {
Expand All @@ -197,13 +198,18 @@ export const QuillEditor = defineComponent({

// Doesn't need reactivity, but does need to be cloned to avoid deep mutations always registering as equal
let internalModel: typeof props.content
const internalModelEquals = (against: Delta | String | undefined) => {
const internalModelEquals = (against: ContentPropType) => {
if (typeof internalModel === typeof against) {
if (against === internalModel) {
return true
}
// Ref/Proxy does not support instanceof, so do a loose check
if (typeof against === 'object' && typeof internalModel === 'object') {
if (
typeof against === 'object' &&
against &&
typeof internalModel === 'object' &&
internalModel
) {
return !deltaHasValuesOtherThanRetain(
internalModel.diff(against as Delta)
)
Expand Down Expand Up @@ -297,15 +303,20 @@ export const QuillEditor = defineComponent({
return quill?.getContents(index, length)
}

const setContents = (content: string | Delta, source: Sources = 'api') => {
const setContents = (content: ContentPropType, source: Sources = 'api') => {
const normalizedContent = !content
? props.contentType === 'delta'
? new Delta()
: ''
: content
if (props.contentType === 'html') {
setHTML(content as string)
setHTML(normalizedContent as string)
} else if (props.contentType === 'text') {
setText(content as string, source)
setText(normalizedContent as string, source)
} else {
quill?.setContents(content as Delta, source)
quill?.setContents(normalizedContent as Delta, source)
}
internalModel = maybeClone(content)
internalModel = maybeClone(normalizedContent)
}

const getText = (index?: number, length?: number): string => {
Expand Down