react-native-enriched-markdown-scaffold 0.7.4-scaffold.9 → 1.0.2-scaffold.2

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 (469) hide show
  1. package/README.md +54 -8
  2. package/ReactNativeEnrichedMarkdown.podspec +82 -73
  3. package/android/build.gradle +186 -1
  4. package/android/consumer-rules.pro +1 -1
  5. package/android/generated/java/com/facebook/react/viewmanagers/EnrichedMarkdownManagerDelegate.java +9 -0
  6. package/android/generated/java/com/facebook/react/viewmanagers/EnrichedMarkdownManagerInterface.java +3 -0
  7. package/android/generated/java/com/facebook/react/viewmanagers/EnrichedMarkdownTextInputManagerDelegate.java +24 -0
  8. package/android/generated/java/com/facebook/react/viewmanagers/EnrichedMarkdownTextInputManagerInterface.java +8 -0
  9. package/android/generated/java/com/facebook/react/viewmanagers/EnrichedMarkdownTextManagerDelegate.java +9 -0
  10. package/android/generated/java/com/facebook/react/viewmanagers/EnrichedMarkdownTextManagerInterface.java +3 -0
  11. package/android/generated/jni/react/renderer/components/EnrichedMarkdownTextSpec/EventEmitters.cpp +75 -0
  12. package/android/generated/jni/react/renderer/components/EnrichedMarkdownTextSpec/EventEmitters.h +63 -0
  13. package/android/generated/jni/react/renderer/components/EnrichedMarkdownTextSpec/Props.cpp +35 -0
  14. package/android/generated/jni/react/renderer/components/EnrichedMarkdownTextSpec/Props.h +886 -23
  15. package/android/src/main/baseline-prof.txt +1 -1
  16. package/android/src/main/cpp/jni-adapter.cpp +74 -0
  17. package/android/src/main/java/com/swmansion/enriched/markdown/EnrichedMarkdown.kt +189 -13
  18. package/android/src/main/java/com/swmansion/enriched/markdown/EnrichedMarkdownInternalText.kt +17 -0
  19. package/android/src/main/java/com/swmansion/enriched/markdown/EnrichedMarkdownManager.kt +50 -0
  20. package/android/src/main/java/com/swmansion/enriched/markdown/EnrichedMarkdownText.kt +48 -1
  21. package/android/src/main/java/com/swmansion/enriched/markdown/EnrichedMarkdownTextLayoutManager.kt +10 -1
  22. package/android/src/main/java/com/swmansion/enriched/markdown/EnrichedMarkdownTextManager.kt +42 -0
  23. package/android/src/main/java/com/swmansion/enriched/markdown/MeasurementStore.kt +82 -4
  24. package/android/src/main/java/com/swmansion/enriched/markdown/events/CopyPressEvent.kt +24 -0
  25. package/android/src/main/java/com/swmansion/enriched/markdown/input/EnrichedMarkdownTextInputManager.kt +54 -4
  26. package/android/src/main/java/com/swmansion/enriched/markdown/input/EnrichedMarkdownTextInputView.kt +901 -462
  27. package/android/src/main/java/com/swmansion/enriched/markdown/input/MarkdownClipboard.kt +42 -0
  28. package/android/src/main/java/com/swmansion/enriched/markdown/input/editing/BlockEditCoordinator.kt +196 -0
  29. package/android/src/main/java/com/swmansion/enriched/markdown/input/editing/ClipboardCoordinator.kt +73 -0
  30. package/android/src/main/java/com/swmansion/enriched/markdown/input/editing/EditContext.kt +19 -0
  31. package/android/src/main/java/com/swmansion/enriched/markdown/input/editing/EditPipeline.kt +248 -0
  32. package/android/src/main/java/com/swmansion/enriched/markdown/input/editing/EditSession.kt +52 -0
  33. package/android/src/main/java/com/swmansion/enriched/markdown/input/editing/InputConnectionWrapper.kt +101 -7
  34. package/android/src/main/java/com/swmansion/enriched/markdown/input/editing/LinkCoordinator.kt +69 -0
  35. package/android/src/main/java/com/swmansion/enriched/markdown/input/editing/MarkdownTextWatcher.kt +3 -3
  36. package/android/src/main/java/com/swmansion/enriched/markdown/input/editing/MentionCoordinator.kt +118 -0
  37. package/android/src/main/java/com/swmansion/enriched/markdown/input/events/OnChangeStateEvent.kt +26 -0
  38. package/android/src/main/java/com/swmansion/enriched/markdown/input/events/OnContextMenuItemPressEvent.kt +26 -0
  39. package/android/src/main/java/com/swmansion/enriched/markdown/input/events/OnInputKeyPressEvent.kt +24 -0
  40. package/android/src/main/java/com/swmansion/enriched/markdown/input/events/OnPasteEvent.kt +24 -0
  41. package/android/src/main/java/com/swmansion/enriched/markdown/input/formatting/BlockStore.kt +254 -0
  42. package/android/src/main/java/com/swmansion/enriched/markdown/input/formatting/FormattingStore.kt +80 -87
  43. package/android/src/main/java/com/swmansion/enriched/markdown/input/formatting/InputFormatter.kt +109 -1
  44. package/android/src/main/java/com/swmansion/enriched/markdown/input/formatting/InputParser.kt +116 -22
  45. package/android/src/main/java/com/swmansion/enriched/markdown/input/formatting/MarkdownSerializer.kt +167 -38
  46. package/android/src/main/java/com/swmansion/enriched/markdown/input/formatting/RangeEditAdjustment.kt +149 -0
  47. package/android/src/main/java/com/swmansion/enriched/markdown/input/layout/InputEventEmitter.kt +66 -5
  48. package/android/src/main/java/com/swmansion/enriched/markdown/input/layout/InputMeasurementStore.kt +4 -2
  49. package/android/src/main/java/com/swmansion/enriched/markdown/input/model/BlockRange.kt +27 -0
  50. package/android/src/main/java/com/swmansion/enriched/markdown/input/model/BlockType.kt +48 -0
  51. package/android/src/main/java/com/swmansion/enriched/markdown/input/model/FormattingRange.kt +9 -4
  52. package/android/src/main/java/com/swmansion/enriched/markdown/input/model/InputFormatterStyle.kt +39 -2
  53. package/android/src/main/java/com/swmansion/enriched/markdown/input/model/MathAtom.kt +20 -0
  54. package/android/src/main/java/com/swmansion/enriched/markdown/input/model/MathChipStyle.kt +1 -1
  55. package/android/src/main/java/com/swmansion/enriched/markdown/input/model/MutableRangeBounds.kt +11 -0
  56. package/android/src/main/java/com/swmansion/enriched/markdown/input/spans/InputBulletSpan.kt +82 -0
  57. package/android/src/main/java/com/swmansion/enriched/markdown/input/spans/InputHeadingSpan.kt +58 -0
  58. package/android/src/main/java/com/swmansion/enriched/markdown/input/spans/InputListItemSpacingSpan.kt +37 -0
  59. package/android/src/main/java/com/swmansion/enriched/markdown/input/spans/InputOrderedListMarkerSpan.kt +63 -0
  60. package/android/src/main/java/com/swmansion/enriched/markdown/input/styles/BlockHandler.kt +54 -0
  61. package/android/src/main/java/com/swmansion/enriched/markdown/input/styles/HeadingBlockHandler.kt +27 -0
  62. package/android/src/main/java/com/swmansion/enriched/markdown/input/styles/OrderedListBlockHandler.kt +38 -0
  63. package/android/src/main/java/com/swmansion/enriched/markdown/input/styles/UnorderedListBlockHandler.kt +37 -0
  64. package/android/src/main/java/com/swmansion/enriched/markdown/input/toolbar/InputContextMenu.kt +8 -26
  65. package/android/src/main/java/com/swmansion/enriched/markdown/parser/MarkdownASTNode.kt +1 -0
  66. package/android/src/main/java/com/swmansion/enriched/markdown/parser/Parser.kt +1 -0
  67. package/android/src/main/java/com/swmansion/enriched/markdown/renderer/BlockStyleContext.kt +9 -2
  68. package/android/src/main/java/com/swmansion/enriched/markdown/renderer/BlockquoteRenderer.kt +100 -12
  69. package/android/src/main/java/com/swmansion/enriched/markdown/renderer/CodeBlockRenderer.kt +16 -1
  70. package/android/src/main/java/com/swmansion/enriched/markdown/renderer/HeadingRenderer.kt +4 -0
  71. package/android/src/main/java/com/swmansion/enriched/markdown/renderer/ListContextManager.kt +2 -1
  72. package/android/src/main/java/com/swmansion/enriched/markdown/renderer/ListItemRenderer.kt +74 -18
  73. package/android/src/main/java/com/swmansion/enriched/markdown/renderer/ListRenderer.kt +43 -4
  74. package/android/src/main/java/com/swmansion/enriched/markdown/renderer/NodeRenderer.kt +9 -1
  75. package/android/src/main/java/com/swmansion/enriched/markdown/renderer/SoftBreakRenderer.kt +16 -0
  76. package/android/src/main/java/com/swmansion/enriched/markdown/renderer/SpanStyleCache.kt +30 -27
  77. package/android/src/main/java/com/swmansion/enriched/markdown/spans/BaseListSpan.kt +24 -0
  78. package/android/src/main/java/com/swmansion/enriched/markdown/spans/BlockquoteSpan.kt +174 -24
  79. package/android/src/main/java/com/swmansion/enriched/markdown/spans/CodeBackgroundSpan.kt +27 -3
  80. package/android/src/main/java/com/swmansion/enriched/markdown/spans/CodeBlockSpan.kt +13 -16
  81. package/android/src/main/java/com/swmansion/enriched/markdown/spans/CodeSpan.kt +1 -1
  82. package/android/src/main/java/com/swmansion/enriched/markdown/spans/EmphasisSpan.kt +1 -1
  83. package/android/src/main/java/com/swmansion/enriched/markdown/spans/ImageSpan.kt +182 -46
  84. package/android/src/main/java/com/swmansion/enriched/markdown/spans/ListItemSpacingSpan.kt +33 -0
  85. package/android/src/main/java/com/swmansion/enriched/markdown/spans/ListMarkerAnchorSpan.kt +38 -0
  86. package/android/src/main/java/com/swmansion/enriched/markdown/spans/OrderedListSpan.kt +2 -0
  87. package/android/src/main/java/com/swmansion/enriched/markdown/spans/StrongSpan.kt +1 -1
  88. package/android/src/main/java/com/swmansion/enriched/markdown/spans/TaskListSpan.kt +3 -2
  89. package/android/src/main/java/com/swmansion/enriched/markdown/spans/UnorderedListSpan.kt +3 -2
  90. package/android/src/main/java/com/swmansion/enriched/markdown/styles/BlockquoteStyle.kt +6 -0
  91. package/android/src/main/java/com/swmansion/enriched/markdown/styles/CodeBlockStyle.kt +26 -0
  92. package/android/src/main/java/com/swmansion/enriched/markdown/styles/ImageStyle.kt +7 -1
  93. package/android/src/main/java/com/swmansion/enriched/markdown/styles/ListStyle.kt +4 -1
  94. package/android/src/main/java/com/swmansion/enriched/markdown/styles/StyleConfig.kt +13 -4
  95. package/android/src/main/java/com/swmansion/enriched/markdown/styles/TableStyle.kt +6 -0
  96. package/android/src/main/java/com/swmansion/enriched/markdown/utils/common/CodeBlockHighlighter.kt +90 -0
  97. package/android/src/main/java/com/swmansion/enriched/markdown/utils/common/CodeBlockNode.kt +57 -0
  98. package/android/src/main/java/com/swmansion/enriched/markdown/utils/common/FeatureFlags.kt +1 -0
  99. package/android/src/main/java/com/swmansion/enriched/markdown/utils/common/MarkdownSegment.kt +9 -0
  100. package/android/src/main/java/com/swmansion/enriched/markdown/utils/common/MarkdownViewManagerUtils.kt +37 -7
  101. package/android/src/main/java/com/swmansion/enriched/markdown/utils/common/ReadableMapExtensions.kt +3 -0
  102. package/android/src/main/java/com/swmansion/enriched/markdown/utils/common/RenderedSegment.kt +10 -0
  103. package/android/src/main/java/com/swmansion/enriched/markdown/utils/common/SegmentSignature.kt +1 -0
  104. package/android/src/main/java/com/swmansion/enriched/markdown/utils/common/StreamingMarkdownFilter.kt +83 -5
  105. package/android/src/main/java/com/swmansion/enriched/markdown/utils/common/serialization/MarkdownASTSerializer.kt +4 -0
  106. package/android/src/main/java/com/swmansion/enriched/markdown/utils/input/MarkdownStyleParser.kt +74 -44
  107. package/android/src/main/java/com/swmansion/enriched/markdown/utils/input/PasteTextUtils.kt +20 -0
  108. package/android/src/main/java/com/swmansion/enriched/markdown/utils/text/ImageCache.kt +26 -3
  109. package/android/src/main/java/com/swmansion/enriched/markdown/utils/text/ImageDownloader.kt +22 -9
  110. package/android/src/main/java/com/swmansion/enriched/markdown/utils/text/LocalImageLoader.kt +161 -0
  111. package/android/src/main/java/com/swmansion/enriched/markdown/utils/text/extensions/TextPaintExtensions.kt +23 -0
  112. package/android/src/main/java/com/swmansion/enriched/markdown/utils/text/interaction/CheckboxTouchHelper.kt +7 -0
  113. package/android/src/main/java/com/swmansion/enriched/markdown/utils/text/interaction/TaskListTapUtils.kt +41 -21
  114. package/android/src/main/java/com/swmansion/enriched/markdown/utils/text/span/BlockSpacing.kt +15 -8
  115. package/android/src/main/java/com/swmansion/enriched/markdown/utils/text/view/LinkLongPressMovementMethod.kt +58 -27
  116. package/android/src/main/java/com/swmansion/enriched/markdown/utils/text/view/SelectionActionMode.kt +49 -15
  117. package/android/src/main/java/com/swmansion/enriched/markdown/views/BlockMenuOptions.kt +45 -0
  118. package/android/src/main/java/com/swmansion/enriched/markdown/views/CodeBlockContainerView.kt +396 -0
  119. package/android/src/main/java/com/swmansion/enriched/markdown/views/ContextMenuPopup.kt +9 -6
  120. package/android/src/main/java/com/swmansion/enriched/markdown/views/CopyGlyph.kt +101 -0
  121. package/android/src/main/java/com/swmansion/enriched/markdown/views/TableContainerView.kt +36 -9
  122. package/android/src/main/jni/CMakeLists.txt +53 -0
  123. package/android/src/main/jni/react/renderer/components/EnrichedMarkdownTextSpec/MarkdownContainerShadowNode.cpp +10 -0
  124. package/android/src/main/jni/react/renderer/components/EnrichedMarkdownTextSpec/MarkdownContainerShadowNode.h +11 -2
  125. package/android/src/main/jni/react/renderer/components/EnrichedMarkdownTextSpec/MarkdownTextShadowNode.cpp +10 -0
  126. package/android/src/main/jni/react/renderer/components/EnrichedMarkdownTextSpec/MarkdownTextShadowNode.h +12 -2
  127. package/android/src/main/jni/react/renderer/components/EnrichedMarkdownTextSpec/MarkdownTextState.cpp +9 -0
  128. package/android/src/main/jni/react/renderer/components/EnrichedMarkdownTextSpec/MarkdownTextState.h +24 -0
  129. package/android/src/main/jni/react/renderer/components/EnrichedMarkdownTextSpec/conversions.h +16 -0
  130. package/android/src/math/java/com/swmansion/enriched/markdown/input/math/MathChipControllerImpl.kt +21 -4
  131. package/android/src/math/java/com/swmansion/enriched/markdown/renderer/MathInlineRenderer.kt +7 -2
  132. package/android/src/math/java/com/swmansion/enriched/markdown/spans/MathChipSpan.kt +1 -1
  133. package/android/src/math/java/com/swmansion/enriched/markdown/views/MathContainerView.kt +6 -4
  134. package/cpp/highlight/CodeBlockHighlighter.cpp +284 -0
  135. package/cpp/highlight/CodeBlockHighlighter.hpp +66 -0
  136. package/cpp/highlight/CodeBlockLanguages.cpp +138 -0
  137. package/cpp/highlight/CodeBlockLanguages.hpp +25 -0
  138. package/cpp/highlight/HighlightGrammars.hpp +28 -0
  139. package/cpp/highlight/code_highlight_podspec.rb +211 -0
  140. package/cpp/highlight/gen-registry.mjs +155 -0
  141. package/cpp/highlight/grammar-versions.json +159 -0
  142. package/cpp/highlight/vendor/generated/generated_queries.h +1665 -0
  143. package/cpp/highlight/vendor/generated/generated_registry.cpp +59 -0
  144. package/cpp/parser/MD4CParser.cpp +173 -61
  145. package/cpp/parser/MD4CParser.hpp +1 -0
  146. package/cpp/parser/MarkdownASTNode.hpp +2 -1
  147. package/cpp/wasm/ASTSerializer.cpp +2 -0
  148. package/cpp/wasm/build.sh +1 -0
  149. package/cpp/wasm/md4c_wasm.cpp +3 -1
  150. package/docs/ACCESSIBILITY.md +14 -2
  151. package/docs/API_REFERENCE.md +234 -12
  152. package/docs/BREAKING_CHANGES.md +129 -0
  153. package/docs/CODE_HIGHLIGHT.md +133 -0
  154. package/docs/COPY_OPTIONS.md +47 -3
  155. package/docs/ELEMENTS_STRUCTURE.md +52 -4
  156. package/docs/IMAGE_CACHING.md +30 -0
  157. package/docs/INPUT.md +108 -11
  158. package/docs/LATEX_MATH.md +87 -45
  159. package/docs/MACOS.md +1 -1
  160. package/docs/MARKDOWN_STREAMING.md +27 -1
  161. package/docs/NATIVE_ASSETS.md +127 -0
  162. package/docs/RTL.md +1 -1
  163. package/docs/STYLES.md +46 -6
  164. package/docs/TESTING.md +112 -0
  165. package/docs/TEXT.md +16 -6
  166. package/docs/WEB.md +3 -1
  167. package/ios/EnrichedMarkdown.h +7 -0
  168. package/ios/EnrichedMarkdown.mm +284 -75
  169. package/ios/EnrichedMarkdownText.h +7 -0
  170. package/ios/EnrichedMarkdownText.mm +101 -73
  171. package/ios/attachments/ENRMImageAttachment.h +9 -0
  172. package/ios/attachments/ENRMImageAttachment.m +143 -40
  173. package/ios/attachments/ENRMMathInlineAttachment.h +2 -0
  174. package/ios/attachments/ENRMMathInlineAttachment.m +48 -81
  175. package/ios/attachments/ENRMMathInlineAttachmentShared.h +2 -0
  176. package/ios/generated/ReactCodegen/EnrichedMarkdownTextSpec/EventEmitters.cpp +75 -0
  177. package/ios/generated/ReactCodegen/EnrichedMarkdownTextSpec/EventEmitters.h +63 -0
  178. package/ios/generated/ReactCodegen/EnrichedMarkdownTextSpec/Props.cpp +35 -0
  179. package/ios/generated/ReactCodegen/EnrichedMarkdownTextSpec/Props.h +886 -23
  180. package/ios/generated/ReactCodegen/EnrichedMarkdownTextSpec/RCTComponentViewHelpers.h +131 -0
  181. package/ios/input/ENRMAutoLinkDetector.h +2 -1
  182. package/ios/input/ENRMAutoLinkDetector.mm +79 -41
  183. package/ios/input/ENRMBlockEditCoordinator.h +71 -0
  184. package/ios/input/ENRMBlockEditCoordinator.mm +195 -0
  185. package/ios/input/ENRMBlockRange.h +28 -0
  186. package/ios/input/ENRMBlockRange.mm +30 -0
  187. package/ios/input/ENRMBlockStore.h +56 -0
  188. package/ios/input/ENRMBlockStore.mm +275 -0
  189. package/ios/input/ENRMClipboardCoordinator.h +45 -0
  190. package/ios/input/ENRMClipboardCoordinator.mm +120 -0
  191. package/ios/input/ENRMDetectorPipeline.h +2 -1
  192. package/ios/input/ENRMEditPipeline.h +76 -0
  193. package/ios/input/ENRMEditPipeline.mm +228 -0
  194. package/ios/input/ENRMEditSession.h +36 -0
  195. package/ios/input/ENRMEditSession.mm +63 -0
  196. package/ios/input/ENRMFormattingStore.h +17 -0
  197. package/ios/input/ENRMFormattingStore.mm +95 -105
  198. package/ios/input/ENRMInputBlockType.h +91 -0
  199. package/ios/input/ENRMInputBlockType.mm +5 -0
  200. package/ios/input/ENRMInputDecorationDrawer.h +18 -0
  201. package/ios/input/ENRMInputEventEmitter.h +56 -0
  202. package/ios/input/ENRMInputEventEmitter.mm +308 -0
  203. package/ios/input/ENRMInputFormatter.h +29 -69
  204. package/ios/input/ENRMInputFormatter.mm +216 -124
  205. package/ios/input/ENRMInputFormatterStyle.h +99 -0
  206. package/ios/input/ENRMInputFormatterStyle.mm +188 -0
  207. package/ios/input/ENRMInputLayoutManager.h +9 -0
  208. package/ios/input/ENRMInputLayoutManager.mm +30 -0
  209. package/ios/input/ENRMInputListMarkerDrawer.h +32 -0
  210. package/ios/input/ENRMInputListMarkerDrawer.mm +426 -0
  211. package/ios/input/ENRMInputParser.h +5 -6
  212. package/ios/input/ENRMInputParser.mm +461 -178
  213. package/ios/input/ENRMInputRemend.mm +2 -2
  214. package/ios/input/ENRMInputStyleStateBuilder.h +40 -0
  215. package/ios/input/ENRMInputStyleStateBuilder.mm +60 -0
  216. package/ios/input/ENRMInputTextView.mm +103 -8
  217. package/ios/input/ENRMInputTypingAttributesController.h +42 -0
  218. package/ios/input/ENRMInputTypingAttributesController.mm +203 -0
  219. package/ios/input/ENRMLinkCoordinator.h +41 -0
  220. package/ios/input/ENRMLinkCoordinator.mm +89 -0
  221. package/ios/input/ENRMMarkdownSerializer.h +29 -5
  222. package/ios/input/ENRMMarkdownSerializer.mm +170 -48
  223. package/ios/input/ENRMMathAtom.h +26 -0
  224. package/ios/input/ENRMMathAtom.mm +12 -0
  225. package/ios/input/ENRMMentionCoordinator.h +45 -0
  226. package/ios/input/ENRMMentionCoordinator.mm +167 -0
  227. package/ios/input/ENRMRangeEditAdjustment.h +38 -0
  228. package/ios/input/ENRMRangeEditAdjustment.mm +91 -0
  229. package/ios/input/ENRMRangeStoreUtils.h +39 -0
  230. package/ios/input/EnrichedMarkdownTextInput+ContextMenu.mm +6 -6
  231. package/ios/input/EnrichedMarkdownTextInput+Internal.h +11 -3
  232. package/ios/input/EnrichedMarkdownTextInput.h +7 -1
  233. package/ios/input/EnrichedMarkdownTextInput.mm +1089 -1023
  234. package/ios/input/InputStylePropsUtils.h +109 -68
  235. package/ios/input/internals/EnrichedMarkdownTextInputShadowNode.mm +2 -1
  236. package/ios/input/styles/ENRMBlockHandler.h +46 -0
  237. package/ios/input/styles/ENRMHeadingBlockHandler.h +15 -0
  238. package/ios/input/styles/ENRMHeadingBlockHandler.mm +38 -0
  239. package/ios/input/styles/ENRMOrderedListBlockHandler.h +14 -0
  240. package/ios/input/styles/ENRMOrderedListBlockHandler.mm +48 -0
  241. package/ios/input/styles/ENRMUnorderedListBlockHandler.h +15 -0
  242. package/ios/input/styles/ENRMUnorderedListBlockHandler.mm +51 -0
  243. package/ios/internals/ENRMViewFreeMeasurement.h +331 -0
  244. package/ios/internals/EnrichedMarkdownShadowNode.h +1 -3
  245. package/ios/internals/EnrichedMarkdownShadowNode.mm +16 -20
  246. package/ios/internals/EnrichedMarkdownTextShadowNode.h +1 -3
  247. package/ios/internals/EnrichedMarkdownTextShadowNode.mm +15 -20
  248. package/ios/internals/MeasurementCache.h +33 -7
  249. package/ios/internals/ShadowMeasurementUtils.h +63 -58
  250. package/ios/math/ENRMMathChipController.h +74 -0
  251. package/ios/math/ENRMMathChipController.mm +476 -0
  252. package/ios/math/ENRMRaTeXBridge.swift +4 -1
  253. package/ios/parser/ENRMMarkdownParser.h +1 -8
  254. package/ios/parser/ENRMMarkdownParser.mm +2 -11
  255. package/ios/parser/MarkdownASTNode.h +2 -1
  256. package/ios/parser/MarkdownParserBridge.mm +4 -0
  257. package/ios/renderer/AttributedRenderer.m +20 -2
  258. package/ios/renderer/BaseRenderer.h +17 -2
  259. package/ios/renderer/BaseRenderer.m +30 -0
  260. package/ios/renderer/BlockquoteRenderer.h +1 -1
  261. package/ios/renderer/BlockquoteRenderer.m +144 -35
  262. package/ios/renderer/CodeBlockRenderer.h +1 -1
  263. package/ios/renderer/CodeBlockRenderer.m +27 -23
  264. package/ios/renderer/CodeRenderer.h +1 -1
  265. package/ios/renderer/CodeRenderer.m +3 -1
  266. package/ios/renderer/ENRMImageRenderer.h +1 -1
  267. package/ios/renderer/ENRMImageRenderer.m +5 -1
  268. package/ios/renderer/ENRMMathInlineRenderer.h +1 -1
  269. package/ios/renderer/ENRMMathInlineRenderer.m +5 -1
  270. package/ios/renderer/ENRMSpoilerRenderer.h +1 -1
  271. package/ios/renderer/ENRMSpoilerRenderer.m +3 -1
  272. package/ios/renderer/EmphasisRenderer.h +1 -1
  273. package/ios/renderer/EmphasisRenderer.m +3 -1
  274. package/ios/renderer/HeadingRenderer.h +1 -1
  275. package/ios/renderer/HeadingRenderer.m +13 -6
  276. package/ios/renderer/HighlightRenderer.h +1 -1
  277. package/ios/renderer/HighlightRenderer.m +3 -1
  278. package/ios/renderer/LinkRenderer.h +1 -1
  279. package/ios/renderer/LinkRenderer.m +3 -1
  280. package/ios/renderer/ListItemRenderer.h +13 -1
  281. package/ios/renderer/ListItemRenderer.m +102 -44
  282. package/ios/renderer/ListRenderer.h +2 -2
  283. package/ios/renderer/ListRenderer.m +63 -25
  284. package/ios/renderer/ParagraphRenderer.h +1 -1
  285. package/ios/renderer/ParagraphRenderer.m +16 -8
  286. package/ios/renderer/RenderContext.h +10 -0
  287. package/ios/renderer/RenderContext.m +44 -0
  288. package/ios/renderer/RendererFactory.m +14 -0
  289. package/ios/renderer/StrikethroughRenderer.h +1 -1
  290. package/ios/renderer/StrikethroughRenderer.m +3 -1
  291. package/ios/renderer/StrongRenderer.h +1 -1
  292. package/ios/renderer/StrongRenderer.m +3 -1
  293. package/ios/renderer/SubscriptRenderer.h +1 -1
  294. package/ios/renderer/SubscriptRenderer.m +3 -1
  295. package/ios/renderer/SuperscriptRenderer.h +1 -1
  296. package/ios/renderer/SuperscriptRenderer.m +3 -1
  297. package/ios/renderer/TextRenderer.h +2 -2
  298. package/ios/renderer/TextRenderer.m +3 -1
  299. package/ios/renderer/ThematicBreakRenderer.h +1 -1
  300. package/ios/renderer/ThematicBreakRenderer.m +3 -1
  301. package/ios/renderer/UnderlineRenderer.h +1 -1
  302. package/ios/renderer/UnderlineRenderer.m +3 -1
  303. package/ios/styles/StyleConfig.h +22 -0
  304. package/ios/styles/StyleConfig.mm +132 -0
  305. package/ios/utils/BlockquoteBorder.h +6 -0
  306. package/ios/utils/BlockquoteBorder.m +249 -52
  307. package/ios/utils/CodeBlockBackground.m +16 -2
  308. package/ios/utils/ENRMAtomicSize.h +65 -0
  309. package/ios/utils/ENRMBlockMenu.h +57 -0
  310. package/ios/utils/ENRMCodeBlockContent.h +37 -0
  311. package/ios/utils/ENRMCodeBlockContent.mm +79 -0
  312. package/ios/utils/ENRMCodeBlockHighlighter.h +37 -0
  313. package/ios/utils/ENRMCodeBlockHighlighter.mm +51 -0
  314. package/ios/utils/ENRMFeatureFlags.h +7 -0
  315. package/ios/utils/ENRMImageDownloader.h +11 -1
  316. package/ios/utils/ENRMImageDownloader.m +60 -16
  317. package/ios/utils/ENRMLocalImageLoader.h +31 -0
  318. package/ios/utils/ENRMLocalImageLoader.m +68 -0
  319. package/ios/utils/ENRMMathFallback.h +26 -0
  320. package/ios/utils/ENRMMathFallback.m +18 -0
  321. package/ios/utils/ENRMTextViewSetup.h +35 -17
  322. package/ios/utils/EditMenuUtils.h +22 -5
  323. package/ios/utils/EditMenuUtils.m +53 -9
  324. package/ios/utils/ImageRequestHeaderUtils.h +35 -0
  325. package/ios/utils/LastElementUtils.h +1 -0
  326. package/ios/utils/ListMarkerDrawer.m +29 -42
  327. package/ios/utils/MarkdownASTSerializer.m +4 -0
  328. package/ios/utils/ParagraphStyleUtils.h +5 -0
  329. package/ios/utils/ParagraphStyleUtils.m +77 -17
  330. package/ios/utils/RenderedMarkdownSegment.h +13 -1
  331. package/ios/utils/RenderedMarkdownSegment.m +20 -0
  332. package/ios/utils/SegmentRenderer.m +17 -4
  333. package/ios/utils/StreamingMarkdownFilter.h +11 -1
  334. package/ios/utils/StreamingMarkdownFilter.m +98 -2
  335. package/ios/utils/StylePropsUtils.h +63 -0
  336. package/ios/utils/TaskListTapUtils.m +24 -0
  337. package/ios/views/ENRMCodeBlockContainerView.h +53 -0
  338. package/ios/views/ENRMCodeBlockContainerView.m +559 -0
  339. package/ios/views/ENRMMathContainerView.h +16 -0
  340. package/ios/views/ENRMMathContainerView.m +74 -19
  341. package/ios/views/TableContainerView.h +22 -0
  342. package/ios/views/TableContainerView.m +261 -175
  343. package/jest.d.ts +1 -0
  344. package/jest.js +5 -0
  345. package/lib/module/EnrichedMarkdownNativeComponent.ts +73 -0
  346. package/lib/module/EnrichedMarkdownTextInput.js +84 -5
  347. package/lib/module/EnrichedMarkdownTextInput.js.map +1 -1
  348. package/lib/module/EnrichedMarkdownTextInputNativeComponent.ts +78 -5
  349. package/lib/module/EnrichedMarkdownTextNativeComponent.ts +74 -0
  350. package/lib/module/headingDefaults.js +34 -0
  351. package/lib/module/headingDefaults.js.map +1 -0
  352. package/lib/module/index.js.map +1 -1
  353. package/lib/module/jest/index.js +191 -0
  354. package/lib/module/jest/index.js.map +1 -0
  355. package/lib/module/native/EnrichedMarkdownText.js +37 -5
  356. package/lib/module/native/EnrichedMarkdownText.js.map +1 -1
  357. package/lib/module/normalizeMarkdownStyle.js +81 -19
  358. package/lib/module/normalizeMarkdownStyle.js.map +1 -1
  359. package/lib/module/normalizeMarkdownStyle.web.js +56 -18
  360. package/lib/module/normalizeMarkdownStyle.web.js.map +1 -1
  361. package/lib/module/normalizeMarkdownTextInputStyle.js +62 -15
  362. package/lib/module/normalizeMarkdownTextInputStyle.js.map +1 -1
  363. package/lib/module/normalizeMenuItem.js +1 -1
  364. package/lib/module/utils/textInputState.js +26 -0
  365. package/lib/module/utils/textInputState.js.map +1 -0
  366. package/lib/module/web/EnrichedMarkdownText.js +9 -5
  367. package/lib/module/web/EnrichedMarkdownText.js.map +1 -1
  368. package/lib/module/web/parseMarkdown.js +4 -3
  369. package/lib/module/web/parseMarkdown.js.map +1 -1
  370. package/lib/module/web/renderers/InlineRenderers.js +6 -0
  371. package/lib/module/web/renderers/InlineRenderers.js.map +1 -1
  372. package/lib/module/web/renderers/ListRenderers.js +7 -2
  373. package/lib/module/web/renderers/ListRenderers.js.map +1 -1
  374. package/lib/module/web/renderers/index.js +7 -4
  375. package/lib/module/web/renderers/index.js.map +1 -1
  376. package/lib/module/web/styles.js +83 -6
  377. package/lib/module/web/styles.js.map +1 -1
  378. package/lib/module/web/utils.js +1 -0
  379. package/lib/module/web/utils.js.map +1 -1
  380. package/lib/module/web/wasm/md4c.js +0 -0
  381. package/lib/module/web/wasm/md4c.js.map +1 -1
  382. package/lib/typescript/src/EnrichedMarkdownNativeComponent.d.ts +66 -0
  383. package/lib/typescript/src/EnrichedMarkdownNativeComponent.d.ts.map +1 -1
  384. package/lib/typescript/src/EnrichedMarkdownTextInput.d.ts +94 -9
  385. package/lib/typescript/src/EnrichedMarkdownTextInput.d.ts.map +1 -1
  386. package/lib/typescript/src/EnrichedMarkdownTextInputNativeComponent.d.ts +69 -5
  387. package/lib/typescript/src/EnrichedMarkdownTextInputNativeComponent.d.ts.map +1 -1
  388. package/lib/typescript/src/EnrichedMarkdownTextNativeComponent.d.ts +66 -0
  389. package/lib/typescript/src/EnrichedMarkdownTextNativeComponent.d.ts.map +1 -1
  390. package/lib/typescript/src/headingDefaults.d.ts +9 -0
  391. package/lib/typescript/src/headingDefaults.d.ts.map +1 -0
  392. package/lib/typescript/src/index.d.ts +2 -2
  393. package/lib/typescript/src/index.d.ts.map +1 -1
  394. package/lib/typescript/src/index.web.d.ts +1 -1
  395. package/lib/typescript/src/index.web.d.ts.map +1 -1
  396. package/lib/typescript/src/jest/index.d.ts +6 -0
  397. package/lib/typescript/src/jest/index.d.ts.map +1 -0
  398. package/lib/typescript/src/native/EnrichedMarkdownText.d.ts +3 -3
  399. package/lib/typescript/src/native/EnrichedMarkdownText.d.ts.map +1 -1
  400. package/lib/typescript/src/normalizeMarkdownStyle.d.ts.map +1 -1
  401. package/lib/typescript/src/normalizeMarkdownStyle.web.d.ts.map +1 -1
  402. package/lib/typescript/src/normalizeMarkdownTextInputStyle.d.ts +19 -5
  403. package/lib/typescript/src/normalizeMarkdownTextInputStyle.d.ts.map +1 -1
  404. package/lib/typescript/src/types/MarkdownStyle.d.ts +72 -0
  405. package/lib/typescript/src/types/MarkdownStyle.d.ts.map +1 -1
  406. package/lib/typescript/src/types/MarkdownStyleInternal.d.ts +27 -0
  407. package/lib/typescript/src/types/MarkdownStyleInternal.d.ts.map +1 -1
  408. package/lib/typescript/src/types/MarkdownTextProps.d.ts +104 -9
  409. package/lib/typescript/src/types/MarkdownTextProps.d.ts.map +1 -1
  410. package/lib/typescript/src/types/MarkdownTextProps.web.d.ts +19 -0
  411. package/lib/typescript/src/types/MarkdownTextProps.web.d.ts.map +1 -1
  412. package/lib/typescript/src/types/events.d.ts +19 -0
  413. package/lib/typescript/src/types/events.d.ts.map +1 -1
  414. package/lib/typescript/src/utils/textInputState.d.ts +24 -0
  415. package/lib/typescript/src/utils/textInputState.d.ts.map +1 -0
  416. package/lib/typescript/src/web/EnrichedMarkdownText.d.ts +1 -1
  417. package/lib/typescript/src/web/EnrichedMarkdownText.d.ts.map +1 -1
  418. package/lib/typescript/src/web/parseMarkdown.d.ts +1 -1
  419. package/lib/typescript/src/web/parseMarkdown.d.ts.map +1 -1
  420. package/lib/typescript/src/web/renderers/InlineRenderers.d.ts.map +1 -1
  421. package/lib/typescript/src/web/renderers/ListRenderers.d.ts.map +1 -1
  422. package/lib/typescript/src/web/renderers/index.d.ts +2 -1
  423. package/lib/typescript/src/web/renderers/index.d.ts.map +1 -1
  424. package/lib/typescript/src/web/styles.d.ts +2 -1
  425. package/lib/typescript/src/web/styles.d.ts.map +1 -1
  426. package/lib/typescript/src/web/types.d.ts +6 -2
  427. package/lib/typescript/src/web/types.d.ts.map +1 -1
  428. package/lib/typescript/src/web/utils.d.ts.map +1 -1
  429. package/package.json +36 -9
  430. package/postinstall.mjs +131 -0
  431. package/ratex-version.json +21 -0
  432. package/src/EnrichedMarkdownNativeComponent.ts +73 -0
  433. package/src/EnrichedMarkdownTextInput.tsx +159 -8
  434. package/src/EnrichedMarkdownTextInputNativeComponent.ts +78 -5
  435. package/src/EnrichedMarkdownTextNativeComponent.ts +74 -0
  436. package/src/headingDefaults.ts +21 -0
  437. package/src/index.tsx +9 -0
  438. package/src/index.web.tsx +1 -0
  439. package/src/jest/index.tsx +215 -0
  440. package/src/native/EnrichedMarkdownText.tsx +53 -2
  441. package/src/normalizeMarkdownStyle.ts +102 -16
  442. package/src/normalizeMarkdownStyle.web.ts +63 -15
  443. package/src/normalizeMarkdownTextInputStyle.ts +110 -35
  444. package/src/normalizeMenuItem.ts +1 -1
  445. package/src/types/MarkdownStyle.ts +74 -0
  446. package/src/types/MarkdownStyleInternal.ts +39 -0
  447. package/src/types/MarkdownTextProps.ts +101 -9
  448. package/src/types/MarkdownTextProps.web.ts +19 -0
  449. package/src/types/events.ts +21 -0
  450. package/src/utils/textInputState.ts +35 -0
  451. package/src/web/EnrichedMarkdownText.tsx +16 -2
  452. package/src/web/parseMarkdown.ts +6 -2
  453. package/src/web/renderers/InlineRenderers.tsx +5 -0
  454. package/src/web/renderers/ListRenderers.tsx +14 -2
  455. package/src/web/renderers/index.tsx +6 -2
  456. package/src/web/styles.ts +89 -5
  457. package/src/web/types.ts +6 -1
  458. package/src/web/utils.ts +1 -0
  459. package/src/web/wasm/md4c.js +0 -0
  460. package/vendor-grammars.mjs +511 -0
  461. package/vendor-ratex.mjs +173 -0
  462. package/app.plugin.js +0 -2
  463. package/plugin/build/withAndroidMath.js +0 -19
  464. package/plugin/build/withIosMath.js +0 -28
  465. package/plugin/build/withReactNativeEnrichedMarkdown.js +0 -11
  466. package/plugin/src/withAndroidMath.ts +0 -24
  467. package/plugin/src/withIosMath.ts +0 -35
  468. package/plugin/src/withReactNativeEnrichedMarkdown.ts +0 -17
  469. package/plugin/tsconfig.build.json +0 -16
@@ -12,6 +12,16 @@ void MarkdownContainerShadowNode::setMeasurementsManager(
12
12
  measurementsManager_ = measurementsManager;
13
13
  }
14
14
 
15
+ void MarkdownContainerShadowNode::dirtyLayoutIfNeeded() {
16
+ const auto state = this->getStateData();
17
+ const auto counter = state.getForceHeightRecalculationCounter();
18
+
19
+ if (forceHeightRecalculationCounter_ != counter) {
20
+ forceHeightRecalculationCounter_ = counter;
21
+ dirtyLayout();
22
+ }
23
+ }
24
+
15
25
  Size MarkdownContainerShadowNode::measureContent(const LayoutContext &layoutContext,
16
26
  const LayoutConstraints &layoutConstraints) const {
17
27
  return measurementsManager_->measure(getSurfaceId(), getTag(), getConcreteProps(), layoutConstraints);
@@ -1,6 +1,7 @@
1
1
  #pragma once
2
2
 
3
3
  #include "MarkdownContainerMeasurementManager.h"
4
+ #include "MarkdownTextState.h"
4
5
 
5
6
  #include <react/renderer/components/EnrichedMarkdownTextSpec/EventEmitters.h>
6
7
  #include <react/renderer/components/EnrichedMarkdownTextSpec/Props.h>
@@ -11,11 +12,16 @@ namespace facebook::react {
11
12
  JSI_EXPORT extern const char MarkdownContainerComponentName[];
12
13
 
13
14
  class MarkdownContainerShadowNode final
14
- : public ConcreteViewShadowNode<MarkdownContainerComponentName, EnrichedMarkdownProps,
15
- EnrichedMarkdownEventEmitter> {
15
+ : public ConcreteViewShadowNode<MarkdownContainerComponentName, EnrichedMarkdownProps, EnrichedMarkdownEventEmitter,
16
+ MarkdownTextState> {
16
17
  public:
17
18
  using ConcreteViewShadowNode::ConcreteViewShadowNode;
18
19
 
20
+ MarkdownContainerShadowNode(ShadowNode const &sourceShadowNode, ShadowNodeFragment const &fragment)
21
+ : ConcreteViewShadowNode(sourceShadowNode, fragment) {
22
+ dirtyLayoutIfNeeded();
23
+ }
24
+
19
25
  static ShadowNodeTraits BaseTraits() {
20
26
  auto traits = ConcreteViewShadowNode::BaseTraits();
21
27
  traits.set(ShadowNodeTraits::Trait::LeafYogaNode);
@@ -25,9 +31,12 @@ public:
25
31
 
26
32
  void setMeasurementsManager(const std::shared_ptr<MarkdownContainerMeasurementManager> &measurementsManager);
27
33
 
34
+ void dirtyLayoutIfNeeded();
35
+
28
36
  Size measureContent(const LayoutContext &layoutContext, const LayoutConstraints &layoutConstraints) const override;
29
37
 
30
38
  private:
39
+ int forceHeightRecalculationCounter_{0};
31
40
  std::shared_ptr<MarkdownContainerMeasurementManager> measurementsManager_;
32
41
  };
33
42
 
@@ -12,6 +12,16 @@ void MarkdownTextShadowNode::setMeasurementsManager(
12
12
  measurementsManager_ = measurementsManager;
13
13
  }
14
14
 
15
+ void MarkdownTextShadowNode::dirtyLayoutIfNeeded() {
16
+ const auto state = this->getStateData();
17
+ const auto counter = state.getForceHeightRecalculationCounter();
18
+
19
+ if (forceHeightRecalculationCounter_ != counter) {
20
+ forceHeightRecalculationCounter_ = counter;
21
+ dirtyLayout();
22
+ }
23
+ }
24
+
15
25
  Size MarkdownTextShadowNode::measureContent(const LayoutContext &layoutContext,
16
26
  const LayoutConstraints &layoutConstraints) const {
17
27
  return measurementsManager_->measure(getSurfaceId(), getTag(), getConcreteProps(), layoutConstraints);
@@ -1,6 +1,7 @@
1
1
  #pragma once
2
2
 
3
3
  #include "MarkdownTextMeasurementManager.h"
4
+ #include "MarkdownTextState.h"
4
5
 
5
6
  #include <react/renderer/components/EnrichedMarkdownTextSpec/EventEmitters.h>
6
7
  #include <react/renderer/components/EnrichedMarkdownTextSpec/Props.h>
@@ -13,11 +14,17 @@ JSI_EXPORT extern const char MarkdownTextComponentName[];
13
14
  /*
14
15
  * `ShadowNode` for <EnrichedMarkdownText> component.
15
16
  */
16
- class MarkdownTextShadowNode final : public ConcreteViewShadowNode<MarkdownTextComponentName, EnrichedMarkdownTextProps,
17
- EnrichedMarkdownTextEventEmitter> {
17
+ class MarkdownTextShadowNode final
18
+ : public ConcreteViewShadowNode<MarkdownTextComponentName, EnrichedMarkdownTextProps,
19
+ EnrichedMarkdownTextEventEmitter, MarkdownTextState> {
18
20
  public:
19
21
  using ConcreteViewShadowNode::ConcreteViewShadowNode;
20
22
 
23
+ MarkdownTextShadowNode(ShadowNode const &sourceShadowNode, ShadowNodeFragment const &fragment)
24
+ : ConcreteViewShadowNode(sourceShadowNode, fragment) {
25
+ dirtyLayoutIfNeeded();
26
+ }
27
+
21
28
  static ShadowNodeTraits BaseTraits() {
22
29
  auto traits = ConcreteViewShadowNode::BaseTraits();
23
30
  traits.set(ShadowNodeTraits::Trait::LeafYogaNode);
@@ -28,9 +35,12 @@ public:
28
35
  // Associates a shared `MarkdownTextMeasurementManager` with the node.
29
36
  void setMeasurementsManager(const std::shared_ptr<MarkdownTextMeasurementManager> &measurementsManager);
30
37
 
38
+ void dirtyLayoutIfNeeded();
39
+
31
40
  Size measureContent(const LayoutContext &layoutContext, const LayoutConstraints &layoutConstraints) const override;
32
41
 
33
42
  private:
43
+ int forceHeightRecalculationCounter_{0};
34
44
  std::shared_ptr<MarkdownTextMeasurementManager> measurementsManager_;
35
45
  };
36
46
 
@@ -0,0 +1,9 @@
1
+ #include "MarkdownTextState.h"
2
+
3
+ namespace facebook::react {
4
+
5
+ int MarkdownTextState::getForceHeightRecalculationCounter() const {
6
+ return forceHeightRecalculationCounter_;
7
+ }
8
+
9
+ } // namespace facebook::react
@@ -0,0 +1,24 @@
1
+ #pragma once
2
+
3
+ #include <folly/dynamic.h>
4
+
5
+ namespace facebook::react {
6
+
7
+ class MarkdownTextState {
8
+ public:
9
+ MarkdownTextState() : forceHeightRecalculationCounter_(0) {}
10
+
11
+ MarkdownTextState(MarkdownTextState const &previousState, folly::dynamic data)
12
+ : forceHeightRecalculationCounter_((int)data["forceHeightRecalculationCounter"].getInt()) {}
13
+
14
+ folly::dynamic getDynamic() const {
15
+ return {};
16
+ }
17
+
18
+ int getForceHeightRecalculationCounter() const;
19
+
20
+ private:
21
+ const int forceHeightRecalculationCounter_{};
22
+ };
23
+
24
+ } // namespace facebook::react
@@ -12,9 +12,17 @@ inline folly::dynamic toDynamic(const EnrichedMarkdownTextProps &props) {
12
12
  serializedProps["markdown"] = props.markdown;
13
13
  serializedProps["markdownStyle"] = toDynamic(props.markdownStyle);
14
14
  serializedProps["md4cFlags"] = toDynamic(props.md4cFlags);
15
+ serializedProps["allowFontScaling"] = props.allowFontScaling;
16
+ serializedProps["maxFontSizeMultiplier"] = props.maxFontSizeMultiplier;
15
17
  serializedProps["allowTrailingMargin"] = props.allowTrailingMargin;
16
18
  serializedProps["streamingAnimation"] = props.streamingAnimation;
17
19
 
20
+ folly::dynamic imageRequestHeaders = folly::dynamic::array();
21
+ for (const auto &header : props.imageRequestHeaders) {
22
+ imageRequestHeaders.push_back(toDynamic(header));
23
+ }
24
+ serializedProps["imageRequestHeaders"] = std::move(imageRequestHeaders);
25
+
18
26
  return serializedProps;
19
27
  }
20
28
 
@@ -23,9 +31,17 @@ inline folly::dynamic toDynamic(const EnrichedMarkdownProps &props) {
23
31
  serializedProps["markdown"] = props.markdown;
24
32
  serializedProps["markdownStyle"] = toDynamic(props.markdownStyle);
25
33
  serializedProps["md4cFlags"] = toDynamic(props.md4cFlags);
34
+ serializedProps["allowFontScaling"] = props.allowFontScaling;
35
+ serializedProps["maxFontSizeMultiplier"] = props.maxFontSizeMultiplier;
26
36
  serializedProps["allowTrailingMargin"] = props.allowTrailingMargin;
27
37
  serializedProps["streamingAnimation"] = props.streamingAnimation;
28
38
 
39
+ folly::dynamic imageRequestHeaders = folly::dynamic::array();
40
+ for (const auto &header : props.imageRequestHeaders) {
41
+ imageRequestHeaders.push_back(toDynamic(header));
42
+ }
43
+ serializedProps["imageRequestHeaders"] = std::move(imageRequestHeaders);
44
+
29
45
  return serializedProps;
30
46
  }
31
47
 
@@ -195,11 +195,28 @@ class MathChipControllerImpl(
195
195
  ) {
196
196
  if (!displayMode) return
197
197
  val blockStyle = style as? MathBlockStyle ?: return
198
- if (blockStyle.alignment == Layout.Alignment.ALIGN_NORMAL) return
198
+ if (blockStyle.textAlign == Layout.Alignment.ALIGN_NORMAL) return
199
+
200
+ // An AlignmentSpan is paragraph-scoped, and SpannableStringBuilder *throws* unless a
201
+ // SPAN_PARAGRAPH span starts at a paragraph boundary and ends just past one — its end
202
+ // check is `charAt(end - 1) == '\n' || end == length`. A bare (position, position + 1)
203
+ // span therefore crashes for every chip that is not the buffer's last character, so
204
+ // the span has to cover the chip's whole paragraph, trailing newline included.
205
+ var start = position
206
+ while (start > 0 && editable[start - 1] != '\n') start--
207
+ var end = position + 1
208
+ while (end < editable.length && editable[end - 1] != '\n') end++
209
+
210
+ // Align only a paragraph the chip owns. Display math can also arrive from the middle
211
+ // of a paragraph ("text $$x$$ more", upstream #537); aligning that whole paragraph
212
+ // because of one formula would move the surrounding prose too.
213
+ val glyphCount = (start until end).count { editable[it] != '\n' }
214
+ if (glyphCount != 1) return
215
+
199
216
  editable.setSpan(
200
- AlignmentSpan.Standard(blockStyle.alignment),
201
- position,
202
- position + 1,
217
+ AlignmentSpan.Standard(blockStyle.textAlign),
218
+ start,
219
+ end,
203
220
  Spanned.SPAN_PARAGRAPH,
204
221
  )
205
222
  }
@@ -43,7 +43,12 @@ class MathInlineRenderer(
43
43
  }
44
44
 
45
45
  private fun extractLatex(node: MarkdownASTNode): String {
46
- if (!node.content.isNullOrEmpty()) return node.content!!
47
- return node.children.mapNotNull { it.content }.joinToString("")
46
+ if (node.content.isNotEmpty()) return node.content
47
+ return node.children.joinToString("") { child ->
48
+ when (child.type) {
49
+ MarkdownASTNode.NodeType.SoftBreak, MarkdownASTNode.NodeType.LineBreak -> " "
50
+ else -> child.content
51
+ }
52
+ }
48
53
  }
49
54
  }
@@ -185,7 +185,7 @@ class MathChipSpan(
185
185
  if (blockStyle != null && totalWidth > intrinsicWidth) {
186
186
  val slack = totalWidth - formulaWidth - style.paddingHorizontal * 2f
187
187
  val offset =
188
- when (blockStyle.alignment) {
188
+ when (blockStyle.textAlign) {
189
189
  Layout.Alignment.ALIGN_CENTER -> slack / 2f
190
190
  Layout.Alignment.ALIGN_OPPOSITE -> slack
191
191
  else -> 0f
@@ -41,6 +41,8 @@ class MathContainerView(
41
41
  // Set reflectively by EnrichedMarkdown (math is an optional module).
42
42
  var copyLabel: String = ""
43
43
  var copyAsMarkdownLabel: String = ""
44
+ var contextMenuHidden: Boolean = false
45
+ var menuOptions: BlockMenuOptions = BlockMenuOptions()
44
46
 
45
47
  override val segmentMarginTop: Int get() = mathStyle.marginTop.toInt()
46
48
  override val segmentMarginBottom: Int get() = mathStyle.marginBottom.toInt()
@@ -117,14 +119,14 @@ class MathContainerView(
117
119
  }
118
120
 
119
121
  private fun showContextMenu(anchor: View) {
122
+ if (contextMenuHidden) return
120
123
  val clipboard = context.getSystemService(Context.CLIPBOARD_SERVICE) as ClipboardManager
121
124
  ContextMenuPopup.show(anchor, this) {
122
- item(ContextMenuPopup.Icon.COPY, copyLabel) {
125
+ blockCopyItems(menuOptions, copyLabel, copyAsMarkdownLabel, copyRaw = {
123
126
  clipboard.setPrimaryClip(ClipData.newPlainText("Math", cachedLatex))
124
- }
125
- item(ContextMenuPopup.Icon.DOCUMENT, copyAsMarkdownLabel) {
127
+ }, copyMarkdown = {
126
128
  clipboard.setPrimaryClip(ClipData.newPlainText("Math", "$$\n$cachedLatex\n$$"))
127
- }
129
+ })
128
130
  }
129
131
  }
130
132
 
@@ -0,0 +1,284 @@
1
+ #include "CodeBlockHighlighter.hpp"
2
+
3
+ // Stub compiled when the syntax highlighting module is disabled. The real
4
+ // implementation defines the same symbol under ENRICHED_MARKDOWN_CODE_HIGHLIGHT,
5
+ // so exactly one definition exists in any build configuration.
6
+
7
+ #if !defined(ENRICHED_MARKDOWN_CODE_HIGHLIGHT)
8
+
9
+ namespace Markdown {
10
+
11
+ std::vector<HighlightToken> highlightCode(const std::string & /*code*/, const std::string & /*language*/) {
12
+ return {};
13
+ }
14
+
15
+ } // namespace Markdown
16
+
17
+ #else
18
+
19
+ #include "CodeBlockLanguages.hpp"
20
+ #include "HighlightGrammars.hpp"
21
+
22
+ #include <tree_sitter/api.h>
23
+
24
+ #include <algorithm>
25
+ #include <cstring>
26
+ #include <memory>
27
+ #include <mutex>
28
+ #include <unordered_map>
29
+
30
+ namespace Markdown {
31
+
32
+ namespace {
33
+
34
+ // Bounds the synchronous main-thread parse against pathological inputs. Typical
35
+ // blocks parse in sub-millisecond to low-millisecond time; anything past these
36
+ // caps falls back to plain rendering instead of risking a frame hang.
37
+ constexpr size_t kMaxBytes = 50u * 1024u;
38
+ constexpr size_t kMaxLines = 2000u;
39
+
40
+ // tree-sitter highlight capture names, flattened to their leading dotted
41
+ // prefix. The longest matching prefix wins, so "variable.member" resolves to
42
+ // Property while a bare "variable" resolves to Variable. Names with no entry
43
+ // (for example "spell", "none") are skipped and leave their bytes uncolored.
44
+ struct CaptureMapping {
45
+ const char *prefix;
46
+ HighlightTokenType type;
47
+ };
48
+
49
+ constexpr CaptureMapping kCaptureMappings[] = {
50
+ {"keyword", HighlightTokenType::Keyword},
51
+ {"operator", HighlightTokenType::Operator},
52
+ {"punctuation", HighlightTokenType::Punctuation},
53
+ {"string", HighlightTokenType::String},
54
+ {"escape", HighlightTokenType::String},
55
+ {"character", HighlightTokenType::String},
56
+ {"number", HighlightTokenType::Number},
57
+ {"float", HighlightTokenType::Number},
58
+ {"boolean", HighlightTokenType::Constant},
59
+ {"constant", HighlightTokenType::Constant},
60
+ {"comment", HighlightTokenType::Comment},
61
+ {"function", HighlightTokenType::Function},
62
+ {"method", HighlightTokenType::Function},
63
+ {"constructor", HighlightTokenType::Type},
64
+ {"type", HighlightTokenType::Type},
65
+ {"module", HighlightTokenType::Type},
66
+ {"namespace", HighlightTokenType::Type},
67
+ {"variable", HighlightTokenType::Variable},
68
+ {"parameter", HighlightTokenType::Variable},
69
+ {"variable.member", HighlightTokenType::Property},
70
+ {"property", HighlightTokenType::Property},
71
+ {"field", HighlightTokenType::Property},
72
+ {"tag", HighlightTokenType::Tag},
73
+ {"attribute", HighlightTokenType::Attribute},
74
+ {"embedded", HighlightTokenType::Embedded},
75
+ {"injection", HighlightTokenType::Embedded},
76
+ };
77
+
78
+ // A capture name matches a prefix only on dotted boundaries so "type" never
79
+ // swallows "typename"-style names. Returns false when nothing maps.
80
+ bool mapCaptureName(const char *name, uint32_t length, HighlightTokenType &out) {
81
+ size_t best = 0;
82
+ bool found = false;
83
+ for (const CaptureMapping &m : kCaptureMappings) {
84
+ size_t plen = std::strlen(m.prefix);
85
+ if (plen > length || plen < best) {
86
+ continue;
87
+ }
88
+ if (std::strncmp(name, m.prefix, plen) != 0) {
89
+ continue;
90
+ }
91
+ if (plen != length && name[plen] != '.') {
92
+ continue;
93
+ }
94
+ best = plen;
95
+ out = m.type;
96
+ found = true;
97
+ }
98
+ return found;
99
+ }
100
+
101
+ // Compiled queries are immutable after creation and reused across calls. Access
102
+ // is serialized on the main thread today; the mutex is cheap insurance should
103
+ // highlighting ever move off-main. A cached nullptr marks a query that failed to
104
+ // compile so it is not retried.
105
+ TSQuery *queryForLanguage(const TSLanguage *language, const char *source) {
106
+ static std::mutex mutex;
107
+ static std::unordered_map<const TSLanguage *, TSQuery *> cache;
108
+
109
+ std::lock_guard<std::mutex> lock(mutex);
110
+ auto it = cache.find(language);
111
+ if (it != cache.end()) {
112
+ return it->second;
113
+ }
114
+
115
+ uint32_t errorOffset = 0;
116
+ TSQueryError errorType = TSQueryErrorNone;
117
+ TSQuery *query = ts_query_new(language, source, static_cast<uint32_t>(std::strlen(source)), &errorOffset, &errorType);
118
+ cache.emplace(language, query);
119
+ return query;
120
+ }
121
+
122
+ // Precomputes, for every byte offset that starts a code point, the number of
123
+ // UTF-16 code units preceding it. Token boundaries always land on code-point
124
+ // boundaries, so mapping a byte offset is a single lookup. Astral code points
125
+ // (4-byte UTF-8) contribute a surrogate pair (+2).
126
+ std::vector<uint32_t> buildUtf16PrefixMap(const std::string &code) {
127
+ const size_t n = code.size();
128
+ std::vector<uint32_t> prefix(n + 1, 0);
129
+ uint32_t units = 0;
130
+ size_t i = 0;
131
+ while (i < n) {
132
+ unsigned char c = static_cast<unsigned char>(code[i]);
133
+ size_t len;
134
+ uint32_t width;
135
+ if (c < 0x80) {
136
+ len = 1;
137
+ width = 1;
138
+ } else if ((c >> 5) == 0x6) {
139
+ len = 2;
140
+ width = 1;
141
+ } else if ((c >> 4) == 0xE) {
142
+ len = 3;
143
+ width = 1;
144
+ } else if ((c >> 3) == 0x1E) {
145
+ len = 4;
146
+ width = 2;
147
+ } else {
148
+ len = 1;
149
+ width = 1;
150
+ }
151
+ units += width;
152
+ for (size_t k = 1; k <= len && i + k <= n; ++k) {
153
+ prefix[i + k] = units;
154
+ }
155
+ i += len;
156
+ }
157
+ return prefix;
158
+ }
159
+
160
+ using ParserPtr = std::unique_ptr<TSParser, decltype(&ts_parser_delete)>;
161
+ using TreePtr = std::unique_ptr<TSTree, decltype(&ts_tree_delete)>;
162
+ using CursorPtr = std::unique_ptr<TSQueryCursor, decltype(&ts_query_cursor_delete)>;
163
+
164
+ } // namespace
165
+
166
+ // Resolves the language to a compiled grammar, parses the code, runs the
167
+ // grammar's highlight query, resolves overlapping captures (innermost span
168
+ // wins per byte), and returns coalesced foreground-only tokens with UTF-16
169
+ // offsets. Any failure along the way degrades to an empty vector (plain
170
+ // rendering).
171
+ std::vector<HighlightToken> highlightCode(const std::string &code, const std::string &language) {
172
+ try {
173
+ if (code.empty()) {
174
+ return {};
175
+ }
176
+
177
+ std::string grammarId = canonicalGrammarId(language);
178
+ if (grammarId.empty()) {
179
+ return {};
180
+ }
181
+ const GrammarEntry *grammar = findGrammar(grammarId.c_str());
182
+ if (grammar == nullptr) {
183
+ return {};
184
+ }
185
+
186
+ if (code.size() > kMaxBytes) {
187
+ return {};
188
+ }
189
+ size_t lines = 1;
190
+ for (char c : code) {
191
+ if (c == '\n' && ++lines > kMaxLines) {
192
+ return {};
193
+ }
194
+ }
195
+
196
+ ParserPtr parser(ts_parser_new(), ts_parser_delete);
197
+ if (!parser) {
198
+ return {};
199
+ }
200
+ const TSLanguage *tsLanguage = grammar->language();
201
+ if (tsLanguage == nullptr || !ts_parser_set_language(parser.get(), tsLanguage)) {
202
+ return {};
203
+ }
204
+
205
+ TSQuery *query = queryForLanguage(tsLanguage, grammar->highlightsQuery);
206
+ if (query == nullptr) {
207
+ return {};
208
+ }
209
+
210
+ TreePtr tree(ts_parser_parse_string(parser.get(), nullptr, code.c_str(), static_cast<uint32_t>(code.size())),
211
+ ts_tree_delete);
212
+ if (!tree) {
213
+ return {};
214
+ }
215
+
216
+ CursorPtr cursor(ts_query_cursor_new(), ts_query_cursor_delete);
217
+ if (!cursor) {
218
+ return {};
219
+ }
220
+ ts_query_cursor_exec(cursor.get(), query, ts_tree_root_node(tree.get()));
221
+
222
+ // Innermost-wins overlap resolution: paint each capture's byte range,
223
+ // widest span first, so tighter captures overwrite. A -1 byte is uncolored.
224
+ struct Capture {
225
+ uint32_t start;
226
+ uint32_t end;
227
+ HighlightTokenType type;
228
+ };
229
+ std::vector<Capture> captures;
230
+ TSQueryMatch match;
231
+ uint32_t captureIndex = 0;
232
+ while (ts_query_cursor_next_capture(cursor.get(), &match, &captureIndex)) {
233
+ const TSQueryCapture &capture = match.captures[captureIndex];
234
+ uint32_t nameLength = 0;
235
+ const char *name = ts_query_capture_name_for_id(query, capture.index, &nameLength);
236
+ HighlightTokenType type;
237
+ if (name == nullptr || !mapCaptureName(name, nameLength, type)) {
238
+ continue;
239
+ }
240
+ uint32_t start = ts_node_start_byte(capture.node);
241
+ uint32_t end = ts_node_end_byte(capture.node);
242
+ if (end > start && end <= code.size()) {
243
+ captures.push_back({start, end, type});
244
+ }
245
+ }
246
+ if (captures.empty()) {
247
+ return {};
248
+ }
249
+
250
+ std::stable_sort(captures.begin(), captures.end(),
251
+ [](const Capture &a, const Capture &b) { return (a.end - a.start) > (b.end - b.start); });
252
+
253
+ std::vector<int8_t> byteType(code.size(), -1);
254
+ for (const Capture &capture : captures) {
255
+ for (uint32_t b = capture.start; b < capture.end; ++b) {
256
+ byteType[b] = static_cast<int8_t>(capture.type);
257
+ }
258
+ }
259
+
260
+ std::vector<uint32_t> u16 = buildUtf16PrefixMap(code);
261
+ std::vector<HighlightToken> tokens;
262
+ size_t b = 0;
263
+ const size_t n = code.size();
264
+ while (b < n) {
265
+ if (byteType[b] < 0) {
266
+ ++b;
267
+ continue;
268
+ }
269
+ int8_t type = byteType[b];
270
+ size_t runStart = b;
271
+ while (b < n && byteType[b] == type) {
272
+ ++b;
273
+ }
274
+ tokens.push_back({u16[runStart], u16[b], static_cast<HighlightTokenType>(type)});
275
+ }
276
+ return tokens;
277
+ } catch (...) {
278
+ return {};
279
+ }
280
+ }
281
+
282
+ } // namespace Markdown
283
+
284
+ #endif
@@ -0,0 +1,66 @@
1
+ #pragma once
2
+
3
+ #include <cstdint>
4
+ #include <string>
5
+ #include <vector>
6
+
7
+ // Shared seam for optional syntax highlighting of fenced code blocks.
8
+ //
9
+ // The real implementation is compiled only when ENRICHED_MARKDOWN_CODE_HIGHLIGHT
10
+ // is defined by the build. Without the flag the stub in CodeBlockHighlighter.cpp
11
+ // returns no tokens and platform callers keep the plain uncolored rendering, so
12
+ // the absent module degrades to the default code block appearance. The same
13
+ // fallback applies at runtime when a language has no compiled grammar or
14
+ // highlighting fails.
15
+ //
16
+ // The seam returns semantic tokens instead of a platform text type on
17
+ // purpose. Platform adapters map token types to foreground colors and apply
18
+ // them to their attributed string. Since foreground color never affects text
19
+ // metrics, the block height measured from the plain string is guaranteed to
20
+ // match the drawn height regardless of what an implementation returns.
21
+ //
22
+ // Token offsets are UTF-16 code units into the code string, because both
23
+ // Android (Spannable) and iOS (NSAttributedString) address text in UTF-16.
24
+ // Implementations are responsible for converting tree-sitter byte offsets.
25
+ //
26
+ // Token types follow tree-sitter's standard highlight capture names,
27
+ // flattened to one level. Values are explicit because they cross the JNI
28
+ // boundary as plain integers.
29
+ //
30
+ // Both markdown flavors call this seam: the github flavor highlights the code
31
+ // string in its container view, and the commonmark renderers
32
+ // (CodeBlockRenderer.kt / CodeBlockRenderer.m) apply the tokens to their
33
+ // content range through the platform adapters.
34
+
35
+ namespace Markdown {
36
+
37
+ enum class HighlightTokenType : uint8_t {
38
+ Keyword = 0,
39
+ Operator = 1,
40
+ Punctuation = 2,
41
+ String = 3,
42
+ Number = 4,
43
+ Constant = 5,
44
+ Comment = 6,
45
+ Function = 7,
46
+ Type = 8,
47
+ Variable = 9,
48
+ Property = 10,
49
+ Tag = 11,
50
+ Attribute = 12,
51
+ Embedded = 13,
52
+ };
53
+
54
+ struct HighlightToken {
55
+ uint32_t start;
56
+ uint32_t end;
57
+ HighlightTokenType type;
58
+ };
59
+
60
+ // code is the UTF-8 code block content without the fence lines; language is
61
+ // the fence info string (for example "python"), empty when absent. Returns an
62
+ // empty vector whenever highlighting is unavailable (module compiled out,
63
+ // unknown language, parse failure).
64
+ std::vector<HighlightToken> highlightCode(const std::string& code, const std::string& language);
65
+
66
+ } // namespace Markdown