@handlewithcare/react-prosemirror 2.0.0 → 2.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (44) hide show
  1. package/README.md +29 -5
  2. package/dist/cjs/components/CustomNodeView.js +80 -4
  3. package/dist/cjs/components/MarkView.js +6 -3
  4. package/dist/cjs/components/NodeView.js +13 -133
  5. package/dist/cjs/components/OutputSpec.js +1 -1
  6. package/dist/cjs/components/ReactNodeView.js +136 -0
  7. package/dist/cjs/components/TextNodeView.js +2 -2
  8. package/dist/cjs/findDOMNode.js +46 -0
  9. package/dist/cjs/hooks/useEditor.js +14 -3
  10. package/dist/cjs/hooks/useEditorEffect.js +5 -2
  11. package/dist/cjs/hooks/useIsNodeSelected.js +21 -0
  12. package/dist/cjs/index.js +4 -0
  13. package/dist/cjs/plugins/componentEventListeners.js +1 -1
  14. package/dist/cjs/plugins/reactKeys.js +1 -1
  15. package/dist/cjs/selection/SelectionDOMObserver.js +0 -3
  16. package/dist/cjs/selection/selectionToDOM.js +1 -1
  17. package/dist/cjs/viewdesc.js +18 -8
  18. package/dist/esm/components/CustomNodeView.js +82 -6
  19. package/dist/esm/components/MarkView.js +6 -3
  20. package/dist/esm/components/NodeView.js +14 -134
  21. package/dist/esm/components/OutputSpec.js +1 -1
  22. package/dist/esm/components/ReactNodeView.js +85 -0
  23. package/dist/esm/components/TextNodeView.js +1 -1
  24. package/dist/esm/findDOMNode.js +31 -0
  25. package/dist/esm/hooks/useEditor.js +14 -3
  26. package/dist/esm/hooks/useEditorEffect.js +5 -2
  27. package/dist/esm/hooks/useIsNodeSelected.js +11 -0
  28. package/dist/esm/index.js +1 -0
  29. package/dist/esm/plugins/componentEventListeners.js +1 -1
  30. package/dist/esm/plugins/reactKeys.js +1 -1
  31. package/dist/esm/selection/SelectionDOMObserver.js +0 -3
  32. package/dist/esm/selection/selectionToDOM.js +1 -1
  33. package/dist/esm/viewdesc.js +18 -8
  34. package/dist/tsconfig.tsbuildinfo +1 -1
  35. package/dist/types/components/CustomNodeView.d.ts +3 -12
  36. package/dist/types/components/ReactNodeView.d.ts +11 -0
  37. package/dist/types/contexts/EditorContext.d.ts +2 -0
  38. package/dist/types/findDOMNode.d.ts +3 -0
  39. package/dist/types/hooks/useEditor.d.ts +1 -0
  40. package/dist/types/hooks/useIsNodeSelected.d.ts +1 -0
  41. package/dist/types/index.d.ts +1 -0
  42. package/dist/types/selection/SelectionDOMObserver.d.ts +0 -1
  43. package/dist/types/viewdesc.d.ts +19 -6
  44. package/package.json +19 -6
package/README.md CHANGED
@@ -22,16 +22,21 @@ ProseMirror renderer will happen in this repository, published as
22
22
 
23
23
  ## Installation
24
24
 
25
+ _Note_: React ProseMirror releases are coupled to specific prosemirror-view
26
+ releases, and are not guaranteed to work with other versions of
27
+ prosemirror-view. Ensure that your version of prosemirror-view matches the
28
+ version in React ProseMirror's peer dependencies!
29
+
25
30
  npm:
26
31
 
27
32
  ```sh
28
- npm install @handlewithcare/react-prosemirror
33
+ npm install @handlewithcare/react-prosemirror prosemirror-view@1.37.1 prosemirror-state prosemirror-model
29
34
  ```
30
35
 
31
36
  yarn:
32
37
 
33
38
  ```sh
34
- yarn add @handlewithcare/react-prosemirror
39
+ yarn add @handlewithcare/react-prosemirror prosemirror-view@1.37.1 prosemirror-state prosemirror-model
35
40
  ```
36
41
 
37
42
  <!-- toc -->
@@ -43,7 +48,7 @@ yarn add @handlewithcare/react-prosemirror
43
48
  - [`useEditorEventCallback`](#useeditoreventcallback)
44
49
  - [`useEditorEventListener`](#useeditoreventlistener)
45
50
  - [Building node views with React](#building-node-views-with-react)
46
- - [What's changing in v2?](#whats-changing-in-v2)
51
+ - [What's new in v2?](#whats-new-in-v2)
47
52
  - [API changes](#api-changes)
48
53
  - [API](#api)
49
54
  - [`ProseMirror`](#prosemirror)
@@ -55,7 +60,9 @@ yarn add @handlewithcare/react-prosemirror
55
60
  - [`NodeViewComponentProps`](#nodeviewcomponentprops)
56
61
  - [`useStopEvent`](#usestopevent)
57
62
  - [`useSelectNode`](#useselectnode)
63
+ - [`useIsNodeSelected`](#useisnodeselected)
58
64
  - [`widget`](#widget)
65
+ - [Looking for someone to collaborate with?](#looking-for-someone-to-collaborate-with)
59
66
 
60
67
  <!-- tocstop -->
61
68
 
@@ -416,9 +423,9 @@ function ProseMirrorEditor() {
416
423
  }
417
424
  ```
418
425
 
419
- ## What's changing in v2?
426
+ ## What's new in v2?
420
427
 
421
- The upcoming v2 release constitutes a significant re-write of the library.
428
+ The v2 release constitutes a significant re-write of the library.
422
429
 
423
430
  Previously, React ProseMirror relied on ProseMirror's EditorView to manage the
424
431
  DOM for the editor. To integrate it with React, we used React
@@ -689,6 +696,16 @@ This hook can be used within a node view component to register
689
696
  The selectNode handler will only be called when a NodeSelection is created whose
690
697
  node is this one.
691
698
 
699
+ ### `useIsNodeSelected`
700
+
701
+ ```tsx
702
+ type useIsNodeSelected = (): boolean
703
+ ```
704
+
705
+ This hook can be used within a node view component to subscribe to a boolean
706
+ value determining whether this node is selected. The hook will return true when
707
+ a NodeSelection is created whose node is this one.
708
+
692
709
  ### `widget`
693
710
 
694
711
  ```tsx
@@ -703,3 +720,10 @@ type widget = (
703
720
 
704
721
  Like ProseMirror View's `Decoration.widget`, but with support for React
705
722
  components.
723
+
724
+ ## Looking for someone to collaborate with?
725
+
726
+ Reach out to [Handle with Care](https://handlewithcare.dev/#get-in-touch)! We're
727
+ a product development collective with years of experience bringing excellent
728
+ ideas to life. We love React and ProseMirror, and we're always looking for new
729
+ folks to work with!
@@ -10,8 +10,10 @@ Object.defineProperty(exports, "CustomNodeView", {
10
10
  });
11
11
  const _react = /*#__PURE__*/ _interop_require_wildcard(require("react"));
12
12
  const _reactdom = require("react-dom");
13
+ const _ChildDescriptorsContext = require("../contexts/ChildDescriptorsContext.js");
13
14
  const _EditorContext = require("../contexts/EditorContext.js");
14
15
  const _useClientOnly = require("../hooks/useClientOnly.js");
16
+ const _useNodeViewDescriptor = require("../hooks/useNodeViewDescriptor.js");
15
17
  const _ChildNodeViews = require("./ChildNodeViews.js");
16
18
  function _getRequireWildcardCache(nodeInterop) {
17
19
  if (typeof WeakMap !== "function") return null;
@@ -54,10 +56,75 @@ function _interop_require_wildcard(obj, nodeInterop) {
54
56
  }
55
57
  return newObj;
56
58
  }
57
- function CustomNodeView(param) {
58
- let { contentDomRef, customNodeViewRef, customNodeViewRootRef, customNodeView, initialNode, node, getPos, initialOuterDeco, initialInnerDeco, innerDeco } = param;
59
+ const CustomNodeView = /*#__PURE__*/ (0, _react.memo)(function CustomNodeView(param) {
60
+ let { customNodeView, node, getPos, innerDeco, outerDeco } = param;
59
61
  const { view } = (0, _react.useContext)(_EditorContext.EditorContext);
62
+ const domRef = (0, _react.useRef)(null);
63
+ const nodeDomRef = (0, _react.useRef)(null);
64
+ const contentDomRef = (0, _react.useRef)(null);
65
+ const getPosFunc = (0, _react.useRef)(()=>getPos.current()).current;
66
+ // this is ill-conceived; should revisit
67
+ const initialNode = (0, _react.useRef)(node);
68
+ const initialOuterDeco = (0, _react.useRef)(outerDeco);
69
+ const initialInnerDeco = (0, _react.useRef)(innerDeco);
70
+ const customNodeViewRootRef = (0, _react.useRef)(null);
71
+ const customNodeViewRef = (0, _react.useRef)(null);
60
72
  const shouldRender = (0, _useClientOnly.useClientOnly)();
73
+ (0, _react.useLayoutEffect)(()=>{
74
+ if (!customNodeViewRef.current || !customNodeViewRootRef.current || !shouldRender) return;
75
+ const { dom } = customNodeViewRef.current;
76
+ nodeDomRef.current = customNodeViewRootRef.current;
77
+ customNodeViewRootRef.current.appendChild(dom);
78
+ return ()=>{
79
+ customNodeViewRef.current?.destroy?.();
80
+ };
81
+ }, [
82
+ customNodeViewRef,
83
+ customNodeViewRootRef,
84
+ nodeDomRef,
85
+ shouldRender
86
+ ]);
87
+ (0, _react.useLayoutEffect)(()=>{
88
+ if (!customNodeView || !customNodeViewRef.current || !shouldRender) return;
89
+ const { destroy, update } = customNodeViewRef.current;
90
+ const updated = update?.call(customNodeViewRef.current, node, outerDeco, innerDeco) ?? true;
91
+ if (updated) return;
92
+ destroy?.call(customNodeViewRef.current);
93
+ if (!customNodeViewRootRef.current) return;
94
+ initialNode.current = node;
95
+ initialOuterDeco.current = outerDeco;
96
+ initialInnerDeco.current = innerDeco;
97
+ customNodeViewRef.current = customNodeView(initialNode.current, // customNodeView will only be set if view is set, and we can only reach
98
+ // this line if customNodeView is set
99
+ // eslint-disable-next-line @typescript-eslint/no-non-null-assertion
100
+ view, getPosFunc, initialOuterDeco.current, initialInnerDeco.current);
101
+ const { dom } = customNodeViewRef.current;
102
+ nodeDomRef.current = customNodeViewRootRef.current;
103
+ customNodeViewRootRef.current.appendChild(dom);
104
+ }, [
105
+ customNodeView,
106
+ view,
107
+ innerDeco,
108
+ node,
109
+ outerDeco,
110
+ getPos,
111
+ customNodeViewRef,
112
+ customNodeViewRootRef,
113
+ initialNode,
114
+ initialOuterDeco,
115
+ initialInnerDeco,
116
+ nodeDomRef,
117
+ shouldRender,
118
+ getPosFunc
119
+ ]);
120
+ const { childDescriptors, nodeViewDescRef } = (0, _useNodeViewDescriptor.useNodeViewDescriptor)(node, ()=>getPos.current(), domRef, nodeDomRef, innerDeco, outerDeco, undefined, contentDomRef);
121
+ const childContextValue = (0, _react.useMemo)(()=>({
122
+ parentRef: nodeViewDescRef,
123
+ siblingsRef: childDescriptors
124
+ }), [
125
+ childDescriptors,
126
+ nodeViewDescRef
127
+ ]);
61
128
  if (!shouldRender) return null;
62
129
  if (!customNodeViewRef.current) {
63
130
  customNodeViewRef.current = customNodeView(initialNode.current, // customNodeView will only be set if view is set, and we can only reach
@@ -67,7 +134,7 @@ function CustomNodeView(param) {
67
134
  }
68
135
  const { contentDOM } = customNodeViewRef.current;
69
136
  contentDomRef.current = contentDOM ?? null;
70
- return /*#__PURE__*/ (0, _react.createElement)(node.isInline ? "span" : "div", {
137
+ const element = /*#__PURE__*/ (0, _react.createElement)(node.isInline ? "span" : "div", {
71
138
  ref: customNodeViewRootRef,
72
139
  contentEditable: !!contentDOM,
73
140
  suppressContentEditableWarning: true
@@ -76,4 +143,13 @@ function CustomNodeView(param) {
76
143
  node: node,
77
144
  innerDecorations: innerDeco
78
145
  }), contentDOM));
79
- }
146
+ const decoratedElement = /*#__PURE__*/ (0, _react.cloneElement)(outerDeco.reduce(_ChildNodeViews.wrapInDeco, element), // eslint-disable-next-line @typescript-eslint/no-explicit-any
147
+ outerDeco.some((d)=>d.type.attrs.nodeName) ? {
148
+ ref: domRef
149
+ } : // we've already passed the domRef to the NodeView component
150
+ // as a prop
151
+ undefined);
152
+ return /*#__PURE__*/ _react.default.createElement(_ChildDescriptorsContext.ChildDescriptorsContext.Provider, {
153
+ value: childContextValue
154
+ }, decoratedElement);
155
+ });
@@ -82,12 +82,15 @@ const MarkView = /*#__PURE__*/ (0, _react.memo)(/*#__PURE__*/ (0, _react.forward
82
82
  if (!domRef.current) return;
83
83
  const firstChildDesc = childDescriptors.current[0];
84
84
  if (!viewDescRef.current) {
85
- viewDescRef.current = new _viewdesc.MarkViewDesc(parentRef.current, childDescriptors.current, ()=>getPos.current(), mark, domRef.current, firstChildDesc?.dom.parentElement ?? domRef.current);
85
+ viewDescRef.current = new _viewdesc.MarkViewDesc(parentRef.current, childDescriptors.current, ()=>getPos.current(), mark, domRef.current, firstChildDesc?.dom.parentElement ?? domRef.current, {
86
+ dom: domRef.current,
87
+ contentDOM: firstChildDesc?.dom.parentElement ?? domRef.current
88
+ });
86
89
  } else {
87
90
  viewDescRef.current.parent = parentRef.current;
88
- viewDescRef.current.dom = domRef.current;
91
+ viewDescRef.current.spec.dom = viewDescRef.current.dom = domRef.current;
89
92
  viewDescRef.current.children = childDescriptors.current;
90
- viewDescRef.current.contentDOM = firstChildDesc?.dom.parentElement ?? domRef.current;
93
+ viewDescRef.current.spec.contentDOM = viewDescRef.current.contentDOM = firstChildDesc?.dom.parentElement ?? domRef.current;
91
94
  viewDescRef.current.mark = mark;
92
95
  viewDescRef.current.getPos = ()=>getPos.current();
93
96
  }
@@ -9,15 +9,9 @@ Object.defineProperty(exports, "NodeView", {
9
9
  }
10
10
  });
11
11
  const _react = /*#__PURE__*/ _interop_require_wildcard(require("react"));
12
- const _ChildDescriptorsContext = require("../contexts/ChildDescriptorsContext.js");
13
12
  const _EditorContext = require("../contexts/EditorContext.js");
14
- const _NodeViewContext = require("../contexts/NodeViewContext.js");
15
- const _SelectNodeContext = require("../contexts/SelectNodeContext.js");
16
- const _StopEventContext = require("../contexts/StopEventContext.js");
17
- const _useNodeViewDescriptor = require("../hooks/useNodeViewDescriptor.js");
18
- const _ChildNodeViews = require("./ChildNodeViews.js");
19
13
  const _CustomNodeView = require("./CustomNodeView.js");
20
- const _OutputSpec = require("./OutputSpec.js");
14
+ const _ReactNodeView = require("./ReactNodeView.js");
21
15
  function _getRequireWildcardCache(nodeInterop) {
22
16
  if (typeof WeakMap !== "function") return null;
23
17
  var cacheBabelInterop = new WeakMap();
@@ -61,136 +55,22 @@ function _interop_require_wildcard(obj, nodeInterop) {
61
55
  }
62
56
  const NodeView = /*#__PURE__*/ (0, _react.memo)(function NodeView(param) {
63
57
  let { outerDeco, getPos, node, innerDeco, ...props } = param;
64
- const domRef = (0, _react.useRef)(null);
65
- const nodeDomRef = (0, _react.useRef)(null);
66
- const contentDomRef = (0, _react.useRef)(null);
67
- const getPosFunc = (0, _react.useRef)(()=>getPos.current()).current;
68
- // this is ill-conceived; should revisit
69
- const initialNode = (0, _react.useRef)(node);
70
- const initialOuterDeco = (0, _react.useRef)(outerDeco);
71
- const initialInnerDeco = (0, _react.useRef)(innerDeco);
72
- const customNodeViewRootRef = (0, _react.useRef)(null);
73
- const customNodeViewRef = (0, _react.useRef)(null);
74
- // const state = useEditorState();
75
- const { nodeViews } = (0, _react.useContext)(_NodeViewContext.NodeViewContext);
76
58
  const { view } = (0, _react.useContext)(_EditorContext.EditorContext);
77
- let element = null;
78
- const Component = nodeViews[node.type.name];
79
- const outputSpec = (0, _react.useMemo)(()=>node.type.spec.toDOM?.(node), [
80
- node
81
- ]);
82
- // TODO: Would be great to pull all of the custom node view stuff into
83
- // a hook
84
59
  const customNodeView = view?.someProp("nodeViews", (nodeViews)=>nodeViews?.[node.type.name]);
85
- (0, _react.useLayoutEffect)(()=>{
86
- if (!customNodeViewRef.current || !customNodeViewRootRef.current) return;
87
- const { dom } = customNodeViewRef.current;
88
- nodeDomRef.current = customNodeViewRootRef.current;
89
- customNodeViewRootRef.current.appendChild(dom);
90
- return ()=>{
91
- customNodeViewRef.current?.destroy?.();
92
- };
93
- }, []);
94
- (0, _react.useLayoutEffect)(()=>{
95
- if (!customNodeView || !customNodeViewRef.current) return;
96
- const { destroy, update } = customNodeViewRef.current;
97
- const updated = update?.call(customNodeViewRef.current, node, outerDeco, innerDeco) ?? true;
98
- if (updated) return;
99
- destroy?.call(customNodeViewRef.current);
100
- if (!customNodeViewRootRef.current) return;
101
- initialNode.current = node;
102
- initialOuterDeco.current = outerDeco;
103
- initialInnerDeco.current = innerDeco;
104
- customNodeViewRef.current = customNodeView(initialNode.current, // customNodeView will only be set if view is set, and we can only reach
105
- // this line if customNodeView is set
106
- // eslint-disable-next-line @typescript-eslint/no-non-null-assertion
107
- view, ()=>getPos.current(), initialOuterDeco.current, initialInnerDeco.current);
108
- const { dom } = customNodeViewRef.current;
109
- nodeDomRef.current = customNodeViewRootRef.current;
110
- customNodeViewRootRef.current.appendChild(dom);
111
- }, [
112
- customNodeView,
113
- view,
114
- innerDeco,
115
- node,
116
- outerDeco,
117
- getPos
118
- ]);
119
- const { hasContentDOM, childDescriptors, setStopEvent, setSelectNode, nodeViewDescRef } = (0, _useNodeViewDescriptor.useNodeViewDescriptor)(node, ()=>getPos.current(), domRef, nodeDomRef, innerDeco, outerDeco, undefined, contentDomRef);
120
- const finalProps = {
121
- ...props,
122
- ...!hasContentDOM && {
123
- contentEditable: false
124
- }
125
- };
126
- const nodeProps = (0, _react.useMemo)(()=>({
127
- node: node,
128
- getPos: getPosFunc,
129
- decorations: outerDeco,
130
- innerDecorations: innerDeco
131
- }), [
132
- getPosFunc,
133
- innerDeco,
134
- node,
135
- outerDeco
136
- ]);
137
- if (Component) {
138
- element = /*#__PURE__*/ _react.default.createElement(Component, {
139
- ...finalProps,
140
- ref: nodeDomRef,
141
- nodeProps: nodeProps
142
- }, /*#__PURE__*/ _react.default.createElement(_ChildNodeViews.ChildNodeViews, {
143
- getPos: getPos,
144
- node: node,
145
- innerDecorations: innerDeco
146
- }));
147
- } else if (customNodeView) {
148
- element = /*#__PURE__*/ _react.default.createElement(_CustomNodeView.CustomNodeView, {
149
- contentDomRef: contentDomRef,
60
+ if (customNodeView) {
61
+ return /*#__PURE__*/ _react.default.createElement(_CustomNodeView.CustomNodeView, {
150
62
  customNodeView: customNodeView,
151
- customNodeViewRef: customNodeViewRef,
152
- customNodeViewRootRef: customNodeViewRootRef,
153
- initialInnerDeco: initialInnerDeco,
154
- initialNode: initialNode,
155
- initialOuterDeco: initialOuterDeco,
156
63
  node: node,
157
- getPos: getPos,
158
- innerDeco: innerDeco
64
+ innerDeco: innerDeco,
65
+ outerDeco: outerDeco,
66
+ getPos: getPos
159
67
  });
160
- } else {
161
- if (outputSpec) {
162
- element = /*#__PURE__*/ _react.default.createElement(_OutputSpec.OutputSpec, {
163
- ...finalProps,
164
- ref: nodeDomRef,
165
- outputSpec: outputSpec
166
- }, /*#__PURE__*/ _react.default.createElement(_ChildNodeViews.ChildNodeViews, {
167
- getPos: getPos,
168
- node: node,
169
- innerDecorations: innerDeco
170
- }));
171
- }
172
- }
173
- if (!element) {
174
- throw new Error(`Node spec for ${node.type.name} is missing toDOM`);
175
68
  }
176
- const decoratedElement = /*#__PURE__*/ (0, _react.cloneElement)(outerDeco.reduce(_ChildNodeViews.wrapInDeco, element), // eslint-disable-next-line @typescript-eslint/no-explicit-any
177
- outerDeco.some((d)=>d.type.attrs.nodeName) ? {
178
- ref: domRef
179
- } : // we've already passed the domRef to the NodeView component
180
- // as a prop
181
- undefined);
182
- const childContextValue = (0, _react.useMemo)(()=>({
183
- parentRef: nodeViewDescRef,
184
- siblingsRef: childDescriptors
185
- }), [
186
- childDescriptors,
187
- nodeViewDescRef
188
- ]);
189
- return /*#__PURE__*/ _react.default.createElement(_SelectNodeContext.SelectNodeContext.Provider, {
190
- value: setSelectNode
191
- }, /*#__PURE__*/ _react.default.createElement(_StopEventContext.StopEventContext.Provider, {
192
- value: setStopEvent
193
- }, /*#__PURE__*/ _react.default.createElement(_ChildDescriptorsContext.ChildDescriptorsContext.Provider, {
194
- value: childContextValue
195
- }, decoratedElement)));
69
+ return /*#__PURE__*/ _react.default.createElement(_ReactNodeView.ReactNodeView, {
70
+ node: node,
71
+ innerDeco: innerDeco,
72
+ outerDeco: outerDeco,
73
+ getPos: getPos,
74
+ ...props
75
+ });
196
76
  });
@@ -57,7 +57,7 @@ const ForwardedOutputSpec = /*#__PURE__*/ (0, _react.memo)(/*#__PURE__*/ (0, _re
57
57
  return /*#__PURE__*/ _react.default.createElement(_react.default.Fragment, null, outputSpec);
58
58
  }
59
59
  if (!Array.isArray(outputSpec)) {
60
- throw new Error("@nytimes/react-prosemirror only supports strings and arrays in toDOM");
60
+ throw new Error("@handlewithcare/react-prosemirror only supports strings and arrays in toDOM");
61
61
  }
62
62
  const tagSpec = outputSpec[0];
63
63
  const tagName = tagSpec.replace(" ", ":");
@@ -0,0 +1,136 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", {
3
+ value: true
4
+ });
5
+ Object.defineProperty(exports, "ReactNodeView", {
6
+ enumerable: true,
7
+ get: function() {
8
+ return ReactNodeView;
9
+ }
10
+ });
11
+ const _react = /*#__PURE__*/ _interop_require_wildcard(require("react"));
12
+ const _ChildDescriptorsContext = require("../contexts/ChildDescriptorsContext.js");
13
+ const _NodeViewContext = require("../contexts/NodeViewContext.js");
14
+ const _SelectNodeContext = require("../contexts/SelectNodeContext.js");
15
+ const _StopEventContext = require("../contexts/StopEventContext.js");
16
+ const _useNodeViewDescriptor = require("../hooks/useNodeViewDescriptor.js");
17
+ const _ChildNodeViews = require("./ChildNodeViews.js");
18
+ const _OutputSpec = require("./OutputSpec.js");
19
+ function _getRequireWildcardCache(nodeInterop) {
20
+ if (typeof WeakMap !== "function") return null;
21
+ var cacheBabelInterop = new WeakMap();
22
+ var cacheNodeInterop = new WeakMap();
23
+ return (_getRequireWildcardCache = function(nodeInterop) {
24
+ return nodeInterop ? cacheNodeInterop : cacheBabelInterop;
25
+ })(nodeInterop);
26
+ }
27
+ function _interop_require_wildcard(obj, nodeInterop) {
28
+ if (!nodeInterop && obj && obj.__esModule) {
29
+ return obj;
30
+ }
31
+ if (obj === null || typeof obj !== "object" && typeof obj !== "function") {
32
+ return {
33
+ default: obj
34
+ };
35
+ }
36
+ var cache = _getRequireWildcardCache(nodeInterop);
37
+ if (cache && cache.has(obj)) {
38
+ return cache.get(obj);
39
+ }
40
+ var newObj = {
41
+ __proto__: null
42
+ };
43
+ var hasPropertyDescriptor = Object.defineProperty && Object.getOwnPropertyDescriptor;
44
+ for(var key in obj){
45
+ if (key !== "default" && Object.prototype.hasOwnProperty.call(obj, key)) {
46
+ var desc = hasPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : null;
47
+ if (desc && (desc.get || desc.set)) {
48
+ Object.defineProperty(newObj, key, desc);
49
+ } else {
50
+ newObj[key] = obj[key];
51
+ }
52
+ }
53
+ }
54
+ newObj.default = obj;
55
+ if (cache) {
56
+ cache.set(obj, newObj);
57
+ }
58
+ return newObj;
59
+ }
60
+ const ReactNodeView = /*#__PURE__*/ (0, _react.memo)(function ReactNodeView(param) {
61
+ let { outerDeco, getPos, node, innerDeco, ...props } = param;
62
+ const domRef = (0, _react.useRef)(null);
63
+ const nodeDomRef = (0, _react.useRef)(null);
64
+ const contentDomRef = (0, _react.useRef)(null);
65
+ const getPosFunc = (0, _react.useRef)(()=>getPos.current()).current;
66
+ const { nodeViews } = (0, _react.useContext)(_NodeViewContext.NodeViewContext);
67
+ let element = null;
68
+ const Component = nodeViews[node.type.name];
69
+ const outputSpec = (0, _react.useMemo)(()=>node.type.spec.toDOM?.(node), [
70
+ node
71
+ ]);
72
+ const { hasContentDOM, childDescriptors, setStopEvent, setSelectNode, nodeViewDescRef } = (0, _useNodeViewDescriptor.useNodeViewDescriptor)(node, ()=>getPos.current(), domRef, nodeDomRef, innerDeco, outerDeco, undefined, contentDomRef);
73
+ const finalProps = {
74
+ ...props,
75
+ ...!hasContentDOM && {
76
+ contentEditable: false
77
+ }
78
+ };
79
+ const nodeProps = (0, _react.useMemo)(()=>({
80
+ node: node,
81
+ getPos: getPosFunc,
82
+ decorations: outerDeco,
83
+ innerDecorations: innerDeco
84
+ }), [
85
+ getPosFunc,
86
+ innerDeco,
87
+ node,
88
+ outerDeco
89
+ ]);
90
+ if (Component) {
91
+ element = /*#__PURE__*/ _react.default.createElement(Component, {
92
+ ...finalProps,
93
+ ref: nodeDomRef,
94
+ nodeProps: nodeProps
95
+ }, /*#__PURE__*/ _react.default.createElement(_ChildNodeViews.ChildNodeViews, {
96
+ getPos: getPos,
97
+ node: node,
98
+ innerDecorations: innerDeco
99
+ }));
100
+ } else {
101
+ if (outputSpec) {
102
+ element = /*#__PURE__*/ _react.default.createElement(_OutputSpec.OutputSpec, {
103
+ ...finalProps,
104
+ ref: nodeDomRef,
105
+ outputSpec: outputSpec
106
+ }, /*#__PURE__*/ _react.default.createElement(_ChildNodeViews.ChildNodeViews, {
107
+ getPos: getPos,
108
+ node: node,
109
+ innerDecorations: innerDeco
110
+ }));
111
+ }
112
+ }
113
+ if (!element) {
114
+ throw new Error(`Node spec for ${node.type.name} is missing toDOM`);
115
+ }
116
+ const decoratedElement = /*#__PURE__*/ (0, _react.cloneElement)(outerDeco.reduce(_ChildNodeViews.wrapInDeco, element), // eslint-disable-next-line @typescript-eslint/no-explicit-any
117
+ outerDeco.some((d)=>d.type.attrs.nodeName) ? {
118
+ ref: domRef
119
+ } : // we've already passed the domRef to the NodeView component
120
+ // as a prop
121
+ undefined);
122
+ const childContextValue = (0, _react.useMemo)(()=>({
123
+ parentRef: nodeViewDescRef,
124
+ siblingsRef: childDescriptors
125
+ }), [
126
+ childDescriptors,
127
+ nodeViewDescRef
128
+ ]);
129
+ return /*#__PURE__*/ _react.default.createElement(_SelectNodeContext.SelectNodeContext.Provider, {
130
+ value: setSelectNode
131
+ }, /*#__PURE__*/ _react.default.createElement(_StopEventContext.StopEventContext.Provider, {
132
+ value: setStopEvent
133
+ }, /*#__PURE__*/ _react.default.createElement(_ChildDescriptorsContext.ChildDescriptorsContext.Provider, {
134
+ value: childContextValue
135
+ }, decoratedElement)));
136
+ });
@@ -10,7 +10,7 @@ Object.defineProperty(exports, "TextNodeView", {
10
10
  });
11
11
  const _prosemirrorview = require("prosemirror-view");
12
12
  const _react = require("react");
13
- const _reactdom = require("react-dom");
13
+ const _findDOMNode = require("../findDOMNode.js");
14
14
  const _viewdesc = require("../viewdesc.js");
15
15
  const _ChildNodeViews = require("./ChildNodeViews.js");
16
16
  function shallowEqual(objA, objB) {
@@ -42,7 +42,7 @@ let TextNodeView = class TextNodeView extends _react.Component {
42
42
  const { view, decorations, siblingsRef, parentRef, getPos, node } = this.props;
43
43
  // There simply is no other way to ref a text node
44
44
  // eslint-disable-next-line react/no-find-dom-node
45
- const dom = (0, _reactdom.findDOMNode)(this);
45
+ const dom = (0, _findDOMNode.findDOMNode)(this);
46
46
  // We only need to explicitly create a CompositionViewDesc
47
47
  // when a composition was started that produces a new text node.
48
48
  // Otherwise we just rely on re-rendering the renderRef
@@ -0,0 +1,46 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", {
3
+ value: true
4
+ });
5
+ function _export(target, all) {
6
+ for(var name in all)Object.defineProperty(target, name, {
7
+ enumerable: true,
8
+ get: all[name]
9
+ });
10
+ }
11
+ _export(exports, {
12
+ findDOMNode: function() {
13
+ return findDOMNode;
14
+ },
15
+ getInstance: function() {
16
+ return getInstance;
17
+ }
18
+ });
19
+ const _reflection = require("react-reconciler/reflection");
20
+ function getInstance(key) {
21
+ return key._reactInternals;
22
+ }
23
+ // https://github.com/facebook/react/blob/main/packages/react-dom-bindings/src/client/ReactFiberConfigDOM.js#L322
24
+ function getPublicInstance(instance) {
25
+ return instance;
26
+ }
27
+ // https://github.com/facebook/react/blob/main/packages/react-reconciler/src/ReactFiberReconciler.js#L153
28
+ function findHostInstance(component) {
29
+ const fiber = getInstance(component);
30
+ if (fiber === undefined) {
31
+ if (typeof component.render === "function") {
32
+ throw new Error("Unable to find node on an unmounted component.");
33
+ } else {
34
+ const keys = Object.keys(component).join(",");
35
+ throw new Error(`Argument appears to not be a ReactComponent. Keys: ${keys}`);
36
+ }
37
+ }
38
+ const hostFiber = (0, _reflection.findCurrentHostFiber)(fiber);
39
+ if (hostFiber === null) {
40
+ return null;
41
+ }
42
+ return getPublicInstance(hostFiber.stateNode);
43
+ }
44
+ function findDOMNode(componentOrElement) {
45
+ return findHostInstance(componentOrElement);
46
+ }
@@ -180,6 +180,7 @@ function useEditor(mount, options) {
180
180
  didWarnValueDefaultValue = true;
181
181
  }
182
182
  }
183
+ const flushSyncRef = (0, _react.useRef)(true);
183
184
  const [cursorWrapper, _setCursorWrapper] = (0, _react.useState)(null);
184
185
  const forceUpdate = (0, _useForceUpdate.useForceUpdate)();
185
186
  const defaultState = options.defaultState ?? EMPTY_STATE;
@@ -201,14 +202,23 @@ function useEditor(mount, options) {
201
202
  setCursorWrapper
202
203
  ]);
203
204
  const dispatchTransaction = (0, _react.useCallback)(function dispatchTransaction(tr) {
204
- (0, _reactdom.flushSync)(()=>{
205
+ if (flushSyncRef.current) {
206
+ (0, _reactdom.flushSync)(()=>{
207
+ if (!options.state) {
208
+ setState((s)=>s.apply(tr));
209
+ }
210
+ if (options.dispatchTransaction) {
211
+ options.dispatchTransaction.call(this, tr);
212
+ }
213
+ });
214
+ } else {
205
215
  if (!options.state) {
206
216
  setState((s)=>s.apply(tr));
207
217
  }
208
218
  if (options.dispatchTransaction) {
209
219
  options.dispatchTransaction.call(this, tr);
210
220
  }
211
- });
221
+ }
212
222
  }, [
213
223
  options.dispatchTransaction,
214
224
  options.state
@@ -273,7 +283,8 @@ function useEditor(mount, options) {
273
283
  registerEventListener,
274
284
  unregisterEventListener,
275
285
  cursorWrapper,
276
- docViewDescRef
286
+ docViewDescRef,
287
+ flushSyncRef
277
288
  }), [
278
289
  view,
279
290
  registerEventListener,
@@ -12,7 +12,7 @@ const _react = require("react");
12
12
  const _EditorContext = require("../contexts/EditorContext.js");
13
13
  const _useLayoutGroupEffect = require("./useLayoutGroupEffect.js");
14
14
  function useEditorEffect(effect, dependencies) {
15
- const { view } = (0, _react.useContext)(_EditorContext.EditorContext);
15
+ const { view, flushSyncRef } = (0, _react.useContext)(_EditorContext.EditorContext);
16
16
  // The rules of hooks want `effect` to be included in the
17
17
  // dependency list, but dependency issues for `effect` will
18
18
  // be caught by the linter at the call-site for
@@ -22,7 +22,10 @@ function useEditorEffect(effect, dependencies) {
22
22
  // be defined inline and run on every re-render.
23
23
  (0, _useLayoutGroupEffect.useLayoutGroupEffect)(()=>{
24
24
  if (view) {
25
- return effect(view);
25
+ flushSyncRef.current = false;
26
+ const result = effect(view);
27
+ flushSyncRef.current = true;
28
+ return result;
26
29
  }
27
30
  }, // The rules of hooks want to be able to statically
28
31
  // verify the dependencies for the effect, but this will