Преглед на файлове

Merge pull request #30 from MGT-Limited/25-implementation-state-signupform

25 implementation state signupform
MGTKenYCS преди 1 година
родител
ревизия
c3c277d4c5

+ 213 - 65
component/global/phone_input.tsx

@@ -1,92 +1,240 @@
-import React, { useState } from "react";
+// import React, { useState } from "react";
+// import { View, Text, TextInput, StyleSheet, ViewStyle, StyleProp } from "react-native";
+// import { HandleSignUpFormDataChange } from "../../types/signup";
+// interface PhoneInputProps {
+// 	placeholder: string;
+// 	extendedStyle?: StyleProp<ViewStyle>;
+// 	handleFormDataChange?: HandleSignUpFormDataChange;
+// 	editable?: boolean;
+// }
+
+// const PhoneInput: React.FC<PhoneInputProps> = ({ placeholder, extendedStyle, handleFormDataChange, editable }) => {
+// 	const [error, setError] = useState("");
+// 	const handleTextChange = (text: string) => {
+// 		if (text.length >= 8) {
+// 			setError("");
+// 			handleFormDataChange?.("phone", text);
+// 			handleFormDataChange?.("phoneVerificationStatus", true);
+// 		} else {
+// 			setError("Please enter at least 8 digits");
+// 			handleFormDataChange?.("phone", text);
+// 			handleFormDataChange?.("phoneVerificationStatus", false);
+// 		}
+// 	};
+
+// 	return (
+// 		<View>
+// 			<View style={[styles.inputContainer, extendedStyle]}>
+// 				<Text style={styles.prefix}>+852</Text>
+// 				<View style={styles.horizontalLine} />
+// 				<TextInput
+// 					keyboardType="numeric"
+// 					onChangeText={handleTextChange}
+// 					placeholder={placeholder}
+// 					style={[styles.input]}
+// 					placeholderTextColor="#888888"
+// 					editable={editable}
+// 				/>
+// 			</View>
+// 			{error && <Text style={styles.errorMessage}>{error}</Text>}
+// 		</View>
+// 	);
+// };
+
+// const styles = StyleSheet.create({
+// 	inputContainer: {
+// 		maxWidth: "100%",
+// 		flexDirection: "row",
+// 		alignItems: "center",
+// 		justifyContent: "center",
+// 		borderWidth: 1,
+// 		borderColor: "#bbbbbb",
+// 		borderRadius: 12,
+// 		padding: 20,
+// 	},
+// 	prefix: {
+// 		marginRight: 5,
+// 		fontSize: 16,
+// 	},
+// 	horizontalLine: {
+// 		width: 24,
+// 		borderColor: "#bbbbbb",
+// 		borderWidth: 0.5,
+// 		transform: [{ rotate: "90deg" }],
+// 	},
+// 	input: {
+// 		flex: 1,
+// 		marginLeft: 5,
+// 		fontSize: 16,
+// 	},
+// 	errorMessage: {
+// 		fontSize: 14,
+// 		color: "#ff0033",
+// 		fontWeight: "400",
+// 		marginLeft: 10,
+// 		marginTop: 10,
+// 	},
+// });
+// export default PhoneInput;
+
+// import React, { useState } from "react";
+// import { View, Text, TextInput, StyleSheet, ViewStyle, StyleProp } from "react-native";
+// import { SignUpFormData } from "../../types/signUpFormData";
+
+// interface PhoneInputProps {
+// 	placeholder: string;
+// 	extendedStyle?: StyleProp<ViewStyle>;
+// 	editable?: boolean;
+// 	signUpFormData?: SignUpFormData;
+// 	setSignUpFormData?: (newFormData: Partial<SignUpFormData>) => void;
+// }
+
+// const PhoneInput: React.FC<PhoneInputProps> = ({
+// 	placeholder,
+// 	extendedStyle,
+// 	editable,
+// 	signUpFormData,
+// 	setSignUpFormData,
+// }) => {
+// 	const [error, setError] = useState("");
+
+// 	const handleTextChange = (text: string) => {
+// 		if (text.length >= 8) {
+// 			setError("");
+// 			setSignUpFormData({
+// 				...signUpFormData,
+// 				phone: text,
+// 				phoneVerificationStatus: true,
+// 			});
+// 		} else {
+// 			setError("Please enter at least 8 digits");
+// 			setSignUpFormData({
+// 				...signUpFormData,
+// 				phone: text,
+// 				phoneVerificationStatus: false,
+// 			});
+// 		}
+// 	};
+
+// 	return (
+// 		<View>
+// 			<View style={[styles.inputContainer, extendedStyle]}>
+// 				<Text style={styles.prefix}>+852</Text>
+// 				<View style={styles.horizontalLine} />
+// 				<TextInput
+// 					value={signUpFormData?.phone}
+// 					keyboardType="numeric"
+// 					onChangeText={handleTextChange}
+// 					placeholder={placeholder}
+// 					style={[styles.input]}
+// 					placeholderTextColor="#888888"
+// 					editable={editable}
+// 				/>
+// 			</View>
+// 			{error && <Text style={styles.errorMessage}>{error}</Text>}
+// 		</View>
+// 	);
+// };
+
+// const styles = StyleSheet.create({
+// 	inputContainer: {
+// 		maxWidth: "100%",
+// 		flexDirection: "row",
+// 		alignItems: "center",
+// 		justifyContent: "center",
+// 		borderWidth: 1,
+// 		borderColor: "#bbbbbb",
+// 		borderRadius: 12,
+// 		padding: 20,
+// 	},
+// 	prefix: {
+// 		marginRight: 5,
+// 		fontSize: 16,
+// 	},
+// 	horizontalLine: {
+// 		width: 24,
+// 		borderColor: "#bbbbbb",
+// 		borderWidth: 0.5,
+// 		transform: [{ rotate: "90deg" }],
+// 	},
+// 	input: {
+// 		flex: 1,
+// 		marginLeft: 5,
+// 		fontSize: 16,
+// 	},
+// 	errorMessage: {
+// 		fontSize: 14,
+// 		color: "#ff0033",
+// 		fontWeight: "400",
+// 		marginLeft: 10,
+// 		marginTop: 10,
+// 	},
+// });
+// export default PhoneInput;
+
+import React from "react";
 import { View, Text, TextInput, StyleSheet, ViewStyle, StyleProp } from "react-native";
-import { HandleForgetPasswordFormDataChange, HandleSignUpFormDataChange } from "../../types/signup";
+
 interface PhoneInputProps {
+	value: string;
+	onChangeText: (text: string) => void;
 	placeholder: string;
 	extendedStyle?: StyleProp<ViewStyle>;
-	handleFormDataChange?: HandleSignUpFormDataChange;
-	handleForgetPasswordFormDataChange?: HandleForgetPasswordFormDataChange;
 	editable?: boolean;
 }
 
-const PhoneInput: React.FC<PhoneInputProps> = ({
-	placeholder,
-	extendedStyle,
-	handleFormDataChange,
-	handleForgetPasswordFormDataChange,
-	editable,
-}) => {
-	const [error, setError] = useState("");
-	//by calling <PhoneInput handleFormDataChange={}... />, we use Registration Form Type.
-	//by calling <PhoneInput handleForgetPasswordFormDataChange={}... />, we use Forget-Password Form Type.
-
-	const handleTextChange = (text: string) => {
-		if (text.length >= 8) {
-			setError("");
-			handleFormDataChange?.("phone", text);
-			handleFormDataChange?.("phoneVerificationStatus", true);
-			handleForgetPasswordFormDataChange?.("phone", text);
-			handleForgetPasswordFormDataChange?.("phoneVerificationStatus", true);
-		} else {
-			setError("Please enter at least 8 digits");
-			handleFormDataChange?.("phone", text);
-			handleFormDataChange?.("phoneVerificationStatus", false);
-			handleForgetPasswordFormDataChange?.("phone", text);
-			handleForgetPasswordFormDataChange?.("phoneVerificationStatus", false);
-		}
-	};
-
+const PhoneInput: React.FC<PhoneInputProps> = ({ value, onChangeText, placeholder, extendedStyle, editable }) => {
 	return (
 		<View>
 			<View style={[styles.inputContainer, extendedStyle]}>
 				<Text style={styles.prefix}>+852</Text>
 				<View style={styles.horizontalLine} />
 				<TextInput
+					value={value}
+					onChangeText={onChangeText}
 					keyboardType="numeric"
-					onChangeText={handleTextChange}
 					placeholder={placeholder}
 					style={[styles.input]}
 					placeholderTextColor="#888888"
 					editable={editable}
 				/>
 			</View>
-			{error && <Text style={styles.errorMessage}>{error}</Text>}
 		</View>
 	);
 };
 
 const styles = StyleSheet.create({
-	inputContainer: {
-		maxWidth: "100%",
-		flexDirection: "row",
-		alignItems: "center",
-		justifyContent: "center",
-		borderWidth: 1,
-		borderColor: "#bbbbbb",
-		borderRadius: 12,
-		padding: 20,
-	},
-	prefix: {
-		marginRight: 5,
-		fontSize: 16,
-	},
-	horizontalLine: {
-		width: 24,
-		borderColor: "#bbbbbb",
-		borderWidth: 0.5,
-		transform: [{ rotate: "90deg" }],
-	},
-	input: {
-		flex: 1,
-		marginLeft: 5,
-		fontSize: 16,
-	},
-	errorMessage: {
-		fontSize: 14,
-		color: "#ff0033",
-		fontWeight: "400",
-		marginLeft: 10,
-		marginTop: 10,
-	},
+    inputContainer: {
+        maxWidth: '100%',
+        flexDirection: 'row',
+        alignItems: 'center',
+        justifyContent: 'center',
+        borderWidth: 1,
+        borderColor: '#bbbbbb',
+        borderRadius: 12,
+        padding: 20
+    },
+    prefix: {
+        marginRight: 5,
+        fontSize: 16
+    },
+    horizontalLine: {
+        width: 24,
+        borderColor: '#bbbbbb',
+        borderWidth: 0.5,
+        transform: [{ rotate: '90deg' }]
+    },
+    input: {
+        flex: 1,
+        marginLeft: 5,
+        fontSize: 16
+    },
+    errorMessage: {
+        fontSize: 14,
+        color: '#ff0033',
+        fontWeight: '400',
+        marginLeft: 10,
+        marginTop: 10
+    }
 });
 export default PhoneInput;

+ 97 - 0
component/multiStepForm/formComponent/formPages/basicInformation.tsx

@@ -0,0 +1,97 @@
+import { View, Text, StyleSheet } from "react-native";
+import NormalInput from "../../../global/normal_input";
+import { useState } from "react";
+import DateModal from "../../../global/date_input";
+import NormalButton from "../../../global/normal_button";
+import useSignUpStore from "../../../../providers/signup_form_store";
+
+type basicInformationProps = {
+	goToNextPage: () => void;
+};
+
+const BasicInformation: React.FC<basicInformationProps> = ({ goToNextPage }) => {
+	const { signUpFormData, setSignUpFormData } = useSignUpStore();
+	const [error, setError] = useState("");
+	const handleNext = () => {
+		if (signUpFormData.name === "" || signUpFormData.password === "" || signUpFormData.birthDate === "") {
+			setError("請確保所有資料都已填寫。");
+		} else {
+			setError("");
+			goToNextPage();
+		}
+	};
+
+	const nameFieldPlaceholder = signUpFormData.name ? signUpFormData.name : "姓名";
+
+	return (
+		<>
+			<View style={styles.container}>
+				<Text style={styles.text}>請填妥以下資料</Text>
+				<View
+					style={{
+						display: "flex",
+						flexDirection: "column",
+						gap: 10,
+					}}
+				>
+					<NormalInput
+						value={signUpFormData.name}
+						placeholder={nameFieldPlaceholder}
+						onChangeText={(text) => {
+							setSignUpFormData({ ...signUpFormData, name: text });
+						}}
+					/>
+
+					<NormalInput
+						placeholder="帳戶密碼"
+						onChangeText={(text) => {
+							setSignUpFormData({ ...signUpFormData, password: text });
+						}}
+						secureTextEntry={true}
+					/>
+
+					<View style={{ display: "flex", flexDirection: "row", gap: 10 }}>
+						{/* await YoYo's code review for gender */}
+						<NormalInput
+							placeholder="性別"
+							onChangeText={(t) => console.log(t)}
+							extendedStyle={{ width: "50%" }}
+						/>
+
+						<DateModal
+							placeholder={signUpFormData.birthDate ? signUpFormData.birthDate : "DD/MM/YY"}
+							onDateChange={(date) => {
+								setSignUpFormData({ ...signUpFormData, birthDate: date });
+							}}
+						/>
+					</View>
+					<NormalButton
+						title={<Text style={{ color: "#fff" }}>下一步</Text>}
+						onPress={handleNext}
+						extendedStyle={{}}
+					/>
+				</View>
+				{error && <Text style={styles.errorMessage}>{error}</Text>}
+			</View>
+		</>
+	);
+};
+
+const styles = StyleSheet.create({
+	container: {
+		flex: 1,
+		marginHorizontal: 20,
+	},
+	text: {
+		fontSize: 20,
+		paddingBottom: 10,
+	},
+	errorMessage: {
+		fontSize: 14,
+		color: "#ff0033",
+		fontWeight: "400",
+		marginLeft: 10,
+		marginTop: 10,
+	},
+});
+export default BasicInformation;

+ 29 - 0
component/multiStepForm/multi_step_form.tsx

@@ -0,0 +1,29 @@
+import { View, StyleSheet } from 'react-native';
+import { StatusBar } from 'expo-status-bar';
+import { useEffect } from 'react';
+import useSignUpStore from '../../providers/signup_form_store';
+import Form from '../registrationMultiStepForm/formComponent/form';
+
+const MultiStepForm: React.FC = () => {
+    const { signUpFormData } = useSignUpStore();
+    //logging to check if parent component can successfully receive user input in the multi-step form
+    useEffect(() => {
+        console.log('Current Zustand Store:', signUpFormData);
+    }, [signUpFormData]);
+
+    return (
+        <View style={styles.container}>
+            <Form />
+            <StatusBar style="auto" />
+        </View>
+    );
+};
+
+const styles = StyleSheet.create({
+    container: {
+        flex: 1,
+        backgroundColor: '#FFFFFF'
+    }
+});
+
+export default MultiStepForm;

+ 14 - 50
component/registrationMultiStepForm/formComponent/form.tsx

@@ -5,17 +5,13 @@ import BasicInformation from "./formPages/basicInformation";
 import UberDriver from "./formPages/uberDriver";
 import CarInformation from "./formPages/carInformation";
 import PaginationIndicator from "../../global/PaginationIndicator";
-import { SignUpFormData, SignUpFormDataKey } from "../../../types/signup";
 import CreateWallet from "./formPages/createWallet";
 import FinishSignUp from "./formPages/finishSignUp";
 import LoginPage from "./formPages/loginPage";
 import { KeyboardAwareScrollView } from "react-native-keyboard-aware-scroll-view";
 
-type FormProps = {
-	formData: SignUpFormData;
-	setFormData: React.Dispatch<React.SetStateAction<SignUpFormData>>;
-};
-const Form: React.FC<FormProps> = ({ formData, setFormData }) => {
+type FormProps = {};
+const Form: React.FC<FormProps> = ({}) => {
 	const [screen, setScreen] = useState<number>(0);
 	const FormTitle = [
 		"",
@@ -26,57 +22,20 @@ const Form: React.FC<FormProps> = ({ formData, setFormData }) => {
 		"註冊 - 設立銀包",
 	];
 
-	const handleFormDataChange = <K extends SignUpFormDataKey>(field: K, value: SignUpFormData[K]) => {
-		setFormData((prevFormData) => ({
-			...prevFormData,
-			[field]: value,
-		}));
-	};
-
 	const ScreenDisplay = () => {
 		switch (screen) {
 			case 0:
 				return <LoginPage goToNextPage={goToNextPage} />;
 			case 1:
-				return (
-					<Verification
-						setScreen={setScreen}
-						formData={formData}
-						handleFormDataChange={handleFormDataChange}
-					/>
-				);
+				return <Verification setScreen={setScreen} />;
 			case 2:
-				return (
-					<BasicInformation
-						formData={formData}
-						handleFormDataChange={handleFormDataChange}
-						goToNextPage={goToNextPage}
-					/>
-				);
+				return <BasicInformation goToNextPage={goToNextPage} />;
 			case 3:
-				return (
-					<UberDriver
-						formData={formData}
-						handleFormDataChange={handleFormDataChange}
-						goToNextPage={goToNextPage}
-					/>
-				);
+				return <UberDriver goToNextPage={goToNextPage} />;
 			case 4:
-				return (
-					<CarInformation
-						formData={formData}
-						handleFormDataChange={handleFormDataChange}
-						goToNextPage={goToNextPage}
-					/>
-				);
+				return <CarInformation goToNextPage={goToNextPage} />;
 			case 5:
-				return (
-					<CreateWallet
-						formData={formData}
-						handleFormDataChange={handleFormDataChange}
-						goToNextPage={goToNextPage}
-					/>
-				);
+				return <CreateWallet goToNextPage={goToNextPage} />;
 			case 6:
 				return <FinishSignUp />;
 			default:
@@ -135,7 +94,13 @@ const Form: React.FC<FormProps> = ({ formData, setFormData }) => {
 };
 
 const styles = StyleSheet.create({
-	topContainer: { flex: 1, alignItems: "center", justifyContent: "center", paddingBottom: "20%", paddingTop: "15%" },
+	topContainer: {
+		flex: 1,
+		alignItems: "center",
+		justifyContent: "center",
+		paddingBottom: "20%",
+		paddingTop: "15%",
+	},
 	previouspageAndPaginationWrapper: {
 		display: "flex",
 		width: "100%",
@@ -144,7 +109,6 @@ const styles = StyleSheet.create({
 		alignItems: "center",
 		paddingHorizontal: 25,
 	},
-
 	bottomContainer: { flex: 2.5 },
 	breakline: { width: 24, height: 1, backgroundColor: "#000000", marginVertical: 17 },
 	text: { fontSize: 24, fontWeight: "300" },

+ 27 - 11
component/registrationMultiStepForm/formComponent/formPages/carInformation.tsx

@@ -1,19 +1,22 @@
 import { View, Text, StyleSheet } from "react-native";
-import { SignUpFormData, HandleSignUpFormDataChange } from "../../../../types/signup";
 import NormalInput from "../../../global/normal_input";
 import NormalButton from "../../../global/normal_button";
 import { useState } from "react";
+import useSignUpStore from "../../../../providers/signup_form_store";
 
 type CarInformationProps = {
 	goToNextPage: () => void;
-	handleFormDataChange: HandleSignUpFormDataChange;
-	formData: SignUpFormData;
 };
 
-const CarInformation: React.FC<CarInformationProps> = ({ goToNextPage, handleFormDataChange, formData }) => {
+const CarInformation: React.FC<CarInformationProps> = ({ goToNextPage }) => {
+	const { signUpFormData, setSignUpFormData } = useSignUpStore();
 	const [error, setError] = useState("");
 	const handleNext = () => {
-		if (formData.vehicleModel === "" || formData.vehicleModel === "" || formData.licensePlate === "") {
+		if (
+			signUpFormData.vehicleModel === "" ||
+			signUpFormData.vehicleModel === "" ||
+			signUpFormData.licensePlate === ""
+		) {
 			setError("請確保所有資料都已填寫。");
 		} else {
 			setError("");
@@ -21,6 +24,10 @@ const CarInformation: React.FC<CarInformationProps> = ({ goToNextPage, handleFor
 		}
 	};
 
+	const vehicleTypeFieldPlaceholder = signUpFormData.vehicleType ? signUpFormData.vehicleType : "車輛品牌";
+	const vehicleModelFieldPlaceholder = signUpFormData.vehicleModel ? signUpFormData.vehicleModel : "車輛型號";
+	const licensePlateFieldPlaceholder = signUpFormData.licensePlate ? signUpFormData.licensePlate : "車輛號碼";
+
 	return (
 		<>
 			<View style={styles.container}>
@@ -33,16 +40,25 @@ const CarInformation: React.FC<CarInformationProps> = ({ goToNextPage, handleFor
 					}}
 				>
 					<NormalInput
-						placeholder={"車輛品牌"}
-						onChangeText={(vehicleType) => handleFormDataChange("vehicleType", vehicleType)}
+						value={signUpFormData.vehicleType}
+						placeholder={vehicleTypeFieldPlaceholder}
+						onChangeText={(vehicleType) => {
+							setSignUpFormData({ ...signUpFormData, vehicleType: vehicleType });
+						}}
 					/>
 					<NormalInput
-						placeholder={"車輛型號"}
-						onChangeText={(vehicleModel) => handleFormDataChange("vehicleModel", vehicleModel)}
+						value={signUpFormData.vehicleModel}
+						placeholder={vehicleModelFieldPlaceholder}
+						onChangeText={(vehicleModel) => {
+							setSignUpFormData({ ...signUpFormData, vehicleModel: vehicleModel });
+						}}
 					/>
 					<NormalInput
-						placeholder="車輛號碼"
-						onChangeText={(licensePlate) => handleFormDataChange("licensePlate", licensePlate)}
+						value={signUpFormData.licensePlate}
+						placeholder={licensePlateFieldPlaceholder}
+						onChangeText={(licensePlate) => {
+							setSignUpFormData({ ...signUpFormData, licensePlate: licensePlate });
+						}}
 					/>
 					<NormalButton
 						title={<Text style={{ color: "#fff" }}>下一步</Text>}

+ 15 - 11
component/registrationMultiStepForm/formComponent/formPages/createWallet.tsx

@@ -1,28 +1,27 @@
 import { View, Text, StyleSheet } from "react-native";
-import { SignUpFormData, HandleSignUpFormDataChange } from "../../../../types/signup";
 import NormalInput from "../../../global/normal_input";
 import NormalButton from "../../../global/normal_button";
 import { useState } from "react";
 import SingleSelectButtonGroup from "../../../global/select_button";
+import useSignUpStore from "../../../../providers/signup_form_store";
 
 type CreateWalletProps = {
 	goToNextPage: () => void;
-	handleFormDataChange: HandleSignUpFormDataChange;
-	formData: SignUpFormData;
 };
 const creditCard = "信用卡";
 const weChatAliPay = "微信支付/支付寶";
 
-const CreateWallet: React.FC<CreateWalletProps> = ({ goToNextPage, handleFormDataChange, formData }) => {
+const CreateWallet: React.FC<CreateWalletProps> = ({ goToNextPage }) => {
 	const options = [{ label: creditCard }, { label: weChatAliPay }];
+	const { signUpFormData, setSignUpFormData } = useSignUpStore();
 
 	const handleSelectedChange = (selectedLabel: string) => {
-		handleFormDataChange("paymentMethod", selectedLabel);
+		setSignUpFormData({ ...signUpFormData, paymentMethod: selectedLabel });
 		setError("");
 	};
 
 	const handleNext = () => {
-		if (formData.paymentMethod === "" || formData.email === "" || formData.address === "") {
+		if (signUpFormData.paymentMethod === "" || signUpFormData.email === "" || signUpFormData.address === "") {
 			setError("請確保所有資料都已填寫。");
 		} else {
 			setError("");
@@ -31,11 +30,11 @@ const CreateWallet: React.FC<CreateWalletProps> = ({ goToNextPage, handleFormDat
 	};
 
 	const selectLabelShown = () => {
-		if (formData.paymentMethod == null) {
+		if (signUpFormData.paymentMethod == null) {
 			return null;
-		} else if (formData.paymentMethod == creditCard) {
+		} else if (signUpFormData.paymentMethod == creditCard) {
 			return creditCard;
-		} else if (formData.paymentMethod == weChatAliPay) {
+		} else if (signUpFormData.paymentMethod == weChatAliPay) {
 			return weChatAliPay;
 		}
 	};
@@ -54,12 +53,17 @@ const CreateWallet: React.FC<CreateWalletProps> = ({ goToNextPage, handleFormDat
 				>
 					<NormalInput
 						placeholder={"電子郵件"}
-						onChangeText={(email) => handleFormDataChange("email", email)}
+						onChangeText={(email) => {
+							setSignUpFormData({ ...signUpFormData, email: email });
+						}}
 					/>
 					<NormalInput
 						placeholder="地址"
-						onChangeText={(address) => handleFormDataChange("address", address)}
+						onChangeText={(address) => {
+							setSignUpFormData({ ...signUpFormData, address: address });
+						}}
 					/>
+
 					<SingleSelectButtonGroup
 						options={options}
 						onSelectionChange={handleSelectedChange}

+ 7 - 1
component/registrationMultiStepForm/formComponent/formPages/loginPage.tsx

@@ -3,12 +3,14 @@ import NormalButton from "../../../global/normal_button";
 import Logo from "../../../global/logo";
 import PhoneInput from "../../../global/phone_input";
 import NormalInput from "../../../global/normal_input";
+import { useState } from "react";
 
 type LoginPageProps = {
 	goToNextPage: () => void;
 };
 
 const LoginPage: React.FC<LoginPageProps> = ({ goToNextPage }) => {
+	const [loginPhone, setLoginPhone] = useState(""); //This loginPhone useState is only a placeholder, will be updated in the future
 	return (
 		<>
 			<View style={styles.container}>
@@ -17,8 +19,12 @@ const LoginPage: React.FC<LoginPageProps> = ({ goToNextPage }) => {
 				</View>
 				<View style={styles.bottomContainer}>
 					<PhoneInput
+						value={loginPhone}
+						onChangeText={(t) => {
+							setLoginPhone(t);
+							console.log(loginPhone);
+						}}
 						placeholder="電話號碼"
-						handleFormDataChange={(field, value) => console.log(`${field}: ${value}`)}
 						extendedStyle={{ borderRadius: 12, padding: 20 }}
 					/>
 					<NormalInput

+ 13 - 15
component/registrationMultiStepForm/formComponent/formPages/uberDriver.tsx

@@ -1,48 +1,46 @@
 import { View, Text, StyleSheet } from "react-native";
-import { SignUpFormData, HandleSignUpFormDataChange } from "../../../../types/signup";
 import NormalButton from "../../../global/normal_button";
 import { useState } from "react";
 import SingleSelectButtonGroup from "../../../global/select_button";
+import useSignUpStore from "../../../../providers/signup_form_store";
 
 type UberDriverProps = {
 	goToNextPage: () => void;
-	handleFormDataChange: HandleSignUpFormDataChange;
-	formData: SignUpFormData;
 };
 
-const UberDriver: React.FC<UberDriverProps> = ({ formData, goToNextPage, handleFormDataChange }) => {
+const UberDriver: React.FC<UberDriverProps> = ({ goToNextPage }) => {
+	const { signUpFormData, setSignUpFormData } = useSignUpStore();
 	const [error, setError] = useState("");
+	const options = [{ label: "是(可享有獨家優惠)" }, { label: "否" }];
+
 	const handleNext = () => {
-		if (formData.isUberDriver == undefined) {
+		if (signUpFormData.isUberDriver == undefined) {
 			setError("請確保所有資料都已填寫。");
 		} else {
 			setError("");
 			goToNextPage();
 		}
 	};
-	const handleSelectedChange = (selectedLabel: string) => {
-		handleFormDataChange("isUberDriver", selectedLabel === "是(可享有獨家優惠)" ? true : false);
-		setError("");
-	};
-
 	const selectLabelShown = () => {
-		if (formData.isUberDriver == undefined) {
+		if (signUpFormData.isUberDriver == undefined) {
 			return null;
-		} else if (formData.isUberDriver == true) {
+		} else if (signUpFormData.isUberDriver == true) {
 			return "是(可享有獨家優惠)";
 		} else {
 			return "否";
 		}
 	};
-
-	const options = [{ label: "是(可享有獨家優惠)" }, { label: "否" }];
 	return (
 		<>
 			<View style={styles.container}>
 				<Text style={styles.text}>請問您是Uber Driver嗎?</Text>
 				<SingleSelectButtonGroup
 					options={options}
-					onSelectionChange={handleSelectedChange}
+					onSelectionChange={(label) => {
+						const convertLabelToBoolean =
+							label === "是(可享有獨家優惠)" ? true : label === "否" ? false : undefined;
+						setSignUpFormData({ ...signUpFormData, isUberDriver: convertLabelToBoolean });
+					}}
 					shouldShowRedOutline={error ? true : false}
 					selectedOption={selectLabelShown()}
 				/>

+ 22 - 10
component/registrationMultiStepForm/formComponent/formPages/verification.tsx

@@ -1,33 +1,41 @@
 import { View, Text, StyleSheet, TextInput, Pressable } from "react-native";
-import { useEffect, useState } from "react";
-import { SignUpFormData, HandleSignUpFormDataChange } from "../../../../types/signup";
+import { useState } from "react";
 import PhoneInput from "../../../global/phone_input";
 import NumberInput from "../../../global/number_input";
 import NormalButton from "../../../global/normal_button";
+import useSignUpStore from "../../../../providers/signup_form_store";
 
 type VerificationProps = {
 	setScreen: React.Dispatch<React.SetStateAction<number>>;
-	formData: SignUpFormData;
-	handleFormDataChange: HandleSignUpFormDataChange;
 };
 
-const Verification: React.FC<VerificationProps> = ({ setScreen, formData, handleFormDataChange }) => {
+const Verification: React.FC<VerificationProps> = ({ setScreen }) => {
+	const { signUpFormData, setSignUpFormData } = useSignUpStore();
 	const [error, setError] = useState("");
 	const [otp, setOtp] = useState("");
 	const [canSendOtp, setCanSendOtp] = useState(true);
 	const [lockPhoneInput, setLockPhoneInput] = useState(false);
 
+	const handleSignUpPhoneChange = (phone: string) => {
+		setSignUpFormData({ phone });
+		if (signUpFormData.phone.length + 1 === 8) {
+			setSignUpFormData({ phoneVerificationStatus: true });
+		} else {
+			setSignUpFormData({ phoneVerificationStatus: false });
+		}
+	};
 	const handleVerification = () => {
-		if (formData.phone === "" || otp === "") {
+		if (signUpFormData.phone === "" || otp === "") {
 			setError("請確保所有資料都已填寫。");
+		} else if (signUpFormData.phoneVerificationStatus === false) {
+			setError("請確保電話號碼長度正確");
 		} else {
 			setError("");
 			setScreen((currentScreenNumber) => currentScreenNumber + 1);
 		}
 	};
-
 	const handleSubmitOtp = () => {
-		if (formData.phoneVerificationStatus) {
+		if (signUpFormData.phoneVerificationStatus) {
 			if (canSendOtp) {
 				setCanSendOtp(false);
 				setLockPhoneInput(true);
@@ -56,16 +64,20 @@ const Verification: React.FC<VerificationProps> = ({ setScreen, formData, handle
 		<Text style={{ color: "#fff" }}>發送</Text>
 	);
 
+	const phoneFieldPlaceholder = signUpFormData.phone ? signUpFormData.phone : "輸入電話號碼";
+
 	return (
 		<>
 			<View style={styles.container}>
 				<Text style={styles.text}>請驗證您的電話號碼</Text>
 				<PhoneInput
-					placeholder="輸入電話號碼"
-					handleFormDataChange={handleFormDataChange}
+					value={signUpFormData.phone}
+					onChangeText={handleSignUpPhoneChange}
+					placeholder={phoneFieldPlaceholder}
 					editable={!lockPhoneInput}
 					extendedStyle={{ opacity: !lockPhoneInput ? 1 : 0.5 }}
 				/>
+
 				<View
 					style={{
 						display: "flex",

+ 23 - 3
providers/signup_form_store.tsx

@@ -1,8 +1,28 @@
 import { create } from "zustand";
-import { ISignUpStore } from "../types/signup_store";
+import { SignUpFormState } from "../types/signUpFormData";
 
-const useSignUpStore = create<ISignUpStore>((set) => ({
-    
+const useSignUpStore = create<SignUpFormState>((set) => ({
+	signUpFormData: {
+		phone: "",
+		phoneVerificationStatus: false,
+		name: "",
+		password: "",
+		email: "",
+		birthDate: "",
+		isUberDriver: undefined,
+		vehicleType: "",
+		vehicleModel: "",
+		licensePlate: "",
+		address: "",
+		paymentMethod: "",
+	},
+	setSignUpFormData: (newFormData) =>
+		set((state) => ({
+			signUpFormData: {
+				...state.signUpFormData,
+				...newFormData,
+			},
+		})),
 }));
 
 export default useSignUpStore;

+ 19 - 0
types/signUpFormData.d.ts

@@ -0,0 +1,19 @@
+export interface SignUpFormData {
+	phone: string;
+	phoneVerificationStatus: boolean;
+	name: string;
+	password: string;
+	email: string;
+	birthDate: string;
+	isUberDriver?: boolean | undefined;
+	vehicleType: string;
+	vehicleModel: string;
+	licensePlate: string;
+	address: string;
+	paymentMethod: string;
+}
+
+export interface SignUpFormState {
+	signUpFormData: SignUpFormData;
+	setSignUpFormData: (newFormData: Partial<SignUpFormData>) => void;
+}

+ 19 - 0
types/signUpFormData.ts

@@ -0,0 +1,19 @@
+export interface SignUpFormData {
+	phone: string;
+	phoneVerificationStatus: boolean;
+	name: string;
+	password: string;
+	email: string;
+	birthDate: string;
+	isUberDriver?: boolean | undefined;
+	vehicleType: string;
+	vehicleModel: string;
+	licensePlate: string;
+	address: string;
+	paymentMethod: string;
+}
+
+export interface SignUpFormState {
+	signUpFormData: SignUpFormData;
+	setSignUpFormData: (newFormData: Partial<SignUpFormData>) => void;
+}