diff --git a/docs/src/demos/Examples/Default/React/index.jsx b/docs/src/demos/Examples/Default/React/index.jsx new file mode 100644 index 00000000..8fb12656 --- /dev/null +++ b/docs/src/demos/Examples/Default/React/index.jsx @@ -0,0 +1,167 @@ +import React, { useState } from 'react' +import { defaultExtensions } from '@tiptap/starter-kit' +import { useEditor, Editor } from '@tiptap/react' +import './styles.scss' + +// useEditor only works for child components of +const MenuBar = () => { + const editor = useEditor() + + return ( + <> + + + + + + + + + + + + + + + + + + + + + + + ) +} + +export default () => { + const [value, setValue] = useState(` +

+ Hi there, +

+

+ this is a basic basic example of tiptap. Sure, there are all kind of basic text styles you’d probably expect from a text editor. But wait until you see the lists: +

+ +

+ Isn’t that great? And all of that is editable. But wait, there’s more. Let’s try a code block: +

+
body {
+  display: none;
+}
+

+ I know, I know, this is impressive. It’s only the tip of the iceberg though. Give it a try and click a little bit around. Don’t forget to check the other examples too. +

+
+ Wow, that’s amazing. Good work, boy! 👏 +
+ — Mom +
+`) + + return ( + <> + + + + + ) +} diff --git a/docs/src/demos/Examples/Default/React/styles.scss b/docs/src/demos/Examples/Default/React/styles.scss new file mode 100644 index 00000000..dc996245 --- /dev/null +++ b/docs/src/demos/Examples/Default/React/styles.scss @@ -0,0 +1,55 @@ +/* Basic editor styles */ +.ProseMirror { + > * + * { + margin-top: 0.75em; + } + + ul, + ol { + padding: 0 1rem; + } + + h1, + h2, + h3, + h4, + h5, + h6 { + line-height: 1.1; + } + + code { + background-color: rgba(#616161, 0.1); + color: #616161; + } + + pre { + background: #0D0D0D; + color: #FFF; + font-family: 'JetBrainsMono', monospace; + padding: 0.75rem 1rem; + border-radius: 0.5rem; + + code { + color: inherit; + background: none; + font-size: 0.8rem; + } + } + + img { + max-width: 100%; + height: auto; + } + + blockquote { + padding-left: 1rem; + border-left: 2px solid rgba(#0D0D0D, 0.1); + } + + hr { + border: none; + border-top: 2px solid rgba(#0D0D0D, 0.1); + margin: 2rem 0; + } +} diff --git a/docs/src/demos/Examples/Default/index.spec.js b/docs/src/demos/Examples/Default/Vue/index.spec.js similarity index 86% rename from docs/src/demos/Examples/Default/index.spec.js rename to docs/src/demos/Examples/Default/Vue/index.spec.js index 33a3d128..8580f40a 100644 --- a/docs/src/demos/Examples/Default/index.spec.js +++ b/docs/src/demos/Examples/Default/Vue/index.spec.js @@ -1,6 +1,6 @@ -context('/demos/Examples/Default', () => { +context('/demos/Examples/Default/Vue', () => { before(() => { - cy.visit('/demos/Examples/Default') + cy.visit('/demos/Examples/Default/Vue') }) beforeEach(() => { diff --git a/docs/src/demos/Examples/Default/index.vue b/docs/src/demos/Examples/Default/Vue/index.vue similarity index 100% rename from docs/src/demos/Examples/Default/index.vue rename to docs/src/demos/Examples/Default/Vue/index.vue diff --git a/docs/src/demos/React/index.jsx b/docs/src/demos/React/index.jsx index 021ac371..3e0bd73a 100644 --- a/docs/src/demos/React/index.jsx +++ b/docs/src/demos/React/index.jsx @@ -1,6 +1,6 @@ import React, { useState } from 'react' import { defaultExtensions } from '@tiptap/starter-kit' -import { useEditor, Editor } from './components/Editor' +import { useEditor, Editor } from '@tiptap/react' // Menu bar example component // useEditor only works for child components of diff --git a/docs/src/docPages/examples/default.md b/docs/src/docPages/examples/default.md index 855996c8..47ff89cd 100644 --- a/docs/src/docPages/examples/default.md +++ b/docs/src/docPages/examples/default.md @@ -1,4 +1,8 @@ # Default text editor Did we mention that you have full control over the rendering of the editor? Here is barebones example without any styling, but packed with a whole set of common extensions. - +## Vue + + +## React + diff --git a/packages/react/README.md b/packages/react/README.md new file mode 100644 index 00000000..a2dfdd18 --- /dev/null +++ b/packages/react/README.md @@ -0,0 +1,14 @@ +# @tiptap/react +[![Version](https://img.shields.io/npm/v/@tiptap/react.svg?label=version)](https://www.npmjs.com/package/@tiptap/react) +[![Downloads](https://img.shields.io/npm/dm/@tiptap/react.svg)](https://npmcharts.com/compare/tiptap?minimal=true) +[![License](https://img.shields.io/npm/l/@tiptap/react.svg)](https://www.npmjs.com/package/@tiptap/react) +[![Sponsor](https://img.shields.io/static/v1?label=Sponsor&message=%E2%9D%A4&logo=GitHub)](https://github.com/sponsors/ueberdosis) + +## Introduction +tiptap is a headless wrapper around [ProseMirror](https://ProseMirror.net) – a toolkit for building rich text WYSIWYG editors, which is already in use at many well-known companies such as *New York Times*, *The Guardian* or *Atlassian*. + +## Offical Documentation +Documentation can be found on the [tiptap website](https://tiptap.dev). + +## License +tiptap is open-sourced software licensed under the [MIT license](https://github.com/ueberdosis/tiptap-next/blob/main/LICENSE.md). diff --git a/packages/react/package.json b/packages/react/package.json new file mode 100644 index 00000000..95f31fb4 --- /dev/null +++ b/packages/react/package.json @@ -0,0 +1,32 @@ +{ + "name": "@tiptap/react", + "description": "React components for tiptap", + "version": "2.0.0-alpha.1", + "private": true, + "homepage": "https://tiptap.dev", + "keywords": [ + "tiptap", + "tiptap react components" + ], + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/ueberdosis" + }, + "main": "dist/tiptap-react.cjs.js", + "umd": "dist/tiptap-react.umd.js", + "module": "dist/tiptap-react.esm.js", + "unpkg": "dist/tiptap-react.bundle.umd.min.js", + "types": "dist/packages/react/src/index.d.ts", + "files": [ + "src", + "dist" + ], + "peerDependencies": { + "@tiptap/core": "^2.0.0-alpha.6", + "react": "^17.0.1" + }, + "dependencies": { + "prosemirror-view": "^1.17.6" + } +} diff --git a/packages/react/src/ReactNodeViewRenderer.ts b/packages/react/src/ReactNodeViewRenderer.ts new file mode 100644 index 00000000..7fb1a1a8 --- /dev/null +++ b/packages/react/src/ReactNodeViewRenderer.ts @@ -0,0 +1 @@ +export default class ReactNodeViewRenderer {} diff --git a/packages/react/src/ReactRenderer.ts b/packages/react/src/ReactRenderer.ts new file mode 100644 index 00000000..d2672c60 --- /dev/null +++ b/packages/react/src/ReactRenderer.ts @@ -0,0 +1 @@ +export default class ReactRenderer {} diff --git a/packages/react/src/components/Editor.jsx b/packages/react/src/components/Editor.jsx new file mode 100644 index 00000000..8eec95cd --- /dev/null +++ b/packages/react/src/components/Editor.jsx @@ -0,0 +1,34 @@ +import React, { + useState, useRef, useEffect, createContext, useContext, +} from 'react' +import { Editor as Tiptap } from '@tiptap/core' + +export const EditorContext = createContext({}) + +export const useEditor = () => useContext(EditorContext) + +export const Editor = ({ + value, onChange, children, ...props +}) => { + const [editor, setEditor] = useState(null) + const editorRef = useRef(null) + + useEffect(() => { + const e = new Tiptap({ + element: editorRef.current, + content: value, + ...props, + }).on('transaction', () => { + onChange(e.getJSON()) + }) + + setEditor(e) + }, []) + + return ( + + {editorRef.current && children} +
+ + ) +} diff --git a/packages/react/src/index.ts b/packages/react/src/index.ts new file mode 100644 index 00000000..2fdac48e --- /dev/null +++ b/packages/react/src/index.ts @@ -0,0 +1,7 @@ +// @ts-nocheck +export * from '@tiptap/core' +export { default as ReactRenderer } from './ReactRenderer' +export { default as ReactNodeViewRenderer } from './ReactNodeViewRenderer' +export { + Editor, EditorContext, useEditor, +} from './components/Editor'