fix: styles
This commit is contained in:
38
src/features/authentication/components/DateOfBirth.tsx
Normal file
38
src/features/authentication/components/DateOfBirth.tsx
Normal file
@@ -0,0 +1,38 @@
|
||||
import { useState, useMemo } from 'react';
|
||||
import { DatePicker } from '@mui/x-date-pickers/DatePicker';
|
||||
import { LocalizationProvider } from '@mui/x-date-pickers';
|
||||
import { AdapterDateFns } from '@mui/x-date-pickers/AdapterDateFns';
|
||||
import { AdapterDateFnsJalali } from '@mui/x-date-pickers/AdapterDateFnsJalali';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
|
||||
export function DateOfBirth() {
|
||||
const { t, i18n } = useTranslation('completionForm');
|
||||
const isFarsi = i18n.language === 'fa' || i18n.language === 'fa-IR';
|
||||
const [birthDate, setBirthDate] = useState<Date | null>(null);
|
||||
|
||||
const Adapter = useMemo(() => {
|
||||
return isFarsi ? AdapterDateFnsJalali : AdapterDateFns;
|
||||
}, [isFarsi]);
|
||||
|
||||
return (
|
||||
<LocalizationProvider dateAdapter={Adapter}>
|
||||
<DatePicker
|
||||
label={t('completion.dateOfBirth')}
|
||||
value={birthDate}
|
||||
onChange={(newValue) => setBirthDate(newValue)}
|
||||
slotProps={{
|
||||
textField: {
|
||||
fullWidth: true,
|
||||
sx: {
|
||||
width: {
|
||||
xs: '100%',
|
||||
sm: '70%',
|
||||
md: '309px',
|
||||
},
|
||||
},
|
||||
},
|
||||
}}
|
||||
/>
|
||||
</LocalizationProvider>
|
||||
);
|
||||
}
|
||||
@@ -56,27 +56,42 @@ export function EmailSection({
|
||||
return (
|
||||
<>
|
||||
<FormGroup>
|
||||
<Box sx={{ display: 'flex', alignItems: 'center', gap: 1, px: 6 }}>
|
||||
<Box
|
||||
sx={{
|
||||
display: 'flex',
|
||||
alignItems: 'center',
|
||||
gap: 1,
|
||||
px: { xs: 2, sm: 6 },
|
||||
}}
|
||||
>
|
||||
<Switch checked={showEmail} onChange={handleToggleEmail} />
|
||||
<Typography sx={{ color: showEmail ? '#2979FF' : 'black' }}>
|
||||
<Typography
|
||||
sx={{ color: showEmail ? 'primary.main' : 'text.primary' }}
|
||||
>
|
||||
{t('completion.determineEmail')}
|
||||
</Typography>
|
||||
</Box>
|
||||
</FormGroup>
|
||||
|
||||
{showEmail && (
|
||||
<Box sx={{ display: 'flex', flexDirection: 'column', gap: 2, px: 6 }}>
|
||||
<Box sx={{ display: 'flex', gap: 4 }}>
|
||||
<Box sx={{ display: 'flex', flexDirection: 'column' }}>
|
||||
<Box
|
||||
sx={{
|
||||
display: 'flex',
|
||||
flexDirection: 'column',
|
||||
gap: 2,
|
||||
px: { xs: 2, sm: 6 },
|
||||
}}
|
||||
>
|
||||
<Box sx={{ display: 'flex', flexWrap: 'wrap', gap: 2 }}>
|
||||
<Box sx={{ flex: 1, minWidth: '260px', maxWidth: '634px' }}>
|
||||
<TextField
|
||||
label={t('completion.email')}
|
||||
variant="outlined"
|
||||
fullWidth
|
||||
value={email}
|
||||
onChange={(e) => setEmail(e.target.value)}
|
||||
error={!correctEmail}
|
||||
sx={{
|
||||
width: !isVerifyingCode && !emailVerified ? '446px' : '634px',
|
||||
transition: 'width 0.3s',
|
||||
}}
|
||||
error={email.length > 0 && !correctEmail}
|
||||
sx={{ maxWidth: '462px' }}
|
||||
InputProps={{
|
||||
startAdornment:
|
||||
!isVerifyingCode && emailVerified ? (
|
||||
@@ -114,46 +129,54 @@ export function EmailSection({
|
||||
/>
|
||||
{email && (
|
||||
<Typography
|
||||
sx={{ color: correctEmail ? 'green' : 'red' }}
|
||||
sx={{ color: correctEmail ? 'success.main' : 'error.main' }}
|
||||
variant="caption"
|
||||
>
|
||||
{correctEmail ? '' : t('completion.emailCorrectForm')}
|
||||
</Typography>
|
||||
)}
|
||||
</Box>
|
||||
|
||||
{!isVerifyingCode && !emailVerified && (
|
||||
<Button
|
||||
variant="text"
|
||||
onClick={handleSendCode}
|
||||
sx={{ width: '156px' }}
|
||||
// disabled={
|
||||
// buttonState === 'sent' ||
|
||||
// buttonState === 'counting' ||
|
||||
// !correctEmail
|
||||
// }
|
||||
sx={{
|
||||
minWidth: '140px',
|
||||
width: { xs: '100%', sm: '156px' },
|
||||
alignSelf: 'center',
|
||||
}}
|
||||
>
|
||||
{getButtonLabel()}
|
||||
</Button>
|
||||
)}
|
||||
</Box>
|
||||
|
||||
{!emailVerified && codeSent && (
|
||||
<Box sx={{ display: 'flex', gap: 4 }}>
|
||||
<Box
|
||||
sx={{
|
||||
display: 'flex',
|
||||
flexDirection: { xs: 'column', sm: 'row' },
|
||||
gap: 2,
|
||||
}}
|
||||
>
|
||||
<TextField
|
||||
label={t('completion.verificationCode')}
|
||||
variant="outlined"
|
||||
value={verificationCode}
|
||||
onChange={(e) => setVerificationCode(e.target.value)}
|
||||
sx={{ width: '446px' }}
|
||||
fullWidth={false}
|
||||
sx={{ flex: 1 }}
|
||||
disabled={isVerifyingCode}
|
||||
/>
|
||||
<Button
|
||||
variant="contained"
|
||||
sx={{
|
||||
width: '156px',
|
||||
border: 0.5,
|
||||
}}
|
||||
onClick={handleVerifyCode}
|
||||
disabled={isVerifyingCode}
|
||||
sx={{
|
||||
width: { xs: '100%', sm: '156px' },
|
||||
border: 0.5,
|
||||
}}
|
||||
>
|
||||
{isVerifyingCode ? (
|
||||
<Box
|
||||
|
||||
@@ -54,26 +54,29 @@ export function PasswordSection({
|
||||
setShowPasswordSection(e.target.checked);
|
||||
};
|
||||
|
||||
const handleTogglePasswordEye = () => {
|
||||
setShowPasswordText((prev) => !prev);
|
||||
};
|
||||
|
||||
const handleTogglePasswordRepetitionEye = () => {
|
||||
const handleTogglePasswordEye = () => setShowPasswordText((prev) => !prev);
|
||||
const handleTogglePasswordRepetitionEye = () =>
|
||||
setShowPasswordRepetitionText((prev) => !prev);
|
||||
};
|
||||
|
||||
return (
|
||||
<>
|
||||
<FormGroup>
|
||||
<Box sx={{ display: 'flex', gap: 0.5, px: 6, alignItems: 'center' }}>
|
||||
<Box dir="ltr">
|
||||
<Switch
|
||||
checked={showPasswordSection}
|
||||
onChange={handleTogglePasswordSection}
|
||||
/>
|
||||
</Box>
|
||||
<Box
|
||||
sx={{
|
||||
display: 'flex',
|
||||
gap: 0.5,
|
||||
px: { xs: 2, sm: 6 },
|
||||
alignItems: 'center',
|
||||
}}
|
||||
>
|
||||
<Switch
|
||||
checked={showPasswordSection}
|
||||
onChange={handleTogglePasswordSection}
|
||||
/>
|
||||
<Typography
|
||||
sx={{ color: showPasswordSection ? '#2979FF' : 'text.primary' }}
|
||||
sx={{
|
||||
color: showPasswordSection ? 'primary.main' : 'text.primary',
|
||||
}}
|
||||
>
|
||||
{t('completion.determinePassword')}
|
||||
</Typography>
|
||||
@@ -81,15 +84,23 @@ export function PasswordSection({
|
||||
</FormGroup>
|
||||
|
||||
{showPasswordSection && (
|
||||
<Box sx={{ display: 'flex', flexDirection: 'column', gap: 2, px: 6 }}>
|
||||
<Box sx={{ display: 'flex', gap: 2 }}>
|
||||
<Box
|
||||
sx={{
|
||||
display: 'flex',
|
||||
flexDirection: 'column',
|
||||
gap: 2,
|
||||
px: { xs: 2, sm: 6 },
|
||||
}}
|
||||
>
|
||||
<Box sx={{ display: 'flex', flexWrap: 'wrap', gap: 2 }}>
|
||||
<TextField
|
||||
label={t('completion.password')}
|
||||
value={password}
|
||||
onChange={(e) => setPassword(e.target.value)}
|
||||
variant="outlined"
|
||||
type={showPasswordText ? 'text' : 'password'}
|
||||
sx={{ width: '309px' }}
|
||||
fullWidth
|
||||
sx={{ maxWidth: '309px', flex: 1 }}
|
||||
InputProps={{
|
||||
endAdornment: (
|
||||
<InputAdornment position="end" sx={{ height: 'unset' }}>
|
||||
@@ -144,7 +155,8 @@ export function PasswordSection({
|
||||
? t('completion.notCompatibility')
|
||||
: ' '
|
||||
}
|
||||
sx={{ width: '309px' }}
|
||||
fullWidth
|
||||
sx={{ maxWidth: '309px', flex: 1 }}
|
||||
type={showPasswordRepititonText ? 'text' : 'password'}
|
||||
InputProps={{
|
||||
endAdornment: (
|
||||
@@ -156,8 +168,8 @@ export function PasswordSection({
|
||||
width: '100%',
|
||||
}}
|
||||
>
|
||||
{confirmPassword.length > 0 ? (
|
||||
matchPassword ? (
|
||||
{confirmPassword.length > 0 &&
|
||||
(matchPassword ? (
|
||||
<TickCircle
|
||||
size="24"
|
||||
color="#14AE5C"
|
||||
@@ -179,8 +191,7 @@ export function PasswordSection({
|
||||
marginRight: '16px',
|
||||
}}
|
||||
/>
|
||||
)
|
||||
) : null}
|
||||
))}
|
||||
|
||||
<IconButton
|
||||
onClick={handleTogglePasswordRepetitionEye}
|
||||
@@ -213,10 +224,12 @@ export function PasswordSection({
|
||||
</Box>
|
||||
|
||||
{password && showValidations && (
|
||||
<Box sx={{ display: 'flex', gap: 2 }}>
|
||||
<Box sx={{ display: 'flex', flexWrap: 'wrap', gap: 2 }}>
|
||||
<Box
|
||||
sx={{
|
||||
width: '317px',
|
||||
flex: 1,
|
||||
minWidth: '260px',
|
||||
maxWidth: '317px',
|
||||
display: 'flex',
|
||||
flexDirection: 'column',
|
||||
}}
|
||||
@@ -232,7 +245,9 @@ export function PasswordSection({
|
||||
</Box>
|
||||
<Box
|
||||
sx={{
|
||||
width: '317px',
|
||||
flex: 1,
|
||||
minWidth: '260px',
|
||||
maxWidth: '317px',
|
||||
display: 'flex',
|
||||
flexDirection: 'column',
|
||||
}}
|
||||
|
||||
@@ -11,13 +11,29 @@ export function PasswordValidationItem({
|
||||
label,
|
||||
}: ValidationItemProps) {
|
||||
return (
|
||||
<Box sx={{ display: 'flex', alignItems: 'center', gap: 1, mb: 0.5 }}>
|
||||
<Box
|
||||
sx={{
|
||||
display: 'flex',
|
||||
alignItems: 'center',
|
||||
gap: 1,
|
||||
mb: 0.5,
|
||||
flexWrap: 'wrap',
|
||||
}}
|
||||
>
|
||||
<TickCircle
|
||||
size="16"
|
||||
color={isValid ? '#14AE5C' : '#2979FF'}
|
||||
variant={isValid ? 'Bold' : 'Outline'}
|
||||
/>
|
||||
<Typography variant="body2" color="text.primary">
|
||||
<Typography
|
||||
variant="body2"
|
||||
color="text.primary"
|
||||
sx={{
|
||||
fontSize: { xs: '0.85rem', sm: '0.875rem' },
|
||||
wordBreak: 'break-word',
|
||||
flex: 1,
|
||||
}}
|
||||
>
|
||||
{label}
|
||||
</Typography>
|
||||
</Box>
|
||||
|
||||
@@ -10,6 +10,8 @@ import {
|
||||
import { useTranslation } from 'react-i18next';
|
||||
import { Woman, Man } from 'iconsax-react';
|
||||
import { useState } from 'react';
|
||||
import { DateOfBirth } from './DateOfBirth';
|
||||
import { countries } from '../data/Countries';
|
||||
|
||||
interface PersonalInfoFieldsProps {
|
||||
sex: string;
|
||||
@@ -27,39 +29,6 @@ export function PersonalInfoFields({
|
||||
const { t } = useTranslation('completionForm');
|
||||
const [countryError, setCountryError] = useState(false);
|
||||
|
||||
const countries = [
|
||||
{ name: 'Afghanistan', fa: 'افغانستان', flag: 'af' },
|
||||
{ name: 'Albania', fa: 'آلبانی', flag: 'al' },
|
||||
{ name: 'Algeria', fa: 'الجزایر', flag: 'dz' },
|
||||
{ name: 'Argentina', fa: 'آرژانتین', flag: 'ar' },
|
||||
{ name: 'Armenia', fa: 'ارمنستان', flag: 'am' },
|
||||
{ name: 'Australia', fa: 'استرالیا', flag: 'au' },
|
||||
{ name: 'Austria', fa: 'اتریش', flag: 'at' },
|
||||
{ name: 'Bahrain', fa: 'بحرین', flag: 'bh' },
|
||||
{ name: 'Canada', fa: 'کانادا', flag: 'ca' },
|
||||
{ name: 'China', fa: 'چین', flag: 'cn' },
|
||||
{ name: 'France', fa: 'فرانسه', flag: 'fr' },
|
||||
{ name: 'Germany', fa: 'آلمان', flag: 'de' },
|
||||
{ name: 'India', fa: 'هند', flag: 'in' },
|
||||
{ name: 'Iran', fa: 'ایران', flag: 'ir' },
|
||||
{ name: 'Iraq', fa: 'عراق', flag: 'iq' },
|
||||
{ name: 'Italy', fa: 'ایتالیا', flag: 'it' },
|
||||
{ name: 'Japan', fa: 'ژاپن', flag: 'jp' },
|
||||
{ name: 'Netherlands', fa: 'هلند', flag: 'nl' },
|
||||
{ name: 'Pakistan', fa: 'پاکستان', flag: 'pk' },
|
||||
{ name: 'Qatar', fa: 'قطر', flag: 'qa' },
|
||||
{ name: 'Russia', fa: 'روسیه', flag: 'ru' },
|
||||
{ name: 'Saudi Arabia', fa: 'عربستان سعودی', flag: 'sa' },
|
||||
{ name: 'Spain', fa: 'اسپانیا', flag: 'es' },
|
||||
{ name: 'Sweden', fa: 'سوئد', flag: 'se' },
|
||||
{ name: 'Switzerland', fa: 'سوئیس', flag: 'ch' },
|
||||
{ name: 'Turkey', fa: 'ترکیه', flag: 'tr' },
|
||||
{ name: 'United Arab Emirates', fa: 'امارات متحده عربی', flag: 'ae' },
|
||||
{ name: 'United Kingdom', fa: 'بریتانیا', flag: 'gb' },
|
||||
{ name: 'United States', fa: 'ایالات متحده آمریکا', flag: 'us' },
|
||||
{ name: 'Yemen', fa: 'یمن', flag: 'ye' },
|
||||
];
|
||||
|
||||
const handleChangeSex = (e: any) => {
|
||||
setSex(e.target.value);
|
||||
};
|
||||
@@ -68,43 +37,46 @@ export function PersonalInfoFields({
|
||||
setCountry(newValue ? newValue.name : '');
|
||||
setCountryError(false);
|
||||
};
|
||||
|
||||
const handleCountryBlur = (e: React.FocusEvent<HTMLInputElement>) => {
|
||||
const inputValue = e.target.value.trim();
|
||||
const exists = countries.some((c) => c.fa === inputValue);
|
||||
if (inputValue && !exists) {
|
||||
setCountryError(true);
|
||||
} else {
|
||||
setCountryError(false);
|
||||
}
|
||||
};
|
||||
const handleInputChange = (_: any, value: string) => {
|
||||
const exists = countries.some((c) => c.fa === value.trim());
|
||||
if (value.trim() && !exists) {
|
||||
setCountryError(true);
|
||||
} else {
|
||||
setCountryError(false);
|
||||
}
|
||||
setCountryError(Boolean(inputValue && !exists));
|
||||
};
|
||||
|
||||
const handleInputChange = (_: any, value: string) => {
|
||||
const exists = countries.some((c) => c.fa === value.trim());
|
||||
setCountryError(Boolean(value.trim() && !exists));
|
||||
};
|
||||
|
||||
const fieldSx = { width: { xs: '100%', sm: '48%', md: '48%' } };
|
||||
|
||||
return (
|
||||
<Box sx={{ display: 'flex', flexDirection: 'column', gap: 2, px: 6 }}>
|
||||
<Box sx={{ display: 'flex', gap: 2 }}>
|
||||
<Box
|
||||
sx={{
|
||||
display: 'flex',
|
||||
flexDirection: 'column',
|
||||
gap: 2,
|
||||
px: { xs: 2, sm: 4, md: 6 },
|
||||
}}
|
||||
>
|
||||
<Box sx={{ display: 'flex', flexWrap: 'wrap', gap: 2 }}>
|
||||
<TextField
|
||||
label={t('completion.name')}
|
||||
placeholder={t('completion.name')}
|
||||
variant="outlined"
|
||||
sx={{ width: '309px' }}
|
||||
sx={fieldSx}
|
||||
/>
|
||||
<TextField
|
||||
label={t('completion.familyName')}
|
||||
placeholder={t('completion.familyName')}
|
||||
variant="outlined"
|
||||
sx={{ width: '309px' }}
|
||||
sx={fieldSx}
|
||||
/>
|
||||
</Box>
|
||||
|
||||
<Box sx={{ display: 'flex', gap: 2 }}>
|
||||
<FormControl sx={{ width: '309px' }}>
|
||||
<Box sx={{ display: 'flex', flexWrap: 'wrap', gap: 2 }}>
|
||||
<FormControl sx={fieldSx}>
|
||||
<InputLabel>{t('completion.gender')}</InputLabel>
|
||||
<Select
|
||||
value={sex}
|
||||
@@ -130,11 +102,11 @@ export function PersonalInfoFields({
|
||||
label={t('completion.optionalNationalCode')}
|
||||
placeholder={t('completion.optionalNationalCode')}
|
||||
variant="outlined"
|
||||
sx={{ width: '309px' }}
|
||||
sx={fieldSx}
|
||||
/>
|
||||
</Box>
|
||||
|
||||
<Box sx={{ display: 'flex', gap: 2 }}>
|
||||
<Box sx={{ display: 'flex', flexWrap: 'wrap', gap: 2 }}>
|
||||
<Autocomplete
|
||||
options={countries}
|
||||
getOptionLabel={(c) => (typeof c === 'string' ? c : c.fa)}
|
||||
@@ -169,15 +141,12 @@ export function PersonalInfoFields({
|
||||
onBlur={handleCountryBlur}
|
||||
/>
|
||||
)}
|
||||
sx={{ width: '309px' }}
|
||||
sx={fieldSx}
|
||||
/>
|
||||
|
||||
<TextField
|
||||
label={t('completion.dateOfBirth')}
|
||||
placeholder={t('completion.dateOfBirth')}
|
||||
variant="outlined"
|
||||
sx={{ width: '309px' }}
|
||||
/>
|
||||
<Box sx={fieldSx}>
|
||||
<DateOfBirth />
|
||||
</Box>
|
||||
</Box>
|
||||
</Box>
|
||||
);
|
||||
|
||||
@@ -5,13 +5,30 @@ export function SubmitSection() {
|
||||
const { t } = useTranslation('completionForm');
|
||||
|
||||
return (
|
||||
<Box sx={{ display: 'flex', gap: 2, px: 6, mb: '17px' }}>
|
||||
<Box
|
||||
sx={{
|
||||
display: 'flex',
|
||||
flexDirection: { xs: 'column', sm: 'row' },
|
||||
alignItems: { xs: 'stretch', sm: 'center' },
|
||||
gap: 2,
|
||||
px: { xs: 2, sm: 4, md: 6 },
|
||||
mb: '17px',
|
||||
}}
|
||||
>
|
||||
<Typography variant="body2" sx={{ flex: 1 }} color="text.primary">
|
||||
{t('completion.agreementPart1')}
|
||||
<Link target="_blank">{t('completion.agreementLinkText')}</Link>{' '}
|
||||
<Link target="_blank" rel="noopener" href="#">
|
||||
{t('completion.agreementLinkText')}
|
||||
</Link>{' '}
|
||||
{t('completion.agreementPart2')}
|
||||
</Typography>
|
||||
<Button variant="contained" sx={{ width: '247px' }}>
|
||||
<Button
|
||||
variant="contained"
|
||||
sx={{
|
||||
width: { xs: '100%', sm: '247px' },
|
||||
alignSelf: { xs: 'stretch', sm: 'auto' },
|
||||
}}
|
||||
>
|
||||
{t('completion.registerButton')}
|
||||
</Button>
|
||||
</Box>
|
||||
|
||||
@@ -19,7 +19,7 @@ export function UserCompletionForm() {
|
||||
const [verificationCode, setVerificationCode] = useState('');
|
||||
const [buttonState, setButtonState] = useState<
|
||||
'default' | 'counting' | 'sent'
|
||||
>('default'); // default | counting | sent
|
||||
>('default');
|
||||
const [countdown, setCountdown] = useState(60);
|
||||
const [emailVerified, setEmailVerified] = useState(false);
|
||||
const [isVerifyingCode, setIsVerifyingCode] = useState(false);
|
||||
@@ -32,7 +32,6 @@ export function UserCompletionForm() {
|
||||
const validPassword =
|
||||
hasNumber && hasMinLength && hasUpperAndLower && hasSpecialChar;
|
||||
const [showPasswordValidations, setShowPasswordValidations] = useState(false);
|
||||
|
||||
const correctEmail = /^[^\s@]+@[^\s@]+\.[^\s@]+$/.test(email);
|
||||
|
||||
useEffect(() => {
|
||||
@@ -40,9 +39,7 @@ export function UserCompletionForm() {
|
||||
if (!validPassword) {
|
||||
setShowPasswordValidations(true);
|
||||
} else {
|
||||
const timer = setTimeout(() => {
|
||||
setShowPasswordValidations(false);
|
||||
}, 1000);
|
||||
const timer = setTimeout(() => setShowPasswordValidations(false), 1000);
|
||||
return () => clearTimeout(timer);
|
||||
}
|
||||
} else {
|
||||
@@ -71,8 +68,7 @@ export function UserCompletionForm() {
|
||||
if (buttonState === 'counting') {
|
||||
const minutes = String(Math.floor(countdown / 60)).padStart(2, '0');
|
||||
const seconds = String(countdown % 60).padStart(2, '0');
|
||||
const time = `${minutes}:${seconds}`;
|
||||
return toPersianDigits(time);
|
||||
return toPersianDigits(`${minutes}:${seconds}`);
|
||||
}
|
||||
return t('completion.vericationCodeButton');
|
||||
};
|
||||
@@ -103,41 +99,38 @@ export function UserCompletionForm() {
|
||||
return (
|
||||
<Box
|
||||
sx={{
|
||||
backgroundColor: '#F5F5F5',
|
||||
backgroundColor: 'background.default',
|
||||
display: 'flex',
|
||||
justifyContent: 'center',
|
||||
alignItems: 'center',
|
||||
p: 2,
|
||||
p: { xs: 1, sm: 2, md: 3 },
|
||||
}}
|
||||
>
|
||||
<Box
|
||||
sx={{
|
||||
width: '730px',
|
||||
backgroundColor: '#FFFFFF',
|
||||
width: '100%',
|
||||
maxWidth: '730px',
|
||||
backgroundColor: 'background.paper',
|
||||
border: '1px solid #ccc',
|
||||
display: 'flex',
|
||||
flexDirection: 'column',
|
||||
gap: 2,
|
||||
px: { xs: 2, sm: 4, md: 6 },
|
||||
py: { xs: 3, sm: 4 },
|
||||
}}
|
||||
>
|
||||
<Box
|
||||
sx={{
|
||||
display: 'flex',
|
||||
flexDirection: 'column',
|
||||
px: 4,
|
||||
width: '100%',
|
||||
maxWidth: '666px',
|
||||
height: '92px',
|
||||
mt: '32px',
|
||||
gap: 1,
|
||||
}}
|
||||
>
|
||||
<Typography
|
||||
variant="h5"
|
||||
color="text.primary"
|
||||
sx={{ mt: '16px', px: 2 }}
|
||||
>
|
||||
<Typography variant="h5" color="text.primary">
|
||||
{t('completion.title')}
|
||||
</Typography>
|
||||
<Typography variant="body2" color="text.secondary" sx={{ px: 2 }}>
|
||||
<Typography variant="body2" color="text.secondary">
|
||||
{t('completion.description')}
|
||||
</Typography>
|
||||
</Box>
|
||||
|
||||
33
src/features/authentication/data/Countries.tsx
Normal file
33
src/features/authentication/data/Countries.tsx
Normal file
@@ -0,0 +1,33 @@
|
||||
// components/CountryList.ts
|
||||
export const countries = [
|
||||
{ name: 'Afghanistan', fa: 'افغانستان', flag: 'af' },
|
||||
{ name: 'Albania', fa: 'آلبانی', flag: 'al' },
|
||||
{ name: 'Algeria', fa: 'الجزایر', flag: 'dz' },
|
||||
{ name: 'Argentina', fa: 'آرژانتین', flag: 'ar' },
|
||||
{ name: 'Armenia', fa: 'ارمنستان', flag: 'am' },
|
||||
{ name: 'Australia', fa: 'استرالیا', flag: 'au' },
|
||||
{ name: 'Austria', fa: 'اتریش', flag: 'at' },
|
||||
{ name: 'Bahrain', fa: 'بحرین', flag: 'bh' },
|
||||
{ name: 'Canada', fa: 'کانادا', flag: 'ca' },
|
||||
{ name: 'China', fa: 'چین', flag: 'cn' },
|
||||
{ name: 'France', fa: 'فرانسه', flag: 'fr' },
|
||||
{ name: 'Germany', fa: 'آلمان', flag: 'de' },
|
||||
{ name: 'India', fa: 'هند', flag: 'in' },
|
||||
{ name: 'Iran', fa: 'ایران', flag: 'ir' },
|
||||
{ name: 'Iraq', fa: 'عراق', flag: 'iq' },
|
||||
{ name: 'Italy', fa: 'ایتالیا', flag: 'it' },
|
||||
{ name: 'Japan', fa: 'ژاپن', flag: 'jp' },
|
||||
{ name: 'Netherlands', fa: 'هلند', flag: 'nl' },
|
||||
{ name: 'Pakistan', fa: 'پاکستان', flag: 'pk' },
|
||||
{ name: 'Qatar', fa: 'قطر', flag: 'qa' },
|
||||
{ name: 'Russia', fa: 'روسیه', flag: 'ru' },
|
||||
{ name: 'Saudi Arabia', fa: 'عربستان سعودی', flag: 'sa' },
|
||||
{ name: 'Spain', fa: 'اسپانیا', flag: 'es' },
|
||||
{ name: 'Sweden', fa: 'سوئد', flag: 'se' },
|
||||
{ name: 'Switzerland', fa: 'سوئیس', flag: 'ch' },
|
||||
{ name: 'Turkey', fa: 'ترکیه', flag: 'tr' },
|
||||
{ name: 'United Arab Emirates', fa: 'امارات متحده عربی', flag: 'ae' },
|
||||
{ name: 'United Kingdom', fa: 'بریتانیا', flag: 'gb' },
|
||||
{ name: 'United States', fa: 'ایالات متحده آمریکا', flag: 'us' },
|
||||
{ name: 'Yemen', fa: 'یمن', flag: 'ye' },
|
||||
];
|
||||
Reference in New Issue
Block a user