diff --git a/src/extensions/rich-text/bold-and-italics.ts b/src/extensions/rich-text/bold-and-italics.ts index 91a7107f..34bf1e12 100644 --- a/src/extensions/rich-text/bold-and-italics.ts +++ b/src/extensions/rich-text/bold-and-italics.ts @@ -1,9 +1,9 @@ import { Mark, markInputRule, markPasteRule } from '@tiptap/core' -const starInputRegex = /(?:^|\s)((?:\*{3})((?:[^*]+))(?:\*{3}))$/ -const starPasteRegex = /(?:^|\s)((?:\*{3})((?:[^*]+))(?:\*{3}))/g -const underscoreInputRegex = /(?:^|\s)((?:_{3})((?:[^_]+))(?:_{3}))$/ -const underscorePasteRegex = /(?:^|\s)((?:_{3})((?:[^_]+))(?:_{3}))/g +const starInputRegex = /(?:^|\s)((?:\*{2})((?:[^*]+))(?:\*{2}))$/ +const starPasteRegex = /(?:^|\s)((?:\*{2})((?:[^*]+))(?:\*{2}))/g +const underscoreInputRegex = /(?:^|\s)((?:_{2})((?:[^_]+))(?:_{2}))$/ +const underscorePasteRegex = /(?:^|\s)((?:_{2})((?:[^_]+))(?:_{2}))/g /** * The `BoldAndItalics` extension adds the ability to use the `***` and `___` Markdown shortcuts diff --git a/src/extensions/rich-text/rich-text-kit.ts b/src/extensions/rich-text/rich-text-kit.ts index 343a6f0c..225e8c61 100644 --- a/src/extensions/rich-text/rich-text-kit.ts +++ b/src/extensions/rich-text/rich-text-kit.ts @@ -13,6 +13,7 @@ import { ListItem } from '@tiptap/extension-list-item' import { OrderedList } from '@tiptap/extension-ordered-list' import { Paragraph } from '@tiptap/extension-paragraph' import { Strike } from '@tiptap/extension-strike' +import { TaskList } from '@tiptap/extension-task-list' import { Text } from '@tiptap/extension-text' import { Typography } from '@tiptap/extension-typography' @@ -30,6 +31,7 @@ import { RichTextDocument } from './rich-text-document' import { RichTextHorizontalRule } from './rich-text-horizontal-rule' import { RichTextImage } from './rich-text-image' import { RichTextLink } from './rich-text-link' +import { RichTextTaskItem } from './rich-text-task-item' import type { Extensions } from '@tiptap/core' import type { BlockquoteOptions } from '@tiptap/extension-blockquote' @@ -46,6 +48,7 @@ import type { ListItemOptions } from '@tiptap/extension-list-item' import type { OrderedListOptions } from '@tiptap/extension-ordered-list' import type { ParagraphOptions } from '@tiptap/extension-paragraph' import type { StrikeOptions } from '@tiptap/extension-strike' +import type { TaskItemOptions } from '@tiptap/extension-task-item' import type { RichTextDocumentOptions } from './rich-text-document' import type { RichTextHorizontalRuleOptions } from './rich-text-horizontal-rule' import type { RichTextImageOptions } from './rich-text-image' @@ -170,6 +173,11 @@ type RichTextKitOptions = { */ strike: Partial | false + /** + * Set options for the `TaskList` extension, or `false` to disable. + */ + taskList: Partial | false + /** * Set to `false` to disable the `Text` extension. */ @@ -311,6 +319,11 @@ const RichTextKit = Extension.create({ extensions.push(Strike.configure(this.options?.strike)) } + if (this.options.taskList !== false) { + extensions.push(TaskList.configure(this.options?.taskList)) + extensions.push(RichTextTaskItem) + } + if (this.options.text !== false) { extensions.push(Text) } diff --git a/src/extensions/rich-text/rich-text-task-item.ts b/src/extensions/rich-text/rich-text-task-item.ts new file mode 100644 index 00000000..7fe88e3b --- /dev/null +++ b/src/extensions/rich-text/rich-text-task-item.ts @@ -0,0 +1,20 @@ +import { wrappingInputRule } from '@tiptap/core' +import { TaskItem } from '@tiptap/extension-task-item' + +const inputRegex = /^\s*(\[([( |x])?\])\s$/ + +const RichTextTaskItem = TaskItem.extend({ + addInputRules() { + return [ + wrappingInputRule({ + find: inputRegex, + type: this.type, + getAttributes: (match) => ({ + checked: match[match.length - 1] === 'x', + }), + }), + ] + }, +}) + +export { RichTextTaskItem } diff --git a/stories/typist-editor/constants/defaults.ts b/stories/typist-editor/constants/defaults.ts index 77cf7eb1..9b89a363 100644 --- a/stories/typist-editor/constants/defaults.ts +++ b/stories/typist-editor/constants/defaults.ts @@ -122,6 +122,9 @@ const DEFAULT_RICH_TEXT_KIT_OPTIONS: Partial = { link: { openOnClick: false, }, + taskList: { + nested: true, + }, } export { DEFAULT_ARG_TYPES, DEFAULT_RICH_TEXT_KIT_OPTIONS, DEFAULT_STORY_ARGS }