forked from github/plane
[WEB-1324] chore: change password page improvement (#4462)
* chore: change password page improvement * chore: confirm password input improvement
This commit is contained in:
parent
061d52727e
commit
5ccb4f7d19
@ -69,6 +69,7 @@ export const InstanceSetupForm: FC = (props) => {
|
||||
const [formData, setFormData] = useState<TFormData>(defaultFromData);
|
||||
const [isPasswordInputFocused, setIsPasswordInputFocused] = useState(false);
|
||||
const [isSubmitting, setIsSubmitting] = useState(false);
|
||||
const [isRetryPasswordInputFocused, setIsRetryPasswordInputFocused] = useState(false);
|
||||
|
||||
const handleFormChange = (key: keyof TFormData, value: string | boolean) =>
|
||||
setFormData((prev) => ({ ...prev, [key]: value }));
|
||||
@ -276,6 +277,8 @@ export const InstanceSetupForm: FC = (props) => {
|
||||
onChange={(e) => handleFormChange("confirm_password", e.target.value)}
|
||||
placeholder="Confirm password"
|
||||
className="w-full border border-onboarding-border-100 !bg-onboarding-background-200 pr-12 placeholder:text-onboarding-text-400"
|
||||
onFocus={() => setIsRetryPasswordInputFocused(true)}
|
||||
onBlur={() => setIsRetryPasswordInputFocused(false)}
|
||||
/>
|
||||
{showPassword ? (
|
||||
<button
|
||||
@ -297,9 +300,9 @@ export const InstanceSetupForm: FC = (props) => {
|
||||
</button>
|
||||
)}
|
||||
</div>
|
||||
{!!formData.confirm_password && formData.password !== formData.confirm_password && (
|
||||
<span className="text-sm text-red-500">Passwords don{"'"}t match</span>
|
||||
)}
|
||||
{!!formData.confirm_password &&
|
||||
formData.password !== formData.confirm_password &&
|
||||
!isRetryPasswordInputFocused && <span className="text-sm text-red-500">Passwords don{"'"}t match</span>}
|
||||
</div>
|
||||
|
||||
<div className="relative flex items-center pt-2 gap-2">
|
||||
|
@ -44,6 +44,7 @@ export const PasswordForm: React.FC<Props> = (props) => {
|
||||
const [csrfToken, setCsrfToken] = useState<string | undefined>(undefined);
|
||||
const [isPasswordInputFocused, setIsPasswordInputFocused] = useState(false);
|
||||
const [isSubmitting, setIsSubmitting] = useState(false);
|
||||
const [isRetryPasswordInputFocused, setIsRetryPasswordInputFocused] = useState(false);
|
||||
// hooks
|
||||
const { data: instance, config: instanceConfig } = useInstance();
|
||||
// router
|
||||
@ -170,6 +171,8 @@ export const PasswordForm: React.FC<Props> = (props) => {
|
||||
onChange={(e) => handleFormChange("confirm_password", e.target.value)}
|
||||
placeholder="Confirm password"
|
||||
className="h-[46px] w-full border border-onboarding-border-100 !bg-onboarding-background-200 pr-12 placeholder:text-onboarding-text-400"
|
||||
onFocus={() => setIsRetryPasswordInputFocused(true)}
|
||||
onBlur={() => setIsRetryPasswordInputFocused(false)}
|
||||
/>
|
||||
{showPassword ? (
|
||||
<EyeOff
|
||||
@ -183,9 +186,9 @@ export const PasswordForm: React.FC<Props> = (props) => {
|
||||
/>
|
||||
)}
|
||||
</div>
|
||||
{!!passwordFormData.confirm_password && passwordFormData.password !== passwordFormData.confirm_password && (
|
||||
<span className="text-sm text-red-500">Passwords don{"'"}t match</span>
|
||||
)}
|
||||
{!!passwordFormData.confirm_password &&
|
||||
passwordFormData.password !== passwordFormData.confirm_password &&
|
||||
!isRetryPasswordInputFocused && <span className="text-sm text-red-500">Passwords don{"'"}t match</span>}
|
||||
</div>
|
||||
)}
|
||||
<div className="space-y-2.5">
|
||||
|
@ -53,6 +53,7 @@ export const AuthPasswordForm: React.FC<Props> = observer((props: Props) => {
|
||||
});
|
||||
const [isSubmitting, setIsSubmitting] = useState(false);
|
||||
const [isPasswordInputFocused, setIsPasswordInputFocused] = useState(false);
|
||||
const [isRetryPasswordInputFocused, setIsRetryPasswordInputFocused] = useState(false);
|
||||
|
||||
const handleShowPassword = (key: keyof typeof showPassword) =>
|
||||
setShowPassword((prev) => ({ ...prev, [key]: !prev[key] }));
|
||||
@ -183,6 +184,8 @@ export const AuthPasswordForm: React.FC<Props> = observer((props: Props) => {
|
||||
onChange={(e) => handleFormChange("confirm_password", e.target.value)}
|
||||
placeholder="Confirm password"
|
||||
className="disable-autofill-style h-[46px] w-full border border-onboarding-border-100 !bg-onboarding-background-200 pr-12 placeholder:text-onboarding-text-400"
|
||||
onFocus={() => setIsRetryPasswordInputFocused(true)}
|
||||
onBlur={() => setIsRetryPasswordInputFocused(false)}
|
||||
/>
|
||||
{showPassword?.retypePassword ? (
|
||||
<EyeOff
|
||||
@ -196,9 +199,9 @@ export const AuthPasswordForm: React.FC<Props> = observer((props: Props) => {
|
||||
/>
|
||||
)}
|
||||
</div>
|
||||
{!!passwordFormData.confirm_password && passwordFormData.password !== passwordFormData.confirm_password && (
|
||||
<span className="text-sm text-red-500">Passwords don{"'"}t match</span>
|
||||
)}
|
||||
{!!passwordFormData.confirm_password &&
|
||||
passwordFormData.password !== passwordFormData.confirm_password &&
|
||||
!isRetryPasswordInputFocused && <span className="text-sm text-red-500">Passwords don{"'"}t match</span>}
|
||||
</div>
|
||||
)}
|
||||
|
||||
|
@ -52,6 +52,8 @@ const ResetPasswordPage: NextPageWithLayout = () => {
|
||||
});
|
||||
const [csrfToken, setCsrfToken] = useState<string | undefined>(undefined);
|
||||
const [isPasswordInputFocused, setIsPasswordInputFocused] = useState(false);
|
||||
const [isRetryPasswordInputFocused, setIsRetryPasswordInputFocused] = useState(false);
|
||||
|
||||
// hooks
|
||||
const { resolvedTheme } = useTheme();
|
||||
|
||||
@ -165,6 +167,8 @@ const ResetPasswordPage: NextPageWithLayout = () => {
|
||||
onChange={(e) => handleFormChange("confirm_password", e.target.value)}
|
||||
placeholder="Confirm password"
|
||||
className="h-[46px] w-full border border-onboarding-border-100 !bg-onboarding-background-200 pr-12 placeholder:text-onboarding-text-400"
|
||||
onFocus={() => setIsRetryPasswordInputFocused(true)}
|
||||
onBlur={() => setIsRetryPasswordInputFocused(false)}
|
||||
/>
|
||||
{showPassword ? (
|
||||
<EyeOff
|
||||
@ -178,9 +182,11 @@ const ResetPasswordPage: NextPageWithLayout = () => {
|
||||
/>
|
||||
)}
|
||||
</div>
|
||||
{!!resetFormData.confirm_password && resetFormData.password !== resetFormData.confirm_password && (
|
||||
<span className="text-sm text-red-500">Passwords don{"'"}t match</span>
|
||||
)}
|
||||
{!!resetFormData.confirm_password &&
|
||||
resetFormData.password !== resetFormData.confirm_password &&
|
||||
!isRetryPasswordInputFocused && (
|
||||
<span className="text-sm text-red-500">Passwords don{"'"}t match</span>
|
||||
)}
|
||||
</div>
|
||||
<Button type="submit" variant="primary" className="w-full" size="lg" disabled={isButtonDisabled}>
|
||||
Set password
|
||||
|
@ -54,6 +54,7 @@ const SetPasswordPage: NextPageWithLayout = observer(() => {
|
||||
});
|
||||
const [csrfToken, setCsrfToken] = useState<string | undefined>(undefined);
|
||||
const [isPasswordInputFocused, setIsPasswordInputFocused] = useState(false);
|
||||
const [isRetryPasswordInputFocused, setIsRetryPasswordInputFocused] = useState(false);
|
||||
// hooks
|
||||
const { resolvedTheme } = useTheme();
|
||||
// hooks
|
||||
@ -179,6 +180,8 @@ const SetPasswordPage: NextPageWithLayout = observer(() => {
|
||||
onChange={(e) => handleFormChange("confirm_password", e.target.value)}
|
||||
placeholder="Confirm password"
|
||||
className="h-[46px] w-full border border-onboarding-border-100 !bg-onboarding-background-200 pr-12 placeholder:text-onboarding-text-400"
|
||||
onFocus={() => setIsRetryPasswordInputFocused(true)}
|
||||
onBlur={() => setIsRetryPasswordInputFocused(false)}
|
||||
/>
|
||||
{showPassword ? (
|
||||
<EyeOff
|
||||
@ -193,7 +196,8 @@ const SetPasswordPage: NextPageWithLayout = observer(() => {
|
||||
)}
|
||||
</div>
|
||||
{!!passwordFormData.confirm_password &&
|
||||
passwordFormData.password !== passwordFormData.confirm_password && (
|
||||
passwordFormData.password !== passwordFormData.confirm_password &&
|
||||
!isRetryPasswordInputFocused && (
|
||||
<span className="text-sm text-red-500">Passwords don{"'"}t match</span>
|
||||
)}
|
||||
</div>
|
||||
|
@ -44,6 +44,7 @@ const ChangePasswordPage: NextPageWithLayout = observer(() => {
|
||||
retypePassword: false,
|
||||
});
|
||||
const [isPasswordInputFocused, setIsPasswordInputFocused] = useState(false);
|
||||
const [isRetryPasswordInputFocused, setIsRetryPasswordInputFocused] = useState(false);
|
||||
|
||||
// router
|
||||
const router = useRouter();
|
||||
@ -150,7 +151,7 @@ const ChangePasswordPage: NextPageWithLayout = observer(() => {
|
||||
<input type="hidden" name="csrfmiddlewaretoken" value={csrfToken} />
|
||||
|
||||
<h3 className="text-xl font-medium">Change password</h3>
|
||||
<div className="grid-col grid w-full grid-cols-1 items-center justify-between gap-10 xl:grid-cols-2 2xl:grid-cols-3">
|
||||
<div className="flex flex-col gap-10 w-full max-w-96">
|
||||
<div className="flex flex-col gap-1 ">
|
||||
<h4 className="text-sm">Current password</h4>
|
||||
<div className="relative flex items-center rounded-md">
|
||||
@ -244,6 +245,8 @@ const ChangePasswordPage: NextPageWithLayout = observer(() => {
|
||||
onChange={onChange}
|
||||
className="w-full"
|
||||
hasError={Boolean(errors.confirm_password)}
|
||||
onFocus={() => setIsRetryPasswordInputFocused(true)}
|
||||
onBlur={() => setIsRetryPasswordInputFocused(false)}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
@ -259,7 +262,7 @@ const ChangePasswordPage: NextPageWithLayout = observer(() => {
|
||||
/>
|
||||
)}
|
||||
</div>
|
||||
{!!retypePassword && password !== retypePassword && (
|
||||
{!!retypePassword && password !== retypePassword && !isRetryPasswordInputFocused && (
|
||||
<span className="text-sm text-red-500">Passwords don{"'"}t match</span>
|
||||
)}
|
||||
</div>
|
||||
|
Loading…
Reference in New Issue
Block a user