feat: implement internship application wizard with terms acceptance and multi-step form view

This commit is contained in:
Ümit Tunç
2026-06-01 23:43:59 +03:00
parent 23f24e426b
commit 36ec1823c8
7 changed files with 491 additions and 118 deletions
+437 -118
View File
@@ -12,133 +12,245 @@
<section class="wrapper bg-white py-12 lg:py-20">
<div class="container px-4">
<div class="text-center mb-12">
<h2 class="text-xs uppercase font-bold tracking-widest text-[#e31e24] mb-2">{{ __('career.remote_work_title', ['default' => 'Süreç Nasıl İşliyor?']) }}</h2>
<h3 class="text-3xl md:text-4xl font-extrabold text-slate-900">{{ __('career.remote_work_title', ['default' => 'Tamamen Uzaktan Staj Deneyimi']) }}</h3>
</div>
<div class="flex flex-col lg:flex-row items-center gap-12 mb-20 max-w-6xl mx-auto">
<div class="w-full lg:w-3/5">
<div class="bg-white p-4 md:p-8 rounded-3xl shadow-2xl border border-slate-100 overflow-hidden flex justify-center">
<pre class="mermaid">
graph TD
A[İnternet Üzerinden Başvuru] --> B{Uzaktan Çalışma Koşulları}
B -- Uygun --> C[CV ve Evrakların İletilmesi]
B -- Uygun Değil --> D[Süreç Sonlandırılır]
C --> E[Ön Değerlendirme]
E --> F[Teknik Görüşme]
F --> G[Projelere Dahil Edilme]
style A fill:#f8fafc,stroke:#cbd5e1,stroke-width:2px
style G fill:#e31e24,stroke:#fff,stroke-width:2px,color:#fff
style B fill:#fff1f2,stroke:#fecdd3
</pre>
<!-- Wizard Progress Tracker -->
<div class="max-w-md mx-auto mb-16">
<div class="relative flex items-center justify-between">
<!-- Progress Line -->
<div class="absolute left-0 top-1/2 -translate-y-1/2 w-full h-1 bg-slate-100 -z-10 rounded-full">
<div id="wizard-progress-bar" class="h-full bg-[#e31e24] rounded-full transition-all duration-500 w-[0%]"></div>
</div>
</div>
<div class="w-full lg:w-2/5 space-y-8">
<h4 class="text-2xl font-bold text-slate-900">{{ __('career.application_conditions_title', ['default' => 'Başvuru Şartları ve Çalışma Modeli']) }}</h4>
<div class="space-y-6">
<div class="flex items-start gap-4">
<div class="flex-shrink-0 w-8 h-8 rounded-full bg-red-50 flex items-center justify-center text-[#e31e24]">
<i class="uil uil-check-circle text-xl"></i>
</div>
<div>
<span class="font-bold text-slate-800 block text-sm">{{ __('career.daily_standup', ['default' => 'Günlük Standup:']) }}</span>
<p class="text-sm text-slate-500">{{ __('career.daily_standup_desc', ['default' => 'Her gün düzenlenen kısa toplantılarla ekip içi iletişim ve ilerleme takibi sağlanır.']) }}</p>
</div>
<!-- Step 1 Dot -->
<div class="flex flex-col items-center">
<div id="step-dot-1" class="w-12 h-12 rounded-full bg-[#e31e24] text-white flex items-center justify-center font-extrabold shadow-lg shadow-red-500/20 transition-all duration-500 ring-4 ring-red-100">
<i class="uil uil-info-circle text-xl"></i>
</div>
<div class="flex items-start gap-4">
<div class="flex-shrink-0 w-8 h-8 rounded-full bg-red-50 flex items-center justify-center text-[#e31e24]">
<i class="uil uil-check-circle text-xl"></i>
</div>
<div>
<span class="font-bold text-slate-800 block text-sm">{{ __('career.flexible_projects', ['default' => 'Esnek Projeler:']) }}</span>
<p class="text-sm text-slate-500">{{ __('career.flexible_projects_desc', ['default' => 'Projelerimizde esneklik esastır. Yeteneklerinize uygun gerçek projelerde görev alırsınız.']) }}</p>
</div>
</div>
<div class="flex items-start gap-4">
<div class="flex-shrink-0 w-8 h-8 rounded-full bg-red-50 flex items-center justify-center text-[#e31e24]">
<i class="uil uil-check-circle text-xl"></i>
</div>
<div>
<span class="font-bold text-slate-800 block text-sm">{{ __('career.focus_on_development', ['default' => 'Gelişim Odaklılık:']) }}</span>
<p class="text-sm text-slate-500">{{ __('career.condition_not_only_for_internship', ['default' => 'Yalnızca staj yapmak için yapmak isteyen kişiler alınmamaktadır.']) }}</p>
</div>
</div>
<div class="flex items-start gap-4">
<div class="flex-shrink-0 w-8 h-8 rounded-full bg-red-50 flex items-center justify-center text-[#e31e24]">
<i class="uil uil-check-circle text-xl"></i>
</div>
<div>
<span class="font-bold text-slate-800 block text-sm">{{ __('career.intent_letter', ['default' => 'Niyet Mektubu:']) }}</span>
<p class="text-sm text-slate-500">{{ __('career.condition_intent_letter', ['default' => 'Mesaj bölümünde nasıl bir katkı sağlayacağınızın niyet mektubu iletilmelidir.']) }}</p>
</div>
<span id="step-label-1" class="text-xs md:text-sm font-bold text-slate-800 mt-3 transition-all duration-300">{{ __('career.intern_step_1_title') }}</span>
</div>
<!-- Step 2 Dot -->
<div class="flex flex-col items-center">
<div id="step-dot-2" class="w-12 h-12 rounded-full bg-slate-100 text-slate-400 flex items-center justify-center font-extrabold transition-all duration-500 ring-4 ring-transparent">
<i class="uil uil-check-circle text-xl"></i>
</div>
<span id="step-label-2" class="text-xs md:text-sm font-medium text-slate-400 mt-3 transition-all duration-300">{{ __('career.intern_step_2_title') }}</span>
</div>
</div>
</div>
<div class="max-w-4xl mx-auto">
<div class="bg-white rounded-[2rem] shadow-2xl overflow-hidden border border-slate-100">
<div class="p-8 md:p-12">
<div class="mb-10">
<h2 class="text-2xl font-bold text-slate-900 mb-2">{{ __('career.internship_title') }}</h2>
<div class="w-12 h-1 bg-[#e31e24] rounded-full"></div>
<!-- Main Form Container -->
<form action="{{ route('career.store') }}" method="POST" enctype="multipart/form-data" id="career-application-form">
@csrf
<input type="hidden" name="type" value="internship">
<!-- ================= STEP 1: TERMS & CONDITIONS ================= -->
<div id="step-content-1" class="wizard-step transition-all duration-500 opacity-100 block">
<div class="max-w-5xl mx-auto mb-12">
<!-- Welcome Message -->
<div class="bg-blue-50 border-l-4 border-blue-500 p-8 rounded-r-2xl shadow-sm mb-12">
<h4 class="text-xl font-bold text-blue-900 mb-4">{{ __('career.dear_intern') }}</h4>
<div class="text-blue-800 space-y-4 leading-relaxed text-sm md:text-base">
<p>{!! __('career.intern_welcome_text_1') !!}</p>
<p>{!! __('career.intern_welcome_text_2') !!}</p>
</div>
</div>
<form action="{{ route('career.store') }}" method="POST" enctype="multipart/form-data" class="space-y-6" id="career-application-form">
@csrf
<input type="hidden" name="type" value="internship">
<div class="grid grid-cols-1 md:grid-cols-12 gap-6 items-center">
<label for="name" class="md:col-span-3 text-sm font-bold text-slate-700 md:text-right">{{ __('career.name', ['default' => 'Ad Soyad']) }} <span class="text-[#e31e24]">*</span></label>
<div class="md:col-span-9">
<input type="text" name="name" id="name" class="w-full px-5 py-3 rounded-xl border border-slate-200 focus:ring-4 focus:ring-red-500/10 focus:border-[#e31e24] outline-none transition-all placeholder-slate-300" placeholder="Örn: Ahmet Yılmaz" value="{{ old('name') }}" required>
<div class="text-center mb-12">
<h2 class="text-xs uppercase font-bold tracking-widest text-[#e31e24] mb-2">{{ __('career.remote_work_title', ['default' => 'Süreç Nasıl İşliyor?']) }}</h2>
<h3 class="text-3xl md:text-4xl font-extrabold text-slate-900">{{ __('career.remote_work_title', ['default' => 'Tamamen Uzaktan Staj Deneyimi']) }}</h3>
</div>
<div class="flex flex-col lg:flex-row gap-12 items-start mb-12">
<!-- Mermaid Flowchart Canvas -->
<div class="w-full lg:w-3/5">
<div id="mermaid-card" class="relative bg-white p-6 md:p-8 rounded-3xl shadow-xl border border-slate-100 overflow-x-auto flex flex-col items-center">
<!-- Fullscreen Toggle Button -->
<button type="button" onclick="toggleFullscreen()" class="absolute top-4 right-4 p-2.5 rounded-xl bg-slate-50 hover:bg-slate-100 border border-slate-100 hover:border-slate-200 text-slate-500 hover:text-slate-700 transition-all duration-200 shadow-sm flex items-center justify-center z-10" title="Tam Ekran / Fullscreen">
<i id="fullscreen-icon" class="uil uil-expand-arrows-alt text-lg"></i>
</button>
<span class="text-xs font-bold text-slate-400 uppercase tracking-widest mb-4"><i class="uil uil-presentation-play mr-1"></i> {{ __('career.hr_flow_diagram') }}</span>
<div class="mermaid w-full flex justify-center" style="min-height: 400px;">
graph TD
%% Styles
classDef startNode fill:#3b82f6,stroke:#1d4ed8,stroke-width:2px,color:#fff,font-weight:bold,rx:10px,ry:10px;
classDef decisionNode fill:#eab308,stroke:#ca8a04,stroke-width:2px,color:#1e293b,font-weight:bold;
classDef processNode fill:#10b981,stroke:#047857,stroke-width:2px,color:#fff,font-weight:bold,rx:5px,ry:5px;
classDef rejectNode fill:#ef4444,stroke:#b91c1c,stroke-width:2px,color:#fff,font-weight:bold,rx:5px,ry:5px;
classDef actionNode fill:#8b5cf6,stroke:#6d28d9,stroke-width:2px,color:#fff,font-weight:bold,rx:5px,ry:5px;
Start["{{ __('career.mermaid_start') }}"]:::startNode
Dec1{"{{ __('career.mermaid_dec1') }}"}:::decisionNode
Red1["{{ __('career.mermaid_red1') }}"]:::rejectNode
GitAccess["{{ __('career.mermaid_git') }}"]:::processNode
SampleTask["{{ __('career.mermaid_sample') }}"]:::processNode
Dec2{"{{ __('career.mermaid_dec2') }}"}:::decisionNode
Red2["{{ __('career.mermaid_red2') }}"]:::rejectNode
Issues["{{ __('career.mermaid_issues') }}"]:::processNode
Dec3{"{{ __('career.mermaid_dec3') }}"}:::decisionNode
WaitTask["{{ __('career.mermaid_wait') }}"]:::actionNode
Assign["{{ __('career.mermaid_assign') }}"]:::processNode
WorkStart["{{ __('career.mermaid_work') }}"]:::processNode
Review["{{ __('career.mermaid_review') }}"]:::processNode
Dec4{"{{ __('career.mermaid_dec4') }}"}:::decisionNode
Feedback["{{ __('career.mermaid_feedback') }}"]:::actionNode
Payment["{{ __('career.mermaid_payment') }}"]:::processNode
Start --> Dec1
Dec1 -- "Hayır" --> Red1
Dec1 -- "Evet" --> GitAccess
GitAccess --> SampleTask
SampleTask --> Dec2
Dec2 -- "Hayır" --> Red2
Dec2 -- "Evet" --> Issues
Issues --> Dec3
Dec3 -- "Hayır" --> WaitTask
Dec3 -- "Evet" --> Assign
Assign --> WorkStart
WorkStart --> Review
Review --> Dec4
Dec4 -- "Hayır" --> Feedback
Feedback --> WorkStart
Dec4 -- "Evet" --> Payment
Payment --> Issues
</div>
</div>
</div>
<div class="grid grid-cols-1 md:grid-cols-12 gap-6 items-center">
<label for="email" class="md:col-span-3 text-sm font-bold text-slate-700 md:text-right">{{ __('career.email', ['default' => 'E-posta']) }} <span class="text-[#e31e24]">*</span></label>
<div class="md:col-span-9">
<input type="email" name="email" id="email" class="w-full px-5 py-3 rounded-xl border border-slate-200 focus:ring-4 focus:ring-red-500/10 focus:border-[#e31e24] outline-none transition-all placeholder-slate-300" placeholder="Örn: ahmet@example.com" value="{{ old('email') }}" required>
<!-- Conditions & Model Requirements -->
<div class="w-full lg:w-2/5 space-y-8">
<h4 class="text-2xl font-bold text-slate-900">{{ __('career.application_conditions_title', ['default' => 'Başvuru Şartları ve Çalışma Modeli']) }}</h4>
<div class="space-y-6">
<div class="flex items-start gap-4">
<div class="flex-shrink-0 w-8 h-8 rounded-full bg-red-50 flex items-center justify-center text-[#e31e24]">
<i class="uil uil-check-circle text-xl"></i>
</div>
<div>
<span class="font-bold text-slate-800 block text-sm">{{ __('career.daily_standup', ['default' => 'Günlük Standup:']) }}</span>
<p class="text-sm text-slate-500">{{ __('career.daily_standup_desc', ['default' => 'Her gün düzenlenen kısa toplantılarla ekip içi iletişim ve ilerleme takibi sağlanır.']) }}</p>
</div>
</div>
<div class="flex items-start gap-4">
<div class="flex-shrink-0 w-8 h-8 rounded-full bg-red-50 flex items-center justify-center text-[#e31e24]">
<i class="uil uil-check-circle text-xl"></i>
</div>
<div>
<span class="font-bold text-slate-800 block text-sm">{{ __('career.flexible_projects', ['default' => 'Esnek Projeler:']) }}</span>
<p class="text-sm text-slate-500">{{ __('career.flexible_projects_desc', ['default' => 'Projelerimizde esneklik esastır. Yeteneklerinize uygun gerçek projelerde görev alırsınız.']) }}</p>
</div>
</div>
<div class="flex items-start gap-4">
<div class="flex-shrink-0 w-8 h-8 rounded-full bg-red-50 flex items-center justify-center text-[#e31e24]">
<i class="uil uil-check-circle text-xl"></i>
</div>
<div>
<span class="font-bold text-slate-800 block text-sm">{{ __('career.focus_on_development', ['default' => 'Gelişim Odaklılık:']) }}</span>
<p class="text-sm text-slate-500">{{ __('career.condition_not_only_for_internship', ['default' => 'Yalnızca staj yapmak için yapmak isteyen kişiler alınmamaktadır.']) }}</p>
</div>
</div>
<div class="flex items-start gap-4">
<div class="flex-shrink-0 w-8 h-8 rounded-full bg-red-50 flex items-center justify-center text-[#e31e24]">
<i class="uil uil-check-circle text-xl"></i>
</div>
<div>
<span class="font-bold text-slate-800 block text-sm">{{ __('career.intent_letter', ['default' => 'Niyet Mektubu:']) }}</span>
<p class="text-sm text-slate-500">{{ __('career.condition_intent_letter', ['default' => 'Mesaj bölümünde nasıl bir katkı sağlayacağınızın niyet mektubu iletilmelidir.']) }}</p>
</div>
</div>
</div>
</div>
<div class="grid grid-cols-1 md:grid-cols-12 gap-6 items-center">
<label for="phone" class="md:col-span-3 text-sm font-bold text-slate-700 md:text-right">{{ __('career.phone', ['default' => 'Telefon']) }}</label>
<div class="md:col-span-9">
<input type="text" name="phone" id="phone" class="w-full px-5 py-3 rounded-xl border border-slate-200 focus:ring-4 focus:ring-red-500/10 focus:border-[#e31e24] outline-none transition-all placeholder-slate-300" placeholder="Örn: 05XX XXX XX XX" value="{{ old('phone') }}">
</div>
</div>
<div class="grid grid-cols-1 md:grid-cols-12 gap-6 items-center">
<label for="cv" class="md:col-span-3 text-sm font-bold text-slate-700 md:text-right">{{ __('career.cv', ['default' => 'Özgeçmiş (CV)']) }} <span class="text-[#e31e24]">*</span></label>
<div class="md:col-span-9">
<input type="file" name="cv" id="cv" class="w-full px-5 py-2.5 rounded-xl border border-slate-200 file:mr-4 file:py-2 file:px-4 file:rounded-full file:border-0 file:text-xs file:font-semibold file:bg-red-50 file:text-[#e31e24] hover:file:bg-red-100 transition-all" required>
<p class="mt-2 text-xs text-slate-400">PDF, DOC, DOCX (Maks. 5MB)</p>
</div>
</div>
<div class="grid grid-cols-1 md:grid-cols-12 gap-6 items-start">
<label for="message" class="md:col-span-3 text-sm font-bold text-slate-700 md:text-right pt-3">{{ __('career.message', ['default' => 'Mesajınız']) }}</label>
<div class="md:col-span-9">
<textarea name="message" id="message" class="w-full px-5 py-4 rounded-xl border border-slate-200 focus:ring-4 focus:ring-red-500/10 focus:border-[#e31e24] outline-none transition-all placeholder-slate-300 min-h-[150px]" placeholder="Staj beklentileriniz ve çalışma alanlarınız hakkında bilgi verebilirsiniz...">{{ old('message') }}</textarea>
</div>
</div>
<div class="grid grid-cols-1 md:grid-cols-12 gap-6">
<div class="md:col-start-4 md:col-span-9">
<button type="submit" id="submit-btn" class="w-full md:w-auto px-10 py-4 bg-[#e31e24] hover:bg-[#c4191f] text-white font-bold rounded-full transition-all shadow-lg shadow-red-500/30 flex items-center justify-center gap-3">
<span class="btn-text">{{ __('career.submit', ['default' => 'Başvuruyu Gönder']) }}</span>
<span class="spinner-border spinner-border-sm hidden animate-spin w-4 h-4 border-2 border-white border-t-transparent rounded-full" role="status"></span>
<i class="uil uil-arrow-right text-xl btn-icon"></i>
<!-- Terms Acceptance & Next Trigger -->
<div class="bg-slate-50 p-6 rounded-2xl border border-slate-100 mt-8 space-y-4">
<div class="flex items-start gap-3">
<input type="checkbox" id="terms-accept-checkbox" class="w-5 h-5 rounded border-slate-300 text-[#e31e24] focus:ring-[#e31e24] mt-1 cursor-pointer">
<label for="terms-accept-checkbox" class="text-sm text-slate-700 font-semibold cursor-pointer">
{{ __('career.intern_terms_accept_label') }} <span class="text-[#e31e24]">*</span>
</label>
</div>
<button type="button" onclick="nextStep(2)" id="step-1-next-btn" class="w-full py-4 bg-slate-300 text-slate-500 font-bold rounded-xl transition-all flex items-center justify-center gap-2 cursor-not-allowed" disabled>
<span>{{ __('career.accept_intern_terms_btn') }}</span>
<i class="uil uil-arrow-right text-lg"></i>
</button>
</div>
</div>
</form>
</div>
</div>
</div>
</div>
<!-- ================= STEP 2: COMPLETE APPLICATION ================= -->
<div id="step-content-2" class="wizard-step transition-all duration-500 opacity-0 hidden">
<div class="max-w-4xl mx-auto">
<div class="bg-white rounded-[2rem] shadow-2xl overflow-hidden border border-slate-100">
<div class="p-8 md:p-12">
<div class="mb-10 text-center">
<h2 class="text-3xl font-bold text-slate-900 mb-2">{{ __('career.form_title') }}</h2>
<p class="text-slate-500">{{ __('career.form_subtitle') }}</p>
<div class="w-12 h-1 bg-[#e31e24] rounded-full mx-auto mt-4"></div>
</div>
<div class="space-y-6">
<!-- Name -->
<div class="grid grid-cols-1 md:grid-cols-12 gap-6 items-center">
<label for="name" class="md:col-span-3 text-sm font-bold text-slate-700 md:text-right">{{ __('career.name') }} <span class="text-[#e31e24]">*</span></label>
<div class="md:col-span-9">
<input type="text" name="name" id="name" class="w-full px-5 py-3 rounded-xl border border-slate-200 focus:ring-4 focus:ring-red-500/10 focus:border-[#e31e24] outline-none transition-all placeholder-slate-300" placeholder="{{ __('career.name_placeholder') }}" value="{{ old('name') }}" required>
</div>
</div>
<!-- Email -->
<div class="grid grid-cols-1 md:grid-cols-12 gap-6 items-center">
<label for="email" class="md:col-span-3 text-sm font-bold text-slate-700 md:text-right">{{ __('career.email') }} <span class="text-[#e31e24]">*</span></label>
<div class="md:col-span-9">
<input type="email" name="email" id="email" class="w-full px-5 py-3 rounded-xl border border-slate-200 focus:ring-4 focus:ring-red-500/10 focus:border-[#e31e24] outline-none transition-all placeholder-slate-300" placeholder="{{ __('career.email_placeholder') }}" value="{{ old('email') }}" required>
</div>
</div>
<!-- Phone -->
<div class="grid grid-cols-1 md:grid-cols-12 gap-6 items-center">
<label for="phone" class="md:col-span-3 text-sm font-bold text-slate-700 md:text-right">{{ __('career.phone') }}</label>
<div class="md:col-span-9">
<input type="text" name="phone" id="phone" class="w-full px-5 py-3 rounded-xl border border-slate-200 focus:ring-4 focus:ring-red-500/10 focus:border-[#e31e24] outline-none transition-all placeholder-slate-300" placeholder="{{ __('career.phone_placeholder') }}" value="{{ old('phone') }}">
</div>
</div>
<!-- CV Upload -->
<div class="grid grid-cols-1 md:grid-cols-12 gap-6 items-center">
<label for="cv" class="md:col-span-3 text-sm font-bold text-slate-700 md:text-right">{{ __('career.cv') }} <span class="text-[#e31e24]">*</span></label>
<div class="md:col-span-9">
<input type="file" name="cv" id="cv" class="w-full px-5 py-2.5 rounded-xl border border-slate-200 file:mr-4 file:py-2 file:px-4 file:rounded-full file:border-0 file:text-xs file:font-semibold file:bg-red-50 file:text-[#e31e24] hover:file:bg-red-100 transition-all" required>
<p class="mt-2 text-xs text-slate-400">{{ __('career.cv_description') }}</p>
</div>
</div>
<!-- Message / Intent Letter -->
<div class="grid grid-cols-1 md:grid-cols-12 gap-6 items-start">
<label for="message" class="md:col-span-3 text-sm font-bold text-slate-700 md:text-right pt-3">{{ __('career.message') }}</label>
<div class="md:col-span-9">
<textarea name="message" id="message" class="w-full px-5 py-4 rounded-xl border border-slate-200 focus:ring-4 focus:ring-red-500/10 focus:border-[#e31e24] outline-none transition-all placeholder-slate-300 min-h-[150px]" placeholder="Staj beklentileriniz ve çalışma alanlarınız hakkında bilgi verebilirsiniz...">{{ old('message') }}</textarea>
</div>
</div>
<!-- Step 2 Navigation -->
<div class="grid grid-cols-1 md:grid-cols-12 gap-6 pt-6 border-t border-slate-100">
<div class="md:col-start-4 md:col-span-9 flex items-center justify-between gap-4">
<button type="button" onclick="prevStep(1)" class="px-6 py-4 bg-slate-100 hover:bg-slate-200 text-slate-700 font-bold rounded-xl transition-all flex items-center gap-2">
<i class="uil uil-arrow-left text-lg"></i>
<span>{{ __('career.go_back') }}</span>
</button>
<button type="submit" id="submit-btn" class="flex-1 md:flex-none px-10 py-4 bg-[#e31e24] hover:bg-[#c4191f] text-white font-bold rounded-full transition-all shadow-lg shadow-red-500/30 flex items-center justify-center gap-3">
<span class="btn-text">{{ __('career.submit') }}</span>
<span class="spinner-border spinner-border-sm hidden animate-spin w-4 h-4 border-2 border-white border-t-transparent rounded-full" role="status"></span>
<i class="uil uil-arrow-right text-xl btn-icon"></i>
</button>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</form>
</div>
</section>
@@ -200,6 +312,16 @@
outline: none;
}
input[type="checkbox"] {
-webkit-appearance: checkbox !important;
appearance: checkbox !important;
width: 1.25rem !important;
height: 1.25rem !important;
accent-color: var(--citrus-red);
cursor: pointer;
margin-top: 0;
}
.bg-soft-primary {
background: linear-gradient(135deg, #f0f7ff 0%, #e8f1ff 100%) !important;
}
@@ -238,22 +360,210 @@
padding-left: 2rem;
position: relative;
}
/* Mermaid diagram readability and aesthetics */
.mermaid .nodeLabel,
.mermaid .node text,
.mermaid text,
.mermaid .node .label {
text-shadow: 0 1px 2px rgba(0, 0, 0, 0.4), 0 0 1px rgba(0, 0, 0, 0.2) !important;
padding: 2px 8px !important;
}
.mermaid .node.decisionNode .nodeLabel,
.mermaid .node.decisionNode text,
.mermaid .node.decisionNode .label {
text-shadow: none !important;
color: #1e293b !important;
}
.mermaid svg {
filter: drop-shadow(0px 10px 20px rgba(15, 23, 42, 0.05));
}
/* Fullscreen styles for card container */
#mermaid-card:fullscreen,
#mermaid-card:-webkit-full-screen,
#mermaid-card:-ms-fullscreen {
background-color: #ffffff !important;
padding: 3rem 2rem !important;
display: flex !important;
flex-direction: column !important;
align-items: center !important;
justify-content: center !important;
overflow: auto !important;
border-radius: 0px !important;
width: 100% !important;
height: 100% !important;
}
</style>
@endpush
@push('scripts')
<script type="module">
import mermaid from 'https://cdn.jsdelivr.net/npm/mermaid@10/dist/mermaid.esm.min.mjs';
mermaid.initialize({
startOnLoad: true,
theme: 'default',
<script src="https://cdn.jsdelivr.net/npm/mermaid@10.2.4/dist/mermaid.min.js"></script>
<script>
// Initialize Mermaid
mermaid.initialize({
startOnLoad: false,
theme: 'neutral',
securityLevel: 'loose',
flowchart: {
useMaxWidth: true,
htmlLabels: true,
curve: 'basis'
useMaxWidth: true,
htmlLabels: true
}
});
// Run mermaid after all fonts are fully loaded to ensure boxes match the text dimensions perfectly
if (document.fonts) {
document.fonts.ready.then(function() {
mermaid.run({
nodes: document.querySelectorAll('.mermaid')
});
});
} else {
window.addEventListener('load', function() {
mermaid.run({
nodes: document.querySelectorAll('.mermaid')
});
});
}
// Fullscreen toggle logic for Mermaid card
function toggleFullscreen() {
const card = document.getElementById('mermaid-card');
const icon = document.getElementById('fullscreen-icon');
if (!document.fullscreenElement && !document.webkitFullscreenElement && !document.msFullscreenElement) {
if (card.requestFullscreen) {
card.requestFullscreen();
} else if (card.webkitRequestFullscreen) { /* Safari */
card.webkitRequestFullscreen();
} else if (card.msRequestFullscreen) { /* IE11 */
card.msRequestFullscreen();
}
} else {
if (document.exitFullscreen) {
document.exitFullscreen();
} else if (document.webkitExitFullscreen) {
document.webkitExitFullscreen();
} else if (document.msExitFullscreen) {
document.msExitFullscreen();
}
}
}
// Handle icon sync on fullscreen change
function handleFullscreenChange() {
const icon = document.getElementById('fullscreen-icon');
if (document.fullscreenElement || document.webkitFullscreenElement || document.msFullscreenElement) {
icon.className = "uil uil-shrink text-lg";
} else {
icon.className = "uil uil-expand-arrows-alt text-lg";
}
}
document.addEventListener('fullscreenchange', handleFullscreenChange);
document.addEventListener('webkitfullscreenchange', handleFullscreenChange);
document.addEventListener('msfullscreenchange', handleFullscreenChange);
// Step variables
let currentStep = 1;
// Track Terms checkbox to enable Step 1 Next button
document.getElementById('terms-accept-checkbox').addEventListener('change', function(e) {
const nextBtn = document.getElementById('step-1-next-btn');
if (e.target.checked) {
nextBtn.disabled = false;
nextBtn.classList.remove('bg-slate-300', 'text-slate-500', 'cursor-not-allowed');
nextBtn.classList.add('bg-[#e31e24]', 'text-white', 'hover:bg-[#c4191f]', 'shadow-lg', 'shadow-red-500/20');
} else {
nextBtn.disabled = true;
nextBtn.classList.add('bg-slate-300', 'text-slate-500', 'cursor-not-allowed');
nextBtn.classList.remove('bg-[#e31e24]', 'text-white', 'hover:bg-[#c4191f]', 'shadow-lg', 'shadow-red-500/20');
}
});
function updateProgressBar() {
const progressPercent = ((currentStep - 1) / 1) * 100;
document.getElementById('wizard-progress-bar').style.width = `${progressPercent}%`;
// Reset indicator classes
for (let i = 1; i <= 2; i++) {
const dot = document.getElementById(`step-dot-${i}`);
const label = document.getElementById(`step-label-${i}`);
if (i < currentStep) {
// Completed Step
dot.className = "w-12 h-12 rounded-full bg-emerald-500 text-white flex items-center justify-center font-extrabold shadow-lg shadow-emerald-500/20 ring-4 ring-emerald-100 transition-all duration-500";
dot.innerHTML = `<i class="uil uil-check text-xl"></i>`;
label.className = "text-xs md:text-sm font-bold text-slate-800 mt-3";
} else if (i === currentStep) {
// Active Step
dot.className = "w-12 h-12 rounded-full bg-[#e31e24] text-white flex items-center justify-center font-extrabold shadow-lg shadow-red-500/20 ring-4 ring-red-100 transition-all duration-500";
if (i === 1) dot.innerHTML = `<i class="uil uil-info-circle text-xl"></i>`;
if (i === 2) dot.innerHTML = `<i class="uil uil-check-circle text-xl"></i>`;
label.className = "text-xs md:text-sm font-bold text-slate-800 mt-3";
} else {
// Pending Step
dot.className = "w-12 h-12 rounded-full bg-slate-100 text-slate-400 flex items-center justify-center font-extrabold ring-4 ring-transparent transition-all duration-500";
if (i === 2) dot.innerHTML = `<i class="uil uil-check-circle text-xl"></i>`;
label.className = "text-xs md:text-sm font-medium text-slate-400 mt-3";
}
}
}
function nextStep(step) {
if (step === 2 && !document.getElementById('terms-accept-checkbox').checked) {
return;
}
// Hide current step content with nice fade animation
const currentStepEl = document.getElementById(`step-content-${currentStep}`);
currentStepEl.classList.remove('opacity-100');
currentStepEl.classList.add('opacity-0');
setTimeout(() => {
currentStepEl.classList.add('hidden');
// Show next step content
const nextStepEl = document.getElementById(`step-content-${step}`);
nextStepEl.classList.remove('hidden');
// Force repaint to trigger animation
nextStepEl.offsetHeight;
nextStepEl.classList.remove('opacity-0');
nextStepEl.classList.add('opacity-100');
currentStep = step;
updateProgressBar();
window.scrollTo({ top: document.querySelector('.wrapper').offsetTop - 50, behavior: 'smooth' });
}, 200);
}
function prevStep(step) {
const currentStepEl = document.getElementById(`step-content-${currentStep}`);
currentStepEl.classList.remove('opacity-100');
currentStepEl.classList.add('opacity-0');
setTimeout(() => {
currentStepEl.classList.add('hidden');
const prevStepEl = document.getElementById(`step-content-${step}`);
prevStepEl.classList.remove('hidden');
prevStepEl.offsetHeight;
prevStepEl.classList.remove('opacity-0');
prevStepEl.classList.add('opacity-100');
currentStep = step;
updateProgressBar();
window.scrollTo({ top: document.querySelector('.wrapper').offsetTop - 50, behavior: 'smooth' });
}, 200);
}
</script>
<script src="https://cdn.jsdelivr.net/npm/sweetalert2@11"></script>
<script>
document.addEventListener('DOMContentLoaded', function() {
@@ -306,6 +616,10 @@ document.addEventListener('DOMContentLoaded', function() {
confirmButtonText: '{{ __("career.ok") ?? "Tamam" }}'
}).then(() => {
form.reset();
// Go back to step 1
document.getElementById('terms-accept-checkbox').checked = false;
document.getElementById('terms-accept-checkbox').dispatchEvent(new Event('change'));
prevStep(1);
});
} else if (result.type === 'validation') {
Object.keys(result.errors).forEach(key => {
@@ -313,9 +627,14 @@ document.addEventListener('DOMContentLoaded', function() {
if (input) {
input.classList.add('is-invalid');
const errorDiv = document.createElement('div');
errorDiv.className = 'invalid-feedback text-start d-block';
errorDiv.className = 'invalid-feedback text-start text-xs text-red-500 mt-1 block';
errorDiv.textContent = result.errors[key][0];
input.closest('.md\\:col-span-9')?.appendChild(errorDiv) || input.closest('.col-md-9')?.appendChild(errorDiv);
if (input.type === 'checkbox') {
input.closest('.flex').parentNode.appendChild(errorDiv);
} else {
input.parentNode.appendChild(errorDiv);
}
}
});