diff options
author | Leon Jiang <35908040+leonyjiang@users.noreply.github.com> | 2020-07-09 10:00:11 -0700 |
---|---|---|
committer | GitHub <noreply@github.com> | 2020-07-09 13:00:11 -0400 |
commit | df4b3f6608423922d0fefd040ab86d49f97bdc9b (patch) | |
tree | c2a9f19b0da21723e93a14c6df41f7f7f5f23084 /src | |
parent | e32241734c8cc258812ac12c7727aaa7f947eed5 (diff) |
[TMA-104] Registration wizard & footer positioning fix (#14)
* Remove KeyboardAvoidingView and add centered prop
* Fix layout to match updated Background component
* Add KeyboardAvoidingView to Login screen
* Fix arrows/wizard position & fix keyboard avoidance effect
Diffstat (limited to 'src')
-rw-r--r-- | src/components/onboarding/Background.tsx | 26 | ||||
-rw-r--r-- | src/screens/Login.tsx | 25 | ||||
-rw-r--r-- | src/screens/Registration.tsx | 315 |
3 files changed, 183 insertions, 183 deletions
diff --git a/src/components/onboarding/Background.tsx b/src/components/onboarding/Background.tsx index 98082022..85675b0d 100644 --- a/src/components/onboarding/Background.tsx +++ b/src/components/onboarding/Background.tsx @@ -5,12 +5,13 @@ import { TouchableWithoutFeedback, Keyboard, ViewProps, - KeyboardAvoidingView, View, - Platform, } from 'react-native'; +import {CenteredView} from '../common'; -interface BackgroundProps extends ViewProps {} +interface BackgroundProps extends ViewProps { + centered?: boolean; +} const Background: React.FC<BackgroundProps> = (props) => { return ( <LinearGradient @@ -19,15 +20,13 @@ const Background: React.FC<BackgroundProps> = (props) => { angle={154.72} angleCenter={{x: 0.5, y: 0.5}} style={styles.container}> - <KeyboardAvoidingView - behavior={Platform.OS === 'ios' ? 'padding' : 'height'} - style={styles.container}> - <TouchableWithoutFeedback accessible={false} onPress={Keyboard.dismiss}> - <View style={[styles.container, styles.view]} {...props}> - {props.children} - </View> - </TouchableWithoutFeedback> - </KeyboardAvoidingView> + <TouchableWithoutFeedback accessible={false} onPress={Keyboard.dismiss}> + {props.centered ? ( + <CenteredView {...props}>{props.children}</CenteredView> + ) : ( + <View {...props}>{props.children}</View> + )} + </TouchableWithoutFeedback> </LinearGradient> ); }; @@ -36,9 +35,6 @@ const styles = StyleSheet.create({ container: { flex: 1, }, - view: { - alignItems: 'center', - }, }); export default Background; diff --git a/src/screens/Login.tsx b/src/screens/Login.tsx index 193ef767..b3b1ab71 100644 --- a/src/screens/Login.tsx +++ b/src/screens/Login.tsx @@ -9,10 +9,12 @@ import { Image, TouchableOpacity, StyleSheet, + KeyboardAvoidingView, + Platform, } from 'react-native'; import {RootStackParamList} from '../routes'; -import {Background, TaggInput, CenteredView} from '../components'; +import {Background, TaggInput} from '../components'; import {usernameRegex, LOGIN_ENDPOINT} from '../constants'; type LoginScreenRouteProp = RouteProp<RootStackParamList, 'Login'>; @@ -204,9 +206,11 @@ const Login: React.FC<LoginProps> = ({navigation}: LoginProps) => { ); return ( - <Background> + <Background centered style={styles.container}> <StatusBar barStyle="light-content" /> - <CenteredView> + <KeyboardAvoidingView + behavior={Platform.OS === 'ios' ? 'padding' : 'height'} + style={styles.keyboardAvoidingView}> <Image source={require('../assets/images/logo.png')} style={styles.logo} @@ -225,7 +229,6 @@ const Login: React.FC<LoginProps> = ({navigation}: LoginProps) => { valid={form.isValidUser} invalidWarning="Username must be at least 6 characters and can only contain letters, numbers, periods, and underscores." attemptedSubmit={form.attemptedSubmit} - width="100%" /> <TaggInput @@ -246,13 +249,21 @@ const Login: React.FC<LoginProps> = ({navigation}: LoginProps) => { /> <ForgotPassword /> <LoginButton /> - <RegistrationPrompt /> - </CenteredView> + </KeyboardAvoidingView> + <RegistrationPrompt /> </Background> ); }; const styles = StyleSheet.create({ + container: { + flex: 1, + justifyContent: 'center', + alignItems: 'center', + }, + keyboardAvoidingView: { + alignItems: 'center', + }, logo: { width: 215, height: 149, @@ -274,7 +285,7 @@ const styles = StyleSheet.create({ alignItems: 'center', backgroundColor: '#fff', borderRadius: 18, - marginBottom: '10%', + marginBottom: '15%', }, startDisabled: { backgroundColor: '#ddd', diff --git a/src/screens/Registration.tsx b/src/screens/Registration.tsx index 52508a76..aaf929ba 100644 --- a/src/screens/Registration.tsx +++ b/src/screens/Registration.tsx @@ -9,6 +9,7 @@ import { Alert, Platform, TouchableOpacity, + KeyboardAvoidingView, } from 'react-native'; import {RootStackParamList} from '../routes'; @@ -18,7 +19,6 @@ import { TaggInput, TermsConditions, Background, - CenteredView, } from '../components'; import { emailRegex, @@ -149,10 +149,12 @@ const Registration: React.FC<RegistrationProps> = ({navigation}) => { */ const handlePasswordUpdate = (password: string) => { let isValidPassword: boolean = passwordRegex.test(password); + let passwordsMatch: boolean = form.password === form.confirm; setForm({ ...form, password, isValidPassword, + passwordsMatch, }); }; @@ -246,146 +248,152 @@ const Registration: React.FC<RegistrationProps> = ({navigation}) => { } }; + const Footer = () => ( + <View style={styles.footer}> + <ArrowButton + direction="backward" + onPress={() => navigation.navigate('Login')} + /> + <TouchableOpacity onPress={handleRegister}> + <ArrowButton + direction="forward" + disabled={ + !( + form.isValidFname && + form.isValidLname && + form.isValidEmail && + form.isValidUsername && + form.isValidPassword && + form.passwordsMatch && + form.tcAccepted + ) + } + onPress={handleRegister} + /> + </TouchableOpacity> + </View> + ); + return ( <Background style={styles.container}> <StatusBar barStyle="light-content" /> - <CenteredView> + <KeyboardAvoidingView + behavior={Platform.OS === 'ios' ? 'padding' : 'height'} + style={styles.container}> <RegistrationWizard style={styles.wizard} step="one" /> - <View style={styles.form}> - <Text style={styles.formHeader}>SIGN UP</Text> - <TaggInput - accessibilityHint="Enter your first name." - accessibilityLabel="First name input field." - placeholder="First Name" - autoCompleteType="name" - textContentType="name" - returnKeyType="next" - onChangeText={handleFnameUpdate} - onSubmitEditing={() => handleFocusChange('lname')} - blurOnSubmit={false} - valid={form.isValidFname} - invalidWarning="First name cannot be empty." - attemptedSubmit={form.attemptedSubmit} - width={280} - /> - <TaggInput - accessibilityHint="Enter your last name." - accessibilityLabel="Last name input field." - placeholder="Last Name" - autoCompleteType="name" - textContentType="name" - returnKeyType="next" - onChangeText={handleLnameUpdate} - onSubmitEditing={() => handleFocusChange('email')} - blurOnSubmit={false} - ref={lnameRef} - valid={form.isValidLname} - invalidWarning="Last name cannot be empty." - attemptedSubmit={form.attemptedSubmit} - width={280} - /> - <TaggInput - accessibilityHint="Enter your email." - accessibilityLabel="Email input field." - placeholder="Email" - autoCompleteType="email" - textContentType="emailAddress" - autoCapitalize="none" - returnKeyType="next" - keyboardType="email-address" - onChangeText={handleEmailUpdate} - onSubmitEditing={() => handleFocusChange('username')} - blurOnSubmit={false} - ref={emailRef} - valid={form.isValidEmail} - invalidWarning={'Please enter a valid email address.'} - attemptedSubmit={form.attemptedSubmit} - width={280} - /> - <TaggInput - accessibilityHint="Enter a username." - accessibilityLabel="Username input field." - placeholder="Username" - autoCompleteType="username" - textContentType="username" - autoCapitalize="none" - returnKeyType="next" - onChangeText={handleUsernameUpdate} - onSubmitEditing={() => handleFocusChange('password')} - blurOnSubmit={false} - ref={usernameRef} - valid={form.isValidUsername} - invalidWarning={ - 'Username must be 6 characters long and contain only alphanumeric characters.' - } - attemptedSubmit={form.attemptedSubmit} - width={280} - /> - <TaggInput - accessibilityHint="Enter a password." - accessibilityLabel="Password input field." - placeholder="Password" - autoCompleteType="password" - textContentType="newPassword" - returnKeyType="next" - onChangeText={handlePasswordUpdate} - onSubmitEditing={() => handleFocusChange('confirm')} - blurOnSubmit={false} - secureTextEntry - ref={passwordRef} - valid={form.isValidPassword} - invalidWarning={ - 'Password must be 8 characters long & contain at least one lowercase, one uppercase, a number, and a special character.' - } - attemptedSubmit={form.attemptedSubmit} - width={280} - /> - <TaggInput - accessibilityHint={'Re-enter your password.'} - accessibilityLabel={'Password confirmation input field.'} - placeholder={'Confirm Password'} - autoCompleteType="password" - textContentType="password" - returnKeyType={form.tcAccepted ? 'go' : 'default'} - onChangeText={handleConfirmUpdate} - onSubmitEditing={handleRegister} - secureTextEntry - ref={confirmRef} - valid={form.passwordsMatch} - invalidWarning={'Passwords must match.'} - attemptedSubmit={form.attemptedSubmit} - width={280} - /> - <TermsConditions - style={styles.tc} - accepted={form.tcAccepted} - onChange={handleTcUpdate} - /> - </View> - <View style={styles.footer}> - <ArrowButton - direction="backward" - onPress={() => navigation.navigate('Login')} - /> - <TouchableOpacity onPress={handleRegister}> - <ArrowButton - direction="forward" - disabled={ - !( - form.isValidFname && - form.isValidLname && - form.isValidEmail && - form.isValidUsername && - form.isValidPassword && - form.passwordsMatch && - form.tcAccepted - ) - } - onPress={handleRegister} - /> - </TouchableOpacity> + <View> + <Text style={styles.formHeader}>Sign up.</Text> </View> - </CenteredView> + <TaggInput + accessibilityHint="Enter your first name." + accessibilityLabel="First name input field." + placeholder="First Name" + autoCompleteType="name" + textContentType="name" + returnKeyType="next" + onChangeText={handleFnameUpdate} + onSubmitEditing={() => handleFocusChange('lname')} + blurOnSubmit={false} + valid={form.isValidFname} + invalidWarning="First name cannot be empty." + attemptedSubmit={form.attemptedSubmit} + width={280} + /> + <TaggInput + accessibilityHint="Enter your last name." + accessibilityLabel="Last name input field." + placeholder="Last Name" + autoCompleteType="name" + textContentType="name" + returnKeyType="next" + onChangeText={handleLnameUpdate} + onSubmitEditing={() => handleFocusChange('email')} + blurOnSubmit={false} + ref={lnameRef} + valid={form.isValidLname} + invalidWarning="Last name cannot be empty." + attemptedSubmit={form.attemptedSubmit} + width={280} + /> + <TaggInput + accessibilityHint="Enter your email." + accessibilityLabel="Email input field." + placeholder="Email" + autoCompleteType="email" + textContentType="emailAddress" + autoCapitalize="none" + returnKeyType="next" + keyboardType="email-address" + onChangeText={handleEmailUpdate} + onSubmitEditing={() => handleFocusChange('username')} + blurOnSubmit={false} + ref={emailRef} + valid={form.isValidEmail} + invalidWarning={'Please enter a valid email address.'} + attemptedSubmit={form.attemptedSubmit} + width={280} + /> + <TaggInput + accessibilityHint="Enter a username." + accessibilityLabel="Username input field." + placeholder="Username" + autoCompleteType="username" + textContentType="username" + autoCapitalize="none" + returnKeyType="next" + onChangeText={handleUsernameUpdate} + onSubmitEditing={() => handleFocusChange('password')} + blurOnSubmit={false} + ref={usernameRef} + valid={form.isValidUsername} + invalidWarning={ + 'Username must beĀ at least 6 characters and contain only alphanumerics.' + } + attemptedSubmit={form.attemptedSubmit} + width={280} + /> + <TaggInput + accessibilityHint="Enter a password." + accessibilityLabel="Password input field." + placeholder="Password" + autoCompleteType="password" + textContentType="newPassword" + returnKeyType="next" + onChangeText={handlePasswordUpdate} + onSubmitEditing={() => handleFocusChange('confirm')} + blurOnSubmit={false} + secureTextEntry + ref={passwordRef} + valid={form.isValidPassword} + invalidWarning={ + 'Password must be at least 8 characters & contain at least one of a-z, A-Z, 0-9, and a special character.' + } + attemptedSubmit={form.attemptedSubmit} + width={280} + /> + <TaggInput + accessibilityHint={'Re-enter your password.'} + accessibilityLabel={'Password confirmation input field.'} + placeholder={'Confirm Password'} + autoCompleteType="password" + textContentType="password" + returnKeyType={form.tcAccepted ? 'go' : 'default'} + onChangeText={handleConfirmUpdate} + onSubmitEditing={handleRegister} + secureTextEntry + ref={confirmRef} + valid={form.passwordsMatch} + invalidWarning={'Passwords must match.'} + attemptedSubmit={form.attemptedSubmit} + width={280} + /> + <TermsConditions + style={styles.tc} + accepted={form.tcAccepted} + onChange={handleTcUpdate} + /> + </KeyboardAvoidingView> + <Footer /> </Background> ); }; @@ -393,53 +401,38 @@ const Registration: React.FC<RegistrationProps> = ({navigation}) => { const styles = StyleSheet.create({ container: { flex: 1, + alignItems: 'center', + justifyContent: 'center', }, wizard: { ...Platform.select({ ios: { - marginBottom: '18%', + bottom: '10%', }, android: { - marginTop: '20%', - marginBottom: '10%', + bottom: '5%', }, }), }, - form: { - alignItems: 'center', - }, formHeader: { color: '#fff', fontSize: 30, fontWeight: '600', - ...Platform.select({ - ios: { - marginBottom: '6%', - }, - android: { - marginBottom: '2%', - }, - }), + marginBottom: '5%', }, tc: { - ...Platform.select({ - ios: { - marginTop: '5%', - marginBottom: '20%', - }, - android: { - marginTop: '7%', - marginBottom: '12%', - }, - }), + marginTop: '5%', }, footer: { width: '100%', flexDirection: 'row', justifyContent: 'space-around', ...Platform.select({ + ios: { + bottom: '20%', + }, android: { - marginBottom: '22%', + bottom: '10%', }, }), }, |