react native scrollView inside Flatlist header can not scroll - react-native

based on the requirement, I need to design a ScrollView(vertical) inside FlatList(vertical)
here is my layout
<FlatList>
renderHeader = <ScrollView/>
renderData= ...
</FlatList>
My code run normally, but the scrollView can not scroll, can someone help

This is a problem only in android.
add nativeScrollEnabled prop to ScrollView.

Here is your solution, fixing size of each renderItem component, And wrapping this component in ScrollView will fix your problem.
import * as React from 'react';
import { Text, View, StyleSheet, FlatList, ScrollView } from 'react-native';
export default function App() {
return (
<View style={styles.container}>
<FlatList
data={['',"","","",""]} //Your Data Object
ListHeaderComponent={() => {
return <ScrollView style={{height: 100, marginVertical: 20}}>
<View>
<Text>Header</Text>
<Text>Header</Text>
<Text>Headr</Text>
<Text>Header</Text>
<Text>Header</Text>
<Text>Header</Text>
<Text>Header</Text>
<Text>Header</Text>
<Text>Header</Text>
<Text>Header</Text>
</View>
</ScrollView>
}}
renderItem={() => {
return <ScrollView style={{height: 100, marginVertical: 20}}>
<View>
<Text>renderItem</Text>
</View>
</ScrollView>
}}
/>
</View>
);
}
const styles = StyleSheet.create({
container: {
flex: 1,
}
});

Related

How to scroll flat list without touch effect

I am new in react native, I have used FlatList which has ListItem as component:
<FlatList
style={styles.container}
data={items}
renderItem={({ item }) => (
<ListItem
title={item.title}
onPress={() => console.log("this is pressed", item.id)}
)}
/>
)}
keyExtractor={(item) => item.id.toString()}
/>
Everything is working fine only the
Problem is: when user scrolls the view i.e FlatList the point where finger is pressed that component shows touch effect. I want touch effect happened only when that element is pressed not when is scrolled. Is there any way to solve this?
Code for ListItem
import React from "react";
import { View, StyleSheet, TouchableHighlight } from "react-native";
import { AppText } from "./AppText";
import colors from "../config/colors";
import Swipeable from "react-native-gesture-handler/Swipeable";
function ListItem({title,onPress}) {
return (
<Swipeable renderRightActions={renderRightActions}>
<TouchableHighlight onPress={onPress}>
<View style={[{ backgroundColor }, styles.container]}>
<View style={styles.textContainer}>
{title && <AppText style={styles.title}>{title}</AppText>}
</View>
</View>
</TouchableHighlight>
</Swipeable>
);
}
const styles = StyleSheet.create({
container: {
flexDirection: "row",
padding: 10,
},
textContainer: {
marginLeft: 10,
justifyContent: "center",
},
title: {
fontWeight: "900",
},
});
export default ListItem;

Change footer style based on view height in react native

In react native, how would I go about applying a different footer style depending on the height of a particular ScrollView?
Basically, I want to create a sticky footer for a view that isn't the entire height of the phone and, if the ScrollView is larger, I want to add the footer onto the end of the ScrollView.
Hope that makes at least some sense!
Sample below for demonstration.
ThanksSimon
//If the view is larger than the phone height, have the footer at the bottom of the scroll view
<View style={{flex: 1}}>
<Header navigation={this.prop.navigation}
<Scrollview>
<View>
<Text>Content</Text>
</View>
<View>
<Image source={image} style={styles.footerImage} />
</View>
</ScrollView>
</View>
//If the content view is smaller than the phone size, the view needs to be outside the scrollview and use stick styles
<View style={{flex: 1}}>
<Header navigation={this.prop.navigation}
<Scrollview>
<View>
<Text>Content</Text>
</View>
</ScrollView>
<View>
<Image source={image} style={styles.stickyFooter} />
</View>
</View>
const styles = StyleSheet.create({
footerImage: {
width: Dimensions.get('window').width,
maxHeight: 235,
resizeMode: "contain"
},
stickyFooter: {
flex: 1,
position: 'absolute',
left: 0,
top: 0,
width: Dimensions.get('window').width,
height: Dimensions.get('window').height,
},
});
Ciao, you could move the footer position using minHeight on Scrollview css. Something like:
<Scrollview style={styles.scrollview}>
<View>
<Text>Content</Text>
</View>
</ScrollView>
Then in your styles:
const styles = StyleSheet.create({
...
scrollview:{
minHeight: 300 // 300 for example
}
});
In this way, if Scrollview does not contains elements, footer appears after 300. Else, if Scrollview contains elements and his height is greater then 300, footer will be moved down according to Scrollview height.
import React from 'react';
import {
Text,
View,
StyleSheet,
ScrollView,
Dimensions,
Image,
} from 'react-native';
export default function App() {
return (
<View>
<ScrollView>
<View style={styles.body}>
<Text>Body</Text>
</View>
<View style={styles.footer}>
<Text>Footer</Text>
</View>
</ScrollView>
</View>
);
}
const { height } = Dimensions.get('window');
const styles = StyleSheet.create({
body: {
minHeight: height, // This is where the magic happens
backgroundColor: 'blue', // This is just for visual indication
},
footer: {
minHeight: 150,
backgroundColor: 'green' // This is just for visual indication
}
});
Should work for different screen heights.

TouchableOpacity is not working inside ScrollView

I am trying to implement A suggestion box for a text field. While entering input the suggestion box should appear just below to current text field and over the next input filed,
This suggestion should scroll after a maxHeight.
I am have implemented everything just the Touchable is not working inside ScrollView, if I replace ScrollView with simple View Touchable Works but the container will not scroll of course.
How to deal with this?
import React from 'react';
import {
View,
StatusBar,
ScrollView,
TextInput,
Text,
SafeAreaView,
TouchableOpacity,
} from 'react-native';
const TestScreen = () => {
const [val, setVal] = React.useState('');
const [show, setShow] = React.useState(false);
return (
<>
<SafeAreaView style={{flex: 1}}>
<TextInput
placeholder="Text"
value={val}
style={{zIndex: 1}}
onFocus={() => setShow(true)}
onBlur={() => setShow(false)}
onChangeText={t => {
setShow(true);
setVal(t);
}}
/>
<TextInput placeholder="Text" value={val} style={{zIndex: 1}} />
{show && (
<View style={{position: 'absolute', top: 50}}>
<ScrollView
style={{
elevation: 5,
zIndex: 5,
backgroundColor: 'white',
width: 100,
maxHeight: 50,
}}>
<TouchableOpacity onPress={() => setVal('Item1')}>
<Text>Item1</Text>
</TouchableOpacity>
<TouchableOpacity onPress={() => setVal('Item2')}>
<Text>Item2</Text>
</TouchableOpacity>
<TouchableOpacity onPress={() => setVal('Item3')}>
<Text>Item3</Text>
</TouchableOpacity>
</ScrollView>
</View>
)}
</SafeAreaView>
</>
);
};
export default TestScreen;
Please let me know where I am wrong.
So If you are looking for the answer to this problem.
Just remove the onBlur function props from TextField component.
Here you go, you got your own custom textfield suggestion box.
Here the solution code that helped to get this done. I still don't know it is the best idea but It worked for me atleast.
import React from 'react';
import {
View,
StatusBar,
ScrollView,
TextInput,
Text,
SafeAreaView,
TouchableOpacity,
} from 'react-native';
import {Button} from 'native-base';
const TestScreen = () => {
const [val, setVal] = React.useState('');
const [show, setShow] = React.useState(false);
return (
<>
<SafeAreaView style={{flex: 1}}>
<TouchableOpacity
style={{flex: 1}}
activeOpacity={1}
onPress={() => {
if (show) {
setShow(false);
}
}}>
<TextInput
placeholder="Text"
value={val}
style={{zIndex: 1}}
onFocus={() => setShow(true)}
onChangeText={t => {
setShow(true);
setVal(t);
}}
/>
<TextInput placeholder="Text" value={val} style={{zIndex: 1}} />
{show && (
<View
style={{
position: 'absolute',
top: 50,
}}>
<ScrollView
style={{
elevation: 5,
zIndex: 5,
backgroundColor: 'white',
width: 100,
maxHeight: 50,
}}>
<TouchableOpacity
onPress={() => {
setShow(false);
setVal('Item1');
}}>
<Text>Item1</Text>
</TouchableOpacity>
<TouchableOpacity onPress={() => setVal('Item2')}>
<Text>Item2</Text>
</TouchableOpacity>
<TouchableOpacity onPress={() => setVal('Item3')}>
<Text>Item3</Text>
</TouchableOpacity>
<TouchableOpacity onPress={() => setVal('Item4')}>
<Text>Item4</Text>
</TouchableOpacity>
<TouchableOpacity onPress={() => setVal('Item5')}>
<Text>Item5</Text>
</TouchableOpacity>
</ScrollView>
</View>
)}
</TouchableOpacity>
</SafeAreaView>
</>
);
};
export default TestScreen;

How to make button with background image redirect to WebView React Native

I have problem to make button with background image and then redirect to my WebView React Native.
I already have run code to show my web view, and I want before my web view show, its triggered from button click who look like this
Below is the code for my WebView;
import React, { Component } from 'react'
import {
View,StyleSheet,AppRegistry
} from 'react-native'
import {WebView} from 'react-native-webview'
export default class ActivityIndicatorDemo extends Component {
render() {
return (
<View style = {styles.container}>
{/*<WebView
source={{html: '<h1>Hello javaTpoint</h1>'}}
/>*/}
{/* <WebView
source={require("./resources/index.html")}
/>*/}
<WebView
// injectedJavaScript={false}
// javaScriptEnabled={false}
// originWhitelist={['*']}
source = {{ uri:'http://myip/login' }}
/>
</View>
)
}
}
const styles = StyleSheet.create({
container: {
justifyContent: 'center',
flexDirection: 'column',
flex: 1,
}
})
AppRegistry.registerComponent('App', () => ActivityIndicatorDemo)
How I can implement button with background image before my WebView shows?
Here is a simple way to do it.
import React, {useState} from 'react';
import {
View,
ImageBackground,
TouchableOpacity,
Text,
StatusBar,
} from 'react-native';
import WebView from "react-native-webview";
const App = () => {
const [visible, showWebview] = useState(false)
const setVisible = (visible) => {
showWebview(visible);
}
return (
<View
style={{
width:'100%',
height:"100%"
}}
>
{
!visible? <View
style={{
width:'100%',
height:"100%"
}}
> <ImageBackground
source={{uri:"https://images.unsplash.com/photo-1556742031-c6961e8560b0?ixlib=rb-1.2.1&q=85&fm=jpg&crop=entropy&cs=srgb&dl=clay-banks-tgquMvhNLc4-unsplash.jpg"}}
style={{width:"100%",height:"90%",zIndex:999,justifyContent:"center",alignItems:"center"}}
/> <TouchableOpacity
onPress={() => setVisible(true)}
style={{
backgroundColor:"white",
justifyContent:"center",
alignItems:"center",
padding:10,height:"10%"
}}
>
<Text>Show Webview</Text>
</TouchableOpacity> </View> :
<View
style={{
flex:1
}}
>
<TouchableOpacity
onPress={() => setVisible(false)}
style={{
backgroundColor:"red",
padding:10,
justifyContent:'center',
alignItems:'center',
width:"100%"
}}
>
<Text style={{color:'white'}} >Hide Webview</Text>
</TouchableOpacity>
<WebView
scalesPageToFit
originWhitelist={["*"]}
source={{ uri:"https://www.google.com"
}}/>
</View>
}
</View>
);
};
export default App;

Disable TouchableOpacity for nested View

I've a touchable opacity, and I have a few views inside it. I have one specific view that I don't want for it to be clickable. How can I achieve this?
The specific view that you don't want for it to be clickable should be "TouchableOpacity" but have activeOpacity={1} . In this way parent TouchableOpacity will not work and activeOpacity={1} will make it like disable
Complete code
import React, { Component } from "react";
import { TouchableOpacity, View, Text } from "react-native";
export default class App extends Component {
render() {
return (
<View style={{ flex: 1, margin: 50 }}>
<TouchableOpacity
style={{ backgroundColor: "red", width: 250, height: 250 }}
>
<TouchableOpacity
style={{
backgroundColor: "green",
width: 100,
height: 100,
margin: 20,
alignItems: "center",
justifyContent: "center"
}}
activeOpacity={1}
>
<Text>No Click Area</Text>
</TouchableOpacity>
</TouchableOpacity>
</View>
);
}
}
App Preview
Go in that view and add a prop => pointerEvents:none
<View pointerEvents="none" />
Please refer here
I don't know what conditions you're talking about, but if you want to do what you want, you can use the status value. To deactivate a button when displaying a screen, change the status value when rendering the screen, or change it when you press a button. The examples are attached together.
Example
import * as React from 'react';
import { Text, View, StyleSheet,TouchableOpacity } from 'react-native';
import Constants from 'expo-constants';
export default class App extends React.Component {
constructor(props){
super(props);
this.state={
disabled: false
}
}
componentDidMount(){
this.setState({ disabled: true})
}
render() {
return (
<View style={styles.container}>
<Text style={styles.paragraph}>
Change code in the editor and watch it change on your phone! Save to get a shareable url.
</Text>
<TouchableOpacity style={{width:"100%",height:20,alignItems:"center",backgroundColor:"blue"}} onPress={() => alert("touch")} disabled={this.state.disabled}>
<Text>Touch </Text>
</TouchableOpacity>
<TouchableOpacity style={{width:"100%",height:20,alignItems:"center",backgroundColor:"red"}} onPress={() => this.setState({disabled:true})}>
<Text>disabled</Text>
</TouchableOpacity>
</View>
);
}
}
Another way you could do it is to wrap you View which you don't want to be clickable with TouchableWithoutFeedback.
export default class App extends React.Component {
render() {
return (
<View style={{flex: 1, justifyContent: 'center'}}>
<TouchableOpacity style={{backgroundColor: "blue", width: 300, height: 300}}>
<TouchableWithoutFeedback>
<View style={{backgroundColor: "yellow", width: 100, height: 100}}>
<Text>Hello</Text>
</View>
</TouchableWithoutFeedback>
</TouchableOpacity>
</View>
);
}
}
As #AnaGard suggested, the key to having a press free view inside a pressable container is to make a pressable inner view without an onPress value.
Better than using TouchableOpacity is using the Pressable component, which the ReactNative's documentation suggests is more future-proof.
Therefore, an updated answer to this question might be as follows:
<View>
<Pressable
style={{ width: 500, height: 250 }}
onPress={() => onClose()}
>
<Pressable style={{ height: 100, width: 200 }}>
<View>
<Text>Your content here</Text>
</View>
</Pressable>
</Pressable>
</View>
Some references:
Pressable
TouchableOpacity