1
This commit is contained in:
parent
de71b1f24e
commit
c8f72f3d98
@ -1,11 +1,6 @@
|
||||
<%- include('partials/header') %>
|
||||
|
||||
<style>
|
||||
|
||||
/* =========================
|
||||
LAYOUT
|
||||
========================= */
|
||||
|
||||
.step { display: none; }
|
||||
.step.active { display: block; }
|
||||
|
||||
@ -31,15 +26,12 @@
|
||||
color: #3b3be3;
|
||||
}
|
||||
|
||||
/* Mobile */
|
||||
@media(max-width:768px){
|
||||
h4{font-size:18px;}
|
||||
button{width:100%;}
|
||||
}
|
||||
|
||||
</style>
|
||||
|
||||
|
||||
<div class="container-form">
|
||||
|
||||
<% if (typeof error !== 'undefined') { %>
|
||||
@ -50,8 +42,6 @@
|
||||
|
||||
<h3 class="text-center mb-4">Mitglied werden</h3>
|
||||
|
||||
|
||||
<!-- Fortschritt -->
|
||||
<div class="progress">
|
||||
<div id="progressBar"
|
||||
class="progress-bar bg-primary"
|
||||
@ -59,84 +49,54 @@
|
||||
</div>
|
||||
</div>
|
||||
|
||||
|
||||
<!-- Navigation -->
|
||||
<div class="step-nav text-center mb-3">
|
||||
<span id="nav1" class="active">Daten</span>
|
||||
<span id="nav1">Daten</span>
|
||||
<span id="nav2">Bank</span>
|
||||
<span id="nav3">Prüfen</span>
|
||||
</div>
|
||||
|
||||
|
||||
<form method="POST" action="/register/create" id="registerForm">
|
||||
|
||||
|
||||
<!-- ========================= -->
|
||||
<!-- STEP 1 -->
|
||||
<!-- ========================= -->
|
||||
<div class="step active" id="step1">
|
||||
<!-- ================= STEP 1 ================= -->
|
||||
<div class="step" id="step1">
|
||||
|
||||
<h4>Mitgliedsdaten</h4>
|
||||
|
||||
<div class="row g-3">
|
||||
|
||||
<input name="vorname" class="form-control" placeholder="Vorname" required>
|
||||
|
||||
<input name="nachname" class="form-control" placeholder="Nachname" required>
|
||||
<input name="vorname" class="form-control mb-2" placeholder="Vorname" required>
|
||||
<input name="nachname" class="form-control mb-2" placeholder="Nachname" required>
|
||||
|
||||
<input type="date"
|
||||
name="geburtsdatum"
|
||||
id="geburtsdatum"
|
||||
class="form-control"
|
||||
class="form-control mb-2"
|
||||
required>
|
||||
|
||||
<input name="mobil" class="form-control" placeholder="Mobilnummer" required>
|
||||
|
||||
<input type="email" name="email" class="form-control" placeholder="E-Mail" required>
|
||||
|
||||
<input name="mobil" class="form-control mb-2" placeholder="Mobilnummer" required>
|
||||
<input type="email" name="email" class="form-control mb-2" placeholder="E-Mail" required>
|
||||
|
||||
<h5 class="mt-3">Adresse</h5>
|
||||
|
||||
<input name="strasse" class="form-control" placeholder="Straße" required>
|
||||
<input name="strasse" class="form-control mb-2" placeholder="Straße" required>
|
||||
<input name="hausnummer" class="form-control mb-2" placeholder="Nr." required>
|
||||
<input name="plz" class="form-control mb-2" placeholder="PLZ" required>
|
||||
<input name="ort" class="form-control mb-2" placeholder="Ort" required>
|
||||
<input name="land" class="form-control mb-2" value="Deutschland">
|
||||
|
||||
<input name="hausnummer" class="form-control" placeholder="Nr." required>
|
||||
|
||||
<input name="plz" class="form-control" placeholder="PLZ" required>
|
||||
|
||||
<input name="ort" class="form-control" placeholder="Ort" required>
|
||||
|
||||
<input name="land" class="form-control" value="Deutschland">
|
||||
|
||||
</div>
|
||||
|
||||
|
||||
<button type="button"
|
||||
class="btn btn-primary mt-4"
|
||||
onclick="nextStep(2)">
|
||||
Weiter →
|
||||
<button type="button" class="btn btn-primary mt-3" onclick="nextStep(2)">
|
||||
Weiter →
|
||||
</button>
|
||||
|
||||
</div>
|
||||
|
||||
|
||||
|
||||
<!-- ========================= -->
|
||||
<!-- STEP 2 -->
|
||||
<!-- ========================= -->
|
||||
<!-- ================= STEP 2 ================= -->
|
||||
<div class="step" id="step2">
|
||||
|
||||
<h4>Bankdaten</h4>
|
||||
|
||||
<div class="row g-3">
|
||||
|
||||
<input name="kontoinhaber" class="form-control" placeholder="Kontoinhaber" required>
|
||||
|
||||
<input name="mandatsreferenz" class="form-control" placeholder="Mandatsreferenz" required>
|
||||
|
||||
<input name="iban" class="form-control" placeholder="IBAN" required>
|
||||
|
||||
<input name="bic" class="form-control" placeholder="BIC" required>
|
||||
|
||||
<input name="kontoinhaber" class="form-control mb-2" placeholder="Kontoinhaber" required>
|
||||
<input name="mandatsreferenz" class="form-control mb-2" placeholder="Mandatsreferenz" required>
|
||||
<input name="iban" class="form-control mb-2" placeholder="IBAN" required>
|
||||
<input name="bic" class="form-control mb-2" placeholder="BIC" required>
|
||||
|
||||
<div class="form-check mt-2">
|
||||
<input class="form-check-input"
|
||||
@ -144,139 +104,92 @@
|
||||
name="agreeSepa"
|
||||
value="on"
|
||||
required>
|
||||
|
||||
<label class="form-check-label">
|
||||
SEPA-Mandat erteilen
|
||||
</label>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
|
||||
<div class="d-flex justify-content-between mt-4">
|
||||
|
||||
<button type="button"
|
||||
class="btn btn-secondary"
|
||||
onclick="nextStep(1)">
|
||||
← Zurück
|
||||
<button type="button" class="btn btn-secondary" onclick="nextStep(1)">
|
||||
← Zurück
|
||||
</button>
|
||||
|
||||
<button type="button"
|
||||
class="btn btn-primary"
|
||||
onclick="nextStep(3)">
|
||||
Weiter →
|
||||
<button type="button" class="btn btn-primary" onclick="nextStep(3)">
|
||||
Weiter →
|
||||
</button>
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
|
||||
|
||||
<!-- ========================= -->
|
||||
<!-- STEP 3 -->
|
||||
<!-- ========================= -->
|
||||
<!-- ================= STEP 3 ================= -->
|
||||
<div class="step" id="step3">
|
||||
|
||||
<h4>Zusammenfassung</h4>
|
||||
|
||||
<div class="card p-3 mb-3 bg-light">
|
||||
|
||||
<div id="summaryBox"></div>
|
||||
|
||||
</div>
|
||||
|
||||
|
||||
<h5>Vertrag</h5>
|
||||
|
||||
<select name="vertragsvariante"
|
||||
class="form-select mb-3"
|
||||
required>
|
||||
|
||||
<select name="vertragsvariante" class="form-select mb-3" required>
|
||||
<option value="">Bitte wählen</option>
|
||||
|
||||
<% vertragsarten.forEach(v => { %>
|
||||
|
||||
<option value="<%= v.id %>">
|
||||
<%= v.name %> – <%= v.betrag.toFixed(2) %> €
|
||||
</option>
|
||||
|
||||
<% }) %>
|
||||
|
||||
</select>
|
||||
|
||||
|
||||
<h5>Rechtliches</h5>
|
||||
|
||||
|
||||
<!-- Eltern-Zustimmung -->
|
||||
<div class="form-check mb-2 d-none" id="consentBox">
|
||||
|
||||
<input class="form-check-input"
|
||||
type="checkbox"
|
||||
name="agreeConsent"
|
||||
id="agreeConsent"
|
||||
value="on">
|
||||
|
||||
<label class="form-check-label">
|
||||
Einverständnis der Erziehungsberechtigten
|
||||
</label>
|
||||
|
||||
</div>
|
||||
|
||||
|
||||
<!-- AGB -->
|
||||
<div class="form-check mb-3">
|
||||
|
||||
<input class="form-check-input"
|
||||
type="checkbox"
|
||||
name="agreeAgb"
|
||||
value="on"
|
||||
required>
|
||||
|
||||
<label class="form-check-label">
|
||||
AGB akzeptiert
|
||||
</label>
|
||||
|
||||
</div>
|
||||
|
||||
|
||||
<div class="d-flex justify-content-between mt-4">
|
||||
|
||||
<button type="button"
|
||||
class="btn btn-secondary"
|
||||
onclick="nextStep(2)">
|
||||
← Zurück
|
||||
<button type="button" class="btn btn-secondary" onclick="nextStep(2)">
|
||||
← Zurück
|
||||
</button>
|
||||
|
||||
<button type="submit"
|
||||
class="btn btn-success btn-lg">
|
||||
Abschließen
|
||||
<button type="submit" class="btn btn-success btn-lg">
|
||||
Abschließen
|
||||
</button>
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
|
||||
</form>
|
||||
</div>
|
||||
|
||||
|
||||
|
||||
<script>
|
||||
|
||||
/* ============================
|
||||
STEPS
|
||||
============================ */
|
||||
|
||||
let currentStep = 1;
|
||||
window.fromServerError = <%= typeof errorStep !== 'undefined' ? 'true' : 'false' %>;
|
||||
let currentStep = <%= typeof errorStep !== 'undefined' ? errorStep : 1 %>;
|
||||
|
||||
const form = document.getElementById('registerForm');
|
||||
|
||||
function nextStep(step){
|
||||
|
||||
// Nur vorwärts validieren
|
||||
if(step > currentStep){
|
||||
if(step > currentStep && !window.fromServerError){
|
||||
if(!validateStep(currentStep)) return;
|
||||
}
|
||||
|
||||
@ -299,145 +212,83 @@ function nextStep(step){
|
||||
}
|
||||
}
|
||||
|
||||
function validateStep(step){
|
||||
const container = document.getElementById('step'+step);
|
||||
const fields = container.querySelectorAll('input,select');
|
||||
|
||||
/* ============================
|
||||
ALTER PRÜFEN
|
||||
============================ */
|
||||
for(let field of fields){
|
||||
if(!field.checkValidity()){
|
||||
field.reportValidity();
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
function updateProgress(){
|
||||
document.getElementById('progressBar')
|
||||
.style.width = (currentStep * 33) + '%';
|
||||
}
|
||||
|
||||
function updateNav(){
|
||||
document.querySelectorAll('.step-nav span')
|
||||
.forEach(n => n.classList.remove('active'));
|
||||
|
||||
document.getElementById('nav'+currentStep)
|
||||
.classList.add('active');
|
||||
}
|
||||
|
||||
function isUnder18(){
|
||||
|
||||
const bday =
|
||||
document.getElementById('geburtsdatum').value;
|
||||
|
||||
const bday = document.getElementById('geburtsdatum').value;
|
||||
if(!bday) return false;
|
||||
|
||||
const birth = new Date(bday);
|
||||
const today = new Date();
|
||||
|
||||
let age = today.getFullYear() - birth.getFullYear();
|
||||
|
||||
if(
|
||||
today.getMonth() < birth.getMonth() ||
|
||||
(today.getMonth() === birth.getMonth() &&
|
||||
today.getDate() < birth.getDate())
|
||||
){
|
||||
if(today.getMonth() < birth.getMonth() ||
|
||||
(today.getMonth() === birth.getMonth() &&
|
||||
today.getDate() < birth.getDate())){
|
||||
age--;
|
||||
}
|
||||
|
||||
return age < 18;
|
||||
}
|
||||
|
||||
|
||||
function checkAgeAndConsent(){
|
||||
|
||||
const box = document.getElementById('consentBox');
|
||||
const checkbox = document.getElementById('agreeConsent');
|
||||
|
||||
if(isUnder18()){
|
||||
|
||||
box.classList.remove('d-none');
|
||||
checkbox.required = true;
|
||||
|
||||
}else{
|
||||
|
||||
box.classList.add('d-none');
|
||||
checkbox.required = false;
|
||||
checkbox.checked = true;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* ============================
|
||||
VALIDIERUNG
|
||||
============================ */
|
||||
|
||||
function validateStep(step){
|
||||
|
||||
const container =
|
||||
document.getElementById('step'+step);
|
||||
|
||||
const fields =
|
||||
container.querySelectorAll('input,select');
|
||||
|
||||
for(let field of fields){
|
||||
|
||||
if(!field.checkValidity()){
|
||||
field.reportValidity();
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
/* ============================
|
||||
PROGRESS
|
||||
============================ */
|
||||
|
||||
function updateProgress(){
|
||||
|
||||
const percent = currentStep * 33;
|
||||
|
||||
document.getElementById('progressBar')
|
||||
.style.width = percent + '%';
|
||||
}
|
||||
|
||||
|
||||
/* ============================
|
||||
NAV
|
||||
============================ */
|
||||
|
||||
function updateNav(){
|
||||
|
||||
document.querySelectorAll('.step-nav span')
|
||||
.forEach(n => n.classList.remove('active'));
|
||||
|
||||
document.getElementById('nav'+currentStep)
|
||||
.classList.add('active');
|
||||
}
|
||||
|
||||
|
||||
/* ============================
|
||||
AUTO SAVE (MIT CHECKBOX FIX)
|
||||
============================ */
|
||||
|
||||
const form = document.getElementById('registerForm');
|
||||
|
||||
form.addEventListener('input', saveForm);
|
||||
|
||||
|
||||
function saveForm(){
|
||||
|
||||
const data = {};
|
||||
|
||||
Array.from(form.elements).forEach(el=>{
|
||||
|
||||
if(!el.name) return;
|
||||
|
||||
if(el.type === 'checkbox'){
|
||||
data[el.name] = el.checked ? 'on' : '';
|
||||
}else{
|
||||
data[el.name] = el.value;
|
||||
}
|
||||
});
|
||||
|
||||
localStorage.setItem('registerData',
|
||||
JSON.stringify(data));
|
||||
localStorage.setItem('registerData', JSON.stringify(data));
|
||||
}
|
||||
|
||||
|
||||
function loadForm(){
|
||||
|
||||
const data =
|
||||
JSON.parse(localStorage.getItem('registerData'));
|
||||
|
||||
const data = JSON.parse(localStorage.getItem('registerData'));
|
||||
if(!data) return;
|
||||
|
||||
Object.keys(data).forEach(key=>{
|
||||
|
||||
const field = form.elements[key];
|
||||
|
||||
if(!field) return;
|
||||
|
||||
if(field.type === 'checkbox'){
|
||||
@ -448,42 +299,27 @@ function loadForm(){
|
||||
});
|
||||
}
|
||||
|
||||
loadForm();
|
||||
|
||||
|
||||
/* ============================
|
||||
SUMMARY
|
||||
============================ */
|
||||
|
||||
function buildSummary(){
|
||||
|
||||
const data =
|
||||
JSON.parse(localStorage.getItem('registerData'));
|
||||
|
||||
const data = JSON.parse(localStorage.getItem('registerData'));
|
||||
if(!data) return;
|
||||
|
||||
let html = `
|
||||
document.getElementById('summaryBox').innerHTML = `
|
||||
<b>Name:</b> ${data.vorname} ${data.nachname}<br>
|
||||
<b>Geburtsdatum:</b> ${data.geburtsdatum}<br>
|
||||
<b>Email:</b> ${data.email}<br>
|
||||
<b>Mobil:</b> ${data.mobil}<br>
|
||||
<b>Adresse:</b>
|
||||
${data.strasse} ${data.hausnummer},
|
||||
${data.plz} ${data.ort}<br>
|
||||
<b>IBAN:</b> ${data.iban}<br>
|
||||
<b>Adresse:</b> ${data.strasse} ${data.hausnummer}, ${data.plz} ${data.ort}<br>
|
||||
<b>IBAN:</b> ${data.iban}
|
||||
`;
|
||||
|
||||
document.getElementById('summaryBox').innerHTML = html;
|
||||
}
|
||||
|
||||
|
||||
/* ============================
|
||||
CLEAR AFTER SUBMIT
|
||||
============================ */
|
||||
|
||||
form.addEventListener('submit',()=>{
|
||||
localStorage.removeItem('registerData');
|
||||
});
|
||||
|
||||
loadForm();
|
||||
setTimeout(()=>{ nextStep(currentStep); },100);
|
||||
|
||||
</script>
|
||||
|
||||
<%- include('partials/footer') %>
|
||||
Loading…
Reference in New Issue
Block a user