211 lines
4.9 KiB
JavaScript
211 lines
4.9 KiB
JavaScript
const form = document.getElementById("change-password-form");
|
|
const currentPass = document.getElementById("current-pass");
|
|
const newPass = document.getElementById("new-pass");
|
|
const confirmPass = document.getElementById("confirm-pass");
|
|
const errEl = document.getElementById("error");
|
|
const successEl = document.getElementById("success");
|
|
|
|
const tempToken = sessionStorage.getItem("temp_token");
|
|
const tempUser = sessionStorage.getItem("temp_user");
|
|
|
|
if (!tempToken || !tempUser) {
|
|
window.location.href = "/";
|
|
}
|
|
|
|
const user = JSON.parse(tempUser);
|
|
|
|
if (typeof anime !== "undefined") {
|
|
const particles = document.querySelectorAll(".particle");
|
|
particles.forEach((particle, i) => {
|
|
anime({
|
|
targets: particle,
|
|
translateX: () => anime.random(-100, 100),
|
|
translateY: () => anime.random(-100, 100),
|
|
scale: () => anime.random(0.5, 1.5),
|
|
opacity: [0, 0.6, 0],
|
|
duration: () => anime.random(3000, 6000),
|
|
delay: i * 200,
|
|
easing: "easeInOutQuad",
|
|
loop: true,
|
|
});
|
|
});
|
|
|
|
anime
|
|
.timeline()
|
|
.add({
|
|
targets: ".login-card",
|
|
opacity: [0, 1],
|
|
translateY: [30, 0],
|
|
duration: 800,
|
|
easing: "easeOutExpo",
|
|
})
|
|
.add(
|
|
{
|
|
targets: ".login-crown-wrapper",
|
|
scale: [0, 1],
|
|
rotate: [180, 0],
|
|
duration: 600,
|
|
easing: "easeOutBack",
|
|
},
|
|
"-=400",
|
|
)
|
|
.add(
|
|
{
|
|
targets: ".login-brand",
|
|
opacity: [0, 1],
|
|
translateY: [-10, 0],
|
|
duration: 500,
|
|
easing: "easeOutQuad",
|
|
},
|
|
"-=300",
|
|
)
|
|
.add(
|
|
{
|
|
targets: ".login-title, .login-subtitle",
|
|
opacity: [0, 1],
|
|
translateY: [10, 0],
|
|
duration: 500,
|
|
delay: anime.stagger(100),
|
|
easing: "easeOutQuad",
|
|
},
|
|
"-=300",
|
|
)
|
|
.add(
|
|
{
|
|
targets: ".form-group",
|
|
opacity: [0, 1],
|
|
translateY: [15, 0],
|
|
duration: 500,
|
|
delay: anime.stagger(100),
|
|
easing: "easeOutQuad",
|
|
},
|
|
"-=300",
|
|
)
|
|
.add(
|
|
{
|
|
targets: ".login-btn",
|
|
opacity: [0, 1],
|
|
scale: [0.95, 1],
|
|
duration: 400,
|
|
easing: "easeOutQuad",
|
|
},
|
|
"-=200",
|
|
);
|
|
|
|
anime({
|
|
targets: ".login-crown",
|
|
scale: [1, 1.08, 1],
|
|
duration: 2000,
|
|
easing: "easeInOutQuad",
|
|
loop: true,
|
|
});
|
|
|
|
document.querySelectorAll(".input-animated input").forEach((input) => {
|
|
input.addEventListener("focus", (e) => {
|
|
anime({
|
|
targets: e.target.parentElement,
|
|
scale: [1, 1.02],
|
|
duration: 200,
|
|
easing: "easeOutQuad",
|
|
});
|
|
});
|
|
|
|
input.addEventListener("blur", (e) => {
|
|
anime({
|
|
targets: e.target.parentElement,
|
|
scale: [1.02, 1],
|
|
duration: 200,
|
|
easing: "easeOutQuad",
|
|
});
|
|
});
|
|
});
|
|
}
|
|
|
|
form?.addEventListener("submit", async (e) => {
|
|
e.preventDefault();
|
|
errEl.textContent = "";
|
|
successEl.style.display = "none";
|
|
|
|
if (newPass.value !== confirmPass.value) {
|
|
errEl.textContent = "New passwords do not match";
|
|
return;
|
|
}
|
|
|
|
if (newPass.value.length < 6) {
|
|
errEl.textContent = "New password must be at least 6 characters";
|
|
return;
|
|
}
|
|
|
|
if (currentPass.value === newPass.value) {
|
|
errEl.textContent = "New password must be different from current password";
|
|
return;
|
|
}
|
|
|
|
try {
|
|
const res = await fetch(`/api/users/${user.id}/password`, {
|
|
method: "PUT",
|
|
headers: {
|
|
"Content-Type": "application/json",
|
|
Authorization: `Bearer ${tempToken}`,
|
|
},
|
|
body: JSON.stringify({
|
|
currentPassword: currentPass.value,
|
|
newPassword: newPass.value,
|
|
}),
|
|
});
|
|
|
|
const data = await res.json();
|
|
|
|
if (!res.ok) {
|
|
throw new Error(data.error || "Failed to change password");
|
|
}
|
|
|
|
sessionStorage.removeItem("temp_token");
|
|
sessionStorage.removeItem("temp_user");
|
|
|
|
successEl.textContent = "Password changed successfully! Redirecting...";
|
|
successEl.style.opacity = "0";
|
|
successEl.style.display = "block";
|
|
|
|
if (typeof anime !== "undefined") {
|
|
anime({
|
|
targets: successEl,
|
|
opacity: [0, 1],
|
|
translateY: [-5, 0],
|
|
duration: 400,
|
|
easing: "easeOutQuad",
|
|
});
|
|
} else {
|
|
successEl.style.opacity = "1";
|
|
}
|
|
|
|
setTimeout(() => {
|
|
window.location.href = "/";
|
|
}, 2000);
|
|
} catch (err) {
|
|
errEl.textContent = err.message || "Failed to change password";
|
|
|
|
if (typeof anime !== "undefined") {
|
|
anime({
|
|
targets: ".login-card",
|
|
translateX: [
|
|
{ value: -10, duration: 100 },
|
|
{ value: 10, duration: 100 },
|
|
{ value: -10, duration: 100 },
|
|
{ value: 10, duration: 100 },
|
|
{ value: 0, duration: 100 },
|
|
],
|
|
easing: "easeInOutQuad",
|
|
});
|
|
|
|
anime({
|
|
targets: "#error",
|
|
opacity: [0, 1],
|
|
translateY: [-5, 0],
|
|
duration: 300,
|
|
easing: "easeOutQuad",
|
|
});
|
|
}
|
|
}
|
|
});
|