React Native: keyboard covers cursor. Some-weird-times - react-native

Why numbers in plain text breaks normal keyboard behaviour? It's so crazy!
I have a hughe text field that overflows screen size.
I tried to make it with just TextInput, but when I overscroll it to the top or to the bottom, app manages this like just touch event and pops up keyboard when it actually do not needed. Sometimes even usual scrolling becomes considered as text selection. This is undesirable behavior.
So, I put TextInput inside ScrollView and that issues goes away, but becomes a weird new one. When I touch some word (only letters characters) at the bottom of the screen, the keyboard pops up and text scrolls up to help me see the cursor above the keyboard. With words it behaviours as I want (photo below).
The problem is here>> But when I point some number, alpha-numeric, or blank row in the bottom of my text, the keyboard appears, but the text doesn't jump up. So I can't see the cursor and must scroll down manually (photo below: see the cursor leaved upon keyboard area).
Why numbers are blocking this stuff?
Environment: React Native 69.6, Expo 46, Android smartphone, Android Studio
My sipmlified code:
import React from "react";
import { StyleSheet, TextInput, ScrollView } from "react-native";
export default function MyScreen() {
return (
<ScrollView
style={{ flex: 1 }}
contentContainerStyle={{
// flex: 1, <--- if uncomment this, I come back to the first issue
paddingHorizontal: 10,
paddingVertical: 5,
}}
>
<TextInput
multiline={true}
style={{ fontSize: 16 }}
value={`Lorem Ipsum...`}
/>
</ScrollView>
);
}
I tried different combinations of KeyboardAvoidingView, KeyboardAwareScrollView, different layouts and Views nestings. KeyboardAvoidingView helps with cursor but it disorders my layouts. I think, the resolving should be simple. How to deal with it?

Related

How do I make an absolut positioned touchable element on top of a FlatList catch only press events and let other events propagate to the FlatList?

I have a FlatList in React Native with fullscreen image and video items (with pagingEnabled). I want to have a short descriptive touchable text floating on top of the FlatList, to open up a view with some information about the image/video when pressed.
To make the user experience nice, I'd like to be able to scroll the FlatList through the touchable text as well. I.e. if the user happen to start their scrolling motion on top of the text, the FlatList would scroll but if it is a simple press event I'd like to open the view with details about the image/video.
No mater what I try I end up with either the text being able to react to the press OR the FlatList being able to scroll. I have tried different configurations with a custom PanResponder and pointerEvents but seem to always end up with a state were one thing does not work. Do you guys have any smart ideas? I am probably just stuck in the wrong train of thought.
This is a simplified view of my component structure:
<View>
<View style={{ position: 'absolute', bottom: 100, zIndex: 10 }}>
<TouchableOpacity onPress={() => console.log('press')}>
<Text>Some Descriptive Text</Text>
</TouchableOpacity>
</View>
<FlatList pagingEnabled horizontal {...otherFlatListProps} />
</View>

React Native Expo How to Hide Status and bar make component take that place

I am not able to fill the status bar area with component. I tried to do it by hiding the status bar using <StatusBar hidden />. But this one leaves a white space there. For example I want to fill the green image the status bar.
TLDR: working project link
On the gist link (you've provided on the comment), I can see that you are using the following structure
<SafeAreaView>
<StatusBar ... />
<ImageBackground ...></ImageBackground>
</SafeAreaView>
If you want to hide the status bar and cover the whole screen with the image you need to change SafeAreaView to just View and also remove StatusBar component.
<View>
<ImageBackground ...></ImageBackground>
</View>
Cause SafeAreaView will dynamically put some padding at the top. So although you've put style={{ height: '100%', width: '100%' }} it will respect the padding of SafeAreaView cause it is the parent component here.
Also at this point, you do not need StatusBar, cause the StatusBas already has an image as background.

How to make possible to deselect text in a Text component in React Native?

I'm trying to make an app with React Native which shows a lot of information to the end user.
It's vital that the user can select/copy/paste the info from and to the app.
The selectable property of Text is quite useful since it uses the native android UI for selecting text.
My only problem is that if you select a part of the text (intentionally or accidentally), you can only deselect if you tap inside the Text component again.
That is, if I touch the screen anywhere else (where any other component would be, even its father), the text keeps being selected.
Take, for example, the "Hello World" in React Native Documentation, and just add the selectable property:
import React from 'react';
import { Text, View } from 'react-native';
export default function YourApp() {
return (
<View style={{ flex: 1, justifyContent: "center", alignItems: "center" }}>
<Text selectable>
Try editing me! 🎉
</Text>
</View>
);
}
If you run it on android, you'll notice that you can indeed select and copy when you double tap (or long tap) as expected. But you won't be able to cancel the selection unless you tap on some part of the text again. If you touch any other part of the screen the selection UI won't go away.
Is there a way to achieve that? There are too many Text components in my app, with varying length and size. When users accidentally select something, a lot feel frustrated tapping away and nothing happening.
In this case I would use a TouchableWithoutFeedback component.
TouchableWithoutFeedback
Example from RN, where alert('Pressed!') is your function to remove selection.
function MyComponent(props) {
return (
<View {...props} style={{ flex: 1, backgroundColor: '#fff' }}>
<Text>My Component</Text>
</View>
);
}
<TouchableWithoutFeedback onPress={() => alert('Pressed!')}>
<MyComponent />
</TouchableWithoutFeedback>;

How to display vertical scroll indicator always in react native scrollview

I am trying to display vertical scroll indicator always. Because I have 4 pages in my screen, But, After loading screen and scroll first page, The vertical scroll indicator is disappearing which is default behaviour of scrollview. So, I have try to show some flashScrollIndicators() But, still it is disappearing.
setScrollView = (scrollView) => {
// NOTE: scrollView will be null when the component is unmounted
this.scrollView = scrollView;
this.scrollView.flashScrollIndicators();
};
render() {
return (
<ScrollView ref={this.setScrollView} style={{ marginTop: 10, flexGrow: 1, flex: 1 }} contentInset={{ bottom: 20 }}>
);
}
Any suggestions, My requirement is I have to display scroll indicator always in my screen.
flashScrollIndicators() will flash the indicator for one or two seconds. You would need to keep calling it to see it (for example with setInterval). But this will make it flash like a Christmas tree, since it will flash every-time it is called, not stay solid.
If what you want the bar to be always solid, then you could use my suggestion for iOS (without native code). Android has the persistentScrollbar prop, which is simple enough to use.

react native flatlist androidTV focus issue

Environment
react: 16.3.1
react-native: 0.55.3
Description
I've implemented a multi dimension list view on React Native with a few horizontal FlatLists . Everything displays correctly. However, when I move my focus all the way to the end of a row, the focus will automatically go to the row below when I try to go right (already at the end of the row).
Is there a solution to prevent this and make sure that focus will stop when it reaches the ends of a flatlist ?
Steps to Reproduce
Render a FlatList vertically with each row being another horizontal FlatList. Scroll to end of a row, try to move RIGHT and focus would go down to the next row.
Expected Behaviour
Expected Behaviour should be none since we're at the ends of the current row.
Actual Behaviour
Focus goes to the next row if at the backend of a row
Note
I've searched the docs and this is a specific issue to firetv/androidtv.
Same issue as issue #20100 but the bug is "closed".
Sample code
import React, {Component} from 'react';
import {View, Text, TouchableOpacity, ScrollView} from 'react-native';
export default class App extends Component {
render() {
const data = [];
for (let i = 0; i < 10; i++)
data.push(i);
return (
<View>
{[1, 2].map(() => (
<ScrollView horizontal style={{height: 210}}>
{data.map(i => (
<TouchableOpacity key={i}>
<View
style={{
backgroundColor: 'grey',
width: 200,
height: 200,
}}
>
<Text style={{fontSize: 60}}>{i}</Text>
</View>
</TouchableOpacity>
))}
</ScrollView>
))}
</View>
);
}
This is not really a (proper) solution, but more of a hack, but it does the job.. I found this out by pure coincidence; if you add a border to the ScrollView, you won't have this problem.. So you can maybe play around with this a bit (e.g. an invisible border).
Currently I have discovered this is not possible for tvOS or android or firetv. Unless I'm mistaken I am assuming there is a low number of people attempting to create connectedTv apps or if they are they have a very very simple interface
you should be able to handle this by setting the last item's nextFocusRight property to null or undefined.