react-native-enriched-markdown-scaffold 0.7.4-scaffold.9 → 1.0.2-scaffold.10
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.
- package/README.md +54 -8
- package/ReactNativeEnrichedMarkdown.podspec +82 -73
- package/android/build.gradle +188 -1
- package/android/consumer-rules.pro +1 -1
- package/android/generated/java/com/facebook/react/viewmanagers/EnrichedMarkdownManagerDelegate.java +27 -0
- package/android/generated/java/com/facebook/react/viewmanagers/EnrichedMarkdownManagerInterface.java +7 -0
- package/android/generated/java/com/facebook/react/viewmanagers/EnrichedMarkdownTextInputManagerDelegate.java +24 -0
- package/android/generated/java/com/facebook/react/viewmanagers/EnrichedMarkdownTextInputManagerInterface.java +8 -0
- package/android/generated/java/com/facebook/react/viewmanagers/EnrichedMarkdownTextManagerDelegate.java +27 -0
- package/android/generated/java/com/facebook/react/viewmanagers/EnrichedMarkdownTextManagerInterface.java +7 -0
- package/android/generated/jni/react/renderer/components/EnrichedMarkdownTextSpec/EventEmitters.cpp +223 -0
- package/android/generated/jni/react/renderer/components/EnrichedMarkdownTextSpec/EventEmitters.h +183 -0
- package/android/generated/jni/react/renderer/components/EnrichedMarkdownTextSpec/Props.cpp +65 -0
- package/android/generated/jni/react/renderer/components/EnrichedMarkdownTextSpec/Props.h +1086 -61
- package/android/src/main/baseline-prof.txt +1 -1
- package/android/src/main/cpp/jni-adapter.cpp +74 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/EnrichedMarkdown.kt +351 -13
- package/android/src/main/java/com/swmansion/enriched/markdown/EnrichedMarkdownInternalText.kt +62 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/EnrichedMarkdownManager.kt +85 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/EnrichedMarkdownText.kt +160 -1
- package/android/src/main/java/com/swmansion/enriched/markdown/EnrichedMarkdownTextLayoutManager.kt +10 -1
- package/android/src/main/java/com/swmansion/enriched/markdown/EnrichedMarkdownTextManager.kt +76 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/MeasurementStore.kt +126 -10
- package/android/src/main/java/com/swmansion/enriched/markdown/events/CopyPressEvent.kt +24 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/events/CopyRequestEvent.kt +28 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/events/LinkLayoutEvent.kt +36 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/events/SelectionChangeEvent.kt +43 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/input/EnrichedMarkdownTextInputManager.kt +54 -4
- package/android/src/main/java/com/swmansion/enriched/markdown/input/EnrichedMarkdownTextInputView.kt +923 -462
- package/android/src/main/java/com/swmansion/enriched/markdown/input/MarkdownClipboard.kt +42 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/input/editing/BlockEditCoordinator.kt +196 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/input/editing/ClipboardCoordinator.kt +73 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/input/editing/EditContext.kt +19 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/input/editing/EditPipeline.kt +248 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/input/editing/EditSession.kt +52 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/input/editing/InputConnectionWrapper.kt +108 -7
- package/android/src/main/java/com/swmansion/enriched/markdown/input/editing/LinkCoordinator.kt +69 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/input/editing/MarkdownTextWatcher.kt +3 -3
- package/android/src/main/java/com/swmansion/enriched/markdown/input/editing/MentionCoordinator.kt +118 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/input/events/OnChangeStateEvent.kt +26 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/input/events/OnContextMenuItemPressEvent.kt +26 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/input/events/OnInputKeyPressEvent.kt +24 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/input/events/OnPasteEvent.kt +24 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/input/formatting/BlockStore.kt +254 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/input/formatting/FormattingStore.kt +80 -87
- package/android/src/main/java/com/swmansion/enriched/markdown/input/formatting/InputFormatter.kt +109 -1
- package/android/src/main/java/com/swmansion/enriched/markdown/input/formatting/InputParser.kt +116 -22
- package/android/src/main/java/com/swmansion/enriched/markdown/input/formatting/MarkdownSerializer.kt +167 -38
- package/android/src/main/java/com/swmansion/enriched/markdown/input/formatting/RangeEditAdjustment.kt +149 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/input/layout/InputEventEmitter.kt +66 -5
- package/android/src/main/java/com/swmansion/enriched/markdown/input/layout/InputMeasurementStore.kt +4 -2
- package/android/src/main/java/com/swmansion/enriched/markdown/input/model/BlockRange.kt +27 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/input/model/BlockType.kt +48 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/input/model/FormattingRange.kt +9 -4
- package/android/src/main/java/com/swmansion/enriched/markdown/input/model/InputFormatterStyle.kt +39 -2
- package/android/src/main/java/com/swmansion/enriched/markdown/input/model/MathAtom.kt +20 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/input/model/MathChipStyle.kt +1 -1
- package/android/src/main/java/com/swmansion/enriched/markdown/input/model/MutableRangeBounds.kt +11 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/input/spans/InputBulletSpan.kt +82 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/input/spans/InputHeadingSpan.kt +58 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/input/spans/InputListItemSpacingSpan.kt +37 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/input/spans/InputOrderedListMarkerSpan.kt +63 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/input/styles/BlockHandler.kt +54 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/input/styles/HeadingBlockHandler.kt +27 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/input/styles/OrderedListBlockHandler.kt +38 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/input/styles/UnorderedListBlockHandler.kt +37 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/input/toolbar/InputContextMenu.kt +8 -26
- package/android/src/main/java/com/swmansion/enriched/markdown/parser/MarkdownASTNode.kt +1 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/parser/Parser.kt +1 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/renderer/BlockStyleContext.kt +9 -2
- package/android/src/main/java/com/swmansion/enriched/markdown/renderer/BlockquoteRenderer.kt +100 -12
- package/android/src/main/java/com/swmansion/enriched/markdown/renderer/CodeBlockRenderer.kt +16 -1
- package/android/src/main/java/com/swmansion/enriched/markdown/renderer/HeadingRenderer.kt +4 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/renderer/LinkRenderer.kt +37 -7
- package/android/src/main/java/com/swmansion/enriched/markdown/renderer/ListContextManager.kt +2 -1
- package/android/src/main/java/com/swmansion/enriched/markdown/renderer/ListItemRenderer.kt +74 -18
- package/android/src/main/java/com/swmansion/enriched/markdown/renderer/ListRenderer.kt +43 -4
- package/android/src/main/java/com/swmansion/enriched/markdown/renderer/NodeRenderer.kt +9 -1
- package/android/src/main/java/com/swmansion/enriched/markdown/renderer/SoftBreakRenderer.kt +16 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/renderer/SpanStyleCache.kt +35 -28
- package/android/src/main/java/com/swmansion/enriched/markdown/spans/BaseListSpan.kt +24 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/spans/BlockquoteSpan.kt +174 -24
- package/android/src/main/java/com/swmansion/enriched/markdown/spans/CodeBackgroundSpan.kt +20 -82
- package/android/src/main/java/com/swmansion/enriched/markdown/spans/CodeBlockSpan.kt +13 -16
- package/android/src/main/java/com/swmansion/enriched/markdown/spans/CodeSpan.kt +1 -1
- package/android/src/main/java/com/swmansion/enriched/markdown/spans/EmphasisSpan.kt +1 -1
- package/android/src/main/java/com/swmansion/enriched/markdown/spans/ImageSpan.kt +182 -46
- package/android/src/main/java/com/swmansion/enriched/markdown/spans/InlineChipPainter.kt +140 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/spans/LinkChipSpans.kt +177 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/spans/LinkSpan.kt +1 -6
- package/android/src/main/java/com/swmansion/enriched/markdown/spans/ListItemSpacingSpan.kt +33 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/spans/ListMarkerAnchorSpan.kt +38 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/spans/OrderedListSpan.kt +2 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/spans/StrongSpan.kt +1 -1
- package/android/src/main/java/com/swmansion/enriched/markdown/spans/TaskListSpan.kt +3 -2
- package/android/src/main/java/com/swmansion/enriched/markdown/spans/UnorderedListSpan.kt +3 -2
- package/android/src/main/java/com/swmansion/enriched/markdown/styles/BlockquoteStyle.kt +6 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/styles/CodeBlockStyle.kt +26 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/styles/ImageStyle.kt +7 -1
- package/android/src/main/java/com/swmansion/enriched/markdown/styles/InlineMathStyle.kt +16 -1
- package/android/src/main/java/com/swmansion/enriched/markdown/styles/LinkStyle.kt +36 -1
- package/android/src/main/java/com/swmansion/enriched/markdown/styles/LinkVariantEntry.kt +7 -3
- package/android/src/main/java/com/swmansion/enriched/markdown/styles/ListStyle.kt +4 -1
- package/android/src/main/java/com/swmansion/enriched/markdown/styles/MathStyle.kt +3 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/styles/StyleConfig.kt +13 -4
- package/android/src/main/java/com/swmansion/enriched/markdown/styles/TableStyle.kt +6 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/utils/common/CodeBlockHighlighter.kt +90 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/utils/common/CodeBlockNode.kt +57 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/utils/common/FeatureFlags.kt +1 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/utils/common/MarkdownSegment.kt +9 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/utils/common/MarkdownViewManagerUtils.kt +84 -7
- package/android/src/main/java/com/swmansion/enriched/markdown/utils/common/ReadableMapExtensions.kt +3 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/utils/common/RenderedSegment.kt +10 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/utils/common/SegmentSignature.kt +1 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/utils/common/StreamingMarkdownFilter.kt +83 -5
- package/android/src/main/java/com/swmansion/enriched/markdown/utils/common/serialization/MarkdownASTSerializer.kt +4 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/utils/input/MarkdownStyleParser.kt +74 -44
- package/android/src/main/java/com/swmansion/enriched/markdown/utils/input/PasteTextUtils.kt +52 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/utils/text/ImageCache.kt +26 -3
- package/android/src/main/java/com/swmansion/enriched/markdown/utils/text/ImageDownloader.kt +22 -9
- package/android/src/main/java/com/swmansion/enriched/markdown/utils/text/LocalImageLoader.kt +161 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/utils/text/conversion/HTMLGenerator.kt +2 -1
- package/android/src/main/java/com/swmansion/enriched/markdown/utils/text/conversion/MarkdownExtractor.kt +6 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/utils/text/extensions/TextPaintExtensions.kt +23 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/utils/text/interaction/CheckboxTouchHelper.kt +7 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/utils/text/interaction/TaskListTapUtils.kt +41 -21
- package/android/src/main/java/com/swmansion/enriched/markdown/utils/text/span/BlockSpacing.kt +15 -8
- package/android/src/main/java/com/swmansion/enriched/markdown/utils/text/view/HeadlessActionMode.kt +88 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/utils/text/view/LinkLayoutCollector.kt +100 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/utils/text/view/LinkLongPressMovementMethod.kt +58 -27
- package/android/src/main/java/com/swmansion/enriched/markdown/utils/text/view/SelectionActionMode.kt +72 -16
- package/android/src/main/java/com/swmansion/enriched/markdown/utils/text/view/SelectionChangeReporter.kt +232 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/views/BlockMenuOptions.kt +64 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/views/CodeBlockContainerView.kt +414 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/views/ContextMenuPopup.kt +9 -6
- package/android/src/main/java/com/swmansion/enriched/markdown/views/CopyGlyph.kt +101 -0
- package/android/src/main/java/com/swmansion/enriched/markdown/views/TableContainerView.kt +61 -11
- package/android/src/main/jni/CMakeLists.txt +53 -0
- package/android/src/main/jni/react/renderer/components/EnrichedMarkdownTextSpec/MarkdownContainerShadowNode.cpp +10 -0
- package/android/src/main/jni/react/renderer/components/EnrichedMarkdownTextSpec/MarkdownContainerShadowNode.h +11 -2
- package/android/src/main/jni/react/renderer/components/EnrichedMarkdownTextSpec/MarkdownTextShadowNode.cpp +10 -0
- package/android/src/main/jni/react/renderer/components/EnrichedMarkdownTextSpec/MarkdownTextShadowNode.h +12 -2
- package/android/src/main/jni/react/renderer/components/EnrichedMarkdownTextSpec/MarkdownTextState.cpp +9 -0
- package/android/src/main/jni/react/renderer/components/EnrichedMarkdownTextSpec/MarkdownTextState.h +24 -0
- package/android/src/main/jni/react/renderer/components/EnrichedMarkdownTextSpec/conversions.h +16 -0
- package/android/src/math/java/com/swmansion/enriched/markdown/input/math/MathChipControllerImpl.kt +21 -4
- package/android/src/math/java/com/swmansion/enriched/markdown/renderer/MathInlineRenderer.kt +8 -2
- package/android/src/math/java/com/swmansion/enriched/markdown/spans/MathChipSpan.kt +1 -1
- package/android/src/math/java/com/swmansion/enriched/markdown/spans/MathInlineSpan.kt +13 -6
- package/android/src/math/java/com/swmansion/enriched/markdown/spans/MathMeasureHelper.kt +2 -1
- package/android/src/math/java/com/swmansion/enriched/markdown/views/MathContainerView.kt +26 -8
- package/cpp/highlight/CodeBlockHighlighter.cpp +284 -0
- package/cpp/highlight/CodeBlockHighlighter.hpp +66 -0
- package/cpp/highlight/CodeBlockLanguages.cpp +138 -0
- package/cpp/highlight/CodeBlockLanguages.hpp +25 -0
- package/cpp/highlight/HighlightGrammars.hpp +28 -0
- package/cpp/highlight/code_highlight_podspec.rb +211 -0
- package/cpp/highlight/gen-registry.mjs +155 -0
- package/cpp/highlight/grammar-versions.json +159 -0
- package/cpp/highlight/vendor/generated/generated_queries.h +1665 -0
- package/cpp/highlight/vendor/generated/generated_registry.cpp +59 -0
- package/cpp/parser/MD4CParser.cpp +173 -61
- package/cpp/parser/MD4CParser.hpp +1 -0
- package/cpp/parser/MarkdownASTNode.hpp +2 -1
- package/cpp/wasm/ASTSerializer.cpp +2 -0
- package/cpp/wasm/build.sh +1 -0
- package/cpp/wasm/md4c_wasm.cpp +3 -1
- package/docs/ACCESSIBILITY.md +14 -2
- package/docs/API_REFERENCE.md +405 -12
- package/docs/BREAKING_CHANGES.md +129 -0
- package/docs/CODE_HIGHLIGHT.md +133 -0
- package/docs/COPY_OPTIONS.md +61 -3
- package/docs/ELEMENTS_STRUCTURE.md +52 -4
- package/docs/IMAGE_CACHING.md +30 -0
- package/docs/INPUT.md +110 -11
- package/docs/LATEX_MATH.md +87 -45
- package/docs/MACOS.md +1 -1
- package/docs/MARKDOWN_STREAMING.md +27 -1
- package/docs/MENTIONS.md +8 -1
- package/docs/NATIVE_ASSETS.md +127 -0
- package/docs/RTL.md +1 -1
- package/docs/STYLES.md +73 -6
- package/docs/TESTING.md +112 -0
- package/docs/TEXT.md +18 -6
- package/docs/WEB.md +4 -1
- package/ios/EnrichedMarkdown.h +7 -0
- package/ios/EnrichedMarkdown.mm +583 -76
- package/ios/EnrichedMarkdownText.h +7 -0
- package/ios/EnrichedMarkdownText.mm +299 -73
- package/ios/attachments/ENRMImageAttachment.h +9 -0
- package/ios/attachments/ENRMImageAttachment.m +143 -40
- package/ios/attachments/ENRMMathInlineAttachment+macOS.m +2 -1
- package/ios/attachments/ENRMMathInlineAttachment.h +5 -0
- package/ios/attachments/ENRMMathInlineAttachment.m +50 -82
- package/ios/attachments/ENRMMathInlineAttachmentShared.h +2 -0
- package/ios/generated/ReactCodegen/EnrichedMarkdownTextSpec/EventEmitters.cpp +223 -0
- package/ios/generated/ReactCodegen/EnrichedMarkdownTextSpec/EventEmitters.h +183 -0
- package/ios/generated/ReactCodegen/EnrichedMarkdownTextSpec/Props.cpp +65 -0
- package/ios/generated/ReactCodegen/EnrichedMarkdownTextSpec/Props.h +1086 -61
- package/ios/generated/ReactCodegen/EnrichedMarkdownTextSpec/RCTComponentViewHelpers.h +181 -2
- package/ios/input/ENRMAutoLinkDetector.h +2 -1
- package/ios/input/ENRMAutoLinkDetector.mm +79 -41
- package/ios/input/ENRMBlockEditCoordinator.h +71 -0
- package/ios/input/ENRMBlockEditCoordinator.mm +195 -0
- package/ios/input/ENRMBlockRange.h +28 -0
- package/ios/input/ENRMBlockRange.mm +30 -0
- package/ios/input/ENRMBlockStore.h +56 -0
- package/ios/input/ENRMBlockStore.mm +275 -0
- package/ios/input/ENRMClipboardCoordinator.h +45 -0
- package/ios/input/ENRMClipboardCoordinator.mm +120 -0
- package/ios/input/ENRMDetectorPipeline.h +2 -1
- package/ios/input/ENRMEditPipeline.h +76 -0
- package/ios/input/ENRMEditPipeline.mm +228 -0
- package/ios/input/ENRMEditSession.h +36 -0
- package/ios/input/ENRMEditSession.mm +63 -0
- package/ios/input/ENRMFormattingStore.h +17 -0
- package/ios/input/ENRMFormattingStore.mm +95 -105
- package/ios/input/ENRMInputBlockType.h +91 -0
- package/ios/input/ENRMInputBlockType.mm +5 -0
- package/ios/input/ENRMInputDecorationDrawer.h +18 -0
- package/ios/input/ENRMInputEventEmitter.h +56 -0
- package/ios/input/ENRMInputEventEmitter.mm +308 -0
- package/ios/input/ENRMInputFormatter.h +29 -69
- package/ios/input/ENRMInputFormatter.mm +216 -124
- package/ios/input/ENRMInputFormatterStyle.h +99 -0
- package/ios/input/ENRMInputFormatterStyle.mm +188 -0
- package/ios/input/ENRMInputLayoutManager.h +9 -0
- package/ios/input/ENRMInputLayoutManager.mm +30 -0
- package/ios/input/ENRMInputListMarkerDrawer.h +32 -0
- package/ios/input/ENRMInputListMarkerDrawer.mm +426 -0
- package/ios/input/ENRMInputParser.h +5 -6
- package/ios/input/ENRMInputParser.mm +461 -178
- package/ios/input/ENRMInputRemend.mm +2 -2
- package/ios/input/ENRMInputStyleStateBuilder.h +40 -0
- package/ios/input/ENRMInputStyleStateBuilder.mm +60 -0
- package/ios/input/ENRMInputTextView.mm +103 -8
- package/ios/input/ENRMInputTypingAttributesController.h +42 -0
- package/ios/input/ENRMInputTypingAttributesController.mm +203 -0
- package/ios/input/ENRMLinkCoordinator.h +41 -0
- package/ios/input/ENRMLinkCoordinator.mm +89 -0
- package/ios/input/ENRMMarkdownSerializer.h +29 -5
- package/ios/input/ENRMMarkdownSerializer.mm +170 -48
- package/ios/input/ENRMMathAtom.h +26 -0
- package/ios/input/ENRMMathAtom.mm +12 -0
- package/ios/input/ENRMMentionCoordinator.h +45 -0
- package/ios/input/ENRMMentionCoordinator.mm +167 -0
- package/ios/input/ENRMRangeEditAdjustment.h +38 -0
- package/ios/input/ENRMRangeEditAdjustment.mm +91 -0
- package/ios/input/ENRMRangeStoreUtils.h +39 -0
- package/ios/input/EnrichedMarkdownTextInput+ContextMenu.mm +6 -6
- package/ios/input/EnrichedMarkdownTextInput+Internal.h +11 -3
- package/ios/input/EnrichedMarkdownTextInput.h +7 -1
- package/ios/input/EnrichedMarkdownTextInput.mm +1089 -1023
- package/ios/input/InputStylePropsUtils.h +109 -68
- package/ios/input/internals/EnrichedMarkdownTextInputShadowNode.mm +2 -1
- package/ios/input/styles/ENRMBlockHandler.h +46 -0
- package/ios/input/styles/ENRMHeadingBlockHandler.h +15 -0
- package/ios/input/styles/ENRMHeadingBlockHandler.mm +38 -0
- package/ios/input/styles/ENRMOrderedListBlockHandler.h +14 -0
- package/ios/input/styles/ENRMOrderedListBlockHandler.mm +48 -0
- package/ios/input/styles/ENRMUnorderedListBlockHandler.h +15 -0
- package/ios/input/styles/ENRMUnorderedListBlockHandler.mm +51 -0
- package/ios/internals/ENRMViewFreeMeasurement.h +331 -0
- package/ios/internals/EnrichedMarkdownShadowNode.h +1 -3
- package/ios/internals/EnrichedMarkdownShadowNode.mm +16 -20
- package/ios/internals/EnrichedMarkdownTextShadowNode.h +1 -3
- package/ios/internals/EnrichedMarkdownTextShadowNode.mm +15 -20
- package/ios/internals/MeasurementCache.h +41 -9
- package/ios/internals/ShadowMeasurementUtils.h +63 -58
- package/ios/math/ENRMMathChipController.h +74 -0
- package/ios/math/ENRMMathChipController.mm +476 -0
- package/ios/math/ENRMRaTeXBridge.swift +27 -6
- package/ios/parser/ENRMMarkdownParser.h +1 -8
- package/ios/parser/ENRMMarkdownParser.mm +2 -11
- package/ios/parser/MarkdownASTNode.h +2 -1
- package/ios/parser/MarkdownParserBridge.mm +4 -0
- package/ios/renderer/AttributedRenderer.m +20 -2
- package/ios/renderer/BaseRenderer.h +17 -2
- package/ios/renderer/BaseRenderer.m +30 -0
- package/ios/renderer/BlockquoteRenderer.h +1 -1
- package/ios/renderer/BlockquoteRenderer.m +144 -35
- package/ios/renderer/CodeBlockRenderer.h +1 -1
- package/ios/renderer/CodeBlockRenderer.m +27 -23
- package/ios/renderer/CodeRenderer.h +1 -1
- package/ios/renderer/CodeRenderer.m +3 -1
- package/ios/renderer/ENRMImageRenderer.h +1 -1
- package/ios/renderer/ENRMImageRenderer.m +5 -1
- package/ios/renderer/ENRMMathInlineRenderer.h +1 -1
- package/ios/renderer/ENRMMathInlineRenderer.m +6 -1
- package/ios/renderer/ENRMSpoilerRenderer.h +1 -1
- package/ios/renderer/ENRMSpoilerRenderer.m +3 -1
- package/ios/renderer/EmphasisRenderer.h +1 -1
- package/ios/renderer/EmphasisRenderer.m +3 -1
- package/ios/renderer/HeadingRenderer.h +1 -1
- package/ios/renderer/HeadingRenderer.m +13 -6
- package/ios/renderer/HighlightRenderer.h +1 -1
- package/ios/renderer/HighlightRenderer.m +3 -1
- package/ios/renderer/LinkRenderer.h +1 -1
- package/ios/renderer/LinkRenderer.m +50 -16
- package/ios/renderer/ListItemRenderer.h +13 -1
- package/ios/renderer/ListItemRenderer.m +102 -44
- package/ios/renderer/ListRenderer.h +2 -2
- package/ios/renderer/ListRenderer.m +63 -25
- package/ios/renderer/ParagraphRenderer.h +1 -1
- package/ios/renderer/ParagraphRenderer.m +16 -8
- package/ios/renderer/RenderContext.h +10 -0
- package/ios/renderer/RenderContext.m +44 -0
- package/ios/renderer/RendererFactory.m +14 -0
- package/ios/renderer/StrikethroughRenderer.h +1 -1
- package/ios/renderer/StrikethroughRenderer.m +3 -1
- package/ios/renderer/StrongRenderer.h +1 -1
- package/ios/renderer/StrongRenderer.m +3 -1
- package/ios/renderer/SubscriptRenderer.h +1 -1
- package/ios/renderer/SubscriptRenderer.m +3 -1
- package/ios/renderer/SuperscriptRenderer.h +1 -1
- package/ios/renderer/SuperscriptRenderer.m +3 -1
- package/ios/renderer/TextRenderer.h +2 -2
- package/ios/renderer/TextRenderer.m +3 -1
- package/ios/renderer/ThematicBreakRenderer.h +1 -1
- package/ios/renderer/ThematicBreakRenderer.m +3 -1
- package/ios/renderer/UnderlineRenderer.h +1 -1
- package/ios/renderer/UnderlineRenderer.m +3 -1
- package/ios/styles/StyleConfig.h +42 -0
- package/ios/styles/StyleConfig.mm +216 -0
- package/ios/utils/BlockquoteBorder.h +6 -0
- package/ios/utils/BlockquoteBorder.m +249 -52
- package/ios/utils/CodeBackground.m +3 -65
- package/ios/utils/CodeBlockBackground.m +16 -2
- package/ios/utils/ENRMAtomicSize.h +65 -0
- package/ios/utils/ENRMBlockMenu.h +66 -0
- package/ios/utils/ENRMChipDrawing.h +24 -0
- package/ios/utils/ENRMChipDrawing.m +83 -0
- package/ios/utils/ENRMCodeBlockContent.h +37 -0
- package/ios/utils/ENRMCodeBlockContent.mm +79 -0
- package/ios/utils/ENRMCodeBlockHighlighter.h +37 -0
- package/ios/utils/ENRMCodeBlockHighlighter.mm +51 -0
- package/ios/utils/ENRMFeatureFlags.h +7 -0
- package/ios/utils/ENRMImageDownloader.h +11 -1
- package/ios/utils/ENRMImageDownloader.m +60 -16
- package/ios/utils/ENRMLinkChip.h +70 -0
- package/ios/utils/ENRMLinkChip.m +213 -0
- package/ios/utils/ENRMLinkLayout.h +50 -0
- package/ios/utils/ENRMLinkLayout.m +45 -0
- package/ios/utils/ENRMLocalImageLoader.h +31 -0
- package/ios/utils/ENRMLocalImageLoader.m +68 -0
- package/ios/utils/ENRMMathFallback.h +26 -0
- package/ios/utils/ENRMMathFallback.m +18 -0
- package/ios/utils/ENRMSelectionChange.h +120 -0
- package/ios/utils/ENRMSelectionChange.m +282 -0
- package/ios/utils/ENRMTextViewSetup.h +35 -17
- package/ios/utils/EditMenuUtils+macOS.m +4 -1
- package/ios/utils/EditMenuUtils.h +35 -6
- package/ios/utils/EditMenuUtils.m +188 -11
- package/ios/utils/HTMLGenerator.m +2 -1
- package/ios/utils/ImageRequestHeaderUtils.h +35 -0
- package/ios/utils/LastElementUtils.h +1 -0
- package/ios/utils/ListMarkerDrawer.m +29 -42
- package/ios/utils/MarkdownASTSerializer.m +4 -0
- package/ios/utils/MarkdownAccessibilityElementBuilder.m +3 -1
- package/ios/utils/MarkdownExtractor.m +2 -1
- package/ios/utils/ParagraphStyleUtils.h +5 -0
- package/ios/utils/ParagraphStyleUtils.m +77 -17
- package/ios/utils/RTFExportUtils.m +2 -0
- package/ios/utils/RenderedMarkdownSegment.h +13 -1
- package/ios/utils/RenderedMarkdownSegment.m +20 -0
- package/ios/utils/SegmentRenderer.m +17 -4
- package/ios/utils/StreamingMarkdownFilter.h +11 -1
- package/ios/utils/StreamingMarkdownFilter.m +98 -2
- package/ios/utils/StylePropsUtils.h +110 -1
- package/ios/utils/TaskListTapUtils.m +24 -0
- package/ios/utils/TextViewLayoutManager.mm +3 -0
- package/ios/views/ENRMCodeBlockContainerView.h +60 -0
- package/ios/views/ENRMCodeBlockContainerView.m +569 -0
- package/ios/views/ENRMMathContainerView.h +23 -0
- package/ios/views/ENRMMathContainerView.m +87 -20
- package/ios/views/TableContainerView.h +32 -0
- package/ios/views/TableContainerView.m +291 -175
- package/jest.d.ts +1 -0
- package/jest.js +5 -0
- package/lib/module/EnrichedMarkdownNativeComponent.ts +203 -1
- package/lib/module/EnrichedMarkdownTextInput.js +84 -5
- package/lib/module/EnrichedMarkdownTextInput.js.map +1 -1
- package/lib/module/EnrichedMarkdownTextInputNativeComponent.ts +78 -5
- package/lib/module/EnrichedMarkdownTextNativeComponent.ts +204 -1
- package/lib/module/headingDefaults.js +34 -0
- package/lib/module/headingDefaults.js.map +1 -0
- package/lib/module/index.js.map +1 -1
- package/lib/module/jest/index.js +205 -0
- package/lib/module/jest/index.js.map +1 -0
- package/lib/module/native/EnrichedMarkdownText.js +199 -15
- package/lib/module/native/EnrichedMarkdownText.js.map +1 -1
- package/lib/module/normalizeMarkdownStyle.js +98 -23
- package/lib/module/normalizeMarkdownStyle.js.map +1 -1
- package/lib/module/normalizeMarkdownStyle.web.js +73 -22
- package/lib/module/normalizeMarkdownStyle.web.js.map +1 -1
- package/lib/module/normalizeMarkdownTextInputStyle.js +62 -15
- package/lib/module/normalizeMarkdownTextInputStyle.js.map +1 -1
- package/lib/module/normalizeMenuItem.js +1 -1
- package/lib/module/utils/textInputState.js +26 -0
- package/lib/module/utils/textInputState.js.map +1 -0
- package/lib/module/web/EnrichedMarkdownText.js +15 -8
- package/lib/module/web/EnrichedMarkdownText.js.map +1 -1
- package/lib/module/web/parseMarkdown.js +4 -3
- package/lib/module/web/parseMarkdown.js.map +1 -1
- package/lib/module/web/renderers/InlineRenderers.js +102 -3
- package/lib/module/web/renderers/InlineRenderers.js.map +1 -1
- package/lib/module/web/renderers/ListRenderers.js +7 -2
- package/lib/module/web/renderers/ListRenderers.js.map +1 -1
- package/lib/module/web/renderers/index.js +7 -4
- package/lib/module/web/renderers/index.js.map +1 -1
- package/lib/module/web/styles.js +101 -6
- package/lib/module/web/styles.js.map +1 -1
- package/lib/module/web/utils.js +14 -0
- package/lib/module/web/utils.js.map +1 -1
- package/lib/module/web/wasm/md4c.js +0 -0
- package/lib/module/web/wasm/md4c.js.map +1 -1
- package/lib/typescript/src/EnrichedMarkdownNativeComponent.d.ts +185 -2
- package/lib/typescript/src/EnrichedMarkdownNativeComponent.d.ts.map +1 -1
- package/lib/typescript/src/EnrichedMarkdownTextInput.d.ts +94 -9
- package/lib/typescript/src/EnrichedMarkdownTextInput.d.ts.map +1 -1
- package/lib/typescript/src/EnrichedMarkdownTextInputNativeComponent.d.ts +69 -5
- package/lib/typescript/src/EnrichedMarkdownTextInputNativeComponent.d.ts.map +1 -1
- package/lib/typescript/src/EnrichedMarkdownTextNativeComponent.d.ts +185 -2
- package/lib/typescript/src/EnrichedMarkdownTextNativeComponent.d.ts.map +1 -1
- package/lib/typescript/src/headingDefaults.d.ts +9 -0
- package/lib/typescript/src/headingDefaults.d.ts.map +1 -0
- package/lib/typescript/src/index.d.ts +3 -3
- package/lib/typescript/src/index.d.ts.map +1 -1
- package/lib/typescript/src/index.web.d.ts +2 -2
- package/lib/typescript/src/index.web.d.ts.map +1 -1
- package/lib/typescript/src/jest/index.d.ts +6 -0
- package/lib/typescript/src/jest/index.d.ts.map +1 -0
- package/lib/typescript/src/native/EnrichedMarkdownText.d.ts +5 -5
- package/lib/typescript/src/native/EnrichedMarkdownText.d.ts.map +1 -1
- package/lib/typescript/src/normalizeMarkdownStyle.d.ts.map +1 -1
- package/lib/typescript/src/normalizeMarkdownStyle.web.d.ts.map +1 -1
- package/lib/typescript/src/normalizeMarkdownTextInputStyle.d.ts +19 -5
- package/lib/typescript/src/normalizeMarkdownTextInputStyle.d.ts.map +1 -1
- package/lib/typescript/src/types/MarkdownStyle.d.ts +122 -5
- package/lib/typescript/src/types/MarkdownStyle.d.ts.map +1 -1
- package/lib/typescript/src/types/MarkdownStyleInternal.d.ts +39 -0
- package/lib/typescript/src/types/MarkdownStyleInternal.d.ts.map +1 -1
- package/lib/typescript/src/types/MarkdownTextProps.d.ts +207 -10
- package/lib/typescript/src/types/MarkdownTextProps.d.ts.map +1 -1
- package/lib/typescript/src/types/MarkdownTextProps.web.d.ts +60 -1
- package/lib/typescript/src/types/MarkdownTextProps.web.d.ts.map +1 -1
- package/lib/typescript/src/types/events.d.ts +85 -0
- package/lib/typescript/src/types/events.d.ts.map +1 -1
- package/lib/typescript/src/utils/textInputState.d.ts +24 -0
- package/lib/typescript/src/utils/textInputState.d.ts.map +1 -0
- package/lib/typescript/src/web/EnrichedMarkdownText.d.ts +1 -1
- package/lib/typescript/src/web/EnrichedMarkdownText.d.ts.map +1 -1
- package/lib/typescript/src/web/parseMarkdown.d.ts +1 -1
- package/lib/typescript/src/web/parseMarkdown.d.ts.map +1 -1
- package/lib/typescript/src/web/renderers/InlineRenderers.d.ts.map +1 -1
- package/lib/typescript/src/web/renderers/ListRenderers.d.ts.map +1 -1
- package/lib/typescript/src/web/renderers/index.d.ts +2 -1
- package/lib/typescript/src/web/renderers/index.d.ts.map +1 -1
- package/lib/typescript/src/web/styles.d.ts +2 -1
- package/lib/typescript/src/web/styles.d.ts.map +1 -1
- package/lib/typescript/src/web/types.d.ts +10 -2
- package/lib/typescript/src/web/types.d.ts.map +1 -1
- package/lib/typescript/src/web/utils.d.ts +4 -0
- package/lib/typescript/src/web/utils.d.ts.map +1 -1
- package/package.json +36 -9
- package/postinstall.mjs +131 -0
- package/ratex-version.json +21 -0
- package/src/EnrichedMarkdownNativeComponent.ts +203 -1
- package/src/EnrichedMarkdownTextInput.tsx +159 -8
- package/src/EnrichedMarkdownTextInputNativeComponent.ts +78 -5
- package/src/EnrichedMarkdownTextNativeComponent.ts +204 -1
- package/src/headingDefaults.ts +21 -0
- package/src/index.tsx +15 -0
- package/src/index.web.tsx +6 -1
- package/src/jest/index.tsx +236 -0
- package/src/native/EnrichedMarkdownText.tsx +260 -11
- package/src/normalizeMarkdownStyle.ts +117 -16
- package/src/normalizeMarkdownStyle.web.ts +76 -15
- package/src/normalizeMarkdownTextInputStyle.ts +110 -35
- package/src/normalizeMenuItem.ts +1 -1
- package/src/types/MarkdownStyle.ts +125 -5
- package/src/types/MarkdownStyleInternal.ts +51 -0
- package/src/types/MarkdownTextProps.ts +215 -10
- package/src/types/MarkdownTextProps.web.ts +62 -1
- package/src/types/events.ts +90 -0
- package/src/utils/textInputState.ts +35 -0
- package/src/web/EnrichedMarkdownText.tsx +26 -5
- package/src/web/parseMarkdown.ts +6 -2
- package/src/web/renderers/InlineRenderers.tsx +116 -3
- package/src/web/renderers/ListRenderers.tsx +14 -2
- package/src/web/renderers/index.tsx +6 -2
- package/src/web/styles.ts +114 -5
- package/src/web/types.ts +10 -1
- package/src/web/utils.ts +9 -0
- package/src/web/wasm/md4c.js +0 -0
- package/vendor-grammars.mjs +511 -0
- package/vendor-ratex.mjs +173 -0
- package/app.plugin.js +0 -2
- package/plugin/build/withAndroidMath.js +0 -19
- package/plugin/build/withIosMath.js +0 -28
- package/plugin/build/withReactNativeEnrichedMarkdown.js +0 -11
- package/plugin/src/withAndroidMath.ts +0 -24
- package/plugin/src/withIosMath.ts +0 -35
- package/plugin/src/withReactNativeEnrichedMarkdown.ts +0 -17
- package/plugin/tsconfig.build.json +0 -16
|
@@ -2,7 +2,9 @@ package com.swmansion.enriched.markdown.renderer
|
|
|
2
2
|
|
|
3
3
|
import android.text.SpannableStringBuilder
|
|
4
4
|
import com.swmansion.enriched.markdown.parser.MarkdownASTNode
|
|
5
|
+
import com.swmansion.enriched.markdown.spans.ListItemSpacingSpan
|
|
5
6
|
import com.swmansion.enriched.markdown.spans.MarginBottomSpan
|
|
7
|
+
import com.swmansion.enriched.markdown.styles.ListStyle
|
|
6
8
|
import com.swmansion.enriched.markdown.utils.text.span.SPAN_FLAGS_EXCLUSIVE_EXCLUSIVE
|
|
7
9
|
import com.swmansion.enriched.markdown.utils.text.span.applyLineHeightSkippingImages
|
|
8
10
|
import com.swmansion.enriched.markdown.utils.text.span.applyMarginTop
|
|
@@ -22,8 +24,15 @@ class ListRenderer(
|
|
|
22
24
|
val listStyle = config.style.listStyle
|
|
23
25
|
val listType = if (isOrdered) BlockStyleContext.ListType.ORDERED else BlockStyleContext.ListType.UNORDERED
|
|
24
26
|
|
|
27
|
+
val startNumber =
|
|
28
|
+
if (isOrdered) {
|
|
29
|
+
node.getAttribute("start")?.toIntOrNull()?.coerceAtLeast(0) ?: 1
|
|
30
|
+
} else {
|
|
31
|
+
1
|
|
32
|
+
}
|
|
33
|
+
|
|
25
34
|
val contextManager = ListContextManager(factory.blockStyleContext)
|
|
26
|
-
val entryState = contextManager.enterList(listType, listStyle)
|
|
35
|
+
val entryState = contextManager.enterList(listType, listStyle, startNumber)
|
|
27
36
|
|
|
28
37
|
// For top-level lists, insert marginTop spacer before rendering content
|
|
29
38
|
if (entryState.previousDepth == 0) {
|
|
@@ -45,7 +54,7 @@ class ListRenderer(
|
|
|
45
54
|
}
|
|
46
55
|
|
|
47
56
|
if (builder.length > contentStart) {
|
|
48
|
-
applyListSpacing(builder, contentStart, entryState.previousDepth, listStyle)
|
|
57
|
+
applyListSpacing(builder, contentStart, entryState.previousDepth, listStyle, factory.blockStyleContext)
|
|
49
58
|
}
|
|
50
59
|
}
|
|
51
60
|
|
|
@@ -53,15 +62,18 @@ class ListRenderer(
|
|
|
53
62
|
builder: SpannableStringBuilder,
|
|
54
63
|
start: Int,
|
|
55
64
|
depth: Int,
|
|
56
|
-
style:
|
|
65
|
+
style: ListStyle,
|
|
66
|
+
styleContext: BlockStyleContext,
|
|
57
67
|
) {
|
|
58
68
|
// TODO: LineHeightSpan may also clip superscript/subscript glyphs that extend
|
|
59
69
|
// outside the normal line bounds. A similar "skip" strategy as for images may
|
|
60
70
|
// be needed here once super/subscript usage in practice is better understood.
|
|
61
71
|
applyLineHeightSkippingImages(builder, start, builder.length, style.lineHeight)
|
|
62
72
|
|
|
63
|
-
//
|
|
73
|
+
// Item spacing and external bottom margin are only handled by the root-level list
|
|
64
74
|
if (depth == 0) {
|
|
75
|
+
applyItemSpacing(builder, start, style.itemSpacing, styleContext)
|
|
76
|
+
|
|
65
77
|
builder.append("\n")
|
|
66
78
|
builder.setSpan(
|
|
67
79
|
MarginBottomSpan(style.marginBottom),
|
|
@@ -71,4 +83,31 @@ class ListRenderer(
|
|
|
71
83
|
)
|
|
72
84
|
}
|
|
73
85
|
}
|
|
86
|
+
|
|
87
|
+
// Inserts the vertical gap between consecutive items (including nested ones)
|
|
88
|
+
// by spanning the newline that precedes each item start. The first item of
|
|
89
|
+
// the root list gets no spacing above it.
|
|
90
|
+
private fun applyItemSpacing(
|
|
91
|
+
builder: SpannableStringBuilder,
|
|
92
|
+
start: Int,
|
|
93
|
+
itemSpacing: Float,
|
|
94
|
+
styleContext: BlockStyleContext,
|
|
95
|
+
) {
|
|
96
|
+
if (itemSpacing <= 0f) return
|
|
97
|
+
|
|
98
|
+
val itemStarts =
|
|
99
|
+
styleContext.listItemStarts
|
|
100
|
+
.filter { it in start until builder.length }
|
|
101
|
+
.distinct()
|
|
102
|
+
.sorted()
|
|
103
|
+
|
|
104
|
+
for (itemStart in itemStarts.drop(1)) {
|
|
105
|
+
builder.setSpan(
|
|
106
|
+
ListItemSpacingSpan(itemSpacing),
|
|
107
|
+
itemStart - 1,
|
|
108
|
+
itemStart,
|
|
109
|
+
SPAN_FLAGS_EXCLUSIVE_EXCLUSIVE,
|
|
110
|
+
)
|
|
111
|
+
}
|
|
112
|
+
}
|
|
74
113
|
}
|
|
@@ -80,6 +80,7 @@ class RendererFactory(
|
|
|
80
80
|
|
|
81
81
|
private val textRenderer = TextRenderer()
|
|
82
82
|
private val lineBreakRenderer = LineBreakRenderer()
|
|
83
|
+
private val softBreakRenderer = SoftBreakRenderer()
|
|
83
84
|
|
|
84
85
|
private val renderers: Map<MarkdownASTNode.NodeType, NodeRenderer> by lazy {
|
|
85
86
|
buildMap {
|
|
@@ -103,13 +104,20 @@ class RendererFactory(
|
|
|
103
104
|
put(MarkdownASTNode.NodeType.Code, CodeRenderer(config))
|
|
104
105
|
put(MarkdownASTNode.NodeType.Image, ImageRenderer())
|
|
105
106
|
put(MarkdownASTNode.NodeType.LineBreak, lineBreakRenderer)
|
|
107
|
+
put(MarkdownASTNode.NodeType.SoftBreak, softBreakRenderer)
|
|
106
108
|
put(MarkdownASTNode.NodeType.ThematicBreak, ThematicBreakRenderer(config))
|
|
107
109
|
put(MarkdownASTNode.NodeType.Spoiler, SpoilerRenderer())
|
|
108
110
|
if (FeatureFlags.IS_MATH_ENABLED) {
|
|
109
111
|
try {
|
|
110
112
|
val mathInlineRendererClass = Class.forName("com.swmansion.enriched.markdown.renderer.MathInlineRenderer")
|
|
111
113
|
val constructor = mathInlineRendererClass.getConstructor(RendererConfig::class.java, Context::class.java)
|
|
112
|
-
|
|
114
|
+
val mathInlineRenderer = constructor.newInstance(config, context) as NodeRenderer
|
|
115
|
+
put(MarkdownASTNode.NodeType.LatexMathInline, mathInlineRenderer)
|
|
116
|
+
// Isolated display math is promoted to a block segment in the parser
|
|
117
|
+
// (see promoteDisplayMathFromParagraphs). What reaches the factory is
|
|
118
|
+
// genuinely mid-line display math (e.g. `a $$x$$ b`); render it inline
|
|
119
|
+
// rather than dropping it via the TextRenderer fallback.
|
|
120
|
+
put(MarkdownASTNode.NodeType.LatexMathDisplay, mathInlineRenderer)
|
|
113
121
|
} catch (_: Exception) {
|
|
114
122
|
// math not available
|
|
115
123
|
}
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
package com.swmansion.enriched.markdown.renderer
|
|
2
|
+
|
|
3
|
+
import android.text.SpannableStringBuilder
|
|
4
|
+
import com.swmansion.enriched.markdown.parser.MarkdownASTNode
|
|
5
|
+
|
|
6
|
+
class SoftBreakRenderer : NodeRenderer {
|
|
7
|
+
override fun render(
|
|
8
|
+
node: MarkdownASTNode,
|
|
9
|
+
builder: SpannableStringBuilder,
|
|
10
|
+
onLinkPress: ((String) -> Unit)?,
|
|
11
|
+
onLinkLongPress: ((String) -> Unit)?,
|
|
12
|
+
factory: RendererFactory,
|
|
13
|
+
) {
|
|
14
|
+
builder.append(" ")
|
|
15
|
+
}
|
|
16
|
+
}
|
|
@@ -1,6 +1,10 @@
|
|
|
1
1
|
package com.swmansion.enriched.markdown.renderer
|
|
2
2
|
|
|
3
|
+
import android.content.res.AssetManager
|
|
3
4
|
import android.graphics.Typeface
|
|
5
|
+
import com.facebook.react.common.ReactConstants
|
|
6
|
+
import com.facebook.react.views.text.ReactTypefaceUtils.applyStyles
|
|
7
|
+
import com.swmansion.enriched.markdown.styles.LinkChipStyle
|
|
4
8
|
import com.swmansion.enriched.markdown.styles.LinkVariantEntry
|
|
5
9
|
import com.swmansion.enriched.markdown.styles.StyleConfig
|
|
6
10
|
|
|
@@ -8,6 +12,8 @@ import com.swmansion.enriched.markdown.styles.StyleConfig
|
|
|
8
12
|
class SpanStyleCache(
|
|
9
13
|
style: StyleConfig,
|
|
10
14
|
) {
|
|
15
|
+
private val assetManager: AssetManager = style.assetManager
|
|
16
|
+
|
|
11
17
|
// Colors to preserve when applying inline styles (links, code, strong, emphasis)
|
|
12
18
|
val colorsToPreserve: IntArray = buildColorsToPreserve(style)
|
|
13
19
|
|
|
@@ -21,7 +27,7 @@ class SpanStyleCache(
|
|
|
21
27
|
val linkFontFamily: String = style.linkStyle.fontFamily
|
|
22
28
|
val linkColor: Int = style.linkStyle.color
|
|
23
29
|
val linkUnderline: Boolean = style.linkStyle.underline
|
|
24
|
-
val
|
|
30
|
+
val linkChip: LinkChipStyle = style.linkStyle.chip
|
|
25
31
|
val linkVariants: List<LinkVariantEntry> = style.linkVariants
|
|
26
32
|
|
|
27
33
|
private val compiledVariantPatterns: List<Pair<Regex, LinkVariantEntry>> =
|
|
@@ -95,36 +101,37 @@ class SpanStyleCache(
|
|
|
95
101
|
return compiledVariantPatterns.firstOrNull { (regex, _) -> regex.containsMatchIn(url) }?.second
|
|
96
102
|
}
|
|
97
103
|
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
/** Cached typeface for font family + style (BOLD, ITALIC, BOLD_ITALIC) */
|
|
102
|
-
fun getTypeface(
|
|
103
|
-
fontFamily: String,
|
|
104
|
-
style: Int,
|
|
105
|
-
): Typeface =
|
|
106
|
-
typefaceCache.getOrPut("$fontFamily|$style") {
|
|
107
|
-
val base =
|
|
108
|
-
fontFamily
|
|
109
|
-
.takeIf { it.isNotEmpty() }
|
|
110
|
-
?.let { Typeface.create(it, Typeface.NORMAL) }
|
|
111
|
-
?: Typeface.DEFAULT
|
|
112
|
-
Typeface.create(base, style)
|
|
113
|
-
}
|
|
104
|
+
/** Chip style for [url]: the matching variant's own, else the base link's (never merged). */
|
|
105
|
+
fun linkChipForUrl(url: String): LinkChipStyle = resolvedVariantForUrl(url)?.chip ?: linkChip
|
|
114
106
|
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
107
|
+
/**
|
|
108
|
+
* Cached typeface for font family + style (BOLD, ITALIC, BOLD_ITALIC).
|
|
109
|
+
*
|
|
110
|
+
* Loads the base custom font at its NORMAL weight (via applyStyles/ReactFontManager)
|
|
111
|
+
* so the bundled assets/fonts file resolves, then synthesizes bold/italic on that real
|
|
112
|
+
* typeface. Requesting bold/italic directly makes ReactFontManager look for `_bold`/
|
|
113
|
+
* `_italic` asset variants that single-file custom fonts don't have — and it then falls
|
|
114
|
+
* back to a default system face, dropping the custom font entirely.
|
|
115
|
+
*/
|
|
116
|
+
fun getTypeface(
|
|
117
|
+
fontFamily: String,
|
|
118
|
+
style: Int,
|
|
119
|
+
): Typeface =
|
|
120
|
+
typefaceCache.getOrPut("family|$fontFamily|$style") {
|
|
121
|
+
val base =
|
|
122
|
+
applyStyles(
|
|
123
|
+
null,
|
|
124
|
+
ReactConstants.UNSET,
|
|
125
|
+
ReactConstants.UNSET,
|
|
126
|
+
fontFamily.takeIf { it.isNotEmpty() },
|
|
127
|
+
assetManager,
|
|
128
|
+
)
|
|
129
|
+
if (style == Typeface.NORMAL) base else Typeface.create(base, style)
|
|
126
130
|
}
|
|
127
131
|
|
|
132
|
+
companion object {
|
|
133
|
+
private val typefaceCache = mutableMapOf<String, Typeface>()
|
|
134
|
+
|
|
128
135
|
/** Cached monospace typeface preserving bold/italic */
|
|
129
136
|
fun getMonospaceTypeface(currentStyle: Int): Typeface =
|
|
130
137
|
typefaceCache.getOrPut("monospace|$currentStyle") {
|
|
@@ -22,11 +22,20 @@ abstract class BaseListSpan(
|
|
|
22
22
|
protected val blockStyle: BlockStyle,
|
|
23
23
|
protected val marginLeft: Float,
|
|
24
24
|
protected val gapWidth: Float,
|
|
25
|
+
internal val drawsMarker: Boolean = true,
|
|
25
26
|
) : MetricAffectingSpan(),
|
|
26
27
|
LeadingMarginSpan {
|
|
27
28
|
private var cachedText: CharSequence? = null
|
|
28
29
|
private var cachedHasDeeperSpanByPosition = mutableMapOf<Int, Boolean>()
|
|
29
30
|
|
|
31
|
+
val markerFontMetrics: Paint.FontMetrics by lazy {
|
|
32
|
+
TextPaint()
|
|
33
|
+
.apply {
|
|
34
|
+
applyBlockStyleFont(blockStyle, context)
|
|
35
|
+
textSize = blockStyle.fontSize
|
|
36
|
+
}.fontMetrics
|
|
37
|
+
}
|
|
38
|
+
|
|
30
39
|
protected abstract fun getMarkerWidth(): Float
|
|
31
40
|
|
|
32
41
|
override fun updateMeasureState(textPaint: TextPaint) = applyTextStyle(textPaint)
|
|
@@ -55,6 +64,7 @@ abstract class BaseListSpan(
|
|
|
55
64
|
first: Boolean,
|
|
56
65
|
layout: Layout?,
|
|
57
66
|
) {
|
|
67
|
+
if (!drawsMarker) return
|
|
58
68
|
if (!first || shouldSkipDrawing(text, start) || !hasContent(text, start, end)) return
|
|
59
69
|
|
|
60
70
|
// Only draw the marker on the true first line of this span.
|
|
@@ -62,6 +72,20 @@ abstract class BaseListSpan(
|
|
|
62
72
|
// but only the line at the span start should get a bullet/number.
|
|
63
73
|
if (text is Spanned && text.getSpanStart(this) != start) return
|
|
64
74
|
|
|
75
|
+
drawMarkerAt(canvas, paint, x, dir, top, baseline, bottom, layout, start)
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
fun drawMarkerAt(
|
|
79
|
+
canvas: Canvas,
|
|
80
|
+
paint: Paint,
|
|
81
|
+
x: Int,
|
|
82
|
+
dir: Int,
|
|
83
|
+
top: Int,
|
|
84
|
+
baseline: Int,
|
|
85
|
+
bottom: Int,
|
|
86
|
+
layout: Layout?,
|
|
87
|
+
start: Int,
|
|
88
|
+
) {
|
|
65
89
|
val originalStyle = paint.style
|
|
66
90
|
val originalColor = paint.color
|
|
67
91
|
drawMarker(canvas, paint, x, dir, top, baseline, bottom, layout, start)
|
|
@@ -5,6 +5,8 @@ import android.content.Context
|
|
|
5
5
|
import android.graphics.Canvas
|
|
6
6
|
import android.graphics.Color
|
|
7
7
|
import android.graphics.Paint
|
|
8
|
+
import android.graphics.Path
|
|
9
|
+
import android.graphics.RectF
|
|
8
10
|
import android.graphics.Typeface
|
|
9
11
|
import android.text.Layout
|
|
10
12
|
import android.text.Spanned
|
|
@@ -12,6 +14,7 @@ import android.text.TextPaint
|
|
|
12
14
|
import android.text.style.LeadingMarginSpan
|
|
13
15
|
import android.text.style.LineBackgroundSpan
|
|
14
16
|
import android.text.style.MetricAffectingSpan
|
|
17
|
+
import androidx.core.graphics.withSave
|
|
15
18
|
import com.swmansion.enriched.markdown.renderer.BlockStyle
|
|
16
19
|
import com.swmansion.enriched.markdown.renderer.SpanStyleCache
|
|
17
20
|
import com.swmansion.enriched.markdown.styles.BlockquoteStyle
|
|
@@ -37,7 +40,13 @@ class BlockquoteSpan(
|
|
|
37
40
|
|
|
38
41
|
// Cache for shouldSkipDrawing to avoid repeated getSpans() calls during draw passes
|
|
39
42
|
private var cachedText: CharSequence? = null
|
|
40
|
-
private var
|
|
43
|
+
private var cachedSpansByPosition = mutableMapOf<Int, Array<BlockquoteSpan>>()
|
|
44
|
+
private var boxLeft = 0f
|
|
45
|
+
private var boxRight = 0f
|
|
46
|
+
|
|
47
|
+
private val path = Path()
|
|
48
|
+
private val rect = RectF()
|
|
49
|
+
private val radiiArray = FloatArray(8)
|
|
41
50
|
|
|
42
51
|
override fun updateMeasureState(tp: TextPaint) = applyTextStyle(tp)
|
|
43
52
|
|
|
@@ -63,13 +72,56 @@ class BlockquoteSpan(
|
|
|
63
72
|
if (shouldSkipDrawing(text, start)) return
|
|
64
73
|
|
|
65
74
|
val borderPaint = configureBorderPaint()
|
|
66
|
-
val
|
|
67
|
-
val
|
|
75
|
+
val radius = blockquoteStyle.borderRadius
|
|
76
|
+
val spanned = text as? Spanned
|
|
77
|
+
|
|
78
|
+
if (spanned == null) {
|
|
79
|
+
drawBorders(c, x, dir, top, bottom, borderPaint)
|
|
80
|
+
return
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
val rootSpan = spanAtMinDepth(spanned, start)
|
|
84
|
+
val clipToRoot =
|
|
85
|
+
radius > 0f && boxRight > boxLeft && rootSpan != null && isBoundaryLine(spanned, start, end, rootSpan)
|
|
86
|
+
|
|
87
|
+
val padding = blockquoteStyle.padding
|
|
88
|
+
var topInset = 0f
|
|
89
|
+
var bottomInset = 0f
|
|
68
90
|
|
|
69
91
|
for (level in 0..depth) {
|
|
70
92
|
val borderX = x + (levelSpacing * level * dir)
|
|
71
93
|
val borderRight = borderX + (blockquoteStyle.borderWidth * dir)
|
|
72
|
-
|
|
94
|
+
val stripeLeft = minOf(borderX, borderRight)
|
|
95
|
+
val stripeRight = maxOf(borderX, borderRight)
|
|
96
|
+
val stripeTop = top.toFloat() + topInset
|
|
97
|
+
val stripeBottom = bottom.toFloat() - bottomInset
|
|
98
|
+
|
|
99
|
+
val levelSpan = if (level == 0) rootSpan else spanAtDepth(spanned, start, level)
|
|
100
|
+
val clipToOwn =
|
|
101
|
+
radius > 0f && level > 0 && levelSpan != null && isBoundaryLine(spanned, start, end, levelSpan)
|
|
102
|
+
|
|
103
|
+
if (!clipToRoot && !clipToOwn) {
|
|
104
|
+
c.drawRect(stripeLeft, stripeTop, stripeRight, stripeBottom, borderPaint)
|
|
105
|
+
} else {
|
|
106
|
+
c.withSave {
|
|
107
|
+
if (clipToRoot) {
|
|
108
|
+
buildBoundaryPath(spanned, start, end, rootSpan!!, boxLeft, top.toFloat(), boxRight, bottom.toFloat())
|
|
109
|
+
clipPath(path)
|
|
110
|
+
}
|
|
111
|
+
if (clipToOwn) {
|
|
112
|
+
val clipLeft = if (dir >= 0) stripeLeft else boxLeft
|
|
113
|
+
val clipRight = if (dir >= 0) boxRight else stripeRight
|
|
114
|
+
buildBoundaryPath(spanned, start, end, levelSpan!!, clipLeft, stripeTop, clipRight, stripeBottom)
|
|
115
|
+
clipPath(path)
|
|
116
|
+
}
|
|
117
|
+
drawRect(stripeLeft, stripeTop, stripeRight, stripeBottom, borderPaint)
|
|
118
|
+
}
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
if (padding > 0 && levelSpan != null) {
|
|
122
|
+
if (start == spanned.getSpanStart(levelSpan)) topInset += padding
|
|
123
|
+
if (isLastLineOf(spanned, end, levelSpan)) bottomInset += padding
|
|
124
|
+
}
|
|
73
125
|
}
|
|
74
126
|
}
|
|
75
127
|
|
|
@@ -87,7 +139,40 @@ class BlockquoteSpan(
|
|
|
87
139
|
lineNum: Int,
|
|
88
140
|
) {
|
|
89
141
|
if (shouldSkipDrawing(text, start)) return
|
|
90
|
-
|
|
142
|
+
|
|
143
|
+
boxLeft = left.toFloat()
|
|
144
|
+
boxRight = right.toFloat()
|
|
145
|
+
|
|
146
|
+
val bgColor = blockquoteStyle.backgroundColor?.takeIf { it != Color.TRANSPARENT } ?: return
|
|
147
|
+
val backgroundPaint = configureBackgroundPaint(bgColor)
|
|
148
|
+
val radius = blockquoteStyle.borderRadius
|
|
149
|
+
val rootSpan = (text as? Spanned)?.let { spanAtMinDepth(it, start) }
|
|
150
|
+
|
|
151
|
+
if (radius <= 0f || rootSpan == null) {
|
|
152
|
+
canvas.drawRect(left.toFloat(), top.toFloat(), right.toFloat(), bottom.toFloat(), backgroundPaint)
|
|
153
|
+
return
|
|
154
|
+
}
|
|
155
|
+
|
|
156
|
+
buildBoundaryPath(text as Spanned, start, end, rootSpan, left.toFloat(), top.toFloat(), right.toFloat(), bottom.toFloat())
|
|
157
|
+
canvas.drawPath(path, backgroundPaint)
|
|
158
|
+
}
|
|
159
|
+
|
|
160
|
+
private fun drawBorders(
|
|
161
|
+
c: Canvas,
|
|
162
|
+
x: Int,
|
|
163
|
+
dir: Int,
|
|
164
|
+
top: Int,
|
|
165
|
+
bottom: Int,
|
|
166
|
+
borderPaint: Paint,
|
|
167
|
+
) {
|
|
168
|
+
val borderTop = top.toFloat()
|
|
169
|
+
val borderBottom = bottom.toFloat()
|
|
170
|
+
|
|
171
|
+
for (level in 0..depth) {
|
|
172
|
+
val borderX = x + (levelSpacing * level * dir)
|
|
173
|
+
val borderRight = borderX + (blockquoteStyle.borderWidth * dir)
|
|
174
|
+
c.drawRect(minOf(borderX, borderRight), borderTop, maxOf(borderX, borderRight), borderBottom, borderPaint)
|
|
175
|
+
}
|
|
91
176
|
}
|
|
92
177
|
|
|
93
178
|
@SuppressLint("WrongConstant") // Result of mask is always valid: 0, 1, 2, or 3
|
|
@@ -118,35 +203,100 @@ class BlockquoteSpan(
|
|
|
118
203
|
color = bgColor
|
|
119
204
|
}
|
|
120
205
|
|
|
206
|
+
private fun spansAt(
|
|
207
|
+
text: Spanned,
|
|
208
|
+
start: Int,
|
|
209
|
+
): Array<BlockquoteSpan> {
|
|
210
|
+
if (cachedText !== text) {
|
|
211
|
+
cachedText = text
|
|
212
|
+
cachedSpansByPosition.clear()
|
|
213
|
+
}
|
|
214
|
+
return cachedSpansByPosition.getOrPut(start) {
|
|
215
|
+
text.getSpans(start, start + 1, BlockquoteSpan::class.java)
|
|
216
|
+
}
|
|
217
|
+
}
|
|
218
|
+
|
|
121
219
|
private fun shouldSkipDrawing(
|
|
122
220
|
text: CharSequence?,
|
|
123
221
|
start: Int,
|
|
124
222
|
): Boolean {
|
|
125
223
|
if (text !is Spanned) return false
|
|
224
|
+
val maxDepth = spansAt(text, start).maxOfOrNull { it.depth } ?: -1
|
|
225
|
+
return maxDepth > depth
|
|
226
|
+
}
|
|
126
227
|
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
228
|
+
private fun spanAtMinDepth(
|
|
229
|
+
text: Spanned,
|
|
230
|
+
start: Int,
|
|
231
|
+
): BlockquoteSpan? = spansAt(text, start).minByOrNull { it.depth }
|
|
131
232
|
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
233
|
+
private fun spanAtDepth(
|
|
234
|
+
text: Spanned,
|
|
235
|
+
start: Int,
|
|
236
|
+
level: Int,
|
|
237
|
+
): BlockquoteSpan? = spansAt(text, start).firstOrNull { it.depth == level }
|
|
137
238
|
|
|
138
|
-
|
|
239
|
+
/**
|
|
240
|
+
* The span range can include trailing '\n'(s) that form no visible line (e.g. a
|
|
241
|
+
* paragraph break closing the quote), so the last drawn line ends before getSpanEnd;
|
|
242
|
+
* this compares against the end of visible content instead.
|
|
243
|
+
*/
|
|
244
|
+
private fun isLastLineOf(
|
|
245
|
+
text: Spanned,
|
|
246
|
+
lineEnd: Int,
|
|
247
|
+
box: BlockquoteSpan,
|
|
248
|
+
): Boolean {
|
|
249
|
+
var boxEnd = text.getSpanEnd(box)
|
|
250
|
+
while (boxEnd > 0 && text[boxEnd - 1] == '\n') {
|
|
251
|
+
boxEnd--
|
|
252
|
+
}
|
|
253
|
+
return lineEnd >= boxEnd
|
|
139
254
|
}
|
|
140
255
|
|
|
141
|
-
private fun
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
256
|
+
private fun isBoundaryLine(
|
|
257
|
+
text: Spanned,
|
|
258
|
+
lineStart: Int,
|
|
259
|
+
lineEnd: Int,
|
|
260
|
+
box: BlockquoteSpan,
|
|
261
|
+
): Boolean {
|
|
262
|
+
val boxStart = text.getSpanStart(box)
|
|
263
|
+
val boxEnd = text.getSpanEnd(box)
|
|
264
|
+
if (boxStart !in 0 until boxEnd) return false
|
|
265
|
+
return lineStart == boxStart || isLastLineOf(text, lineEnd, box)
|
|
266
|
+
}
|
|
267
|
+
|
|
268
|
+
private fun buildBoundaryPath(
|
|
269
|
+
text: Spanned,
|
|
270
|
+
lineStart: Int,
|
|
271
|
+
lineEnd: Int,
|
|
272
|
+
box: BlockquoteSpan,
|
|
273
|
+
left: Float,
|
|
274
|
+
top: Float,
|
|
275
|
+
right: Float,
|
|
276
|
+
bottom: Float,
|
|
147
277
|
) {
|
|
148
|
-
val
|
|
149
|
-
|
|
150
|
-
|
|
278
|
+
val boxStart = text.getSpanStart(box)
|
|
279
|
+
|
|
280
|
+
val isFirstLine = lineStart == boxStart
|
|
281
|
+
val isLastLine = isLastLineOf(text, lineEnd, box)
|
|
282
|
+
|
|
283
|
+
val radius = blockquoteStyle.borderRadius
|
|
284
|
+
radiiArray.fill(0f)
|
|
285
|
+
if (isFirstLine) {
|
|
286
|
+
radiiArray[0] = radius
|
|
287
|
+
radiiArray[1] = radius // Top-Left
|
|
288
|
+
radiiArray[2] = radius
|
|
289
|
+
radiiArray[3] = radius // Top-Right
|
|
290
|
+
}
|
|
291
|
+
if (isLastLine) {
|
|
292
|
+
radiiArray[4] = radius
|
|
293
|
+
radiiArray[5] = radius // Bottom-Right
|
|
294
|
+
radiiArray[6] = radius
|
|
295
|
+
radiiArray[7] = radius // Bottom-Left
|
|
296
|
+
}
|
|
297
|
+
|
|
298
|
+
rect.set(left, top, right, bottom)
|
|
299
|
+
path.reset()
|
|
300
|
+
path.addRoundRect(rect, radiiArray, Path.Direction.CW)
|
|
151
301
|
}
|
|
152
302
|
}
|
|
@@ -5,8 +5,6 @@ import android.graphics.Paint
|
|
|
5
5
|
import android.graphics.Path
|
|
6
6
|
import android.graphics.RectF
|
|
7
7
|
import android.text.Spanned
|
|
8
|
-
import android.text.StaticLayout
|
|
9
|
-
import android.text.TextPaint
|
|
10
8
|
import android.text.style.LineBackgroundSpan
|
|
11
9
|
import com.swmansion.enriched.markdown.styles.StyleConfig
|
|
12
10
|
import kotlin.math.max
|
|
@@ -58,8 +56,9 @@ class CodeBackgroundSpan(
|
|
|
58
56
|
|
|
59
57
|
// 2. Calculate coordinates
|
|
60
58
|
val finalBottom = adjustBottomForMargin(text, end, bottom)
|
|
61
|
-
val
|
|
62
|
-
val
|
|
59
|
+
val leadingMargin = leadingMarginAt(text, start)
|
|
60
|
+
val startX = if (isFirst) getHorizontalOffset(text, start, end, spanStart, p, leadingMargin) + left else left.toFloat() + leadingMargin
|
|
61
|
+
val endX = if (isLast) getHorizontalOffset(text, start, end, spanEnd, p, leadingMargin) + left else right.toFloat()
|
|
63
62
|
|
|
64
63
|
rect.set(min(startX, endX), top.toFloat(), max(startX, endX), finalBottom.toFloat())
|
|
65
64
|
|
|
@@ -77,92 +76,31 @@ class CodeBackgroundSpan(
|
|
|
77
76
|
lineEnd: Int,
|
|
78
77
|
index: Int,
|
|
79
78
|
paint: Paint,
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
val lineText = text.subSequence(lineStart, lineEnd)
|
|
83
|
-
val textPaint = paint as? TextPaint ?: TextPaint(paint)
|
|
84
|
-
val layout = StaticLayout.Builder.obtain(lineText, 0, lineText.length, textPaint, 10000).build()
|
|
85
|
-
return layout.getPrimaryHorizontal(index - lineStart)
|
|
86
|
-
}
|
|
79
|
+
leadingMargin: Int,
|
|
80
|
+
): Float = InlineChipPainter.horizontalOffset(text, lineStart, lineEnd, index, paint, leadingMargin)
|
|
87
81
|
|
|
88
82
|
private fun drawShapes(
|
|
89
83
|
canvas: Canvas,
|
|
90
84
|
isFirst: Boolean,
|
|
91
85
|
isLast: Boolean,
|
|
92
86
|
) {
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
}
|
|
105
|
-
|
|
106
|
-
private fun drawOpenBorders(
|
|
107
|
-
canvas: Canvas,
|
|
108
|
-
isFirst: Boolean,
|
|
109
|
-
isLast: Boolean,
|
|
110
|
-
) {
|
|
111
|
-
val r = CORNER_RADIUS
|
|
112
|
-
path.reset()
|
|
113
|
-
|
|
114
|
-
if (isFirst) {
|
|
115
|
-
path.moveTo(rect.right, rect.top)
|
|
116
|
-
path.lineTo(rect.left + r, rect.top)
|
|
117
|
-
path.quadTo(rect.left, rect.top, rect.left, rect.top + r)
|
|
118
|
-
path.lineTo(rect.left, rect.bottom - r)
|
|
119
|
-
path.quadTo(rect.left, rect.bottom, rect.left + r, rect.bottom)
|
|
120
|
-
path.lineTo(rect.right, rect.bottom)
|
|
121
|
-
} else if (isLast) {
|
|
122
|
-
path.moveTo(rect.left, rect.top)
|
|
123
|
-
path.lineTo(rect.right - r, rect.top)
|
|
124
|
-
path.quadTo(rect.right, rect.top, rect.right, rect.top + r)
|
|
125
|
-
path.lineTo(rect.right, rect.bottom - r)
|
|
126
|
-
path.quadTo(rect.right, rect.bottom, rect.right - r, rect.bottom)
|
|
127
|
-
path.lineTo(rect.left, rect.bottom)
|
|
128
|
-
} else {
|
|
129
|
-
path.moveTo(rect.left, rect.top)
|
|
130
|
-
path.lineTo(rect.right, rect.top)
|
|
131
|
-
path.moveTo(rect.left, rect.bottom)
|
|
132
|
-
path.lineTo(rect.right, rect.bottom)
|
|
133
|
-
}
|
|
134
|
-
canvas.drawPath(path, sharedBorderPaint)
|
|
87
|
+
InlineChipPainter.draw(
|
|
88
|
+
canvas,
|
|
89
|
+
rect,
|
|
90
|
+
path,
|
|
91
|
+
CORNER_RADIUS,
|
|
92
|
+
sharedBackgroundPaint,
|
|
93
|
+
sharedBorderPaint,
|
|
94
|
+
isFirst,
|
|
95
|
+
isLast,
|
|
96
|
+
strokeInset = false,
|
|
97
|
+
)
|
|
135
98
|
}
|
|
136
99
|
|
|
137
|
-
private fun
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
) =
|
|
141
|
-
isFirst && isLast -> {
|
|
142
|
-
floatArrayOf(
|
|
143
|
-
CORNER_RADIUS,
|
|
144
|
-
CORNER_RADIUS,
|
|
145
|
-
CORNER_RADIUS,
|
|
146
|
-
CORNER_RADIUS,
|
|
147
|
-
CORNER_RADIUS,
|
|
148
|
-
CORNER_RADIUS,
|
|
149
|
-
CORNER_RADIUS,
|
|
150
|
-
CORNER_RADIUS,
|
|
151
|
-
)
|
|
152
|
-
}
|
|
153
|
-
|
|
154
|
-
isFirst -> {
|
|
155
|
-
floatArrayOf(CORNER_RADIUS, CORNER_RADIUS, 0f, 0f, 0f, 0f, CORNER_RADIUS, CORNER_RADIUS)
|
|
156
|
-
}
|
|
157
|
-
|
|
158
|
-
isLast -> {
|
|
159
|
-
floatArrayOf(0f, 0f, CORNER_RADIUS, CORNER_RADIUS, CORNER_RADIUS, CORNER_RADIUS, 0f, 0f)
|
|
160
|
-
}
|
|
161
|
-
|
|
162
|
-
else -> {
|
|
163
|
-
floatArrayOf(0f, 0f, 0f, 0f, 0f, 0f, 0f, 0f)
|
|
164
|
-
}
|
|
165
|
-
}
|
|
100
|
+
private fun leadingMarginAt(
|
|
101
|
+
text: Spanned,
|
|
102
|
+
lineStart: Int,
|
|
103
|
+
): Int = InlineChipPainter.leadingMarginAt(text, lineStart)
|
|
166
104
|
|
|
167
105
|
private fun adjustBottomForMargin(
|
|
168
106
|
text: Spanned,
|