react-native-enriched 0.2.0 → 0.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (186) hide show
  1. package/README.md +16 -17
  2. package/android/build.gradle +77 -72
  3. package/android/generated/java/com/facebook/react/viewmanagers/EnrichedTextInputViewManagerDelegate.java +21 -0
  4. package/android/generated/java/com/facebook/react/viewmanagers/EnrichedTextInputViewManagerInterface.java +7 -0
  5. package/android/generated/jni/react/renderer/components/RNEnrichedTextInputViewSpec/EventEmitters.cpp +156 -0
  6. package/android/generated/jni/react/renderer/components/RNEnrichedTextInputViewSpec/EventEmitters.h +147 -0
  7. package/android/generated/jni/react/renderer/components/RNEnrichedTextInputViewSpec/Props.cpp +10 -0
  8. package/android/generated/jni/react/renderer/components/RNEnrichedTextInputViewSpec/Props.h +194 -0
  9. package/android/lint.gradle +70 -0
  10. package/android/src/main/java/com/swmansion/enriched/EnrichedTextInputConnectionWrapper.kt +140 -0
  11. package/android/src/main/java/com/swmansion/enriched/EnrichedTextInputView.kt +304 -83
  12. package/android/src/main/java/com/swmansion/enriched/EnrichedTextInputViewLayoutManager.kt +3 -1
  13. package/android/src/main/java/com/swmansion/enriched/EnrichedTextInputViewManager.kt +166 -51
  14. package/android/src/main/java/com/swmansion/enriched/EnrichedTextInputViewPackage.kt +1 -3
  15. package/android/src/main/java/com/swmansion/enriched/MeasurementStore.kt +70 -21
  16. package/android/src/main/java/com/swmansion/enriched/events/MentionHandler.kt +21 -11
  17. package/android/src/main/java/com/swmansion/enriched/events/OnChangeHtmlEvent.kt +8 -9
  18. package/android/src/main/java/com/swmansion/enriched/events/OnChangeSelectionEvent.kt +10 -9
  19. package/android/src/main/java/com/swmansion/enriched/events/OnChangeStateDeprecatedEvent.kt +21 -0
  20. package/android/src/main/java/com/swmansion/enriched/events/OnChangeStateEvent.kt +9 -12
  21. package/android/src/main/java/com/swmansion/enriched/events/OnChangeTextEvent.kt +10 -10
  22. package/android/src/main/java/com/swmansion/enriched/events/OnInputBlurEvent.kt +7 -9
  23. package/android/src/main/java/com/swmansion/enriched/events/OnInputFocusEvent.kt +7 -9
  24. package/android/src/main/java/com/swmansion/enriched/events/OnInputKeyPressEvent.kt +27 -0
  25. package/android/src/main/java/com/swmansion/enriched/events/OnLinkDetectedEvent.kt +13 -11
  26. package/android/src/main/java/com/swmansion/enriched/events/OnMentionDetectedEvent.kt +10 -9
  27. package/android/src/main/java/com/swmansion/enriched/events/OnMentionEvent.kt +9 -8
  28. package/android/src/main/java/com/swmansion/enriched/events/OnRequestHtmlResultEvent.kt +32 -0
  29. package/android/src/main/java/com/swmansion/enriched/spans/EnrichedBlockQuoteSpan.kt +24 -5
  30. package/android/src/main/java/com/swmansion/enriched/spans/EnrichedBoldSpan.kt +8 -1
  31. package/android/src/main/java/com/swmansion/enriched/spans/EnrichedCodeBlockSpan.kt +10 -2
  32. package/android/src/main/java/com/swmansion/enriched/spans/EnrichedH1Span.kt +8 -1
  33. package/android/src/main/java/com/swmansion/enriched/spans/EnrichedH2Span.kt +8 -1
  34. package/android/src/main/java/com/swmansion/enriched/spans/EnrichedH3Span.kt +8 -1
  35. package/android/src/main/java/com/swmansion/enriched/spans/EnrichedH4Span.kt +24 -0
  36. package/android/src/main/java/com/swmansion/enriched/spans/EnrichedH5Span.kt +24 -0
  37. package/android/src/main/java/com/swmansion/enriched/spans/EnrichedH6Span.kt +24 -0
  38. package/android/src/main/java/com/swmansion/enriched/spans/EnrichedImageSpan.kt +34 -17
  39. package/android/src/main/java/com/swmansion/enriched/spans/EnrichedInlineCodeSpan.kt +8 -1
  40. package/android/src/main/java/com/swmansion/enriched/spans/EnrichedItalicSpan.kt +7 -1
  41. package/android/src/main/java/com/swmansion/enriched/spans/EnrichedLinkSpan.kt +10 -4
  42. package/android/src/main/java/com/swmansion/enriched/spans/EnrichedMentionSpan.kt +14 -11
  43. package/android/src/main/java/com/swmansion/enriched/spans/EnrichedOrderedListSpan.kt +18 -11
  44. package/android/src/main/java/com/swmansion/enriched/spans/EnrichedSpans.kt +174 -72
  45. package/android/src/main/java/com/swmansion/enriched/spans/EnrichedStrikeThroughSpan.kt +7 -1
  46. package/android/src/main/java/com/swmansion/enriched/spans/EnrichedUnderlineSpan.kt +7 -1
  47. package/android/src/main/java/com/swmansion/enriched/spans/EnrichedUnorderedListSpan.kt +11 -5
  48. package/android/src/main/java/com/swmansion/enriched/spans/interfaces/EnrichedBlockSpan.kt +3 -2
  49. package/android/src/main/java/com/swmansion/enriched/spans/interfaces/EnrichedHeadingSpan.kt +1 -2
  50. package/android/src/main/java/com/swmansion/enriched/spans/interfaces/EnrichedInlineSpan.kt +1 -2
  51. package/android/src/main/java/com/swmansion/enriched/spans/interfaces/EnrichedParagraphSpan.kt +3 -2
  52. package/android/src/main/java/com/swmansion/enriched/spans/interfaces/EnrichedSpan.kt +5 -0
  53. package/android/src/main/java/com/swmansion/enriched/spans/interfaces/EnrichedZeroWidthSpaceSpan.kt +1 -2
  54. package/android/src/main/java/com/swmansion/enriched/spans/utils/ForceRedrawSpan.kt +2 -1
  55. package/android/src/main/java/com/swmansion/enriched/styles/HtmlStyle.kt +155 -20
  56. package/android/src/main/java/com/swmansion/enriched/styles/InlineStyles.kt +25 -8
  57. package/android/src/main/java/com/swmansion/enriched/styles/ListStyles.kt +60 -20
  58. package/android/src/main/java/com/swmansion/enriched/styles/ParagraphStyles.kt +161 -25
  59. package/android/src/main/java/com/swmansion/enriched/styles/ParametrizedStyles.kt +128 -52
  60. package/android/src/main/java/com/swmansion/enriched/utils/AsyncDrawable.kt +10 -7
  61. package/android/src/main/java/com/swmansion/enriched/utils/EnrichedConstants.kt +11 -0
  62. package/android/src/main/java/com/swmansion/enriched/utils/EnrichedEditableFactory.kt +17 -0
  63. package/android/src/main/java/com/swmansion/enriched/utils/EnrichedParser.java +136 -87
  64. package/android/src/main/java/com/swmansion/enriched/utils/EnrichedSelection.kt +71 -42
  65. package/android/src/main/java/com/swmansion/enriched/utils/EnrichedSpanState.kt +183 -48
  66. package/android/src/main/java/com/swmansion/enriched/utils/EnrichedSpannable.kt +82 -0
  67. package/android/src/main/java/com/swmansion/enriched/utils/EnrichedSpannableStringBuilder.kt +15 -0
  68. package/android/src/main/java/com/swmansion/enriched/utils/Utils.kt +0 -70
  69. package/android/src/main/java/com/swmansion/enriched/watchers/EnrichedSpanWatcher.kt +46 -14
  70. package/android/src/main/java/com/swmansion/enriched/watchers/EnrichedTextWatcher.kt +34 -11
  71. package/android/src/main/new_arch/CMakeLists.txt +6 -0
  72. package/android/src/main/new_arch/RNEnrichedTextInputViewSpec.cpp +6 -6
  73. package/android/src/main/new_arch/RNEnrichedTextInputViewSpec.h +6 -6
  74. package/android/src/main/new_arch/react/renderer/components/RNEnrichedTextInputViewSpec/EnrichedTextInputComponentDescriptor.h +19 -19
  75. package/android/src/main/new_arch/react/renderer/components/RNEnrichedTextInputViewSpec/EnrichedTextInputMeasurementManager.cpp +40 -51
  76. package/android/src/main/new_arch/react/renderer/components/RNEnrichedTextInputViewSpec/EnrichedTextInputMeasurementManager.h +13 -15
  77. package/android/src/main/new_arch/react/renderer/components/RNEnrichedTextInputViewSpec/EnrichedTextInputShadowNode.cpp +23 -21
  78. package/android/src/main/new_arch/react/renderer/components/RNEnrichedTextInputViewSpec/EnrichedTextInputShadowNode.h +35 -36
  79. package/android/src/main/new_arch/react/renderer/components/RNEnrichedTextInputViewSpec/EnrichedTextInputState.cpp +4 -4
  80. package/android/src/main/new_arch/react/renderer/components/RNEnrichedTextInputViewSpec/EnrichedTextInputState.h +13 -14
  81. package/android/src/main/new_arch/react/renderer/components/RNEnrichedTextInputViewSpec/conversions.h +33 -14
  82. package/ios/EnrichedTextInputView.h +26 -14
  83. package/ios/EnrichedTextInputView.mm +1209 -586
  84. package/ios/config/InputConfig.h +24 -6
  85. package/ios/config/InputConfig.mm +154 -38
  86. package/ios/{utils → extensions}/ColorExtension.mm +7 -5
  87. package/ios/extensions/FontExtension.mm +106 -0
  88. package/ios/{utils → extensions}/LayoutManagerExtension.h +1 -1
  89. package/ios/extensions/LayoutManagerExtension.mm +396 -0
  90. package/ios/{utils → extensions}/StringExtension.mm +19 -16
  91. package/ios/generated/RNEnrichedTextInputViewSpec/EventEmitters.cpp +156 -0
  92. package/ios/generated/RNEnrichedTextInputViewSpec/EventEmitters.h +147 -0
  93. package/ios/generated/RNEnrichedTextInputViewSpec/Props.cpp +10 -0
  94. package/ios/generated/RNEnrichedTextInputViewSpec/Props.h +194 -0
  95. package/ios/generated/RNEnrichedTextInputViewSpec/RCTComponentViewHelpers.h +95 -0
  96. package/ios/inputParser/InputParser.h +5 -5
  97. package/ios/inputParser/InputParser.mm +864 -380
  98. package/ios/inputTextView/InputTextView.h +1 -1
  99. package/ios/inputTextView/InputTextView.mm +100 -59
  100. package/ios/{utils → interfaces}/BaseStyleProtocol.h +2 -2
  101. package/ios/interfaces/ImageAttachment.h +10 -0
  102. package/ios/interfaces/ImageAttachment.mm +36 -0
  103. package/ios/interfaces/LinkRegexConfig.h +19 -0
  104. package/ios/interfaces/LinkRegexConfig.mm +37 -0
  105. package/ios/interfaces/MediaAttachment.h +23 -0
  106. package/ios/interfaces/MediaAttachment.mm +31 -0
  107. package/ios/{utils → interfaces}/MentionParams.h +0 -1
  108. package/ios/{utils → interfaces}/MentionStyleProps.mm +27 -20
  109. package/ios/{utils → interfaces}/StyleHeaders.h +37 -15
  110. package/ios/{utils → interfaces}/StyleTypeEnum.h +3 -0
  111. package/ios/internals/EnrichedTextInputViewComponentDescriptor.h +11 -9
  112. package/ios/internals/EnrichedTextInputViewShadowNode.h +28 -25
  113. package/ios/internals/EnrichedTextInputViewShadowNode.mm +45 -40
  114. package/ios/internals/EnrichedTextInputViewState.h +3 -1
  115. package/ios/styles/BlockQuoteStyle.mm +189 -118
  116. package/ios/styles/BoldStyle.mm +110 -63
  117. package/ios/styles/CodeBlockStyle.mm +204 -128
  118. package/ios/styles/H1Style.mm +10 -4
  119. package/ios/styles/H2Style.mm +10 -4
  120. package/ios/styles/H3Style.mm +10 -4
  121. package/ios/styles/H4Style.mm +17 -0
  122. package/ios/styles/H5Style.mm +17 -0
  123. package/ios/styles/H6Style.mm +17 -0
  124. package/ios/styles/HeadingStyleBase.mm +148 -86
  125. package/ios/styles/ImageStyle.mm +75 -73
  126. package/ios/styles/InlineCodeStyle.mm +162 -88
  127. package/ios/styles/ItalicStyle.mm +76 -52
  128. package/ios/styles/LinkStyle.mm +411 -232
  129. package/ios/styles/MentionStyle.mm +363 -246
  130. package/ios/styles/OrderedListStyle.mm +171 -106
  131. package/ios/styles/StrikethroughStyle.mm +52 -35
  132. package/ios/styles/UnderlineStyle.mm +68 -46
  133. package/ios/styles/UnorderedListStyle.mm +169 -106
  134. package/ios/utils/OccurenceUtils.h +42 -42
  135. package/ios/utils/OccurenceUtils.mm +142 -119
  136. package/ios/utils/ParagraphAttributesUtils.h +10 -2
  137. package/ios/utils/ParagraphAttributesUtils.mm +182 -71
  138. package/ios/utils/ParagraphsUtils.h +2 -1
  139. package/ios/utils/ParagraphsUtils.mm +41 -27
  140. package/ios/utils/TextInsertionUtils.h +13 -2
  141. package/ios/utils/TextInsertionUtils.mm +38 -20
  142. package/ios/utils/WordsUtils.h +2 -1
  143. package/ios/utils/WordsUtils.mm +32 -22
  144. package/ios/utils/ZeroWidthSpaceUtils.h +3 -1
  145. package/ios/utils/ZeroWidthSpaceUtils.mm +145 -79
  146. package/lib/module/EnrichedTextInput.js +61 -2
  147. package/lib/module/EnrichedTextInput.js.map +1 -1
  148. package/lib/module/EnrichedTextInputNativeComponent.ts +149 -12
  149. package/lib/module/{normalizeHtmlStyle.js → utils/normalizeHtmlStyle.js} +12 -0
  150. package/lib/module/utils/normalizeHtmlStyle.js.map +1 -0
  151. package/lib/module/utils/regexParser.js +46 -0
  152. package/lib/module/utils/regexParser.js.map +1 -0
  153. package/lib/typescript/src/EnrichedTextInput.d.ts +24 -14
  154. package/lib/typescript/src/EnrichedTextInput.d.ts.map +1 -1
  155. package/lib/typescript/src/EnrichedTextInputNativeComponent.d.ts +129 -12
  156. package/lib/typescript/src/EnrichedTextInputNativeComponent.d.ts.map +1 -1
  157. package/lib/typescript/src/index.d.ts +1 -1
  158. package/lib/typescript/src/index.d.ts.map +1 -1
  159. package/lib/typescript/src/utils/normalizeHtmlStyle.d.ts +4 -0
  160. package/lib/typescript/src/utils/normalizeHtmlStyle.d.ts.map +1 -0
  161. package/lib/typescript/src/utils/regexParser.d.ts +3 -0
  162. package/lib/typescript/src/utils/regexParser.d.ts.map +1 -0
  163. package/package.json +17 -6
  164. package/src/EnrichedTextInput.tsx +96 -13
  165. package/src/EnrichedTextInputNativeComponent.ts +149 -12
  166. package/src/index.tsx +2 -0
  167. package/src/{normalizeHtmlStyle.ts → utils/normalizeHtmlStyle.ts} +14 -2
  168. package/src/utils/regexParser.ts +56 -0
  169. package/ios/utils/FontExtension.mm +0 -91
  170. package/ios/utils/LayoutManagerExtension.mm +0 -286
  171. package/lib/module/normalizeHtmlStyle.js.map +0 -1
  172. package/lib/typescript/src/normalizeHtmlStyle.d.ts +0 -4
  173. package/lib/typescript/src/normalizeHtmlStyle.d.ts.map +0 -1
  174. package/ios/{utils → extensions}/ColorExtension.h +0 -0
  175. package/ios/{utils → extensions}/FontExtension.h +0 -0
  176. package/ios/{utils → extensions}/StringExtension.h +1 -1
  177. package/ios/{utils → interfaces}/ImageData.h +0 -0
  178. package/ios/{utils → interfaces}/ImageData.mm +0 -0
  179. package/ios/{utils → interfaces}/LinkData.h +0 -0
  180. package/ios/{utils → interfaces}/LinkData.mm +0 -0
  181. package/ios/{utils → interfaces}/MentionParams.mm +0 -0
  182. package/ios/{utils → interfaces}/MentionStyleProps.h +1 -1
  183. /package/ios/{utils → interfaces}/StylePair.h +0 -0
  184. /package/ios/{utils → interfaces}/StylePair.mm +0 -0
  185. /package/ios/{utils → interfaces}/TextDecorationLineEnum.h +0 -0
  186. /package/ios/{utils → interfaces}/TextDecorationLineEnum.mm +0 -0
@@ -1,17 +1,21 @@
1
- #import "StyleHeaders.h"
1
+ #import "ColorExtension.h"
2
2
  #import "EnrichedTextInputView.h"
3
3
  #import "FontExtension.h"
4
4
  #import "OccurenceUtils.h"
5
5
  #import "ParagraphsUtils.h"
6
- #import "ColorExtension.h"
6
+ #import "StyleHeaders.h"
7
7
 
8
8
  @implementation InlineCodeStyle {
9
9
  EnrichedTextInputView *_input;
10
10
  }
11
11
 
12
- + (StyleType)getStyleType { return InlineCode; }
12
+ + (StyleType)getStyleType {
13
+ return InlineCode;
14
+ }
13
15
 
14
- + (BOOL)isParagraphStyle { return NO; }
16
+ + (BOOL)isParagraphStyle {
17
+ return NO;
18
+ }
15
19
 
16
20
  - (instancetype)initWithInput:(id)input {
17
21
  self = [super init];
@@ -21,48 +25,76 @@
21
25
 
22
26
  - (void)applyStyle:(NSRange)range {
23
27
  BOOL isStylePresent = [self detectStyle:range];
24
- if(range.length >= 1) {
25
- isStylePresent ? [self removeAttributes:range] : [self addAttributes:range];
28
+ if (range.length >= 1) {
29
+ isStylePresent ? [self removeAttributes:range]
30
+ : [self addAttributes:range withTypingAttr:YES];
26
31
  } else {
27
32
  isStylePresent ? [self removeTypingAttributes] : [self addTypingAttributes];
28
33
  }
29
34
  }
30
35
 
31
- - (void)addAttributes:(NSRange)range {
36
+ - (void)addAttributes:(NSRange)range withTypingAttr:(BOOL)withTypingAttr {
32
37
  // we don't want to apply inline code to newline characters, it looks bad
33
- NSArray *nonNewlineRanges = [ParagraphsUtils getNonNewlineRangesIn:_input->textView range:range];
34
-
35
- for(NSValue *value in nonNewlineRanges) {
38
+ NSArray *nonNewlineRanges =
39
+ [ParagraphsUtils getNonNewlineRangesIn:_input->textView range:range];
40
+
41
+ for (NSValue *value in nonNewlineRanges) {
36
42
  NSRange currentRange = [value rangeValue];
37
43
  [_input->textView.textStorage beginEditing];
38
44
 
39
- [_input->textView.textStorage addAttribute:NSBackgroundColorAttributeName value:[[_input->config inlineCodeBgColor] colorWithAlphaIfNotTransparent:0.4] range:currentRange];
40
- [_input->textView.textStorage addAttribute:NSForegroundColorAttributeName value:[_input->config inlineCodeFgColor] range:currentRange];
41
- [_input->textView.textStorage addAttribute:NSUnderlineColorAttributeName value:[_input->config inlineCodeFgColor] range:currentRange];
42
- [_input->textView.textStorage addAttribute:NSStrikethroughColorAttributeName value:[_input->config inlineCodeFgColor] range:currentRange];
43
- [_input->textView.textStorage enumerateAttribute:NSFontAttributeName inRange:currentRange options:0
44
- usingBlock:^(id _Nullable value, NSRange range, BOOL * _Nonnull stop) {
45
- UIFont *font = (UIFont *)value;
46
- if(font != nullptr) {
47
- UIFont *newFont = [[[_input->config monospacedFont] withFontTraits:font] setSize:font.pointSize];
48
- [_input->textView.textStorage addAttribute:NSFontAttributeName value:newFont range:range];
49
- }
50
- }
51
- ];
52
-
45
+ [_input->textView.textStorage
46
+ addAttribute:NSBackgroundColorAttributeName
47
+ value:[[_input->config inlineCodeBgColor]
48
+ colorWithAlphaIfNotTransparent:0.4]
49
+ range:currentRange];
50
+ [_input->textView.textStorage
51
+ addAttribute:NSForegroundColorAttributeName
52
+ value:[_input->config inlineCodeFgColor]
53
+ range:currentRange];
54
+ [_input->textView.textStorage
55
+ addAttribute:NSUnderlineColorAttributeName
56
+ value:[_input->config inlineCodeFgColor]
57
+ range:currentRange];
58
+ [_input->textView.textStorage
59
+ addAttribute:NSStrikethroughColorAttributeName
60
+ value:[_input->config inlineCodeFgColor]
61
+ range:currentRange];
62
+ [_input->textView.textStorage
63
+ enumerateAttribute:NSFontAttributeName
64
+ inRange:currentRange
65
+ options:0
66
+ usingBlock:^(id _Nullable value, NSRange range,
67
+ BOOL *_Nonnull stop) {
68
+ UIFont *font = (UIFont *)value;
69
+ if (font != nullptr) {
70
+ UIFont *newFont = [[[_input->config monospacedFont]
71
+ withFontTraits:font] setSize:font.pointSize];
72
+ [_input->textView.textStorage
73
+ addAttribute:NSFontAttributeName
74
+ value:newFont
75
+ range:range];
76
+ }
77
+ }];
78
+
53
79
  [_input->textView.textStorage endEditing];
54
80
  }
55
81
  }
56
82
 
57
83
  - (void)addTypingAttributes {
58
- NSMutableDictionary *newTypingAttrs = [_input->textView.typingAttributes mutableCopy];
59
- newTypingAttrs[NSBackgroundColorAttributeName] = [[_input->config inlineCodeBgColor] colorWithAlphaIfNotTransparent:0.4];
60
- newTypingAttrs[NSForegroundColorAttributeName] = [_input->config inlineCodeFgColor];
61
- newTypingAttrs[NSUnderlineColorAttributeName] = [_input->config inlineCodeFgColor];
62
- newTypingAttrs[NSStrikethroughColorAttributeName] = [_input->config inlineCodeFgColor];
63
- UIFont* currentFont = (UIFont *)newTypingAttrs[NSFontAttributeName];
64
- if(currentFont != nullptr) {
65
- newTypingAttrs[NSFontAttributeName] = [[[_input->config monospacedFont] withFontTraits:currentFont] setSize:currentFont.pointSize];
84
+ NSMutableDictionary *newTypingAttrs =
85
+ [_input->textView.typingAttributes mutableCopy];
86
+ newTypingAttrs[NSBackgroundColorAttributeName] =
87
+ [[_input->config inlineCodeBgColor] colorWithAlphaIfNotTransparent:0.4];
88
+ newTypingAttrs[NSForegroundColorAttributeName] =
89
+ [_input->config inlineCodeFgColor];
90
+ newTypingAttrs[NSUnderlineColorAttributeName] =
91
+ [_input->config inlineCodeFgColor];
92
+ newTypingAttrs[NSStrikethroughColorAttributeName] =
93
+ [_input->config inlineCodeFgColor];
94
+ UIFont *currentFont = (UIFont *)newTypingAttrs[NSFontAttributeName];
95
+ if (currentFont != nullptr) {
96
+ newTypingAttrs[NSFontAttributeName] = [[[_input->config monospacedFont]
97
+ withFontTraits:currentFont] setSize:currentFont.pointSize];
66
98
  }
67
99
  _input->textView.typingAttributes = newTypingAttrs;
68
100
  }
@@ -70,100 +102,142 @@
70
102
  - (void)removeAttributes:(NSRange)range {
71
103
  [_input->textView.textStorage beginEditing];
72
104
 
73
- [_input->textView.textStorage removeAttribute:NSBackgroundColorAttributeName range:range];
74
- [_input->textView.textStorage addAttribute:NSForegroundColorAttributeName value:[_input->config primaryColor] range:range];
75
- [_input->textView.textStorage addAttribute:NSUnderlineColorAttributeName value:[_input->config primaryColor] range:range];
76
- [_input->textView.textStorage addAttribute:NSStrikethroughColorAttributeName value:[_input->config primaryColor] range:range];
77
- [_input->textView.textStorage enumerateAttribute:NSFontAttributeName inRange:range options:0
78
- usingBlock:^(id _Nullable value, NSRange range, BOOL * _Nonnull stop) {
79
- UIFont *font = (UIFont *)value;
80
- if(font != nullptr) {
81
- UIFont *newFont = [[[_input->config primaryFont] withFontTraits:font] setSize:font.pointSize];
82
- [_input->textView.textStorage addAttribute:NSFontAttributeName value:newFont range:range];
83
- }
84
- }
85
- ];
86
-
105
+ [_input->textView.textStorage removeAttribute:NSBackgroundColorAttributeName
106
+ range:range];
107
+ [_input->textView.textStorage addAttribute:NSForegroundColorAttributeName
108
+ value:[_input->config primaryColor]
109
+ range:range];
110
+ [_input->textView.textStorage addAttribute:NSUnderlineColorAttributeName
111
+ value:[_input->config primaryColor]
112
+ range:range];
113
+ [_input->textView.textStorage addAttribute:NSStrikethroughColorAttributeName
114
+ value:[_input->config primaryColor]
115
+ range:range];
116
+ [_input->textView.textStorage
117
+ enumerateAttribute:NSFontAttributeName
118
+ inRange:range
119
+ options:0
120
+ usingBlock:^(id _Nullable value, NSRange range,
121
+ BOOL *_Nonnull stop) {
122
+ UIFont *font = (UIFont *)value;
123
+ if (font != nullptr) {
124
+ UIFont *newFont = [[[_input->config primaryFont]
125
+ withFontTraits:font] setSize:font.pointSize];
126
+ [_input->textView.textStorage addAttribute:NSFontAttributeName
127
+ value:newFont
128
+ range:range];
129
+ }
130
+ }];
131
+
87
132
  [_input->textView.textStorage endEditing];
88
133
  }
89
134
 
90
135
  - (void)removeTypingAttributes {
91
- NSMutableDictionary *newTypingAttrs = [_input->textView.typingAttributes mutableCopy];
136
+ NSMutableDictionary *newTypingAttrs =
137
+ [_input->textView.typingAttributes mutableCopy];
92
138
  [newTypingAttrs removeObjectForKey:NSBackgroundColorAttributeName];
93
- newTypingAttrs[NSForegroundColorAttributeName] = [_input->config primaryColor];
139
+ newTypingAttrs[NSForegroundColorAttributeName] =
140
+ [_input->config primaryColor];
94
141
  newTypingAttrs[NSUnderlineColorAttributeName] = [_input->config primaryColor];
95
- newTypingAttrs[NSStrikethroughColorAttributeName] = [_input->config primaryColor];
96
- UIFont* currentFont = (UIFont *)newTypingAttrs[NSFontAttributeName];
97
- if(currentFont != nullptr) {
98
- newTypingAttrs[NSFontAttributeName] = [[[_input->config primaryFont] withFontTraits:currentFont] setSize:currentFont.pointSize];
142
+ newTypingAttrs[NSStrikethroughColorAttributeName] =
143
+ [_input->config primaryColor];
144
+ UIFont *currentFont = (UIFont *)newTypingAttrs[NSFontAttributeName];
145
+ if (currentFont != nullptr) {
146
+ newTypingAttrs[NSFontAttributeName] = [[[_input->config primaryFont]
147
+ withFontTraits:currentFont] setSize:currentFont.pointSize];
99
148
  }
100
149
  _input->textView.typingAttributes = newTypingAttrs;
101
150
  }
102
151
 
103
152
  // making sure no newlines get inline code style, it looks bad
104
153
  - (void)handleNewlines {
105
- for(int i = 0; i < _input->textView.textStorage.string.length; i++) {
106
- if([[NSCharacterSet newlineCharacterSet] characterIsMember:[_input->textView.textStorage.string characterAtIndex:i]]) {
107
- NSRange mockRange = NSMakeRange(0, 0);
108
- // can't use detect style because it intentionally doesn't take newlines into consideration
109
- UIColor *bgColor = [_input->textView.textStorage attribute:NSBackgroundColorAttributeName atIndex:i effectiveRange:&mockRange];
110
- if([self styleCondition:bgColor :NSMakeRange(i, 1)]) {
111
- [self removeAttributes:NSMakeRange(i, 1)];
112
- }
154
+ NSTextStorage *storage = _input->textView.textStorage;
155
+ NSString *string = storage.string;
156
+ NSUInteger length = string.length;
157
+
158
+ if (length == 0)
159
+ return;
160
+
161
+ CFStringInlineBuffer buffer;
162
+ CFStringInitInlineBuffer((CFStringRef)string, &buffer,
163
+ CFRangeMake(0, length));
164
+
165
+ for (NSUInteger index = 0; index < length; index++) {
166
+ unichar ch = CFStringGetCharacterFromInlineBuffer(&buffer, index);
167
+ // check new lines only
168
+ if (![[NSCharacterSet newlineCharacterSet] characterIsMember:ch])
169
+ continue;
170
+
171
+ NSRange newlineRange = NSMakeRange(index, 1);
172
+
173
+ UIColor *bgColor = [storage attribute:NSBackgroundColorAttributeName
174
+ atIndex:index
175
+ effectiveRange:nil];
176
+
177
+ if (bgColor != nil && [self styleCondition:bgColor range:newlineRange]) {
178
+ [self removeAttributes:newlineRange];
113
179
  }
114
180
  }
115
181
  }
116
182
 
117
- // emojis don't retain monospace font attribute so we check for the background color if there is no mention
118
- - (BOOL)styleCondition:(id _Nullable)value :(NSRange)range {
183
+ // emojis don't retain monospace font attribute so we check for the background
184
+ // color if there is no mention
185
+ - (BOOL)styleCondition:(id _Nullable)value range:(NSRange)range {
119
186
  UIColor *bgColor = (UIColor *)value;
120
187
  MentionStyle *mStyle = _input->stylesDict[@([MentionStyle getStyleType])];
121
188
  return bgColor != nullptr && mStyle != nullptr && ![mStyle detectStyle:range];
122
189
  }
123
190
 
124
191
  - (BOOL)detectStyle:(NSRange)range {
125
- if(range.length >= 1) {
192
+ if (range.length >= 1) {
126
193
  // detect only in non-newline characters
127
- NSArray *nonNewlineRanges = [ParagraphsUtils getNonNewlineRangesIn:_input->textView range:range];
128
- if(nonNewlineRanges.count == 0) {
194
+ NSArray *nonNewlineRanges =
195
+ [ParagraphsUtils getNonNewlineRangesIn:_input->textView range:range];
196
+ if (nonNewlineRanges.count == 0) {
129
197
  return NO;
130
198
  }
131
-
199
+
132
200
  BOOL detected = YES;
133
- for(NSValue *value in nonNewlineRanges) {
201
+ for (NSValue *value in nonNewlineRanges) {
134
202
  NSRange currentRange = [value rangeValue];
135
- BOOL currentDetected = [OccurenceUtils detect:NSBackgroundColorAttributeName withInput:_input inRange:currentRange
136
- withCondition: ^BOOL(id _Nullable value, NSRange range) {
137
- return [self styleCondition:value :range];
138
- }
139
- ];
203
+ BOOL currentDetected =
204
+ [OccurenceUtils detect:NSBackgroundColorAttributeName
205
+ withInput:_input
206
+ inRange:currentRange
207
+ withCondition:^BOOL(id _Nullable value, NSRange range) {
208
+ return [self styleCondition:value range:range];
209
+ }];
140
210
  detected = detected && currentDetected;
141
211
  }
142
-
212
+
143
213
  return detected;
144
214
  } else {
145
- return [OccurenceUtils detect:NSBackgroundColorAttributeName withInput:_input atIndex:range.location checkPrevious:NO
146
- withCondition:^BOOL(id _Nullable value, NSRange range) {
147
- return [self styleCondition:value :range];
148
- }
149
- ];
215
+ return [OccurenceUtils detect:NSBackgroundColorAttributeName
216
+ withInput:_input
217
+ atIndex:range.location
218
+ checkPrevious:NO
219
+ withCondition:^BOOL(id _Nullable value, NSRange range) {
220
+ return [self styleCondition:value range:range];
221
+ }];
150
222
  }
151
223
  }
152
224
 
153
225
  - (BOOL)anyOccurence:(NSRange)range {
154
- return [OccurenceUtils any:NSBackgroundColorAttributeName withInput:_input inRange:range
155
- withCondition:^BOOL(id _Nullable value, NSRange range) {
156
- return [self styleCondition:value :range];
157
- }
158
- ];
226
+ return [OccurenceUtils any:NSBackgroundColorAttributeName
227
+ withInput:_input
228
+ inRange:range
229
+ withCondition:^BOOL(id _Nullable value, NSRange range) {
230
+ return [self styleCondition:value range:range];
231
+ }];
159
232
  }
160
233
 
161
234
  - (NSArray<StylePair *> *_Nullable)findAllOccurences:(NSRange)range {
162
- return [OccurenceUtils all:NSBackgroundColorAttributeName withInput:_input inRange:range
163
- withCondition:^BOOL(id _Nullable value, NSRange range) {
164
- return [self styleCondition:value :range];
165
- }
166
- ];
235
+ return [OccurenceUtils all:NSBackgroundColorAttributeName
236
+ withInput:_input
237
+ inRange:range
238
+ withCondition:^BOOL(id _Nullable value, NSRange range) {
239
+ return [self styleCondition:value range:range];
240
+ }];
167
241
  }
168
242
 
169
243
  @end
@@ -1,15 +1,19 @@
1
- #import "StyleHeaders.h"
2
1
  #import "EnrichedTextInputView.h"
3
2
  #import "FontExtension.h"
4
3
  #import "OccurenceUtils.h"
4
+ #import "StyleHeaders.h"
5
5
 
6
6
  @implementation ItalicStyle {
7
7
  EnrichedTextInputView *_input;
8
8
  }
9
9
 
10
- + (StyleType)getStyleType { return Italic; }
10
+ + (StyleType)getStyleType {
11
+ return Italic;
12
+ }
11
13
 
12
- + (BOOL)isParagraphStyle { return NO; }
14
+ + (BOOL)isParagraphStyle {
15
+ return NO;
16
+ }
13
17
 
14
18
  - (instancetype)initWithInput:(id)input {
15
19
  self = [super init];
@@ -19,31 +23,39 @@
19
23
 
20
24
  - (void)applyStyle:(NSRange)range {
21
25
  BOOL isStylePresent = [self detectStyle:range];
22
- if(range.length >= 1) {
23
- isStylePresent ? [self removeAttributes:range] : [self addAttributes:range];
26
+ if (range.length >= 1) {
27
+ isStylePresent ? [self removeAttributes:range]
28
+ : [self addAttributes:range withTypingAttr:YES];
24
29
  } else {
25
30
  isStylePresent ? [self removeTypingAttributes] : [self addTypingAttributes];
26
31
  }
27
32
  }
28
33
 
29
- - (void)addAttributes:(NSRange)range {
34
+ - (void)addAttributes:(NSRange)range withTypingAttr:(BOOL)withTypingAttr {
30
35
  [_input->textView.textStorage beginEditing];
31
- [_input->textView.textStorage enumerateAttribute:NSFontAttributeName inRange:range options:0
32
- usingBlock:^(id _Nullable value, NSRange range, BOOL * _Nonnull stop) {
33
- UIFont *font = (UIFont *)value;
34
- if(font != nullptr) {
35
- UIFont *newFont = [font setItalic];
36
- [_input->textView.textStorage addAttribute:NSFontAttributeName value:newFont range:range];
37
- }
38
- }
39
- ];
36
+ [_input->textView.textStorage
37
+ enumerateAttribute:NSFontAttributeName
38
+ inRange:range
39
+ options:0
40
+ usingBlock:^(id _Nullable value, NSRange range,
41
+ BOOL *_Nonnull stop) {
42
+ UIFont *font = (UIFont *)value;
43
+ if (font != nullptr) {
44
+ UIFont *newFont = [font setItalic];
45
+ [_input->textView.textStorage addAttribute:NSFontAttributeName
46
+ value:newFont
47
+ range:range];
48
+ }
49
+ }];
40
50
  [_input->textView.textStorage endEditing];
41
51
  }
42
52
 
43
53
  - (void)addTypingAttributes {
44
- UIFont *currentFontAttr = (UIFont *)_input->textView.typingAttributes[NSFontAttributeName];
45
- if(currentFontAttr != nullptr) {
46
- NSMutableDictionary *newTypingAttrs = [_input->textView.typingAttributes mutableCopy];
54
+ UIFont *currentFontAttr =
55
+ (UIFont *)_input->textView.typingAttributes[NSFontAttributeName];
56
+ if (currentFontAttr != nullptr) {
57
+ NSMutableDictionary *newTypingAttrs =
58
+ [_input->textView.typingAttributes mutableCopy];
47
59
  newTypingAttrs[NSFontAttributeName] = [currentFontAttr setItalic];
48
60
  _input->textView.typingAttributes = newTypingAttrs;
49
61
  }
@@ -51,62 +63,74 @@
51
63
 
52
64
  - (void)removeAttributes:(NSRange)range {
53
65
  [_input->textView.textStorage beginEditing];
54
- [_input->textView.textStorage enumerateAttribute:NSFontAttributeName inRange:range options:0
55
- usingBlock:^(id _Nullable value, NSRange range, BOOL * _Nonnull stop) {
56
- UIFont *font = (UIFont *)value;
57
- if(font != nullptr) {
58
- UIFont *newFont = [font removeItalic];
59
- [_input->textView.textStorage addAttribute:NSFontAttributeName value:newFont range:range];
60
- }
61
- }
62
- ];
66
+ [_input->textView.textStorage
67
+ enumerateAttribute:NSFontAttributeName
68
+ inRange:range
69
+ options:0
70
+ usingBlock:^(id _Nullable value, NSRange range,
71
+ BOOL *_Nonnull stop) {
72
+ UIFont *font = (UIFont *)value;
73
+ if (font != nullptr) {
74
+ UIFont *newFont = [font removeItalic];
75
+ [_input->textView.textStorage addAttribute:NSFontAttributeName
76
+ value:newFont
77
+ range:range];
78
+ }
79
+ }];
63
80
  [_input->textView.textStorage endEditing];
64
81
  }
65
82
 
66
83
  - (void)removeTypingAttributes {
67
- UIFont *currentFontAttr = (UIFont *)_input->textView.typingAttributes[NSFontAttributeName];
68
- if(currentFontAttr != nullptr) {
69
- NSMutableDictionary *newTypingAttrs = [_input->textView.typingAttributes mutableCopy];
84
+ UIFont *currentFontAttr =
85
+ (UIFont *)_input->textView.typingAttributes[NSFontAttributeName];
86
+ if (currentFontAttr != nullptr) {
87
+ NSMutableDictionary *newTypingAttrs =
88
+ [_input->textView.typingAttributes mutableCopy];
70
89
  newTypingAttrs[NSFontAttributeName] = [currentFontAttr removeItalic];
71
90
  _input->textView.typingAttributes = newTypingAttrs;
72
91
  }
73
92
  }
74
93
 
75
- - (BOOL)styleCondition:(id _Nullable)value :(NSRange)range {
94
+ - (BOOL)styleCondition:(id _Nullable)value range:(NSRange)range {
76
95
  UIFont *font = (UIFont *)value;
77
96
  return font != nullptr && [font isItalic];
78
97
  }
79
98
 
80
99
  - (BOOL)detectStyle:(NSRange)range {
81
- if(range.length >= 1) {
82
- return [OccurenceUtils detect:NSFontAttributeName withInput:_input inRange:range
83
- withCondition: ^BOOL(id _Nullable value, NSRange range) {
84
- return [self styleCondition:value :range];
85
- }
86
- ];
100
+ if (range.length >= 1) {
101
+ return [OccurenceUtils detect:NSFontAttributeName
102
+ withInput:_input
103
+ inRange:range
104
+ withCondition:^BOOL(id _Nullable value, NSRange range) {
105
+ return [self styleCondition:value range:range];
106
+ }];
87
107
  } else {
88
- return [OccurenceUtils detect:NSFontAttributeName withInput:_input atIndex:range.location checkPrevious:NO
89
- withCondition:^BOOL(id _Nullable value, NSRange range) {
90
- return [self styleCondition:value :range];
91
- }
92
- ];
108
+ return [OccurenceUtils detect:NSFontAttributeName
109
+ withInput:_input
110
+ atIndex:range.location
111
+ checkPrevious:NO
112
+ withCondition:^BOOL(id _Nullable value, NSRange range) {
113
+ return [self styleCondition:value range:range];
114
+ }];
93
115
  }
94
116
  }
95
117
 
96
118
  - (BOOL)anyOccurence:(NSRange)range {
97
- return [OccurenceUtils any:NSFontAttributeName withInput:_input inRange:range
98
- withCondition:^BOOL(id _Nullable value, NSRange range) {
99
- return [self styleCondition:value :range];
100
- }
101
- ];
119
+ return [OccurenceUtils any:NSFontAttributeName
120
+ withInput:_input
121
+ inRange:range
122
+ withCondition:^BOOL(id _Nullable value, NSRange range) {
123
+ return [self styleCondition:value range:range];
124
+ }];
102
125
  }
103
126
 
104
127
  - (NSArray<StylePair *> *_Nullable)findAllOccurences:(NSRange)range {
105
- return [OccurenceUtils all:NSFontAttributeName withInput:_input inRange:range
106
- withCondition:^BOOL(id _Nullable value, NSRange range) {
107
- return [self styleCondition:value :range];
108
- }
109
- ];
128
+ return [OccurenceUtils all:NSFontAttributeName
129
+ withInput:_input
130
+ inRange:range
131
+ withCondition:^BOOL(id _Nullable value, NSRange range) {
132
+ return [self styleCondition:value range:range];
133
+ }];
110
134
  }
111
135
 
112
136
  @end