@expensify/react-native-live-markdown 0.1.74 → 0.1.76
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/ios/MarkdownTextInputDecoratorView.mm +12 -9
- package/ios/RCTBaseTextInputView+Markdown.h +2 -0
- package/ios/RCTBaseTextInputView+Markdown.mm +19 -0
- package/ios/RCTMarkdownUtils.mm +45 -0
- package/ios/RCTTextInputComponentView+Markdown.h +3 -1
- package/ios/RCTTextInputComponentView+Markdown.mm +29 -6
- package/package.json +1 -1
|
@@ -22,6 +22,7 @@
|
|
|
22
22
|
#else
|
|
23
23
|
__weak RCTBaseTextInputView *_textInput;
|
|
24
24
|
#endif /* RCT_NEW_ARCH_ENABLED */
|
|
25
|
+
__weak UIView<RCTBackedTextInputViewProtocol> *_backedTextInputView;
|
|
25
26
|
__weak RCTBackedTextFieldDelegateAdapter *_adapter;
|
|
26
27
|
__weak RCTUITextView *_textView;
|
|
27
28
|
}
|
|
@@ -51,11 +52,11 @@
|
|
|
51
52
|
#ifdef RCT_NEW_ARCH_ENABLED
|
|
52
53
|
react_native_assert([view isKindOfClass:[RCTTextInputComponentView class]] && "Previous sibling component is not an instance of RCTTextInputComponentView.");
|
|
53
54
|
_textInput = (RCTTextInputComponentView *)view;
|
|
54
|
-
|
|
55
|
+
_backedTextInputView = [_textInput valueForKey:@"_backedTextInputView"];
|
|
55
56
|
#else
|
|
56
57
|
react_native_assert([view isKindOfClass:[RCTBaseTextInputView class]] && "Previous sibling component is not an instance of RCTBaseTextInputView.");
|
|
57
58
|
_textInput = (RCTBaseTextInputView *)view;
|
|
58
|
-
|
|
59
|
+
_backedTextInputView = _textInput.backedTextInputView;
|
|
59
60
|
#endif /* RCT_NEW_ARCH_ENABLED */
|
|
60
61
|
|
|
61
62
|
_markdownUtils = [[RCTMarkdownUtils alloc] init];
|
|
@@ -63,12 +64,12 @@
|
|
|
63
64
|
[_markdownUtils setMarkdownStyle:_markdownStyle];
|
|
64
65
|
|
|
65
66
|
[_textInput setMarkdownUtils:_markdownUtils];
|
|
66
|
-
if ([
|
|
67
|
-
RCTUITextField *textField = (RCTUITextField *)
|
|
67
|
+
if ([_backedTextInputView isKindOfClass:[RCTUITextField class]]) {
|
|
68
|
+
RCTUITextField *textField = (RCTUITextField *)_backedTextInputView;
|
|
68
69
|
_adapter = [textField valueForKey:@"textInputDelegateAdapter"];
|
|
69
70
|
[_adapter setMarkdownUtils:_markdownUtils];
|
|
70
|
-
} else if ([
|
|
71
|
-
_textView = (RCTUITextView *)
|
|
71
|
+
} else if ([_backedTextInputView isKindOfClass:[RCTUITextView class]]) {
|
|
72
|
+
_textView = (RCTUITextView *)_backedTextInputView;
|
|
72
73
|
[_textView setMarkdownUtils:_markdownUtils];
|
|
73
74
|
NSLayoutManager *layoutManager = _textView.layoutManager; // switching to TextKit 1 compatibility mode
|
|
74
75
|
layoutManager.allowsNonContiguousLayout = NO; // workaround for onScroll issue
|
|
@@ -100,11 +101,13 @@
|
|
|
100
101
|
{
|
|
101
102
|
_markdownStyle = markdownStyle;
|
|
102
103
|
[_markdownUtils setMarkdownStyle:markdownStyle];
|
|
104
|
+
|
|
105
|
+
// apply new styles
|
|
103
106
|
#ifdef RCT_NEW_ARCH_ENABLED
|
|
104
|
-
[_textInput
|
|
107
|
+
[_textInput _setAttributedString:_backedTextInputView.attributedText];
|
|
105
108
|
#else
|
|
106
|
-
[_textInput setAttributedText:_textInput.attributedText];
|
|
107
|
-
#endif
|
|
109
|
+
[_textInput setAttributedText:_textInput.attributedText];
|
|
110
|
+
#endif /* RCT_NEW_ARCH_ENABLED */
|
|
108
111
|
}
|
|
109
112
|
|
|
110
113
|
@end
|
|
@@ -23,6 +23,16 @@
|
|
|
23
23
|
[self markdown_setAttributedText:attributedText];
|
|
24
24
|
}
|
|
25
25
|
|
|
26
|
+
- (BOOL)markdown_textOf:(NSAttributedString *)newText equals:(NSAttributedString *)oldText
|
|
27
|
+
{
|
|
28
|
+
RCTMarkdownUtils *markdownUtils = [self getMarkdownUtils];
|
|
29
|
+
if (markdownUtils != nil) {
|
|
30
|
+
return [newText isEqualToAttributedString:oldText];
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
return [self markdown_textOf:newText equals:oldText];
|
|
34
|
+
}
|
|
35
|
+
|
|
26
36
|
- (void)markdown_updateLocalData
|
|
27
37
|
{
|
|
28
38
|
RCTMarkdownUtils *markdownUtils = [self getMarkdownUtils];
|
|
@@ -69,6 +79,15 @@
|
|
|
69
79
|
Method swizzledMethod = class_getInstanceMethod(cls, swizzledSelector);
|
|
70
80
|
method_exchangeImplementations(originalMethod, swizzledMethod);
|
|
71
81
|
}
|
|
82
|
+
|
|
83
|
+
{
|
|
84
|
+
// swizzle textOf
|
|
85
|
+
SEL originalSelector = @selector(textOf:equals:);
|
|
86
|
+
SEL swizzledSelector = @selector(markdown_textOf:equals:);
|
|
87
|
+
Method originalMethod = class_getInstanceMethod(cls, originalSelector);
|
|
88
|
+
Method swizzledMethod = class_getInstanceMethod(cls, swizzledSelector);
|
|
89
|
+
method_exchangeImplementations(originalMethod, swizzledMethod);
|
|
90
|
+
}
|
|
72
91
|
});
|
|
73
92
|
}
|
|
74
93
|
|
package/ios/RCTMarkdownUtils.mm
CHANGED
|
@@ -136,6 +136,8 @@
|
|
|
136
136
|
}
|
|
137
137
|
}];
|
|
138
138
|
|
|
139
|
+
RCTApplyBaselineOffset(attributedString);
|
|
140
|
+
|
|
139
141
|
[attributedString endEditing];
|
|
140
142
|
|
|
141
143
|
_prevInputString = inputString;
|
|
@@ -148,4 +150,47 @@
|
|
|
148
150
|
}
|
|
149
151
|
}
|
|
150
152
|
|
|
153
|
+
static void RCTApplyBaselineOffset(NSMutableAttributedString *attributedText)
|
|
154
|
+
{
|
|
155
|
+
__block CGFloat maximumLineHeight = 0;
|
|
156
|
+
|
|
157
|
+
[attributedText enumerateAttribute:NSParagraphStyleAttributeName
|
|
158
|
+
inRange:NSMakeRange(0, attributedText.length)
|
|
159
|
+
options:NSAttributedStringEnumerationLongestEffectiveRangeNotRequired
|
|
160
|
+
usingBlock:^(NSParagraphStyle *paragraphStyle, __unused NSRange range, __unused BOOL *stop) {
|
|
161
|
+
if (!paragraphStyle) {
|
|
162
|
+
return;
|
|
163
|
+
}
|
|
164
|
+
|
|
165
|
+
maximumLineHeight = MAX(paragraphStyle.maximumLineHeight, maximumLineHeight);
|
|
166
|
+
}];
|
|
167
|
+
|
|
168
|
+
if (maximumLineHeight == 0) {
|
|
169
|
+
// `lineHeight` was not specified, nothing to do.
|
|
170
|
+
return;
|
|
171
|
+
}
|
|
172
|
+
|
|
173
|
+
__block CGFloat maximumFontLineHeight = 0;
|
|
174
|
+
|
|
175
|
+
[attributedText enumerateAttribute:NSFontAttributeName
|
|
176
|
+
inRange:NSMakeRange(0, attributedText.length)
|
|
177
|
+
options:NSAttributedStringEnumerationLongestEffectiveRangeNotRequired
|
|
178
|
+
usingBlock:^(UIFont *font, NSRange range, __unused BOOL *stop) {
|
|
179
|
+
if (!font) {
|
|
180
|
+
return;
|
|
181
|
+
}
|
|
182
|
+
|
|
183
|
+
maximumFontLineHeight = MAX(font.lineHeight, maximumFontLineHeight);
|
|
184
|
+
}];
|
|
185
|
+
|
|
186
|
+
if (maximumLineHeight < maximumFontLineHeight) {
|
|
187
|
+
return;
|
|
188
|
+
}
|
|
189
|
+
|
|
190
|
+
CGFloat baseLineOffset = (maximumLineHeight - maximumFontLineHeight) / 2.0;
|
|
191
|
+
[attributedText addAttribute:NSBaselineOffsetAttributeName
|
|
192
|
+
value:@(baseLineOffset)
|
|
193
|
+
range:NSMakeRange(0, attributedText.length)];
|
|
194
|
+
}
|
|
195
|
+
|
|
151
196
|
@end
|
|
@@ -12,7 +12,9 @@ NS_ASSUME_NONNULL_BEGIN
|
|
|
12
12
|
|
|
13
13
|
- (void)markdown__setAttributedString:(NSAttributedString *)attributedString;
|
|
14
14
|
|
|
15
|
-
- (
|
|
15
|
+
- (BOOL)markdown__textOf:(NSAttributedString *)newText equals:(NSAttributedString *)oldText;
|
|
16
|
+
|
|
17
|
+
- (void)_setAttributedString:(NSAttributedString *)attributedString;
|
|
16
18
|
|
|
17
19
|
@end
|
|
18
20
|
|
|
@@ -47,16 +47,39 @@
|
|
|
47
47
|
[self markdown__setAttributedString:attributedString];
|
|
48
48
|
}
|
|
49
49
|
|
|
50
|
+
- (BOOL)markdown__textOf:(NSAttributedString *)newText equals:(NSAttributedString *)oldText
|
|
51
|
+
{
|
|
52
|
+
RCTMarkdownUtils *markdownUtils = [self getMarkdownUtils];
|
|
53
|
+
if (markdownUtils != nil) {
|
|
54
|
+
return [newText isEqualToAttributedString:oldText];
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
return [self markdown__textOf:newText equals:oldText];
|
|
58
|
+
}
|
|
59
|
+
|
|
50
60
|
+ (void)load
|
|
51
61
|
{
|
|
52
62
|
static dispatch_once_t onceToken;
|
|
53
63
|
dispatch_once(&onceToken, ^{
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
64
|
+
{
|
|
65
|
+
// swizzle _setAttributedString
|
|
66
|
+
Class cls = [self class];
|
|
67
|
+
SEL originalSelector = @selector(_setAttributedString:);
|
|
68
|
+
SEL swizzledSelector = @selector(markdown__setAttributedString:);
|
|
69
|
+
Method originalMethod = class_getInstanceMethod(cls, originalSelector);
|
|
70
|
+
Method swizzledMethod = class_getInstanceMethod(cls, swizzledSelector);
|
|
71
|
+
method_exchangeImplementations(originalMethod, swizzledMethod);
|
|
72
|
+
}
|
|
73
|
+
|
|
74
|
+
{
|
|
75
|
+
// swizzle _textOf
|
|
76
|
+
Class cls = [self class];
|
|
77
|
+
SEL originalSelector = @selector(_textOf:equals:);
|
|
78
|
+
SEL swizzledSelector = @selector(markdown__textOf:equals:);
|
|
79
|
+
Method originalMethod = class_getInstanceMethod(cls, originalSelector);
|
|
80
|
+
Method swizzledMethod = class_getInstanceMethod(cls, swizzledSelector);
|
|
81
|
+
method_exchangeImplementations(originalMethod, swizzledMethod);
|
|
82
|
+
}
|
|
60
83
|
});
|
|
61
84
|
}
|
|
62
85
|
|
package/package.json
CHANGED