skripsiProject/resources/views/auth/reset-password.blade.php

444 lines
16 KiB
PHP

<!DOCTYPE html>
<html lang="id">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Reset Password - Sistem Akademik</title>
<link href="https://fonts.googleapis.com/css2?family=Plus+Jakarta+Sans:wght@400;500;600;700;800&display=swap" rel="stylesheet">
<style>
* { margin: 0; padding: 0; box-sizing: border-box; font-family: 'Plus Jakarta Sans', sans-serif; }
html, body { height: 100%; }
.page { display: flex; height: 100vh; width: 100%; }
/* ── LEFT ── */
.left {
width: 38%;
background: #F3F4F8;
display: flex; flex-direction: column;
justify-content: center; align-items: center;
text-align: center; padding: 48px 40px;
position: relative;
}
.left::after {
content: '';
position: absolute; right: 0; top: 0; bottom: 0; width: 1px;
background: linear-gradient(to bottom, transparent, #C7D2FE 30%, #C7D2FE 70%, transparent);
}
.logo {
width: 280px;
max-width: 100%;
margin-bottom: 32px;
filter: drop-shadow(0 8px 24px rgba(79,70,229,.18));
transition: transform .3s;
}
.logo:hover { transform: scale(1.04); }
.left-title { font-size: 22px; font-weight: 800; color: #1E3A6E; line-height: 1.3; margin-bottom: 10px; }
.left-sub { font-size: 13px; color: #6B7280; line-height: 1.7; }
.left-badge {
margin-top: 28px;
display: inline-flex; align-items: center; gap: 6px;
background: #EEF2FF; border: 1px solid #C7D2FE;
border-radius: 99px; padding: 6px 16px;
font-size: 11.5px; font-weight: 600; color: #4F46E5;
}
.left-badge span { width: 6px; height: 6px; background: #4F46E5; border-radius: 50%; display: inline-block; }
/* Step indicators */
.steps {
margin-top: 36px;
display: flex; flex-direction: column; gap: 12px;
width: 100%; max-width: 220px;
}
.step { display: flex; align-items: center; gap: 12px; text-align: left; }
.step-dot {
width: 30px; height: 30px; border-radius: 50%;
display: flex; align-items: center; justify-content: center;
font-size: 12px; font-weight: 700; flex-shrink: 0;
}
.step-dot.done { background: #D1FAE5; color: #059669; }
.step-dot.active { background: #4F46E5; color: #fff; box-shadow: 0 0 0 4px #C7D2FE; }
.step-dot.pending { background: #F3F4F6; color: #9CA3AF; }
.step-text { font-size: 12.5px; font-weight: 600; }
.step-text.done { color: #059669; }
.step-text.active { color: #4F46E5; }
.step-text.pending { color: #9CA3AF; }
/* ── RIGHT ── */
.right {
flex: 1;
background: linear-gradient(145deg, #1E3A6E 0%, #2D5BB5 55%, #4F8DD6 100%);
display: flex; justify-content: center; align-items: center;
position: relative; overflow: hidden;
}
.right::before {
content: ''; position: absolute;
width: 420px; height: 420px; border-radius: 50%;
border: 1px solid rgba(255,255,255,.07);
top: -80px; right: -80px;
}
.right::after {
content: ''; position: absolute;
width: 300px; height: 300px; border-radius: 50%;
border: 1px solid rgba(255,255,255,.06);
bottom: -60px; left: -60px;
}
/* ── FORM BOX ── */
.form-box { width: 340px; position: relative; z-index: 2; }
/* Icon ring */
.form-icon {
width: 64px; height: 64px; border-radius: 50%;
background: rgba(255,255,255,.12);
border: 2px solid rgba(255,255,255,.25);
display: flex; align-items: center; justify-content: center;
margin: 0 0 22px;
backdrop-filter: blur(8px);
}
.form-title {
font-size: 24px; font-weight: 800; color: #fff;
letter-spacing: -.5px; margin-bottom: 6px;
}
.form-sub {
font-size: 13px; color: rgba(255,255,255,.65);
line-height: 1.6; margin-bottom: 28px;
}
/* ── INPUT ── */
.input-wrap { position: relative; margin-bottom: 14px; }
.input-wrap svg {
position: absolute; left: 16px; top: 50%;
transform: translateY(-50%); color: rgba(255,255,255,.5); pointer-events: none;
}
.input-label {
font-size: 11px; font-weight: 700;
color: rgba(255,255,255,.5);
text-transform: uppercase; letter-spacing: 1px;
margin-bottom: 6px; display: block;
}
.input-wrap input {
width: 100%;
padding: 13px 16px 13px 44px;
border-radius: 12px;
border: 1.5px solid rgba(255,255,255,.15);
background: rgba(255,255,255,.12);
color: #fff; font-size: 14px;
font-family: 'Plus Jakarta Sans', sans-serif;
outline: none; transition: all .2s;
backdrop-filter: blur(6px);
}
.input-wrap input::placeholder { color: rgba(255,255,255,.45); }
.input-wrap input:focus {
border-color: rgba(255,255,255,.5);
background: rgba(255,255,255,.18);
box-shadow: 0 0 0 3px rgba(255,255,255,.1);
}
/* Toggle password visibility */
.toggle-pw {
position: absolute; right: 14px; top: 50%;
transform: translateY(-50%);
background: none; border: none; cursor: pointer;
color: rgba(255,255,255,.4); padding: 0;
transition: color .2s;
display: flex; align-items: center;
}
.toggle-pw:hover { color: rgba(255,255,255,.8); }
/* Password strength bar */
.pw-strength {
margin-top: 8px; margin-bottom: 4px;
display: flex; gap: 4px; height: 3px;
}
.pw-strength-bar {
flex: 1; border-radius: 99px;
background: rgba(255,255,255,.15);
transition: background .3s;
}
.pw-strength-bar.weak { background: #EF4444; }
.pw-strength-bar.medium { background: #F59E0B; }
.pw-strength-bar.strong { background: #10B981; }
.pw-strength-text {
font-size: 11px; color: rgba(255,255,255,.45);
margin-bottom: 14px; min-height: 16px;
}
/* ── BUTTON ── */
.btn-submit {
width: 100%; padding: 13px; border-radius: 12px; border: none;
background: linear-gradient(135deg, #10B981, #059669);
color: #fff; font-size: 14px; font-weight: 700;
font-family: 'Plus Jakarta Sans', sans-serif;
cursor: pointer; transition: all .2s; margin-top: 4px;
box-shadow: 0 4px 16px rgba(5,150,105,.35);
display: flex; align-items: center; justify-content: center; gap: 8px;
}
.btn-submit:hover { transform: translateY(-2px); box-shadow: 0 8px 24px rgba(5,150,105,.4); }
/* ── ALERTS ── */
.sw-alert-error {
display: flex; align-items: center; gap: 8px;
background: rgba(239,68,68,.15); border: 1px solid rgba(239,68,68,.3);
border-radius: 10px; padding: 11px 14px;
font-size: 12.5px; color: #FCA5A5; margin-bottom: 18px;
}
.sw-alert-success {
display: flex; align-items: center; gap: 8px;
background: rgba(16,185,129,.15); border: 1px solid rgba(16,185,129,.3);
border-radius: 10px; padding: 11px 14px;
font-size: 12.5px; color: #6EE7B7; margin-bottom: 18px;
}
/* ── BACK LINK ── */
.back-link {
display: flex; align-items: center; justify-content: center; gap: 6px;
margin-top: 20px;
font-size: 12.5px; color: rgba(255,255,255,.6);
text-decoration: none; transition: color .2s;
}
.back-link:hover { color: #fff; }
/* ================================================================
RESPONSIVE MOBILE
Layout: logo + info sekolah di atas, form di bawah
================================================================ */
@media (max-width: 768px) {
.page {
flex-direction: column;
height: auto;
min-height: 100vh;
}
.left {
width: 100%;
padding: 32px 24px 28px;
order: 1;
}
.left::after {
right: unset; top: unset; left: 0; bottom: 0;
width: 100%; height: 1px;
background: linear-gradient(to right, transparent, #C7D2FE 30%, #C7D2FE 70%, transparent);
}
/* Sembunyikan steps di mobile agar tidak terlalu panjang */
.steps { display: none; }
.logo { width: 180px; margin-bottom: 20px; }
.left-title { font-size: 18px; }
.left-sub { font-size: 12px; }
.left-badge { margin-top: 20px; font-size: 11px; }
.right {
order: 2;
padding: 36px 24px 52px;
min-height: auto;
align-items: flex-start;
justify-content: center;
}
.right::before,
.right::after { display: none; }
.form-box { width: 100%; max-width: 420px; }
.form-title { font-size: 21px; }
.form-sub { font-size: 12.5px; margin-bottom: 22px; }
.input-wrap input { font-size: 16px; }
}
@media (max-width: 380px) {
.left { padding: 24px 20px 22px; }
.logo { width: 150px; }
.right { padding: 28px 20px 44px; }
.form-title { font-size: 19px; }
}
</style>
</head>
<body>
<div class="page">
<!-- LEFT -->
<div class="left">
<img src="{{ asset('sbadmin2/img/logosmasa.png') }}" class="logo" alt="Logo">
<div class="left-title">SMAN 1<br>BONDOWOSO</div>
<div class="left-sub">Buat password baru untuk<br>mengamankan akun Anda</div>
<div class="left-badge"><span></span> Sistem Akademik Sekolah</div>
<!-- Step indicators -->
<div class="steps">
<div class="step">
<div class="step-dot done">
<svg width="13" height="13" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="3"><polyline points="20 6 9 17 4 12"/></svg>
</div>
<div class="step-text done">Masukkan Email</div>
</div>
<div class="step">
<div class="step-dot done">
<svg width="13" height="13" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="3"><polyline points="20 6 9 17 4 12"/></svg>
</div>
<div class="step-text done">Verifikasi OTP</div>
</div>
<div class="step">
<div class="step-dot active">3</div>
<div class="step-text active">Reset Password</div>
</div>
</div>
</div>
<!-- RIGHT -->
<div class="right">
<div class="form-box">
<div class="form-icon">
<svg width="28" height="28" viewBox="0 0 24 24" fill="none" stroke="rgba(255,255,255,0.9)" stroke-width="1.8">
<rect x="3" y="11" width="18" height="11" rx="2" ry="2"/>
<path d="M7 11V7a5 5 0 0 1 10 0v4"/>
</svg>
</div>
<div class="form-title">Reset Password</div>
<div class="form-sub">Buat password baru yang kuat<br>untuk mengamankan akun Anda.</div>
{{-- Alert Error --}}
@if(session('error'))
<div class="sw-alert-error">
<svg width="15" height="15" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.2" style="flex-shrink:0">
<circle cx="12" cy="12" r="10"/><line x1="12" y1="8" x2="12" y2="12"/><line x1="12" y1="16" x2="12.01" y2="16"/>
</svg>
{{ session('error') }}
</div>
@endif
{{-- Alert Success --}}
@if(session('success'))
<div class="sw-alert-success">
<svg width="15" height="15" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.2" style="flex-shrink:0">
<path d="M22 11.08V12a10 10 0 1 1-5.93-9.14"/><polyline points="22 4 12 14.01 9 11.01"/>
</svg>
{{ session('success') }}
</div>
@endif
<form method="POST" action="{{ route('password.update') }}">
@csrf
<input type="hidden" name="email" value="{{ session('email') ?? request('email') }}">
{{-- Password Baru --}}
<label class="input-label">Password Baru</label>
<div class="input-wrap" style="margin-bottom:6px;">
<svg width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2">
<rect x="3" y="11" width="18" height="11" rx="2" ry="2"/>
<path d="M7 11V7a5 5 0 0 1 10 0v4"/>
</svg>
<input type="password" name="password" id="pw-new"
placeholder="Minimal 8 karakter" required
oninput="checkStrength(this.value)">
<button type="button" class="toggle-pw" onclick="togglePw('pw-new', this)" tabindex="-1">
<svg width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" id="eye-new">
<path d="M1 12s4-8 11-8 11 8 11 8-4 8-11 8-11-8-11-8z"/><circle cx="12" cy="12" r="3"/>
</svg>
</button>
</div>
{{-- Strength bar --}}
<div class="pw-strength">
<div class="pw-strength-bar" id="bar1"></div>
<div class="pw-strength-bar" id="bar2"></div>
<div class="pw-strength-bar" id="bar3"></div>
<div class="pw-strength-bar" id="bar4"></div>
</div>
<div class="pw-strength-text" id="strength-text"></div>
{{-- Konfirmasi Password --}}
<label class="input-label">Konfirmasi Password</label>
<div class="input-wrap">
<svg width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2">
<polyline points="9 11 12 14 22 4"/>
<path d="M21 12v7a2 2 0 0 1-2 2H5a2 2 0 0 1-2-2V5a2 2 0 0 1 2-2h11"/>
</svg>
<input type="password" name="password_confirmation" id="pw-confirm"
placeholder="Ulangi password baru" required>
<button type="button" class="toggle-pw" onclick="togglePw('pw-confirm', this)" tabindex="-1">
<svg width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" id="eye-confirm">
<path d="M1 12s4-8 11-8 11 8 11 8-4 8-11 8-11-8-11-8z"/><circle cx="12" cy="12" r="3"/>
</svg>
</button>
</div>
<button type="submit" class="btn-submit">
<svg width="15" height="15" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.3">
<path d="M19 21H5a2 2 0 0 1-2-2V5a2 2 0 0 1 2-2h11l5 5v11a2 2 0 0 1-2 2z"/>
<polyline points="17 21 17 13 7 13 7 21"/>
<polyline points="7 3 7 8 15 8"/>
</svg>
Simpan Password Baru
</button>
</form>
<a href="{{ route('login') }}" class="back-link">
<svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.3">
<line x1="19" y1="12" x2="5" y2="12"/><polyline points="12 19 5 12 12 5"/>
</svg>
Kembali ke Login
</a>
</div>
</div>
</div>
<script>
// ── Toggle show/hide password ──
function togglePw(id, btn) {
const inp = document.getElementById(id);
const isHidden = inp.type === 'password';
inp.type = isHidden ? 'text' : 'password';
btn.querySelector('svg').innerHTML = isHidden
? '<line x1="1" y1="1" x2="23" y2="23"/><path d="M17.94 17.94A10.07 10.07 0 0 1 12 20c-7 0-11-8-11-8a18.45 18.45 0 0 1 5.06-5.94"/><path d="M9.9 4.24A9.12 9.12 0 0 1 12 4c7 0 11 8 11 8a18.5 18.5 0 0 1-2.16 3.19"/>'
: '<path d="M1 12s4-8 11-8 11 8 11 8-4 8-11 8-11-8-11-8z"/><circle cx="12" cy="12" r="3"/>';
}
// ── Password strength checker ──
function checkStrength(val) {
const bars = [
document.getElementById('bar1'),
document.getElementById('bar2'),
document.getElementById('bar3'),
document.getElementById('bar4'),
];
const txt = document.getElementById('strength-text');
// Reset
bars.forEach(b => { b.className = 'pw-strength-bar'; });
if (!val) { txt.textContent = ''; return; }
let score = 0;
if (val.length >= 8) score++;
if (/[A-Z]/.test(val)) score++;
if (/[0-9]/.test(val)) score++;
if (/[^A-Za-z0-9]/.test(val)) score++;
const levels = [
{ cls: 'weak', label: 'Lemah', color: '#EF4444' },
{ cls: 'weak', label: 'Lemah', color: '#EF4444' },
{ cls: 'medium', label: 'Sedang', color: '#F59E0B' },
{ cls: 'strong', label: 'Kuat', color: '#10B981' },
{ cls: 'strong', label: 'Sangat Kuat', color: '#10B981' },
];
const lv = levels[score] || levels[0];
for (let i = 0; i < score; i++) bars[i].classList.add(lv.cls);
txt.textContent = lv.label;
txt.style.color = lv.color;
}
</script>
</body>
</html>