@apollohg/react-native-rich-text-editor 2.0.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 (494) hide show
  1. package/LICENSE +160 -0
  2. package/README.md +259 -0
  3. package/RUST-STANDARD-LIBRARY-NOTICES.html +8266 -0
  4. package/ReactNativeProseEditor.podspec +59 -0
  5. package/THIRD_PARTY_NOTICES.md +31155 -0
  6. package/android/build.gradle +188 -0
  7. package/android/consumer-rules.pro +18 -0
  8. package/android/expo/build.gradle +17 -0
  9. package/android/src/debug/java/com/apollohg/editor/viewer/PreparedProseDrawInstrumentation.kt +7 -0
  10. package/android/src/main/assets/editor-icons/MaterialIcons.json +2236 -0
  11. package/android/src/main/assets/editor-icons/MaterialIcons.ttf +0 -0
  12. package/android/src/main/java/com/apollohg/editor/AndroidApiCompat.kt +19 -0
  13. package/android/src/main/java/com/apollohg/editor/AndroidCollaborationTransport.kt +860 -0
  14. package/android/src/main/java/com/apollohg/editor/CaretGeometry.kt +91 -0
  15. package/android/src/main/java/com/apollohg/editor/CodeHighlighting.kt +141 -0
  16. package/android/src/main/java/com/apollohg/editor/DecodedBitmapBudget.kt +250 -0
  17. package/android/src/main/java/com/apollohg/editor/EditorAddons.kt +133 -0
  18. package/android/src/main/java/com/apollohg/editor/EditorBlockSpacing.kt +51 -0
  19. package/android/src/main/java/com/apollohg/editor/EditorBoxDrawable.kt +16 -0
  20. package/android/src/main/java/com/apollohg/editor/EditorBoxDrawing.kt +234 -0
  21. package/android/src/main/java/com/apollohg/editor/EditorCheckboxSpan.kt +87 -0
  22. package/android/src/main/java/com/apollohg/editor/EditorCodeHighlighting.kt +120 -0
  23. package/android/src/main/java/com/apollohg/editor/EditorDecorationLayer.java +18 -0
  24. package/android/src/main/java/com/apollohg/editor/EditorDocumentLayout.kt +626 -0
  25. package/android/src/main/java/com/apollohg/editor/EditorEditText.kt +1042 -0
  26. package/android/src/main/java/com/apollohg/editor/EditorEditTextAnnotations.kt +191 -0
  27. package/android/src/main/java/com/apollohg/editor/EditorEditTextCaret.kt +100 -0
  28. package/android/src/main/java/com/apollohg/editor/EditorEditTextClipboard.kt +101 -0
  29. package/android/src/main/java/com/apollohg/editor/EditorEditTextComposition.kt +220 -0
  30. package/android/src/main/java/com/apollohg/editor/EditorEditTextConfiguration.kt +316 -0
  31. package/android/src/main/java/com/apollohg/editor/EditorEditTextCorrection.kt +303 -0
  32. package/android/src/main/java/com/apollohg/editor/EditorEditTextDeferredUpdates.kt +327 -0
  33. package/android/src/main/java/com/apollohg/editor/EditorEditTextDeletion.kt +258 -0
  34. package/android/src/main/java/com/apollohg/editor/EditorEditTextDiagnostics.kt +83 -0
  35. package/android/src/main/java/com/apollohg/editor/EditorEditTextDragDrop.kt +67 -0
  36. package/android/src/main/java/com/apollohg/editor/EditorEditTextExternalComposition.kt +357 -0
  37. package/android/src/main/java/com/apollohg/editor/EditorEditTextHardwareInput.kt +277 -0
  38. package/android/src/main/java/com/apollohg/editor/EditorEditTextImages.kt +280 -0
  39. package/android/src/main/java/com/apollohg/editor/EditorEditTextInputLifecycle.kt +183 -0
  40. package/android/src/main/java/com/apollohg/editor/EditorEditTextInputPreparation.kt +79 -0
  41. package/android/src/main/java/com/apollohg/editor/EditorEditTextInputTraits.kt +384 -0
  42. package/android/src/main/java/com/apollohg/editor/EditorEditTextLayout.kt +100 -0
  43. package/android/src/main/java/com/apollohg/editor/EditorEditTextNativeMutation.kt +243 -0
  44. package/android/src/main/java/com/apollohg/editor/EditorEditTextPlaceholder.kt +154 -0
  45. package/android/src/main/java/com/apollohg/editor/EditorEditTextRenderPatch.kt +347 -0
  46. package/android/src/main/java/com/apollohg/editor/EditorEditTextRendering.kt +313 -0
  47. package/android/src/main/java/com/apollohg/editor/EditorEditTextRustCommands.kt +281 -0
  48. package/android/src/main/java/com/apollohg/editor/EditorEditTextSelection.kt +352 -0
  49. package/android/src/main/java/com/apollohg/editor/EditorEditTextState.kt +113 -0
  50. package/android/src/main/java/com/apollohg/editor/EditorEditTextTaskMarkers.kt +92 -0
  51. package/android/src/main/java/com/apollohg/editor/EditorEditTextTextCommit.kt +327 -0
  52. package/android/src/main/java/com/apollohg/editor/EditorEditTextToolbar.kt +84 -0
  53. package/android/src/main/java/com/apollohg/editor/EditorEditTextUpdates.kt +245 -0
  54. package/android/src/main/java/com/apollohg/editor/EditorGlyphHeightCursorDrawable.kt +42 -0
  55. package/android/src/main/java/com/apollohg/editor/EditorHeightBehavior.kt +13 -0
  56. package/android/src/main/java/com/apollohg/editor/EditorInputConnection.kt +923 -0
  57. package/android/src/main/java/com/apollohg/editor/EditorInputCoordinates.kt +191 -0
  58. package/android/src/main/java/com/apollohg/editor/EditorInputCorrection.kt +107 -0
  59. package/android/src/main/java/com/apollohg/editor/EditorInputCursorGeometry.kt +128 -0
  60. package/android/src/main/java/com/apollohg/editor/EditorInputSnapshots.kt +134 -0
  61. package/android/src/main/java/com/apollohg/editor/EditorInputSurroundingDeletion.kt +321 -0
  62. package/android/src/main/java/com/apollohg/editor/EditorKeyboardToolbarView.kt +851 -0
  63. package/android/src/main/java/com/apollohg/editor/EditorMentionStyle.kt +192 -0
  64. package/android/src/main/java/com/apollohg/editor/EditorReconciliationWatcher.kt +46 -0
  65. package/android/src/main/java/com/apollohg/editor/EditorStyleSheet.kt +303 -0
  66. package/android/src/main/java/com/apollohg/editor/EditorStyleSheetSpans.kt +253 -0
  67. package/android/src/main/java/com/apollohg/editor/EditorSurfaceInputConnection.kt +67 -0
  68. package/android/src/main/java/com/apollohg/editor/EditorTextDecorationDrawing.kt +143 -0
  69. package/android/src/main/java/com/apollohg/editor/EditorTextSurface.kt +712 -0
  70. package/android/src/main/java/com/apollohg/editor/EditorTextSurfaceDragDrop.kt +94 -0
  71. package/android/src/main/java/com/apollohg/editor/EditorTextSurfaceInteraction.kt +708 -0
  72. package/android/src/main/java/com/apollohg/editor/EditorTheme.kt +650 -0
  73. package/android/src/main/java/com/apollohg/editor/EditorV2Adapter.kt +912 -0
  74. package/android/src/main/java/com/apollohg/editor/EditorV2AdapterMutations.kt +402 -0
  75. package/android/src/main/java/com/apollohg/editor/EditorV2AdapterRendering.kt +123 -0
  76. package/android/src/main/java/com/apollohg/editor/EditorV2AdapterSelection.kt +203 -0
  77. package/android/src/main/java/com/apollohg/editor/EditorV2Backend.kt +120 -0
  78. package/android/src/main/java/com/apollohg/editor/EditorV2Driver.kt +87 -0
  79. package/android/src/main/java/com/apollohg/editor/EditorV2Registry.kt +97 -0
  80. package/android/src/main/java/com/apollohg/editor/EditorV2RenderValidation.kt +409 -0
  81. package/android/src/main/java/com/apollohg/editor/ExpoAutoGrowStyleSizePublisher.kt +34 -0
  82. package/android/src/main/java/com/apollohg/editor/ImageResizeOverlayView.kt +266 -0
  83. package/android/src/main/java/com/apollohg/editor/ImeTextCoordinateMapper.kt +102 -0
  84. package/android/src/main/java/com/apollohg/editor/KeyboardToolbarImeAnimationController.kt +101 -0
  85. package/android/src/main/java/com/apollohg/editor/MentionSuggestionChipView.kt +234 -0
  86. package/android/src/main/java/com/apollohg/editor/NativeCollaborationTransportRegistry.kt +493 -0
  87. package/android/src/main/java/com/apollohg/editor/NativeEditorExpoView.kt +813 -0
  88. package/android/src/main/java/com/apollohg/editor/NativeEditorExpoViewAtoms.kt +68 -0
  89. package/android/src/main/java/com/apollohg/editor/NativeEditorExpoViewBinding.kt +126 -0
  90. package/android/src/main/java/com/apollohg/editor/NativeEditorExpoViewDiagnostics.kt +208 -0
  91. package/android/src/main/java/com/apollohg/editor/NativeEditorExpoViewErrors.kt +146 -0
  92. package/android/src/main/java/com/apollohg/editor/NativeEditorExpoViewEvents.kt +150 -0
  93. package/android/src/main/java/com/apollohg/editor/NativeEditorExpoViewExternalComposition.kt +39 -0
  94. package/android/src/main/java/com/apollohg/editor/NativeEditorExpoViewFocus.kt +176 -0
  95. package/android/src/main/java/com/apollohg/editor/NativeEditorExpoViewLifecycle.kt +302 -0
  96. package/android/src/main/java/com/apollohg/editor/NativeEditorExpoViewMentions.kt +259 -0
  97. package/android/src/main/java/com/apollohg/editor/NativeEditorExpoViewNativeActions.kt +179 -0
  98. package/android/src/main/java/com/apollohg/editor/NativeEditorExpoViewOutsideTap.kt +214 -0
  99. package/android/src/main/java/com/apollohg/editor/NativeEditorExpoViewPendingUpdates.kt +376 -0
  100. package/android/src/main/java/com/apollohg/editor/NativeEditorExpoViewProperties.kt +234 -0
  101. package/android/src/main/java/com/apollohg/editor/NativeEditorExpoViewPropertyRetries.kt +197 -0
  102. package/android/src/main/java/com/apollohg/editor/NativeEditorExpoViewToolbar.kt +285 -0
  103. package/android/src/main/java/com/apollohg/editor/NativeEditorExpoViewTypes.kt +28 -0
  104. package/android/src/main/java/com/apollohg/editor/NativeEditorExpoViewUpdates.kt +271 -0
  105. package/android/src/main/java/com/apollohg/editor/NativeEditorModule.kt +687 -0
  106. package/android/src/main/java/com/apollohg/editor/NativeEditorOutsideTapDispatcher.kt +380 -0
  107. package/android/src/main/java/com/apollohg/editor/NativeEditorV2Numbers.kt +45 -0
  108. package/android/src/main/java/com/apollohg/editor/NativeEditorViewRegistry.kt +372 -0
  109. package/android/src/main/java/com/apollohg/editor/NativeImagePipeline.kt +22 -0
  110. package/android/src/main/java/com/apollohg/editor/NativeToolbar.kt +193 -0
  111. package/android/src/main/java/com/apollohg/editor/NativeToolbarIcons.kt +177 -0
  112. package/android/src/main/java/com/apollohg/editor/NativeToolbarItem.kt +274 -0
  113. package/android/src/main/java/com/apollohg/editor/OkHttpCollaborationSocket.kt +102 -0
  114. package/android/src/main/java/com/apollohg/editor/OrderedListMarkerFormatter.kt +130 -0
  115. package/android/src/main/java/com/apollohg/editor/PointerTransparentView.java +18 -0
  116. package/android/src/main/java/com/apollohg/editor/PositionBridge.kt +128 -0
  117. package/android/src/main/java/com/apollohg/editor/ProseViewerView.kt +854 -0
  118. package/android/src/main/java/com/apollohg/editor/RemoteSelectionOverlayView.kt +314 -0
  119. package/android/src/main/java/com/apollohg/editor/RenderBlockSpans.kt +314 -0
  120. package/android/src/main/java/com/apollohg/editor/RenderBridge.kt +224 -0
  121. package/android/src/main/java/com/apollohg/editor/RenderBridgeBlockStyles.kt +407 -0
  122. package/android/src/main/java/com/apollohg/editor/RenderBridgeElements.kt +544 -0
  123. package/android/src/main/java/com/apollohg/editor/RenderBridgeInlineAndAtoms.kt +631 -0
  124. package/android/src/main/java/com/apollohg/editor/RenderBridgeParagraphs.kt +215 -0
  125. package/android/src/main/java/com/apollohg/editor/RenderImageDecoder.kt +748 -0
  126. package/android/src/main/java/com/apollohg/editor/RenderImageLoader.kt +900 -0
  127. package/android/src/main/java/com/apollohg/editor/RenderLayoutConstants.kt +117 -0
  128. package/android/src/main/java/com/apollohg/editor/RenderMediaSpans.kt +337 -0
  129. package/android/src/main/java/com/apollohg/editor/RenderParagraphSpans.kt +182 -0
  130. package/android/src/main/java/com/apollohg/editor/RichTextEditorView.kt +951 -0
  131. package/android/src/main/java/com/apollohg/editor/SharedNativeImagePipeline.kt +78 -0
  132. package/android/src/main/java/com/apollohg/editor/UniffiEditorV2Backend.kt +261 -0
  133. package/android/src/main/java/com/apollohg/editor/viewer/AndroidProseLayoutEngine.kt +1656 -0
  134. package/android/src/main/java/com/apollohg/editor/viewer/FabricAttachmentSidecars.kt +80 -0
  135. package/android/src/main/java/com/apollohg/editor/viewer/FabricLeaseHandleBridge.kt +59 -0
  136. package/android/src/main/java/com/apollohg/editor/viewer/FallbackSelectionGeometry.kt +450 -0
  137. package/android/src/main/java/com/apollohg/editor/viewer/PreparedProseDrawingView.kt +678 -0
  138. package/android/src/main/java/com/apollohg/editor/viewer/PreparedProseInstrumentation.kt +608 -0
  139. package/android/src/main/java/com/apollohg/editor/viewer/PreparedProseLayout.kt +186 -0
  140. package/android/src/main/java/com/apollohg/editor/viewer/PreparedProseLayoutCache.kt +393 -0
  141. package/android/src/main/java/com/apollohg/editor/viewer/PreparedProseLayoutRegistry.kt +828 -0
  142. package/android/src/main/java/com/apollohg/editor/viewer/PreparedProseTheme.kt +316 -0
  143. package/android/src/main/java/com/apollohg/editor/viewer/PreparedProseViewerManager.kt +900 -0
  144. package/android/src/main/java/com/apollohg/editor/viewer/PreparedProseViewerPackage.kt +16 -0
  145. package/android/src/main/java/com/apollohg/editor/viewer/PreparedViewerAtoms.kt +89 -0
  146. package/android/src/main/java/com/apollohg/editor/viewer/ViewerCodeHighlighting.kt +91 -0
  147. package/android/src/main/java/com/apollohg/editor/viewer/ViewerDocument.kt +453 -0
  148. package/android/src/main/java/com/apollohg/editor/viewer/ViewerFontEnvironment.kt +282 -0
  149. package/android/src/main/java/com/apollohg/editor/viewer/ViewerImagePipeline.kt +460 -0
  150. package/android/src/main/jni/CMakeLists.txt +85 -0
  151. package/android/src/main/jni/PreparedProseViewerMeasurementsManager.cpp +334 -0
  152. package/android/src/main/jni/ReactNativeProseEditorSpec.h +17 -0
  153. package/android/src/main/jni/reactnativeproseeditor.h +6 -0
  154. package/android/src/main/res/values/attrs.xml +6 -0
  155. package/android/src/release/java/com/apollohg/editor/viewer/PreparedProseDrawInstrumentation.kt +9 -0
  156. package/app.plugin.js +62 -0
  157. package/common/cpp/react/renderer/components/PreparedProseViewer/PreparedProseMeasurementsManager.h +62 -0
  158. package/common/cpp/react/renderer/components/PreparedProseViewer/PreparedProseViewerComponentDescriptor.h +30 -0
  159. package/common/cpp/react/renderer/components/PreparedProseViewer/PreparedProseViewerShadowNode.cpp +192 -0
  160. package/common/cpp/react/renderer/components/PreparedProseViewer/PreparedProseViewerShadowNode.h +46 -0
  161. package/common/cpp/react/renderer/components/PreparedProseViewer/PreparedProseViewerState.h +145 -0
  162. package/dist/AtomHost.d.ts +17 -0
  163. package/dist/AtomHost.js +135 -0
  164. package/dist/DefaultAtomChip.d.ts +2 -0
  165. package/dist/DefaultAtomChip.js +22 -0
  166. package/dist/EditorAddon.d.ts +32 -0
  167. package/dist/EditorAddon.js +29 -0
  168. package/dist/EditorAddonNormalization.d.ts +6 -0
  169. package/dist/EditorAddonNormalization.js +48 -0
  170. package/dist/EditorMentionThemeNormalization.d.ts +8 -0
  171. package/dist/EditorMentionThemeNormalization.js +22 -0
  172. package/dist/EditorMentionThemeValidation.d.ts +12 -0
  173. package/dist/EditorMentionThemeValidation.js +95 -0
  174. package/dist/EditorStyleSheet.d.ts +4 -0
  175. package/dist/EditorStyleSheet.js +10 -0
  176. package/dist/EditorStyleSheetNormalization.d.ts +3 -0
  177. package/dist/EditorStyleSheetNormalization.js +226 -0
  178. package/dist/EditorStyleSheetTypes.d.ts +151 -0
  179. package/dist/EditorStyleSheetTypes.js +2 -0
  180. package/dist/EditorTheme.d.ts +117 -0
  181. package/dist/EditorTheme.js +41 -0
  182. package/dist/EditorToolbar.d.ts +4 -0
  183. package/dist/EditorToolbar.js +17 -0
  184. package/dist/EditorToolbarComponent.d.ts +13 -0
  185. package/dist/EditorToolbarComponent.js +24 -0
  186. package/dist/EditorToolbarItems.d.ts +9 -0
  187. package/dist/EditorToolbarItems.js +58 -0
  188. package/dist/EditorToolbarRegistry.d.ts +59 -0
  189. package/dist/EditorToolbarRegistry.js +175 -0
  190. package/dist/EditorToolbarTypes.d.ts +273 -0
  191. package/dist/EditorToolbarTypes.js +2 -0
  192. package/dist/EditorToolbarVisuals.d.ts +154 -0
  193. package/dist/EditorToolbarVisuals.js +228 -0
  194. package/dist/EditorUpdateRevision.d.ts +8 -0
  195. package/dist/EditorUpdateRevision.js +22 -0
  196. package/dist/ExternalTextComposition.d.ts +45 -0
  197. package/dist/ExternalTextComposition.js +537 -0
  198. package/dist/ImageLoadingPolicy.d.ts +54 -0
  199. package/dist/ImageLoadingPolicy.js +60 -0
  200. package/dist/NativeEditorBoundaryError.d.ts +111 -0
  201. package/dist/NativeEditorBoundaryError.js +268 -0
  202. package/dist/NativeEditorBridge.d.ts +9 -0
  203. package/dist/NativeEditorBridge.js +37 -0
  204. package/dist/NativeEditorCollaborationTransport.d.ts +154 -0
  205. package/dist/NativeEditorCollaborationTransport.js +275 -0
  206. package/dist/NativeEditorCreateConfig.d.ts +16 -0
  207. package/dist/NativeEditorCreateConfig.js +249 -0
  208. package/dist/NativeEditorCreateJson.d.ts +76 -0
  209. package/dist/NativeEditorCreateJson.js +474 -0
  210. package/dist/NativeEditorCreateValidation.d.ts +32 -0
  211. package/dist/NativeEditorCreateValidation.js +150 -0
  212. package/dist/NativeEditorDocumentBridge.d.ts +72 -0
  213. package/dist/NativeEditorDocumentBridge.js +305 -0
  214. package/dist/NativeEditorDocumentHandle.d.ts +70 -0
  215. package/dist/NativeEditorDocumentHandle.js +89 -0
  216. package/dist/NativeEditorLocalAwareness.d.ts +34 -0
  217. package/dist/NativeEditorLocalAwareness.js +153 -0
  218. package/dist/NativeEditorNativeModule.d.ts +48 -0
  219. package/dist/NativeEditorNativeModule.js +34 -0
  220. package/dist/NativeEditorRenderNormalization.d.ts +22 -0
  221. package/dist/NativeEditorRenderNormalization.js +274 -0
  222. package/dist/NativeEditorResultNormalization.d.ts +108 -0
  223. package/dist/NativeEditorResultNormalization.js +400 -0
  224. package/dist/NativeEditorTypes.d.ts +318 -0
  225. package/dist/NativeEditorTypes.js +15 -0
  226. package/dist/NativeEditorV2Decimal.d.ts +5 -0
  227. package/dist/NativeEditorV2Decimal.js +18 -0
  228. package/dist/NativeProseViewer.d.ts +122 -0
  229. package/dist/NativeProseViewer.js +130 -0
  230. package/dist/NativeRichTextEditor.d.ts +3 -0
  231. package/dist/NativeRichTextEditor.js +6 -0
  232. package/dist/ResourceLimits.d.ts +100 -0
  233. package/dist/ResourceLimits.js +80 -0
  234. package/dist/RichTextEditor.d.ts +4 -0
  235. package/dist/RichTextEditor.js +25 -0
  236. package/dist/RichTextEditorNativeTypes.d.ts +122 -0
  237. package/dist/RichTextEditorNativeTypes.js +2 -0
  238. package/dist/RichTextEditorNativeView.d.ts +12 -0
  239. package/dist/RichTextEditorNativeView.js +15 -0
  240. package/dist/RichTextEditorSerialization.d.ts +53 -0
  241. package/dist/RichTextEditorSerialization.js +283 -0
  242. package/dist/RichTextEditorTypes.d.ts +281 -0
  243. package/dist/RichTextEditorTypes.js +2 -0
  244. package/dist/ViewerConfiguration.d.ts +22 -0
  245. package/dist/ViewerConfiguration.js +6 -0
  246. package/dist/YjsCollaboration.d.ts +146 -0
  247. package/dist/YjsCollaboration.js +496 -0
  248. package/dist/addons.d.ts +193 -0
  249. package/dist/addons.js +122 -0
  250. package/dist/atomConstants.d.ts +3 -0
  251. package/dist/atomConstants.js +6 -0
  252. package/dist/atomInstances.d.ts +35 -0
  253. package/dist/atomInstances.js +79 -0
  254. package/dist/atomPolicy.d.ts +4 -0
  255. package/dist/atomPolicy.js +47 -0
  256. package/dist/atomUpdates.d.ts +2 -0
  257. package/dist/atomUpdates.js +38 -0
  258. package/dist/atoms.d.ts +92 -0
  259. package/dist/atoms.js +222 -0
  260. package/dist/attributeValidation.d.ts +4 -0
  261. package/dist/attributeValidation.js +97 -0
  262. package/dist/contentExpression.d.ts +6 -0
  263. package/dist/contentExpression.js +335 -0
  264. package/dist/index.d.ts +21 -0
  265. package/dist/index.js +78 -0
  266. package/dist/listMarkers.d.ts +15 -0
  267. package/dist/listMarkers.js +21 -0
  268. package/dist/schemaDefinition.d.ts +143 -0
  269. package/dist/schemaDefinition.js +206 -0
  270. package/dist/schemaDocument.d.ts +17 -0
  271. package/dist/schemaDocument.js +69 -0
  272. package/dist/schemaDocumentConstruction.d.ts +5 -0
  273. package/dist/schemaDocumentConstruction.js +125 -0
  274. package/dist/schemaNormalization.d.ts +29 -0
  275. package/dist/schemaNormalization.js +313 -0
  276. package/dist/schemaPresets.d.ts +68 -0
  277. package/dist/schemaPresets.js +198 -0
  278. package/dist/schemaResolution.d.ts +9 -0
  279. package/dist/schemaResolution.js +211 -0
  280. package/dist/schemas.d.ts +5 -0
  281. package/dist/schemas.js +28 -0
  282. package/dist/specs/PreparedProseViewerNativeComponent.d.ts +37 -0
  283. package/dist/specs/PreparedProseViewerNativeComponent.js +6 -0
  284. package/dist/useEditorToolbarInteractions.d.ts +12 -0
  285. package/dist/useEditorToolbarInteractions.js +218 -0
  286. package/dist/useEditorToolbarItems.d.ts +8 -0
  287. package/dist/useEditorToolbarItems.js +280 -0
  288. package/dist/useEditorToolbarPresentation.d.ts +4 -0
  289. package/dist/useEditorToolbarPresentation.js +203 -0
  290. package/dist/useEditorToolbarState.d.ts +63 -0
  291. package/dist/useEditorToolbarState.js +108 -0
  292. package/dist/useFocusPreservingFrames.d.ts +17 -0
  293. package/dist/useFocusPreservingFrames.js +108 -0
  294. package/dist/useNativeEditor.d.ts +66 -0
  295. package/dist/useNativeEditor.js +370 -0
  296. package/dist/useRichTextEditorCommands.d.ts +21 -0
  297. package/dist/useRichTextEditorCommands.js +299 -0
  298. package/dist/useRichTextEditorEvents.d.ts +18 -0
  299. package/dist/useRichTextEditorEvents.js +216 -0
  300. package/dist/useRichTextEditorMentions.d.ts +11 -0
  301. package/dist/useRichTextEditorMentions.js +316 -0
  302. package/dist/useRichTextEditorPresentation.d.ts +5 -0
  303. package/dist/useRichTextEditorPresentation.js +178 -0
  304. package/dist/useRichTextEditorState.d.ts +180 -0
  305. package/dist/useRichTextEditorState.js +405 -0
  306. package/dist/useRichTextEditorUpdates.d.ts +10 -0
  307. package/dist/useRichTextEditorUpdates.js +308 -0
  308. package/dist/useViewerAtoms.d.ts +38 -0
  309. package/dist/useViewerAtoms.js +288 -0
  310. package/expo-module.config.json +13 -0
  311. package/ios/EditorAddons.swift +354 -0
  312. package/ios/EditorCodeHighlighting.swift +184 -0
  313. package/ios/EditorCore.xcframework/Info.plist +44 -0
  314. package/ios/EditorCore.xcframework/ios-arm64/libeditor_core.a +0 -0
  315. package/ios/EditorCore.xcframework/ios-arm64_x86_64-simulator/libeditor_core.a +0 -0
  316. package/ios/EditorInteractionOverlays.swift +697 -0
  317. package/ios/EditorLayoutManager.swift +971 -0
  318. package/ios/EditorNodeTypes.swift +37 -0
  319. package/ios/EditorStyleSheet.swift +461 -0
  320. package/ios/EditorTextView+AttributedPatch.swift +305 -0
  321. package/ios/EditorTextView+Binding.swift +61 -0
  322. package/ios/EditorTextView+Caret.swift +333 -0
  323. package/ios/EditorTextView+Commands.swift +203 -0
  324. package/ios/EditorTextView+Delegate.swift +65 -0
  325. package/ios/EditorTextView+Diagnostics.swift +225 -0
  326. package/ios/EditorTextView+DragDrop.swift +290 -0
  327. package/ios/EditorTextView+ExternalComposition.swift +364 -0
  328. package/ios/EditorTextView+Images.swift +354 -0
  329. package/ios/EditorTextView+InputTraits.swift +200 -0
  330. package/ios/EditorTextView+KeyboardInput.swift +318 -0
  331. package/ios/EditorTextView+Layout.swift +245 -0
  332. package/ios/EditorTextView+MarkedText.swift +267 -0
  333. package/ios/EditorTextView+NativeInputLifecycle.swift +372 -0
  334. package/ios/EditorTextView+NativeMutation.swift +471 -0
  335. package/ios/EditorTextView+Reconciliation.swift +97 -0
  336. package/ios/EditorTextView+RenderPatch.swift +573 -0
  337. package/ios/EditorTextView+Rendering.swift +539 -0
  338. package/ios/EditorTextView+Selection.swift +542 -0
  339. package/ios/EditorTextView.swift +953 -0
  340. package/ios/EditorTheme.swift +626 -0
  341. package/ios/EditorV2Adapter+Commands.swift +204 -0
  342. package/ios/EditorV2Adapter+Envelope.swift +238 -0
  343. package/ios/EditorV2Adapter+Mutation.swift +392 -0
  344. package/ios/EditorV2Adapter+Registry.swift +185 -0
  345. package/ios/EditorV2Adapter+RenderState.swift +360 -0
  346. package/ios/EditorV2Adapter+RenderValidation.swift +420 -0
  347. package/ios/EditorV2Adapter+Selection.swift +329 -0
  348. package/ios/EditorV2Adapter+TextCommands.swift +430 -0
  349. package/ios/EditorV2Adapter.swift +376 -0
  350. package/ios/EditorV2Shadow.swift +353 -0
  351. package/ios/Generated_editor_core.swift +2378 -0
  352. package/ios/NativeCodeHighlighting.swift +159 -0
  353. package/ios/NativeCollaborationSocket.swift +144 -0
  354. package/ios/NativeCollaborationTransport+Protocol.swift +258 -0
  355. package/ios/NativeCollaborationTransport+Socket.swift +379 -0
  356. package/ios/NativeCollaborationTransport+Validation.swift +103 -0
  357. package/ios/NativeCollaborationTransport.swift +322 -0
  358. package/ios/NativeCollaborationTransportRegistry.swift +521 -0
  359. package/ios/NativeEditorExpoView+AccessoryRetry.swift +219 -0
  360. package/ios/NativeEditorExpoView+Binding.swift +268 -0
  361. package/ios/NativeEditorExpoView+Diagnostics.swift +66 -0
  362. package/ios/NativeEditorExpoView+Events.swift +131 -0
  363. package/ios/NativeEditorExpoView+Focus.swift +169 -0
  364. package/ios/NativeEditorExpoView+MentionRetry.swift +288 -0
  365. package/ios/NativeEditorExpoView+Mentions.swift +288 -0
  366. package/ios/NativeEditorExpoView+Properties.swift +300 -0
  367. package/ios/NativeEditorExpoView+Toolbar.swift +86 -0
  368. package/ios/NativeEditorExpoView+Updates.swift +312 -0
  369. package/ios/NativeEditorExpoView.swift +349 -0
  370. package/ios/NativeEditorModule.swift +856 -0
  371. package/ios/NativeEditorViewRegistry.swift +226 -0
  372. package/ios/NativeToolbar+ButtonStyle.swift +214 -0
  373. package/ios/NativeToolbar+Buttons.swift +228 -0
  374. package/ios/NativeToolbar+Diagnostics.swift +114 -0
  375. package/ios/NativeToolbar+Menu.swift +101 -0
  376. package/ios/NativeToolbar+Models.swift +519 -0
  377. package/ios/NativeToolbar+Placeholder.swift +39 -0
  378. package/ios/NativeToolbar.swift +612 -0
  379. package/ios/OrderedListMarkerFormatter.swift +103 -0
  380. package/ios/PositionBridge.swift +596 -0
  381. package/ios/ProseViewerView.swift +462 -0
  382. package/ios/RenderBridge+Atoms.swift +288 -0
  383. package/ios/RenderBridge+Attachments.swift +246 -0
  384. package/ios/RenderBridge+BlockBoundaries.swift +313 -0
  385. package/ios/RenderBridge+Style.swift +343 -0
  386. package/ios/RenderBridge.swift +704 -0
  387. package/ios/RichTextEditorView.swift +930 -0
  388. package/ios/SharedNativeImagePipeline+Cache.swift +189 -0
  389. package/ios/SharedNativeImagePipeline+Transport.swift +328 -0
  390. package/ios/SharedNativeImagePipeline.swift +533 -0
  391. package/ios/Viewer/CoreTextProseLayoutEngine+AttributedText.swift +436 -0
  392. package/ios/Viewer/CoreTextProseLayoutEngine+Models.swift +322 -0
  393. package/ios/Viewer/CoreTextProseLayoutEngine.swift +635 -0
  394. package/ios/Viewer/Fabric/PREPPreparedProseViewerComponentView.h +4 -0
  395. package/ios/Viewer/Fabric/PREPPreparedProseViewerComponentView.mm +767 -0
  396. package/ios/Viewer/Fabric/PreparedProseMeasurementsManager.mm +118 -0
  397. package/ios/Viewer/NativeSVGImageDecoder.h +9 -0
  398. package/ios/Viewer/NativeSVGImageDecoder.mm +106 -0
  399. package/ios/Viewer/NativeSVGPreflight.h +11 -0
  400. package/ios/Viewer/NativeSVGPreflight.mm +219 -0
  401. package/ios/Viewer/PreparedProseDrawingView.swift +639 -0
  402. package/ios/Viewer/PreparedProseInstrumentation.swift +387 -0
  403. package/ios/Viewer/PreparedProseLayout.swift +326 -0
  404. package/ios/Viewer/PreparedProseLayoutCache.swift +766 -0
  405. package/ios/Viewer/PreparedProseLayoutRegistry+Artifacts.swift +377 -0
  406. package/ios/Viewer/PreparedProseLayoutRegistry+Fabric.swift +582 -0
  407. package/ios/Viewer/PreparedProseLayoutRegistry+FabricOwnership.swift +128 -0
  408. package/ios/Viewer/PreparedProseLayoutRegistry.swift +381 -0
  409. package/ios/Viewer/ViewerDocument.swift +575 -0
  410. package/ios/Viewer/ViewerFontEnvironment.swift +283 -0
  411. package/ios/Viewer/ViewerImagePipeline.swift +478 -0
  412. package/ios/editor_coreFFI/editor_coreFFI.h +1023 -0
  413. package/ios/editor_coreFFI/module.modulemap +7 -0
  414. package/package.json +151 -0
  415. package/react-native.config.js +17 -0
  416. package/rust/android/arm64-v8a/libeditor_core.so +0 -0
  417. package/rust/android/armeabi-v7a/libeditor_core.so +0 -0
  418. package/rust/android/x86/libeditor_core.so +0 -0
  419. package/rust/android/x86_64/libeditor_core.so +0 -0
  420. package/rust/bindings/kotlin/uniffi/editor_core/editor_core.kt +3146 -0
  421. package/src/AtomHost.tsx +180 -0
  422. package/src/DefaultAtomChip.tsx +27 -0
  423. package/src/EditorAddon.ts +65 -0
  424. package/src/EditorAddonNormalization.ts +49 -0
  425. package/src/EditorMentionThemeNormalization.ts +25 -0
  426. package/src/EditorMentionThemeValidation.ts +133 -0
  427. package/src/EditorStyleSheet.ts +9 -0
  428. package/src/EditorStyleSheetNormalization.ts +219 -0
  429. package/src/EditorStyleSheetTypes.ts +189 -0
  430. package/src/EditorTheme.ts +196 -0
  431. package/src/EditorToolbar.tsx +31 -0
  432. package/src/EditorToolbarComponent.tsx +23 -0
  433. package/src/EditorToolbarItems.tsx +64 -0
  434. package/src/EditorToolbarRegistry.tsx +254 -0
  435. package/src/EditorToolbarTypes.tsx +322 -0
  436. package/src/EditorToolbarVisuals.tsx +270 -0
  437. package/src/EditorUpdateRevision.ts +26 -0
  438. package/src/ExternalTextComposition.ts +658 -0
  439. package/src/ImageLoadingPolicy.ts +125 -0
  440. package/src/NativeEditorBoundaryError.ts +345 -0
  441. package/src/NativeEditorBridge.ts +93 -0
  442. package/src/NativeEditorCollaborationTransport.ts +493 -0
  443. package/src/NativeEditorCreateConfig.ts +326 -0
  444. package/src/NativeEditorCreateJson.ts +579 -0
  445. package/src/NativeEditorCreateValidation.ts +178 -0
  446. package/src/NativeEditorDocumentBridge.ts +485 -0
  447. package/src/NativeEditorDocumentHandle.ts +168 -0
  448. package/src/NativeEditorLocalAwareness.ts +168 -0
  449. package/src/NativeEditorNativeModule.ts +97 -0
  450. package/src/NativeEditorRenderNormalization.ts +320 -0
  451. package/src/NativeEditorResultNormalization.ts +469 -0
  452. package/src/NativeEditorTypes.ts +366 -0
  453. package/src/NativeEditorV2Decimal.ts +13 -0
  454. package/src/NativeProseViewer.tsx +356 -0
  455. package/src/NativeRichTextEditor.tsx +33 -0
  456. package/src/ResourceLimits.ts +187 -0
  457. package/src/RichTextEditor.tsx +27 -0
  458. package/src/RichTextEditorNativeTypes.tsx +144 -0
  459. package/src/RichTextEditorNativeView.tsx +21 -0
  460. package/src/RichTextEditorSerialization.tsx +381 -0
  461. package/src/RichTextEditorTypes.tsx +327 -0
  462. package/src/ViewerConfiguration.ts +23 -0
  463. package/src/YjsCollaboration.ts +692 -0
  464. package/src/addons.ts +311 -0
  465. package/src/atomConstants.ts +3 -0
  466. package/src/atomInstances.ts +123 -0
  467. package/src/atomPolicy.ts +47 -0
  468. package/src/atomUpdates.ts +52 -0
  469. package/src/atoms.ts +379 -0
  470. package/src/attributeValidation.ts +116 -0
  471. package/src/contentExpression.ts +338 -0
  472. package/src/index.ts +295 -0
  473. package/src/listMarkers.ts +18 -0
  474. package/src/schemaDefinition.ts +395 -0
  475. package/src/schemaDocument.ts +92 -0
  476. package/src/schemaDocumentConstruction.ts +148 -0
  477. package/src/schemaNormalization.ts +367 -0
  478. package/src/schemaPresets.ts +250 -0
  479. package/src/schemaResolution.ts +242 -0
  480. package/src/schemas.ts +43 -0
  481. package/src/specs/PreparedProseViewerNativeComponent.ts +40 -0
  482. package/src/useEditorToolbarInteractions.tsx +329 -0
  483. package/src/useEditorToolbarItems.tsx +390 -0
  484. package/src/useEditorToolbarPresentation.tsx +483 -0
  485. package/src/useEditorToolbarState.tsx +172 -0
  486. package/src/useFocusPreservingFrames.ts +171 -0
  487. package/src/useNativeEditor.ts +534 -0
  488. package/src/useRichTextEditorCommands.tsx +478 -0
  489. package/src/useRichTextEditorEvents.tsx +342 -0
  490. package/src/useRichTextEditorMentions.tsx +441 -0
  491. package/src/useRichTextEditorPresentation.tsx +563 -0
  492. package/src/useRichTextEditorState.tsx +620 -0
  493. package/src/useRichTextEditorUpdates.tsx +403 -0
  494. package/src/useViewerAtoms.tsx +427 -0
@@ -0,0 +1,171 @@
1
+ import { useCallback, useEffect, useLayoutEffect, useRef, useState, type RefObject } from 'react';
2
+ import { Keyboard } from 'react-native';
3
+
4
+ import type { EditorToolbarFrame } from './EditorToolbar';
5
+
6
+ export interface RichTextEditorFocusPreservingElement {
7
+ measureInWindow(callback: (x: number, y: number, width: number, height: number) => void): void;
8
+ }
9
+
10
+ export type RichTextEditorFocusPreservingRef =
11
+ RefObject<RichTextEditorFocusPreservingElement | null>;
12
+
13
+ export type RichTextEditorFocusPreservingRefs =
14
+ | RichTextEditorFocusPreservingRef
15
+ | readonly RichTextEditorFocusPreservingRef[];
16
+
17
+ const EMPTY_FRAMES: readonly EditorToolbarFrame[] = [];
18
+
19
+ interface MeasuredFocusPreservingFrame {
20
+ target: RichTextEditorFocusPreservingElement;
21
+ frame: EditorToolbarFrame;
22
+ }
23
+
24
+ function sameRefs(
25
+ left: readonly RichTextEditorFocusPreservingRef[],
26
+ right: readonly RichTextEditorFocusPreservingRef[]
27
+ ): boolean {
28
+ return left.length === right.length && left.every((ref, index) => ref === right[index]);
29
+ }
30
+
31
+ function sameFrames(
32
+ left: readonly EditorToolbarFrame[],
33
+ right: readonly EditorToolbarFrame[]
34
+ ): boolean {
35
+ return (
36
+ left.length === right.length &&
37
+ left.every((frame, index) => {
38
+ const candidate = right[index];
39
+ return (
40
+ frame.x === candidate.x &&
41
+ frame.y === candidate.y &&
42
+ frame.width === candidate.width &&
43
+ frame.height === candidate.height
44
+ );
45
+ })
46
+ );
47
+ }
48
+
49
+ function validFrame(
50
+ x: number,
51
+ y: number,
52
+ width: number,
53
+ height: number
54
+ ): EditorToolbarFrame | null {
55
+ if (![x, y, width, height].every(Number.isFinite) || width <= 0 || height <= 0) {
56
+ return null;
57
+ }
58
+ return { x, y, width, height };
59
+ }
60
+
61
+ export function useFocusPreservingFrames(
62
+ refs: RichTextEditorFocusPreservingRefs | undefined,
63
+ enabled: boolean
64
+ ): {
65
+ frames: readonly EditorToolbarFrame[];
66
+ refresh: () => void;
67
+ } {
68
+ const normalizedRefs: readonly RichTextEditorFocusPreservingRef[] =
69
+ refs == null ? [] : Array.isArray(refs) ? refs : [refs as RichTextEditorFocusPreservingRef];
70
+ const stableRefs = useRef<readonly RichTextEditorFocusPreservingRef[]>(normalizedRefs);
71
+ if (!sameRefs(stableRefs.current, normalizedRefs)) {
72
+ stableRefs.current = normalizedRefs;
73
+ }
74
+ const currentRefs = stableRefs.current;
75
+
76
+ const generation = useRef(0);
77
+ const framesByRef = useRef(
78
+ new Map<RichTextEditorFocusPreservingRef, MeasuredFocusPreservingFrame>()
79
+ );
80
+ const [frames, setFrames] = useState<readonly EditorToolbarFrame[]>(EMPTY_FRAMES);
81
+
82
+ const publish = useCallback(() => {
83
+ const nextFrames = currentRefs.flatMap((ref) => {
84
+ const measurement = framesByRef.current.get(ref);
85
+ return measurement == null ? [] : [measurement.frame];
86
+ });
87
+ setFrames((current) => (sameFrames(current, nextFrames) ? current : nextFrames));
88
+ }, [currentRefs]);
89
+
90
+ const refresh = useCallback(() => {
91
+ const callbackGeneration = ++generation.current;
92
+ if (!enabled) {
93
+ framesByRef.current.clear();
94
+ setFrames((current) => (current.length === 0 ? current : EMPTY_FRAMES));
95
+ return;
96
+ }
97
+
98
+ const admittedRefs = new Set(currentRefs);
99
+ for (const ref of framesByRef.current.keys()) {
100
+ const measurement = framesByRef.current.get(ref);
101
+ if (
102
+ !admittedRefs.has(ref) ||
103
+ ref.current == null ||
104
+ measurement?.target !== ref.current
105
+ ) {
106
+ framesByRef.current.delete(ref);
107
+ }
108
+ }
109
+ publish();
110
+
111
+ currentRefs.forEach((ref) => {
112
+ const target = ref.current;
113
+ if (target == null || typeof target.measureInWindow !== 'function') {
114
+ framesByRef.current.delete(ref);
115
+ publish();
116
+ return;
117
+ }
118
+
119
+ try {
120
+ target.measureInWindow((x, y, width, height) => {
121
+ // An older measurement must not restore a removed or replaced target.
122
+ if (generation.current !== callbackGeneration || ref.current !== target) return;
123
+ const frame = validFrame(x, y, width, height);
124
+ if (frame == null) {
125
+ framesByRef.current.delete(ref);
126
+ } else {
127
+ framesByRef.current.set(ref, { target, frame });
128
+ }
129
+ publish();
130
+ });
131
+ } catch {
132
+ if (generation.current !== callbackGeneration) return;
133
+ framesByRef.current.delete(ref);
134
+ publish();
135
+ }
136
+ });
137
+ }, [currentRefs, enabled, publish]);
138
+
139
+ useLayoutEffect(() => {
140
+ refresh();
141
+ });
142
+
143
+ useEffect(() => {
144
+ if (!enabled) return;
145
+ const subscriptions = [
146
+ Keyboard.addListener('keyboardDidShow', refresh),
147
+ Keyboard.addListener('keyboardDidHide', refresh),
148
+ Keyboard.addListener('keyboardDidChangeFrame', refresh),
149
+ ];
150
+ return () => subscriptions.forEach((subscription) => subscription.remove());
151
+ }, [enabled, refresh]);
152
+
153
+ useEffect(
154
+ () => () => {
155
+ generation.current += 1;
156
+ framesByRef.current.clear();
157
+ },
158
+ []
159
+ );
160
+
161
+ return { frames, refresh };
162
+ }
163
+
164
+ /** @deprecated Use RichTextEditorFocusPreservingElement instead. */
165
+ export type NativeRichTextEditorFocusPreservingElement = RichTextEditorFocusPreservingElement;
166
+
167
+ /** @deprecated Use RichTextEditorFocusPreservingRef instead. */
168
+ export type NativeRichTextEditorFocusPreservingRef = RichTextEditorFocusPreservingRef;
169
+
170
+ /** @deprecated Use RichTextEditorFocusPreservingRefs instead. */
171
+ export type NativeRichTextEditorFocusPreservingRefs = RichTextEditorFocusPreservingRefs;
@@ -0,0 +1,534 @@
1
+ import { useCallback, useEffect, useMemo, useRef, useState } from 'react';
2
+
3
+ import {
4
+ _assertNativeEditorDocumentHandle,
5
+ _getNativeEditorDocumentHandleDescriptor,
6
+ type DocumentJSON,
7
+ type HistoryState,
8
+ type NativeEditorDocumentHandle,
9
+ type NativeEditorDocumentOrigin,
10
+ type NativeEditorDocumentState,
11
+ } from './NativeEditorBridge';
12
+ import { NativeEditorOperationError } from './NativeEditorBoundaryError';
13
+
14
+ //
15
+ // Headless document/control binding over a shared NativeEditorDocumentHandle
16
+ // (one native session per handle; the collaboration controller attaches to
17
+ // the same one). It mirrors the editor's retained document API — controlled
18
+ // `value`/`valueJSON` with the replace/reset history policy, `setContent`,
19
+ // `setContentJson`, `getContent`, `getContentJson` — through the v2 engine:
20
+ //
21
+ // - `valueJSONUpdateMode="replace"` lowers to one undoable local-API
22
+ // replacement (`undoableBoundary`); `"reset"` clears history
23
+ // (`resetAndClear`). Imperative setContent/setContentJson are undoable;
24
+ // clearContent is a non-undoable reset.
25
+ // - A room document in `AwaitRemote` renders as not-ready; content getters
26
+ // return empty values until Rust promotes an accepted server Step 2.
27
+ // - Remote commits arrive through `revisionSignal` (the collaboration
28
+ // controller's rendered revision): the binding re-reads the engine and
29
+ // emits content callbacks. It never pushes document state anywhere.
30
+ // - Controlled applies carry the last rendered engine revision as their base;
31
+ // a REVISION_MISMATCH refreshes from the engine and the effect re-applies
32
+ // against the fresh revision — never against guessed positions.
33
+
34
+ /** Configuration for {@link useNativeEditorDocument}. */
35
+ export interface UseNativeEditorDocumentOptions {
36
+ /** The shared document session. The binding never creates or destroys it. */
37
+ handle: NativeEditorDocumentHandle;
38
+ /** Controlled HTML content. */
39
+ value?: string;
40
+ /** Controlled ProseMirror JSON content (already normalized by the caller). Ignored when value is set. */
41
+ valueJSON?: DocumentJSON;
42
+ /** History policy for controlled replacements. Defaults to 'replace'. */
43
+ valueJSONUpdateMode?: 'replace' | 'reset';
44
+ /** External revision signal (e.g. from the collaboration controller) forcing an engine re-read. */
45
+ revisionSignal?: string | null;
46
+ onContentChange?: (html: string) => void;
47
+ onContentChangeJSON?: (json: DocumentJSON) => void;
48
+ onHistoryStateChange?: (state: HistoryState) => void;
49
+ /** Application notification after a successful local mutation. Transport does not depend on it. */
50
+ onLocalCommit?: () => void;
51
+ }
52
+
53
+ /** What {@link useNativeEditorDocument} returns. */
54
+ export interface UseNativeEditorDocumentReturn {
55
+ /** True once the engine document is ready (LocalReady/RoomReady). */
56
+ isReady: boolean;
57
+ /** Raw engine readiness. Null before the first read. */
58
+ documentState: NativeEditorDocumentState | null;
59
+ /** Decimal-string engine document revision; null while awaiting the server document. */
60
+ documentRevision: string | null;
61
+ /** Trusted origin paired with documentRevision. */
62
+ documentOrigin: NativeEditorDocumentOrigin | null;
63
+ /** Current undo/redo availability. */
64
+ historyState: HistoryState;
65
+ /**
66
+ * Re-read the engine now, emitting content/history callbacks when the
67
+ * engine advanced. The interactive editor calls this when the native
68
+ * view reports an adapter-driven commit (typing, toolbar commands).
69
+ */
70
+ refresh(): void;
71
+ /** Current document as HTML. Empty until the document is ready. */
72
+ getContent(): string;
73
+ /** Current document as ProseMirror JSON. Empty until the document is ready. */
74
+ getContentJson(): DocumentJSON;
75
+ /** The engine's own answer for whether the document holds no content. */
76
+ getIsEmpty(): boolean;
77
+ /** Current document as plain text, with markup stripped. */
78
+ getTextContent(): string;
79
+ /** Replace the document with HTML, as one undoable step. */
80
+ setContent(html: string): void;
81
+ /** Replace the document with JSON, as one undoable step. */
82
+ setContentJson(doc: DocumentJSON): void;
83
+ /** Reset to the schema's empty document and clear undo history. */
84
+ clearContent(): void;
85
+ undo(): void;
86
+ redo(): void;
87
+ canUndo(): boolean;
88
+ canRedo(): boolean;
89
+ }
90
+
91
+ const DEFAULT_V2_HISTORY_STATE: HistoryState = { canUndo: false, canRedo: false };
92
+
93
+ function isRevisionMismatchError(error: unknown): boolean {
94
+ return error instanceof NativeEditorOperationError && error.code === 'REVISION_MISMATCH';
95
+ }
96
+
97
+ interface V2EngineView {
98
+ editorId: string;
99
+ ready: boolean;
100
+ documentState: NativeEditorDocumentState | null;
101
+ documentRevision: string | null;
102
+ documentOrigin: NativeEditorDocumentOrigin | null;
103
+ historyState: HistoryState;
104
+ contentKey: string | null;
105
+ }
106
+
107
+ /**
108
+ * Headless binding to a document handle: the same controlled content,
109
+ * getters, and history the editor exposes, with no view attached. Use it to
110
+ * read or drive a document that is not currently mounted — a preview, a
111
+ * background save, a test.
112
+ *
113
+ * `RichTextEditor` uses this internally, so mounting an editor on the
114
+ * same handle does not conflict with it.
115
+ */
116
+ export function useNativeEditorDocument(
117
+ options: UseNativeEditorDocumentOptions
118
+ ): UseNativeEditorDocumentReturn {
119
+ const {
120
+ handle,
121
+ value,
122
+ valueJSON,
123
+ valueJSONUpdateMode = 'replace',
124
+ revisionSignal,
125
+ onLocalCommit,
126
+ } = options;
127
+
128
+ _assertNativeEditorDocumentHandle(handle);
129
+ const editorId = handle.editorId;
130
+
131
+ const onContentChangeRef = useRef(options.onContentChange);
132
+ onContentChangeRef.current = options.onContentChange;
133
+ const onContentChangeJSONRef = useRef(options.onContentChangeJSON);
134
+ onContentChangeJSONRef.current = options.onContentChangeJSON;
135
+ const onHistoryStateChangeRef = useRef(options.onHistoryStateChange);
136
+ onHistoryStateChangeRef.current = options.onHistoryStateChange;
137
+ const onLocalCommitRef = useRef(onLocalCommit);
138
+ onLocalCommitRef.current = onLocalCommit;
139
+
140
+ const [engineView, setEngineView] = useState<V2EngineView>({
141
+ editorId,
142
+ ready: false,
143
+ documentState: null,
144
+ documentRevision: null,
145
+ documentOrigin: null,
146
+ historyState: DEFAULT_V2_HISTORY_STATE,
147
+ contentKey: null,
148
+ });
149
+ const currentEditorIdRef = useRef(editorId);
150
+ currentEditorIdRef.current = editorId;
151
+ const readyRef = useRef({ editorId, ready: false });
152
+ const emittedRef = useRef({
153
+ editorId,
154
+ lastRevision: null as string | null,
155
+ lastContentKey: null as string | null,
156
+ lastHistoryKey: null as string | null,
157
+ });
158
+ const pendingControlledEchoesRef = useRef({
159
+ editorId,
160
+ keys: [] as string[],
161
+ });
162
+ const controlledKindRef = useRef<'html' | 'json' | null>(null);
163
+ controlledKindRef.current = value != null ? 'html' : valueJSON != null ? 'json' : null;
164
+ const ignoredControlledEchoRef = useRef<string | null>(null);
165
+ const lastControlledContentKeyRef = useRef<string | null>(null);
166
+ if (readyRef.current.editorId !== editorId) {
167
+ readyRef.current = { editorId, ready: false };
168
+ }
169
+ if (emittedRef.current.editorId !== editorId) {
170
+ emittedRef.current = {
171
+ editorId,
172
+ lastRevision: null,
173
+ lastContentKey: null,
174
+ lastHistoryKey: null,
175
+ };
176
+ pendingControlledEchoesRef.current = { editorId, keys: [] };
177
+ ignoredControlledEchoRef.current = null;
178
+ lastControlledContentKeyRef.current = null;
179
+ }
180
+
181
+ const refresh = useCallback(
182
+ (emitContentCallbacks: boolean) => {
183
+ const refreshedEditorId = handle.editorId;
184
+ if (handle.isDestroyed || currentEditorIdRef.current !== refreshedEditorId) {
185
+ return;
186
+ }
187
+ const state = handle.bridge.getState();
188
+ const ready = state.documentState !== 'AwaitRemote';
189
+ let contentKey: string | null = null;
190
+ let snapshotHtml: string | null = null;
191
+ let snapshotJson: DocumentJSON | null = null;
192
+ if (ready) {
193
+ const snapshot = handle.bridge.getContentSnapshot();
194
+ snapshotHtml = snapshot.html;
195
+ snapshotJson = snapshot.json;
196
+ contentKey = JSON.stringify(snapshot.json);
197
+ }
198
+ if (currentEditorIdRef.current !== refreshedEditorId) return;
199
+ const historyState: HistoryState = {
200
+ canUndo: state.canUndo,
201
+ canRedo: state.canRedo,
202
+ };
203
+ readyRef.current = { editorId: refreshedEditorId, ready };
204
+ setEngineView({
205
+ editorId: refreshedEditorId,
206
+ ready,
207
+ documentState: state.documentState,
208
+ documentRevision: state.documentRevision,
209
+ documentOrigin: state.documentOrigin,
210
+ historyState,
211
+ contentKey,
212
+ });
213
+
214
+ const historyKey = `${state.canUndo}/${state.canRedo}`;
215
+ const emitted = emittedRef.current;
216
+ if (
217
+ currentEditorIdRef.current !== refreshedEditorId ||
218
+ emitted.editorId !== refreshedEditorId
219
+ ) {
220
+ return;
221
+ }
222
+ if (historyKey !== emitted.lastHistoryKey) {
223
+ emitted.lastHistoryKey = historyKey;
224
+ onHistoryStateChangeRef.current?.(historyState);
225
+ }
226
+
227
+ if (ready) {
228
+ const lastRevision = emitted.lastRevision;
229
+ if (
230
+ emitContentCallbacks &&
231
+ lastRevision != null &&
232
+ lastRevision !== state.documentRevision &&
233
+ emitted.lastContentKey !== contentKey
234
+ ) {
235
+ if (snapshotHtml != null) {
236
+ if (
237
+ controlledKindRef.current === 'html' &&
238
+ onContentChangeRef.current != null
239
+ ) {
240
+ const echoes = pendingControlledEchoesRef.current.keys;
241
+ echoes.push(`html:${snapshotHtml}`);
242
+ if (echoes.length > 32) echoes.shift();
243
+ }
244
+ onContentChangeRef.current?.(snapshotHtml);
245
+ }
246
+ if (snapshotJson != null) {
247
+ if (
248
+ controlledKindRef.current === 'json' &&
249
+ onContentChangeJSONRef.current != null
250
+ ) {
251
+ const echoes = pendingControlledEchoesRef.current.keys;
252
+ echoes.push(`json:${contentKey}`);
253
+ if (echoes.length > 32) echoes.shift();
254
+ }
255
+ onContentChangeJSONRef.current?.(snapshotJson);
256
+ }
257
+ }
258
+ emitted.lastRevision = state.documentRevision;
259
+ emitted.lastContentKey = contentKey;
260
+ }
261
+ },
262
+ [handle]
263
+ );
264
+
265
+ useEffect(() => {
266
+ refresh(true);
267
+ }, [refresh, revisionSignal]);
268
+
269
+ const refreshFromEngine = useCallback(() => {
270
+ refresh(true);
271
+ }, [refresh]);
272
+
273
+ const serializedControlledJson = useMemo(
274
+ () => (value == null && valueJSON != null ? JSON.stringify(valueJSON) : null),
275
+ [value, valueJSON]
276
+ );
277
+
278
+ // Controlled document flow: external value/valueJSON changes lower to one
279
+ // local-API replacement carrying the rendered engine revision as its
280
+ // base. Content callbacks stay suppressed (controlled sync parity).
281
+ useEffect(() => {
282
+ if (engineView.editorId !== editorId || !engineView.ready || handle.isDestroyed) return;
283
+ if (engineView.documentRevision == null) return;
284
+ const wantsHtml = value != null;
285
+ const wantsJson = value == null && serializedControlledJson != null;
286
+ if (!wantsHtml && !wantsJson) return;
287
+
288
+ const controlledContentKey = wantsHtml
289
+ ? `html:${value}`
290
+ : `json:${serializedControlledJson}`;
291
+ const controlledContentChanged =
292
+ lastControlledContentKeyRef.current !== controlledContentKey;
293
+ if (controlledContentChanged) {
294
+ lastControlledContentKeyRef.current = controlledContentKey;
295
+ ignoredControlledEchoRef.current = null;
296
+ }
297
+ if (ignoredControlledEchoRef.current === controlledContentKey) return;
298
+ if (!controlledContentChanged && pendingControlledEchoesRef.current.keys.length > 0) return;
299
+
300
+ const snapshot = handle.bridge.getContentSnapshot();
301
+ if (currentEditorIdRef.current !== editorId || emittedRef.current.editorId !== editorId) {
302
+ return;
303
+ }
304
+ const currentJsonKey = JSON.stringify(snapshot.json);
305
+ if (wantsHtml && snapshot.html === value) {
306
+ const echoIndex = pendingControlledEchoesRef.current.keys.indexOf(controlledContentKey);
307
+ if (echoIndex >= 0) {
308
+ pendingControlledEchoesRef.current.keys.splice(0, echoIndex + 1);
309
+ }
310
+ emittedRef.current.lastRevision = engineView.documentRevision;
311
+ emittedRef.current.lastContentKey = currentJsonKey;
312
+ return;
313
+ }
314
+ if (wantsJson && currentJsonKey === serializedControlledJson) {
315
+ const echoIndex = pendingControlledEchoesRef.current.keys.indexOf(controlledContentKey);
316
+ if (echoIndex >= 0) {
317
+ pendingControlledEchoesRef.current.keys.splice(0, echoIndex + 1);
318
+ }
319
+ emittedRef.current.lastRevision = engineView.documentRevision;
320
+ emittedRef.current.lastContentKey = currentJsonKey;
321
+ return;
322
+ }
323
+
324
+ const echoIndex = pendingControlledEchoesRef.current.keys.indexOf(controlledContentKey);
325
+ if (echoIndex >= 0) {
326
+ pendingControlledEchoesRef.current.keys.splice(0, echoIndex + 1);
327
+ ignoredControlledEchoRef.current = controlledContentKey;
328
+ return;
329
+ }
330
+
331
+ try {
332
+ pendingControlledEchoesRef.current.keys = [];
333
+ handle.bridge.applyLocalApi({
334
+ ...(wantsHtml
335
+ ? { setHtml: value }
336
+ : { setJson: JSON.parse(serializedControlledJson!) as DocumentJSON }),
337
+ history: valueJSONUpdateMode === 'reset' ? 'resetAndClear' : 'undoableBoundary',
338
+ baseDocumentRevision: engineView.documentRevision,
339
+ });
340
+ if (currentEditorIdRef.current !== editorId) return;
341
+ onLocalCommitRef.current?.();
342
+ refresh(false);
343
+ } catch (error) {
344
+ if (isRevisionMismatchError(error)) {
345
+ // Refresh from the engine; the effect re-applies against the
346
+ // fresh revision (never a guessed one).
347
+ refresh(false);
348
+ return;
349
+ }
350
+ throw error;
351
+ }
352
+ }, [
353
+ handle,
354
+ value,
355
+ serializedControlledJson,
356
+ valueJSONUpdateMode,
357
+ editorId,
358
+ engineView.editorId,
359
+ engineView.ready,
360
+ engineView.documentRevision,
361
+ refresh,
362
+ ]);
363
+
364
+ const mutate = useCallback(
365
+ (operation: () => unknown) => {
366
+ if (handle.isDestroyed || currentEditorIdRef.current !== handle.editorId) {
367
+ if (__DEV__) {
368
+ console.error(
369
+ 'useNativeEditorDocument: dropped a mutation because the handle is not the current binding',
370
+ {
371
+ destroyed: handle.isDestroyed,
372
+ boundEditorId: currentEditorIdRef.current,
373
+ handleEditorId: handle.editorId,
374
+ }
375
+ );
376
+ }
377
+ return;
378
+ }
379
+ operation();
380
+ if (currentEditorIdRef.current !== handle.editorId) return;
381
+ onLocalCommitRef.current?.();
382
+ refresh(true);
383
+ },
384
+ [handle, refresh]
385
+ );
386
+
387
+ const setContent = useCallback(
388
+ (html: string) => {
389
+ mutate(() =>
390
+ handle.bridge.replaceDocument({ setHtml: html, history: 'undoableBoundary' })
391
+ );
392
+ },
393
+ [handle, mutate]
394
+ );
395
+
396
+ const setContentJson = useCallback(
397
+ (doc: DocumentJSON) => {
398
+ mutate(() =>
399
+ handle.bridge.replaceDocument({ setJson: doc, history: 'undoableBoundary' })
400
+ );
401
+ },
402
+ [handle, mutate]
403
+ );
404
+
405
+ const clearContent = useCallback(() => {
406
+ mutate(() => {
407
+ return handle.bridge.replaceDocument({
408
+ setJson: _getNativeEditorDocumentHandleDescriptor(handle).emptyDocument,
409
+ history: 'resetAndClear',
410
+ });
411
+ });
412
+ }, [handle, mutate]);
413
+
414
+ const undo = useCallback(() => {
415
+ mutate(() => handle.bridge.undo());
416
+ }, [handle, mutate]);
417
+
418
+ const redo = useCallback(() => {
419
+ mutate(() => handle.bridge.redo());
420
+ }, [handle, mutate]);
421
+
422
+ const getContent = useCallback((): string => {
423
+ if (
424
+ handle.isDestroyed ||
425
+ readyRef.current.editorId !== handle.editorId ||
426
+ !readyRef.current.ready
427
+ ) {
428
+ return '';
429
+ }
430
+ return handle.bridge.getDocumentHtml();
431
+ }, [handle]);
432
+
433
+ const getContentJson = useCallback((): DocumentJSON => {
434
+ if (
435
+ handle.isDestroyed ||
436
+ readyRef.current.editorId !== handle.editorId ||
437
+ !readyRef.current.ready
438
+ ) {
439
+ return {};
440
+ }
441
+ return handle.bridge.getDocumentJson();
442
+ }, [handle]);
443
+
444
+ const getIsEmpty = useCallback((): boolean => {
445
+ if (
446
+ handle.isDestroyed ||
447
+ readyRef.current.editorId !== handle.editorId ||
448
+ !readyRef.current.ready
449
+ ) {
450
+ return true;
451
+ }
452
+ return handle.bridge.renderUpdate().documentIsEmpty;
453
+ }, [handle]);
454
+
455
+ const getTextContent = useCallback((): string => {
456
+ if (
457
+ handle.isDestroyed ||
458
+ readyRef.current.editorId !== handle.editorId ||
459
+ !readyRef.current.ready
460
+ ) {
461
+ return '';
462
+ }
463
+ return handle.bridge.getDocumentHtml().replace(/<[^>]+>/g, '');
464
+ }, [handle]);
465
+
466
+ const canUndo = useCallback((): boolean => {
467
+ if (
468
+ handle.isDestroyed ||
469
+ readyRef.current.editorId !== handle.editorId ||
470
+ !readyRef.current.ready
471
+ ) {
472
+ return false;
473
+ }
474
+ return handle.bridge.getState().canUndo;
475
+ }, [handle]);
476
+
477
+ const canRedo = useCallback((): boolean => {
478
+ if (
479
+ handle.isDestroyed ||
480
+ readyRef.current.editorId !== handle.editorId ||
481
+ !readyRef.current.ready
482
+ ) {
483
+ return false;
484
+ }
485
+ return handle.bridge.getState().canRedo;
486
+ }, [handle]);
487
+
488
+ let renderedEngineView = engineView;
489
+ if (engineView.editorId !== editorId) {
490
+ if (handle.isDestroyed) {
491
+ renderedEngineView = {
492
+ editorId,
493
+ ready: false,
494
+ documentState: null,
495
+ documentRevision: null,
496
+ documentOrigin: null,
497
+ historyState: DEFAULT_V2_HISTORY_STATE,
498
+ contentKey: null,
499
+ };
500
+ } else {
501
+ const state = handle.bridge.getState();
502
+ renderedEngineView = {
503
+ editorId,
504
+ ready: state.documentState !== 'AwaitRemote',
505
+ documentState: state.documentState,
506
+ documentRevision: state.documentRevision,
507
+ documentOrigin: state.documentOrigin,
508
+ historyState: { canUndo: state.canUndo, canRedo: state.canRedo },
509
+ contentKey: null,
510
+ };
511
+ }
512
+ readyRef.current = { editorId, ready: renderedEngineView.ready };
513
+ }
514
+
515
+ return {
516
+ isReady: renderedEngineView.ready,
517
+ documentState: renderedEngineView.documentState,
518
+ documentRevision: renderedEngineView.documentRevision,
519
+ documentOrigin: renderedEngineView.documentOrigin,
520
+ historyState: renderedEngineView.historyState,
521
+ refresh: refreshFromEngine,
522
+ getContent,
523
+ getContentJson,
524
+ getIsEmpty,
525
+ getTextContent,
526
+ setContent,
527
+ setContentJson,
528
+ clearContent,
529
+ undo,
530
+ redo,
531
+ canUndo,
532
+ canRedo,
533
+ };
534
+ }