Hello,
I am trying to use react-native-screens combine with react-navigation for my app for better performance, however I have a weird problem. Indeed, when I have a new page mounting with a TextInput set on autoFocus, it focused as expected but the keyboard does not show up on the screen.
If I don't put useScreens() it works perfectly, the TextInput is focused and the Keyboard appears.
react-native: 0.59.1;
react-navigation: 3.8.1;
react-native-screens: 1.0.0-alpha.22;
OS: Android;
Device: Real;
Same problem on all platforms and simulators?
I guess you could workaround it by using a ref to the TextInputand calling .focus() but it should work out of the box with autofocus too.
I am seeing this, as well, on Android. iOS is working fine. If I push a screen onto a React Navigation StackNavigator, and autoFocus is set on a TextInput, the TextInput is focused, but the keyboard does not pop up (or maybe it pops up and is immediately dismissed, hard to tell). If I don't call useScreens() on Android, then I have no issue.
react-native-screen: 1.0.0-alpha.22
react-navigation: 3.8.0
Expo: SDK 31
Android: 8.0 / Galaxy S8 (device)
@mifi Indeed it is possible to make a work around with .focus() and DidFocus(); with NavigationEvents, but the user experience is not the same at all since it takes around 0.5-1s to show the keyboard giving the impression that the app is lagging, whereas with autoFocus, the keyboard pop up straight away.
Yea, it seems this project has quite a few issues compared to plain View-based screens that need to resolved. Everything is more complicated in Native code than in JS.
I see the same on my Pixel 2 (Android 9.0).
Bump?
This issue is pretty significant for user experience. I may take care of it later this year if it's not fixed by then.
@Palid any ideas in mind where the problem is and possible fixes?
My idea is that because it's creating a new native view it just doesn't propagate focus event properly on Android. Haven't researched it properly yet, though.
Any updates for this problem? I have this problem in Android.
I have tried to use autoFocus and ref, but it didn't help. What workarounds did you use?
```
componentDidMount() {
this.ref.focus();
}
autoFocus={true}
value={this.props.reflection}
onChange={ e => this.props.onChange('reflection', e) }
/>
```
Any updates for this problem? I have this problem in Android.
I have tried to use autoFocus and ref, but it didn't help. What workarounds did you use?
componentDidMount() { this.ref.focus(); } <TextInput ref={ref => this.ref = ref} autoFocus={true} value={this.props.reflection} onChange={ e => this.props.onChange('reflection', e) } />
Me too ^^^
any workarounds for this?
Same problem here.
I'm using a settimeout in componentdidmount to trigger the focus after some milliseconds, but still not the best because there is a necessary delay.
setTimeout(() => this.ref.focus(), 150)
Remove autoFocus prop on the component or else it won't work.
Looking forward to a better solution if possible.
react-navigation NavigationEvents component seems to also work using the onDidFocus prop, but it feels slower than using the setTimout like above.
<>
<NavigationEvents onDidFocus={() => this.refs.searchbar.focus()} />
<Searchbar
ref="searchbar"
placeholder="Search"
onChangeText={this._handleChangeText}
value={this.state.searchTerms}
/>
</>
Can you try 2.0.0-alpha3? This https://github.com/kmagiera/react-native-screens/pull/152/files should solve the issue.
@ferrannp I had the same problem and can confirm that 2.0.0-alpha.3 fixes this issue.
I confirm that with 2.0.0-alpha3 it works now ! Sorry for answering so late but I had to update all my react-native package to use 2.0.0-alpha3 version.
@AlexandreMaistret its mentioned in reactnavigation docs to install react-native-screens@^1.0.0-alpha.23 so I'm not sure what I have to do to upgrade react-native-screens and why they are recommending this particular version!
Can this be backported to 1.0 as well for people who are still RN < 0.60.....
@mnzaki people with RN < 0.60 can probably use something like patch-package to manually modify and maintain changes while using older version of library.
Same problem here.
I'm using a settimeout in componentdidmount to trigger the focus after some milliseconds, but still not the best because there is a necessary delay.
setTimeout(() => this.ref.focus(), 150)
Remove autoFocus prop on the component or else it won't work.Looking forward to a better solution if possible.
I was able to get this to work using a shortened timer (50ms), thank you to the workaround above.
Platform.OS === "ios" ? this.ref.focus() : setTimeout(() => this.ref.focus(), 50)
I would like to avoid using things like patch-package, too many moving parts for my taste....
Also it is rather straightforward to backport this fix for now: https://github.com/jolocom/react-native-screens/tree/fix_1.0_soft_keyboard
This can be installed using yarn add jolocom/react-native-screens#1.0.0-alpha.24
This branch works for me, and I am wondering if it is possible to PR it and release a 1.0-alpha.24 version? @kmagiera @ferrannp thoughts?
2.0-alpha is compatible with 1.0-alpha in terms of react-navigation integration. You should be safe to upgrade to 2.0 where I believe the issue has been fixed
The problem is with androidx. A lot of projects are still not androidx compatible, and moving to 2.0 forces androidx
I personally am still seeing this issue with 2.0.0-alpha.17 && react-navigation: 4.0.10 on Android devices.
mind preparing a minimal app that demonstrates how the issue can be reproduced @iamgerardm ?
400ms only working for me
Platform.OS === "ios" ? this.ref.focus() : setTimeout(() => this.ref.focus(), 400)
Still not working on :
"react-native-screens": "^2.7.0",
"react-navigation": "^4.3.8",
Had the same issue.
react-native-screens upgrading didn't help.
Solved it by removing autoFocus={true} and setting timeout.
I have a popup as a functional component and using "current.focus()" with Refs like this:
const Popup = ({
placeholder,
autoFocus,
showStatus,
}) => {
const inputRef = useRef(null);
useEffect(() => {
Platform.OS === 'ios'
? inputRef.current.focus()
: setTimeout(() => inputRef.current.focus(), 40);
}, [showStatus]);
return (
<View style={styles.inputContainer}>
<TextInput
style={styles.inputText}
defaultValue={placeholder}
ref={inputRef}
/>
</View>
};
I solved the problem by showing TextInput only in focused screen. In other words, re-show TextInput fire auto focus.
const [isFocused, setIsFocued] = React.useState(true)
const setFocus = React.useCallback(() => {
setIsFocued(true)
}, [])
const setBlur = React.useCallback(() => {
setIsFocued(false)
}, [])
const navi = useNavigation()
React.useEffect(() => {
navi.addListener('focus', setFocus)
navi.addListener('blur', setBlur)
return () => {
navi.removeListener('focus', setFocus)
navi.removeListener('blur', setBlur)
}
}, [])
return (
<View>
{focused && <TextInput autoFocus />}
</View>
)
const _input = useRef();
useEffect(() => {
setTimeout(() => {
_input.current.input.focus();
}, 400);
});
<Input
ref={_input}
placeholder="Say something about this..."
inputStyle={style.inputShareStyle}
inputContainerStyle={{borderBottomWidth: 0}}
placeholderTextColor="#90949c"
/>
make sure in android you removed autofocus
For anyone looking for some typescript implementation
const MyTextInput = ({ autoFocus, ...props }: TextInputProps) => {
const ref = useRef<TextInput>(null);
useEffect(() => {
autoFocus &&
setTimeout(() => {
if (ref.current) {
ref.current.focus();
}
}, 40);
});
return <TextInput ref={ref} {...props} />;
};
Here it's working with InteractionManager:
useEffect(() => {
if (autoFocus && inputRef.current) {
if (inputRef.current) {
InteractionManager.runAfterInteractions(() => {
inputRef.current?.focus();
});
}
}
}, [autoFocus, inputRef]);
Hello,
I am trying to use react-native-screens combine with react-navigation for my app for better performance, however I have a weird problem. Indeed, when I have a new page mounting with a
TextInputset onautoFocus, it focused as expected but the keyboard does not show up on the screen.If I don't put
useScreens()it works perfectly, the TextInput is focused and the Keyboard appears.react-native: 0.59.1;
react-navigation: 3.8.1;
react-native-screens: 1.0.0-alpha.22;
OS: Android;
Device: Real;
if you are using Visual Studio, go to I/O -> keyboard-> toggle software keyboard. The keyboard should appear. And for it to disappear use this :
import {Keyboard} from 'react-native'
`import {Keyboard} from 'react-native'
`
Most helpful comment
Same problem here.
I'm using a settimeout in componentdidmount to trigger the focus after some milliseconds, but still not the best because there is a necessary delay.
setTimeout(() => this.ref.focus(), 150)Remove autoFocus prop on the component or else it won't work.
Looking forward to a better solution if possible.