@@ -598,12 +598,33 @@ export type Props = $ReadOnly<{|
598
598
*/
599
599
onChange ?: ?( e : ChangeEvent ) => mixed ,
600
600
601
+ /**
602
+ * DANGER: this API is not stable and will change in the future.
603
+ *
604
+ * Callback will be called on the main thread and may result in dropped frames.
605
+ * Callback that is called when the text input's text changes.
606
+ *
607
+ * @platform ios
608
+ */
609
+ unstable_onChangeSync ?: ?( e : ChangeEvent ) => mixed ,
610
+
601
611
/**
602
612
* Callback that is called when the text input's text changes.
603
613
* Changed text is passed as an argument to the callback handler.
604
614
*/
605
615
onChangeText ?: ?( text : string ) => mixed ,
606
616
617
+ /**
618
+ * DANGER: this API is not stable and will change in the future.
619
+ *
620
+ * Callback will be called on the main thread and may result in dropped frames.
621
+ * Callback that is called when the text input's text changes.
622
+ * Changed text is passed as an argument to the callback handler.
623
+ *
624
+ * @platform ios
625
+ */
626
+ unstable_onChangeTextSync ?: ?( text : string ) => mixed ,
627
+
607
628
/**
608
629
* Callback that is called when the text input's content size changes.
609
630
* This will be called with
@@ -643,7 +664,7 @@ export type Props = $ReadOnly<{|
643
664
* the typed-in character otherwise including `' '` for space.
644
665
* Fires before `onChange` callbacks.
645
666
*
646
- * Only available in Fabric on iOS.
667
+ * @platform ios
647
668
*/
648
669
unstable_onKeyPressSync ?: ?( e : KeyPressEvent ) => mixed ,
649
670
@@ -1101,6 +1122,26 @@ function InternalTextInput(props: Props): React.Node {
1101
1122
setMostRecentEventCount ( event . nativeEvent . eventCount ) ;
1102
1123
} ;
1103
1124
1125
+ const _onChangeSync = ( event : ChangeEvent ) => {
1126
+ const currentText = event . nativeEvent . text ;
1127
+ props . unstable_onChangeSync && props . unstable_onChangeSync ( event ) ;
1128
+ props . unstable_onChangeTextSync &&
1129
+ props . unstable_onChangeTextSync ( currentText ) ;
1130
+
1131
+ if ( inputRef . current == null ) {
1132
+ // calling `props.onChange` or `props.onChangeText`
1133
+ // may clean up the input itself. Exits here.
1134
+ return ;
1135
+ }
1136
+
1137
+ setLastNativeText ( currentText ) ;
1138
+ // This must happen last, after we call setLastNativeText.
1139
+ // Different ordering can cause bugs when editing AndroidTextInputs
1140
+ // with multiple Fragments.
1141
+ // We must update this so that controlled input updates work.
1142
+ setMostRecentEventCount ( event . nativeEvent . eventCount ) ;
1143
+ } ;
1144
+
1104
1145
const _onSelectionChange = ( event : SelectionChangeEvent ) => {
1105
1146
props . onSelectionChange && props . onSelectionChange ( event ) ;
1106
1147
@@ -1187,6 +1228,10 @@ function InternalTextInput(props: Props): React.Node {
1187
1228
? [ styles . multilineInput , props . style ]
1188
1229
: props . style ;
1189
1230
1231
+ const useOnChangeSync =
1232
+ ( props . unstable_onChangeSync || props . unstable_onChangeTextSync ) &&
1233
+ ! ( props . onChange || props . onChangeText ) ;
1234
+
1190
1235
textInput = (
1191
1236
< RCTTextInputView
1192
1237
ref = { _setNativeRef }
@@ -1201,6 +1246,7 @@ function InternalTextInput(props: Props): React.Node {
1201
1246
onBlur = { _onBlur }
1202
1247
onKeyPressSync = { props . unstable_onKeyPressSync }
1203
1248
onChange = { _onChange }
1249
+ onChangeSync = { useOnChangeSync === true ? _onChangeSync : null }
1204
1250
onContentSizeChange = { props . onContentSizeChange }
1205
1251
onFocus = { _onFocus }
1206
1252
onScroll = { _onScroll }
0 commit comments