Deploy Laravel rebuild via Coolify

Point Docker and Coolify compose to the Laravel rebuild app so mahasiswa, dosen, and admin flows are served from the new Laravel public entrypoint.
This commit is contained in:
Power BI Dev
2026-05-03 18:50:29 +07:00
parent 89ce9d30a7
commit dab8ea396b
107 changed files with 17544 additions and 20 deletions

View File

@@ -0,0 +1,91 @@
@import 'tailwindcss';
@source '../../vendor/laravel/framework/src/Illuminate/Pagination/resources/views/*.blade.php';
@source '../../storage/framework/views/*.php';
@source '../**/*.blade.php';
@source '../**/*.js';
@theme {
--font-sans: 'Inter', ui-sans-serif, system-ui, sans-serif, 'Apple Color Emoji', 'Segoe UI Emoji',
'Segoe UI Symbol', 'Noto Color Emoji';
}
@layer base {
html {
scroll-behavior: smooth;
}
body {
font-feature-settings: 'cv02', 'cv03', 'cv04', 'cv11';
}
::selection {
background: rgba(15, 23, 42, 0.12);
}
}
@layer components {
.section-card {
@apply rounded-xl bg-white shadow-[0_8px_12px_rgba(13,10,44,0.04)];
}
.muted-label {
@apply text-sm font-semibold text-[#2D68F8];
}
.metric-card {
@apply rounded-[20px] border border-slate-200 bg-slate-50 p-5;
}
.template-input {
@apply w-full rounded-md border border-[#D1D5DB] bg-white px-6 py-3.5 text-[#15171A] outline-hidden duration-200 placeholder:text-[#979797] focus:border-transparent focus:ring-2 focus:ring-[#5C6A78]/20;
}
.template-button-dark {
@apply inline-flex items-center justify-center rounded-md bg-[#15171A] px-5 py-3.5 font-medium text-white transition duration-200 hover:opacity-90;
}
.dashboard-shell {
@apply mx-auto flex max-w-[1400px] gap-6 px-4 pb-10 pt-24 sm:px-6 xl:px-8;
}
.dashboard-sidebar {
@apply hidden w-full max-w-[290px] shrink-0 lg:block;
}
.dashboard-sidebar-card {
@apply sticky top-24 rounded-xl border border-[#E5E7EB] bg-white p-5 shadow-[0_8px_12px_rgba(13,10,44,0.04)];
}
.dashboard-sidebar-link {
@apply flex items-center gap-3 rounded-lg px-3 py-2.5 text-sm text-[#374151] transition hover:bg-[#F9FAFB] hover:text-[#15171A];
}
.dashboard-sidebar-link-active {
@apply bg-[#15171A] text-white hover:bg-[#15171A] hover:text-white;
}
.dashboard-sidebar-group {
@apply mt-5;
}
.dashboard-sidebar-group-label {
@apply flex items-center gap-3 rounded-lg px-3 py-2.5 text-sm font-semibold text-[#15171A];
}
.dashboard-sidebar-submenu {
@apply ml-4 mt-1 space-y-1 border-l border-[#E5E7EB] pl-3.5;
}
.dashboard-sidebar-icon {
@apply inline-flex h-4.5 w-4.5 shrink-0 items-center justify-center text-[#7A8594];
}
.dashboard-sidebar-link-active .dashboard-sidebar-icon {
@apply text-white;
}
.dashboard-content {
@apply min-w-0 flex-1;
}
}

View File

@@ -0,0 +1 @@
//

View File

@@ -0,0 +1,94 @@
<x-admin.partials.page-shell :title="$title" :sidebar="$sidebar">
<section class="rounded-xl bg-white p-4 shadow-[0_8px_12px_rgba(13,10,44,0.04)] lg:p-6">
<div class="flex flex-col gap-4 lg:flex-row lg:items-start lg:justify-between">
<div>
<ol class="flex flex-wrap items-center gap-2 text-sm text-[#6B7280]">
<li class="inline-flex items-center gap-2">
<span class="text-[#625DF5]">@include('dashboard.partials.icon', ['icon' => 'home'])</span>
<span>Home</span>
</li>
<li>/</li>
<li class="font-medium text-[#15171A]">{{ $pageTitle }}</li>
</ol>
<h1 class="mt-4 text-[26px] font-bold leading-[34px] text-[#15171A]">{{ $pageTitle }}</h1>
<p class="mt-2 max-w-[880px] text-sm leading-7 text-[#4B5563]">{{ $pageDescription }}</p>
</div>
<div class="flex flex-wrap items-center gap-3">
<div class="rounded-md border border-[#E5E7EB] bg-[#F9FAFB] px-4 py-3 text-sm text-[#15171A]">{{ $pageDate }}</div>
<div class="rounded-md border border-[#E5E7EB] bg-[#F9FAFB] px-4 py-3 text-sm text-[#15171A]">{{ $user['username'] }} · {{ $user['nmprodi'] }}</div>
</div>
</div>
</section>
@if (session('error'))
<div class="rounded-xl border border-rose-200 bg-rose-50 px-4 py-3 text-sm text-rose-800">{{ session('error') }}</div>
@endif
@if ($errors->any())
<div class="rounded-xl border border-rose-200 bg-rose-50 px-4 py-3 text-sm text-rose-800">
<p class="font-semibold">Import belum bisa diproses.</p>
<ul class="mt-2 list-disc space-y-1 pl-5">
@foreach ($errors->all() as $error)
<li>{{ $error }}</li>
@endforeach
</ul>
</div>
@endif
<div class="grid gap-5 lg:grid-cols-[minmax(0,1fr)_420px]">
<form method="POST" action="{{ route('admin.data.mahasiswa.import.store') }}" enctype="multipart/form-data" class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
@csrf
<div class="grid gap-5">
<div>
<label class="text-sm font-semibold text-[#15171A]">File CSV</label>
<input type="file" name="csv" accept=".csv,text/csv,text/plain" class="mt-2 w-full rounded-md border border-[#D1D5DB] px-4 py-3 text-sm" required>
<p class="mt-2 text-xs leading-5 text-[#6B7280]">Maksimal 5 MB. Baris pertama harus berisi header.</p>
</div>
<div>
<label class="text-sm font-semibold text-[#15171A]">Mode Import</label>
<select name="mode" class="mt-2 w-full rounded-md border border-[#D1D5DB] px-4 py-3 text-sm">
<option value="insert_only">Tambah data baru saja</option>
<option value="upsert">Tambah dan update jika NIM sudah ada</option>
</select>
</div>
<div>
<label class="text-sm font-semibold text-[#15171A]">Password Default</label>
<input type="text" name="default_password" value="123456" class="mt-2 w-full rounded-md border border-[#D1D5DB] px-4 py-3 text-sm">
<p class="mt-2 text-xs leading-5 text-[#6B7280]">Dipakai jika kolom `password` kosong atau tidak ada pada baris mahasiswa baru.</p>
</div>
<div class="flex flex-wrap gap-3 border-t border-[#E5E7EB] pt-5">
<button class="rounded-md bg-[#15171A] px-5 py-2.5 text-sm font-medium text-white hover:opacity-90">Import CSV</button>
<a href="{{ route('admin.data.mahasiswa', [], false) }}" class="rounded-md border border-[#D1D5DB] bg-white px-5 py-2.5 text-sm font-medium text-[#15171A] hover:bg-[#F9FAFB]">Batal</a>
</div>
</div>
</form>
<aside class="space-y-5">
<section class="rounded-xl border border-[#E5E7EB] bg-white p-5 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<h2 class="text-lg font-semibold text-[#15171A]">Format Header</h2>
<p class="mt-3 text-sm leading-7 text-[#6B7280]">Header wajib:</p>
<div class="mt-3 flex flex-wrap gap-2">
@foreach ($requiredHeaders as $header)
<span class="rounded-full bg-[#625DF5]/10 px-3 py-1 text-xs font-semibold text-[#625DF5]">{{ $header }}</span>
@endforeach
</div>
<p class="mt-5 text-sm leading-7 text-[#6B7280]">Header opsional:</p>
<div class="mt-3 flex flex-wrap gap-2">
@foreach ($optionalHeaders as $header)
<span class="rounded-full bg-[#F9FAFB] px-3 py-1 text-xs font-semibold text-[#4B5563]">{{ $header }}</span>
@endforeach
</div>
</section>
<section class="rounded-xl border border-[#E5E7EB] bg-white p-5 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<h2 class="text-lg font-semibold text-[#15171A]">Contoh CSV</h2>
<pre class="mt-4 overflow-x-auto rounded-lg bg-[#15171A] p-4 text-xs leading-6 text-white"><code>nim,nama,email,thnmasuk,password,status,noHP,noHPOrtu,bolehUploadDraft
D1041231001,Budi Saputra,budi@example.com,2023,123456,A,08123456789,08129876543,1
D1041231002,Siti Aminah,siti@example.com,2023,,A,,,1</code></pre>
</section>
</aside>
</div>
</x-admin.partials.page-shell>

View File

@@ -0,0 +1,68 @@
<x-admin.partials.page-shell :title="$title" :sidebar="$sidebar">
<section class="rounded-xl bg-white p-4 shadow-[0_8px_12px_rgba(13,10,44,0.04)] lg:p-6">
<div class="flex flex-col gap-4 lg:flex-row lg:items-start lg:justify-between">
<div>
<ol class="flex flex-wrap items-center gap-2 text-sm text-[#6B7280]">
<li class="inline-flex items-center gap-2">
<span class="text-[#625DF5]">@include('dashboard.partials.icon', ['icon' => 'home'])</span>
<span>Home</span>
</li>
<li>/</li>
<li class="font-medium text-[#15171A]">{{ $pageTitle }}</li>
</ol>
<h1 class="mt-4 text-[26px] font-bold leading-[34px] text-[#15171A]">{{ $pageTitle }}</h1>
<p class="mt-2 max-w-[880px] text-sm leading-7 text-[#4B5563]">{{ $pageDescription }}</p>
</div>
<div class="flex flex-wrap items-center gap-3">
<div class="rounded-md border border-[#E5E7EB] bg-[#F9FAFB] px-4 py-3 text-sm text-[#15171A]">{{ $pageDate }}</div>
<div class="rounded-md border border-[#E5E7EB] bg-[#F9FAFB] px-4 py-3 text-sm text-[#15171A]">{{ $user['username'] }} · {{ $user['nmprodi'] }}</div>
</div>
</div>
</section>
@if ($errors->any())
<div class="rounded-xl border border-rose-200 bg-rose-50 px-4 py-3 text-sm text-rose-800">
<p class="font-semibold">Form belum bisa disimpan.</p>
<ul class="mt-2 list-disc space-y-1 pl-5">
@foreach ($errors->all() as $error)
<li>{{ $error }}</li>
@endforeach
</ul>
</div>
@endif
<form method="POST" action="{{ route('admin.pengumuman.store') }}" class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
@csrf
<div class="grid gap-5">
<div>
<label class="text-sm font-semibold text-[#15171A]">Judul</label>
<input name="judul" value="{{ old('judul') }}" class="mt-2 w-full rounded-md border border-[#D1D5DB] px-4 py-3 text-sm focus:border-[#625DF5] focus:outline-none" required>
</div>
<div>
<label class="text-sm font-semibold text-[#15171A]">Isi Pengumuman</label>
<textarea name="isi" rows="8" class="mt-2 w-full rounded-md border border-[#D1D5DB] px-4 py-3 text-sm focus:border-[#625DF5] focus:outline-none" required>{{ old('isi') }}</textarea>
</div>
<div class="grid gap-5 lg:grid-cols-2">
<div>
<label class="text-sm font-semibold text-[#15171A]">Tujuan</label>
<select name="tujuan" class="mt-2 w-full rounded-md border border-[#D1D5DB] px-4 py-3 text-sm">
<option value="A" @selected(old('tujuan', 'A') === 'A')>Semua</option>
<option value="M" @selected(old('tujuan') === 'M')>Mahasiswa</option>
<option value="D" @selected(old('tujuan') === 'D')>Dosen</option>
</select>
</div>
<div>
<label class="text-sm font-semibold text-[#15171A]">Publish</label>
<select name="publish" class="mt-2 w-full rounded-md border border-[#D1D5DB] px-4 py-3 text-sm">
<option value="Y" @selected(old('publish', 'Y') === 'Y')>Ya</option>
<option value="N" @selected(old('publish') === 'N')>Tidak</option>
</select>
</div>
</div>
<div class="flex flex-wrap gap-3 border-t border-[#E5E7EB] pt-5">
<button class="rounded-md bg-[#15171A] px-5 py-2.5 text-sm font-medium text-white hover:opacity-90">Simpan Pengumuman</button>
<a href="{{ route('admin.pengumuman.index', [], false) }}" class="rounded-md border border-[#D1D5DB] bg-white px-5 py-2.5 text-sm font-medium text-[#15171A] hover:bg-[#F9FAFB]">Batal</a>
</div>
</div>
</form>
</x-admin.partials.page-shell>

View File

@@ -0,0 +1,59 @@
<x-admin.partials.page-shell :title="$title" :sidebar="$sidebar">
<section class="rounded-xl bg-white p-4 shadow-[0_8px_12px_rgba(13,10,44,0.04)] lg:p-6">
<div class="flex flex-col gap-4 lg:flex-row lg:items-start lg:justify-between">
<div>
<ol class="flex flex-wrap items-center gap-2 text-sm text-[#6B7280]">
<li class="inline-flex items-center gap-2"><span class="text-[#625DF5]">@include('dashboard.partials.icon', ['icon' => 'home'])</span><span>Home</span></li>
<li>/</li>
<li class="font-medium text-[#15171A]">{{ $pageTitle }}</li>
</ol>
<h1 class="mt-4 text-[26px] font-bold leading-[34px] text-[#15171A]">{{ $pageTitle }}</h1>
<p class="mt-2 max-w-[880px] text-sm leading-7 text-[#4B5563]">{{ $pageDescription }}</p>
</div>
<div class="rounded-md border border-[#E5E7EB] bg-[#F9FAFB] px-4 py-3 text-sm text-[#15171A]">{{ $user['username'] }} · {{ $user['nmprodi'] }}</div>
</div>
</section>
@if ($errors->any())
<div class="rounded-xl border border-rose-200 bg-rose-50 px-4 py-3 text-sm text-rose-800">
<p class="font-semibold">Form belum bisa disimpan.</p>
<ul class="mt-2 list-disc space-y-1 pl-5">
@foreach ($errors->all() as $error)
<li>{{ $error }}</li>
@endforeach
</ul>
</div>
@endif
<form method="POST" action="{{ $action }}" class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
@csrf
@if (($method ?? 'POST') !== 'POST')
@method($method)
@endif
<div class="grid gap-5 lg:grid-cols-2">
@foreach ($fields as $field)
<div class="{{ ($field['type'] ?? 'text') === 'textarea' ? 'lg:col-span-2' : '' }}">
<label class="text-sm font-semibold text-[#15171A]">{{ $field['label'] }}</label>
@if (($field['type'] ?? 'text') === 'select')
<select name="{{ $field['name'] }}" class="mt-2 w-full rounded-md border border-[#D1D5DB] px-4 py-3 text-sm">
@foreach ($field['options'] as $value => $label)
<option value="{{ $value }}" @selected((string) old($field['name'], $field['value'] ?? '') === (string) $value)>{{ $label }}</option>
@endforeach
</select>
@elseif (($field['type'] ?? 'text') === 'textarea')
<textarea name="{{ $field['name'] }}" rows="7" class="mt-2 w-full rounded-md border border-[#D1D5DB] px-4 py-3 text-sm focus:border-[#625DF5] focus:outline-none">{{ old($field['name'], $field['value'] ?? '') }}</textarea>
@else
<input type="{{ $field['type'] ?? 'text' }}" name="{{ $field['name'] }}" value="{{ old($field['name'], $field['value'] ?? '') }}" class="mt-2 w-full rounded-md border border-[#D1D5DB] px-4 py-3 text-sm focus:border-[#625DF5] focus:outline-none" @if(!empty($field['required'])) required @endif>
@endif
@if (!empty($field['help']))
<p class="mt-2 text-xs leading-5 text-[#6B7280]">{{ $field['help'] }}</p>
@endif
</div>
@endforeach
</div>
<div class="mt-6 flex flex-wrap gap-3 border-t border-[#E5E7EB] pt-5">
<button class="rounded-md bg-[#15171A] px-5 py-2.5 text-sm font-medium text-white hover:opacity-90">Simpan</button>
<a href="{{ $cancel }}" class="rounded-md border border-[#D1D5DB] bg-white px-5 py-2.5 text-sm font-medium text-[#15171A] hover:bg-[#F9FAFB]">Batal</a>
</div>
</form>
</x-admin.partials.page-shell>

View File

@@ -0,0 +1,101 @@
<x-admin.partials.page-shell :title="$title" :sidebar="$sidebar">
<section class="rounded-xl bg-white p-4 shadow-[0_8px_12px_rgba(13,10,44,0.04)] lg:p-6">
<div class="flex flex-col gap-4 lg:flex-row lg:items-start lg:justify-between">
<div>
<ol class="flex flex-wrap items-center gap-2 text-sm text-[#6B7280]">
<li class="inline-flex items-center gap-2">
<span class="text-[#625DF5]">@include('dashboard.partials.icon', ['icon' => 'home'])</span>
<span>Home</span>
</li>
<li>/</li>
<li class="font-medium text-[#15171A]">{{ $pageTitle }}</li>
</ol>
<h1 class="mt-4 text-[26px] font-bold leading-[34px] text-[#15171A]">{{ $pageTitle }}</h1>
<p class="mt-2 max-w-[880px] text-sm leading-7 text-[#4B5563]">{{ $pageDescription }}</p>
</div>
<div class="flex flex-wrap items-center gap-3">
<div class="rounded-md border border-[#E5E7EB] bg-[#F9FAFB] px-4 py-3 text-sm text-[#15171A]">{{ $pageDate }}</div>
<div class="rounded-md border border-[#E5E7EB] bg-[#F9FAFB] px-4 py-3 text-sm text-[#15171A]">{{ $user['username'] }} · {{ $user['nmprodi'] }}</div>
<form method="POST" action="{{ route('legacy.logout') }}">
@csrf
<button type="submit" class="rounded-md bg-[#15171A] px-5.5 py-2.5 text-sm font-medium text-white hover:opacity-90">Logout</button>
</form>
</div>
</div>
@if (!empty($actions ?? []))
<div class="mt-5 flex flex-wrap gap-3 border-t border-[#E5E7EB] pt-5">
@foreach ($actions as $action)
<a href="{{ $action['href'] }}" class="{{ ($action['variant'] ?? 'light') === 'dark' ? 'rounded-md bg-[#15171A] px-4 py-2.5 text-sm font-medium text-white hover:opacity-90' : 'rounded-md border border-[#D1D5DB] bg-white px-4 py-2.5 text-sm font-medium text-[#15171A] hover:bg-[#F9FAFB]' }}">{{ $action['label'] }}</a>
@endforeach
</div>
@endif
</section>
@if (session('success'))
<div class="rounded-xl border border-emerald-200 bg-emerald-50 px-4 py-3 text-sm text-emerald-800">{{ session('success') }}</div>
@endif
@if (!empty($search ?? false))
<form method="GET" class="rounded-xl border border-[#E5E7EB] bg-white p-5 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<div class="grid gap-3 lg:grid-cols-[minmax(0,1fr)_auto]">
<input name="q" value="{{ $keyword ?? '' }}" placeholder="Cari judul, nama mahasiswa, atau NIM" class="rounded-md border border-[#D1D5DB] px-4 py-3 text-sm focus:border-[#625DF5] focus:outline-none">
<button type="submit" class="rounded-md bg-[#15171A] px-5 py-3 text-sm font-medium text-white hover:opacity-90">Cari</button>
</div>
</form>
@endif
<section class="overflow-hidden rounded-xl border border-[#E5E7EB] bg-white shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<div class="overflow-x-auto">
<table class="min-w-[900px] w-full text-left text-sm">
<thead class="bg-[#F9FAFB] text-xs uppercase tracking-[0.12em] text-[#6B7280]">
<tr>
<th class="px-4 py-3">No.</th>
@foreach ($columns as $column)
<th class="px-4 py-3">{{ $column }}</th>
@endforeach
@if (!empty($rowActions ?? null))
<th class="px-4 py-3 text-right">Aksi</th>
@endif
</tr>
</thead>
<tbody class="divide-y divide-[#E5E7EB]">
@forelse ($rows as $row)
<tr>
<td class="px-4 py-4 text-[#6B7280]">{{ method_exists($rows, 'currentPage') ? $loop->iteration + ($rows->currentPage() - 1) * $rows->perPage() : $loop->iteration }}</td>
@foreach ($map($row) as $value)
<td class="px-4 py-4 text-[#374151]">{!! is_string($value) ? e($value) : $value !!}</td>
@endforeach
@if (!empty($rowActions ?? null))
<td class="px-4 py-4">
<div class="flex justify-end gap-2 whitespace-nowrap">
@foreach ($rowActions($row) as $action)
@if (($action['method'] ?? 'GET') === 'GET')
<a href="{{ $action['href'] }}" class="rounded-md border border-[#D1D5DB] px-3 py-2 text-xs font-medium text-[#15171A] hover:bg-[#F9FAFB]">{{ $action['label'] }}</a>
@else
<form method="POST" action="{{ $action['href'] }}" onsubmit="return confirm('{{ $action['confirm'] ?? 'Lanjutkan aksi ini?' }}')">
@csrf
@method($action['method'])
<button class="rounded-md bg-rose-600 px-3 py-2 text-xs font-medium text-white hover:opacity-90">{{ $action['label'] }}</button>
</form>
@endif
@endforeach
</div>
</td>
@endif
</tr>
@empty
<tr>
<td colspan="{{ count($columns) + 1 + (!empty($rowActions ?? null) ? 1 : 0) }}" class="px-4 py-8 text-center text-[#6B7280]">Belum ada data.</td>
</tr>
@endforelse
</tbody>
</table>
</div>
@if (method_exists($rows, 'links'))
<div class="border-t border-[#E5E7EB] px-4 py-3">
{{ $rows->links() }}
</div>
@endif
</section>
</x-admin.partials.page-shell>

View File

@@ -0,0 +1,74 @@
<x-layouts.app :title="$meta['title']">
<section class="bg-[#F9FAFB] pb-15 pt-34 lg:pb-20 lg:pt-39">
<div class="mx-auto max-w-[1170px] px-4 sm:px-8 xl:px-0">
<div class="grid gap-6 lg:grid-cols-[minmax(0,1.05fr)_minmax(360px,440px)] lg:items-start">
<article class="rounded-xl bg-white p-7 shadow-[0_8px_12px_rgba(13,10,44,0.04)] sm:p-9">
<span class="inline-flex rounded-full bg-[#625DF5]/[0.08] px-3 py-1 text-sm font-medium text-[#625DF5]">{{ $meta['eyebrow'] }}</span>
<h1 class="mt-5 max-w-[760px] text-[28px] font-bold leading-[38px] text-[#15171A] sm:text-[38px] sm:leading-[48px]">{{ $meta['heading'] }}</h1>
<p class="mt-5 max-w-[760px] text-sm leading-8 text-[#4B5563] sm:text-base">{{ $meta['description'] }}</p>
<div class="mt-8 rounded-xl border border-[#E5E7EB] bg-[#F9FAFB] p-5">
<p class="text-sm font-semibold uppercase tracking-[0.16em] text-[#979797]">{{ $meta['summary_title'] }}</p>
<div class="mt-4 space-y-3 text-sm leading-7 text-[#374151]">
@foreach ($meta['summary_points'] as $point)
<div class="rounded-lg bg-white px-4 py-3">{{ $point }}</div>
@endforeach
</div>
</div>
<div class="mt-6 rounded-xl border border-[#E5E7EB] bg-white p-5 text-sm leading-7 text-[#4B5563]">
<p class="font-semibold text-[#15171A]">Informasi Login</p>
<p class="mt-2">{{ $meta['status_note'] }}</p>
<p class="mt-2">{{ $meta['help_note'] }}</p>
</div>
</article>
<div class="rounded-xl bg-white p-5 shadow-[0_8px_12px_rgba(13,10,44,0.04)] sm:p-7.5 xl:p-9">
<div class="mb-6 grid grid-cols-2 rounded-[14px] bg-[#F9FAFB] p-1.5 text-sm font-medium text-[#15171A]">
<a href="{{ route('legacy.login', 'mahasiswa') }}" class="rounded-[10px] px-4 py-3 text-center {{ $role === 'mahasiswa' ? 'bg-white shadow-[0_4px_10px_rgba(13,10,44,0.05)]' : 'text-[#5C6A78]' }}">Mahasiswa</a>
<a href="{{ route('legacy.login', 'dosen') }}" class="rounded-[10px] px-4 py-3 text-center {{ $role === 'dosen' ? 'bg-white shadow-[0_4px_10px_rgba(13,10,44,0.05)]' : 'text-[#5C6A78]' }}">Dosen</a>
</div>
<div class="mb-6 inline-flex rounded-full border border-[#E5E7EB] bg-[#F9FAFB] px-3 py-1.5 text-sm font-medium text-[#15171A]">
{{ $meta['status'] }}
</div>
@if ($errors->any())
<div class="mb-6 rounded-md border border-rose-200 bg-rose-50 px-4 py-3 text-sm text-rose-700">
<ul class="space-y-1">
@foreach ($errors->all() as $error)
<li>{{ $error }}</li>
@endforeach
</ul>
</div>
@endif
<form method="POST" action="{{ route('legacy.authenticate', $role) }}">
@csrf
<div class="mb-4">
<label for="identifier" class="mb-3 block text-[14px] font-medium leading-[22px] text-[#15171A]">{{ $meta['input'] }}</label>
<input id="identifier" name="identifier" type="text" value="{{ old('identifier') }}" placeholder="{{ $meta['placeholder'] }}" class="template-input">
</div>
@if ($role === 'dosen')
<div class="mb-4">
<label for="prodi" class="mb-3 block text-[14px] font-medium leading-[22px] text-[#15171A]">Program Studi</label>
<input id="prodi" type="text" value="Informatika" disabled class="template-input bg-[#F9FAFB] text-[#5C6A78]">
</div>
@endif
<div class="mb-5">
<label for="password" class="mb-3 block text-[14px] font-medium leading-[22px] text-[#15171A]">Password</label>
<input id="password" name="password" type="password" placeholder="Masukkan password" class="template-input">
</div>
<div class="mb-7 flex items-center justify-between text-sm text-[#374151]">
<span>{{ $role === 'mahasiswa' ? 'Gunakan akun mahasiswa aktif' : ($role === 'dosen' ? 'Gunakan akun dosen aktif' : 'Akses admin belum tersedia') }}</span>
<a href="{{ route('role-login') }}" class="text-[#15171A]">Kembali</a>
</div>
<button type="submit" class="flex w-full justify-center rounded-md bg-[#15171A] px-5 py-3.5 font-medium text-white hover:opacity-90 {{ $role === 'admin' ? 'opacity-75' : '' }}">{{ $role === 'mahasiswa' ? 'Masuk ke Portal Mahasiswa' : ($role === 'dosen' ? 'Masuk ke Dashboard Dosen' : 'Coba Masuk') }}</button>
</form>
<p class="mt-5 text-sm leading-7 text-[#5C6A78]">{{ $role === 'mahasiswa' ? 'Login mahasiswa tetap memakai data autentikasi SPOTA yang aktif saat ini.' : ($role === 'dosen' ? 'Login dosen membaca akun legacy aktif dengan struktur session yang mengikuti sistem lama.' : 'Halaman admin akan dibuka setelah modul utama selesai dipindahkan.') }}</p>
</div>
</div>
</div>
</section>
</x-layouts.app>

View File

@@ -0,0 +1,43 @@
<x-layouts.app :title="$title">
<main>
<section class="relative z-10 overflow-hidden rounded-b-[50px] pb-15 pt-34">
<div class="absolute bottom-0 left-0 h-full w-full rounded-b-[50px] bg-[#F9FAFB]"></div>
<div class="mx-auto relative z-10 max-w-[1170px] px-4 sm:px-8 xl:px-0">
<div class="grid gap-6 lg:grid-cols-[minmax(0,1.3fr)_minmax(320px,0.7fr)] lg:items-start">
<article class="rounded-xl bg-white p-7 shadow-[0_8px_12px_rgba(13,10,44,0.04)] sm:p-9">
<span class="inline-flex rounded-full bg-[#625DF5]/[0.08] px-3 py-1 text-sm font-medium text-[#625DF5]">{{ $intro['eyebrow'] }}</span>
<h1 class="mt-5 max-w-[820px] text-[28px] font-bold leading-[38px] text-[#15171A] sm:text-[38px] sm:leading-[48px]">{{ $intro['heading'] }}</h1>
<p class="mt-5 max-w-[820px] text-sm leading-8 text-[#4B5563] sm:text-base">{{ $intro['description'] }}</p>
<div class="mt-8 grid gap-4">
@foreach ($intro['details'] as $detail)
<div class="rounded-xl border border-[#E5E7EB] bg-[#F9FAFB] px-5 py-4 text-sm leading-7 text-[#374151]">
{{ $detail }}
</div>
@endforeach
</div>
</article>
<aside class="rounded-xl bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)] sm:p-7">
<p class="text-xs font-semibold uppercase tracking-[0.18em] text-[#979797]">Akses Akun</p>
<h2 class="mt-3 text-[24px] font-semibold leading-[32px] text-[#15171A]">Pilih peran pengguna</h2>
<p class="mt-3 text-sm leading-7 text-[#5C6A78]">Gunakan akun yang sudah aktif pada SPOTA. Saat ini rebuild berfokus pada alur mahasiswa dan dosen.</p>
<div class="mt-6 space-y-4">
@foreach ($roles as $role)
<a href="{{ route('legacy.login', $role['slug']) }}" class="block rounded-xl border border-[#E5E7EB] bg-[#F9FAFB] px-5 py-4 transition hover:border-[#15171A] hover:bg-white">
<p class="text-base font-semibold text-[#15171A]">{{ $role['name'] }}</p>
<p class="mt-2 text-sm leading-7 text-[#5C6A78]">{{ $role['summary'] }}</p>
</a>
@endforeach
</div>
<div class="mt-6 rounded-xl border border-[#E5E7EB] bg-white px-5 py-4 text-sm leading-7 text-[#4B5563]">
Jika belum yakin masuk sebagai siapa, mulai dari peran yang memang digunakan sehari-hari pada proses tugas akhir di SPOTA.
</div>
</aside>
</div>
</div>
</section>
</main>
</x-layouts.app>

View File

@@ -0,0 +1,41 @@
<x-layouts.app :title="$title" :dashboard-layout="true">
<main class="min-h-screen bg-[#F9FAFB]">
<div class="dashboard-shell">
<aside class="dashboard-sidebar">
<div class="dashboard-sidebar-card">
<p class="text-xs font-semibold uppercase tracking-[0.18em] text-[#979797]">Menu Admin</p>
<div class="mt-4 space-y-1">
@foreach ($sidebar['main'] as $menu)
<a href="{{ $menu['href'] }}" class="dashboard-sidebar-link {{ !empty($menu['active']) ? 'dashboard-sidebar-link-active' : '' }}">
<span class="dashboard-sidebar-icon">@include('dashboard.partials.icon', ['icon' => $menu['icon']])</span>
<span>{{ $menu['title'] }}</span>
</a>
@endforeach
</div>
<div class="mt-6 space-y-5 border-t border-[#E5E7EB] pt-6">
@foreach ($sidebar['sections'] as $group)
<section class="dashboard-sidebar-group">
<div class="dashboard-sidebar-group-label">
<span class="dashboard-sidebar-icon">@include('dashboard.partials.icon', ['icon' => $group['icon']])</span>
<span>{{ $group['title'] }}</span>
</div>
<div class="dashboard-sidebar-submenu">
@foreach ($group['items'] as $item)
<a href="{{ $item['href'] }}" @if(!empty($item['external'])) target="_blank" rel="noreferrer" @endif class="dashboard-sidebar-link">
<span class="dashboard-sidebar-icon">@include('dashboard.partials.icon', ['icon' => $item['icon']])</span>
<span>{{ $item['title'] }}</span>
</a>
@endforeach
</div>
</section>
@endforeach
</div>
</div>
</aside>
<div class="dashboard-content space-y-5">
{{ $slot }}
</div>
</div>
</main>
</x-layouts.app>

View File

@@ -0,0 +1,86 @@
<x-layouts.app :title="$title" :dashboard-layout="true">
<main class="min-h-screen bg-[#F9FAFB]">
<div class="dashboard-shell">
<aside class="dashboard-sidebar">
<div class="dashboard-sidebar-card">
<p class="text-xs font-semibold uppercase tracking-[0.18em] text-[#979797]">Menu Dosen</p>
<div class="mt-4 space-y-1">
@foreach ($sidebar['main'] as $menu)
<a href="{{ $menu['href'] }}" class="dashboard-sidebar-link {{ !empty($menu['active']) ? 'dashboard-sidebar-link-active' : '' }}">
<span class="dashboard-sidebar-icon">@include('dashboard.partials.icon', ['icon' => $menu['icon']])</span>
<span>{{ $menu['title'] }}</span>
</a>
@endforeach
</div>
<div class="mt-6 space-y-5 border-t border-[#E5E7EB] pt-6">
@foreach ($sidebar['sections'] as $group)
<section class="dashboard-sidebar-group">
<div class="dashboard-sidebar-group-label">
<span class="dashboard-sidebar-icon">@include('dashboard.partials.icon', ['icon' => $group['icon']])</span>
<span>{{ $group['title'] }}</span>
</div>
<div class="dashboard-sidebar-submenu">
@foreach ($group['items'] as $item)
<a href="{{ $item['href'] }}" @if(!empty($item['external'])) target="_blank" rel="noreferrer" @endif class="dashboard-sidebar-link {{ !empty($item['active']) ? 'dashboard-sidebar-link-active' : '' }}">
<span class="dashboard-sidebar-icon">@include('dashboard.partials.icon', ['icon' => $item['icon']])</span>
<span>{{ $item['title'] }}</span>
</a>
@endforeach
</div>
</section>
@endforeach
</div>
</div>
</aside>
<div class="dashboard-content space-y-5">
<div class="rounded-xl bg-white p-4 shadow-[0_8px_12px_rgba(13,10,44,0.04)] lg:p-6">
<div class="flex flex-col gap-4 lg:flex-row lg:items-start lg:justify-between">
<div>
<ol class="flex flex-wrap items-center gap-2 text-sm text-[#6B7280]">
<li class="inline-flex items-center gap-2">
<span class="text-[#625DF5]">@include('dashboard.partials.icon', ['icon' => 'home'])</span>
<span>Home</span>
</li>
<li>/</li>
<li class="font-medium text-[#15171A]">{{ $pageTitle }}</li>
</ol>
<h1 class="mt-4 text-[26px] font-bold leading-[34px] text-[#15171A]">{{ $pageTitle }}</h1>
<p class="mt-2 max-w-[880px] text-sm leading-7 text-[#4B5563]">{{ $pageDescription }}</p>
</div>
<div class="flex flex-wrap items-center gap-3">
<div class="rounded-md border border-[#E5E7EB] bg-[#F9FAFB] px-4 py-3 text-sm text-[#15171A]">{{ $pageDate }}</div>
<div class="rounded-md border border-[#E5E7EB] bg-[#F9FAFB] px-4 py-3 text-sm text-[#15171A]">{{ $user['nip'] }} · {{ $user['nmprodi'] }}</div>
<form method="POST" action="{{ route('legacy.logout') }}">
@csrf
<button type="submit" class="rounded-md bg-[#15171A] px-5.5 py-2.5 text-sm font-medium text-white hover:opacity-90">Logout</button>
</form>
</div>
</div>
@if (!empty($pageActions ?? []))
<div class="mt-5 flex flex-wrap gap-3 border-t border-[#E5E7EB] pt-5">
@foreach ($pageActions as $action)
<a href="{{ $action['href'] }}" @if(!empty($action['external'])) target="_blank" rel="noreferrer" @endif class="{{ ($action['variant'] ?? 'light') === 'dark' ? 'rounded-md bg-[#15171A] px-4 py-2.5 text-sm font-medium text-white hover:opacity-90' : 'rounded-md border border-[#D1D5DB] bg-white px-4 py-2.5 text-sm font-medium text-[#15171A] hover:bg-[#F9FAFB]' }}">{{ $action['label'] }}</a>
@endforeach
</div>
@endif
</div>
@if (session('success'))
<div class="rounded-xl border border-emerald-200 bg-emerald-50 px-4 py-3 text-sm text-emerald-800">
{{ session('success') }}
</div>
@endif
@if (session('error'))
<div class="rounded-xl border border-rose-200 bg-rose-50 px-4 py-3 text-sm text-rose-800">
{{ session('error') }}
</div>
@endif
{{ $slot }}
</div>
</div>
</main>
</x-layouts.app>

View File

@@ -0,0 +1,65 @@
<!DOCTYPE html>
<html lang="{{ str_replace('_', '-', app()->getLocale()) }}">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>{{ $title ?? 'SPOTA Rebuild' }}</title>
<meta name="description" content="Rebuild modern SPOTA Universitas Tanjungpura dengan Laravel Blade dan Tailwind.">
<link rel="preconnect" href="https://fonts.googleapis.com">
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
<link href="https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700;800;900&display=swap" rel="stylesheet">
@vite(['resources/css/app.css', 'resources/js/app.js'])
</head>
<body class="min-h-screen bg-white font-[Inter] text-[#374151] antialiased">
@php
$legacyAuth = session('legacy_auth');
$legacyRole = $legacyAuth['role'] ?? null;
$spotaLogoUrl = route('assets.spota-logo');
$dashboardRoute = match ($legacyRole) {
'mahasiswa' => route('dashboard.mahasiswa'),
'dosen' => route('dashboard.dosen'),
default => null,
};
$isDashboardShell = isset($dashboardLayout) && $dashboardLayout === true;
@endphp
<div class="min-h-screen">
<header class="fixed left-0 top-0 z-40 w-full border-b border-[#E5E7EB] bg-white">
<div class="mx-auto flex max-w-[1400px] items-center justify-between px-4 py-4 sm:px-6 xl:px-8 lg:relative">
<div class="flex w-full items-center justify-between lg:w-3/12">
<a href="{{ route('home') }}" class="inline-flex items-center">
<img src="{{ $spotaLogoUrl }}" alt="SPOTA" class="h-11 w-auto max-w-[180px] object-contain">
</a>
</div>
<div class="hidden w-full items-center justify-between lg:flex lg:w-9/12">
@if (! $isDashboardShell)
<nav>
<ul class="flex items-center gap-10 text-sm text-[#374151]">
<li><a href="{{ route('home') }}" class="hover:text-[#15171A]">Beranda</a></li>
<li><a href="{{ route('role-login') }}" class="hover:text-[#15171A]">Pilih Akun</a></li>
<li><a href="{{ route('legacy.login', 'mahasiswa') }}" class="hover:text-[#15171A]">Mahasiswa</a></li>
<li><a href="{{ route('legacy.login', 'dosen') }}" class="hover:text-[#15171A]">Dosen</a></li>
</ul>
</nav>
@else
<div class="text-sm text-[#5C6A78]">
{{ $legacyAuth['user']['nama_lengkap'] ?? 'Pengguna' }}
</div>
@endif
@if ($dashboardRoute && $isDashboardShell)
<div class="flex items-center gap-3">
<a href="{{ route('role-login') }}" class="rounded-md border border-[#E5E7EB] bg-white px-5.5 py-2.5 text-sm font-medium text-[#15171A] hover:bg-[#F3F4F6]">Portal</a>
<form method="POST" action="{{ route('legacy.logout') }}">
@csrf
<button type="submit" class="rounded-md bg-[#15171A] px-5.5 py-2.5 text-sm font-medium text-white hover:opacity-90">Logout</button>
</form>
</div>
@else
<a href="{{ route('legacy.login', 'mahasiswa') }}" class="rounded-md bg-[#15171A] px-5.5 py-2.5 text-sm font-medium text-white hover:opacity-90">Masuk</a>
@endif
</div>
</div>
</header>
{{ $slot }}
</div>
</body>
</html>

View File

@@ -0,0 +1,97 @@
<x-layouts.app :title="$title" :dashboard-layout="true">
<main class="min-h-screen bg-[#F9FAFB]">
<div class="dashboard-shell">
<aside class="dashboard-sidebar">
<div class="dashboard-sidebar-card">
<p class="text-xs font-semibold uppercase tracking-[0.18em] text-[#979797]">Menu Mahasiswa</p>
<div class="mt-4 space-y-1">
@foreach ($sidebar['main'] as $menu)
<a href="{{ $menu['href'] }}" class="dashboard-sidebar-link {{ !empty($menu['active']) ? 'dashboard-sidebar-link-active' : '' }}">
<span class="dashboard-sidebar-icon">@include('dashboard.partials.icon', ['icon' => $menu['icon']])</span>
<span>{{ $menu['title'] }}</span>
</a>
@endforeach
</div>
<div class="mt-6 space-y-5 border-t border-[#E5E7EB] pt-6">
@foreach ($sidebar['sections'] as $group)
<section class="dashboard-sidebar-group">
<div class="dashboard-sidebar-group-label">
<span class="dashboard-sidebar-icon">@include('dashboard.partials.icon', ['icon' => $group['icon']])</span>
<span>{{ $group['title'] }}</span>
</div>
<div class="dashboard-sidebar-submenu">
@foreach ($group['items'] as $item)
<a href="{{ $item['href'] }}" class="dashboard-sidebar-link {{ !empty($item['active']) ? 'dashboard-sidebar-link-active' : '' }}">
<span class="dashboard-sidebar-icon">@include('dashboard.partials.icon', ['icon' => $item['icon']])</span>
<span>{{ $item['title'] }}</span>
</a>
@endforeach
</div>
</section>
@endforeach
</div>
</div>
</aside>
<div class="dashboard-content space-y-5">
<div class="rounded-xl bg-white p-4 shadow-[0_8px_12px_rgba(13,10,44,0.04)] lg:p-6">
<div class="flex flex-col gap-4 lg:flex-row lg:items-start lg:justify-between">
<div>
<ol class="flex flex-wrap items-center gap-2 text-sm text-[#6B7280]">
<li class="inline-flex items-center gap-2">
<span class="text-[#625DF5]">@include('dashboard.partials.icon', ['icon' => 'home'])</span>
<span>Home</span>
</li>
<li>/</li>
<li class="font-medium text-[#15171A]">{{ $pageTitle }}</li>
</ol>
<h1 class="mt-4 text-[26px] font-bold leading-[34px] text-[#15171A]">{{ $pageTitle }}</h1>
<p class="mt-2 max-w-[880px] text-sm leading-7 text-[#4B5563]">{{ $pageDescription }}</p>
</div>
<div class="flex flex-wrap items-center gap-3">
<div class="rounded-md border border-[#E5E7EB] bg-[#F9FAFB] px-4 py-3 text-sm text-[#15171A]">{{ $pageDate }}</div>
<div class="rounded-md border border-[#E5E7EB] bg-[#F9FAFB] px-4 py-3 text-sm text-[#15171A]">{{ $user['nim'] }} · {{ $user['nmprodi'] }}</div>
<form method="POST" action="{{ route('legacy.logout') }}">
@csrf
<button type="submit" class="rounded-md bg-[#15171A] px-5.5 py-2.5 text-sm font-medium text-white hover:opacity-90">Logout</button>
</form>
</div>
</div>
@if (!empty($pageActions ?? []))
<div class="mt-5 flex flex-wrap gap-3 border-t border-[#E5E7EB] pt-5">
@foreach ($pageActions as $action)
<a href="{{ $action['href'] }}" class="{{ ($action['variant'] ?? 'light') === 'dark' ? 'rounded-md bg-[#15171A] px-4 py-2.5 text-sm font-medium text-white hover:opacity-90' : 'rounded-md border border-[#D1D5DB] bg-white px-4 py-2.5 text-sm font-medium text-[#15171A] hover:bg-[#F9FAFB]' }}">{{ $action['label'] }}</a>
@endforeach
</div>
@endif
</div>
@if (session('success'))
<div class="rounded-xl border border-emerald-200 bg-emerald-50 px-4 py-3 text-sm text-emerald-800">
{{ session('success') }}
</div>
@endif
@if (session('error'))
<div class="rounded-xl border border-rose-200 bg-rose-50 px-4 py-3 text-sm text-rose-800">
{{ session('error') }}
</div>
@endif
@if ($errors->any())
<div class="rounded-xl border border-rose-200 bg-rose-50 px-4 py-3 text-sm text-rose-800">
<p class="font-semibold">Form belum bisa disimpan.</p>
<ul class="mt-2 list-disc space-y-1 pl-5">
@foreach ($errors->all() as $error)
<li>{{ $error }}</li>
@endforeach
</ul>
</div>
@endif
{{ $slot }}
</div>
</div>
</main>
</x-layouts.app>

View File

@@ -0,0 +1,87 @@
<x-admin.partials.page-shell :title="$title" :sidebar="$sidebar">
<section class="rounded-xl bg-white p-4 shadow-[0_8px_12px_rgba(13,10,44,0.04)] lg:p-6">
<div class="flex flex-col gap-4 lg:flex-row lg:items-start lg:justify-between">
<div>
<ol class="flex flex-wrap items-center gap-2 text-sm text-[#6B7280]">
<li class="inline-flex items-center gap-2">
<span class="text-[#625DF5]">@include('dashboard.partials.icon', ['icon' => 'home'])</span>
<span>Home</span>
</li>
<li>/</li>
<li class="font-medium text-[#15171A]">Dashboard</li>
</ol>
<h1 class="mt-4 text-[26px] font-bold leading-[34px] text-[#15171A]">Dashboard Admin</h1>
<p class="mt-2 max-w-[880px] text-sm leading-7 text-[#4B5563]">Selamat datang di halaman administrator Sistem Pendukung Outline Tugas Akhir (SPOTA) Universitas Tanjungpura.</p>
</div>
<div class="flex flex-wrap items-center gap-3">
<div class="rounded-md border border-[#E5E7EB] bg-[#F9FAFB] px-4 py-3 text-sm text-[#15171A]">{{ $pageDate }}</div>
<div class="rounded-md border border-[#E5E7EB] bg-[#F9FAFB] px-4 py-3 text-sm text-[#15171A]">{{ $user['username'] }} · {{ $user['nmprodi'] }}</div>
<form method="POST" action="{{ route('legacy.logout') }}">
@csrf
<button type="submit" class="rounded-md bg-[#15171A] px-5.5 py-2.5 text-sm font-medium text-white hover:opacity-90">Logout</button>
</form>
</div>
</div>
</section>
<section class="grid gap-4 sm:grid-cols-2 xl:grid-cols-4">
@foreach ($stats as $stat)
<article class="rounded-xl border border-[#E5E7EB] bg-white p-5 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<p class="text-sm font-semibold text-[#5C6A78]">{{ $stat['label'] }}</p>
<p class="mt-3 text-3xl font-bold text-[#15171A]">{{ $stat['value'] }}</p>
<p class="mt-3 text-sm leading-7 text-[#6B7280]">{{ $stat['note'] }}</p>
</article>
@endforeach
</section>
<div class="grid gap-5 lg:grid-cols-[minmax(0,1fr)_380px]">
<section class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<h2 class="text-xl font-semibold text-[#15171A]">Menu Kerja Administrator</h2>
<p class="mt-2 text-sm leading-7 text-[#6B7280]">Link di bawah mengikuti struktur fungsi administrator lama. Rebuild ini menjaga akses menuju halaman yang sudah aktif tanpa mengubah proses data yang berjalan.</p>
<div class="mt-5 grid gap-4 md:grid-cols-2">
@foreach ($sidebar['sections'] as $group)
<article class="rounded-xl border border-[#E5E7EB] bg-[#F9FAFB] p-4">
<div class="flex items-center gap-2 font-semibold text-[#15171A]">
<span class="text-[#625DF5]">@include('dashboard.partials.icon', ['icon' => $group['icon']])</span>
<span>{{ $group['title'] }}</span>
</div>
<div class="mt-4 space-y-2">
@foreach ($group['items'] as $item)
<a href="{{ $item['href'] }}" @if(!empty($item['external'])) target="_blank" rel="noreferrer" @endif class="flex items-center justify-between rounded-md bg-white px-3 py-2 text-sm text-[#374151] hover:text-[#625DF5]">
<span>{{ $item['title'] }}</span>
<span>@include('dashboard.partials.icon', ['icon' => 'search'])</span>
</a>
@endforeach
</div>
</article>
@endforeach
</div>
</section>
<section class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<div class="flex items-center justify-between gap-3">
<div>
<p class="text-sm font-semibold uppercase tracking-[0.16em] text-[#979797]">Jadwal</p>
<h2 class="mt-2 text-xl font-semibold text-[#15171A]">Seminar/Sidang Terbaru</h2>
</div>
<a href="{{ route('admin.jadwal.kalender', [], false) }}" class="rounded-md border border-[#D1D5DB] px-3 py-2 text-xs font-medium text-[#15171A] hover:bg-[#F9FAFB]">Kalender</a>
</div>
<div class="mt-5 space-y-3">
@forelse ($schedules as $schedule)
<article class="rounded-xl border border-[#E5E7EB] bg-[#F9FAFB] p-4">
<div class="flex items-start justify-between gap-3">
<div>
<p class="font-semibold text-[#15171A]">{{ $schedule['jenis'] }}</p>
<p class="mt-1 text-sm text-[#6B7280]">{{ $schedule['mahasiswa'] }}</p>
</div>
<span class="rounded-full bg-white px-2.5 py-1 text-xs font-semibold text-[#4B5563]">{{ $schedule['ruangan'] }}</span>
</div>
<p class="mt-3 text-sm text-[#4B5563]">{{ $schedule['tanggal'] }}</p>
</article>
@empty
<div class="rounded-xl border border-dashed border-[#D1D5DB] bg-[#F9FAFB] p-5 text-center text-sm text-[#6B7280]">Belum ada jadwal seminar/sidang.</div>
@endforelse
</div>
</section>
</div>
</x-admin.partials.page-shell>

View File

@@ -0,0 +1,128 @@
<x-dosen.partials.page-shell :title="$title" :sidebar="$sidebar ?? $dashboard['sidebar']" :page-title="$dashboard['pageTitle']" :page-description="$dashboard['welcomeText']" :page-date="$dashboard['dateLabel']" :user="$user">
<section>
<article class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)] lg:p-7">
<h2 class="text-[22px] font-semibold leading-[30px] text-[#15171A]">{{ $dashboard['welcomeTitle'] }}</h2>
<p class="mt-3 max-w-[920px] text-[15px] leading-7 text-[#4B5563]">{{ $dashboard['welcomeText'] }}</p>
@if ($dashboard['androidLink'])
<div class="mt-5">
<a href="{{ $dashboard['androidLink'] }}" target="_blank" rel="noreferrer" class="inline-flex items-center rounded-md bg-[#2D68F8] px-4 py-2.5 text-sm font-medium text-white hover:opacity-90">Unduh Aplikasi SPOTA Android</a>
</div>
@endif
</article>
</section>
<section class="grid gap-5 lg:grid-cols-3">
<article class="rounded-xl border border-[#F2D38B] bg-[#FFF9E9] p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<div class="flex items-start gap-3">
<div class="mt-0.5 inline-flex h-9 w-9 shrink-0 items-center justify-center rounded-full bg-[#FDE7AE] text-[#A16207]">
@include('dashboard.partials.icon', ['icon' => 'warning'])
</div>
<div class="min-w-0 flex-1">
<h3 class="text-lg font-semibold text-[#15171A]">{{ $dashboard['announcementNotice']['title'] }}</h3>
<p class="mt-2 text-sm leading-7 text-[#5B4A1C]">{{ $dashboard['announcementNotice']['message'] }}</p>
<div class="mt-4">
<a href="{{ $dashboard['announcementNotice']['primaryHref'] }}" class="inline-flex items-center rounded-md bg-[#EAB308] px-4 py-2.5 text-sm font-medium text-[#15171A] hover:opacity-90">{{ $dashboard['announcementNotice']['primaryLabel'] }}</a>
</div>
</div>
</div>
</article>
<article class="rounded-xl border border-[#F2D38B] bg-[#FFF9E9] p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<div class="flex items-start gap-3">
<div class="mt-0.5 inline-flex h-9 w-9 shrink-0 items-center justify-center rounded-full bg-[#FDE7AE] text-[#A16207]">
@include('dashboard.partials.icon', ['icon' => 'warning'])
</div>
<div class="min-w-0 flex-1">
<h3 class="text-lg font-semibold text-[#15171A]">{{ $dashboard['proposalNotice']['title'] }}</h3>
<p class="mt-2 text-sm leading-7 text-[#5B4A1C]">{{ $dashboard['proposalNotice']['message'] }}</p>
<div class="mt-4 flex flex-wrap gap-3">
<a href="{{ $dashboard['proposalNotice']['primaryHref'] }}" class="inline-flex items-center rounded-md bg-[#EAB308] px-4 py-2.5 text-sm font-medium text-[#15171A] hover:opacity-90">{{ $dashboard['proposalNotice']['primaryLabel'] }}</a>
@if ($dashboard['proposalNotice']['secondaryLabel'])
<a href="{{ $dashboard['proposalNotice']['secondaryHref'] }}" class="inline-flex items-center rounded-md border border-[#E5C35C] bg-white px-4 py-2.5 text-sm font-medium text-[#15171A] hover:bg-[#FFFDF5]">{{ $dashboard['proposalNotice']['secondaryLabel'] }}</a>
@endif
</div>
</div>
</div>
</article>
<article class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<div class="flex items-center justify-between gap-3">
<div>
<p class="text-sm font-semibold uppercase tracking-[0.16em] text-[#979797]">Agenda Terdekat</p>
<h3 class="mt-2 text-xl font-semibold text-[#15171A]">Jadwal Seminar</h3>
</div>
<span class="rounded-full border border-[#E5E7EB] bg-[#F9FAFB] px-3 py-1 text-xs font-semibold text-[#4B5563]">{{ count($dashboard['upcomingSchedules']) }} data</span>
</div>
@if ($dashboard['upcomingSchedules'] === [])
<div class="mt-5 rounded-lg border border-dashed border-[#D1D5DB] bg-[#F9FAFB] p-5 text-sm leading-7 text-[#6B7280]">
Belum ada jadwal seminar terdekat yang terpublikasi untuk program studi ini.
</div>
@else
<div class="mt-5 space-y-3">
@foreach ($dashboard['upcomingSchedules'] as $schedule)
<div class="rounded-lg border border-[#E5E7EB] bg-[#F9FAFB] p-4">
<div class="flex flex-wrap items-start justify-between gap-3">
<div>
<div class="flex flex-wrap items-center gap-2">
<span class="rounded-full px-2.5 py-1 text-[11px] font-semibold {{ $schedule['jenisClass'] }}">{{ $schedule['jenis'] }}</span>
<p class="text-sm font-semibold text-[#15171A]">{{ $schedule['nama'] }}</p>
<span class="text-sm text-[#6B7280]">{{ $schedule['nim'] }}</span>
</div>
<p class="mt-2 text-sm leading-6 text-[#4B5563]">{{ $schedule['judul'] }}</p>
</div>
<div class="text-right text-sm text-[#6B7280]">
<p>{{ $schedule['tanggal'] }}</p>
<p class="mt-1">{{ $schedule['ruangan'] }}</p>
</div>
</div>
</div>
@endforeach
</div>
@endif
</article>
</section>
<section>
<article class="rounded-xl border border-[#E5E7EB] bg-white p-5 shadow-[0_8px_12px_rgba(13,10,44,0.04)] lg:p-6 xl:p-7">
<div class="flex items-center justify-between gap-3">
<div>
<p class="text-sm font-semibold uppercase tracking-[0.16em] text-[#979797]">Kalender</p>
<h3 class="mt-2 text-xl font-semibold text-[#15171A]">{{ $dashboard['calendar']['monthLabel'] }}</h3>
</div>
<span class="rounded-full border border-[#E5E7EB] bg-[#F9FAFB] px-3 py-1 text-xs font-semibold text-[#4B5563]">Publikasi jadwal aktif</span>
</div>
<div class="mt-6 grid grid-cols-7 gap-2.5 text-center text-xs font-semibold uppercase tracking-[0.12em] text-[#9CA3AF]">
@foreach ($dashboard['calendar']['weekdays'] as $weekday)
<div class="rounded-md bg-[#F9FAFB] px-2 py-2.5">{{ $weekday }}</div>
@endforeach
</div>
<div class="mt-3 space-y-2.5">
@foreach ($dashboard['calendar']['weeks'] as $week)
<div class="grid grid-cols-7 gap-2.5">
@foreach ($week as $day)
<div class="aspect-[0.82/1] min-h-[72px] rounded-lg border px-1.5 py-1.5 {{ $day['isCurrentMonth'] ? 'border-[#E5E7EB] bg-white' : 'border-[#EEF2F7] bg-[#F9FAFB]/80' }} {{ $day['isToday'] ? 'ring-2 ring-[#625DF5]/20' : '' }}">
<div class="flex items-center justify-between">
<span class="text-[13px] font-semibold {{ $day['isCurrentMonth'] ? 'text-[#15171A]' : 'text-[#9CA3AF]' }}">{{ $day['day'] }}</span>
@if ($day['isToday'])
<span class="rounded-full bg-[#625DF5] px-1 py-0.5 text-[8px] font-semibold leading-none text-white">Hari ini</span>
@endif
</div>
<div class="mt-1.5 space-y-1">
@foreach (array_slice($day['events'], 0, 3) as $event)
<div class="rounded-md border px-1.5 py-0.5 text-[8px] leading-3 {{ $event['className'] }}">
<p class="font-semibold">{{ $event['jenis'] }}</p>
<p class="truncate">{{ $event['title'] }}</p>
</div>
@endforeach
</div>
</div>
@endforeach
</div>
@endforeach
</div>
</article>
</section>
</x-dosen.partials.page-shell>

View File

@@ -0,0 +1,118 @@
<x-layouts.app :title="$title" :dashboard-layout="true">
<main class="bg-[#F9FAFB] min-h-screen">
<div class="dashboard-shell">
<aside class="dashboard-sidebar">
<div class="dashboard-sidebar-card">
<p class="text-xs font-semibold uppercase tracking-[0.18em] text-[#979797]">Menu Mahasiswa</p>
<div class="mt-4 space-y-1">
@foreach ($dashboard['menus'] as $menu)
@if (isset($menu['children']))
<div class="dashboard-sidebar-group">
<div class="dashboard-sidebar-group-label">
<span class="dashboard-sidebar-icon">@include('dashboard.partials.icon', ['icon' => $menu['icon']])</span>
<span>{{ $menu['title'] }}</span>
</div>
<div class="dashboard-sidebar-submenu">
@foreach ($menu['children'] as $child)
<a href="{{ $child['href'] }}" class="dashboard-sidebar-link">
<span class="dashboard-sidebar-icon">@include('dashboard.partials.icon', ['icon' => $child['icon']])</span>
<span>{{ $child['title'] }}</span>
</a>
@endforeach
</div>
</div>
@else
<a href="{{ $menu['href'] }}" class="dashboard-sidebar-link {{ !empty($menu['active']) ? 'dashboard-sidebar-link-active' : '' }}">
<span class="dashboard-sidebar-icon">@include('dashboard.partials.icon', ['icon' => $menu['icon']])</span>
<span>{{ $menu['title'] }}</span>
</a>
@endif
@endforeach
</div>
</div>
</aside>
<div class="dashboard-content">
<div class="flex flex-col gap-7.5 rounded-xl bg-white p-4 shadow-[0_8px_12px_rgba(13,10,44,0.04)] lg:flex-row lg:items-center lg:justify-between lg:p-6">
<div class="lg:max-w-[700px]">
<span class="mb-4 inline-flex rounded-full bg-[#625DF5]/[0.08] px-3 py-1 text-sm font-medium text-[#625DF5]">{{ $dashboard['eyebrow'] }}</span>
<h1 class="mb-4 font-bold text-[22px] leading-[30px] text-[#15171A] xl:text-[30px] xl:leading-[38px]">{{ $dashboard['title'] }}</h1>
<p>{{ $dashboard['description'] }}</p>
</div>
<div class="flex flex-wrap items-center gap-3">
<div class="rounded-md border border-[#E5E7EB] bg-[#F9FAFB] px-4 py-3 text-sm text-[#15171A]">{{ $user['nim'] }} · {{ $user['nmprodi'] }}</div>
<form method="POST" action="{{ route('legacy.logout') }}">
@csrf
<button type="submit" class="rounded-md bg-[#15171A] px-5.5 py-2.5 text-sm font-medium text-white hover:opacity-90">Logout</button>
</form>
</div>
</div>
<section id="ringkasan" class="mt-5 grid gap-4 sm:grid-cols-2 xl:grid-cols-4">
@foreach ($dashboard['stats'] as $stat)
<article class="rounded-xl border border-[#E5E7EB] bg-white p-5 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<p class="text-sm font-semibold text-[#5C6A78]">{{ $stat['label'] }}</p>
<div class="mt-3 flex items-start justify-between gap-4">
<p class="text-3xl font-bold text-[#15171A]">{{ $stat['value'] }}</p>
<span class="rounded-md px-3 py-1 text-xs font-semibold {{ $stat['deltaClass'] }}">{{ $stat['delta'] }}</span>
</div>
<p class="mt-3 text-sm leading-7">{{ $stat['note'] }}</p>
</article>
@endforeach
</section>
<div class="mt-6 grid gap-6 lg:grid-cols-[minmax(0,1fr)_380px]">
<section class="space-y-6">
<article id="status-usulan" class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<h2 class="text-xl font-semibold text-[#15171A]">Status Usulan</h2>
@if ($dashboard['latestTitle'])
<p class="mt-3 text-sm leading-7 text-[#4B5563]">Judul terakhir: {{ $dashboard['latestTitle'] }}</p>
@endif
<div class="mt-5 rounded-xl border p-5 {{ $dashboard['statusAlert']['class'] }}">
<h3 class="text-lg font-semibold">{{ $dashboard['statusAlert']['title'] }}</h3>
<p class="mt-3 text-sm leading-7">{{ $dashboard['statusAlert']['description'] }}</p>
@if ($dashboard['statusAlert']['button'])
<div class="mt-4">
<a href="{{ $dashboard['statusAlert']['buttonHref'] }}" class="inline-flex rounded-md px-4 py-2.5 text-sm font-medium {{ $dashboard['statusAlert']['buttonClass'] }}">{{ $dashboard['statusAlert']['button'] }}</a>
</div>
@endif
</div>
</article>
<article id="pengumuman" class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<h2 class="text-xl font-semibold text-[#15171A]">Pengumuman</h2>
<div class="mt-5 rounded-xl border p-5 {{ $dashboard['announcementAlert']['class'] }}">
<h3 class="text-lg font-semibold">{{ $dashboard['announcementAlert']['title'] }}</h3>
<p class="mt-3 text-sm leading-7">{{ $dashboard['announcementAlert']['description'] }}</p>
<div class="mt-4">
<a href="{{ $dashboard['announcementAlert']['buttonHref'] }}" class="inline-flex rounded-md px-4 py-2.5 text-sm font-medium {{ $dashboard['announcementAlert']['buttonClass'] }}">{{ $dashboard['announcementAlert']['button'] }}</a>
</div>
</div>
</article>
</section>
<section id="jadwal" class="space-y-6">
<article class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<div class="flex items-center justify-between gap-3">
<div>
<p class="text-sm font-semibold uppercase tracking-[0.16em] text-[#979797]">Jadwal</p>
<h2 class="mt-2 text-xl font-semibold text-[#15171A]">Jadwal Terdekat</h2>
</div>
<span class="rounded-full border border-[#E5E7EB] bg-[#F9FAFB] px-3 py-1 text-xs font-semibold text-[#4B5563]">{{ $dashboard['publishedSchedules'] }} publikasi</span>
</div>
@if ($dashboard['nextSchedule'])
<div class="mt-5 rounded-xl border border-sky-200 bg-sky-50 p-5 text-sky-900">
<p class="text-sm font-semibold uppercase tracking-[0.16em]">{{ $dashboard['nextSchedule']['jenis'] }}</p>
<p class="mt-3 text-lg font-semibold">{{ $dashboard['nextSchedule']['tanggal'] }}</p>
<p class="mt-2 text-sm leading-7">Ruangan: {{ $dashboard['nextSchedule']['ruangan'] }}</p>
</div>
@else
<div class="mt-5 rounded-xl border border-dashed border-[#D1D5DB] bg-[#F9FAFB] p-5 text-sm leading-7 text-[#6B7280]">
Belum ada jadwal seminar yang dipublikasikan untuk mahasiswa ini.
</div>
@endif
</article>
</section>
</div>
</div>
</div>
</main>
</x-layouts.app>

View File

@@ -0,0 +1,46 @@
@switch($icon)
@case('home')
<svg viewBox="0 0 24 24" class="h-[18px] w-[18px]" fill="none" stroke="currentColor" stroke-width="1.8" stroke-linecap="round" stroke-linejoin="round"><path d="M3 10.5 12 3l9 7.5"/><path d="M5 9.5V21h14V9.5"/></svg>
@break
@case('folder')
<svg viewBox="0 0 24 24" class="h-[18px] w-[18px]" fill="none" stroke="currentColor" stroke-width="1.8" stroke-linecap="round" stroke-linejoin="round"><path d="M3 7.5A2.5 2.5 0 0 1 5.5 5H10l2 2h6.5A2.5 2.5 0 0 1 21 9.5v8A2.5 2.5 0 0 1 18.5 20h-13A2.5 2.5 0 0 1 3 17.5z"/></svg>
@break
@case('briefcase')
<svg viewBox="0 0 24 24" class="h-[18px] w-[18px]" fill="none" stroke="currentColor" stroke-width="1.8" stroke-linecap="round" stroke-linejoin="round"><path d="M9 6V4.5h6V6"/><path d="M4 8.5h16v9A2.5 2.5 0 0 1 17.5 20h-11A2.5 2.5 0 0 1 4 17.5z"/><path d="M4 11h16"/></svg>
@break
@case('chat')
<svg viewBox="0 0 24 24" class="h-[18px] w-[18px]" fill="none" stroke="currentColor" stroke-width="1.8" stroke-linecap="round" stroke-linejoin="round"><path d="M5 6.5A2.5 2.5 0 0 1 7.5 4h9A2.5 2.5 0 0 1 19 6.5v6A2.5 2.5 0 0 1 16.5 15H10l-4 4v-4H7.5A2.5 2.5 0 0 1 5 12.5z"/></svg>
@break
@case('search')
<svg viewBox="0 0 24 24" class="h-[18px] w-[18px]" fill="none" stroke="currentColor" stroke-width="1.8" stroke-linecap="round" stroke-linejoin="round"><circle cx="11" cy="11" r="5.5"/><path d="m16 16 4 4"/></svg>
@break
@case('users')
<svg viewBox="0 0 24 24" class="h-[18px] w-[18px]" fill="none" stroke="currentColor" stroke-width="1.8" stroke-linecap="round" stroke-linejoin="round"><path d="M16.5 19a4.5 4.5 0 0 0-9 0"/><circle cx="12" cy="9" r="3"/><path d="M18.5 18a3.5 3.5 0 0 0-2.5-3.36"/><path d="M8 14.64A3.5 3.5 0 0 0 5.5 18"/></svg>
@break
@case('bell')
<svg viewBox="0 0 24 24" class="h-[18px] w-[18px]" fill="none" stroke="currentColor" stroke-width="1.8" stroke-linecap="round" stroke-linejoin="round"><path d="M12 4.5a4 4 0 0 0-4 4V11c0 1.4-.5 2.75-1.4 3.82L5.5 16h13l-1.1-1.18A5.74 5.74 0 0 1 16 11V8.5a4 4 0 0 0-4-4Z"/><path d="M10 18a2 2 0 0 0 4 0"/></svg>
@break
@case('megaphone')
<svg viewBox="0 0 24 24" class="h-[18px] w-[18px]" fill="none" stroke="currentColor" stroke-width="1.8" stroke-linecap="round" stroke-linejoin="round"><path d="M4 11v2a2 2 0 0 0 2 2h2l3 3V6L8 9H6a2 2 0 0 0-2 2Z"/><path d="M14 8.5a6 6 0 0 1 0 7"/><path d="M16.5 6a9 9 0 0 1 0 12"/></svg>
@break
@case('user')
<svg viewBox="0 0 24 24" class="h-[18px] w-[18px]" fill="none" stroke="currentColor" stroke-width="1.8" stroke-linecap="round" stroke-linejoin="round"><circle cx="12" cy="8" r="3.5"/><path d="M5.5 19a6.5 6.5 0 0 1 13 0"/></svg>
@break
@case('document')
<svg viewBox="0 0 24 24" class="h-[18px] w-[18px]" fill="none" stroke="currentColor" stroke-width="1.8" stroke-linecap="round" stroke-linejoin="round"><path d="M8 3.5h6l4 4V20a1.5 1.5 0 0 1-1.5 1.5h-8A1.5 1.5 0 0 1 7 20V5A1.5 1.5 0 0 1 8.5 3.5Z"/><path d="M14 3.5V8h4"/></svg>
@break
@case('warning')
<svg viewBox="0 0 24 24" class="h-[18px] w-[18px]" fill="none" stroke="currentColor" stroke-width="1.8" stroke-linecap="round" stroke-linejoin="round"><path d="M12 4 21 20H3z"/><path d="M12 9v4.5"/><circle cx="12" cy="16.5" r=".8" fill="currentColor" stroke="none"/></svg>
@break
@case('clipboard')
<svg viewBox="0 0 24 24" class="h-[18px] w-[18px]" fill="none" stroke="currentColor" stroke-width="1.8" stroke-linecap="round" stroke-linejoin="round"><path d="M9 4.5h6"/><path d="M9.5 3h5A1.5 1.5 0 0 1 16 4.5V6h2A1.5 1.5 0 0 1 19.5 7.5v12A1.5 1.5 0 0 1 18 21h-12a1.5 1.5 0 0 1-1.5-1.5v-12A1.5 1.5 0 0 1 6 6h2V4.5A1.5 1.5 0 0 1 9.5 3Z"/></svg>
@break
@case('clock')
<svg viewBox="0 0 24 24" class="h-[18px] w-[18px]" fill="none" stroke="currentColor" stroke-width="1.8" stroke-linecap="round" stroke-linejoin="round"><circle cx="12" cy="12" r="8"/><path d="M12 7.5V12l3 2"/></svg>
@break
@case('chart')
<svg viewBox="0 0 24 24" class="h-[18px] w-[18px]" fill="none" stroke="currentColor" stroke-width="1.8" stroke-linecap="round" stroke-linejoin="round"><path d="M5 19.5h14"/><path d="M7.5 17V10"/><path d="M12 17V6.5"/><path d="M16.5 17v-4"/></svg>
@break
@default
<svg viewBox="0 0 24 24" class="h-[18px] w-[18px]" fill="none" stroke="currentColor" stroke-width="1.8" stroke-linecap="round" stroke-linejoin="round"><circle cx="12" cy="12" r="7"/></svg>
@endswitch

View File

@@ -0,0 +1,25 @@
<x-dosen.partials.page-shell :title="$title" :sidebar="$sidebar" :page-title="$pageTitle" :page-description="$pageDescription" :page-date="$pageDate" :user="$user">
<section class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<div class="space-y-4">
@forelse ($bimbingan as $item)
<article class="rounded-xl border border-[#E5E7EB] bg-[#F9FAFB] p-5">
<div class="flex flex-col gap-4 lg:flex-row lg:items-start lg:justify-between">
<div class="min-w-0 flex-1">
<h3 class="break-words text-lg font-semibold leading-7 text-[#15171A]">{{ $item['judul'] }}</h3>
<div class="mt-3 grid gap-2 text-sm text-[#6B7280] sm:grid-cols-2 xl:grid-cols-3">
<span class="break-words">{{ $item['mahasiswa'] }}</span>
<span>{{ $item['periode'] }}</span>
<span>{{ $item['tanggal'] }}</span>
</div>
</div>
<div class="shrink-0">
<a href="{{ $item['reviewHref'] }}" class="inline-flex rounded-md border border-[#D1D5DB] bg-white px-3 py-2 text-xs font-medium text-[#15171A] hover:bg-[#F9FAFB]">Lihat Data</a>
</div>
</div>
</article>
@empty
<div class="rounded-xl border border-dashed border-[#D1D5DB] bg-[#F9FAFB] p-6 text-center text-[#6B7280]">Belum ada data bimbingan.</div>
@endforelse
</div>
</section>
</x-dosen.partials.page-shell>

View File

@@ -0,0 +1,34 @@
<x-dosen.partials.page-shell :title="$title" :sidebar="$sidebar" :page-title="$pageTitle" :page-description="$pageDescription" :page-date="$pageDate" :user="$user">
<section class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<form method="GET" class="grid gap-4 lg:grid-cols-[220px_minmax(0,1fr)_120px]">
<select name="by" class="template-input">
<option value="nim" @selected($searchBy === 'nim')>NIM</option>
<option value="judul" @selected($searchBy === 'judul')>Judul Praoutline</option>
<option value="dosen" @selected($searchBy === 'dosen')>Pembimbing/Penguji</option>
</select>
<input type="text" name="q" value="{{ $keyword }}" class="template-input" placeholder="Cari...">
<button type="submit" class="template-button-dark">Cari</button>
</form>
<div class="mt-6 space-y-4">
@if ($keyword !== '' && $results === [])
<div class="rounded-xl border border-dashed border-[#D1D5DB] bg-[#F9FAFB] p-6 text-center text-[#6B7280]">Tidak ada hasil untuk `{{ $keyword }}`.</div>
@endif
@foreach ($results as $item)
<article class="rounded-xl border border-[#E5E7EB] bg-[#F9FAFB] p-5">
<h3 class="text-lg font-semibold text-[#15171A]">{{ $item['judul'] }}</h3>
<p class="mt-2 text-sm text-[#4B5563]">{{ $item['deskripsi'] }}</p>
<div class="mt-3 flex flex-wrap gap-3 text-sm text-[#6B7280]">
<span>{{ $item['mahasiswa'] }}</span>
<span>{{ $item['tanggal'] }}</span>
<span>{{ $item['status'] }}</span>
</div>
<div class="mt-4">
<a href="{{ $item['reviewHref'] }}" class="rounded-md bg-[#15171A] px-3 py-2 text-xs font-medium text-white hover:opacity-90">Buka Review</a>
</div>
</article>
@endforeach
</div>
</section>
</x-dosen.partials.page-shell>

View File

@@ -0,0 +1,26 @@
<x-dosen.partials.page-shell :title="$title" :sidebar="$sidebar" :page-title="$pageTitle" :page-description="$pageDescription" :page-date="$pageDate" :user="$user">
<section class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<div class="space-y-4">
@forelse ($usulan as $item)
<article class="rounded-xl border border-[#E5E7EB] bg-[#F9FAFB] p-5">
<div class="flex flex-wrap items-start justify-between gap-4">
<div>
<h3 class="text-lg font-semibold text-[#15171A]">{{ $item['judul'] }}</h3>
<p class="mt-2 text-sm text-[#4B5563]">{{ $item['mahasiswa'] }}</p>
<p class="mt-2 text-sm text-[#6B7280]">{{ $item['periode'] }} · {{ $item['tanggal'] }}</p>
<div class="mt-4 flex flex-wrap gap-2">
<a href="{{ $item['reviewHref'] }}" class="rounded-md bg-[#15171A] px-3 py-2 text-xs font-medium text-white hover:opacity-90">Review</a>
</div>
</div>
<div class="text-right">
<div class="rounded-full bg-white px-3 py-1 text-xs font-semibold text-[#15171A]">{{ $item['status'] }}</div>
<p class="mt-3 text-sm text-[#6B7280]">KK: {{ $item['kk'] }}</p>
</div>
</div>
</article>
@empty
<div class="rounded-xl border border-dashed border-[#D1D5DB] bg-[#F9FAFB] p-6 text-center text-[#6B7280]">Tidak ada usulan aktif.</div>
@endforelse
</div>
</section>
</x-dosen.partials.page-shell>

View File

@@ -0,0 +1,70 @@
<x-dosen.partials.page-shell :title="$title" :sidebar="$sidebar" :page-title="$pageTitle" :page-description="$pageDescription" :page-date="$pageDate" :user="$user">
<section class="grid gap-5 lg:grid-cols-6">
<article class="rounded-xl border border-[#3B0A0A] bg-[#FFF1F1] p-5 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<p class="text-sm font-semibold uppercase tracking-[0.16em] text-[#7F1D1D]">Ancaman DO</p>
<p class="mt-3 text-3xl font-bold text-[#3B0A0A]">{{ $summary['dropoutCount'] }}</p>
<p class="mt-2 text-sm leading-6 text-[#7F1D1D]">Mahasiswa angkatan lama di ambang akhir masa studi.</p>
</article>
<article class="rounded-xl border border-rose-300 bg-rose-50 p-5 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<p class="text-sm font-semibold uppercase tracking-[0.16em] text-rose-700">Kritis</p>
<p class="mt-3 text-3xl font-bold text-rose-800">{{ $summary['criticalCount'] }}</p>
<p class="mt-2 text-sm leading-6 text-rose-700">Tahun akhir studi dan berisiko tinggi.</p>
</article>
<article class="rounded-xl border border-rose-200 bg-rose-50 p-5 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<p class="text-sm font-semibold uppercase tracking-[0.16em] text-rose-700">Warning</p>
<p class="mt-3 text-3xl font-bold text-rose-800">{{ $summary['warningCount'] }}</p>
<p class="mt-2 text-sm leading-6 text-rose-700">Sudah masuk fase studi lanjut dan perlu follow-up.</p>
</article>
<article class="rounded-xl border border-amber-200 bg-amber-50 p-5 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<p class="text-sm font-semibold uppercase tracking-[0.16em] text-amber-700">Perlu Pantau</p>
<p class="mt-3 text-3xl font-bold text-amber-800">{{ $summary['watchCount'] }}</p>
<p class="mt-2 text-sm leading-6 text-amber-700">Mulai masuk tahun studi yang perlu perhatian.</p>
</article>
<article class="rounded-xl border border-emerald-200 bg-emerald-50 p-5 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<p class="text-sm font-semibold uppercase tracking-[0.16em] text-emerald-700">Aman</p>
<p class="mt-3 text-3xl font-bold text-emerald-800">{{ $summary['safeCount'] }}</p>
<p class="mt-2 text-sm leading-6 text-emerald-700">Masih dalam rentang monitoring rutin.</p>
</article>
<article class="rounded-xl border border-[#E5E7EB] bg-white p-5 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<p class="text-sm font-semibold uppercase tracking-[0.16em] text-[#979797]">Total Data</p>
<p class="mt-3 text-3xl font-bold text-[#15171A]">{{ $summary['totalCount'] }}</p>
<p class="mt-2 text-sm leading-6 text-[#4B5563]">Seluruh mahasiswa bimbingan yang termonitor.</p>
</article>
</section>
<section class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<div class="mb-5 rounded-xl border border-rose-200 bg-rose-50 p-4 text-sm leading-7 text-rose-800">
Prioritaskan mahasiswa dengan status <strong>Ancaman DO</strong>, <strong>Kritis</strong>, dan <strong>Warning</strong>. Penilaian risiko memakai angkatan mahasiswa dan umur studi, dengan fallback pembacaan angkatan dari pola NIM.
</div>
<div class="space-y-4">
@forelse ($records as $item)
<article class="rounded-xl border border-[#E5E7EB] bg-[#F9FAFB] p-5">
<div class="flex flex-col gap-4 lg:flex-row lg:items-start lg:justify-between">
<div class="min-w-0 flex-1">
<div class="flex flex-wrap items-center gap-2">
<h3 class="text-lg font-semibold text-[#15171A]">{{ $item['mahasiswa'] }}</h3>
<span class="rounded-full px-2.5 py-1 text-[11px] font-semibold {{ $item['statusClass'] }}">{{ $item['status'] }}</span>
</div>
<p class="mt-3 break-words text-sm leading-7 text-[#4B5563]">{{ $item['judul'] }}</p>
<div class="mt-3 flex flex-wrap gap-3 text-sm text-[#6B7280]">
<span>Angkatan {{ $item['angkatan'] ?? '-' }}</span>
<span>{{ !is_null($item['tahunStudi']) ? $item['tahunStudi'].' tahun studi' : 'Tahun studi tidak diketahui' }}</span>
<span>{{ $item['tanggal'] }}</span>
@if (!is_null($item['days']))
<span>{{ $item['days'] }} hari sejak keputusan</span>
@endif
</div>
<p class="mt-3 text-sm leading-6 {{ in_array($item['severity'], ['dropout', 'critical', 'warning'], true) ? 'text-rose-700' : ($item['severity'] === 'watch' ? 'text-amber-700' : 'text-emerald-700') }}">{{ $item['warningText'] }}</p>
</div>
<div class="shrink-0">
<a href="{{ $item['detailHref'] }}" target="_blank" rel="noreferrer" class="inline-flex rounded-md border border-[#D1D5DB] bg-white px-3 py-2 text-xs font-medium text-[#15171A] hover:bg-[#F9FAFB]">Buka Monitoring Lengkap</a>
</div>
</div>
</article>
@empty
<div class="rounded-xl border border-dashed border-[#D1D5DB] bg-[#F9FAFB] p-6 text-center text-[#6B7280]">Belum ada data early warning.</div>
@endforelse
</div>
</section>
</x-dosen.partials.page-shell>

View File

@@ -0,0 +1,19 @@
<x-dosen.partials.page-shell :title="$title" :sidebar="$sidebar" :page-title="$pageTitle" :page-description="$pageDescription" :page-date="$pageDate" :user="$user">
<section class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<div class="space-y-3">
@forelse ($pemberitahuan as $item)
<article class="rounded-xl border border-[#E5E7EB] bg-[#F9FAFB] p-4">
<p class="text-sm text-[#6B7280]">{{ \Carbon\Carbon::parse($item['tgl'])->locale('id')->translatedFormat('j F Y, H:i') }}</p>
<p class="mt-2 text-[#15171A]">{{ $item['msg'] }}</p>
@if ($item['reviewHref'])
<div class="mt-4">
<a href="{{ $item['reviewHref'] }}" class="rounded-md border border-[#D1D5DB] bg-white px-3 py-2 text-xs font-medium text-[#15171A] hover:bg-[#F9FAFB]">Buka Review</a>
</div>
@endif
</article>
@empty
<div class="rounded-xl border border-dashed border-[#D1D5DB] bg-[#F9FAFB] p-6 text-center text-[#6B7280]">Tidak Ada Pemberitahuan Terbaru</div>
@endforelse
</div>
</section>
</x-dosen.partials.page-shell>

View File

@@ -0,0 +1,31 @@
<x-dosen.partials.page-shell :title="$title" :sidebar="$sidebar" :page-title="$pageTitle" :page-description="$pageDescription" :page-date="$pageDate" :user="$user">
<section class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<form method="POST" action="{{ $formAction }}" class="space-y-6">
@csrf
@if ($formMethod !== 'POST')
@method($formMethod)
@endif
<div>
<label for="judul_penawaran" class="mb-2 block text-sm font-medium text-[#15171A]">Judul</label>
<input id="judul_penawaran" type="text" name="judul_penawaran" value="{{ $penawaranItem['judul'] }}" class="template-input" required>
@error('judul_penawaran')
<p class="mt-2 text-sm text-rose-600">{{ $message }}</p>
@enderror
</div>
<div>
<label for="keterangan_penawaran" class="mb-2 block text-sm font-medium text-[#15171A]">Keterangan</label>
<textarea id="keterangan_penawaran" name="keterangan_penawaran" rows="10" class="template-input">{{ $penawaranItem['deskripsi'] }}</textarea>
@error('keterangan_penawaran')
<p class="mt-2 text-sm text-rose-600">{{ $message }}</p>
@enderror
</div>
<div class="flex flex-wrap gap-3">
<button type="submit" class="template-button-dark">{{ $formMode === 'create' ? 'Simpan Data' : 'Simpan Perubahan' }}</button>
<a href="{{ route('dosen.penawaran.index') }}" class="rounded-md border border-[#D1D5DB] bg-white px-4 py-2.5 text-sm font-medium text-[#15171A] hover:bg-[#F9FAFB]">Kembali</a>
</div>
</form>
</section>
</x-dosen.partials.page-shell>

View File

@@ -0,0 +1,94 @@
<x-dosen.partials.page-shell :title="$title" :sidebar="$sidebar" :page-title="$pageTitle" :page-description="$pageDescription" :page-date="$pageDate" :user="$user" :page-actions="$pageActions ?? []">
<section class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<form method="GET" class="grid gap-4 border-b border-[#E5E7EB] pb-6 lg:grid-cols-4">
<label class="block text-sm text-[#374151]">
<span class="mb-2 block font-medium text-[#15171A]">Tampilkan :</span>
<select name="sumber" class="template-input">
<option value="0" @selected($source === '0')>Judul Saya</option>
<option value="1" @selected($source === '1')>Semua Dosen</option>
</select>
</label>
<label class="block text-sm text-[#374151]">
<span class="mb-2 block font-medium text-[#15171A]">Status :</span>
<select name="status" class="template-input">
<option value="Semua" @selected($statusFilter === 'Semua')>Semua</option>
<option value="Belum Diambil" @selected($statusFilter === 'Belum Diambil')>Belum Diambil</option>
<option value="Belum Diproses" @selected($statusFilter === 'Belum Diproses')>Belum Diproses</option>
<option value="Diterima" @selected($statusFilter === 'Diterima')>Diterima</option>
</select>
</label>
<label class="block text-sm text-[#374151]">
<span class="mb-2 block font-medium text-[#15171A]">Status :</span>
<select name="kk" class="template-input">
<option value="all" @selected($kkFilter === 'all')>Semua KK</option>
@foreach ($kkOptions as $option)
<option value="{{ $option['value'] }}" @selected($kkFilter === $option['value'])>{{ $option['label'] }}</option>
@endforeach
</select>
</label>
<div class="flex items-end gap-3">
<button type="submit" class="template-button-dark w-full lg:w-auto">Filter</button>
</div>
</form>
<div class="mt-6 overflow-x-auto">
<table class="min-w-full divide-y divide-[#E5E7EB] text-sm">
<thead>
<tr class="text-left text-[#6B7280]">
<th class="px-4 py-3 font-semibold">No.</th>
<th class="px-4 py-3 font-semibold">Judul</th>
<th class="px-4 py-3 font-semibold">Deskripsi</th>
<th class="px-4 py-3 font-semibold">Ditawarkan Oleh</th>
<th class="px-4 py-3 font-semibold">Status</th>
<th class="px-4 py-3 font-semibold">Diambil Oleh</th>
<th class="px-4 py-3 font-semibold">Aksi</th>
</tr>
</thead>
<tbody class="divide-y divide-[#F1F5F9]">
@forelse ($penawaran as $index => $item)
<tr>
<td class="px-4 py-4 text-[#374151]">{{ $index + 1 }}</td>
<td class="px-4 py-4 align-top">
<p class="font-semibold text-[#15171A]">{{ $item['judul'] }}</p>
<p class="mt-1 text-xs text-[#6B7280]">{{ $item['waktu'] }}</p>
</td>
<td class="px-4 py-4 text-[#374151]">{{ $item['deskripsi'] }}</td>
<td class="px-4 py-4 text-[#374151]">{{ $item['ditawarkanOleh'] }}</td>
<td class="px-4 py-4 text-[#374151]">{{ $item['status'] }}</td>
<td class="px-4 py-4 text-[#374151]">{{ $item['mahasiswa'] }}</td>
<td class="px-4 py-4">
<div class="flex flex-wrap gap-2">
@if ($item['canApprove'])
<form method="POST" action="{{ $item['approveHref'] }}">
@csrf
<button type="submit" class="rounded-md border border-emerald-200 bg-emerald-50 px-3 py-1.5 text-xs font-medium text-emerald-700 hover:bg-emerald-100">Setujui</button>
</form>
<form method="POST" action="{{ $item['rejectHref'] }}">
@csrf
<button type="submit" class="rounded-md border border-amber-200 bg-amber-50 px-3 py-1.5 text-xs font-medium text-amber-700 hover:bg-amber-100">Tolak</button>
</form>
@endif
@if ($item['isMine'])
<a href="{{ $item['editHref'] }}" class="rounded-md bg-[#15171A] px-3 py-1.5 text-xs font-medium text-white hover:opacity-90">Edit</a>
<form method="POST" action="{{ $item['destroyHref'] }}" onsubmit="return confirm('Hapus data penawaran judul ini?');">
@csrf
@method('DELETE')
<button type="submit" class="rounded-md border border-rose-200 bg-rose-50 px-3 py-1.5 text-xs font-medium text-rose-700 hover:bg-rose-100">Hapus</button>
</form>
@endif
</div>
</td>
</tr>
@empty
<tr>
<td colspan="7" class="px-4 py-8 text-center text-[#6B7280]">Mengambil Data . . .</td>
</tr>
@endforelse
</tbody>
</table>
</div>
</section>
</x-dosen.partials.page-shell>

View File

@@ -0,0 +1,10 @@
<x-dosen.partials.page-shell :title="$title" :sidebar="$sidebar" :page-title="$pageTitle" :page-description="$pageDescription" :page-date="$pageDate" :user="$user">
<section class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<h2 class="text-2xl font-semibold text-[#15171A]">{{ $pengumumanItem->judul }}</h2>
<p class="mt-2 text-sm text-[#6B7280]">Diposting {{ \Carbon\Carbon::parse($pengumumanItem->tgl)->locale('id')->translatedFormat('j F Y, H:i') }}</p>
<div class="prose mt-6 max-w-none text-[#374151]">{!! $pengumumanItem->isi !!}</div>
<div class="mt-6">
<a href="{{ route('dosen.pengumuman.index') }}" class="inline-flex items-center rounded-md border border-[#D1D5DB] bg-white px-4 py-2.5 text-sm font-medium text-[#15171A] hover:bg-[#F9FAFB]">Kembali</a>
</div>
</section>
</x-dosen.partials.page-shell>

View File

@@ -0,0 +1,17 @@
<x-dosen.partials.page-shell :title="$title" :sidebar="$sidebar" :page-title="$pageTitle" :page-description="$pageDescription" :page-date="$pageDate" :user="$user">
<section class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<div class="space-y-4">
@forelse ($pengumuman as $item)
<article class="rounded-xl border border-[#E5E7EB] bg-[#F9FAFB] p-5">
<a href="{{ $item['detailHref'] }}" class="text-lg font-semibold text-[#15171A] hover:text-[#625DF5]">{{ $item['judul'] }}</a>
<p class="mt-2 text-sm text-[#6B7280]">{{ \Carbon\Carbon::parse($item['tgl'])->locale('id')->translatedFormat('j F Y, H:i') }}</p>
<div class="mt-4 flex flex-wrap gap-2">
<a href="{{ $item['detailHref'] }}" class="rounded-md bg-[#15171A] px-3 py-2 text-xs font-medium text-white hover:opacity-90">Lihat Detail</a>
</div>
</article>
@empty
<div class="rounded-xl border border-dashed border-[#D1D5DB] bg-[#F9FAFB] p-6 text-center text-[#6B7280]">Belum ada pengumuman.</div>
@endforelse
</div>
</section>
</x-dosen.partials.page-shell>

View File

@@ -0,0 +1,12 @@
<x-dosen.partials.page-shell :title="$title" :sidebar="$sidebar" :page-title="$pageTitle" :page-description="$pageDescription" :page-date="$pageDate" :user="$user">
<section class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<h3 class="text-xl font-semibold text-[#15171A]">Integrasi Pra LIRS</h3>
<p class="mt-4 max-w-[820px] text-sm leading-7 text-[#4B5563]">Modul lama mengambil data Pra LIRS dari layanan eksternal Informatika. Untuk tahap overhaul ini, jalur modul dikembalikan sebagai halaman rebuild dan sumber integrasinya dipertahankan sama agar perilaku existing tidak berubah mendadak.</p>
<div class="mt-6 rounded-xl border border-[#E5E7EB] bg-[#F9FAFB] p-5 text-sm text-[#374151]">
Endpoint sumber: <span class="font-mono text-[13px]">{{ $externalUrl }}</span>
</div>
<div class="mt-6">
<a href="https://informatika.untan.ac.id/konsultasi/" target="_blank" rel="noreferrer" class="inline-flex items-center rounded-md bg-[#15171A] px-4 py-2.5 text-sm font-medium text-white hover:opacity-90">Buka Layanan Terkait</a>
</div>
</section>
</x-dosen.partials.page-shell>

View File

@@ -0,0 +1,65 @@
<x-dosen.partials.page-shell :title="$title" :sidebar="$sidebar" :page-title="$pageTitle" :page-description="$pageDescription" :page-date="$pageDate" :user="$user">
<section class="grid gap-5 lg:grid-cols-[minmax(0,1.2fr)_minmax(320px,0.8fr)]">
<article class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<h3 class="text-xl font-semibold text-[#15171A]">Edit Profil</h3>
<form method="POST" action="{{ route('dosen.profile.update', [], false) }}" class="mt-5 space-y-5">
@csrf
@method('PUT')
<div class="grid gap-5 md:grid-cols-2">
<label class="block text-sm text-[#374151]">
<span class="mb-2 block font-medium text-[#15171A]">NIP</span>
<input type="text" value="{{ $profile->nip ?? '-' }}" class="template-input bg-[#F9FAFB]" readonly>
</label>
<label class="block text-sm text-[#374151]">
<span class="mb-2 block font-medium text-[#15171A]">Nama Lengkap</span>
<input type="text" name="nmLengkap" value="{{ old('nmLengkap', $profile->nmLengkap ?? '') }}" class="template-input @error('nmLengkap') border-rose-300 ring-rose-100 @enderror" required>
@error('nmLengkap')<p class="mt-2 text-xs text-rose-600">{{ $message }}</p>@enderror
</label>
<label class="block text-sm text-[#374151]">
<span class="mb-2 block font-medium text-[#15171A]">Email</span>
<input type="email" name="email" value="{{ old('email', $profile->email ?? '') }}" class="template-input @error('email') border-rose-300 ring-rose-100 @enderror">
@error('email')<p class="mt-2 text-xs text-rose-600">{{ $message }}</p>@enderror
</label>
<label class="block text-sm text-[#374151]">
<span class="mb-2 block font-medium text-[#15171A]">No Telp/HP</span>
<input type="text" name="nohp" value="{{ old('nohp', $profile->nohp ?? '') }}" class="template-input @error('nohp') border-rose-300 ring-rose-100 @enderror">
@error('nohp')<p class="mt-2 text-xs text-rose-600">{{ $message }}</p>@enderror
</label>
<label class="block text-sm text-[#374151]">
<span class="mb-2 block font-medium text-[#15171A]">Password Baru</span>
<input type="password" name="password" class="template-input @error('password') border-rose-300 ring-rose-100 @enderror" placeholder="Kosongkan jika tidak diubah">
@error('password')<p class="mt-2 text-xs text-rose-600">{{ $message }}</p>@enderror
</label>
<label class="block text-sm text-[#374151]">
<span class="mb-2 block font-medium text-[#15171A]">Konfirmasi Password</span>
<input type="password" name="password_again" class="template-input @error('password_again') border-rose-300 ring-rose-100 @enderror" placeholder="Ulangi password baru">
@error('password_again')<p class="mt-2 text-xs text-rose-600">{{ $message }}</p>@enderror
</label>
</div>
<div class="flex flex-wrap gap-3 border-t border-[#E5E7EB] pt-5">
<button type="submit" class="rounded-md bg-[#15171A] px-4 py-2.5 text-sm font-medium text-white hover:opacity-90">Simpan Perubahan</button>
</div>
</form>
</article>
<article class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<h3 class="text-xl font-semibold text-[#15171A]">Ringkasan Akun</h3>
<div class="mt-5 space-y-4 text-sm text-[#374151]">
<div><span class="font-semibold text-[#15171A]">NIP:</span> {{ $profile->nip ?? '-' }}</div>
<div><span class="font-semibold text-[#15171A]">Jenis Dosen:</span> {{ ($profile->jenis ?? 'D') === 'K' ? 'Ketua Program Studi' : 'Dosen' }}</div>
<div><span class="font-semibold text-[#15171A]">Status Akun:</span> {{ ($profile->status ?? 'N') === 'A' ? 'Aktif' : 'Nonaktif' }}</div>
<div><span class="font-semibold text-[#15171A]">Jabatan:</span> {{ $profile->jabatan ?: '-' }}</div>
</div>
<div class="mt-6 rounded-xl border border-[#E5E7EB] bg-[#F9FAFB] p-4 text-sm leading-7 text-[#4B5563]">
Perubahan foto profil belum dipindahkan ke rebuild. Saat ini yang sudah aktif native adalah pembaruan nama lengkap, email, nomor HP, dan password.
</div>
</article>
</section>
</x-dosen.partials.page-shell>

View File

@@ -0,0 +1,59 @@
<x-dosen.partials.page-shell :title="$title" :sidebar="$sidebar" :page-title="$pageTitle" :page-description="$pageDescription" :page-date="$pageDate" :user="$user" :page-actions="$pageActions ?? []">
<section class="space-y-5">
<article class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<div class="flex flex-col gap-4 lg:flex-row lg:items-start lg:justify-between">
<div class="min-w-0 flex-1">
<h2 class="break-words text-[22px] font-semibold leading-8 text-[#15171A]">{{ $outline['judul'] }}</h2>
<p class="mt-3 text-sm text-[#4B5563]">{{ $outline['mahasiswa'] }}</p>
<div class="mt-3 flex flex-wrap gap-3 text-sm text-[#6B7280]">
<span>{{ $outline['periode'] }}</span>
<span>{{ $outline['tanggal'] }}</span>
<span>KK: {{ $outline['kk'] }}</span>
</div>
</div>
<div class="shrink-0 rounded-full bg-[#F9FAFB] px-3 py-1 text-xs font-semibold text-[#15171A]">
{{ $outline['status'] }}
</div>
</div>
<div class="mt-5 rounded-xl border border-[#E5E7EB] bg-[#F9FAFB] p-4 text-sm leading-7 text-[#374151]">
{!! $outline['deskripsi'] ?: '<span class="text-[#6B7280]">Tidak ada deskripsi.</span>' !!}
</div>
</article>
<section id="post_review" class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<div class="flex items-center justify-between gap-3">
<div>
<p class="text-sm font-semibold uppercase tracking-[0.16em] text-[#979797]">Diskusi</p>
<h3 class="mt-2 text-xl font-semibold text-[#15171A]">Riwayat Review</h3>
</div>
<span class="rounded-full border border-[#E5E7EB] bg-[#F9FAFB] px-3 py-1 text-xs font-semibold text-[#4B5563]">{{ count($reviews) }} entri</span>
</div>
<div class="mt-5 space-y-4">
@forelse ($reviews as $review)
<article class="rounded-xl border border-[#E5E7EB] bg-[#F9FAFB] p-5">
<div class="flex flex-col gap-3 sm:flex-row sm:items-start sm:justify-between">
<div>
<div class="flex flex-wrap items-center gap-2">
<p class="font-semibold text-[#15171A]">{{ $review['author'] }}</p>
<span class="rounded-full bg-white px-2.5 py-1 text-[11px] font-semibold text-[#4B5563]">{{ $review['role'] }}</span>
<span class="rounded-full px-2.5 py-1 text-[11px] font-semibold {{ $review['type'] === 'Putusan' ? 'bg-amber-100 text-amber-800' : 'bg-slate-100 text-slate-700' }}">{{ $review['type'] }}</span>
@if ($review['decision'])
<span class="rounded-full px-2.5 py-1 text-[11px] font-semibold {{ $review['decision'] === 'Setuju' ? 'bg-emerald-100 text-emerald-700' : 'bg-rose-100 text-rose-700' }}">{{ $review['decision'] }}</span>
@endif
</div>
<p class="mt-2 text-xs text-[#6B7280]">{{ $review['timestamp'] }}</p>
</div>
</div>
<div class="prose prose-sm mt-4 max-w-none text-[#374151] prose-p:leading-7">
{!! $review['body'] !!}
</div>
</article>
@empty
<div class="rounded-xl border border-dashed border-[#D1D5DB] bg-[#F9FAFB] p-6 text-center text-[#6B7280]">Belum ada review untuk usulan ini.</div>
@endforelse
</div>
</section>
</section>
</x-dosen.partials.page-shell>

View File

@@ -0,0 +1,36 @@
<x-dosen.partials.page-shell :title="$title" :sidebar="$sidebar" :page-title="$pageTitle" :page-description="$pageDescription" :page-date="$pageDate" :user="$user">
<section class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<div class="overflow-x-auto">
<table class="min-w-[1100px] divide-y divide-[#E5E7EB] text-sm">
<thead>
<tr class="text-left text-[#6B7280]">
<th class="w-[220px] px-4 py-3 font-semibold">Mahasiswa</th>
<th class="w-[420px] px-4 py-3 font-semibold">Judul Usulan</th>
<th class="w-[160px] px-4 py-3 font-semibold">Periode</th>
<th class="w-[180px] px-4 py-3 font-semibold">Tanggal</th>
<th class="w-[140px] px-4 py-3 font-semibold">Status</th>
<th class="w-[140px] px-4 py-3 font-semibold">Aksi</th>
</tr>
</thead>
<tbody class="divide-y divide-[#F1F5F9]">
@forelse ($reviews as $item)
<tr class="align-top">
<td class="px-4 py-4 text-[#374151]">{{ $item['mahasiswa'] }}</td>
<td class="px-4 py-4 font-medium leading-6 text-[#15171A]">{{ $item['judul'] }}</td>
<td class="px-4 py-4 text-[#374151]">{{ $item['periode'] }}</td>
<td class="px-4 py-4 text-[#374151]">{{ $item['tanggal'] }}</td>
<td class="px-4 py-4 text-[#374151]">{{ $item['status'] }}</td>
<td class="whitespace-nowrap px-4 py-4">
<a href="{{ $item['reviewHref'] }}" class="inline-flex rounded-md border border-[#D1D5DB] bg-white px-3 py-1.5 text-xs font-medium text-[#15171A] hover:bg-[#F9FAFB]">Lihat Review</a>
</td>
</tr>
@empty
<tr>
<td colspan="6" class="px-4 py-8 text-center text-[#6B7280]">Belum ada data review.</td>
</tr>
@endforelse
</tbody>
</table>
</div>
</section>
</x-dosen.partials.page-shell>

View File

@@ -0,0 +1,43 @@
<x-dosen.partials.page-shell :title="$title" :sidebar="$sidebar" :page-title="$pageTitle" :page-description="$pageDescription" :page-date="$pageDate" :user="$user">
<section class="grid gap-5 xl:grid-cols-2">
<article class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<h3 class="text-xl font-semibold text-[#15171A]">Statistik Draft Praoutline</h3>
<div class="mt-5 overflow-x-auto">
<table class="min-w-full divide-y divide-[#E5E7EB] text-sm">
<thead>
<tr class="text-left text-[#6B7280]">
<th class="px-4 py-3 font-semibold">Semester</th>
<th class="px-4 py-3 font-semibold">Proses</th>
<th class="px-4 py-3 font-semibold">Disetujui</th>
<th class="px-4 py-3 font-semibold">Ditolak</th>
<th class="px-4 py-3 font-semibold">Gugur</th>
<th class="px-4 py-3 font-semibold">Total</th>
</tr>
</thead>
<tbody class="divide-y divide-[#F1F5F9]">
@foreach ($draftStats as $item)
<tr>
<td class="px-4 py-4">{{ $item->semester }}</td>
<td class="px-4 py-4">{{ $item->proses }}</td>
<td class="px-4 py-4">{{ $item->terima }}</td>
<td class="px-4 py-4">{{ $item->tolak }}</td>
<td class="px-4 py-4">{{ $item->gugur }}</td>
<td class="px-4 py-4">{{ $item->totaldraft }}</td>
</tr>
@endforeach
</tbody>
</table>
</div>
</article>
<article class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<h3 class="text-xl font-semibold text-[#15171A]">Statistik Dosen</h3>
<div class="mt-5 grid gap-4 sm:grid-cols-2">
<div class="metric-card"><p class="text-sm text-[#6B7280]">Pembimbing 1</p><p class="mt-2 text-3xl font-bold text-[#15171A]">{{ $dosenStats->pemb1 ?? 0 }}</p></div>
<div class="metric-card"><p class="text-sm text-[#6B7280]">Pembimbing 2</p><p class="mt-2 text-3xl font-bold text-[#15171A]">{{ $dosenStats->pemb2 ?? 0 }}</p></div>
<div class="metric-card"><p class="text-sm text-[#6B7280]">Penguji 1</p><p class="mt-2 text-3xl font-bold text-[#15171A]">{{ $dosenStats->peng1 ?? 0 }}</p></div>
<div class="metric-card"><p class="text-sm text-[#6B7280]">Penguji 2</p><p class="mt-2 text-3xl font-bold text-[#15171A]">{{ $dosenStats->peng2 ?? 0 }}</p></div>
</div>
</article>
</section>
</x-dosen.partials.page-shell>

View File

@@ -0,0 +1,63 @@
<x-layouts.app :title="$title">
<main class="overflow-hidden bg-[#F5F7FB] pt-20">
<section class="relative border-b border-slate-200 bg-white">
<div class="absolute inset-x-0 top-0 h-56 bg-gradient-to-br from-[#0F5132] via-[#146C43] to-[#198754]"></div>
<div class="relative mx-auto max-w-[1180px] px-4 pb-12 pt-10 sm:px-6 lg:pb-16 lg:pt-14 xl:px-0">
<div class="grid gap-6 lg:grid-cols-[minmax(0,1fr)_380px] lg:items-stretch">
<div class="rounded-[28px] border border-white/30 bg-white p-6 shadow-[0_24px_70px_rgba(15,23,42,0.14)] sm:p-8 lg:p-10">
<div class="inline-flex items-center gap-2 rounded-full border border-emerald-100 bg-emerald-50 px-3 py-1 text-xs font-semibold uppercase tracking-[0.18em] text-emerald-800">
Teknik Informatika UNTAN
</div>
<h1 class="mt-6 max-w-3xl text-[34px] font-black leading-[1.05] tracking-[-0.04em] text-slate-950 sm:text-[48px] lg:text-[64px]">
SPOTA untuk pengajuan, review, dan monitoring tugas akhir.
</h1>
<p class="mt-6 max-w-2xl text-base leading-8 text-slate-600 sm:text-lg">
SPOTA membantu mahasiswa mengajukan outline tugas akhir, memantau status persetujuan, melihat jadwal seminar atau sidang, serta menerima pengumuman akademik. Dosen dan admin dapat meninjau usulan, mengelola penawaran judul, dan memantau proses tugas akhir dalam satu sistem.
</p>
<div class="mt-8 flex flex-col gap-3 sm:flex-row">
<a href="{{ route('legacy.login', 'mahasiswa') }}" class="inline-flex items-center justify-center rounded-2xl bg-slate-950 px-6 py-3.5 text-sm font-bold text-white shadow-lg shadow-slate-950/15 transition hover:-translate-y-0.5 hover:bg-slate-800">
Masuk Mahasiswa
</a>
<a href="{{ route('legacy.login', 'dosen') }}" class="inline-flex items-center justify-center rounded-2xl border border-slate-200 bg-white px-6 py-3.5 text-sm font-bold text-slate-950 transition hover:-translate-y-0.5 hover:border-emerald-300 hover:text-emerald-800">
Masuk Dosen
</a>
<a href="{{ route('legacy.login', 'admin') }}" class="inline-flex items-center justify-center rounded-2xl border border-slate-200 bg-slate-50 px-6 py-3.5 text-sm font-bold text-slate-700 transition hover:-translate-y-0.5 hover:bg-white hover:text-slate-950">
Admin Prodi
</a>
</div>
</div>
<aside class="rounded-[28px] border border-white/30 bg-slate-950 p-6 text-white shadow-[0_24px_70px_rgba(15,23,42,0.22)] sm:p-8">
<p class="text-xs font-semibold uppercase tracking-[0.2em] text-emerald-300">Status Rebuild</p>
<div class="mt-6 space-y-4">
@foreach ($systemStatus as $status)
<div class="rounded-2xl border border-white/10 bg-white/[0.06] p-4">
<p class="text-xs font-semibold uppercase tracking-[0.16em] text-white/45">{{ $status['label'] }}</p>
<p class="mt-2 text-lg font-bold text-white">{{ $status['value'] }}</p>
</div>
@endforeach
</div>
<div class="mt-6 rounded-2xl bg-emerald-400 p-5 text-slate-950">
<p class="text-sm font-black uppercase tracking-[0.16em]">Akses aktif</p>
<p class="mt-3 text-sm leading-7 font-medium">Login mahasiswa, dosen, dan admin sudah memakai akun dari database SPOTA.</p>
</div>
</aside>
</div>
</div>
</section>
<section class="mx-auto max-w-[1180px] px-4 py-10 sm:px-6 lg:py-14 xl:px-0">
<div class="grid gap-4 md:grid-cols-3">
@foreach ($highlights as $item)
<a href="{{ $item['href'] }}" class="group rounded-[24px] border border-slate-200 bg-white p-6 shadow-[0_14px_40px_rgba(15,23,42,0.06)] transition hover:-translate-y-1 hover:border-emerald-200 hover:shadow-[0_20px_50px_rgba(15,23,42,0.1)]">
<div class="flex h-12 w-12 items-center justify-center rounded-2xl bg-emerald-50 text-lg font-black text-emerald-700">{{ $item['number'] }}</div>
<h2 class="mt-5 text-xl font-black tracking-[-0.02em] text-slate-950">{{ $item['label'] }}</h2>
<p class="mt-3 text-sm leading-7 text-slate-600">{{ $item['description'] }}</p>
<p class="mt-5 text-sm font-bold text-emerald-700 group-hover:text-emerald-900">Buka portal</p>
</a>
@endforeach
</div>
</section>
</main>
</x-layouts.app>

View File

@@ -0,0 +1,22 @@
<x-mahasiswa.partials.page-shell :title="$title" :sidebar="$sidebar" :page-title="$pageTitle" :page-description="$pageDescription" :page-date="$pageDate" :user="$user" :page-actions="$pageActions ?? []">
<article class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<div class="flex flex-col gap-4 lg:flex-row lg:items-start lg:justify-between">
<div class="min-w-0 flex-1">
<h2 class="break-words text-[24px] font-semibold leading-8 text-[#15171A]">{{ $penawaran->judul }}</h2>
<div class="mt-3 flex flex-wrap gap-3 text-sm text-[#6B7280]">
<span>Ditawarkan oleh: {{ $penawaran->dosen ?: '-' }}</span>
<span>KK: {{ $penawaran->kk ?: '-' }}</span>
<span>{{ $penawaran->waktuInput ? \Carbon\Carbon::parse($penawaran->waktuInput)->locale('id')->translatedFormat('j F Y, H:i') : '-' }}</span>
</div>
</div>
<form method="POST" action="{{ route('mahasiswa.penawaran.book', ['id' => $penawaran->idPenawaran]) }}" class="shrink-0">
@csrf
<button type="submit" class="rounded-md bg-[#15171A] px-5 py-2.5 text-sm font-medium text-white hover:opacity-90">Booking Judul Ini</button>
</form>
</div>
<div class="prose prose-sm mt-6 max-w-none rounded-xl border border-[#E5E7EB] bg-[#F9FAFB] p-5 text-[#374151] prose-p:leading-7">
{!! $penawaran->deskripsi ?: '<p>Tidak ada deskripsi.</p>' !!}
</div>
</article>
</x-mahasiswa.partials.page-shell>

View File

@@ -0,0 +1,82 @@
<x-mahasiswa.partials.page-shell :title="$title" :sidebar="$sidebar" :page-title="$pageTitle" :page-description="$pageDescription" :page-date="$pageDate" :user="$user">
<section class="space-y-5">
<form method="GET" action="{{ route('mahasiswa.penawaran.index') }}" class="rounded-xl border border-[#E5E7EB] bg-white p-5 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<div class="grid gap-4 lg:grid-cols-[220px_minmax(0,1fr)_auto] lg:items-end">
<div>
<label class="text-sm font-semibold text-[#15171A]">Status Judul</label>
<select name="status" class="mt-2 w-full rounded-md border border-[#D1D5DB] px-4 py-3 text-sm">
<option value="0" @selected($filters['status'] === '0')>Belum Diambil</option>
<option value="1" @selected($filters['status'] === '1')>Sudah Diambil</option>
<option value="Semua" @selected($filters['status'] === 'Semua')>Semua Status</option>
</select>
</div>
<div>
<label class="text-sm font-semibold text-[#15171A]">Tampilkan</label>
<select name="kk" class="mt-2 w-full rounded-md border border-[#D1D5DB] px-4 py-3 text-sm">
<option value="Semua" @selected($filters['kk'] === 'Semua')>Semua Kelompok Keahlian</option>
@foreach ($kelompokKeahlian as $kk)
<option value="{{ $kk->idKK }}" @selected((string) $filters['kk'] === (string) $kk->idKK)>{{ $kk->namaKK }}</option>
@endforeach
</select>
</div>
<button type="submit" class="rounded-md bg-[#15171A] px-5 py-3 text-sm font-medium text-white hover:opacity-90">Filter</button>
</div>
</form>
<section class="overflow-hidden rounded-xl border border-[#E5E7EB] bg-white shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<div class="overflow-x-auto">
<table class="min-w-[980px] w-full text-left text-sm">
<thead class="bg-[#F9FAFB] text-xs uppercase tracking-[0.12em] text-[#6B7280]">
<tr>
<th class="px-4 py-3">No.</th>
<th class="px-4 py-3">Judul</th>
<th class="px-4 py-3">Ditawarkan Oleh</th>
<th class="px-4 py-3">KK</th>
<th class="px-4 py-3">Status</th>
<th class="px-4 py-3">Diambil Oleh</th>
<th class="px-4 py-3 text-right">Aksi</th>
</tr>
</thead>
<tbody class="divide-y divide-[#E5E7EB]">
@forelse ($penawaran as $item)
@php
$available = is_null($item->statusPengambilan) || $item->statusPengambilan === '2';
@endphp
<tr>
<td class="px-4 py-4 text-[#6B7280]">{{ $loop->iteration + ($penawaran->currentPage() - 1) * $penawaran->perPage() }}</td>
<td class="px-4 py-4">
<a href="{{ route('mahasiswa.penawaran.show', ['id' => $item->idPenawaran], false) }}" class="font-semibold text-[#15171A] hover:text-[#625DF5]">{{ $item->judul }}</a>
<p class="mt-1 line-clamp-2 text-xs leading-5 text-[#6B7280]">{{ str($item->deskripsi)->stripTags()->squish()->limit(120) }}</p>
</td>
<td class="px-4 py-4 text-[#374151]">{{ $item->dosen ?: '-' }}</td>
<td class="px-4 py-4 text-[#374151]">{{ $item->kk ?: '-' }}</td>
<td class="px-4 py-4">
<span class="rounded-full px-2.5 py-1 text-xs font-semibold {{ $available ? 'bg-emerald-100 text-emerald-800' : 'bg-amber-100 text-amber-800' }}">{{ $available ? 'Belum Diambil' : 'Sudah Diambil' }}</span>
</td>
<td class="px-4 py-4 text-[#374151]">{{ $item->diambil_oleh ?: '-' }}</td>
<td class="px-4 py-4">
<div class="flex justify-end gap-2 whitespace-nowrap">
<a href="{{ route('mahasiswa.penawaran.show', ['id' => $item->idPenawaran], false) }}" class="rounded-md border border-[#D1D5DB] px-3 py-2 text-xs font-medium text-[#15171A] hover:bg-[#F9FAFB]">Lihat</a>
@if ($available)
<form method="POST" action="{{ route('mahasiswa.penawaran.book', ['id' => $item->idPenawaran]) }}">
@csrf
<button type="submit" class="rounded-md bg-[#15171A] px-3 py-2 text-xs font-medium text-white hover:opacity-90">Booking</button>
</form>
@endif
</div>
</td>
</tr>
@empty
<tr>
<td colspan="7" class="px-4 py-8 text-center text-[#6B7280]">Tidak ada penawaran judul sesuai filter.</td>
</tr>
@endforelse
</tbody>
</table>
</div>
<div class="border-t border-[#E5E7EB] px-4 py-3">
{{ $penawaran->links() }}
</div>
</section>
</section>
</x-mahasiswa.partials.page-shell>

View File

@@ -0,0 +1,9 @@
<x-mahasiswa.partials.page-shell :title="$title" :sidebar="$sidebar" :page-title="$pageTitle" :page-description="$pageDescription" :page-date="$pageDate" :user="$user" :page-actions="$pageActions ?? []">
<article class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<h2 class="text-[24px] font-semibold leading-8 text-[#15171A]">{{ $pengumuman['judul'] }}</h2>
<p class="mt-3 text-sm text-[#6B7280]">{{ $pengumuman['tgl'] }}</p>
<div class="prose prose-sm mt-6 max-w-none text-[#374151] prose-p:leading-7">
{!! $pengumuman['isi'] !!}
</div>
</article>
</x-mahasiswa.partials.page-shell>

View File

@@ -0,0 +1,18 @@
<x-mahasiswa.partials.page-shell :title="$title" :sidebar="$sidebar" :page-title="$pageTitle" :page-description="$pageDescription" :page-date="$pageDate" :user="$user">
<section class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<div class="space-y-4">
@forelse ($pengumuman as $item)
<article class="rounded-xl border border-[#E5E7EB] bg-[#F9FAFB] p-5">
<a href="{{ $item['detailHref'] }}" class="text-lg font-semibold text-[#15171A] hover:text-[#625DF5]">{{ $item['judul'] }}</a>
<p class="mt-2 text-sm text-[#6B7280]">{{ \Carbon\Carbon::parse($item['tgl'])->locale('id')->translatedFormat('j F Y, H:i') }}</p>
<p class="mt-4 text-sm leading-7 text-[#4B5563]">{{ $item['preview'] }}</p>
<div class="mt-4 flex flex-wrap gap-2">
<a href="{{ $item['detailHref'] }}" class="rounded-md bg-[#15171A] px-3 py-2 text-xs font-medium text-white hover:opacity-90">Lihat Detail</a>
</div>
</article>
@empty
<div class="rounded-xl border border-dashed border-[#D1D5DB] bg-[#F9FAFB] p-6 text-center text-[#6B7280]">Belum ada pengumuman untuk mahasiswa.</div>
@endforelse
</div>
</section>
</x-mahasiswa.partials.page-shell>

View File

@@ -0,0 +1,71 @@
<x-mahasiswa.partials.page-shell :title="$title" :sidebar="$sidebar" :page-title="$pageTitle" :page-description="$pageDescription" :page-date="$pageDate" :user="$user" :page-actions="$pageActions ?? []">
<section class="space-y-5">
@if ($outline)
<article class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<div class="flex flex-col gap-4 lg:flex-row lg:items-start lg:justify-between">
<div class="min-w-0 flex-1">
<h2 class="break-words text-[22px] font-semibold leading-8 text-[#15171A]">{{ $outline['judul'] }}</h2>
<div class="mt-3 flex flex-wrap gap-3 text-sm text-[#6B7280]">
<span>Draft #{{ $outline['id'] }}</span>
<span>{{ $outline['tanggal'] }}</span>
<span>KK: {{ $outline['kelompokKeahlian'] }}</span>
</div>
</div>
<div class="shrink-0 rounded-full px-3 py-1 text-xs font-semibold {{ $outline['statusClass'] }}">
{{ $outline['status'] }}
</div>
</div>
<div class="mt-5 rounded-xl border border-[#E5E7EB] bg-[#F9FAFB] p-4 text-sm leading-7 text-[#374151]">
{!! $outline['deskripsi'] ?: '<span class="text-[#6B7280]">Tidak ada deskripsi usulan.</span>' !!}
</div>
@if ($outline['catatan'])
<div class="mt-5 rounded-xl border border-amber-200 bg-amber-50 p-4 text-sm leading-7 text-amber-900">
<p class="font-semibold">Catatan Putusan</p>
<p class="mt-2">{{ $outline['catatan'] }}</p>
</div>
@endif
</article>
<section class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<div class="flex items-center justify-between gap-3">
<div>
<p class="text-sm font-semibold uppercase tracking-[0.16em] text-[#979797]">Diskusi</p>
<h3 class="mt-2 text-xl font-semibold text-[#15171A]">Riwayat Review</h3>
</div>
<span class="rounded-full border border-[#E5E7EB] bg-[#F9FAFB] px-3 py-1 text-xs font-semibold text-[#4B5563]">{{ count($reviews) }} entri</span>
</div>
<div class="mt-5 space-y-4">
@forelse ($reviews as $review)
<article class="rounded-xl border border-[#E5E7EB] bg-[#F9FAFB] p-5">
<div class="flex flex-col gap-3 sm:flex-row sm:items-start sm:justify-between">
<div>
<div class="flex flex-wrap items-center gap-2">
<p class="font-semibold text-[#15171A]">{{ $review['author'] }}</p>
<span class="rounded-full bg-white px-2.5 py-1 text-[11px] font-semibold text-[#4B5563]">{{ $review['role'] }}</span>
<span class="rounded-full bg-white px-2.5 py-1 text-[11px] font-semibold text-[#4B5563]">{{ $review['type'] }}</span>
@if ($review['decision'])
<span class="rounded-full px-2.5 py-1 text-[11px] font-semibold {{ $review['decision'] === 'Setuju' ? 'bg-emerald-100 text-emerald-700' : 'bg-rose-100 text-rose-700' }}">{{ $review['decision'] }}</span>
@endif
</div>
<p class="mt-2 text-xs text-[#6B7280]">{{ $review['timestamp'] }}</p>
</div>
</div>
<div class="prose prose-sm mt-4 max-w-none text-[#374151] prose-p:leading-7">
{!! $review['body'] !!}
</div>
</article>
@empty
<div class="rounded-xl border border-dashed border-[#D1D5DB] bg-[#F9FAFB] p-6 text-center text-[#6B7280]">Belum ada review untuk usulan terbaru.</div>
@endforelse
</div>
</section>
@else
<div class="rounded-xl border border-dashed border-[#D1D5DB] bg-white p-8 text-center text-[#6B7280] shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
Belum ada draft praoutline yang tercatat untuk akun mahasiswa ini.
</div>
@endif
</section>
</x-mahasiswa.partials.page-shell>

View File

@@ -0,0 +1,89 @@
<x-mahasiswa.partials.page-shell :title="$title" :sidebar="$sidebar" :page-title="$pageTitle" :page-description="$pageDescription" :page-date="$pageDate" :user="$user">
@if ($hasActiveDraft)
<section class="rounded-xl border border-sky-200 bg-sky-50 p-6 text-sky-900 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
<h2 class="text-xl font-semibold">Draft Praoutline Anda Telah Diupload</h2>
<p class="mt-3 text-sm leading-7">Anda masih memiliki draft aktif. Silakan lihat status usulan dan riwayat review sebelum mengajukan draft baru.</p>
<div class="mt-5">
<a href="{{ route('mahasiswa.status-usulan', [], false) }}" class="inline-flex rounded-md bg-sky-600 px-4 py-2.5 text-sm font-medium text-white hover:opacity-90">Lihat Review</a>
</div>
</section>
@else
<section class="space-y-5">
<div class="rounded-xl border border-amber-200 bg-amber-50 p-5 text-sm leading-7 text-amber-900">
<p class="font-semibold">Perhatian</p>
<p class="mt-2">Pastikan file yang diupload berupa PDF dan draft sudah diperiksa. Jika terdapat kesalahan upload, hubungi administrator prodi.</p>
</div>
<form method="POST" action="{{ route('mahasiswa.praoutline.store') }}" enctype="multipart/form-data" class="rounded-xl border border-[#E5E7EB] bg-white p-6 shadow-[0_8px_12px_rgba(13,10,44,0.04)]">
@csrf
<div class="grid gap-5">
<div>
<label class="text-sm font-semibold text-[#15171A]">Judul Skripsi</label>
<input type="text" name="judul" value="{{ old('judul') }}" class="mt-2 w-full rounded-md border border-[#D1D5DB] px-4 py-3 text-sm focus:border-[#625DF5] focus:outline-none" required>
</div>
<div>
<label class="text-sm font-semibold text-[#15171A]">Deskripsi</label>
<textarea name="deskripsi" rows="7" class="mt-2 w-full rounded-md border border-[#D1D5DB] px-4 py-3 text-sm focus:border-[#625DF5] focus:outline-none">{{ old('deskripsi') }}</textarea>
</div>
<div class="grid gap-5 lg:grid-cols-2">
<div>
<label class="text-sm font-semibold text-[#15171A]">Berkas PDF</label>
<input type="file" name="berkas" accept="application/pdf" class="mt-2 w-full rounded-md border border-[#D1D5DB] px-4 py-3 text-sm" required>
</div>
<div>
<label class="text-sm font-semibold text-[#15171A]">Kelompok Keahlian Tujuan</label>
<select name="kelompokKeahlian" class="mt-2 w-full rounded-md border border-[#D1D5DB] px-4 py-3 text-sm focus:border-[#625DF5] focus:outline-none" required>
<option value="">Pilih Kelompok Keahlian</option>
@foreach ($kelompokKeahlian as $kk)
<option value="{{ $kk->idKK }}" @selected(old('kelompokKeahlian') == $kk->idKK)>{{ $kk->namaKK }}</option>
@endforeach
</select>
</div>
</div>
<div class="grid gap-5 lg:grid-cols-2">
<div>
<label class="text-sm font-semibold text-[#15171A]">Dosen Pembimbing Akademik (PA)</label>
<select name="dosenpa" class="mt-2 w-full rounded-md border border-[#D1D5DB] px-4 py-3 text-sm focus:border-[#625DF5] focus:outline-none" required>
<option value="">Pilih Dosen</option>
@foreach ($dosen as $item)
<option value="{{ $item->nmLengkap }}" @selected(old('dosenpa') === $item->nmLengkap)>{{ $item->nmLengkap }}</option>
@endforeach
</select>
</div>
<div>
<label class="text-sm font-semibold text-[#15171A]">Dosen Yang Merekomendasikan Judul</label>
<select name="drekomjudul" class="mt-2 w-full rounded-md border border-[#D1D5DB] px-4 py-3 text-sm focus:border-[#625DF5] focus:outline-none">
<option value="">Pilih Dosen</option>
@foreach ($dosen as $item)
<option value="{{ $item->nmLengkap }}" @selected(old('drekomjudul') === $item->nmLengkap)>{{ $item->nmLengkap }}</option>
@endforeach
</select>
</div>
</div>
<div>
<p class="text-sm font-semibold text-[#15171A]">Pilihan Dosen Pembimbing</p>
<div class="mt-2 grid gap-3 lg:grid-cols-2">
@for ($i = 1; $i <= 4; $i++)
<select name="pilpemb{{ $i }}" class="w-full rounded-md border border-[#D1D5DB] px-4 py-3 text-sm focus:border-[#625DF5] focus:outline-none">
<option value="">Pilihan {{ $i }}</option>
@foreach ($dosen as $item)
<option value="{{ $item->nmLengkap }}" @selected(old('pilpemb'.$i) === $item->nmLengkap)>{{ $item->nmLengkap }}</option>
@endforeach
</select>
@endfor
</div>
</div>
<div class="flex flex-wrap gap-3 border-t border-[#E5E7EB] pt-5">
<button type="submit" class="rounded-md bg-[#15171A] px-5 py-2.5 text-sm font-medium text-white hover:opacity-90">Upload Draft</button>
<a href="{{ route('mahasiswa.status-usulan', [], false) }}" class="rounded-md border border-[#D1D5DB] bg-white px-5 py-2.5 text-sm font-medium text-[#15171A] hover:bg-[#F9FAFB]">Batal</a>
</div>
</div>
</form>
</section>
@endif
</x-mahasiswa.partials.page-shell>