diff --git a/src/components/ChangePassword/index.js b/src/components/ChangePassword/index.js new file mode 100644 index 00000000..05c309f6 --- /dev/null +++ b/src/components/ChangePassword/index.js @@ -0,0 +1,163 @@ +import { Component } from 'pet-dex-utilities'; +import TextInput from '../TextInput'; +import Button from '../Button'; +import './index.scss'; + +const events = ['password:change']; + +const html = ` +
+

+ Senha antiga +

+
+ Senha inválida +
+ +

Nova senha

+ +
+ Senha inválida + As senhas não coincidem +
+ Senha inválida + As senhas não coincidem + + +
+`; + +const validatePassword = (password) => { + const hasMinLength = password.length >= 10; + const hasUppercase = /[A-Z]/g.test(password); + const hasNumber = /[0-9]/g.test(password); + const hasSpecialCharacter = /[!@#$%^&*(),.?":{}|<>]/g.test(password); + + return hasMinLength && hasUppercase && hasNumber && hasSpecialCharacter; +}; + +export default function ChangePassword() { + Component.call(this, { html, events }); + const $changePasswordForm = this.selected.get('change-password'); + const $passwordInputContainer = this.selected.get('password'); + const $currentPasswordErrorMessage = this.selected.get('password-error'); + const $newPasswordInputContainer = this.selected.get('new-password'); + const $newPasswordErrorMessage = this.selected.get('new-password-error'); + const $newPasswordErrorMatch = this.selected.get('new-password-error-match'); + const $confirmPasswordInputContainer = this.selected.get('confirm-password'); + const $confirmPasswordErrorMessage = this.selected.get( + 'confirm-password-error', + ); + const $confirmPasswordErrorMatch = this.selected.get( + 'confirm-password-error-match', + ); + + const currentPasswordInput = new TextInput({ + placeholder: 'Senha', + assetPosition: 'suffix', + type: 'password', + }); + const newPasswordInput = new TextInput({ + placeholder: 'Nova senha', + assetPosition: 'suffix', + type: 'password', + }); + const confirmPasswordInput = new TextInput({ + placeholder: ' Confirmar senha', + assetPosition: 'suffix', + type: 'password', + }); + const submitButton = new Button({ + text: 'Salvar', + isFullWidth: true, + isDisabled: true, + }); + + currentPasswordInput.mount($passwordInputContainer); + newPasswordInput.mount($newPasswordInputContainer); + confirmPasswordInput.mount($confirmPasswordInputContainer); + submitButton.mount($changePasswordForm); + + const validateSubmit = () => { + if ( + currentPasswordInput.getValue() && + newPasswordInput.getValue() && + confirmPasswordInput.getValue() + ) { + submitButton.enable(); + } else { + submitButton.disable(); + } + }; + + submitButton.selected.get('button').classList.add('change-password__button'); + currentPasswordInput.selected + .get('input-text') + .addEventListener('input', () => { + $currentPasswordErrorMessage.classList.remove('show-error'); + validateSubmit(); + }); + newPasswordInput.selected.get('input-text').addEventListener('input', () => { + $newPasswordErrorMessage.classList.remove('show-error'); + validateSubmit(); + }); + confirmPasswordInput.selected + .get('input-text') + .addEventListener('input', () => { + $confirmPasswordErrorMessage.classList.remove('show-error'); + validateSubmit(); + }); + + submitButton.listen('click', () => { + let validPasswords = true; + const newPassword = newPasswordInput.selected.get('input-text').value; + const confirmPassword = + confirmPasswordInput.selected.get('input-text').value; + + const showErrorMessage = (field, error) => { + const fieldValue = field.selected.get('input-text').value; + if (!validatePassword(fieldValue)) { + validPasswords = false; + error.classList.add('show-error'); + field.inputError(); + } + }; + + showErrorMessage(currentPasswordInput, $currentPasswordErrorMessage); + showErrorMessage(newPasswordInput, $newPasswordErrorMessage); + showErrorMessage(confirmPasswordInput, $confirmPasswordErrorMessage); + + if (confirmPassword !== newPassword) { + validPasswords = false; + $newPasswordErrorMatch.classList.add('show-error'); + $confirmPasswordErrorMatch.classList.add('show-error'); + newPasswordInput.inputError(); + confirmPasswordInput.inputError(); + } + + const removeErrors = (div) => { + div.classList.remove('show-error'); + }; + + if (validPasswords) { + removeErrors($currentPasswordErrorMessage); + removeErrors($newPasswordErrorMessage); + removeErrors($confirmPasswordErrorMessage); + removeErrors($newPasswordErrorMatch); + removeErrors($confirmPasswordErrorMatch); + this.emit('password:change'); + } + }); +} +ChangePassword.prototype = Object.assign( + ChangePassword.prototype, + Component.prototype, +); diff --git a/src/components/ChangePassword/index.scss b/src/components/ChangePassword/index.scss new file mode 100644 index 00000000..6d9d36e3 --- /dev/null +++ b/src/components/ChangePassword/index.scss @@ -0,0 +1,56 @@ +@use '~styles/colors.scss' as colors; +@use '~styles/fonts.scss' as fonts; +@use '~styles/breakpoints.scss' as breakpoints; + +.change-password { + height: 100%; + + display: flex; + flex-direction: column; + gap: 2rem; + + font-family: fonts.$primaryFont; + line-height: 1.5; + + padding: 0 2rem; + + background-color: colors.$secondary100; + + &__title { + color: colors.$gray600; + font-size: fonts.$sm; + font-weight: fonts.$bold; + } + + &__error { + display: none; + + color: colors.$error100; + + &.show-error { + display: block; + } + } + + &__tips { + color: colors.$gray500; + font-weight: fonts.$regular; + + list-style-type: disc; + padding-inline-start: 3rem; + } + + &__button { + margin-top: auto; + margin-bottom: 1rem; + } + + &__separator { + width: 100%; + + display: flex; + + border: 0; + border-top: 0.1rem solid colors.$gray200; + } +} diff --git a/src/stories/ChangePassword.stories.js b/src/stories/ChangePassword.stories.js new file mode 100644 index 00000000..b607bcbb --- /dev/null +++ b/src/stories/ChangePassword.stories.js @@ -0,0 +1,33 @@ +import ChangePassword from '../components/ChangePassword'; +import { initializeSwiper } from '../utils/swiper'; +import Drawer from '../components/Drawer'; +import Button from '../components/Button'; + +export default { + title: 'Components/ChangePassword', + render: (args) => { + initializeSwiper(); + const button = new Button({ + text: 'Abrir change password', + isFullWidth: true, + isDisabled: false, + }); + + const changePassword = new ChangePassword(args); + const drawer = new Drawer({ + title: 'Alterar Senha', + content: changePassword, + }); + + const $container = document.createElement('div'); + button.mount($container); + + button.listen('click', () => { + drawer.open(); + }); + + return $container; + }, +}; + +export const Default = {};