我试图在我的项目中实现SrollView,但是由于某种原因,当我尝试滚动查看其中的所有元素时,它会跳回到ScrollView的顶部。我环顾四周,将flex:1
添加到ScrollView可以解决其他一些问题,但是当我尝试整个ScrollView不在屏幕上时。我尝试将position:'absolute'
添加到ScrollView中,但这只会导致scrollView不再移动
我也尝试过尝试<KeyboardAwareScrollView>
,但是屏幕似乎无法适应输入。
这是我的代码:
import React from "react";
import {
View,
Dimensions,
Platform,
ActivityIndicator,
Alert,
Image,
KeyboardAvoidingView,
TouchableHighlight,
Keyboard
} from "react-native";
import { KeyboardAwareScrollView } from 'react-native-keyboard-aware-scroll-view'
import { Form, Item, Input, Label, Button, Text, Picker } from "native-base";
import * as firebase from "firebase";
import { ScrollView } from "react-native-gesture-handler";
import { LinearGradient, ImagePicker, Permissions } from "expo";
import Modal from "react-native-modal";
import uuid from "uuid";
import axios from "axios";
<View style={{borderBottomLeftRadius:20, borderBottomRightRadius:20, marginTop:20}}>
<TouchableHighlight onPress={this.toggleModal} underlayColor="white">
<Image source={{ uri: this.state.imageUrl }} style={{ width: SCREEN_WIDTH, height: SCREEN_HEIGHT/3, borderRadius: 20, marginBottom:20 }}/>
</TouchableHighlight>
</View>
}
{!this.state.loading ? (
<Button
full
style={{
fontFamily: "nunito",
backgroundColor: 'transparent',
alignSelf: "center",
height: SCREEN_HEIGHT/3,
width: SCREEN_WIDTH
}}
onPress={() => this.alertOptions()}
>
<View style={{flexDirection:'column'}}>
<Text
style={{
fontFamily: "nunito",
color: "black",
fontSize: 30,
textAlign: 'center'
}}
>
{this.state.imageUrl === ""
? "Tap"
: ""}
</Text>
<Text
style={{
fontFamily: "nunito",
color: "black",
fontSize: 30,
textAlign: 'center'
}}
>
{this.state.imageUrl === ""
? "to"
: ""}
</Text>
<Text
style={{
fontFamily: "nunito",
color: "black",
fontSize: 30,
textAlign:'center'
}}
>
{this.state.imageUrl === ""
? "Upload Photo"
: ""}
</Text>
</View>
</Button>
) : (
<Text style={{color:'white', textAlign:'center', fontSize: 40, marginTop: 25}}>Loading...Please Wait</Text>
)}
</View>
<View>
<ScrollView showsVerticalScrollIndicator={false} style={{ borderTopRightRadius: -20, borderTopLeftRadius: -20, backgroundColor:"#a2b6d8",}}>
<Text
style={{
fontSize: 28,
color: "#404040",
fontWeight: "700",
marginLeft: 12,
marginBottom: 10,
marginTop: 20,
textAlign: "center"
}}
>
Enter your details below
</Text>
<Form>
<Item stackedLabel rounded>
<Label style={{ fontFamily: "nunito" }}>
Address (Street, City)<Text style={{ color: "red", marginLeft: 10 }}>*</Text>
</Label>
<Input
placeholderTextColor="#9e9e9e"
placeholder="Required"
onChangeText={e => this.setState({ address: e })}
style={{ fontFamily: "nunito" }}
/>
</Item>
<Item stackedLabel>
<Label style={{ fontFamily: "nunito" }}>
Name
<Text style={{ color: "red", marginLeft: 10 }}>*</Text>
</Label>
<Input
placeholderTextColor="#9e9e9e"
placeholder="Required"
onChangeText={e => this.setState({ name: e })}
style={{ fontFamily: "nunito" }}
/>
</Item>
<Item stackedLabel>
<Label style={{ fontFamily: "nunito" }}>
Contractor{" "}
<Text style={{ color: "red", marginLeft: 10 }}>*</Text>
</Label>
<Input
placeholderTextColor="#9e9e9e"
placeholder="Required"
onChangeText={e => this.setState({ contractor: e })}
style={{ fontFamily: "nunito" }}
/>
</Item>
<Item stackedLabel>
<Label style={{ fontFamily: "nunito" }}>
Zip
<Text style={{ color: "red", marginLeft: 10 }}>*</Text>
</Label>
<Input
placeholderTextColor="#9e9e9e"
placeholder="Required"
onChangeText={e => this.setState({ zip: e })}
style={{ fontFamily: "nunito" }}
/>
</Item>
<Item stackedLabel>
<Label style={{ fontFamily: "nunito" }}>
Type of work performed
<Text style={{ color: "red", marginLeft: 10 }}>*</Text>
</Label>
<Input
placeholderTextColor="#9e9e9e"
placeholder="Required"
onChangeText={e => this.setState({ performed: e })}
style={{ fontFamily: "nunito" }}
/>
</Item>
</Form>
<View
style={{
flexDirection: "row",
justifyContent: "center",
alignItems: "center",
marginTop: 20,
marginBottom: 10
}}
>
</View>
<View
style={{
justifyContent:'space-around',
marginLeft: 15,
flexDirection:'row'
}}
>
{!this.state.loader ? (
<Button
full
style={{
fontFamily: "nunito",
backgroundColor: "#f3d95c",
width: SCREEN_WIDTH/3,
borderRadius:50,
shadowColor: "#918236",
shadowOffset: {
width: 0,
height: 0,
},
shadowOpacity: 0.8,
shadowRadius: 4,
// alignSelf: "center",
}}
onPress={() => this.add()}
>
<Text
style={{
fontFamily: "nunito",
color: "black",
fontSize: 22
}}
>
SEND
</Text>
</Button>
) : (
<ActivityIndicator size="large" color="#f3d95c" />
)}
<Button
onPress={() => this.logout()}
style={{ alignSelf: "center", marginBottom: 20, backgroundColor:'red', borderRadius:50 }}
>
<Text style={{fontSize:18}}>Logout</Text>
</Button>
</View>
</ScrollView>
</View>
答案 0 :(得分:1)
替换文件的内容。
EnterDetails.js
import React from "react";
import {
View,
Dimensions,
Platform,
ActivityIndicator,
Alert,
Image,
KeyboardAvoidingView,
TouchableHighlight,
TouchableWithoutFeedback,
Keyboard,
ScrollView
} from "react-native";
import { KeyboardAwareScrollView } from "react-native-keyboard-aware-scroll-view";
import { Form, Item, Input, Label, Button, Text, Picker } from "native-base";
import * as firebase from "firebase";
import { LinearGradient, ImagePicker, Permissions } from "expo";
import Modal from "react-native-modal";
import uuid from "uuid";
import axios from "axios";
const SCREEN_WIDTH = Dimensions.get("window").width;
const SCREEN_HEIGHT = Dimensions.get("window").height;
export default class EnterDetails extends React.Component {
constructor(props) {
super(props);
this.state = {
loader: false,
loading: false,
address: "",
name: "",
contractor: "",
zip: "",
email: "frank.gully2800@gmail.com",
// userEmail: firebase.auth().currentUser.email,
imageUrl: "",
performed: ""
};
}
state = {
isModalVisible: false
};
toggleModal = () => {
this.setState({ isModalVisible: !this.state.isModalVisible });
};
onValueChange(value) {
this.setState({
selected: value
});
}
imagePicker = () => {
Permissions.askAsync(Permissions.CAMERA_ROLL);
ImagePicker.launchImageLibraryAsync({
allowsEditing: false,
base64: true
}).then(async result => {
const blob = await new Promise((resolve, reject) => {
const xhr = new XMLHttpRequest();
xhr.onload = function() {
resolve(xhr.response);
};
xhr.onerror = function(e) {
reject(new TypeError("Network request failed"));
};
xhr.responseType = "blob";
xhr.open("GET", result.uri, true);
xhr.send(null);
});
const ref = firebase
.storage()
.ref()
.child(uuid.v4());
const snapshot = await ref.put(blob);
blob.close();
let imageUrl = await snapshot.ref.getDownloadURL();
this.setState({ imageUrl: imageUrl, loading: false });
});
};
cameraUsage = () => {
this.setState({ loading: true });
Permissions.askAsync(Permissions.CAMERA);
ImagePicker.launchCameraAsync({
allowsEditing: false,
base64: true
}).then(async result => {
const blob = await new Promise((resolve, reject) => {
const xhr = new XMLHttpRequest();
xhr.onload = function() {
resolve(xhr.response);
};
xhr.onerror = function(e) {
reject(new TypeError("Network request failed"));
};
xhr.responseType = "blob";
xhr.open("GET", result.uri, true);
xhr.send(null);
});
const ref = firebase
.storage()
.ref()
.child(uuid.v4());
const snapshot = await ref.put(blob);
blob.close();
let imageUrl = await snapshot.ref.getDownloadURL();
this.setState({ imageUrl: imageUrl, loading: false });
});
};
add = () => {
if (
this.state.zip !== "" &&
this.state.address !== "" &&
this.state.name !== "" &&
this.state.contractor !== "" &&
this.state.email !== "" &&
this.state.imageUrl !== "" &&
this.state.performed !== ""
) {
const {
name,
imageUrl,
contractor,
address,
email,
zip,
performed
} = this.state;
axios
.post(
"https://us-central1-cccproject-2b2f6.cloudfunctions.net/sendMailToUser",
{
zip: zip,
name: name,
imageUrl: imageUrl,
address: address,
email: email,
contractor: contractor,
performed: performed,
userEmail: this.state.userEmail
}
)
.then(response => {
Alert.alert("Details Sent");
})
.catch(error => {});
} else {
Alert.alert("Please Complete The form");
}
};
alertOptions = () => {
Alert.alert(
"Photo Options",
"Choose how you upload your photo",
[
{ text: "Camera", onPress: () => this.cameraUsage() },
{
text: "Image Library",
onPress: () => this.imagePicker()
},
{
text: "Cancel",
onPress: () => console.log("Day sayd no :("),
style: "cancel"
}
],
{ cancelable: false }
);
};
logout = () => {
firebase
.auth()
.signOut()
.then(s => {
this.props.navigation.navigate("Login");
})
.catch(e => {});
};
render() {
return (
<View style={{ flex: 1 }}>
<View
style={{
width: SCREEN_WIDTH,
height: SCREEN_HEIGHT / 3,
alignSelf: "center",
marginTop: 0,
backgroundColor: "red",
borderBottomLeftRadius: 20,
borderBottomRightRadius: 20
}}
>
{this.state.imageUrl === "" ? null : (
<View
style={{
borderBottomLeftRadius: 20,
borderBottomRightRadius: 20,
marginTop: 20
}}
>
<TouchableHighlight
onPress={this.toggleModal}
underlayColor="white"
>
<Image
source={{ uri: this.state.imageUrl }}
style={{
width: SCREEN_WIDTH,
height: SCREEN_HEIGHT / 3,
borderRadius: 20,
marginBottom: 20
}}
/>
</TouchableHighlight>
</View>
)}
{!this.state.loading ? (
<Button
full
style={{
fontFamily: "nunito",
backgroundColor: "transparent",
alignSelf: "center",
height: SCREEN_HEIGHT / 3,
width: SCREEN_WIDTH
}}
onPress={() => this.alertOptions()}
>
<View style={{ flexDirection: "column" }}>
<Text
style={{
fontFamily: "nunito",
color: "black",
fontSize: 30,
textAlign: "center"
}}
>
{this.state.imageUrl === "" ? "Tap" : ""}
</Text>
<Text
style={{
fontFamily: "nunito",
color: "black",
fontSize: 30,
textAlign: "center"
}}
>
{this.state.imageUrl === "" ? "to" : ""}
</Text>
<Text
style={{
fontFamily: "nunito",
color: "black",
fontSize: 30,
textAlign: "center"
}}
>
{this.state.imageUrl === "" ? "Upload Photo" : ""}
</Text>
</View>
</Button>
) : (
<Text
style={{
color: "white",
textAlign: "center",
fontSize: 40,
marginTop: 25
}}
>
Loading...Please Wait
</Text>
)}
</View>
<View style={{ borderWidth: 2, borderColor: "pink", flex: 1 }}>
<ScrollView
style={{
borderTopRightRadius: -20,
borderTopLeftRadius: -20,
backgroundColor: "#a2b6d8",
position: "relative",
flex: 1
}}
>
<Text
style={{
fontSize: 28,
color: "#404040",
fontWeight: "700",
marginLeft: 12,
marginBottom: 10,
marginTop: 20,
textAlign: "center"
}}
>
Enter your details below
</Text>
<Form>
<Item stackedLabel rounded>
<Label style={{ fontFamily: "nunito" }}>
Address (Street, City)
<Text style={{ color: "red", marginLeft: 10 }}>*</Text>
</Label>
<Input
placeholderTextColor="#9e9e9e"
placeholder="Required"
onChangeText={e => this.setState({ address: e })}
style={{ fontFamily: "nunito" }}
/>
</Item>
<Modal isVisible={this.state.isModalVisible}>
<Image
source={{ uri: this.state.imageUrl }}
style={{
width: SCREEN_WIDTH / 1.1,
height: SCREEN_HEIGHT / 1.1,
justifyContent: "center",
alignSelf: "center",
marginBottom: 0
}}
resizeMode="contain"
/>
<Button
style={{
backgroundColor: "red",
borderBottomRightRadius: 20,
borderBottomLeftRadius: 20,
borderTopLeftRadius: 20,
borderTopRightRadius: 20,
width: SCREEN_WIDTH - 20,
alignSelf: "center",
justifyContent: "center"
}}
onPress={this.toggleModal}
>
<Text style={{ fontFamily: "nunito", textAlign: "center" }}>
Close
</Text>
</Button>
</Modal>
<Item stackedLabel>
<Label style={{ fontFamily: "nunito" }}>
Name
<Text style={{ color: "red", marginLeft: 10 }}>*</Text>
</Label>
<Input
placeholderTextColor="#9e9e9e"
placeholder="Required"
onChangeText={e => this.setState({ name: e })}
style={{ fontFamily: "nunito" }}
/>
</Item>
<Item stackedLabel>
<Label style={{ fontFamily: "nunito" }}>
Contractor{" "}
<Text style={{ color: "red", marginLeft: 10 }}>*</Text>
</Label>
<Input
placeholderTextColor="#9e9e9e"
placeholder="Required"
onChangeText={e => this.setState({ contractor: e })}
style={{ fontFamily: "nunito" }}
/>
</Item>
<Item stackedLabel>
<Label style={{ fontFamily: "nunito" }}>
Zip
<Text style={{ color: "red", marginLeft: 10 }}>*</Text>
</Label>
<Input
placeholderTextColor="#9e9e9e"
placeholder="Required"
onChangeText={e => this.setState({ zip: e })}
style={{ fontFamily: "nunito" }}
/>
</Item>
<Item stackedLabel>
<Label style={{ fontFamily: "nunito" }}>
Type of work performed
<Text style={{ color: "red", marginLeft: 10 }}>*</Text>
</Label>
<Input
placeholderTextColor="#9e9e9e"
placeholder="Required"
onChangeText={e => this.setState({ performed: e })}
style={{ fontFamily: "nunito" }}
/>
</Item>
</Form>
<View
style={{
flexDirection: "row",
justifyContent: "center",
alignItems: "center",
marginTop: 20,
marginBottom: 10
}}
></View>
<View
style={{
justifyContent: "space-around",
marginLeft: 15,
flexDirection: "row"
}}
>
{!this.state.loader ? (
<Button
full
style={{
fontFamily: "nunito",
backgroundColor: "#f3d95c",
width: SCREEN_WIDTH / 3,
borderRadius: 50,
shadowColor: "#918236",
shadowOffset: {
width: 0,
height: 0
},
shadowOpacity: 0.8,
shadowRadius: 4
// alignSelf: "center",
}}
onPress={() => this.add()}
>
<Text
style={{
fontFamily: "nunito",
color: "black",
fontSize: 22
}}
>
SEND
</Text>
</Button>
) : (
<ActivityIndicator size="large" color="#f3d95c" />
)}
<Button
onPress={() => this.logout()}
style={{
alignSelf: "center",
marginBottom: 20,
backgroundColor: "red",
borderRadius: 50
}}
>
<Text style={{ fontSize: 18 }}>Logout</Text>
</Button>
</View>
</ScrollView>
</View>
</View>
);
}
}
App.js
import React from "react";
import { AppLoading } from "expo";
import * as Font from "expo-font";
import { Ionicons } from "@expo/vector-icons";
import Routes from "./Routes";
import { View, StatusBar } from "react-native";
import * as firebase from "firebase";
var firebaseConfig = {//ADD YOUR CREDS HERE};
// Initialize Firebase
firebase.initializeApp(firebaseConfig);
export default class App extends React.Component {
state = {
isReady: true,
isTrue: false
};
async componentWillMount() {
await Font.loadAsync({
...Ionicons.font,
Roboto: require("native-base/Fonts/Roboto.ttf"),
Roboto_medium: require("native-base/Fonts/Roboto_medium.ttf"),
nunito: require("./assets/nunito/Nunito-Regular.ttf"),
MonReg: require("./assets/Montserrat-Regular.ttf"),
MonBold: require("./assets/Montserrat-Bold.ttf")
});
this.setState({ isReady: false });
}
render() {
setTimeout(() => this.setState({ isTrue: true }), 6000);
if (this.state.isReady) {
return <AppLoading />;
}
return (
<View style={{ flex: 1 }}>
<StatusBar backgroundColor="rgba(255,255,255,1)" />
<Routes />
</View>
);
}
}