UNPKG

react-native-login-screen

Version:

Fully Customizable & Ready to use Login Screen for React Native

148 lines 8.15 kB
import * as React from "react"; import { Image, SafeAreaView, StatusBar, Text, TouchableOpacity, View, LayoutAnimation, } from "react-native"; import TextInput from "react-native-text-input-interactive"; /** * ? Local Imports */ import styles from "./LoginScreen.style"; import SocialButton from "./components/social-button/SocialButton"; import useStateWithCallback from "./helpers/useStateWithCallback"; import emailValidator from "./helpers/emailValidator"; import passwordValidator from "./helpers/passwordValidator"; import Tooltip from "./components/tooltip/Tooltip"; const dummyFunction = () => { }; const LoginScreen = ({ style, dividerStyle, logoImageStyle, loginTextStyle, loginButtonStyle, signupTextStyle, signupStyle, textInputContainerStyle, signupText = "Create an account", disableDivider, logoImageSource, onLoginPress, disableSocialButtons, disablePasswordInput = false, loginButtonText = "Login", onSignupPress, onEmailChange, onPasswordChange, onFacebookPress = dummyFunction, onTwitterPress = dummyFunction, onApplePress = dummyFunction, onDiscordPress = dummyFunction, emailPlaceholder = "Email", passwordPlaceholder = "Password", disableSignup = false, customSocialLoginButtons, customLogo, customTextInputs, textInputChildren, customLoginButton, customSignupButton, customDivider, emailTextInputProps, passwordTextInputProps, disableEmailValidation = false, enablePasswordValidation = false, disableEmailTooltip = false, disablePasswordTooltip = false, emailContentTooltip, passwordContentTooltip, TouchableComponent = TouchableOpacity, onEyePress, children, }) => { const [isPasswordVisible, setPasswordVisible] = React.useState(false); const [email, setEmail] = React.useState(""); const [password, setPassword] = React.useState(""); const [isEmailTooltipVisible, setEmailTooltipVisible] = useStateWithCallback(false); const [isPasswordTooltipVisible, setPasswordTooltipVisible] = useStateWithCallback(false); const handleEmailChange = (text) => { isEmailTooltipVisible && setEmailTooltipVisible(false); setEmail(text); onEmailChange?.(text); }; const handlePasswordChange = (text) => { isPasswordTooltipVisible && setPasswordTooltipVisible(false); setPassword(text); onPasswordChange?.(text); }; const handleEyePress = () => { setPasswordVisible((oldValue) => !oldValue); onEyePress?.(); }; const handleEmailValidation = () => { if (disableEmailValidation) { handlePasswordValidation(); onEmailChange(email); return; } if (emailValidator(email)) { !disableEmailTooltip && setEmailTooltipVisible(false); handlePasswordValidation(); onEmailChange(email); return; } else { LayoutAnimation.spring(); !disableEmailTooltip && setEmailTooltipVisible(true); onEmailChange(email); } }; const handlePasswordValidation = () => { if (isEmailTooltipVisible) { return; } if (!enablePasswordValidation) { onPasswordChange(password); return; } if (enablePasswordValidation && passwordValidator(password)) { !disablePasswordTooltip && setPasswordTooltipVisible(false); onPasswordChange(password); return; } else { LayoutAnimation.spring(); !disableEmailTooltip && setEmailTooltipVisible(false); !disablePasswordTooltip && setPasswordTooltipVisible(true); onPasswordChange(password); } }; const renderLogo = () => customLogo || (<Image resizeMode="contain" source={logoImageSource} style={[styles.logoImageStyle, logoImageStyle]}/>); const renderEmailInput = () => { const tooltipContent = () => emailContentTooltip || (<View style={styles.emailTooltipContainer}> <Text style={styles.emailTooltipTextStyle}> That{" "} <Text style={styles.emailTooltipRedTextStyle}>email address</Text>{" "} doesn't look right </Text> </View>); return (<View style={styles.emailTextInputContainer}> <> {!disableEmailTooltip && isEmailTooltipVisible && (<Tooltip>{tooltipContent()}</Tooltip>)} <TextInput placeholder={emailPlaceholder} onChangeText={handleEmailChange} autoCapitalize="none" onFocus={() => setEmailTooltipVisible(false)} {...emailTextInputProps}/> </> </View>); }; const renderPasswordInput = () => { const eyeIcon = isPasswordVisible ? require("./local-assets/eye.png") : require("./local-assets/eye-off.png"); const renderTooltipContent = () => passwordContentTooltip || (<View style={styles.passwordTooltipContainer}> <Text style={styles.passwordTooltipTextStyle}> Incorrect{" "} <Text style={styles.passwordTooltipRedTextStyle}>password</Text> </Text> </View>); return (!disablePasswordInput && (<View style={styles.passwordTextInputContainer}> {!disablePasswordTooltip && isPasswordTooltipVisible && (<Tooltip>{renderTooltipContent()}</Tooltip>)} <TextInput placeholder={passwordPlaceholder} secureTextEntry={!isPasswordVisible} onChangeText={handlePasswordChange} enableIcon iconImageSource={eyeIcon} autoCapitalize="none" onFocus={() => { setPasswordTooltipVisible(false); }} onIconPress={handleEyePress} {...passwordTextInputProps}/> </View>)); }; const renderTextInputContainer = () => { return (customTextInputs || (<View style={[styles.textInputContainer, textInputContainerStyle]}> {renderEmailInput()} {renderPasswordInput()} {textInputChildren} </View>)); }; const renderLoginButton = () => customLoginButton || (<TouchableComponent style={[styles.loginButtonStyle, loginButtonStyle]} onPress={() => { handleEmailValidation(); onLoginPress?.(); }}> <Text style={[styles.loginTextStyle, loginTextStyle]}> {loginButtonText} </Text> </TouchableComponent>); const renderSignUp = () => customSignupButton || (!disableSignup && (<TouchableComponent style={[styles.signupStyle, signupStyle]} onPress={onSignupPress}> <Text style={[styles.signupTextStyle, signupTextStyle]}> {signupText} </Text> </TouchableComponent>)); const renderDivider = () => customDivider || (!disableDivider && <View style={[styles.dividerStyle, dividerStyle]}/>); const renderDefaultSocialLoginButtons = () => !disableSocialButtons ? (<> <SocialButton text="Continue with Facebook" TouchableComponent={TouchableComponent} textStyle={styles.facebookSocialButtonTextStyle} onPress={onFacebookPress}/> <SocialButton text="Continue with Twitter" style={styles.socialButtonStyle} TouchableComponent={TouchableComponent} textStyle={styles.twitterSocialButtonTextStyle} imageSource={require("./local-assets/twitter.png")} onPress={onTwitterPress}/> <SocialButton text="Continue with Apple" style={styles.socialButtonStyle} TouchableComponent={TouchableComponent} imageSource={require("./local-assets/apple.png")} onPress={onApplePress}/> <SocialButton text="Continue with Discord" style={styles.socialButtonStyle} TouchableComponent={TouchableComponent} textStyle={styles.discordSocialButtonTextStyle} imageSource={require("./local-assets/discord.png")} onPress={onDiscordPress}/> </>) : null; return (<SafeAreaView style={[styles.container, style]}> <StatusBar barStyle="dark-content"/> {renderLogo()} {renderTextInputContainer()} {renderLoginButton()} {renderSignUp()} {renderDivider()} <View style={styles.socialLoginContainer}> {customSocialLoginButtons || renderDefaultSocialLoginButtons()} </View> {children} </SafeAreaView>); }; export default LoginScreen; //# sourceMappingURL=LoginScreen.js.map