Upload isi proyek skripsi

This commit is contained in:
e41220539 2026-06-12 10:31:08 +07:00
parent d39281e1bc
commit 76e932e367
180 changed files with 26804 additions and 0 deletions

172
README.md Normal file
View File

@ -0,0 +1,172 @@
# 📚 Perpus Digital - Prototipe Frontend Aplikasi Perpustakaan
Prototipe frontend untuk aplikasi **perpustakaan digital** yang ditujukan untuk siswa dan guru.
Aplikasi ini mencakup alur otentikasi (login & register) dan halaman dashboard yang komprehensif untuk menampilkan aktivitas perpustakaan.
> ⚠️ Prototipe ini **dibangun tanpa backend atau database**.
> Semua data yang ditampilkan bersifat statis (**dummy data**) yang disimulasikan melalui Laravel Service untuk keperluan demonstrasi dan pengembangan antarmuka (**UI/UX**).
---
## ✨ Fitur Utama
- [x] **Autentikasi (Login & Register)**
Sistem login siswa menggunakan **NISN** dan registrasi sederhana.
- [x] **Dashboard**
Menampilkan ringkasan aktivitas siswa/guru seperti statistik pinjaman, grafik, dan pengumuman.
- [x] **Peminjaman Buku Offline**
Simulasi peminjaman buku fisik di perpustakaan.
- [x] **Peminjaman Buku Online**
Simulasi membaca atau meminjam buku digital langsung di aplikasi.
- [x] **Riwayat Peminjaman Offline**
Daftar histori buku fisik yang pernah dipinjam.
- [x] **Riwayat Peminjaman Online**
Daftar histori buku digital yang pernah dipinjam atau dibaca.
- [ ] **Role Management**
Manajemen peran (siswa & guru) untuk akses fitur yang berbeda.
- Siswa : [x]
- Penjaga Perpus : [x]
- Guru : []
- [x] **Katalog Buku**
Daftar buku dengan informasi detail dan cover.
---
## 🛠️ Teknologi yang Digunakan
- **Framework**: Laravel 12
- **Frontend**:
- Bootstrap 5
- Sass (SCSS) untuk theming kustom
- Vite.js untuk kompilasi aset
- **Grafik (Charting)**: Chart.js
- **Ikon**: Bootstrap Icons
- **Bahasa**: PHP 8.4, JavaScript
---
## 📦 Prasyarat
Sebelum menjalankan proyek ini, pastikan sudah terinstal:
- [PHP](https://www.php.net/) **8.2+**
- [Composer](https://getcomposer.org/) (manajer paket PHP)
- [Node.js & NPM](https://nodejs.org/) (manajer paket JavaScript)
---
## 🚀 Instalasi & Cara Menjalankan
### 1. Clone atau Unduh Proyek
Jika proyek ada di repositori Git:
```bash
git clone https://github.com/zhadaarsita/skripsi-perpus-fe.git
cd skripsi-perpus-fe
````
Atau ekstrak file **ZIP** jika tidak menggunakan Git.
---
### 2. Instal Dependensi PHP
```bash
composer install
```
---
### 3. Buat File Environment
```bash
cp .env.example .env
```
---
### 4. Hasilkan Kunci Aplikasi
```bash
php artisan key:generate
```
---
### 5. Instal Dependensi Frontend
```bash
npm install
```
---
### 6. Compile Aset Frontend & Jalankan Server
**A. Development (auto-refresh browser)**
Gunakan 2 terminal terpisah:
* Terminal 1:
```bash
npm run dev
```
* Terminal 2:
```bash
php artisan serve
```
**B. Simulasi Produksi**
```bash
npm run build
php artisan serve
```
---
### 7. Buka Aplikasi
```text
http://127.0.0.1:8000
```
---
## 🔑 Informasi Login (Dummy Data)
Gunakan kredensial berikut untuk masuk sebagai siswa:
* **NISN**: `1234567890`
* **Password**: `password`
Gunakan kredensial berikut untuk masuk sebagai guru:
* **email**: `rina.marlina@smkn1perpus.sch.id`
* **Password**: `password`
Gunakan kredensial berikut untuk masuk sebagai penjaga perpus:
* **email**: `budi.santoso@smkn1perpus.sch.id`
* **Password**: `password`
---
## 📚 Belajar Laravel
Untuk dokumentasi resmi Laravel:
👉 [https://laravel.com/docs](https://laravel.com/docs)
---
# skripsi-perpus-fe
# skripsi-perpus-fe
# skripsi-perpus-fe-main

View File

@ -0,0 +1,41 @@
<?php
namespace App\Auth;
use App\Models\User;
use App\Services\DummyDataService;
use Illuminate\Contracts\Auth\Authenticatable;
use Illuminate\Contracts\Auth\UserProvider;
class DummyUserProvider implements UserProvider
{
/**
* Retrieve a user by their unique identifier.
*/
public function retrieveById($identifier)
{
$allSiswa = DummyDataService::getAllSiswa();
$userArray = collect($allSiswa)->firstWhere('id', $identifier);
if ($userArray) {
$userModel = new User();
$userArray['name'] = $userArray['nama_lengkap'];
$userModel->forceFill($userArray);
return $userModel;
}
return null;
}
/**
* Rehash the user's password if required.
*/
public function rehashPasswordIfRequired(Authenticatable $user, array $credentials, bool $force = false): void
{
}
public function retrieveByToken($identifier, $token) { return null; }
public function updateRememberToken(Authenticatable $user, $token) { }
public function retrieveByCredentials(array $credentials) { return null; }
public function validateCredentials(Authenticatable $user, array $credentials) { return false; }
}

View File

@ -0,0 +1,210 @@
<?php
namespace App\Http\Controllers\Admin;
use App\Http\Controllers\Controller;
use App\Services\DummyDataService;
use Illuminate\Http\Request;
use Carbon\Carbon;
class AdminPeminjamanController extends Controller
{
public function index(Request $request)
{
$peminjamanAktif = DummyDataService::getAdminPeminjamanAktif();
$allUsers = collect(DummyDataService::getAllSiswa());
// LOGIC DENDA & WA LINK (Update Request Client)
$peminjamanAktif = $peminjamanAktif->map(function ($item) use ($allUsers) {
$userData = $allUsers->firstWhere('id', $item['user_id']);
$role = $userData ? strtolower($userData['role']) : 'siswa';
$item['role'] = $role;
// Hitung Denda Flat 1000/hari
$tenggat = Carbon::parse($item['tenggat_kembali']);
$now = Carbon::now();
$item['hari_terlambat'] = 0;
$item['total_denda'] = 0;
$item['denda_per_hari'] = 1000;
if ($now->greaterThan($tenggat)) {
$hariTelat = $tenggat->diffInDays($now);
$item['hari_terlambat'] = $hariTelat;
if ($role === 'guru') {
$item['total_denda'] = 0;
$item['denda_per_hari'] = 0;
} else {
$item['total_denda'] = $hariTelat * 1000;
}
}
// Generate WA Link
$hp = $item['nomor_hp'];
if (substr($hp, 0, 1) == '0') {
$hp = '62' . substr($hp, 1);
}
// Pesan WA dibedakan antara Guru dan Siswa
if ($role === 'guru') {
$pesan = "Halo Bapak/Ibu {$item['peminjam']}, buku yang dipinjam sudah melewati tenggat waktu {$item['hari_terlambat']} hari. Mohon berkenan untuk segera dikembalikan ke perpustakaan ya.";
} else {
$pesan = "Halo kak {$item['peminjam']}, buku anda sudah terlambat {$item['hari_terlambat']} hari dengan denda Rp " . number_format($item['total_denda'], 0, ',', '.') . ". Mohon segera dikembalikan ya.";
}
$item['wa_link'] = "https://wa.me/{$hp}?text=" . urlencode($pesan);
return $item;
});
$daftarPeminjam = $peminjamanAktif->pluck('peminjam')->unique();
return view('admin.peminjaman.index', [
'pageTitle' => 'Manajemen Peminjaman',
'peminjamanAktif' => $peminjamanAktif,
'daftarPeminjam' => $daftarPeminjam,
]);
}
public function create()
{
$allUsers = collect(DummyDataService::getAllSiswa());
$peminjamanAktif = DummyDataService::getAdminPeminjamanAktif();
$groupedUsers = $allUsers
->whereIn('role', ['siswa', 'guru'])
->map(function ($user) use ($peminjamanAktif) {
// Hitung berapa buku yang sedang dipinjam
$jumlahPinjam = $peminjamanAktif->where('peminjam', $user['nama_lengkap'])->count();
$user['jumlah_pinjam'] = $jumlahPinjam;
if (strtolower($user['role']) === 'siswa') {
$user['kena_limit'] = $jumlahPinjam >= 2;
} else {
$user['kena_limit'] = false;
}
// Cek apakah user di-banned (Nonaktif Manual)
$user['is_banned'] = $user['is_banned'] ?? false;
$user['disabled'] = $user['kena_limit'] || $user['is_banned'];
if ($user['is_banned']) {
$user['status_text'] = "(Akun Dibekukan)";
} elseif ($user['kena_limit']) {
$user['status_text'] = "(Limit Penuh: 2/2)";
} else {
$user['status_text'] = "";
}
$user['jabatan'] = $user['jabatan'] ?? 'Guru Mata Pelajaran';
return $user;
})
->groupBy('role');
$daftarBuku = DummyDataService::getAllBooks()
->where('status', 'Tersedia')
->filter(function ($buku) {
if (is_array($buku['tipe_akses'])) {
return in_array('offline', $buku['tipe_akses']);
}
return $buku['tipe_akses'] === 'offline';
});
return view('admin.peminjaman.create', [
'pageTitle' => 'Buat Peminjaman Manual',
'groupedUsers' => $groupedUsers,
'daftarBuku' => $daftarBuku,
]);
}
/**
* Menampilkan halaman KHUSUS Manajemen Denda (Siswa & Guru Telat).
*/
public function dendaIndex()
{
$allData = DummyDataService::getAdminPeminjamanAktif();
$allSiswaRaw = collect(DummyDataService::getAllSiswa());
$now = \Carbon\Carbon::now();
// LOGIC AUTO-BAN
$allSiswa = $allSiswaRaw->map(function ($siswa) use ($allData, $now) {
$pinjamanUser = $allData->firstWhere('user_id', $siswa['id']);
$isTelat = false;
if ($pinjamanUser) {
$isTelat = $pinjamanUser['tenggat_kembali']->startOfDay()->lt($now->startOfDay());
}
if ($siswa['role'] === 'siswa' && $isTelat) {
$siswa['is_banned'] = true;
}
return $siswa;
});
$siswaTelat = $allData->filter(function ($item) use ($now, $allSiswa) {
$userData = $allSiswa->firstWhere('id', $item['user_id']);
if (!$userData) return false;
$isTelat = $item['tenggat_kembali']->startOfDay()->lt($now->startOfDay());
$isBanned = $userData['is_banned'];
$isTargetRole = in_array($userData['role'], ['siswa', 'guru']);
return ($isTelat || $isBanned) && $isTargetRole;
})->map(function ($item) use ($now, $allSiswa) {
$tenggat = $item['tenggat_kembali']->startOfDay();
$hariTelat = ($tenggat->lt($now->startOfDay())) ? $tenggat->diffInDays($now->startOfDay()) : 0;
$dataSiswa = $allSiswa->firstWhere('id', $item['user_id']);
$role = $dataSiswa ? strtolower($dataSiswa['role']) : 'siswa';
$item['role'] = $role;
if ($role === 'guru') {
$item['total_denda'] = 0;
} else {
$item['total_denda'] = $hariTelat * $item['denda_per_hari'];
}
$item['hari_terlambat'] = $hariTelat;
$item['is_banned'] = $dataSiswa['is_banned'] ?? false;
$item['kelas'] = $dataSiswa['kelas'] ?? 'Guru';
// Link WA
$hp = $item['nomor_hp'];
if (substr($hp, 0, 1) == '0') $hp = '62' . substr($hp, 1);
if ($hariTelat > 0 && $role !== 'guru') {
$pesan = "Halo {$item['peminjam']}, anda terlambat pengembalian buku. Total Denda: Rp " . number_format($item['total_denda'], 0, ',', '.');
} elseif ($hariTelat > 0 && $role === 'guru') {
$pesan = "Halo Bapak/Ibu {$item['peminjam']}, mohon berkenan untuk mengembalikan buku yang telah melewati tenggat waktu.";
} else {
$pesan = "Halo {$item['peminjam']}, akun anda sedang dinonaktifkan sementara. Mohon hubungi petugas.";
}
$item['wa_link'] = "https://wa.me/{$hp}?text=" . urlencode($pesan);
return $item;
});
$listKelas = $siswaTelat->pluck('kelas')->unique()->values();
return view('admin.denda.index', [
'pageTitle' => 'Manajemen Denda & Sanksi',
'siswaTelat' => $siswaTelat,
'listKelas' => $listKelas
]);
}
/**
* Dummy function untuk tombol Sanksi
*/
public function berikanSanksi(Request $request)
{
return response()->json(['status' => 'success']);
}
}

View File

@ -0,0 +1,52 @@
<?php
namespace App\Http\Controllers\Admin;
use App\Http\Controllers\Controller;
use App\Services\DummyDataService;
use Illuminate\Http\Request;
class AdminRekomendasiController extends Controller
{
/**
* Helper function untuk mengekstrak ID video dari URL YouTube.
*/
private function extractYouTubeId(string $url): ?string
{
preg_match('/(v=|vi=|youtu.be\/|embed\/|\/v\/|\?v=|\&v=)(.+?)\b/i', $url, $matches);
return $matches[2] ?? null;
}
public function index()
{
$rekomendasiMentah = DummyDataService::getRekomendasiPembelajaran();
// Menambahkan thumbnail YouTube ke setiap rekomendasi
$semuaRekomendasi = $rekomendasiMentah->map(function ($item) {
$videoId = $this->extractYouTubeId($item['youtube_link']);
if ($videoId) {
$item['thumbnail'] = "https://img.youtube.com/vi/{$videoId}/hqdefault.jpg";
} else {
$item['thumbnail'] = 'https://via.placeholder.com/150?text=No+Preview';
}
return $item;
});
return view('admin.rekomendasi.index', [
'pageTitle' => 'Manajemen Rekomendasi',
'semuaRekomendasi' => $semuaRekomendasi
]);
}
public function create()
{
return view('admin.rekomendasi.create', ['pageTitle' => 'Tambah Rekomendasi']);
}
public function edit($id)
{
$rekomendasi = DummyDataService::getRekomendasiPembelajaran()->firstWhere('id', (int)$id);
abort_if(!$rekomendasi, 404);
return view('admin.rekomendasi.edit', ['pageTitle' => 'Edit Rekomendasi', 'rekomendasi' => $rekomendasi]);
}
}

View File

@ -0,0 +1,50 @@
<?php
namespace App\Http\Controllers\Admin;
use App\Http\Controllers\Controller;
use App\Services\DummyDataService;
use Illuminate\Http\Request;
class BookController extends Controller
{
public function index(Request $request)
{
$filters = $request->only(['search']);
$semuaBuku = DummyDataService::getKatalogBuku($filters);
// Memisahkan buku menjadi dua koleksi: online dan offline
[$bukuOnline, $bukuOffline] = $semuaBuku->partition(function ($buku) {
$tipe = $buku['tipe_akses'];
return $tipe === 'online' || (is_array($tipe) && in_array('online', $tipe));
});
return view('admin.buku.index', [
'pageTitle' => 'Manajemen Buku',
'bukuOnline' => $bukuOnline,
'bukuOffline' => $bukuOffline,
'input' => $filters
]);
}
/**
* Menampilkan halaman form untuk menambah buku baru.
*/
public function create()
{
return view('admin.buku.create', [
'pageTitle' => 'Tambah Buku Baru'
]);
}
public function edit($id)
{
$buku = DummyDataService::getKatalogBuku()->firstWhere('id', (int)$id);
abort_if(!$buku, 404);
return view('admin.buku.edit', [
'pageTitle' => 'Edit Buku: ' . $buku['judul'],
'buku' => $buku
]);
}
}

View File

@ -0,0 +1,23 @@
<?php
namespace App\Http\Controllers\Admin;
use App\Http\Controllers\Controller;
use App\Services\DummyDataService;
class DashboardController extends Controller
{
public function index()
{
return view('admin.dashboard', [
'pageTitle' => 'Beranda',
'user' => auth()->user(),
'greeting' => 'Selamat Datang',
'stats' => DummyDataService::getAdminDashboardStats(),
'statistikBulanan' => DummyDataService::getStatistikPeminjamanAdmin(),
'komposisiBuku' => DummyDataService::getKomposisiBukuAdmin(),
'pengumuman' => DummyDataService::getPengumuman(),
'aktivitasTerakhir' => DummyDataService::getAktivitasTerakhir(),
]);
}
}

View File

@ -0,0 +1,31 @@
<?php
namespace App\Http\Controllers\Admin;
use App\Http\Controllers\Controller;
use App\Models\MasterInduk;
use Illuminate\Http\Request;
class MasterIndukController extends Controller
{
// Menyimpan Data Induk Baru (Pre-Register)
public function store(Request $request)
{
$request->validate([
'nomor_induk' => 'required|unique:master_induks,nomor_induk',
'role' => 'required|in:siswa,guru',
'nama_pemilik' => 'required|string',
]);
MasterInduk::create($request->all());
return back()->with('success', 'Data Induk berhasil ditambahkan. User dengan NIP/NISN ini sekarang bisa mendaftar.');
}
// Menghapus Data
public function destroy($id)
{
MasterInduk::findOrFail($id)->delete();
return back()->with('success', 'Data Induk dihapus.');
}
}

View File

@ -0,0 +1,48 @@
<?php
namespace App\Http\Controllers\Admin;
use App\Http\Controllers\Controller;
use App\Services\DummyDataService;
use Illuminate\Http\Request;
class PengumumanController extends Controller
{
/**
* Menampilkan daftar semua pengumuman.
*/
public function index()
{
$semuaPengumuman = DummyDataService::getPengumuman();
return view('admin.pengumuman.index', [
'pageTitle' => 'Manajemen Pengumuman',
'semuaPengumuman' => $semuaPengumuman,
]);
}
/**
* Menampilkan form untuk membuat pengumuman baru.
*/
public function create()
{
return view('admin.pengumuman.create', [
'pageTitle' => 'Buat Pengumuman Baru',
]);
}
/**
* Menampilkan form untuk mengedit pengumuman yang ada.
*/
public function edit($id)
{
$pengumuman = collect(DummyDataService::getPengumuman())->firstWhere('id', (int)$id);
// Hentikan jika pengumuman tidak ditemukan
abort_if(!$pengumuman, 404);
return view('admin.pengumuman.edit', [
'pageTitle' => 'Edit Pengumuman',
'pengumuman' => $pengumuman,
]);
}
}

View File

@ -0,0 +1,173 @@
<?php
namespace App\Http\Controllers\Admin;
use App\Http\Controllers\Controller;
use App\Models\User;
use App\Models\MasterInduk;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Hash;
class UserController extends Controller
{
public function index()
{
$query = User::orderBy('created_at', 'desc');
if (request()->has('role') && request('role') != '') {
$query->where('role', request('role'));
}
$users = $query->paginate(10)->appends(request()->query());
$whitelists = MasterInduk::orderBy('created_at', 'desc')->get();
return view('admin.pengguna.index', [
'pageTitle' => 'Daftar Pengguna',
'users' => $users,
'whitelists' => $whitelists
]);
}
public function create()
{
return view('admin.pengguna.create', ['pageTitle' => 'Tambah Pengguna Baru']);
}
public function store(Request $request)
{
$request->validate([
'nama_lengkap' => 'required|string|max:255',
'email' => 'required|email|unique:users,email',
'role' => 'required|in:siswa,guru,penjaga perpus',
'no_hp' => 'nullable|string|max:20',
'password' => 'required|min:6|confirmed',
'nomor_induk' => [
'required',
function ($attribute, $value, $fail) use ($request) {
$label = $request->role == 'siswa' ? 'NISN' : 'NIP/NIK';
// Cek Nisn/Nip sudah dipakai di tabel users
$sudahDipakai = User::where('nisn', $value)->orWhere('nip', $value)->exists();
if ($sudahDipakai) {
$fail("{$label} ini sudah digunakan oleh akun lain.");
return;
}
if (in_array($request->role, ['siswa', 'guru'])) {
$terdaftar = MasterInduk::where('nomor_induk', $value)
->where('role', $request->role)
->exists();
if (!$terdaftar) {
$fail("{$label} tidak terdaftar di data sekolah. Hubungi admin.");
}
}
},
],
], [
'role.in' => 'Pilih role yang valid.',
'email.unique' => 'Email sudah terdaftar.',
'password.confirmed' => 'Konfirmasi password tidak cocok.'
]);
$user = new User();
$user->name = $request->nama_lengkap;
$user->email = $request->email;
$user->role = $request->role;
$user->password = Hash::make($request->password);
$user->no_hp = $request->no_hp;
// Validasi NISN dan NIP berdasarkan Role
if ($request->role == 'siswa') {
$user->nisn = $request->nomor_induk;
$user->kelas = $request->kelas;
$user->golongan = $request->golongan;
} else {
$user->nip = $request->nomor_induk;
}
$user->save();
return redirect()->route('admin.pengguna.index')->with('success', 'Pengguna berhasil ditambahkan.');
}
public function edit($id)
{
$pengguna = User::findOrFail($id);
return view('admin.pengguna.edit', [
'pageTitle' => 'Edit Pengguna',
'pengguna' => $pengguna,
]);
}
public function update(Request $request, $id)
{
$request->validate([
'nama_lengkap' => 'required|string|max:255',
'email' => 'required|email|unique:users,email,' . $id,
'role' => 'required|in:siswa,guru,penjaga perpus',
'no_hp' => 'nullable|string|max:20',
'password' => 'nullable|min:6|confirmed',
'nomor_induk' => [
'required',
function ($attribute, $value, $fail) use ($request, $id) {
$label = $request->role == 'siswa' ? 'NISN' : 'NIP/NIK';
// cek nisn/nip sudah dipakai di tabel users (kecuali oleh dirinya sendiri)
$sudahDipakai = User::where(function ($query) use ($value) {
$query->where('nisn', $value)->orWhere('nip', $value);
})->where('id', '!=', $id)->exists();
if ($sudahDipakai) {
$fail("{$label} ini sudah digunakan oleh akun lain.");
return;
}
if (in_array($request->role, ['siswa', 'guru'])) {
$terdaftar = MasterInduk::where('nomor_induk', $value)
->where('role', $request->role)
->exists();
if (!$terdaftar) {
$fail("{$label} tidak terdaftar di data sekolah. Hubungi admin.");
}
}
},
],
]);
$user = User::findOrFail($id);
$user->name = $request->nama_lengkap;
$user->email = $request->email;
$user->role = $request->role;
$user->no_hp = $request->no_hp;
// Jika password diisi, maka update. Jika kosong, biarkan password lama.
if ($request->filled('password')) {
$user->password = \Illuminate\Support\Facades\Hash::make($request->password);
}
$user->nisn = null;
$user->nip = null;
$user->kelas = null;
$user->golongan = null;
// Masukkan kembali sesuai role
if ($request->role == 'siswa') {
$user->nisn = $request->nomor_induk;
$user->kelas = $request->kelas;
$user->golongan = $request->golongan;
} else {
$user->nip = $request->nomor_induk;
}
$user->save();
return redirect()->route('admin.pengguna.index')->with('success', 'Data pengguna berhasil diperbarui.');
}
public function destroy($id)
{
User::findOrFail($id)->delete();
return back()->with('success', 'Pengguna berhasil dihapus.');
}
}

View File

@ -0,0 +1,26 @@
<?php
namespace App\Http\Controllers\Auth;
use App\Http\Controllers\Controller;
use App\Http\Requests\Auth\LoginRequest;
use Illuminate\Http\RedirectResponse;
use Illuminate\Http\Request;
use Illuminate\View\View;
class AdminLoginController extends Controller
{
// Menampilkan form login admin
public function create(): View
{
return view('auth.admin-login');
}
// Memproses login admin
public function store(LoginRequest $request): RedirectResponse
{
$request->authenticate();
$request->session()->regenerate();
return redirect()->route('admin.dashboard');
}
}

View File

@ -0,0 +1,52 @@
<?php
namespace App\Http\Controllers\Auth;
use App\Http\Controllers\Controller;
use App\Http\Requests\Auth\LoginRequest;
use Illuminate\Http\RedirectResponse;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\View\View;
class AuthenticatedSessionController extends Controller
{
/**
* Display the login view.
*/
public function create(Request $request): View
{
// Ambil 'role' dari URL, jika tidak ada, defaultnya 'siswa'
$role = $request->query('role', 'siswa');
return view('auth.login', [
'role' => $role
]);
}
/**
* Handle an incoming authentication request.
*/
public function store(LoginRequest $request): RedirectResponse
{
$request->authenticate(); // Menjalankan logika di LoginRequest
$request->session()->regenerate();
// Karena login sudah dijamin benar, cukup arahkan ke dashboard umum
return redirect()->intended(route('dashboard'));
}
/**
* Destroy an authenticated session.
*/
public function destroy(Request $request): RedirectResponse
{
Auth::guard('web')->logout();
$request->session()->forget('user_data');
$request->session()->invalidate();
$request->session()->regenerateToken();
return redirect('/');
}
}

View File

@ -0,0 +1,40 @@
<?php
namespace App\Http\Controllers\Auth;
use App\Http\Controllers\Controller;
use Illuminate\Http\RedirectResponse;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\Validation\ValidationException;
use Illuminate\View\View;
class ConfirmablePasswordController extends Controller
{
/**
* Show the confirm password view.
*/
public function show(): View
{
return view('auth.confirm-password');
}
/**
* Confirm the user's password.
*/
public function store(Request $request): RedirectResponse
{
if (! Auth::guard('web')->validate([
'email' => $request->user()->email,
'password' => $request->password,
])) {
throw ValidationException::withMessages([
'password' => __('auth.password'),
]);
}
$request->session()->put('auth.password_confirmed_at', time());
return redirect()->intended(route('dashboard', absolute: false));
}
}

View File

@ -0,0 +1,24 @@
<?php
namespace App\Http\Controllers\Auth;
use App\Http\Controllers\Controller;
use Illuminate\Http\RedirectResponse;
use Illuminate\Http\Request;
class EmailVerificationNotificationController extends Controller
{
/**
* Send a new email verification notification.
*/
public function store(Request $request): RedirectResponse
{
if ($request->user()->hasVerifiedEmail()) {
return redirect()->intended(route('dashboard', absolute: false));
}
$request->user()->sendEmailVerificationNotification();
return back()->with('status', 'verification-link-sent');
}
}

View File

@ -0,0 +1,21 @@
<?php
namespace App\Http\Controllers\Auth;
use App\Http\Controllers\Controller;
use Illuminate\Http\RedirectResponse;
use Illuminate\Http\Request;
use Illuminate\View\View;
class EmailVerificationPromptController extends Controller
{
/**
* Display the email verification prompt.
*/
public function __invoke(Request $request): RedirectResponse|View
{
return $request->user()->hasVerifiedEmail()
? redirect()->intended(route('dashboard', absolute: false))
: view('auth.verify-email');
}
}

View File

@ -0,0 +1,62 @@
<?php
namespace App\Http\Controllers\Auth;
use App\Http\Controllers\Controller;
use App\Models\User;
use Illuminate\Auth\Events\PasswordReset;
use Illuminate\Http\RedirectResponse;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Password;
use Illuminate\Support\Str;
use Illuminate\Validation\Rules;
use Illuminate\View\View;
class NewPasswordController extends Controller
{
/**
* Display the password reset view.
*/
public function create(Request $request): View
{
return view('auth.reset-password', ['request' => $request]);
}
/**
* Handle an incoming new password request.
*
* @throws \Illuminate\Validation\ValidationException
*/
public function store(Request $request): RedirectResponse
{
$request->validate([
'token' => ['required'],
'email' => ['required', 'email'],
'password' => ['required', 'confirmed', Rules\Password::defaults()],
]);
// Here we will attempt to reset the user's password. If it is successful we
// will update the password on an actual user model and persist it to the
// database. Otherwise we will parse the error and return the response.
$status = Password::reset(
$request->only('email', 'password', 'password_confirmation', 'token'),
function (User $user) use ($request) {
$user->forceFill([
'password' => Hash::make($request->password),
'remember_token' => Str::random(60),
])->save();
event(new PasswordReset($user));
}
);
// If the password was successfully reset, we will redirect the user back to
// the application's home authenticated view. If there is an error we can
// redirect them back to where they came from with their error message.
return $status == Password::PASSWORD_RESET
? redirect()->route('login')->with('status', __($status))
: back()->withInput($request->only('email'))
->withErrors(['email' => __($status)]);
}
}

View File

@ -0,0 +1,29 @@
<?php
namespace App\Http\Controllers\Auth;
use App\Http\Controllers\Controller;
use Illuminate\Http\RedirectResponse;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Hash;
use Illuminate\Validation\Rules\Password;
class PasswordController extends Controller
{
/**
* Update the user's password.
*/
public function update(Request $request): RedirectResponse
{
$validated = $request->validateWithBag('updatePassword', [
'current_password' => ['required', 'current_password'],
'password' => ['required', Password::defaults(), 'confirmed'],
]);
$request->user()->update([
'password' => Hash::make($validated['password']),
]);
return back()->with('status', 'password-updated');
}
}

View File

@ -0,0 +1,44 @@
<?php
namespace App\Http\Controllers\Auth;
use App\Http\Controllers\Controller;
use Illuminate\Http\RedirectResponse;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Password;
use Illuminate\View\View;
class PasswordResetLinkController extends Controller
{
/**
* Display the password reset link request view.
*/
public function create(): View
{
return view('auth.forgot-password');
}
/**
* Handle an incoming password reset link request.
*
* @throws \Illuminate\Validation\ValidationException
*/
public function store(Request $request): RedirectResponse
{
$request->validate([
'email' => ['required', 'email'],
]);
// We will send the password reset link to this user. Once we have attempted
// to send the link, we will examine the response then see the message we
// need to show to the user. Finally, we'll send out a proper response.
$status = Password::sendResetLink(
$request->only('email')
);
return $status == Password::RESET_LINK_SENT
? back()->with('status', __($status))
: back()->withInput($request->only('email'))
->withErrors(['email' => __($status)]);
}
}

View File

@ -0,0 +1,75 @@
<?php
namespace App\Http\Controllers\Auth;
use App\Http\Controllers\Controller;
use App\Models\User;
use App\Models\MasterInduk;
use Illuminate\Auth\Events\Registered;
use Illuminate\Http\RedirectResponse;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Hash;
use Illuminate\Validation\Rules;
use Illuminate\Validation\ValidationException;
use Illuminate\View\View;
class RegisteredUserController extends Controller
{
public function create(Request $request): View
{
$role = $request->query('role', 'siswa');
return view('auth.register', ['role' => $role]);
}
public function store(Request $request): RedirectResponse
{
$role = $request->input('role');
$rules = [
'name' => ['required', 'string', 'max:255'],
'email' => ['required', 'string', 'email', 'max:255', 'unique:users'],
'password' => ['required', 'confirmed', Rules\Password::defaults()],
'role' => ['required', 'in:siswa,guru'],
];
if ($role === 'siswa') {
$rules['nisn'] = ['required', 'string', 'max:255', 'unique:users,nisn'];
} else {
$rules['nip'] = ['required', 'string', 'max:255', 'unique:users,nip'];
}
$request->validate($rules);
$nomorInduk = ($role === 'siswa') ? $request->nisn : $request->nip;
$isWhitelisted = MasterInduk::where('nomor_induk', $nomorInduk)
->where('role', $role)
->exists();
if (!$isWhitelisted) {
throw ValidationException::withMessages([
($role === 'siswa' ? 'nisn' : 'nip') => ['Nomor induk tidak terdaftar di Data Sekolah. Hubungi petugas.'],
]);
}
$user = User::create([
'name' => $request->name,
'email' => $request->email,
'password' => Hash::make($request->password),
'role' => $role,
'nisn' => ($role === 'siswa') ? $nomorInduk : null,
'nip' => ($role === 'guru') ? $nomorInduk : null,
]);
event(new Registered($user));
Auth::login($user);
return redirect()->route('dashboard');
}
}

View File

@ -0,0 +1,27 @@
<?php
namespace App\Http\Controllers\Auth;
use App\Http\Controllers\Controller;
use Illuminate\Auth\Events\Verified;
use Illuminate\Foundation\Auth\EmailVerificationRequest;
use Illuminate\Http\RedirectResponse;
class VerifyEmailController extends Controller
{
/**
* Mark the authenticated user's email address as verified.
*/
public function __invoke(EmailVerificationRequest $request): RedirectResponse
{
if ($request->user()->hasVerifiedEmail()) {
return redirect()->intended(route('dashboard', absolute: false).'?verified=1');
}
if ($request->user()->markEmailAsVerified()) {
event(new Verified($request->user()));
}
return redirect()->intended(route('dashboard', absolute: false).'?verified=1');
}
}

View File

@ -0,0 +1,113 @@
<?php
namespace App\Http\Controllers;
use App\Services\DummyDataService;
use Illuminate\Http\RedirectResponse;
use Illuminate\Http\Request;
use Illuminate\Http\Response;
use Illuminate\Support\Str;
use Illuminate\View\View;
use Symfony\Component\HttpFoundation\BinaryFileResponse;
class BacaOnlineController extends Controller
{
public function index(Request $request): View
{
$filters = $request->only(['search', 'kategori', 'tahun', 'penulis']);
$filters['tipe_akses'] = 'online';
$semuaBuku = DummyDataService::getKatalogBuku($filters);
$filterOptions = DummyDataService::getFilterOptions();
return view('katalog.index', [
'semuaBuku' => $semuaBuku,
'filterOptions' => $filterOptions,
'input' => $request->query(),
'pageTitle' => 'Baca Buku Online',
'mode' => 'online',
]);
}
public function ringkasan(int $id): View
{
$book = $this->getBookOrFail($id);
return view('katalog.ringkasan', [
'buku' => $book,
'pageTitle' => 'Baca Buku Online',
'actionRoute' => 'baca.request_code',
'previousRoute' => 'baca.index',
'actionButtonText' => 'Baca Sekarang',
'actionButtonIcon' => 'bi-book-half',
]);
}
public function showCodeRequestPage(int $id): View
{
$book = $this->getBookOrFail($id);
$sessionKey = 'access_code_for_book_' . $id;
if (session()->has($sessionKey)) {
$accessCode = session($sessionKey);
} else {
$accessCode = 'BCO-' . date('Ymd') . '-' . $book['id'] . '-' . Str::upper(Str::random(4));
session([$sessionKey => $accessCode]);
}
session(['book_verified_' . $id => false]);
return view('baca.request_code', [
'book' => $book,
'accessCode' => $accessCode
]);
}
public function verifyCode(Request $request, int $id): RedirectResponse
{
$request->validate(['kode_akses' => 'required|string']);
$correctCode = session('access_code_for_book_' . $id);
if ($request->input('kode_akses') === $correctCode) {
session(['book_verified_' . $id => true]);
session()->forget('access_code_for_book_' . $id);
return redirect()->route('baca.view_book', ['id' => $id]);
}
return back()->with('error', 'Kode akses yang Anda masukkan salah!');
}
public function viewBook(int $id): View|RedirectResponse
{
if (!session('book_verified_' . $id, false)) {
return redirect()->route('baca.request_code', ['id' => $id])
->with('error', 'Silakan masukkan kode akses terlebih dahulu.');
}
$book = $this->getBookOrFail($id);
return view('baca.view_book', ['book' => $book]);
}
public function streamPdf(int $id): BinaryFileResponse|Response
{
if (!session('book_verified_' . $id, false)) {
abort(403, 'Akses Ditolak.');
}
$book = $this->getBookOrFail($id);
$filePath = 'books/' . $book['file_pdf'];
$absolutePath = storage_path('app/' . $filePath);
if (!file_exists($absolutePath)) {
abort(404, 'GAGAL - PHP tidak dapat menemukan file di: ' . $absolutePath);
}
return response()->file($absolutePath);
}
private function getBookOrFail(int $id): array
{
$book = DummyDataService::getKatalogBuku()->firstWhere('id', $id);
if (!$book) {
abort(404, 'Buku tidak ditemukan.');
}
return $book;
}
}

View File

@ -0,0 +1,8 @@
<?php
namespace App\Http\Controllers;
abstract class Controller
{
//
}

View File

@ -0,0 +1,82 @@
<?php
namespace App\Http\Controllers;
use App\Services\DummyDataService;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
class DashboardController extends Controller
{
public function index()
{
$user = Auth::user();
$bukuPinjam = DummyDataService::getBukuPinjamOffline($user);
$isTelat = collect($bukuPinjam)->contains(function ($buku) {
return $buku['sisa_hari'] < 0;
});
if ($isTelat && $user->role === 'siswa') {
$user->is_banned = true;
}
$stats = DummyDataService::getDashboardStats();
$pengumuman = DummyDataService::getPengumuman();
$pemberitahuan = DummyDataService::getPemberitahuan();
$progressMembaca = DummyDataService::getProgressMembaca();
$statistikBulanan = DummyDataService::getStatistikBulanan();
$bukuPinjamOffline = $bukuPinjam;
$bacaBukuOnline = DummyDataService::getBacaBukuOnline($user);
$rekomendasiPembelajaran = DummyDataService::getRekomendasiPembelajaran();
$personalNotif = DummyDataService::getNotifikasiForUser($user);
// Cek apakah ada notifikasi denda aktif
$dendaAlert = collect($personalNotif)->where('type', 'denda_active');
// Menambahkan thumbnail YouTube ke setiap rekomendasi
$rekomendasiPembelajaran = $rekomendasiPembelajaran->map(function ($item) {
$videoId = $this->extractYouTubeId($item['youtube_link']);
if ($videoId) {
$item['thumbnail'] = "https://img.youtube.com/vi/{$videoId}/hqdefault.jpg";
} else {
$item['thumbnail'] = 'https://via.placeholder.com/150?text=No+Preview';
}
return $item;
});
$dendaAlert = collect($personalNotif)->where('type', 'denda_active');
$hour = date('H');
$greeting = "Selamat Pagi";
if ($hour >= 12 && $hour < 15)
$greeting = "Selamat Siang";
elseif ($hour >= 15 && $hour < 18)
$greeting = "Selamat Sore";
elseif ($hour >= 18)
$greeting = "Selamat Malam";
return view('dashboard', compact(
'user',
'stats',
'pengumuman',
'pemberitahuan',
'dendaAlert',
'progressMembaca',
'statistikBulanan',
'bukuPinjamOffline',
'bacaBukuOnline',
'greeting',
'rekomendasiPembelajaran'
))->with('notifikasi', $personalNotif);
}
/**
* Helper function untuk mengekstrak ID video dari URL YouTube.
*/
private function extractYouTubeId(string $url): ?string
{
preg_match('/(v=|vi=|youtu.be\/|embed\/|\/v\/|\?v=|\&v=)(.+?)\b/i', $url, $matches);
return $matches[2] ?? null;
}
}

View File

@ -0,0 +1,24 @@
<?php
namespace App\Http\Controllers\Guru;
use App\Http\Controllers\Controller;
use App\Services\DummyDataService;
use Illuminate\Http\Request;
class LaporanController extends Controller
{
public function index()
{
$laporan = DummyDataService::getLaporanMinatBaca();
$siswaTeraktif = DummyDataService::getSiswaTeraktif();
$aktivitasMingguan = DummyDataService::getAktivitasMingguan();
return view('guru.laporan.index', [
'pageTitle' => 'Laporan Minat Baca Siswa',
'laporan' => $laporan,
'siswaTeraktif' => $siswaTeraktif,
'aktivitasMingguan' => $aktivitasMingguan,
]);
}
}

View File

@ -0,0 +1,36 @@
<?php
namespace App\Http\Controllers;
use App\Services\DummyDataService;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
class KatalogController extends Controller
{
public function index(Request $request)
{
$user = Auth::user();
$isBanned = false;
if ($user && $user->role === 'siswa') {
$bukuPinjam = DummyDataService::getBukuPinjamOffline($user);
$isTelat = collect($bukuPinjam)->contains(fn($b) => $b['sisa_hari'] < 0);
$isBannedManual = $user->is_banned ?? false;
$isBanned = $isTelat || $isBannedManual;
}
$filters = $request->only(['search', 'kategori', 'tahun', 'penulis']);
$semuaBuku = DummyDataService::getKatalogBuku($filters);
$filterOptions = DummyDataService::getFilterOptions();
return view('katalog.index', [
'semuaBuku' => $semuaBuku,
'filterOptions' => $filterOptions,
'input' => $filters,
'pageTitle' => 'Katalog Buku',
'mode' => 'umum',
'isBanned' => $isBanned,
]);
}
}

View File

@ -0,0 +1,89 @@
<?php
namespace App\Http\Controllers;
use App\Services\DummyDataService;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
class PeminjamanController extends Controller
{
public function index(Request $request)
{
$user = \Illuminate\Support\Facades\Auth::user();
$bukuPinjam = \App\Services\DummyDataService::getBukuPinjamOffline($user);
$isTelat = collect($bukuPinjam)->contains(function ($buku) {
return $buku['sisa_hari'] < 0;
});
$isBannedManual = $user->is_banned ?? false;
if (($isTelat || $isBannedManual) && $user->role === 'siswa') {
return redirect()->route('dashboard')->with('error', 'AKSES DITOLAK: Akun Anda sedang dibekukan karena ada buku terlambat!');
}
$filters = $request->only(['search', 'kategori', 'tahun', 'penulis']);
$filters['tipe_akses'] = 'offline';
$semuaBuku = DummyDataService::getKatalogBuku($filters);
$filterOptions = DummyDataService::getFilterOptions();
return view('katalog.index', [
'semuaBuku' => $semuaBuku,
'filterOptions' => $filterOptions,
'input' => $request->query(),
'pageTitle' => 'Peminjaman Buku Offline',
'mode' => 'offline',
]);
}
public function ringkasan($id)
{
$user = Auth::user();
$buku = DummyDataService::getKatalogBuku()->firstWhere('id', $id);
return view('katalog.ringkasan', [
'user' => $user,
'buku' => $buku,
'pageTitle' => 'Peminjaman Buku Offline',
'actionRoute' => 'peminjaman.form',
'previousRoute' => 'peminjaman.index',
'actionButtonText' => 'Lanjutkan ke Form Peminjaman',
'actionButtonIcon' => 'bi-file-earmark-text-fill',
]);
}
public function form($id)
{
$user = Auth::user();
$buku = DummyDataService::getKatalogBuku()->firstWhere('id', $id);
$filters = ['tipe_akses' => 'offline'];
$semuaBuku = DummyDataService::getKatalogBuku($filters);
return view('peminjaman.form', compact('user', 'buku', 'semuaBuku'));
}
public function store(Request $request)
{
$request->validate([
'buku_ids' => 'required|array|min:1|max:3',
'buku_ids.*' => 'integer'
]);
$bukuIds = $request->input('buku_ids');
foreach ($bukuIds as $bukuId) {
// Di backend nanti kayak gini
// Peminjaman::create([
// 'user_id' => auth()->id(),
// 'book_id' => $bukuId,
// 'tanggal_pinjam' => now(),
// 'tanggal_kembali' => now()->addDays(7),
// 'status' => 'dipinjam'
// ]);
}
return redirect()->route('dashboard')
->with('success', 'Berhasil meminjam ' . count($bukuIds) . ' buku!');
}
}

View File

@ -0,0 +1,98 @@
<?php
namespace App\Http\Controllers;
use App\Http\Requests\ProfileUpdateRequest;
use Illuminate\Http\RedirectResponse;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Redirect;
use Illuminate\View\View;
use Illuminate\Support\Facades\Hash;
use App\Services\DummyDataService;
class ProfileController extends Controller
{
/**
* Tampilkan halaman profil user.
*/
public function index(Request $request): View
{
$user = $request->user();
$viewData = ['user' => $user];
if ($user->role === 'penjaga perpus') {
$viewData['statistik'] = DummyDataService::getAdminDashboardStats();
$viewData['aktivitasTerakhir'] = DummyDataService::getAktivitasTerakhir();
} elseif ($user->role === 'guru') {
$viewData['bukuOffline'] = DummyDataService::getBukuPinjamOffline($user);
$viewData['bukuOnline'] = DummyDataService::getBacaBukuOnline($user);
$viewData['laporan'] = DummyDataService::getLaporanMinatBaca();
} else {
$viewData['bukuOffline'] = DummyDataService::getBukuPinjamOffline($user);
$viewData['bukuOnline'] = DummyDataService::getBacaBukuOnline($user);
$viewData['statistik'] = DummyDataService::getDashboardStats();
}
return view('profile.index', $viewData);
}
/**
* Tampilkan form edit profil.
*/
public function edit(Request $request): View
{
return view('profile.edit', [
'user' => $request->user(),
]);
}
/**
* Update data profil ke Database MySQL.
*/
public function update(Request $request): RedirectResponse
{
$request->validate([
'name' => ['required', 'string', 'max:255'],
'email' => ['required', 'string', 'email', 'max:255', 'unique:users,email,'.Auth::id()],
'no_hp' => ['nullable', 'string', 'max:15'],
]);
$user = $request->user();
$user->name = $request->name;
$user->email = $request->email;
$user->no_hp = $request->no_hp;
if ($user->isDirty('email')) {
$user->email_verified_at = null;
}
$user->save();
return Redirect::route('profile.edit')->with('status', 'profile-updated');
}
/**
* Hapus akun user.
*/
public function destroy(Request $request): RedirectResponse
{
$request->validateWithBag('userDeletion', [
'password' => ['required', 'current_password'],
]);
$user = $request->user();
Auth::logout();
$user->delete();
$request->session()->invalidate();
$request->session()->regenerateToken();
return Redirect::to('/');
}
}

View File

@ -0,0 +1,36 @@
<?php
namespace App\Http\Controllers;
use App\Services\DummyDataService;
class RekomendasiController extends Controller
{
/**
* Helper function untuk mengekstrak ID video dari URL YouTube.
*/
private function extractYouTubeId(string $url): ?string
{
preg_match('/(v=|vi=|youtu.be\/|embed\/|\/v\/|\?v=|\&v=)(.+?)\b/i', $url, $matches);
return $matches[2] ?? null;
}
public function show($id)
{
$rekomendasi = DummyDataService::getRekomendasiPembelajaran()->firstWhere('id', (int)$id);
abort_if(!$rekomendasi, 404);
// Menambahkan thumbnail YouTube ke setiap rekomendasi
$embedLink = null;
$videoId = $this->extractYouTubeId($rekomendasi['youtube_link']);
if ($videoId) {
$embedLink = "https://www.youtube.com/embed/" . $videoId;
}
$rekomendasi['youtube_embed_link'] = $embedLink;
return view('rekomendasiShow', [
'pageTitle' => $rekomendasi['judul'],
'rekomendasi' => $rekomendasi,
]);
}
}

View File

@ -0,0 +1,49 @@
<?php
namespace App\Http\Controllers;
use App\Services\DummyDataService;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
class RiwayatController extends Controller
{
public function offlineIndex()
{
$user = Auth::user();
if (!$user) $user = (object) ['id' => 1];
$dataOffline = DummyDataService::getRiwayatOffline($user);
$riwayatOffline = collect($dataOffline)
->sortBy([
['status', 'asc'],
['tanggal_pinjam', 'desc']
])
->values()
->all();
return view('riwayat.offline', [
'pageTitle' => 'Riwayat Peminjaman Offline',
'riwayatOffline' => $riwayatOffline,
]);
}
public function onlineIndex()
{
$dataOnline = DummyDataService::getRiwayatOnline();
$riwayatOnline = collect($dataOnline)
->sortBy([
['status', 'asc'],
['tanggal_baca', 'desc']
])
->values()
->all();
return view('riwayat.online', [
'pageTitle' => 'Riwayat Baca Online',
'riwayatOnline' => $riwayatOnline,
]);
}
}

View File

@ -0,0 +1,21 @@
<?php
namespace App\Http\Middleware;
use Closure;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Symfony\Component\HttpFoundation\Response;
class CheckRole
{
public function handle(Request $request, Closure $next, ...$roles): Response
{
if (!Auth::check() || !in_array(Auth::user()->role, $roles)) {
return redirect()->route('login')
->with('error', 'Akses ditolak. Anda tidak memiliki izin untuk mengakses halaman tersebut.');
}
return $next($request);
}
}

View File

@ -0,0 +1,86 @@
<?php
namespace App\Http\Requests\Auth;
use Illuminate\Auth\Events\Lockout;
use Illuminate\Foundation\Http\FormRequest;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\RateLimiter;
use Illuminate\Support\Str;
use Illuminate\Validation\ValidationException;
class LoginRequest extends FormRequest
{
public function authorize(): bool
{
return true;
}
public function rules(): array
{
return [
'password' => ['required', 'string'],
];
}
public function authenticate(): void
{
$this->ensureIsNotRateLimited();
$loginString = $this->input('email') ?? $this->input('nisn') ?? $this->input('nip');
$password = $this->input('password');
if (!$loginString) {
throw ValidationException::withMessages([
'email' => 'Mohon masukkan NISN, NIP, atau Email.',
]);
}
if (Auth::attempt(['nisn' => $loginString, 'password' => $password], $this->boolean('remember'))) {
RateLimiter::clear($this->throttleKey());
return;
}
if (Auth::attempt(['nip' => $loginString, 'password' => $password], $this->boolean('remember'))) {
RateLimiter::clear($this->throttleKey());
return;
}
if (Auth::attempt(['email' => $loginString, 'password' => $password], $this->boolean('remember'))) {
RateLimiter::clear($this->throttleKey());
return;
}
RateLimiter::hit($this->throttleKey());
$fieldError = $this->input('nisn') ? 'nisn' : ($this->input('nip') ? 'nip' : 'email');
throw ValidationException::withMessages([
$fieldError => trans('auth.failed'),
]);
}
public function ensureIsNotRateLimited(): void
{
if (! RateLimiter::tooManyAttempts($this->throttleKey(), 5)) {
return;
}
event(new Lockout($this));
$seconds = RateLimiter::availableIn($this->throttleKey());
throw ValidationException::withMessages([
'email' => trans('auth.throttle', [
'seconds' => $seconds,
'minutes' => ceil($seconds / 60),
]),
]);
}
public function throttleKey(): string
{
$field = $this->input('email') ?? $this->input('nisn') ?? $this->input('nip') ?? 'unknown';
return Str::transliterate(Str::lower($field).'|'.$this->ip());
}
}

View File

@ -0,0 +1,30 @@
<?php
namespace App\Http\Requests;
use App\Models\User;
use Illuminate\Foundation\Http\FormRequest;
use Illuminate\Validation\Rule;
class ProfileUpdateRequest extends FormRequest
{
/**
* Get the validation rules that apply to the request.
*
* @return array<string, \Illuminate\Contracts\Validation\ValidationRule|array<mixed>|string>
*/
public function rules(): array
{
return [
'name' => ['required', 'string', 'max:255'],
'email' => [
'required',
'string',
'lowercase',
'email',
'max:255',
Rule::unique(User::class)->ignore($this->user()->id),
],
];
}
}

View File

@ -0,0 +1,12 @@
<?php
namespace App\Models;
use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;
class MasterInduk extends Model
{
use HasFactory;
protected $guarded = ['id'];
}

59
app/Models/User.php Normal file
View File

@ -0,0 +1,59 @@
<?php
namespace App\Models;
// use Illuminate\Contracts\Auth\MustVerifyEmail;
use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Foundation\Auth\User as Authenticatable;
use Illuminate\Notifications\Notifiable;
class User extends Authenticatable
{
/** @use HasFactory<\Database\Factories\UserFactory> */
use HasFactory, Notifiable;
/**
* The attributes that are mass assignable.
*
* @var list<string>
*/
protected $fillable = [
'name',
'email',
'password',
'role',
'nisn',
'nip',
'no_hp',
'kelas',
'nomor_induk'
];
/**
* The attributes that should be hidden for serialization.
*
* @var list<string>
*/
protected $hidden = [
'password',
'remember_token',
];
/**
* Get the attributes that should be cast.
*
* @return array<string, string>
*/
protected function casts(): array
{
return [
'email_verified_at' => 'datetime',
'password' => 'hashed',
];
}
public function getNamaLengkapAttribute()
{
return $this->name;
}
}

View File

@ -0,0 +1,44 @@
<?php
namespace App\Providers;
use App\Services\DummyDataService;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\URL;
use Illuminate\Support\ServiceProvider;
use Illuminate\Support\Facades\View;
class AppServiceProvider extends ServiceProvider
{
/**
* Register any application services.
*/
public function register(): void
{
//
}
/**
* Bootstrap any application services.
*/
public function boot(): void
{
if ($this->app->environment('production')) {
URL::forceScheme('https');
}
// View Composer untuk semua view (*)
View::composer('*', function ($view) {
if (Auth::check()) {
$user = Auth::user();
$notifikasi = collect(DummyDataService::getNotifikasiForUser($user));
$unreadCount = $notifikasi->where('read', false)->count();
$view->with('notifikasi', $notifikasi);
$view->with('unreadNotificationsCount', $unreadCount);
} else {
$view->with('notifikasi', collect([]));
$view->with('unreadNotificationsCount', 0);
}
});
}
}

View File

@ -0,0 +1,32 @@
<?php
namespace App\Providers;
// use App\Auth\DummyUserProvider; // Hapus atau Komen baris ini
use Illuminate\Support\Facades\Gate;
use Illuminate\Foundation\Support\Providers\AuthServiceProvider as ServiceProvider;
class AuthServiceProvider extends ServiceProvider
{
/**
* The model to policy mappings for the application.
*/
protected $policies = [
//
];
/**
* Register any authentication / authorization services.
*/
public function boot(): void
{
// $this->registerPolicies(); // Laravel 10/11 biasanya auto-discovery
// HAPUS atau KOMENTARI bagian ini:
/*
Auth::provider('dummy', function ($app, array $config) {
return new DummyUserProvider();
});
*/
}
}

View File

@ -0,0 +1,770 @@
<?php
namespace App\Services;
use Carbon\Carbon;
class DummyDataService
{
/**
* Data dummy untuk daftar siswa dan pengguna.
*/
public static function getAllSiswa(): array
{
return [
[
'id' => 1,
'nisn' => '1234567890',
'nama_lengkap' => 'Silvi Rahmawati',
'email' => 'silvi.rahmawati@smkn1perpus.sch.id',
'nomor_hp' => '08123456789',
'password' => 'password',
'role' => 'siswa',
'kelas' => 'XII RPL',
'golongan' => 'A',
'is_banned' => false,
],
[
'id' => 2,
'nama_lengkap' => 'Budi Santoso',
'nip' => '197812312005011',
'email' => 'budi.santoso@smkn1perpus.sch.id',
'password' => 'password',
'role' => 'penjaga perpus',
],
[
'id' => 3,
'nisn' => '9988776655',
'nama_lengkap' => 'Siti Nurhaliza',
'email' => 'siti.nurhaliza@smkn1perpus.sch.id',
'nomor_hp' => '081998877665',
'password' => 'password',
'role' => 'siswa',
'kelas' => 'XII RPL A',
'golongan' => 'A',
'is_banned' => true,
],
[
'id' => 4,
'nisn' => '5566778899',
'nama_lengkap' => 'Andi Pratama',
'email' => 'andi.pratama@smkn1perpus.sch.id',
'nomor_hp' => '081556677889',
'password' => 'password',
'role' => 'siswa',
'kelas' => 'XII RPL A',
'golongan' => 'A',
'is_banned' => false,
],
[
'id' => 5,
'nama_lengkap' => 'Rina Marlina',
'nip' => '198506152010012',
'email' => 'rina.marlina@smkn1perpus.sch.id',
'password' => 'password',
'role' => 'guru',
'is_banned' => false,
],
];
}
/**
* Data dummy untuk grafik aktivitas membaca mingguan di laporan guru.
*/
public static function getAktivitasMingguan(): array
{
return [
'labels' => ['Senin', 'Selasa', 'Rabu', 'Kamis', 'Jumat', 'Sabtu', 'Minggu'],
'data' => [15, 22, 18, 25, 20, 30, 28],
];
}
/**
* Data dummy untuk tabel peminjaman aktif di dashboard admin.
*/
public static function getAdminPeminjamanAktif(): \Illuminate\Support\Collection
{
$allBooks = self::getAllBooks();
$allSiswa = collect(self::getAllSiswa());
$bukuDipinjam = $allBooks->whereIn('status', ['Dipinjam', 'Terlambat']);
$grouped = $bukuDipinjam->groupBy(function ($item) {
return is_array($item['user_id']) ? $item['user_id'][0] : $item['user_id'];
});
return $grouped->map(function ($books, $userId) use ($allSiswa) {
$siswa = $allSiswa->firstWhere('id', $userId);
$firstBook = $books->first();
$tglKembali = Carbon::now()->addDays($firstBook['sisa_hari']);
return [
'id_peminjaman' => 'PIN-ADM-' . sprintf('%03d', $userId),
'user_id' => $userId,
'role' => $siswa ? $siswa['role'] : 'siswa',
'is_banned' => $siswa ? ($siswa['is_banned'] ?? false) : false,
'peminjam' => $siswa ? $siswa['nama_lengkap'] : 'User Tidak Dikenal',
'nomor_hp' => $siswa ? ($siswa['nomor_hp'] ?? '-') : '-',
'tanggal_pinjam' => Carbon::now()->subDays(7),
'tenggat_kembali' => $tglKembali,
'denda_per_hari' => 1000,
'books' => $books->map(function ($b) {
return [
'id' => $b['id'],
'judul' => $b['judul'],
'cover' => $b['cover']
];
})->toArray()
];
})->values();
}
/**
*Data Dummy untuk fitur Rekomendasi Pembelajaran.
*/
public static function getRekomendasiPembelajaran(): \Illuminate\Support\Collection
{
return collect([
[
'id' => 1,
'judul' => 'Sistem Tata Surya - Rangkuman Materi IPA Terpadu',
'kategori' => 'IPA',
'youtube_link' => 'https://www.youtube.com/watch?v=libKVRa01L8',
'deskripsi' => '<p>Video animasi seru yang menjelaskan tentang planet-planet di tata surya kita...</p>',
],
[
'id' => 2,
'judul' => 'Macam-macam Zat dan Perubahannya - IPA Kelas 7',
'kategori' => 'IPA',
'youtube_link' => 'https://www.youtube.com/watch?v=CfwPsKdC5w8',
'deskripsi' => '<p>Zat (materi) adalah sesuatu yang menempati ruang dan mempunyai massa...</p>',
],
[
'id' => 3,
'judul' => 'Sejarah Kerajaan Majapahit, Kerajaan Terbesar di Nusantara',
'kategori' => 'IPS',
'youtube_link' => 'https://www.youtube.com/watch?v=2Z9hqVqPY_s',
'deskripsi' => '<p>Pelajari sejarah salah satu kerajaan terbesar di Indonesia...</p>',
],
[
'id' => 4,
'judul' => 'Belajar HTML dari NOL untuk Pemula',
'kategori' => 'Informatika',
'youtube_link' => 'https://www.youtube.com/watch?v=NBZ9Ro6UKV8',
'deskripsi' => '<p>Ingin belajar membuat website? Mulai dari sini!...</p>',
],
[
'id' => 5,
'judul' => 'Rumus Cepat Teorema Pythagoras',
'kategori' => 'Matematika',
'youtube_link' => 'https://youtu.be/JJaptwjRbxc?si=XRxkrAf5G76iJ5CG',
'deskripsi' => '<p>Jangan takut lagi dengan soal Pythagoras!...</p>',
],
[
'id' => 6,
'judul' => 'Cara Menggambar Perspektif 1 Titik Hilang',
'kategori' => 'Seni Budaya',
'youtube_link' => 'https://youtu.be/SS7dLGDWUSs?si=lVw8jBkaWT---7ch',
'deskripsi' => '<p>Buat gambarmu terlihat lebih hidup dan realistis!...</p>',
],
[
'id' => 7,
'judul' => 'Sistem Peredaran Darah pada Manusia',
'kategori' => 'IPA',
'youtube_link' => 'https://youtu.be/QLoqMruGbkc?si=KiP5VZ4ByKSdFJK9',
'deskripsi' => '<p>Pahami bagaimana jantung memompa darah ke seluruh tubuh...</p>',
],
[
'id' => 8,
'judul' => 'Unsur-Unsur Intrinsik Cerpen',
'kategori' => 'Bahasa Indonesia',
'youtube_link' => 'https://youtu.be/PQNuvyQZYvI?si=Lr9AeTO_k6vY21ei',
'deskripsi' => '<p>Analisis sebuah cerita pendek menjadi lebih mudah...</p>',
],
[
'id' => 9,
'judul' => 'Apa itu Pemanasan Global?',
'kategori' => 'IPS',
'youtube_link' => 'https://youtu.be/pVjXm340tbw?si=GeMhYK1FSOGtV86X',
'deskripsi' => '<p>Mengapa suhu bumi semakin panas? Pelajari tentang penyebabnya...</p>',
],
[
'id' => 10,
'judul' => 'APA ITU LUBANG HITAM?',
'kategori' => 'Sains',
'youtube_link' => 'https://youtu.be/Tx87wEaDtxo?si=fNORkTYOeLiH9_xh',
'deskripsi' => '<p>Jelajahi salah satu objek paling misterius di alam semesta...</p>',
],
]);
}
/**
* Data dummy untuk menampilkan 10 siswa paling aktif di laporan guru.
*/
public static function getSiswaTeraktif(): array
{
return [
['nama' => 'Silvi Rahmawati', 'total_buku' => 45, 'kelas' => 'XII RPL'],
['nama' => 'Siti Nurhaliza', 'total_buku' => 33, 'kelas' => 'XII RPL A'],
['nama' => 'Andi Pratama', 'total_buku' => 30, 'kelas' => 'XII RPL B'],
['nama' => 'John Wick', 'total_buku' => 28, 'kelas' => 'XI TKJ'],
['nama' => 'Dewi Lestari', 'total_buku' => 25, 'kelas' => 'XII AKL'],
['nama' => 'Eko Prasetyo', 'total_buku' => 22, 'kelas' => 'XI MM'],
['nama' => 'Rina Marlina', 'total_buku' => 20, 'kelas' => 'XII TKJ A'],
['nama' => 'Budi Santoso', 'total_buku' => 18, 'kelas' => 'X OTKP'],
['nama' => 'Putri Amelia', 'total_buku' => 16, 'kelas' => 'XI RPL C'],
['nama' => 'Ahmad Jono', 'total_buku' => 12, 'kelas' => 'X TKJ B'],
];
}
/**
* Data dummy untuk halaman Laporan Minat Baca khusus Guru.
*/
public static function getLaporanMinatBaca(): array
{
return [
'buku_terpopuler' => [
['judul' => 'Modul Ajar IPAS', 'penulis' => 'Tim Kemdikbud Ristek', 'total_pembaca' => 125, 'cover' => 'images/covers/ipas.jpg'],
['judul' => 'Ayah', 'penulis' => 'Andrea Hirata', 'total_pembaca' => 98, 'cover' => 'images/covers/ayah.png'],
['judul' => 'Si Anak Pintar', 'penulis' => 'Tere Liye', 'total_pembaca' => 92, 'cover' => 'images/covers/sianakpintar.jpg'],
],
'kategori_populer' => [
['nama' => 'Sains', 'total_pembaca' => 230, 'trend' => 'naik', 'icon' => 'bi-arrow-up-right'],
['nama' => 'Fiksi', 'total_pembaca' => 190, 'trend' => 'stabil', 'icon' => 'bi-arrow-right'],
['nama' => 'Pendidikan', 'total_pembaca' => 150, 'trend' => 'turun', 'icon' => 'bi-arrow-down-right'],
['nama' => 'Novel', 'total_pembaca' => 110, 'trend' => 'naik', 'icon' => 'bi-arrow-up-right'],
],
'insight' => 'Siswa menunjukkan minat baca tertinggi pada kategori Sains dan Fiksi. Buku-buku karangan Tere Liye dan Andrea Hirata masih menjadi favorit.',
];
}
/**
* Data dummy untuk Halaman Dashboard Statistik Petugas Perpus
*/
public static function getAdminDashboardStats(): array
{
$allBooks = self::getAllBooks();
$allUsers = self::getAllSiswa();
$bukuDipinjam = $allBooks->filter(fn($buku) => $buku['status'] === 'Dipinjam')->count();
return [
['label' => 'Total Buku', 'value' => $allBooks->count(), 'icon' => 'bi-journal-bookmark-fill', 'color' => 'primary'],
['label' => 'Total Anggota', 'value' => count($allUsers), 'icon' => 'bi-people-fill', 'color' => 'success'],
['label' => 'Buku Dipinjam', 'value' => $bukuDipinjam, 'icon' => 'bi-arrow-up-right-circle-fill', 'color' => 'warning'],
['label' => 'Denda Menunggu', 'value' => 0, 'icon' => 'bi-cash-coin', 'color' => 'danger'],
];
}
/**
* Data untuk bar chart di dashboard admin (total peminjaman per bulan).
*/
public static function getStatistikPeminjamanAdmin(): array
{
return [
'labels' => ['Jan', 'Feb', 'Mar', 'Apr', 'Mei', 'Jun', 'Jul'],
'data' => [65, 59, 80, 81, 56, 55, 70],
];
}
/**
* Data untuk donut chart di dashboard admin (komposisi buku).
*/
public static function getKomposisiBukuAdmin(): array
{
$allBooks = self::getAllBooks();
return [
'tersedia' => $allBooks->where('status', 'Tersedia')->count(),
'dipinjam' => $allBooks->where('status', 'Dipinjam')->count(),
];
}
/**
* Data untuk tabel aktivitas terakhir di dashboard admin.
*/
public static function getAktivitasTerakhir(): array
{
return [
['nama' => 'Silvi Rahmawati', 'judul_buku' => 'Perahu Kertas', 'tipe' => 'Peminjaman', 'waktu' => '5 menit yang lalu', 'status' => 'Dipinjam'],
['nama' => 'Andi Pratama', 'judul_buku' => 'The Last Spell Breather', 'tipe' => 'Pengembalian', 'waktu' => '1 jam yang lalu', 'status' => 'Dikembalikan'],
['nama' => 'Siti Nurhaliza', 'judul_buku' => 'Ayah', 'tipe' => 'Baca Online', 'waktu' => '3 jam yang lalu', 'status' => 'Selesai'],
['nama' => 'Rina Marlina', 'judul_buku' => 'Modul Ajar IPAS', 'tipe' => 'Peminjaman', 'waktu' => 'Kemarin', 'status' => 'Dipinjam'],
];
}
/**
* Data untuk halaman Dashboard Siswa dan Guru dengan warna spesifik.
*/
public static function getDashboardStats(): array
{
return [
['label' => 'Buku yang dipinjam', 'value' => 3, 'icon' => 'bi-book-half', 'color' => 'primary'],
['label' => 'Tenggat Waktu', 'value' => '2', 'icon' => 'bi-clock-history', 'color' => 'danger'],
['label' => 'Buku dikembalikan', 'value' => 12, 'icon' => 'bi-check-circle', 'color' => 'success'],
['label' => 'History Baca', 'value' => 15, 'icon' => 'bi-hourglass-split', 'color' => 'warning'],
];
}
/**
* Data untuk pengumuman
*/
public static function getPengumuman(): array
{
$pengumuman = [
['id' => 1, 'type' => 'warning', 'icon' => 'bi-exclamation-triangle-fill', 'title' => 'Perpustakaan Tutup', 'content' => 'Perpustakaan akan tutup pada tanggal 25 Desember untuk perayaan Natal.'],
['id' => 2, 'type' => 'info', 'icon' => 'bi-info-circle-fill', 'title' => 'Buku Baru Tersedia', 'content' => 'Edisi baru telah ditambahkan ke koleksi perpustakaan digital.'],
];
// Buat 30 data dummy tambahan dengan 'id'
for ($i = 3; $i <= 32; $i++) {
$pengumuman[] = ['id' => $i, 'type' => 'secondary', 'icon' => 'bi-megaphone-fill', 'title' => "Pengumuman Biasa #{$i}", 'content' => "Ini adalah isi dari pengumuman rutin nomor {$i}."];
}
return $pengumuman;
}
/**
* Data untuk pemberitahuan
*/
public static function getPemberitahuan(): array
{
$pemberitahuan = [
['type' => 'danger', 'icon' => 'bi-exclamation-octagon', 'title' => 'Buku Akan Jatuh Tempo Besok', 'content' => 'Sejarah Indonesia Modern', 'badge' => 'Segera!'],
['type' => 'success', 'icon' => 'bi-check2-circle', 'title' => 'Peminjaman Berhasil', 'content' => 'Buku Kimia Dasar Berhasil Dipinjam', 'badge' => 'Baru'],
];
// Buat 20 data dummy tambahan
for ($i = 1; $i <= 20; $i++) {
$pemberitahuan[] = ['type' => 'info', 'icon' => 'bi-bell-fill', 'title' => "Notifikasi Sistem #{$i}", 'content' => "Pemberitahuan sistem terjadwal nomor {$i}.", 'badge' => 'Info'];
}
return $pemberitahuan;
}
/**
* Data untuk progress membaca (donut chart)
*/
public static function getProgressMembaca(): array
{
return ['selesai' => 70, 'sisa' => 30];
}
/**
* Data untuk statistik bulanan (bar chart)
*/
public static function getStatistikBulanan(): array
{
return [
'labels' => ['Jan', 'Feb', 'Mar', 'Apr', 'Mei', 'Jun', 'Jul'],
'data' => [10, 15, 8, 20, 18, 25, 22],
];
}
/**
* Master list untuk semua buku
* @return \Illuminate\Support\Collection
*/
public static function getAllBooks()
{
return collect([
// --- BUKU MILIK USER 1 (SILVI) ---
[
'id' => 1,
'judul' => 'Modul Ajar IPAS',
'penulis' => 'Tim Kemdikbud Ristek',
'cover' => 'images/covers/ipas.jpg',
'kode_buku' => '510',
'kategori' => 'Sains',
'tahun' => 2022,
'status' => 'Dipinjam',
'is_new' => true,
'tipe_akses' => ['online', 'offline'],
'sisa_hari' => -5,
'user_id' => 1,
],
[
'id' => 2,
'judul' => 'Perahu Kertas',
'penulis' => 'Dewi Lestari',
'cover' => 'images/covers/ayah.png',
'kode_buku' => '844',
'kategori' => 'Fiksi',
'tahun' => 2012,
'status' => 'Dipinjam',
'is_new' => false,
'tipe_akses' => 'offline',
'sisa_hari' => 3,
'user_id' => 1,
],
// --- BUKU TERSEDIA (UNTUK CEK PEMINJAMAN BARU) ---
[
'id' => 3,
'judul' => 'Si Anak Pintar',
'penulis' => 'Tere Liye',
'cover' => 'images/covers/sianakpintar.jpg',
'kode_buku' => '843',
'kategori' => 'Fiksi',
'tahun' => 2018,
'status' => 'Tersedia',
'is_new' => true,
'tipe_akses' => 'offline',
'sisa_hari' => 0,
'user_id' => null,
],
[
'id' => 4,
'judul' => 'Laskar Pelangi',
'penulis' => 'Andrea Hirata',
'cover' => 'https://upload.wikimedia.org/wikipedia/id/8/8e/Laskar_pelangi_sampul.jpg',
'kode_buku' => 'NOV-001',
'kategori' => 'Novel',
'tahun' => 2005,
'status' => 'Tersedia',
'is_new' => false,
'tipe_akses' => 'offline',
'sisa_hari' => 0,
'user_id' => null,
],
[
'id' => 5,
'judul' => 'Filosofi Teras',
'penulis' => 'Henry Manampiring',
'cover' => 'https://upload.wikimedia.org/wikipedia/id/3/36/Filosofi_Teras.jpg',
'kode_buku' => 'PSI-002',
'kategori' => 'Psikologi',
'tahun' => 2018,
'status' => 'Tersedia',
'is_new' => true,
'tipe_akses' => 'offline',
'sisa_hari' => 0,
'user_id' => null,
],
[
'id' => 6,
'judul' => 'Atomic Habits',
'penulis' => 'James Clear',
'cover' => 'https://images-na.ssl-images-amazon.com/images/I/91bYsX41DVL.jpg',
'kode_buku' => 'SELF-003',
'kategori' => 'Refleksi Diri',
'tahun' => 2018,
'status' => 'Tersedia',
'is_new' => true,
'tipe_akses' => ['offline', 'online'],
'sisa_hari' => 0,
'user_id' => null,
],
[
'id' => 7,
'judul' => 'Bumi Manusia',
'penulis' => 'Pramoedya Ananta Toer',
'cover' => 'https://upload.wikimedia.org/wikipedia/id/4/44/Bumi_Manusia.jpg',
'kode_buku' => 'SAS-004',
'kategori' => 'Sastra',
'tahun' => 1980,
'status' => 'Tersedia',
'is_new' => false,
'tipe_akses' => 'offline',
'sisa_hari' => 0,
'user_id' => null,
],
[
'id' => 8,
'judul' => 'Laut Bercerita',
'penulis' => 'Leila S. Chudori',
'cover' => 'https://upload.wikimedia.org/wikipedia/id/6/6d/Laut_Bercerita.jpeg',
'kode_buku' => 'NOV-005',
'kategori' => 'Novel',
'tahun' => 2017,
'status' => 'Tersedia',
'is_new' => true,
'tipe_akses' => 'offline',
'sisa_hari' => 0,
'user_id' => null,
],
// --- BUKU MILIK USER 3 (SITI) - TELAT ---
[
'id' => 99,
'judul' => 'Seni Berbicara',
'penulis' => 'Larry King',
'cover' => 'https://via.placeholder.com/150',
'kode_buku' => 'COM-001',
'kategori' => 'Refleksi Diri',
'tahun' => 2019,
'status' => 'Dipinjam',
'is_new' => false,
'tipe_akses' => 'offline',
'sisa_hari' => -2,
'user_id' => 3,
],
// --- BUKU MILIK GURU (USER 5) - TESTING MANUAL BAN ---
[
'id' => 88,
'judul' => 'Strategi Pembelajaran Abad 21',
'penulis' => 'Prof. Dr. Pendidikan',
'cover' => 'https://via.placeholder.com/150',
'kode_buku' => 'GURU-001',
'kategori' => 'Pendidikan',
'tahun' => 2020,
'status' => 'Dipinjam',
'is_new' => false,
'tipe_akses' => 'offline',
'sisa_hari' => -3,
'user_id' => 5,
],
]);
}
/**
* Data untuk buku pinjam offline
*/
public static function getBukuPinjamOffline($user): array
{
return self::getAllBooks()
->filter(function ($buku) {
// Handle tipe akses string atau array
if (is_array($buku['tipe_akses'])) {
return in_array('offline', $buku['tipe_akses']);
}
return $buku['tipe_akses'] === 'offline';
})
->filter(function ($buku) use ($user) {
if (!isset($buku['user_id']) || $buku['user_id'] === null)
return false;
if (is_array($buku['user_id'])) {
return in_array($user->id, $buku['user_id']);
}
return $buku['user_id'] == $user->id;
})
->map(fn($buku) => [
'judul' => $buku['judul'],
'penulis' => $buku['penulis'],
'sisa_hari' => $buku['sisa_hari'],
'cover' => $buku['cover'],
])
->values()
->all();
}
/**
* Data untuk baca buku online
*/
public static function getBacaBukuOnline($user): array
{
return self::getAllBooks()
->where('tipe_akses', 'online')
->filter(function ($buku) use ($user) {
if (!isset($buku['user_id']))
return false;
if (is_array($buku['user_id'])) {
return in_array($user->id, $buku['user_id']);
}
return $buku['user_id'] == $user->id;
})
->map(fn($buku) => [
'judul' => $buku['judul'],
'penulis' => $buku['penulis'],
'progress' => $buku['progress'],
'cover' => $buku['cover'],
])
->values()
->all();
}
/**
* Mengambil daftar buku untuk katalog dengan filter.
*/
public static function getKatalogBuku(array $filters = []): \Illuminate\Support\Collection
{
$buku = self::getAllBooks();
$buku = $buku->when($filters['search'] ?? null, function ($query, $search) {
return $query->filter(fn($item) => str_contains(strtolower($item['judul']), strtolower($search)));
})->when($filters['kategori'] ?? null, function ($query, $kategori) {
return $query->where('kategori', $kategori);
})->when($filters['tahun'] ?? null, function ($query, $tahun) {
return $query->where('tahun', $tahun);
})->when($filters['penulis'] ?? null, function ($query, $penulis) {
return $query->where('penulis', $penulis);
})
->when($filters['tipe_akses'] ?? null, function ($query, $tipe) {
if ($tipe === 'offline') {
return $query->filter(function ($buku) {
return $buku['tipe_akses'] === 'offline' || (is_array($buku['tipe_akses']) && in_array('offline', $buku['tipe_akses']));
});
}
if ($tipe === 'online') {
return $query->filter(function ($buku) {
return $buku['tipe_akses'] === 'online' || (is_array($buku['tipe_akses']) && in_array('online', $buku['tipe_akses']));
});
}
return $query;
})
->sortByDesc('status');
return $buku;
}
/**
* Method baru untuk mengambil daftar unik untuk dropdown filter
*/
public static function getFilterOptions(): array
{
$buku = self::getAllBooks();
return [
'kategori' => $buku->pluck('kategori')->unique()->sort()->values(),
'tahun' => $buku->pluck('tahun')->unique()->sortDesc()->values(),
'penulis' => $buku->pluck('penulis')->unique()->sort()->values(),
];
}
/**
* Data untuk riwayat peminjaman offline.
* Setiap item mewakili satu transaksi peminjaman.
*/
public static function getRiwayatOffline($user): array
{
$allBooks = self::getAllBooks();
$myBooks = $allBooks->filter(function ($buku) use ($user) {
if (is_array($buku['user_id'])) {
return in_array($user->id, $buku['user_id']);
}
return $buku['user_id'] == $user->id;
})->whereIn('status', ['Dipinjam', 'Dikembalikan', 'Terlambat']);
// Mapping ke format tampilan View
return $myBooks->map(function ($buku, $index) {
// Logika Tanggal Dummy
$tglPinjam = Carbon::now()->subDays(7);
// Hitung tanggal kembali berdasarkan sisa hari di Master Data
$tglKembali = Carbon::now()->addDays($buku['sisa_hari']);
return [
'id' => $index + 1,
'id_peminjaman' => 'PIN-' . date('Ym') . '-' . sprintf('%03d', $buku['id']),
'kode_buku' => $buku['kode_buku'],
'judul_utama' => $buku['judul'],
'tanggal_pinjam' => $tglPinjam->format('d/m/Y'),
'tanggal_kembali' => $tglKembali->format('d/m/Y'),
'status' => $buku['status'],
'books' => [
[
'id' => $buku['id'],
'judul' => $buku['judul'],
'kode_buku' => $buku['kode_buku'],
'cover' => $buku['cover'],
'deskripsi' => 'Deskripsi buku ' . $buku['judul'],
'kategori' => $buku['kategori'],
'tahun' => $buku['tahun'],
'keterangan' => ($buku['sisa_hari'] < 0) ? 'Buku Terlambat' : null,
]
]
];
})->values()->toArray();
}
/**
* Data untuk riwayat baca buku online.
*/
public static function getRiwayatOnline(): array
{
return [
[
'id' => 1,
'id_baca' => 'BCO-20240527-002',
'judul_buku' => 'Ayah',
'tanggal_akses' => '27/05/2024',
'status' => 'Selesai',
'books' => [
[
'id' => 9,
'judul' => 'Ayah',
'cover' => 'images/covers/ayah.png',
'deskripsi' => 'Novel yang mengisahkan perjuangan dan kasih sayang seorang ayah.',
'kategori' => 'Novel',
'tahun' => 2015,
'keterangan' => null
]
]
],
];
}
/**
* Data untuk notifikasi pengguna.
* @param \App\Models\User $user Pengguna yang sedang login.
* @return array Daftar notifikasi.
*/
public static function getNotifikasiForUser($user): array
{
$notifikasi = [];
$allBooks = self::getAllBooks();
$myBooks = $allBooks->filter(function ($buku) use ($user) {
if (!isset($buku['user_id']) || $buku['user_id'] === null) {
return false;
}
if (is_array($buku['user_id'])) {
return in_array($user->id, $buku['user_id']);
}
return $buku['user_id'] == $user->id;
});
foreach ($myBooks as $buku) {
// LOGIC TELAT
if ($buku['sisa_hari'] < 0 && $buku['status'] == 'Dipinjam') {
$hariTelat = abs($buku['sisa_hari']);
$denda = $hariTelat * 1000;
$notifikasi[] = [
'icon' => 'bi-exclamation-octagon-fill',
'color' => 'danger',
'title' => 'TERLAMBAT: ' . $buku['judul'],
'content' => "Telat {$hariTelat} hari. Denda: Rp " . number_format($denda, 0, ',', '.'),
'time' => 'Sekarang',
'read' => false,
'type' => 'denda_active',
'link_id' => null,
];
}
// LOGIC JATUH TEMPO
elseif ($buku['sisa_hari'] >= 0 && $buku['sisa_hari'] <= 3 && $buku['status'] == 'Dipinjam') {
$notifikasi[] = [
'icon' => 'bi-exclamation-triangle-fill',
'color' => 'warning',
'title' => 'Jatuh Tempo: ' . $buku['judul'],
'content' => "Sisa waktu tinggal " . $buku['sisa_hari'] . " hari lagi.",
'time' => 'Segera',
'read' => false,
'type' => 'warning_jatuh_tempo',
'link_id' => null,
];
}
}
// Notif Default
$notifikasi[] = [
'icon' => 'bi-info-circle-fill',
'color' => 'primary',
'title' => 'Selamat Datang di DigiPus!',
'content' => 'Silakan jelajahi koleksi buku terbaru kami.',
'time' => 'Baru saja',
'read' => true,
'type' => 'info',
'link_id' => null,
];
return $notifikasi;
}
}

View File

@ -0,0 +1,17 @@
<?php
namespace App\View\Components;
use Illuminate\View\Component;
use Illuminate\View\View;
class AppLayout extends Component
{
/**
* Get the view / contents that represents the component.
*/
public function render(): View
{
return view('layouts.app');
}
}

View File

@ -0,0 +1,17 @@
<?php
namespace App\View\Components;
use Illuminate\View\Component;
use Illuminate\View\View;
class GuestLayout extends Component
{
/**
* Get the view / contents that represents the component.
*/
public function render(): View
{
return view('layouts.guest');
}
}

18
artisan Normal file
View File

@ -0,0 +1,18 @@
#!/usr/bin/env php
<?php
use Illuminate\Foundation\Application;
use Symfony\Component\Console\Input\ArgvInput;
define('LARAVEL_START', microtime(true));
// Register the Composer autoloader...
require __DIR__.'/vendor/autoload.php';
// Bootstrap Laravel and handle the command...
/** @var Application $app */
$app = require_once __DIR__.'/bootstrap/app.php';
$status = $app->handleCommand(new ArgvInput);
exit($status);

23
bootstrap/app.php Normal file
View File

@ -0,0 +1,23 @@
<?php
use Illuminate\Foundation\Application;
use Illuminate\Foundation\Configuration\Exceptions;
use Illuminate\Foundation\Configuration\Middleware;
return Application::configure(basePath: dirname(__DIR__))
->withRouting(
web: __DIR__ . '/../routes/web.php',
commands: __DIR__ . '/../routes/console.php',
health: '/up',
)
->withMiddleware(function (Middleware $middleware) {
$middleware->alias([
'role' => \App\Http\Middleware\CheckRole::class,
]);
})
->withProviders([
App\Providers\AuthServiceProvider::class,
])
->withExceptions(function (Exceptions $exceptions): void {
//
})->create();

2
bootstrap/cache/.gitignore vendored Normal file
View File

@ -0,0 +1,2 @@
*
!.gitignore

6
bootstrap/providers.php Normal file
View File

@ -0,0 +1,6 @@
<?php
return [
App\Providers\AppServiceProvider::class,
App\Providers\AuthServiceProvider::class,
];

80
composer.json Normal file
View File

@ -0,0 +1,80 @@
{
"$schema": "https://getcomposer.org/schema.json",
"name": "laravel/laravel",
"type": "project",
"description": "The skeleton application for the Laravel framework.",
"keywords": [
"laravel",
"framework"
],
"license": "MIT",
"require": {
"php": "^8.3",
"laravel/framework": "^12.0",
"laravel/tinker": "^2.10.1"
},
"require-dev": {
"fakerphp/faker": "^1.23",
"laravel/breeze": "^2.3",
"laravel/pail": "^1.2.2",
"laravel/pint": "^1.24",
"laravel/sail": "^1.41",
"mockery/mockery": "^1.6",
"nunomaduro/collision": "^8.6",
"pestphp/pest": "^4.1",
"pestphp/pest-plugin-laravel": "^4.0"
},
"autoload": {
"psr-4": {
"App\\": "app/",
"Database\\Factories\\": "database/factories/",
"Database\\Seeders\\": "database/seeders/"
}
},
"autoload-dev": {
"psr-4": {
"Tests\\": "tests/"
}
},
"scripts": {
"post-autoload-dump": [
"Illuminate\\Foundation\\ComposerScripts::postAutoloadDump",
"@php artisan package:discover --ansi"
],
"post-update-cmd": [
"@php artisan vendor:publish --tag=laravel-assets --ansi --force"
],
"post-root-package-install": [
"@php -r \"file_exists('.env') || copy('.env.example', '.env');\""
],
"post-create-project-cmd": [
"@php artisan key:generate --ansi",
"@php -r \"file_exists('database/database.sqlite') || touch('database/database.sqlite');\"",
"@php artisan migrate --graceful --ansi"
],
"dev": [
"Composer\\Config::disableProcessTimeout",
"npx concurrently -c \"#93c5fd,#c4b5fd,#fb7185,#fdba74\" \"php artisan serve\" \"php artisan queue:listen --tries=1\" \"php artisan pail --timeout=0\" \"npm run dev\" --names=server,queue,logs,vite --kill-others"
],
"test": [
"@php artisan config:clear --ansi",
"@php artisan test"
]
},
"extra": {
"laravel": {
"dont-discover": []
}
},
"config": {
"optimize-autoloader": true,
"preferred-install": "dist",
"sort-packages": true,
"allow-plugins": {
"pestphp/pest-plugin": true,
"php-http/discovery": true
}
},
"minimum-stability": "stable",
"prefer-stable": true
}

9435
composer.lock generated Normal file

File diff suppressed because it is too large Load Diff

126
config/app.php Normal file
View File

@ -0,0 +1,126 @@
<?php
return [
/*
|--------------------------------------------------------------------------
| Application Name
|--------------------------------------------------------------------------
|
| This value is the name of your application, which will be used when the
| framework needs to place the application's name in a notification or
| other UI elements where an application name needs to be displayed.
|
*/
'name' => env('APP_NAME', 'Laravel'),
/*
|--------------------------------------------------------------------------
| Application Environment
|--------------------------------------------------------------------------
|
| This value determines the "environment" your application is currently
| running in. This may determine how you prefer to configure various
| services the application utilizes. Set this in your ".env" file.
|
*/
'env' => env('APP_ENV', 'production'),
/*
|--------------------------------------------------------------------------
| Application Debug Mode
|--------------------------------------------------------------------------
|
| When your application is in debug mode, detailed error messages with
| stack traces will be shown on every error that occurs within your
| application. If disabled, a simple generic error page is shown.
|
*/
'debug' => (bool) env('APP_DEBUG', false),
/*
|--------------------------------------------------------------------------
| Application URL
|--------------------------------------------------------------------------
|
| This URL is used by the console to properly generate URLs when using
| the Artisan command line tool. You should set this to the root of
| the application so that it's available within Artisan commands.
|
*/
'url' => env('APP_URL', 'http://localhost'),
/*
|--------------------------------------------------------------------------
| Application Timezone
|--------------------------------------------------------------------------
|
| Here you may specify the default timezone for your application, which
| will be used by the PHP date and date-time functions. The timezone
| is set to "UTC" by default as it is suitable for most use cases.
|
*/
'timezone' => 'UTC',
/*
|--------------------------------------------------------------------------
| Application Locale Configuration
|--------------------------------------------------------------------------
|
| The application locale determines the default locale that will be used
| by Laravel's translation / localization methods. This option can be
| set to any locale for which you plan to have translation strings.
|
*/
'locale' => env('APP_LOCALE', 'en'),
'fallback_locale' => env('APP_FALLBACK_LOCALE', 'en'),
'faker_locale' => env('APP_FAKER_LOCALE', 'en_US'),
/*
|--------------------------------------------------------------------------
| Encryption Key
|--------------------------------------------------------------------------
|
| This key is utilized by Laravel's encryption services and should be set
| to a random, 32 character string to ensure that all encrypted values
| are secure. You should do this prior to deploying the application.
|
*/
'cipher' => 'AES-256-CBC',
'key' => env('APP_KEY'),
'previous_keys' => [
...array_filter(
explode(',', (string) env('APP_PREVIOUS_KEYS', ''))
),
],
/*
|--------------------------------------------------------------------------
| Maintenance Mode Driver
|--------------------------------------------------------------------------
|
| These configuration options determine the driver used to determine and
| manage Laravel's "maintenance mode" status. The "cache" driver will
| allow maintenance mode to be controlled across multiple machines.
|
| Supported drivers: "file", "cache"
|
*/
'maintenance' => [
'driver' => env('APP_MAINTENANCE_DRIVER', 'file'),
'store' => env('APP_MAINTENANCE_STORE', 'database'),
],
];

110
config/auth.php Normal file
View File

@ -0,0 +1,110 @@
<?php
return [
/*
|--------------------------------------------------------------------------
| Authentication Defaults
|--------------------------------------------------------------------------
|
| This option defines the default authentication "guard" and password
| reset "broker" for your application. You may change these values
| as required, but they're a perfect start for most applications.
|
*/
'defaults' => [
'guard' => env('AUTH_GUARD', 'web'),
'passwords' => env('AUTH_PASSWORD_BROKER', 'users'),
],
/*
|--------------------------------------------------------------------------
| Authentication Guards
|--------------------------------------------------------------------------
|
| Next, you may define every authentication guard for your application.
| Of course, a great default configuration has been defined for you
| which utilizes session storage plus the Eloquent user provider.
|
| All authentication guards have a user provider, which defines how the
| users are actually retrieved out of your database or other storage
| system used by the application. Typically, Eloquent is utilized.
|
| Supported: "session"
|
*/
'guards' => [
'web' => [
'driver' => 'session',
'provider' => 'users',
],
],
/*
|--------------------------------------------------------------------------
| User Providers
|--------------------------------------------------------------------------
|
| All authentication guards have a user provider, which defines how the
| users are actually retrieved out of your database or other storage
| system used by the application. Typically, Eloquent is utilized.
|
| If you have multiple user tables or models you may configure multiple
| providers to represent the model / table. These providers may then
| be assigned to any extra authentication guards you have defined.
|
| Supported: "database", "eloquent"
|
*/
'providers' => [
'users' => [
'driver' => 'eloquent',
'model' => env('AUTH_MODEL', App\Models\User::class),
],
],
/*
|--------------------------------------------------------------------------
| Resetting Passwords
|--------------------------------------------------------------------------
|
| These configuration options specify the behavior of Laravel's password
| reset functionality, including the table utilized for token storage
| and the user provider that is invoked to actually retrieve users.
|
| The expiry time is the number of minutes that each reset token will be
| considered valid. This security feature keeps tokens short-lived so
| they have less time to be guessed. You may change this as needed.
|
| The throttle setting is the number of seconds a user must wait before
| generating more password reset tokens. This prevents the user from
| quickly generating a very large amount of password reset tokens.
|
*/
'passwords' => [
'users' => [
'provider' => 'users',
'table' => env('AUTH_PASSWORD_RESET_TOKEN_TABLE', 'password_reset_tokens'),
'expire' => 60,
'throttle' => 60,
],
],
/*
|--------------------------------------------------------------------------
| Password Confirmation Timeout
|--------------------------------------------------------------------------
|
| Here you may define the number of seconds before a password confirmation
| window expires and users are asked to re-enter their password via the
| confirmation screen. By default, the timeout lasts for three hours.
|
*/
'password_timeout' => env('AUTH_PASSWORD_TIMEOUT', 10800),
];

108
config/cache.php Normal file
View File

@ -0,0 +1,108 @@
<?php
use Illuminate\Support\Str;
return [
/*
|--------------------------------------------------------------------------
| Default Cache Store
|--------------------------------------------------------------------------
|
| This option controls the default cache store that will be used by the
| framework. This connection is utilized if another isn't explicitly
| specified when running a cache operation inside the application.
|
*/
'default' => env('CACHE_STORE', 'database'),
/*
|--------------------------------------------------------------------------
| Cache Stores
|--------------------------------------------------------------------------
|
| Here you may define all of the cache "stores" for your application as
| well as their drivers. You may even define multiple stores for the
| same cache driver to group types of items stored in your caches.
|
| Supported drivers: "array", "database", "file", "memcached",
| "redis", "dynamodb", "octane", "null"
|
*/
'stores' => [
'array' => [
'driver' => 'array',
'serialize' => false,
],
'database' => [
'driver' => 'database',
'connection' => env('DB_CACHE_CONNECTION'),
'table' => env('DB_CACHE_TABLE', 'cache'),
'lock_connection' => env('DB_CACHE_LOCK_CONNECTION'),
'lock_table' => env('DB_CACHE_LOCK_TABLE'),
],
'file' => [
'driver' => 'file',
'path' => storage_path('framework/cache/data'),
'lock_path' => storage_path('framework/cache/data'),
],
'memcached' => [
'driver' => 'memcached',
'persistent_id' => env('MEMCACHED_PERSISTENT_ID'),
'sasl' => [
env('MEMCACHED_USERNAME'),
env('MEMCACHED_PASSWORD'),
],
'options' => [
// Memcached::OPT_CONNECT_TIMEOUT => 2000,
],
'servers' => [
[
'host' => env('MEMCACHED_HOST', '127.0.0.1'),
'port' => env('MEMCACHED_PORT', 11211),
'weight' => 100,
],
],
],
'redis' => [
'driver' => 'redis',
'connection' => env('REDIS_CACHE_CONNECTION', 'cache'),
'lock_connection' => env('REDIS_CACHE_LOCK_CONNECTION', 'default'),
],
'dynamodb' => [
'driver' => 'dynamodb',
'key' => env('AWS_ACCESS_KEY_ID'),
'secret' => env('AWS_SECRET_ACCESS_KEY'),
'region' => env('AWS_DEFAULT_REGION', 'us-east-1'),
'table' => env('DYNAMODB_CACHE_TABLE', 'cache'),
'endpoint' => env('DYNAMODB_ENDPOINT'),
],
'octane' => [
'driver' => 'octane',
],
],
/*
|--------------------------------------------------------------------------
| Cache Key Prefix
|--------------------------------------------------------------------------
|
| When utilizing the APC, database, memcached, Redis, and DynamoDB cache
| stores, there might be other applications using the same cache. For
| that reason, you may prefix every cache key to avoid collisions.
|
*/
'prefix' => env('CACHE_PREFIX', Str::slug((string) env('APP_NAME', 'laravel')).'-cache-'),
];

183
config/database.php Normal file
View File

@ -0,0 +1,183 @@
<?php
use Illuminate\Support\Str;
return [
/*
|--------------------------------------------------------------------------
| Default Database Connection Name
|--------------------------------------------------------------------------
|
| Here you may specify which of the database connections below you wish
| to use as your default connection for database operations. This is
| the connection which will be utilized unless another connection
| is explicitly specified when you execute a query / statement.
|
*/
'default' => env('DB_CONNECTION', 'sqlite'),
/*
|--------------------------------------------------------------------------
| Database Connections
|--------------------------------------------------------------------------
|
| Below are all of the database connections defined for your application.
| An example configuration is provided for each database system which
| is supported by Laravel. You're free to add / remove connections.
|
*/
'connections' => [
'sqlite' => [
'driver' => 'sqlite',
'url' => env('DB_URL'),
'database' => env('DB_DATABASE', database_path('database.sqlite')),
'prefix' => '',
'foreign_key_constraints' => env('DB_FOREIGN_KEYS', true),
'busy_timeout' => null,
'journal_mode' => null,
'synchronous' => null,
'transaction_mode' => 'DEFERRED',
],
'mysql' => [
'driver' => 'mysql',
'url' => env('DB_URL'),
'host' => env('DB_HOST', '127.0.0.1'),
'port' => env('DB_PORT', '3306'),
'database' => env('DB_DATABASE', 'laravel'),
'username' => env('DB_USERNAME', 'root'),
'password' => env('DB_PASSWORD', ''),
'unix_socket' => env('DB_SOCKET', ''),
'charset' => env('DB_CHARSET', 'utf8mb4'),
'collation' => env('DB_COLLATION', 'utf8mb4_unicode_ci'),
'prefix' => '',
'prefix_indexes' => true,
'strict' => true,
'engine' => null,
'options' => extension_loaded('pdo_mysql') ? array_filter([
PDO::MYSQL_ATTR_SSL_CA => env('MYSQL_ATTR_SSL_CA'),
]) : [],
],
'mariadb' => [
'driver' => 'mariadb',
'url' => env('DB_URL'),
'host' => env('DB_HOST', '127.0.0.1'),
'port' => env('DB_PORT', '3306'),
'database' => env('DB_DATABASE', 'laravel'),
'username' => env('DB_USERNAME', 'root'),
'password' => env('DB_PASSWORD', ''),
'unix_socket' => env('DB_SOCKET', ''),
'charset' => env('DB_CHARSET', 'utf8mb4'),
'collation' => env('DB_COLLATION', 'utf8mb4_unicode_ci'),
'prefix' => '',
'prefix_indexes' => true,
'strict' => true,
'engine' => null,
'options' => extension_loaded('pdo_mysql') ? array_filter([
PDO::MYSQL_ATTR_SSL_CA => env('MYSQL_ATTR_SSL_CA'),
]) : [],
],
'pgsql' => [
'driver' => 'pgsql',
'url' => env('DB_URL'),
'host' => env('DB_HOST', '127.0.0.1'),
'port' => env('DB_PORT', '5432'),
'database' => env('DB_DATABASE', 'laravel'),
'username' => env('DB_USERNAME', 'root'),
'password' => env('DB_PASSWORD', ''),
'charset' => env('DB_CHARSET', 'utf8'),
'prefix' => '',
'prefix_indexes' => true,
'search_path' => 'public',
'sslmode' => 'prefer',
],
'sqlsrv' => [
'driver' => 'sqlsrv',
'url' => env('DB_URL'),
'host' => env('DB_HOST', 'localhost'),
'port' => env('DB_PORT', '1433'),
'database' => env('DB_DATABASE', 'laravel'),
'username' => env('DB_USERNAME', 'root'),
'password' => env('DB_PASSWORD', ''),
'charset' => env('DB_CHARSET', 'utf8'),
'prefix' => '',
'prefix_indexes' => true,
// 'encrypt' => env('DB_ENCRYPT', 'yes'),
// 'trust_server_certificate' => env('DB_TRUST_SERVER_CERTIFICATE', 'false'),
],
],
/*
|--------------------------------------------------------------------------
| Migration Repository Table
|--------------------------------------------------------------------------
|
| This table keeps track of all the migrations that have already run for
| your application. Using this information, we can determine which of
| the migrations on disk haven't actually been run on the database.
|
*/
'migrations' => [
'table' => 'migrations',
'update_date_on_publish' => true,
],
/*
|--------------------------------------------------------------------------
| Redis Databases
|--------------------------------------------------------------------------
|
| Redis is an open source, fast, and advanced key-value store that also
| provides a richer body of commands than a typical key-value system
| such as Memcached. You may define your connection settings here.
|
*/
'redis' => [
'client' => env('REDIS_CLIENT', 'phpredis'),
'options' => [
'cluster' => env('REDIS_CLUSTER', 'redis'),
'prefix' => env('REDIS_PREFIX', Str::slug((string) env('APP_NAME', 'laravel')).'-database-'),
'persistent' => env('REDIS_PERSISTENT', false),
],
'default' => [
'url' => env('REDIS_URL'),
'host' => env('REDIS_HOST', '127.0.0.1'),
'username' => env('REDIS_USERNAME'),
'password' => env('REDIS_PASSWORD'),
'port' => env('REDIS_PORT', '6379'),
'database' => env('REDIS_DB', '0'),
'max_retries' => env('REDIS_MAX_RETRIES', 3),
'backoff_algorithm' => env('REDIS_BACKOFF_ALGORITHM', 'decorrelated_jitter'),
'backoff_base' => env('REDIS_BACKOFF_BASE', 100),
'backoff_cap' => env('REDIS_BACKOFF_CAP', 1000),
],
'cache' => [
'url' => env('REDIS_URL'),
'host' => env('REDIS_HOST', '127.0.0.1'),
'username' => env('REDIS_USERNAME'),
'password' => env('REDIS_PASSWORD'),
'port' => env('REDIS_PORT', '6379'),
'database' => env('REDIS_CACHE_DB', '1'),
'max_retries' => env('REDIS_MAX_RETRIES', 3),
'backoff_algorithm' => env('REDIS_BACKOFF_ALGORITHM', 'decorrelated_jitter'),
'backoff_base' => env('REDIS_BACKOFF_BASE', 100),
'backoff_cap' => env('REDIS_BACKOFF_CAP', 1000),
],
],
];

80
config/filesystems.php Normal file
View File

@ -0,0 +1,80 @@
<?php
return [
/*
|--------------------------------------------------------------------------
| Default Filesystem Disk
|--------------------------------------------------------------------------
|
| Here you may specify the default filesystem disk that should be used
| by the framework. The "local" disk, as well as a variety of cloud
| based disks are available to your application for file storage.
|
*/
'default' => env('FILESYSTEM_DISK', 'local'),
/*
|--------------------------------------------------------------------------
| Filesystem Disks
|--------------------------------------------------------------------------
|
| Below you may configure as many filesystem disks as necessary, and you
| may even configure multiple disks for the same driver. Examples for
| most supported storage drivers are configured here for reference.
|
| Supported drivers: "local", "ftp", "sftp", "s3"
|
*/
'disks' => [
'local' => [
'driver' => 'local',
'root' => storage_path('app/private'),
'serve' => true,
'throw' => false,
'report' => false,
],
'public' => [
'driver' => 'local',
'root' => storage_path('app/public'),
'url' => env('APP_URL').'/storage',
'visibility' => 'public',
'throw' => false,
'report' => false,
],
's3' => [
'driver' => 's3',
'key' => env('AWS_ACCESS_KEY_ID'),
'secret' => env('AWS_SECRET_ACCESS_KEY'),
'region' => env('AWS_DEFAULT_REGION'),
'bucket' => env('AWS_BUCKET'),
'url' => env('AWS_URL'),
'endpoint' => env('AWS_ENDPOINT'),
'use_path_style_endpoint' => env('AWS_USE_PATH_STYLE_ENDPOINT', false),
'throw' => false,
'report' => false,
],
],
/*
|--------------------------------------------------------------------------
| Symbolic Links
|--------------------------------------------------------------------------
|
| Here you may configure the symbolic links that will be created when the
| `storage:link` Artisan command is executed. The array keys should be
| the locations of the links and the values should be their targets.
|
*/
'links' => [
public_path('storage') => storage_path('app/public'),
],
];

132
config/logging.php Normal file
View File

@ -0,0 +1,132 @@
<?php
use Monolog\Handler\NullHandler;
use Monolog\Handler\StreamHandler;
use Monolog\Handler\SyslogUdpHandler;
use Monolog\Processor\PsrLogMessageProcessor;
return [
/*
|--------------------------------------------------------------------------
| Default Log Channel
|--------------------------------------------------------------------------
|
| This option defines the default log channel that is utilized to write
| messages to your logs. The value provided here should match one of
| the channels present in the list of "channels" configured below.
|
*/
'default' => env('LOG_CHANNEL', 'stack'),
/*
|--------------------------------------------------------------------------
| Deprecations Log Channel
|--------------------------------------------------------------------------
|
| This option controls the log channel that should be used to log warnings
| regarding deprecated PHP and library features. This allows you to get
| your application ready for upcoming major versions of dependencies.
|
*/
'deprecations' => [
'channel' => env('LOG_DEPRECATIONS_CHANNEL', 'null'),
'trace' => env('LOG_DEPRECATIONS_TRACE', false),
],
/*
|--------------------------------------------------------------------------
| Log Channels
|--------------------------------------------------------------------------
|
| Here you may configure the log channels for your application. Laravel
| utilizes the Monolog PHP logging library, which includes a variety
| of powerful log handlers and formatters that you're free to use.
|
| Available drivers: "single", "daily", "slack", "syslog",
| "errorlog", "monolog", "custom", "stack"
|
*/
'channels' => [
'stack' => [
'driver' => 'stack',
'channels' => explode(',', (string) env('LOG_STACK', 'single')),
'ignore_exceptions' => false,
],
'single' => [
'driver' => 'single',
'path' => storage_path('logs/laravel.log'),
'level' => env('LOG_LEVEL', 'debug'),
'replace_placeholders' => true,
],
'daily' => [
'driver' => 'daily',
'path' => storage_path('logs/laravel.log'),
'level' => env('LOG_LEVEL', 'debug'),
'days' => env('LOG_DAILY_DAYS', 14),
'replace_placeholders' => true,
],
'slack' => [
'driver' => 'slack',
'url' => env('LOG_SLACK_WEBHOOK_URL'),
'username' => env('LOG_SLACK_USERNAME', 'Laravel Log'),
'emoji' => env('LOG_SLACK_EMOJI', ':boom:'),
'level' => env('LOG_LEVEL', 'critical'),
'replace_placeholders' => true,
],
'papertrail' => [
'driver' => 'monolog',
'level' => env('LOG_LEVEL', 'debug'),
'handler' => env('LOG_PAPERTRAIL_HANDLER', SyslogUdpHandler::class),
'handler_with' => [
'host' => env('PAPERTRAIL_URL'),
'port' => env('PAPERTRAIL_PORT'),
'connectionString' => 'tls://'.env('PAPERTRAIL_URL').':'.env('PAPERTRAIL_PORT'),
],
'processors' => [PsrLogMessageProcessor::class],
],
'stderr' => [
'driver' => 'monolog',
'level' => env('LOG_LEVEL', 'debug'),
'handler' => StreamHandler::class,
'handler_with' => [
'stream' => 'php://stderr',
],
'formatter' => env('LOG_STDERR_FORMATTER'),
'processors' => [PsrLogMessageProcessor::class],
],
'syslog' => [
'driver' => 'syslog',
'level' => env('LOG_LEVEL', 'debug'),
'facility' => env('LOG_SYSLOG_FACILITY', LOG_USER),
'replace_placeholders' => true,
],
'errorlog' => [
'driver' => 'errorlog',
'level' => env('LOG_LEVEL', 'debug'),
'replace_placeholders' => true,
],
'null' => [
'driver' => 'monolog',
'handler' => NullHandler::class,
],
'emergency' => [
'path' => storage_path('logs/laravel.log'),
],
],
];

118
config/mail.php Normal file
View File

@ -0,0 +1,118 @@
<?php
return [
/*
|--------------------------------------------------------------------------
| Default Mailer
|--------------------------------------------------------------------------
|
| This option controls the default mailer that is used to send all email
| messages unless another mailer is explicitly specified when sending
| the message. All additional mailers can be configured within the
| "mailers" array. Examples of each type of mailer are provided.
|
*/
'default' => env('MAIL_MAILER', 'log'),
/*
|--------------------------------------------------------------------------
| Mailer Configurations
|--------------------------------------------------------------------------
|
| Here you may configure all of the mailers used by your application plus
| their respective settings. Several examples have been configured for
| you and you are free to add your own as your application requires.
|
| Laravel supports a variety of mail "transport" drivers that can be used
| when delivering an email. You may specify which one you're using for
| your mailers below. You may also add additional mailers if needed.
|
| Supported: "smtp", "sendmail", "mailgun", "ses", "ses-v2",
| "postmark", "resend", "log", "array",
| "failover", "roundrobin"
|
*/
'mailers' => [
'smtp' => [
'transport' => 'smtp',
'scheme' => env('MAIL_SCHEME'),
'url' => env('MAIL_URL'),
'host' => env('MAIL_HOST', '127.0.0.1'),
'port' => env('MAIL_PORT', 2525),
'username' => env('MAIL_USERNAME'),
'password' => env('MAIL_PASSWORD'),
'timeout' => null,
'local_domain' => env('MAIL_EHLO_DOMAIN', parse_url((string) env('APP_URL', 'http://localhost'), PHP_URL_HOST)),
],
'ses' => [
'transport' => 'ses',
],
'postmark' => [
'transport' => 'postmark',
// 'message_stream_id' => env('POSTMARK_MESSAGE_STREAM_ID'),
// 'client' => [
// 'timeout' => 5,
// ],
],
'resend' => [
'transport' => 'resend',
],
'sendmail' => [
'transport' => 'sendmail',
'path' => env('MAIL_SENDMAIL_PATH', '/usr/sbin/sendmail -bs -i'),
],
'log' => [
'transport' => 'log',
'channel' => env('MAIL_LOG_CHANNEL'),
],
'array' => [
'transport' => 'array',
],
'failover' => [
'transport' => 'failover',
'mailers' => [
'smtp',
'log',
],
'retry_after' => 60,
],
'roundrobin' => [
'transport' => 'roundrobin',
'mailers' => [
'ses',
'postmark',
],
'retry_after' => 60,
],
],
/*
|--------------------------------------------------------------------------
| Global "From" Address
|--------------------------------------------------------------------------
|
| You may wish for all emails sent by your application to be sent from
| the same address. Here you may specify a name and address that is
| used globally for all emails that are sent by your application.
|
*/
'from' => [
'address' => env('MAIL_FROM_ADDRESS', 'hello@example.com'),
'name' => env('MAIL_FROM_NAME', 'Example'),
],
];

112
config/queue.php Normal file
View File

@ -0,0 +1,112 @@
<?php
return [
/*
|--------------------------------------------------------------------------
| Default Queue Connection Name
|--------------------------------------------------------------------------
|
| Laravel's queue supports a variety of backends via a single, unified
| API, giving you convenient access to each backend using identical
| syntax for each. The default queue connection is defined below.
|
*/
'default' => env('QUEUE_CONNECTION', 'database'),
/*
|--------------------------------------------------------------------------
| Queue Connections
|--------------------------------------------------------------------------
|
| Here you may configure the connection options for every queue backend
| used by your application. An example configuration is provided for
| each backend supported by Laravel. You're also free to add more.
|
| Drivers: "sync", "database", "beanstalkd", "sqs", "redis", "null"
|
*/
'connections' => [
'sync' => [
'driver' => 'sync',
],
'database' => [
'driver' => 'database',
'connection' => env('DB_QUEUE_CONNECTION'),
'table' => env('DB_QUEUE_TABLE', 'jobs'),
'queue' => env('DB_QUEUE', 'default'),
'retry_after' => (int) env('DB_QUEUE_RETRY_AFTER', 90),
'after_commit' => false,
],
'beanstalkd' => [
'driver' => 'beanstalkd',
'host' => env('BEANSTALKD_QUEUE_HOST', 'localhost'),
'queue' => env('BEANSTALKD_QUEUE', 'default'),
'retry_after' => (int) env('BEANSTALKD_QUEUE_RETRY_AFTER', 90),
'block_for' => 0,
'after_commit' => false,
],
'sqs' => [
'driver' => 'sqs',
'key' => env('AWS_ACCESS_KEY_ID'),
'secret' => env('AWS_SECRET_ACCESS_KEY'),
'prefix' => env('SQS_PREFIX', 'https://sqs.us-east-1.amazonaws.com/your-account-id'),
'queue' => env('SQS_QUEUE', 'default'),
'suffix' => env('SQS_SUFFIX'),
'region' => env('AWS_DEFAULT_REGION', 'us-east-1'),
'after_commit' => false,
],
'redis' => [
'driver' => 'redis',
'connection' => env('REDIS_QUEUE_CONNECTION', 'default'),
'queue' => env('REDIS_QUEUE', 'default'),
'retry_after' => (int) env('REDIS_QUEUE_RETRY_AFTER', 90),
'block_for' => null,
'after_commit' => false,
],
],
/*
|--------------------------------------------------------------------------
| Job Batching
|--------------------------------------------------------------------------
|
| The following options configure the database and table that store job
| batching information. These options can be updated to any database
| connection and table which has been defined by your application.
|
*/
'batching' => [
'database' => env('DB_CONNECTION', 'sqlite'),
'table' => 'job_batches',
],
/*
|--------------------------------------------------------------------------
| Failed Queue Jobs
|--------------------------------------------------------------------------
|
| These options configure the behavior of failed queue job logging so you
| can control how and where failed jobs are stored. Laravel ships with
| support for storing failed jobs in a simple file or in a database.
|
| Supported drivers: "database-uuids", "dynamodb", "file", "null"
|
*/
'failed' => [
'driver' => env('QUEUE_FAILED_DRIVER', 'database-uuids'),
'database' => env('DB_CONNECTION', 'sqlite'),
'table' => 'failed_jobs',
],
];

38
config/services.php Normal file
View File

@ -0,0 +1,38 @@
<?php
return [
/*
|--------------------------------------------------------------------------
| Third Party Services
|--------------------------------------------------------------------------
|
| This file is for storing the credentials for third party services such
| as Mailgun, Postmark, AWS and more. This file provides the de facto
| location for this type of information, allowing packages to have
| a conventional file to locate the various service credentials.
|
*/
'postmark' => [
'token' => env('POSTMARK_TOKEN'),
],
'resend' => [
'key' => env('RESEND_KEY'),
],
'ses' => [
'key' => env('AWS_ACCESS_KEY_ID'),
'secret' => env('AWS_SECRET_ACCESS_KEY'),
'region' => env('AWS_DEFAULT_REGION', 'us-east-1'),
],
'slack' => [
'notifications' => [
'bot_user_oauth_token' => env('SLACK_BOT_USER_OAUTH_TOKEN'),
'channel' => env('SLACK_BOT_USER_DEFAULT_CHANNEL'),
],
],
];

217
config/session.php Normal file
View File

@ -0,0 +1,217 @@
<?php
use Illuminate\Support\Str;
return [
/*
|--------------------------------------------------------------------------
| Default Session Driver
|--------------------------------------------------------------------------
|
| This option determines the default session driver that is utilized for
| incoming requests. Laravel supports a variety of storage options to
| persist session data. Database storage is a great default choice.
|
| Supported: "file", "cookie", "database", "memcached",
| "redis", "dynamodb", "array"
|
*/
'driver' => env('SESSION_DRIVER', 'database'),
/*
|--------------------------------------------------------------------------
| Session Lifetime
|--------------------------------------------------------------------------
|
| Here you may specify the number of minutes that you wish the session
| to be allowed to remain idle before it expires. If you want them
| to expire immediately when the browser is closed then you may
| indicate that via the expire_on_close configuration option.
|
*/
'lifetime' => (int) env('SESSION_LIFETIME', 120),
'expire_on_close' => env('SESSION_EXPIRE_ON_CLOSE', false),
/*
|--------------------------------------------------------------------------
| Session Encryption
|--------------------------------------------------------------------------
|
| This option allows you to easily specify that all of your session data
| should be encrypted before it's stored. All encryption is performed
| automatically by Laravel and you may use the session like normal.
|
*/
'encrypt' => env('SESSION_ENCRYPT', false),
/*
|--------------------------------------------------------------------------
| Session File Location
|--------------------------------------------------------------------------
|
| When utilizing the "file" session driver, the session files are placed
| on disk. The default storage location is defined here; however, you
| are free to provide another location where they should be stored.
|
*/
'files' => storage_path('framework/sessions'),
/*
|--------------------------------------------------------------------------
| Session Database Connection
|--------------------------------------------------------------------------
|
| When using the "database" or "redis" session drivers, you may specify a
| connection that should be used to manage these sessions. This should
| correspond to a connection in your database configuration options.
|
*/
'connection' => env('SESSION_CONNECTION'),
/*
|--------------------------------------------------------------------------
| Session Database Table
|--------------------------------------------------------------------------
|
| When using the "database" session driver, you may specify the table to
| be used to store sessions. Of course, a sensible default is defined
| for you; however, you're welcome to change this to another table.
|
*/
'table' => env('SESSION_TABLE', 'sessions'),
/*
|--------------------------------------------------------------------------
| Session Cache Store
|--------------------------------------------------------------------------
|
| When using one of the framework's cache driven session backends, you may
| define the cache store which should be used to store the session data
| between requests. This must match one of your defined cache stores.
|
| Affects: "dynamodb", "memcached", "redis"
|
*/
'store' => env('SESSION_STORE'),
/*
|--------------------------------------------------------------------------
| Session Sweeping Lottery
|--------------------------------------------------------------------------
|
| Some session drivers must manually sweep their storage location to get
| rid of old sessions from storage. Here are the chances that it will
| happen on a given request. By default, the odds are 2 out of 100.
|
*/
'lottery' => [2, 100],
/*
|--------------------------------------------------------------------------
| Session Cookie Name
|--------------------------------------------------------------------------
|
| Here you may change the name of the session cookie that is created by
| the framework. Typically, you should not need to change this value
| since doing so does not grant a meaningful security improvement.
|
*/
'cookie' => env(
'SESSION_COOKIE',
Str::slug(env('APP_NAME', 'laravel')).'-session'
),
/*
|--------------------------------------------------------------------------
| Session Cookie Path
|--------------------------------------------------------------------------
|
| The session cookie path determines the path for which the cookie will
| be regarded as available. Typically, this will be the root path of
| your application, but you're free to change this when necessary.
|
*/
'path' => env('SESSION_PATH', '/'),
/*
|--------------------------------------------------------------------------
| Session Cookie Domain
|--------------------------------------------------------------------------
|
| This value determines the domain and subdomains the session cookie is
| available to. By default, the cookie will be available to the root
| domain and all subdomains. Typically, this shouldn't be changed.
|
*/
'domain' => env('SESSION_DOMAIN'),
/*
|--------------------------------------------------------------------------
| HTTPS Only Cookies
|--------------------------------------------------------------------------
|
| By setting this option to true, session cookies will only be sent back
| to the server if the browser has a HTTPS connection. This will keep
| the cookie from being sent to you when it can't be done securely.
|
*/
'secure' => env('SESSION_SECURE_COOKIE'),
/*
|--------------------------------------------------------------------------
| HTTP Access Only
|--------------------------------------------------------------------------
|
| Setting this value to true will prevent JavaScript from accessing the
| value of the cookie and the cookie will only be accessible through
| the HTTP protocol. It's unlikely you should disable this option.
|
*/
'http_only' => env('SESSION_HTTP_ONLY', true),
/*
|--------------------------------------------------------------------------
| Same-Site Cookies
|--------------------------------------------------------------------------
|
| This option determines how your cookies behave when cross-site requests
| take place, and can be used to mitigate CSRF attacks. By default, we
| will set this value to "lax" to permit secure cross-site requests.
|
| See: https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Set-Cookie#samesitesamesite-value
|
| Supported: "lax", "strict", "none", null
|
*/
'same_site' => env('SESSION_SAME_SITE', 'lax'),
/*
|--------------------------------------------------------------------------
| Partitioned Cookies
|--------------------------------------------------------------------------
|
| Setting this value to true will tie the cookie to the top-level site for
| a cross-site context. Partitioned cookies are accepted by the browser
| when flagged "secure" and the Same-Site attribute is set to "none".
|
*/
'partitioned' => env('SESSION_PARTITIONED_COOKIE', false),
];

1
database/.gitignore vendored Normal file
View File

@ -0,0 +1 @@
*.sqlite*

View File

@ -0,0 +1,44 @@
<?php
namespace Database\Factories;
use Illuminate\Database\Eloquent\Factories\Factory;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Str;
/**
* @extends \Illuminate\Database\Eloquent\Factories\Factory<\App\Models\User>
*/
class UserFactory extends Factory
{
/**
* The current password being used by the factory.
*/
protected static ?string $password;
/**
* Define the model's default state.
*
* @return array<string, mixed>
*/
public function definition(): array
{
return [
'name' => fake()->name(),
'email' => fake()->unique()->safeEmail(),
'email_verified_at' => now(),
'password' => static::$password ??= Hash::make('password'),
'remember_token' => Str::random(10),
];
}
/**
* Indicate that the model's email address should be unverified.
*/
public function unverified(): static
{
return $this->state(fn (array $attributes) => [
'email_verified_at' => null,
]);
}
}

View File

@ -0,0 +1,55 @@
<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
return new class extends Migration
{
/**
* Run the migrations.
*/
public function up(): void
{
Schema::create('users', function (Blueprint $table) {
$table->id();
$table->string('name');
$table->string('email')->unique();
$table->timestamp('email_verified_at')->nullable();
$table->string('password');
$table->string('role')->default('siswa');
$table->string('nisn')->nullable();
$table->string('nip')->nullable();
$table->string('no_hp')->nullable();
$table->string('golongan')->nullable();
$table->string('kelas')->nullable();
$table->rememberToken();
$table->timestamps();
});
Schema::create('password_reset_tokens', function (Blueprint $table) {
$table->string('email')->primary();
$table->string('token');
$table->timestamp('created_at')->nullable();
});
Schema::create('sessions', function (Blueprint $table) {
$table->string('id')->primary();
$table->foreignId('user_id')->nullable()->index();
$table->string('ip_address', 45)->nullable();
$table->text('user_agent')->nullable();
$table->longText('payload');
$table->integer('last_activity')->index();
});
}
/**
* Reverse the migrations.
*/
public function down(): void
{
Schema::dropIfExists('users');
Schema::dropIfExists('password_reset_tokens');
Schema::dropIfExists('sessions');
}
};

View File

@ -0,0 +1,35 @@
<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
return new class extends Migration
{
/**
* Run the migrations.
*/
public function up(): void
{
Schema::create('cache', function (Blueprint $table) {
$table->string('key')->primary();
$table->mediumText('value');
$table->integer('expiration');
});
Schema::create('cache_locks', function (Blueprint $table) {
$table->string('key')->primary();
$table->string('owner');
$table->integer('expiration');
});
}
/**
* Reverse the migrations.
*/
public function down(): void
{
Schema::dropIfExists('cache');
Schema::dropIfExists('cache_locks');
}
};

View File

@ -0,0 +1,57 @@
<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
return new class extends Migration
{
/**
* Run the migrations.
*/
public function up(): void
{
Schema::create('jobs', function (Blueprint $table) {
$table->id();
$table->string('queue')->index();
$table->longText('payload');
$table->unsignedTinyInteger('attempts');
$table->unsignedInteger('reserved_at')->nullable();
$table->unsignedInteger('available_at');
$table->unsignedInteger('created_at');
});
Schema::create('job_batches', function (Blueprint $table) {
$table->string('id')->primary();
$table->string('name');
$table->integer('total_jobs');
$table->integer('pending_jobs');
$table->integer('failed_jobs');
$table->longText('failed_job_ids');
$table->mediumText('options')->nullable();
$table->integer('cancelled_at')->nullable();
$table->integer('created_at');
$table->integer('finished_at')->nullable();
});
Schema::create('failed_jobs', function (Blueprint $table) {
$table->id();
$table->string('uuid')->unique();
$table->text('connection');
$table->text('queue');
$table->longText('payload');
$table->longText('exception');
$table->timestamp('failed_at')->useCurrent();
});
}
/**
* Reverse the migrations.
*/
public function down(): void
{
Schema::dropIfExists('jobs');
Schema::dropIfExists('job_batches');
Schema::dropIfExists('failed_jobs');
}
};

View File

@ -0,0 +1,29 @@
<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
return new class extends Migration {
/**
* Run the migrations.
*/
public function up()
{
Schema::create('master_induks', function (Blueprint $table) {
$table->id();
$table->string('nomor_induk')->unique();
$table->enum('role', ['siswa', 'guru']);
$table->string('nama_pemilik')->nullable();
$table->timestamps();
});
}
/**
* Reverse the migrations.
*/
public function down(): void
{
Schema::dropIfExists('master_induks');
}
};

View File

@ -0,0 +1,93 @@
<?php
namespace Database\Seeders;
use Illuminate\Database\Seeder;
use App\Models\User;
use App\Models\MasterInduk;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\DB;
class DatabaseSeeder extends Seeder
{
public function run()
{
// Bersihkan data lama
DB::statement('SET FOREIGN_KEY_CHECKS=0;');
User::truncate();
MasterInduk::truncate();
DB::statement('SET FOREIGN_KEY_CHECKS=1;');
$whitelist = [
['nomor_induk' => '1234567890', 'role' => 'siswa', 'nama_pemilik' => 'Silvi Rahmawati'],
['nomor_induk' => '9988776655', 'role' => 'siswa', 'nama_pemilik' => 'Siti Nurhaliza'],
['nomor_induk' => '5566778899', 'role' => 'siswa', 'nama_pemilik' => 'Andi Pratama'],
['nomor_induk' => '198506152010012', 'role' => 'guru', 'nama_pemilik' => 'Rina Marlina'],
];
foreach ($whitelist as $w) {
MasterInduk::create($w);
}
// ISI USER ASLI
// ID 1: Silvi (Siswa)
User::create([
'id' => 1,
'name' => 'Silvi Rahmawati',
'email' => 'silvi.rahmawati@smkn1perpus.sch.id',
'password' => Hash::make('password'),
'role' => 'siswa',
'nisn' => '1234567890',
'no_hp' => '08123456789',
'kelas' => 'XII RPL',
'golongan' => 'A'
]);
// ID 2: Budi (Admin/Penjaga)
User::create([
'id' => 2,
'name' => 'Budi Santoso',
'email' => 'budi.santoso@smkn1perpus.sch.id',
'password' => Hash::make('password'),
'role' => 'penjaga perpus',
'nip' => '197812312005011',
]);
// ID 3: Siti (Siswa)
User::create([
'id' => 3,
'name' => 'Siti Nurhaliza',
'email' => 'siti.nurhaliza@smkn1perpus.sch.id',
'password' => Hash::make('password'),
'role' => 'siswa',
'nisn' => '9988776655',
'no_hp' => '081998877665',
'kelas' => 'XII RPL',
'golongan' => 'B'
]);
// ID 4: Andi (Siswa)
User::create([
'id' => 4,
'name' => 'Andi Pratama',
'email' => 'andi.pratama@smkn1perpus.sch.id',
'password' => Hash::make('password'),
'role' => 'siswa',
'nisn' => '5566778899',
'no_hp' => '081556677889',
'kelas' => 'XII RPL',
'golongan' => 'C'
]);
// ID 5: Rina (Guru)
User::create([
'id' => 5,
'name' => 'Rina Marlina',
'email' => 'rina.marlina@smkn1perpus.sch.id',
'password' => Hash::make('password'),
'role' => 'guru',
'nip' => '198506152010012',
]);
}
}

2947
package-lock.json generated Normal file

File diff suppressed because it is too large Load Diff

23
package.json Normal file
View File

@ -0,0 +1,23 @@
{
"$schema": "https://json.schemastore.org/package.json",
"private": true,
"type": "module",
"scripts": {
"build": "vite build",
"dev": "vite"
},
"devDependencies": {
"@tailwindcss/forms": "^0.5.2",
"@tailwindcss/vite": "^4.0.0",
"alpinejs": "^3.4.2",
"axios": "^1.11.0",
"concurrently": "^9.0.1",
"laravel-vite-plugin": "^2.0.0",
"vite": "^7.0.4"
},
"dependencies": {
"@popperjs/core": "^2.11.8",
"bootstrap": "^5.3.8",
"sass": "^1.92.1"
}
}

34
phpunit.xml Normal file
View File

@ -0,0 +1,34 @@
<?xml version="1.0" encoding="UTF-8"?>
<phpunit xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:noNamespaceSchemaLocation="vendor/phpunit/phpunit/phpunit.xsd"
bootstrap="vendor/autoload.php"
colors="true"
>
<testsuites>
<testsuite name="Unit">
<directory>tests/Unit</directory>
</testsuite>
<testsuite name="Feature">
<directory>tests/Feature</directory>
</testsuite>
</testsuites>
<source>
<include>
<directory>app</directory>
</include>
</source>
<php>
<env name="APP_ENV" value="testing"/>
<env name="APP_MAINTENANCE_DRIVER" value="file"/>
<env name="BCRYPT_ROUNDS" value="4"/>
<env name="CACHE_STORE" value="array"/>
<env name="DB_CONNECTION" value="sqlite"/>
<env name="DB_DATABASE" value=":memory:"/>
<env name="MAIL_MAILER" value="array"/>
<env name="QUEUE_CONNECTION" value="sync"/>
<env name="SESSION_DRIVER" value="array"/>
<env name="PULSE_ENABLED" value="false"/>
<env name="TELESCOPE_ENABLED" value="false"/>
<env name="NIGHTWATCH_ENABLED" value="false"/>
</php>
</phpunit>

25
public/.htaccess Normal file
View File

@ -0,0 +1,25 @@
<IfModule mod_rewrite.c>
<IfModule mod_negotiation.c>
Options -MultiViews -Indexes
</IfModule>
RewriteEngine On
# Handle Authorization Header
RewriteCond %{HTTP:Authorization} .
RewriteRule .* - [E=HTTP_AUTHORIZATION:%{HTTP:Authorization}]
# Handle X-XSRF-Token Header
RewriteCond %{HTTP:x-xsrf-token} .
RewriteRule .* - [E=HTTP_X_XSRF_TOKEN:%{HTTP:X-XSRF-Token}]
# Redirect Trailing Slashes If Not A Folder...
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_URI} (.+)/$
RewriteRule ^ %1 [L,R=301]
# Send Requests To Front Controller...
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^ index.php [L]
</IfModule>

0
public/favicon.ico Normal file
View File

View File

@ -0,0 +1,457 @@
<svg width="1223" height="889" viewBox="0 0 1223 889" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M619.925 44.6429C572.139 -12.855 451.446 1.62462 451.446 1.62462L31 20.6986V889H1217.85C1217.85 889 1229.44 850.553 1217.85 832.476C1175.08 765.782 1082.3 850.004 1049.97 778.018C1033.61 741.597 1080 709.127 1064.37 672.408C1035.03 603.503 895.641 651.02 871.13 580.369C852.594 526.937 896.755 504.938 891.39 448.814C885.838 390.727 871.13 353.273 813.9 331.264C755.075 308.642 653.846 315.929 608.209 272.739C543.747 211.734 676.432 112.635 619.925 44.6429Z" fill="#CEDEFF"/>
<path d="M572 54.6861C524.646 -4.17798 421.03 0.067467 421.03 0.067467H0V889H1191C1191 889 1182.46 855.452 1170.97 836.945C1128.59 768.666 1041.81 849.078 1009.77 775.381C993.56 738.094 1017.25 717.371 1001.76 679.78C972.687 609.237 856.838 678.032 832.549 605.703C814.179 551.001 837.865 524.014 832.549 466.557C827.046 407.089 807.541 368.8 760.958 331.415C711.63 291.826 648.986 336.59 603.76 292.374C539.88 229.919 627.997 124.294 572 54.6861Z" fill="#0C5495"/>
<ellipse cx="501.5" cy="782" rx="444.5" ry="23" fill="white" fill-opacity="0.37"/>
<path d="M262.178 752.508H147.396C145.395 752.508 143.773 750.885 143.773 748.885V501.231C143.773 499.231 145.395 497.61 147.396 497.61H262.178C264.178 497.61 265.801 499.231 265.801 501.231V748.885C265.801 750.885 264.178 752.508 262.178 752.508Z" fill="#4188E4"/>
<path d="M258.509 575.918H151.093V518.397H258.509V575.918Z" fill="#142666"/>
<path d="M258.509 638.676H151.093V581.155H258.509V638.676Z" fill="#142666"/>
<path d="M258.509 701.433H151.093V643.914H258.509V701.433Z" fill="#142666"/>
<path d="M503.017 752.508H292.18C290.179 752.508 288.559 750.885 288.559 748.885V501.231C288.559 499.231 290.179 497.61 292.18 497.61H503.017C505.017 497.61 506.639 499.231 506.639 501.231V748.885C506.639 750.885 505.017 752.508 503.017 752.508Z" fill="#4188E4"/>
<path d="M493.608 575.918H301.637V518.397H493.608V575.918Z" fill="#142666"/>
<path d="M493.608 638.676H301.637V581.155H493.608V638.676Z" fill="#142666"/>
<path d="M493.608 701.433H301.637V643.914H493.608V701.433Z" fill="#142666"/>
<path d="M420.667 695.522V701.433H388.406V695.522H420.667Z" fill="#AFDBFE"/>
<path d="M421.72 690.266V695.521H392.864V690.266H421.72Z" fill="white"/>
<path d="M417.27 685.01V690.267H388.416V685.01H417.27Z" fill="#70C0FD"/>
<path d="M449.02 701.433H442.455V665.411H449.02V701.433Z" fill="#AFDBFE"/>
<path d="M455.758 701.433H450.575V671.511H455.758V701.433Z" fill="#70C0FD"/>
<path d="M433.845 701.433H427.28V665.411H433.845V701.433Z" fill="#AFDBFE"/>
<path d="M440.581 701.433H435.398V671.511H440.581V701.433Z" fill="#70C0FD"/>
<path d="M331.475 701.433H320.015V672.661H331.475V701.433Z" fill="#AFDBFE"/>
<path d="M318.056 701.433H314.832V675.481H318.056V701.433Z" fill="white"/>
<path d="M313.794 701.433H308.669V671.338H313.794V701.433Z" fill="#70C0FD"/>
<path d="M382.846 701.433H377.721V671.338H382.846V701.433Z" fill="#70C0FD"/>
<path d="M351.227 701.433H340.805V675.481H351.227V701.433Z" fill="white"/>
<path d="M358.887 701.433H352.322V665.411H358.887V701.433Z" fill="#AFDBFE"/>
<path d="M365.626 701.433H360.443V671.511H365.626V701.433Z" fill="#70C0FD"/>
<path d="M338.846 701.433H332.8V669.381H338.846V701.433Z" fill="#70C0FD"/>
<path d="M376.166 701.433H366.662V674.446H376.166V701.433Z" fill="white"/>
<path d="M166.311 701.413H163.086V675.46H166.311V701.413Z" fill="white"/>
<path d="M162.049 701.413H156.924V671.316H162.049V701.413Z" fill="#A2CFF6"/>
<path d="M255.17 701.413H243.71V672.639H255.17V701.413Z" fill="#AFDBFE"/>
<path d="M241.752 701.413H238.527V675.46H241.752V701.413Z" fill="white"/>
<path d="M237.491 701.413H232.365V671.316H237.491V701.413Z" fill="#70C0FD"/>
<path d="M212.44 701.413H205.875V665.39H212.44V701.413Z" fill="#AFDBFE"/>
<path d="M200.329 695.502V701.413H168.067V695.502H200.329Z" fill="#B0C1EC"/>
<path d="M201.381 690.246V695.503H172.526V690.246H201.381Z" fill="white"/>
<path d="M196.931 684.99V690.247H168.076V684.99H196.931Z" fill="#A2CFF6"/>
<path d="M219.178 701.413H213.995V671.49H219.178V701.413Z" fill="#70C0FD"/>
<path d="M230.811 701.413H221.31V674.424H230.811V701.413Z" fill="white"/>
<path d="M314.267 575.918H311.043V549.964H314.267V575.918Z" fill="white"/>
<path d="M310.006 575.918H304.881V545.821H310.006V575.918Z" fill="#70C0FD"/>
<path d="M403.129 575.918H391.669V547.144H403.129V575.918Z" fill="#AFDBFE"/>
<path d="M389.711 575.918H386.486V549.964H389.711V575.918Z" fill="white"/>
<path d="M385.449 575.918H380.323V545.821H385.449V575.918Z" fill="#70C0FD"/>
<path d="M360.399 575.918H353.834V539.895H360.399V575.918Z" fill="#AFDBFE"/>
<path d="M348.287 570.007V575.918H316.025V570.007H348.287Z" fill="#AFDBFE"/>
<path d="M349.339 564.75V570.007H320.483V564.75H349.339Z" fill="white"/>
<path d="M344.889 559.493V564.75H316.035V559.493H344.889Z" fill="#70C0FD"/>
<path d="M367.136 575.918H361.953V545.995H367.136V575.918Z" fill="#70C0FD"/>
<path d="M378.769 575.918H369.268V548.929H378.769V575.918Z" fill="white"/>
<path d="M546.886 572.653H543.66V546.702H546.886V572.653Z" fill="white"/>
<path d="M542.624 572.653H537.499V542.558H542.624V572.653Z" fill="#70C0FD"/>
<path d="M618.065 572.653H612.939V542.558H618.065V572.653Z" fill="#70C0FD"/>
<path d="M593.015 572.653H586.45V536.632H593.015V572.653Z" fill="#AFDBFE"/>
<path d="M580.904 566.742V572.653H548.643V566.742H580.904Z" fill="#AFDBFE"/>
<path d="M581.955 561.488V566.743H553.1V561.488H581.955Z" fill="white"/>
<path d="M577.505 556.23V561.487H548.651V556.23H577.505Z" fill="#A2CFF6"/>
<path d="M599.754 572.653H594.569V542.732H599.754V572.653Z" fill="#70C0FD"/>
<path d="M611.385 572.653H601.884V545.666H611.385V572.653Z" fill="white"/>
<path d="M471.439 575.918H464.874V539.895H471.439V575.918Z" fill="#AFDBFE"/>
<path d="M478.178 575.918H472.995V545.995H478.178V575.918Z" fill="#70C0FD"/>
<path d="M489.812 575.918H480.309V548.929H489.812V575.918Z" fill="white"/>
<path d="M179.729 575.918H168.269V547.144H179.729V575.918Z" fill="#AFDBFE"/>
<path d="M166.311 575.918H163.086V549.964H166.311V575.918Z" fill="white"/>
<path d="M162.049 575.918H156.924V545.821H162.049V575.918Z" fill="#70C0FD"/>
<path d="M249.871 575.918H238.411V547.144H249.871V575.918Z" fill="#AFDBFE"/>
<path d="M236.453 575.918H233.229V549.964H236.453V575.918Z" fill="white"/>
<path d="M232.192 575.918H227.066V545.821H232.192V575.918Z" fill="#70C0FD"/>
<path d="M199.482 575.918H189.059V549.964H199.482V575.918Z" fill="white"/>
<path d="M207.141 575.918H200.576V539.895H207.141V575.918Z" fill="#AFDBFE"/>
<path d="M213.879 575.918H208.696V545.995H213.879V575.918Z" fill="#70C0FD"/>
<path d="M187.1 575.918H181.054V543.865H187.1V575.918Z" fill="#70C0FD"/>
<path d="M428.853 575.918H417.392V547.144H428.853V575.918Z" fill="#AFDBFE"/>
<path d="M415.434 575.918H412.208V549.964H415.434V575.918Z" fill="white"/>
<path d="M411.173 575.918H406.048V545.821H411.173V575.918Z" fill="#70C0FD"/>
<path d="M448.605 575.918H438.181V549.964H448.605V575.918Z" fill="white"/>
<path d="M456.265 575.918H449.7V539.895H456.265V575.918Z" fill="#AFDBFE"/>
<path d="M463.004 575.918H457.819V545.995H463.004V575.918Z" fill="#70C0FD"/>
<path d="M436.225 575.918H430.177V543.865H436.225V575.918Z" fill="#70C0FD"/>
<path d="M564.8 521.109H558.235V485.086H564.8V521.109Z" fill="#AFDBFE"/>
<path d="M571.537 521.109H566.354V491.186H571.537V521.109Z" fill="#70C0FD"/>
<path d="M583.171 521.109H573.669V494.121H583.171V521.109Z" fill="white"/>
<path d="M541.965 521.109H531.542V495.158H541.965V521.109Z" fill="white"/>
<path d="M549.625 521.109H543.06V485.086H549.625V521.109Z" fill="#AFDBFE"/>
<path d="M556.362 521.109H551.18V491.186H556.362V521.109Z" fill="#70C0FD"/>
<path d="M529.584 521.109H523.537V489.056H529.584V521.109Z" fill="#70C0FD"/>
<path d="M451.479 638.676H440.02V609.902H451.479V638.676Z" fill="#AFDBFE"/>
<path d="M438.061 638.676H434.837V612.722H438.061V638.676Z" fill="white"/>
<path d="M433.799 638.676H428.674V608.579H433.799V638.676Z" fill="#70C0FD"/>
<path d="M477.204 638.676H465.744V609.902H477.204V638.676Z" fill="#AFDBFE"/>
<path d="M463.786 638.676H460.56V612.722H463.786V638.676Z" fill="white"/>
<path d="M459.524 638.676H454.398V608.579H459.524V638.676Z" fill="#70C0FD"/>
<path d="M484.575 638.676H478.528V606.622H484.575V638.676Z" fill="#70C0FD"/>
<path d="M225.511 575.918H216.01V548.929H225.511V575.918Z" fill="white"/>
<path d="M331.475 638.676H320.015V609.902H331.475V638.676Z" fill="#AFDBFE"/>
<path d="M318.056 638.676H314.832V612.722H318.056V638.676Z" fill="white"/>
<path d="M313.794 638.676H308.669V608.579H313.794V638.676Z" fill="#70C0FD"/>
<path d="M401.618 638.676H390.158V609.902H401.618V638.676Z" fill="#AFDBFE"/>
<path d="M388.2 638.676H384.974V612.722H388.2V638.676Z" fill="white"/>
<path d="M383.938 638.676H378.812V608.579H383.938V638.676Z" fill="#70C0FD"/>
<path d="M351.227 638.676H340.805V612.722H351.227V638.676Z" fill="white"/>
<path d="M358.887 638.676H352.322V602.652H358.887V638.676Z" fill="#AFDBFE"/>
<path d="M365.626 638.676H360.443V608.752H365.626V638.676Z" fill="#70C0FD"/>
<path d="M338.846 638.676H332.8V606.622H338.846V638.676Z" fill="#70C0FD"/>
<path d="M377.259 638.676H367.756V611.687H377.259V638.676Z" fill="white"/>
<path d="M179.729 638.676H168.269V607.271H179.729V638.676Z" fill="white"/>
<path d="M166.311 638.676H163.086V612.722H166.311V638.676Z" fill="#70C0FD"/>
<path d="M162.049 638.676H156.924V608.579H162.049V638.676Z" fill="#AFDBFE"/>
<path d="M236.453 638.676H233.229V612.722H236.453V638.676Z" fill="#70C0FD"/>
<path d="M232.192 638.676H227.066V605.33H232.192V638.676Z" fill="white"/>
<path d="M199.482 638.676H189.059V605.33H199.482V638.676Z" fill="#70C0FD"/>
<path d="M207.141 638.676H200.576V609.902H207.141V638.676Z" fill="white"/>
<path d="M213.879 638.676H208.696V600.801H213.879V638.676Z" fill="#AFDBFE"/>
<path d="M187.1 638.676H181.054V610.669H187.1V638.676Z" fill="#AFDBFE"/>
<path d="M225.511 638.676H216.01V606.622H225.511V638.676Z" fill="#70C0FD"/>
<path d="M254.731 635.589L245.783 638.783L234.992 608.599L243.941 605.405L254.731 635.589Z" fill="white"/>
<path d="M420.911 635.589L411.962 638.783L401.174 608.599L410.122 605.405L420.911 635.589Z" fill="white"/>
<path d="M426.485 637.078L422.011 638.676L411.221 608.491L415.696 606.893L426.485 637.078Z" fill="#70C0FD"/>
<path d="M597.239 519.378L592.763 520.976L581.975 490.791L586.448 489.193L597.239 519.378Z" fill="#70C0FD"/>
<path d="M556.651 764.873L555.451 774.5L548.991 775L549.09 766.072L556.651 764.873Z" fill="#FFC0BB"/>
<path d="M442.771 673.434H505.291L498.461 720.671L446.861 712.271L442.771 673.434Z" fill="#F9537F"/>
<path d="M539.174 782.047L556.824 782.165C557.209 782.169 557.518 781.866 557.516 781.488L557.51 780.981C557.508 780.603 557.192 780.296 556.806 780.294L539.157 780.174C538.772 780.172 538.461 780.476 538.465 780.851L538.469 781.36C538.472 781.736 538.787 782.045 539.174 782.047Z" fill="#3D3A55"/>
<path d="M556.584 774.605L557.261 779.817C557.343 780.459 556.981 781.039 556.499 781.037L539.715 780.923C539.278 780.921 538.846 780.652 538.613 780.15C538.373 779.637 538.319 778.865 539.061 777.832C540.546 775.769 545.479 775.296 547.878 773.541L555.696 773.593C556.133 773.597 556.508 774.026 556.584 774.605Z" fill="#09083C"/>
<path d="M549.09 776.571C549.212 776.501 549.254 776.3 549.181 776.148C548.846 775.433 547.801 773.688 545.709 774.031C545.587 774.052 545.507 774.209 545.528 774.371L545.53 774.374C545.551 774.533 545.661 774.636 545.778 774.617C547.654 774.317 548.542 775.854 548.815 776.453C548.872 776.581 548.99 776.632 549.09 776.571Z" fill="white"/>
<path d="M547.352 777.231C547.472 777.158 547.516 776.958 547.444 776.807C547.108 776.09 546.063 774.347 543.97 774.689C543.85 774.71 543.769 774.866 543.79 775.028L543.792 775.034C543.813 775.19 543.924 775.293 544.04 775.274C545.917 774.975 546.805 776.512 547.076 777.11C547.135 777.238 547.253 777.29 547.352 777.231Z" fill="white"/>
<path d="M545.738 777.844C545.858 777.772 545.9 777.574 545.829 777.421C545.494 776.704 544.449 774.961 542.355 775.305C542.235 775.324 542.153 775.48 542.176 775.642V775.648C542.199 775.804 542.307 775.907 542.425 775.89C544.3 775.589 545.19 777.126 545.461 777.726C545.52 777.854 545.637 777.904 545.738 777.844Z" fill="white"/>
<path d="M556.502 781.037C556.501 781.037 556.5 781.037 556.499 781.037L552.02 781.007C553.204 777.136 555.231 776.453 556.518 776.453C556.624 776.453 556.729 776.457 556.825 776.466L557.261 779.817C557.261 779.83 557.263 779.841 557.265 779.855C557.265 779.855 557.265 779.855 557.265 779.857C557.265 779.862 557.267 779.868 557.267 779.874C557.322 780.492 556.97 781.037 556.502 781.037Z" fill="#090730"/>
<path d="M585.422 764.272L585.97 774.368L579.395 774.412L578.768 765.078L585.422 764.272Z" fill="#FFC0BB"/>
<path d="M569.953 782.22L587.6 782.34C587.987 782.342 588.296 782.039 588.294 781.661L588.288 781.154C588.285 780.778 587.97 780.469 587.585 780.467L569.935 780.347C569.55 780.345 569.239 780.649 569.243 781.026L569.247 781.533C569.251 781.911 569.565 782.218 569.953 782.22Z" fill="#3D3A55"/>
<path d="M587.362 774.777L588.037 779.987C588.121 780.629 587.758 781.211 587.276 781.207L570.492 781.095C570.056 781.091 569.623 780.822 569.39 780.32C569.15 779.807 569.097 779.035 569.838 778.004C571.322 775.939 576.255 775.466 578.655 773.711L586.473 773.765C586.91 773.767 587.286 774.196 587.362 774.777Z" fill="#09083C"/>
<path d="M579.868 776.743C579.988 776.671 580.032 776.471 579.959 776.318C579.624 775.603 578.579 773.86 576.485 774.201C576.365 774.222 576.285 774.379 576.306 774.541L576.308 774.547C576.329 774.703 576.438 774.806 576.556 774.787C578.43 774.487 579.321 776.024 579.592 776.623C579.651 776.751 579.769 776.802 579.868 776.743Z" fill="white"/>
<path d="M578.131 777.403C578.251 777.33 578.295 777.132 578.222 776.98C577.887 776.265 576.842 774.52 574.748 774.863C574.628 774.882 574.548 775.039 574.569 775.201L574.571 775.206C574.592 775.363 574.7 775.468 574.819 775.448C576.693 775.147 577.583 776.684 577.854 777.285C577.913 777.412 578.03 777.462 578.131 777.403Z" fill="white"/>
<path d="M576.515 778.016C576.635 777.944 576.677 777.746 576.607 777.593C576.271 776.878 575.224 775.133 573.132 775.477C573.012 775.496 572.93 775.652 572.953 775.814V775.82C572.974 775.978 573.085 776.081 573.201 776.062C575.077 775.761 575.966 777.298 576.238 777.898C576.296 778.026 576.414 778.077 576.515 778.016Z" fill="white"/>
<path d="M587.28 781.207C587.278 781.207 587.276 781.207 587.276 781.207L582.797 781.177C583.981 777.306 586.008 776.623 587.293 776.623C587.402 776.623 587.505 776.629 587.602 776.636L588.037 779.987C588.039 780 588.041 780.013 588.042 780.025V780.027C588.042 780.032 588.042 780.038 588.044 780.042C588.056 780.168 588.05 780.292 588.029 780.406C588.029 780.408 588.029 780.408 588.029 780.408C588.029 780.41 588.029 780.412 588.029 780.414C588.029 780.416 588.027 780.418 588.027 780.42C588.027 780.42 588.027 780.42 588.027 780.421V780.423C587.945 780.87 587.648 781.207 587.28 781.207Z" fill="#090730"/>
<path d="M668.394 749.717H454.535C454.137 749.717 453.814 749.395 453.814 748.996V746.799C453.814 746.401 454.137 746.077 454.535 746.077H668.394C668.793 746.077 669.115 746.401 669.115 746.799V748.996C669.115 749.395 668.793 749.717 668.394 749.717Z" fill="#3D3A55"/>
<path d="M682.106 641.707C681.301 641.764 542.861 641.726 497.382 641.712C489.488 641.709 483.091 648.104 483.091 655.992V714.287H654.234L680.78 687.76L682.106 641.707Z" fill="#FF5B7E"/>
<path d="M677.875 696.484H686.335C687.868 696.484 689.11 695.243 689.11 693.71V644.482C689.11 642.949 687.868 641.708 686.335 641.708H677.875C676.342 641.708 675.099 642.949 675.099 644.482V693.71C675.099 695.243 676.342 696.484 677.875 696.484Z" fill="#E03268"/>
<path d="M446.861 740.538H622.71V705.571H446.861V740.538Z" fill="#E03268"/>
<path d="M583.773 692.452C583.773 692.452 551.346 692.57 546.342 699.07C541.339 705.57 537.535 749.471 546.342 768.672C546.342 768.672 557.753 769.073 560.353 767.473C560.353 767.473 559.553 735.071 559.953 726.471C560.353 717.869 566.358 716.67 567.159 715.871C567.96 715.07 583.773 692.452 583.773 692.452Z" fill="#2B1C35"/>
<path d="M633.445 625.141L634.675 635.115L624.78 634.776L625.064 623.362L633.445 625.141Z" fill="#FFC0BB"/>
<path d="M633.806 628.054L633.562 626.084H633.567L633.806 628.054Z" fill="#E8B5B5"/>
<path d="M628.265 629.072C627.18 629.072 626.047 628.945 624.936 628.617L625.065 623.361L633.562 626.084L633.806 628.054C632.536 628.529 630.498 629.072 628.265 629.072Z" fill="#FDA19A"/>
<path d="M613.136 609.346L614.417 616.15L615.653 616.516L615.344 607.885L613.136 609.346Z" fill="#FEE4CB"/>
<path d="M616.211 614.909C616.918 616.333 616.568 617.949 615.425 618.515C614.281 619.081 612.781 618.385 612.073 616.961C611.364 615.536 611.717 613.923 612.859 613.357C614.001 612.789 615.502 613.485 616.211 614.909Z" fill="#F99893"/>
<path d="M617.268 623.473C616.855 622.867 616.496 622.216 616.195 621.532C615.35 619.694 614.847 617.714 614.547 615.977C614.482 615.604 614.397 615.236 614.305 614.87C613.93 613.388 613.817 611.798 614.05 610.135C614.797 604.786 619.059 600.481 624.411 599.682C631.623 598.606 638.039 603.871 638.562 610.932C639.3 610.448 640.156 610.286 640.941 610.568C642.45 611.109 643.119 613.075 642.44 614.955C641.759 616.835 639.984 617.922 638.478 617.381C638.268 617.305 638.077 617.2 637.9 617.074C637.73 623.128 633.141 628.131 627.216 628.475C624.318 628.642 621.61 627.664 619.499 625.921C619.358 625.82 619.211 625.702 619.055 625.563C618.367 624.951 617.777 624.241 617.268 623.473Z" fill="#FFC0BB"/>
<path d="M627.597 612.819C627.629 613.412 628.138 613.864 628.731 613.829C629.326 613.795 629.78 613.288 629.746 612.695C629.711 612.104 629.202 611.65 628.609 611.684C628.016 611.718 627.562 612.228 627.597 612.819Z" fill="#333333"/>
<path d="M618.401 613.957C618.436 614.55 618.945 615.002 619.538 614.968C620.131 614.934 620.585 614.424 620.552 613.833C620.518 613.24 620.009 612.788 619.416 612.823C618.821 612.857 618.367 613.364 618.401 613.957Z" fill="#333333"/>
<path d="M626.176 610.768C626.691 610.522 627.183 610.319 627.68 610.171C628.178 610.024 628.676 609.944 629.169 609.942C629.661 609.944 630.163 609.99 630.655 610.146L630.844 610.194C630.907 610.211 630.966 610.239 631.029 610.26L631.404 610.392C631.658 610.487 631.898 610.613 632.178 610.703C632.007 610.48 631.818 610.26 631.604 610.066C631.374 609.9 631.156 609.694 630.884 609.58C630.371 609.288 629.759 609.162 629.16 609.162C628.555 609.168 627.959 609.328 627.444 609.61C626.933 609.896 626.477 610.278 626.176 610.768Z" fill="#07085B"/>
<path d="M621.865 611.237C621.467 610.821 620.938 610.547 620.378 610.377C619.815 610.215 619.197 610.184 618.606 610.31C618.021 610.44 617.451 610.693 617.012 611.088C616.772 611.262 616.602 611.508 616.412 611.721C616.246 611.956 616.108 612.209 615.99 612.465C616.244 612.318 616.45 612.143 616.679 611.996L617.018 611.786C617.075 611.752 617.125 611.712 617.184 611.681L617.357 611.593C617.806 611.334 618.284 611.183 618.765 611.073C619.249 610.97 619.752 610.941 620.267 610.978C620.786 611.014 621.31 611.107 621.865 611.237Z" fill="#07085B"/>
<path d="M611.416 601.257C611.416 601.257 607.73 601.558 611.452 598.252C615.174 594.945 625.397 590.781 632.235 593.963C632.235 593.963 633.428 591.071 635.388 591.65C637.349 592.23 634.263 594.333 634.263 594.333C634.263 594.333 636.721 594.131 637.53 595.3C638.128 596.162 636.624 596.276 635.798 596.276C637.211 596.444 641.915 598.919 639.747 609.858C638.781 609.694 631.045 603.354 631.045 603.354C631.045 603.354 620.925 610.102 622.113 606.51C622.113 606.51 610.043 613.376 611.553 606.632C611.553 606.632 606.569 607.244 611.416 601.257Z" fill="#07085B"/>
<path d="M623.528 610.953C623.804 611.678 623.96 612.439 624.027 613.217C624.06 613.606 624.062 614 624.02 614.405C623.97 614.807 623.888 615.223 623.644 615.629L623.537 615.776L623.44 615.903C623.4 615.963 623.337 616.014 623.31 616.077C623.234 616.195 623.188 616.321 623.173 616.451C623.127 616.714 623.259 616.994 623.455 617.242C623.88 617.74 624.609 617.999 625.364 618.129C624.62 618.298 623.73 618.232 623.049 617.648C622.717 617.368 622.454 616.912 622.477 616.407C622.483 616.283 622.498 616.159 622.54 616.043C622.568 615.921 622.626 615.816 622.683 615.709C622.734 615.596 622.818 615.516 622.887 615.421C622.931 615.368 622.938 615.35 622.961 615.32L623.02 615.238C623.175 614.992 623.263 614.651 623.329 614.305C623.404 613.958 623.417 613.59 623.453 613.222C623.495 612.481 623.503 611.726 623.528 610.953Z" fill="#F99893"/>
<path d="M631.044 603.355C631.044 603.355 635.321 610.107 635.416 614.1C635.416 614.1 637.222 610.522 640.2 610.431C640.2 610.431 641.169 603.706 639.35 599.503L632.623 600.943L631.044 603.355Z" fill="#07085B"/>
<path d="M622.406 630.967C622.406 630.967 625.409 635.667 635.416 630.967C635.416 630.967 653.53 625.967 654.932 647.468L655.634 667.468C655.634 667.468 646.275 667.501 641.472 667.678L641.321 671.867L613.999 694.068C613.999 694.068 597.785 692.669 594.482 691.069C594.482 691.069 600.289 679.569 601.189 676.968C602.089 674.369 602.739 649.268 603.69 646.667C604.642 644.068 607.435 631.323 622.406 630.967Z" fill="#FEB546"/>
<path d="M608.951 646.018C608.586 646.617 608.295 647.25 608.045 647.9C607.908 648.218 607.803 648.55 607.679 648.876L607.368 649.87C606.973 651.202 606.682 652.564 606.474 653.939C606.226 655.308 606.115 656.698 605.997 658.084C605.947 658.78 605.919 659.476 605.879 660.172C605.858 660.87 605.848 661.568 605.816 662.268C605.77 661.57 605.749 660.87 605.715 660.17C605.721 659.472 605.721 658.771 605.738 658.071C605.803 656.671 605.917 655.272 606.142 653.885C606.378 652.503 606.668 651.124 607.12 649.793C607.576 648.468 608.115 647.149 608.951 646.018Z" fill="#452B52"/>
<path d="M593.465 660.91C593.219 660.919 583.311 654.919 583.311 654.919L581.46 655.312L582.118 655.798L581.01 655.519L579.208 655.798C579.208 655.798 585.163 662.819 585.264 663.019C585.363 663.219 587.966 664.22 588.166 664.319C588.366 664.418 593.465 660.91 593.465 660.91Z" fill="#DAEEF7"/>
<path d="M609.32 656.118L608.42 655.555L608.006 655.837V655.311L607.444 654.918L593.032 660.618C593.032 660.618 597.649 663.545 597.799 663.43C597.948 663.32 606.168 661.819 606.317 661.594C606.468 661.369 609.32 656.118 609.32 656.118Z" fill="#DAEEF7"/>
<path d="M609.093 655.853L592.757 661.139L579.585 655.409C578.786 655.06 577.909 655.706 578.006 656.572L580.516 679.007C580.556 679.381 580.781 679.709 581.113 679.883L593.76 686.545L605.216 682.308L605.512 681.875L606.996 681.65L611.801 679.873C612.23 679.713 612.499 679.288 612.46 678.832L610.571 656.833C610.508 656.107 609.785 655.628 609.093 655.853Z" fill="#E03268"/>
<path d="M594.771 686.05L592.758 661.139L609.093 655.854C609.097 655.852 609.103 655.85 609.109 655.848C609.219 655.814 609.332 655.798 609.44 655.796H609.442C609.448 655.796 609.452 655.796 609.456 655.796C610.02 655.804 610.52 656.235 610.571 656.834L612.457 678.804C612.499 679.277 612.219 679.717 611.772 679.883L606.996 681.651L605.512 681.876L605.217 682.309L594.771 686.05Z" fill="#D21E49"/>
<path d="M590.321 663.82L580.135 659.369L580.459 663.995L590.443 668.619L590.321 663.82Z" fill="#C1215B"/>
<path d="M614.549 678.41C614.593 678.262 614.682 678.048 614.48 677.898C614.425 677.861 614.37 677.823 614.314 677.787C613.508 677.247 612.957 676.593 612.545 675.714C612.453 675.52 612.35 675.205 612.24 675.076C612.161 674.984 612.14 675.114 612.14 675.114L612.322 677.211L609.887 678.098C609.887 678.098 605.621 678.769 603.52 677.844C603.52 677.844 602.42 677.07 602.769 678.47C602.803 678.605 602.879 678.727 602.99 678.841C602.835 678.937 602.668 679.183 602.969 680.127C602.98 680.163 602.995 680.197 603.015 680.233C602.938 680.794 602.997 681.498 603.617 681.875C603.76 682.339 604.101 682.838 604.885 683.063C605.972 683.376 608.458 683.723 610.032 683.923C611.41 684.135 612.406 684.23 612.955 684.119L613.534 684.213C613.529 684.06 615.029 681.923 615.188 681.008C615.348 680.09 614.289 679.301 614.549 678.41Z" fill="#FFC0BB"/>
<path d="M614.48 677.898C614.48 677.898 629.259 677.145 633.389 675.72C637.517 674.294 641.32 671.868 641.32 671.868V667.67L655.342 667.46C655.342 667.46 657.108 680.295 653.13 681.795C649.151 683.294 621.811 685.695 612.954 684.12L614.48 677.898Z" fill="#FFC0BB"/>
<path d="M602.989 680.159C603.243 680.455 603.569 680.678 603.91 680.867C604.252 681.055 604.621 681.191 604.997 681.296C605.375 681.389 605.762 681.454 606.151 681.471C606.343 681.484 606.538 681.473 606.732 681.475C606.925 681.461 607.117 681.444 607.31 681.419C606.923 681.402 606.54 681.389 606.162 681.341C605.783 681.294 605.407 681.227 605.039 681.132C604.673 681.034 604.314 680.908 603.967 680.752C603.624 680.592 603.289 680.401 602.989 680.159Z" fill="#F99893"/>
<path d="M603.611 681.879C603.888 682.152 604.231 682.35 604.586 682.511C604.94 682.673 605.32 682.779 605.703 682.854C606.086 682.917 606.477 682.951 606.866 682.936C607.061 682.936 607.253 682.909 607.446 682.896C607.638 682.865 607.829 682.835 608.018 682.797C607.631 682.808 607.249 682.825 606.866 682.806C606.485 682.791 606.107 682.753 605.732 682.688C605.36 682.619 604.992 682.52 604.633 682.392C604.279 682.259 603.93 682.097 603.611 681.879Z" fill="#F99893"/>
<path d="M602.989 678.841C603.243 679.135 603.569 679.36 603.91 679.548C604.252 679.737 604.621 679.873 604.997 679.976C605.375 680.071 605.762 680.136 606.151 680.151C606.343 680.164 606.538 680.155 606.732 680.157C606.925 680.141 607.117 680.124 607.31 680.101C606.923 680.082 606.54 680.071 606.162 680.021C605.783 679.976 605.407 679.909 605.039 679.813C604.673 679.716 604.314 679.588 603.967 679.432C603.624 679.272 603.289 679.083 602.989 678.841Z" fill="#F99893"/>
<path d="M651.853 667.482C650.594 667.482 649.334 667.479 648.076 667.461L644.3 667.408C643.101 667.385 641.901 667.355 640.704 667.313C640.826 666.083 640.923 664.851 640.984 663.617C641.041 662.321 641.097 661.026 641.091 659.731C641.093 658.435 641.076 657.14 641.038 655.845C640.986 654.552 640.929 653.258 640.82 651.969C640.851 653.261 640.875 654.556 640.87 655.849C640.877 657.142 640.864 658.435 640.83 659.727C640.793 661.018 640.752 662.311 640.675 663.6C640.605 664.889 640.488 666.176 640.351 667.458L640.332 667.641L640.513 667.644C641.775 667.679 643.034 667.7 644.294 667.713C645.555 667.725 646.815 667.736 648.076 667.719C650.596 667.694 653.117 667.627 655.632 667.469C654.372 667.475 653.113 667.492 651.853 667.482Z" fill="#452B52"/>
<path d="M582.514 666.935C582.344 666.582 579.37 667.095 579.339 666.883C579.307 666.672 582.266 665.188 582.19 664.835C582.104 664.443 578.975 665.499 578.765 665.354C578.556 665.209 581.341 662.913 580.817 662.622C580.418 662.4 578.527 663.703 577.635 664.347C577.348 664.553 577.207 664.906 577.274 665.253L578.479 672.396C578.584 673.021 579.147 673.468 579.782 673.429L579.888 673.424L579.719 669.553C580.615 669.522 582.291 669.419 582.146 669.089C582.013 668.784 580.569 668.556 579.669 668.443L579.665 668.373C579.681 668.231 582.667 667.253 582.514 666.935Z" fill="#FFC0BB"/>
<path d="M541.157 729.369H463.681C456.664 729.369 450.978 723.687 450.978 716.677V681.632C450.978 677.103 447.304 673.433 442.771 673.433C438.239 673.433 434.564 677.103 434.564 681.632V717.579C434.564 733.318 447.332 746.076 463.084 746.076H483.327H500.122H519.671H521.473H541.49C541.065 740.575 540.981 734.858 541.157 729.369Z" fill="#FF85A5"/>
<path d="M559.873 729.369C559.806 733.547 559.854 739.818 559.942 746.076H599.386V729.369H559.873Z" fill="#FF85A5"/>
<path d="M623.872 673.534L682.223 673.951C687.86 673.951 692.431 678.518 692.431 684.151V720.115C692.431 734.452 680.799 746.076 666.448 746.076H605.961C605.961 746.076 617.97 725.153 617.97 724.554C617.97 723.953 623.872 673.534 623.872 673.534Z" fill="#F9537F"/>
<path d="M624.607 673.433C620.074 673.433 616.4 677.103 616.4 681.632V716.677C616.4 716.917 616.392 717.158 616.379 717.394L616.381 717.402H616.379C616.003 724.074 610.47 729.369 603.697 729.369H586.356C586.871 734.359 587.516 740.306 588.151 746.076H604.296C620.046 746.076 632.814 733.318 632.814 717.579V681.632C632.814 677.103 629.139 673.433 624.607 673.433Z" fill="#FF85A5"/>
<path d="M587.438 739.558C587.146 736.855 586.767 733.342 586.357 729.368C585.621 721.564 584.86 716.433 585.678 716.98C588.494 715.962 605.957 716.818 616.379 717.401H616.381C616.444 715.676 616.377 689.061 616.4 687.672C547.94 693.37 563.025 705.091 569.445 745.557C569.481 745.731 569.518 745.904 569.552 746.076C572.338 759.458 574.965 770.471 574.965 770.471C574.965 770.471 584.974 770.872 590.779 769.472C590.786 769.533 588.975 753.728 587.438 739.558Z" fill="#3A2645"/>
<path d="M472.05 778.793L480.295 773.709L487.417 778.009L484.928 779.779L476.292 780.995C476.292 780.995 472.923 780.564 472.774 780.465C472.626 780.364 472.05 778.793 472.05 778.793Z" fill="#F7AEAA"/>
<path d="M472.05 778.793L469.96 780.137C468.991 780.747 469.42 782.242 470.566 782.248L486.385 782.322C486.944 782.324 487.398 781.876 487.401 781.317L487.417 778.009C476.865 781.312 473.23 780.274 472.05 778.793Z" fill="#FF6088"/>
<path d="M481.046 778.793L489.291 773.709L496.413 778.009L493.924 779.779L485.289 780.995C485.289 780.995 481.919 780.564 481.77 780.465C481.622 780.364 481.046 778.793 481.046 778.793Z" fill="#FFC0BB"/>
<path d="M481.046 778.793L478.956 780.137C477.987 780.747 478.416 782.242 479.562 782.248L495.381 782.322C495.94 782.324 496.394 781.876 496.398 781.317L496.413 778.009C485.861 781.312 482.226 780.274 481.046 778.793Z" fill="#FF6088"/>
<path d="M525.259 633.556C529.511 630.577 527.254 629.382 529.751 626.792C531.696 624.775 532.303 623.267 532.265 621.791C532.312 620.315 531.719 618.803 529.79 616.77C527.311 614.164 529.576 612.985 525.349 609.974C521.119 606.965 516.625 614.263 516.625 614.263L511.988 619.993L512.855 622.964L511.038 628.753C511.038 628.753 521.009 636.532 525.259 633.556Z" fill="#07085B"/>
<path d="M485.525 690.27C485.525 690.27 467.91 696.871 466.909 702.071C465.908 707.271 473.114 773.275 476.216 776.475C476.216 776.475 482.636 778.275 487.684 775.474C492.731 772.674 490.328 750.874 490.328 750.273C490.328 749.673 495.982 717.673 495.957 716.471C495.932 715.272 505.138 700.872 507.341 698.872C509.545 696.871 513.097 687.122 513.097 687.122L485.525 690.27Z" fill="#030321"/>
<path d="M537.417 685.324C537.417 685.324 538.788 702.584 533.964 708.736C529.139 714.885 501.838 715.02 501.838 715.02L496.413 778.008C496.413 778.008 489.158 777.56 484.503 776.66C484.503 776.66 480.67 707.22 485.624 702.569C490.578 697.92 513.097 687.12 513.097 687.12L537.417 685.324Z" fill="#09083C"/>
<path d="M508.996 602.731C508.996 602.731 501.663 599.934 497.33 606.099C494.012 610.82 494.707 617.278 498.745 621.401L500.379 623.069C500.379 623.069 507.053 615.892 507.126 615.547C507.198 615.2 508.996 602.731 508.996 602.731Z" fill="#07085B"/>
<path d="M504.025 638.165C504.025 638.165 514.35 636.266 519.098 636.426C523.846 636.586 516.221 648.923 516.221 648.923L508.466 649.095C508.466 649.095 503.712 643.79 504.025 643.172C504.338 642.554 504.01 638.508 504.01 638.508L504.025 638.165Z" fill="#FFC0BB"/>
<path d="M515.647 627.858L517.5 636.354C517.5 636.354 514.633 640.982 507.631 638.128C507.631 638.128 508.632 636.513 507.892 632.893C507.135 629.196 515.647 627.858 515.647 627.858Z" fill="#FFC0BB"/>
<path d="M508.115 636.318C508.18 635.712 508.19 634.949 508.077 634.015V634.017C508.192 634.949 508.182 635.712 508.117 636.318H508.115Z" fill="#E8B5B5"/>
<path d="M516.514 631.836L516.287 630.795C516.289 630.793 516.289 630.793 516.291 630.791L516.518 631.826C516.518 631.83 516.516 631.832 516.514 631.836Z" fill="#9A5874"/>
<path d="M508.117 636.318C508.182 635.712 508.192 634.949 508.077 634.017C508.329 634.034 508.579 634.044 508.828 634.044C511.706 634.044 514.364 632.814 516.288 630.796L516.515 631.837C515.464 634.558 512.808 636.208 508.117 636.318Z" fill="#FDA19A"/>
<path d="M499.752 620.124C500.198 621.518 499.657 622.939 498.539 623.297C497.422 623.654 496.154 622.813 495.708 621.417C495.26 620.021 495.803 618.602 496.921 618.244C498.038 617.887 499.306 618.728 499.752 620.124Z" fill="#F99893"/>
<path d="M499.526 628.065C499.234 627.455 498.998 626.814 498.821 626.149C498.306 624.36 498.123 622.486 498.09 620.863C498.085 620.514 498.058 620.167 498.024 619.822C497.888 618.421 498.006 616.956 498.449 615.475C499.868 610.71 504.337 607.382 509.314 607.397C516.018 607.418 521.121 613.103 520.617 619.603C521.355 619.265 522.158 619.237 522.833 619.603C524.128 620.305 524.465 622.187 523.586 623.804C522.707 625.422 520.945 626.164 519.651 625.461C519.469 625.363 519.311 625.241 519.168 625.102C518.177 630.59 513.31 634.51 507.876 633.999C505.22 633.749 502.894 632.483 501.216 630.603C501.101 630.493 500.985 630.363 500.861 630.214C500.321 629.564 499.885 628.836 499.526 628.065Z" fill="#FFC0BB"/>
<path d="M506.787 618.422C506.937 619.055 506.981 619.705 506.951 620.359C506.933 620.687 506.891 621.015 506.811 621.347C506.726 621.675 506.613 622.011 506.365 622.323L506.258 622.434L506.165 622.527C506.125 622.573 506.068 622.607 506.037 622.657C505.961 622.747 505.909 622.848 505.883 622.954C505.814 623.168 505.892 623.414 506.03 623.643C506.327 624.104 506.903 624.402 507.515 624.594C506.878 624.652 506.146 624.497 505.646 623.936C505.402 623.666 505.234 623.258 505.309 622.84C505.328 622.737 505.355 622.636 505.402 622.545C505.438 622.445 505.499 622.363 505.557 622.281C505.614 622.196 505.692 622.138 505.759 622.066C505.803 622.026 505.81 622.012 505.831 621.99L505.89 621.927C506.045 621.74 506.157 621.465 506.251 621.187C506.352 620.907 506.403 620.601 506.474 620.3C506.592 619.688 506.682 619.063 506.787 618.422Z" fill="#F99893"/>
<path d="M510.391 619.798C510.34 620.342 510.738 620.824 511.284 620.875C511.827 620.927 512.309 620.526 512.361 619.983C512.412 619.44 512.012 618.957 511.469 618.906C510.925 618.854 510.441 619.255 510.391 619.798Z" fill="#333333"/>
<path d="M501.876 619.56C501.824 620.103 502.223 620.586 502.768 620.637C503.311 620.689 503.794 620.288 503.845 619.745C503.897 619.201 503.496 618.717 502.953 618.667C502.409 618.616 501.925 619.014 501.876 619.56Z" fill="#333333"/>
<path d="M507.286 629.359C507.232 629.359 507.179 629.359 507.126 629.356C504.757 629.254 504.456 627.069 504.456 627.069C504.774 626.877 505.101 626.804 505.408 626.804C506.281 626.804 507.013 627.376 507.013 627.376C507.52 627.113 508.022 627.029 508.455 627.029C509.227 627.029 509.784 627.296 509.784 627.296C509.784 627.296 509.507 629.359 507.286 629.359Z" fill="#FDA8A3"/>
<path d="M511.095 626.663C510.807 626.852 510.51 627.021 510.199 627.165C509.892 627.313 509.577 627.443 509.255 627.546C508.611 627.752 507.941 627.874 507.27 627.86C506.599 627.851 505.937 627.698 505.316 627.435C504.698 627.165 504.128 626.781 503.598 626.343C503.826 626.598 504.078 626.838 504.351 627.054C504.622 627.271 504.923 627.452 505.232 627.616C505.544 627.773 505.876 627.897 506.218 627.983C506.561 628.065 506.914 628.11 507.264 628.12C507.972 628.127 508.674 627.99 509.322 627.733C509.97 627.475 510.58 627.124 511.095 626.663Z" fill="#F99893"/>
<path d="M509.473 617.414C509.995 617.33 510.481 617.278 510.956 617.273C511.429 617.267 511.887 617.318 512.321 617.435C512.752 617.557 513.183 617.713 513.582 617.967C513.797 618.068 513.977 618.23 514.19 618.358C514.396 618.499 514.581 618.669 514.812 618.812C514.722 618.566 514.61 618.323 514.47 618.096C514.31 617.885 514.163 617.652 513.952 617.479C513.568 617.09 513.054 616.827 512.516 616.682C511.976 616.537 511.402 616.539 510.876 616.666C510.35 616.8 509.854 617.038 509.473 617.414Z" fill="#07085B"/>
<path d="M505.087 617.288C504.74 616.884 504.265 616.604 503.754 616.426C503.239 616.253 502.669 616.201 502.118 616.299C501.57 616.398 501.035 616.617 500.619 616.972C500.394 617.126 500.226 617.346 500.051 617.542C499.893 617.757 499.759 617.99 499.648 618.225C499.891 618.103 500.089 617.95 500.306 617.828C500.531 617.719 500.722 617.572 500.947 617.489C501.365 617.271 501.807 617.151 502.247 617.067C502.692 616.987 503.151 616.976 503.622 617.021C504.095 617.069 504.576 617.161 505.087 617.288Z" fill="#07085B"/>
<path d="M492.291 658.265C492.291 658.265 491.351 681.659 488.718 685.324L503.198 682.035V656.573L492.291 658.265Z" fill="#FFC0BB"/>
<path d="M498.461 661.458C498.461 661.458 500.476 667.346 500.843 670.475C501.752 678.242 500.764 683.72 499.155 688.142C496.897 694.343 515.327 692.087 515.704 691.9C516.08 691.711 531.876 685.604 531.876 685.604L534.885 676.867V661.458L534.038 654.413L498.461 661.458Z" fill="#02CCC0"/>
<path d="M542.596 654.414L530.998 658.36C530.998 658.36 533.004 676.899 532.377 679.531C531.841 681.779 523.432 686.25 518.103 688.754C517.245 689.156 516.299 689.328 515.355 689.252C512.319 689.002 506.938 688.533 506.094 688.474C504.767 688.382 501.119 688.476 501.003 688.941C500.894 689.372 503.851 688.897 505.77 689.294C506.04 689.349 505.895 689.709 505.832 689.711C504.814 689.749 502.194 689.86 501.332 690.148C500.276 690.499 504.013 690.22 506.033 690.592C506.176 690.617 506.288 691.017 506.185 691.12C505.945 691.357 505.066 691.565 502.654 691.811C498.629 692.222 502.566 692.72 502.566 692.72C502.566 692.72 502.928 692.617 506.385 692.144C506.513 692.127 506.654 692.486 506.464 692.653C506.13 692.945 505.356 693.523 504.317 693.83C503.022 694.211 503.964 694.547 503.964 694.547C503.964 694.547 506.414 693.818 507.789 693.716C508.818 693.637 513.669 694.032 515.658 694.146L515.811 693.805C518.509 693.727 540.023 693.168 542.094 679.844C544.224 666.126 542.596 654.414 542.596 654.414Z" fill="#FFC0BB"/>
<path d="M458.302 667.69H495.257L505.735 693.247H523.537C524.035 693.247 524.439 693.649 524.439 694.147C524.439 694.645 524.035 695.047 523.537 695.047H470.583L458.302 667.69Z" fill="#07085B"/>
<path d="M476.627 682.275C476.845 683.364 477.794 684.092 478.748 683.901C479.703 683.711 480.298 682.673 480.081 681.585C479.863 680.496 478.912 679.767 477.958 679.958C477.005 680.149 476.408 681.186 476.627 682.275Z" fill="#DAEEF7"/>
<path d="M504.025 638.165C504.025 638.165 511.044 646.35 519.098 636.426C519.098 636.426 527.898 635.71 534.385 640.313C540.874 644.917 544.758 655.257 544.758 655.257C544.758 655.257 533.004 661.176 530.089 661.458H497.462C497.462 661.458 492.479 661.082 487.684 658.64C487.684 658.64 488.511 642.203 504.025 638.165Z" fill="#02CCC0"/>
<path d="M524.864 649.094C525.202 650.099 525.499 651.115 525.799 652.13C526.102 653.144 526.374 654.168 526.645 655.192C526.905 656.22 527.164 657.248 527.389 658.285C527.612 659.32 527.831 660.362 527.997 661.412L527.749 661.164C528.07 661.197 528.464 661.185 528.827 661.157C529.197 661.132 529.568 661.079 529.938 661.025C530.678 660.894 531.42 660.752 532.148 660.547L532.696 660.402L533.239 660.236C533.599 660.123 533.964 660.018 534.322 659.891L535.397 659.519L536.46 659.109C537.171 658.84 537.867 658.527 538.57 658.239L540.651 657.292L542.712 656.296C543.391 655.945 544.071 655.596 544.758 655.257C544.112 655.665 543.457 656.066 542.803 656.462C542.142 656.849 541.476 657.225 540.805 657.597C540.128 657.955 539.446 658.304 538.759 658.647L537.714 659.132C537.365 659.294 537.018 659.458 536.66 659.597C535.249 660.207 533.794 660.722 532.303 661.132L531.744 661.283L531.178 661.41C530.802 661.506 530.415 661.563 530.034 661.63C529.647 661.683 529.261 661.736 528.869 661.759C528.47 661.786 528.096 661.803 527.656 661.754L527.442 661.729L527.408 661.504C527.091 659.427 526.668 657.356 526.228 655.291L525.556 652.193L524.864 649.094Z" fill="white"/>
<path d="M500.058 646.716C499.597 647.918 499.179 649.125 498.808 650.343C498.44 651.562 498.115 652.79 497.9 654.035C497.78 654.654 497.702 655.28 497.65 655.907C497.585 656.533 497.58 657.162 497.602 657.789C497.648 659.044 499.509 664.949 500.058 666.118C499.284 665.081 497.259 659.126 497.122 657.827C496.964 656.523 497.072 655.206 497.292 653.926C497.414 653.287 497.557 652.652 497.734 652.029C497.919 651.407 498.115 650.789 498.352 650.187C498.817 648.982 499.368 647.807 500.058 646.716Z" fill="white"/>
<path d="M520.618 619.602C520.618 619.602 508.929 615.464 504.052 606.727C504.052 606.727 504.376 599.06 515.119 602.21C522.561 604.393 525.16 614.467 520.618 619.602Z" fill="#07085B"/>
<path d="M629.748 620.142C628.873 620.285 628.007 620.379 627.144 620.501C626.28 620.619 625.431 620.754 624.571 620.966C625.336 620.504 626.226 620.293 627.098 620.165C627.977 620.052 628.867 620.02 629.748 620.142Z" fill="#F99893"/>
<path d="M457.912 782.36H454.427L463.12 748.229L466.394 749.06L457.912 782.36Z" fill="#3D3A55"/>
<path d="M664.258 782.34H667.743L659.05 748.206L655.778 749.039L664.258 782.34Z" fill="#3D3A55"/>
<path d="M627.25 782.34H623.765L632.458 748.206L635.732 749.039L627.25 782.34Z" fill="#3D3A55"/>
<path d="M593.501 660.721L594.771 686.05C594.79 686.425 594.473 686.73 594.098 686.698L592.917 686.595C592.603 686.566 592.36 686.309 592.351 685.996L591.602 660.533C591.602 660.533 592.563 660.06 593.501 660.721Z" fill="#C1215B"/>
<path d="M218.72 734.264H144.728V703.829H218.72V734.264Z" fill="#E03268"/>
<path d="M87.8848 639.682C88.8071 639.746 162.018 639.682 162.018 639.682V709.141H114.56L89.1541 683.755L87.8848 639.682Z" fill="#FF5B7E"/>
<path d="M217.234 678.706C217.234 678.706 166.461 681.738 166.461 678.706C166.461 675.676 166.461 691.914 166.461 691.914C166.461 691.914 191.293 696.365 194.087 696.365C196.881 696.365 209.891 703.254 211.615 703.828C213.339 704.404 217.043 689.018 217.234 688.886C217.427 688.755 217.234 678.706 217.234 678.706Z" fill="#F9537F"/>
<path d="M91.7554 692.105H84.0151C82.4496 692.105 81.1807 690.837 81.1807 689.27V642.517C81.1807 640.952 82.4496 639.682 84.0151 639.682H91.7554C93.3207 639.682 94.5897 640.952 94.5897 642.517V689.27C94.5897 690.837 93.3207 692.105 91.7554 692.105Z" fill="#E03268"/>
<path d="M142.911 678.706H82.9531C77.5576 678.706 73.1836 683.076 73.1836 688.468V722.884C73.1836 736.608 84.3165 747.73 98.0492 747.73L159.784 748.109C159.784 748.109 155.499 746.967 154.794 745.735C151.888 740.656 144.443 727.594 144.443 727.133C144.443 726.559 142.911 678.706 142.911 678.706Z" fill="#F9537F"/>
<path d="M209.381 686.554V720.091C209.381 726.801 203.939 732.239 197.224 732.239H162.921C156.207 732.239 150.764 726.801 150.764 720.091V686.554C150.764 682.22 147.248 678.706 142.911 678.706C138.573 678.706 135.057 682.22 135.057 686.554V720.956C135.057 736.018 147.276 748.228 162.35 748.228H197.796C212.87 748.228 225.089 736.018 225.089 720.956V686.554C225.089 682.22 221.572 678.706 217.234 678.706C212.898 678.706 209.381 682.22 209.381 686.554Z" fill="#FF85A5"/>
<path d="M210.361 764.182L211.61 774.2L218.335 774.723L218.23 765.431L210.361 764.182Z" fill="#FFC0BB"/>
<path d="M228.551 782.057L210.182 782.181C209.78 782.183 209.457 781.868 209.461 781.475L209.466 780.947C209.469 780.554 209.797 780.236 210.199 780.232L228.568 780.108C228.968 780.106 229.292 780.421 229.289 780.813L229.283 781.342C229.281 781.734 228.951 782.055 228.551 782.057Z" fill="#3D3A55"/>
<path d="M210.432 774.312L209.727 779.735C209.641 780.404 210.018 781.009 210.521 781.005L227.989 780.887C228.443 780.885 228.893 780.604 229.137 780.084C229.384 779.548 229.442 778.745 228.669 777.67C227.123 775.521 221.99 775.029 219.494 773.204L211.356 773.258C210.902 773.261 210.51 773.708 210.432 774.312Z" fill="#E03268"/>
<path d="M218.229 776.358C218.103 776.284 218.06 776.076 218.134 775.918C218.483 775.172 219.572 773.359 221.749 773.716C221.875 773.737 221.959 773.899 221.936 774.067V774.072C221.913 774.236 221.799 774.345 221.677 774.324C219.726 774.011 218.799 775.611 218.517 776.235C218.456 776.368 218.334 776.421 218.229 776.358Z" fill="white"/>
<path d="M220.037 777.044C219.911 776.968 219.867 776.762 219.942 776.602C220.292 775.858 221.379 774.043 223.557 774.399C223.683 774.42 223.767 774.582 223.744 774.752V774.758C223.721 774.92 223.606 775.028 223.484 775.009C221.534 774.697 220.607 776.294 220.325 776.92C220.264 777.053 220.142 777.105 220.037 777.044Z" fill="white"/>
<path d="M221.72 777.683C221.594 777.608 221.55 777.4 221.624 777.242C221.973 776.497 223.062 774.681 225.239 775.04C225.365 775.059 225.449 775.223 225.426 775.391V775.396C225.403 775.56 225.289 775.667 225.167 775.648C223.216 775.335 222.29 776.935 222.007 777.559C221.946 777.692 221.824 777.746 221.72 777.683Z" fill="white"/>
<path d="M197.556 764.395L200.528 774.063L207.371 774.11L206.179 767.051L197.556 764.395Z" fill="#FFC0BB"/>
<path d="M136.927 617.753C136.927 617.753 134.883 607.446 140.856 603.822C146.829 600.197 152.984 600.839 157.097 603.278C161.211 605.719 163.414 613.802 161.351 618.306L147.569 613.457L136.927 617.753Z" fill="#07085B"/>
<path d="M217.2 782.236L198.831 782.36C198.43 782.362 198.107 782.048 198.11 781.655L198.115 781.127C198.119 780.734 198.447 780.413 198.848 780.412L217.217 780.288C217.62 780.286 217.942 780.6 217.938 780.993L217.932 781.521C217.93 781.914 217.602 782.234 217.2 782.236Z" fill="#3D3A55"/>
<path d="M199.081 774.491L198.377 779.914C198.29 780.583 198.667 781.187 199.17 781.184L216.638 781.065C217.092 781.064 217.544 780.783 217.786 780.263C218.034 779.727 218.091 778.924 217.319 777.849C215.774 775.7 210.64 775.208 208.142 773.383L200.006 773.438C199.551 773.44 199.16 773.886 199.081 774.491Z" fill="#F9537F"/>
<path d="M206.879 776.535C206.753 776.461 206.709 776.253 206.783 776.095C207.133 775.349 208.221 773.536 210.399 773.892C210.525 773.913 210.609 774.076 210.586 774.245L210.585 774.249C210.563 774.413 210.448 774.52 210.327 774.501C208.374 774.188 207.449 775.788 207.166 776.411C207.106 776.545 206.983 776.598 206.879 776.535Z" fill="white"/>
<path d="M208.687 777.223C208.562 777.146 208.517 776.94 208.592 776.78C208.941 776.036 210.03 774.221 212.208 774.578C212.333 774.599 212.417 774.761 212.394 774.931L212.394 774.936C212.371 775.098 212.257 775.207 212.135 775.188C210.183 774.875 209.258 776.473 208.975 777.099C208.914 777.232 208.792 777.284 208.687 777.223Z" fill="white"/>
<path d="M210.368 777.862C210.243 777.788 210.198 777.58 210.273 777.422C210.622 776.676 211.71 774.861 213.887 775.218C214.013 775.239 214.097 775.403 214.074 775.57V775.576C214.051 775.74 213.937 775.847 213.815 775.828C211.864 775.515 210.938 777.115 210.655 777.738C210.595 777.872 210.472 777.925 210.368 777.862Z" fill="white"/>
<path d="M199.165 781.184C198.713 781.184 198.364 780.694 198.363 780.108C198.363 780.043 198.367 779.98 198.376 779.914L198.829 776.426C198.93 776.419 199.037 776.413 199.149 776.413C200.487 776.413 202.598 777.124 203.831 781.153L199.169 781.184C199.168 781.184 199.166 781.184 199.165 781.184Z" fill="#F24665"/>
<path d="M143.242 627.131L142.243 638.641L152.691 638.154L151.486 627.964L143.242 627.131Z" fill="#FFC0BB"/>
<path d="M152.059 632.81L151.486 627.965L143.241 627.131L142.896 631.117C144.535 632.705 147.483 634.35 152.059 632.81Z" fill="#F99893"/>
<path d="M158.465 619.378C157.837 620.64 158.17 622.061 159.209 622.549C160.249 623.037 161.6 622.41 162.229 621.148C162.857 619.883 162.524 618.465 161.484 617.975C160.445 617.487 159.093 618.114 158.465 619.378Z" fill="#F99893"/>
<path d="M157.588 626.938C157.956 626.398 158.276 625.822 158.541 625.216C159.288 623.588 159.726 621.837 159.981 620.302C160.036 619.972 160.11 619.648 160.191 619.322C160.516 618.014 160.602 616.609 160.377 615.146C159.65 610.436 155.753 606.682 150.901 606.03C144.364 605.153 138.605 609.857 138.198 616.088C137.526 615.669 136.749 615.533 136.04 615.791C134.681 616.283 134.092 618.022 134.725 619.673C135.359 621.324 136.975 622.264 138.334 621.772C138.523 621.704 138.695 621.608 138.853 621.496C139.063 626.833 143.265 631.202 148.631 631.446C151.255 631.564 153.696 630.675 155.592 629.117C155.718 629.028 155.851 628.921 155.991 628.797C156.607 628.252 157.134 627.621 157.588 626.938Z" fill="#FFC0BB"/>
<path d="M148.14 617.644C148.115 618.166 147.659 618.571 147.121 618.546C146.584 618.521 146.168 618.079 146.193 617.556C146.219 617.032 146.675 616.629 147.212 616.654C147.75 616.677 148.165 617.121 148.14 617.644Z" fill="#333333"/>
<path d="M156.473 618.559C156.448 619.081 155.992 619.486 155.454 619.461C154.917 619.436 154.501 618.994 154.526 618.471C154.552 617.947 155.008 617.544 155.545 617.569C156.083 617.592 156.498 618.036 156.473 618.559Z" fill="#333333"/>
<path d="M149.363 615.505C148.867 615.356 148.4 615.242 147.938 615.173C147.477 615.105 147.025 615.091 146.585 615.145C146.147 615.202 145.707 615.293 145.283 615.48C145.058 615.547 144.862 615.677 144.635 615.77C144.416 615.875 144.212 616.01 143.967 616.115C144.09 615.896 144.233 615.68 144.399 615.484C144.583 615.305 144.759 615.103 144.989 614.967C145.417 614.651 145.956 614.47 146.499 614.403C147.046 614.34 147.604 614.416 148.1 614.611C148.593 614.807 149.045 615.099 149.363 615.505Z" fill="#07085B"/>
<path d="M209.5 750.973H94.6079C94.201 750.973 93.8711 750.643 93.8711 750.235V748.227C93.8711 747.819 94.201 747.489 94.6079 747.489H209.5C209.907 747.489 210.237 747.819 210.237 748.227V750.235C210.237 750.643 209.907 750.973 209.5 750.973Z" fill="#3D3A55"/>
<path d="M153.656 615.976C154.05 615.636 154.551 615.434 155.075 615.335C155.6 615.24 156.163 615.268 156.687 615.434C157.206 615.602 157.698 615.882 158.055 616.273C158.253 616.451 158.386 616.681 158.53 616.891C158.654 617.116 158.752 617.352 158.828 617.591C158.608 617.442 158.436 617.272 158.242 617.127C158.037 616.994 157.871 616.828 157.664 616.719C157.286 616.456 156.872 616.285 156.454 616.145C156.032 616.01 155.587 615.938 155.12 615.919C154.653 615.899 154.173 615.922 153.656 615.976Z" fill="#07085B"/>
<path d="M138.353 616.24C137.734 615.678 137.241 615.699 137.241 615.699L137.664 612.406L138.8 610.455C138.8 610.455 143.152 605.257 143.303 605.129C143.454 605.003 146.681 603.39 146.879 603.308C147.077 603.228 151.474 604.044 151.474 604.044C151.474 604.044 159.315 602.793 157.843 606.699C156.372 610.602 150.608 612.459 150.324 612.272C151.282 611.422 151.478 608.909 151.478 608.909C147.286 612.995 139.556 615.817 138.353 616.24Z" fill="#07085B"/>
<path d="M151.585 617.567C151.87 618.013 152.113 618.48 152.333 618.958C152.553 619.437 152.746 619.927 152.897 620.438C152.966 620.696 153.029 620.955 153.048 621.237C153.05 621.308 153.05 621.38 153.041 621.456C153.037 621.495 153.025 621.535 153.017 621.575C153 621.617 152.989 621.659 152.958 621.702C152.942 621.723 152.925 621.744 152.907 621.765L152.865 621.8C152.837 621.822 152.81 621.847 152.781 621.868C152.722 621.908 152.664 621.95 152.603 621.983C152.363 622.126 152.11 622.229 151.853 622.314C151.596 622.4 151.335 622.471 151.068 622.515C151.554 622.292 152.043 622.068 152.459 621.775C152.512 621.739 152.558 621.699 152.606 621.66L152.672 621.599L152.704 621.569L152.713 621.552C152.745 621.5 152.749 621.371 152.736 621.256C152.711 621.018 152.651 620.768 152.579 620.524C152.44 620.03 152.263 619.542 152.094 619.05C151.921 618.56 151.745 618.068 151.585 617.567Z" fill="#F99893"/>
<path d="M153.789 635.803C153.789 635.803 161.97 636.148 166.247 641.354C170.523 646.558 182.653 697.61 182.653 697.61L169.012 696.152C169.012 696.152 151.273 671.901 151.273 671.277C151.273 670.652 153.789 635.803 153.789 635.803Z" fill="#050849"/>
<path d="M137.711 635.885C137.711 635.885 153.371 635.852 153.613 635.87C153.855 635.885 155.056 635.757 155.498 636.22C155.941 636.682 156.704 639.233 154.525 640.482C152.347 641.731 156.977 641.783 151.068 642.824C145.16 643.865 146.93 645.268 142.452 643.447C137.973 641.626 137.396 642.406 137.241 640.793C137.087 639.18 137.711 635.885 137.711 635.885Z" fill="#FFC0BB"/>
<path d="M168.835 659.06C167.927 650.867 165.729 645.373 163.265 641.691C161.423 638.94 158.634 637.027 155.498 636.221C155.484 636.274 154.705 639.184 150.681 639.649C146.618 640.118 137.867 635.876 137.711 635.885L137.711 635.883C133.19 636.165 129.281 637.014 127.244 639.39C123.182 644.124 109.745 677.194 110.057 681.866C110.37 686.537 113.964 686.537 113.964 686.537L150.764 686.555V695.019L177.459 696.842C176.715 696.35 171.409 682.27 168.835 659.06Z" fill="#07085B"/>
<path d="M171.793 655.846C172.028 655.853 181.51 650.112 181.51 650.112L183.282 650.488L182.653 650.951L183.713 650.686L185.437 650.951C185.437 650.951 179.738 657.673 179.642 657.863C179.547 658.056 177.056 659.013 176.865 659.108C176.673 659.204 171.793 655.846 171.793 655.846Z" fill="#DAEEF7"/>
<path d="M156.618 651.259L157.48 650.721L157.875 650.99V650.486L158.414 650.111L172.206 655.566C172.206 655.566 167.788 658.365 167.645 658.257C167.501 658.15 159.635 656.714 159.492 656.499C159.348 656.283 156.618 651.259 156.618 651.259Z" fill="#DAEEF7"/>
<path d="M156.837 651.007L172.469 656.065L185.075 650.579C185.84 650.248 186.68 650.865 186.587 651.695L184.186 673.165C184.146 673.522 183.931 673.837 183.613 674.003L171.509 680.379L160.546 676.323L160.264 675.909L158.843 675.694L154.246 673.993C153.835 673.84 153.577 673.432 153.614 672.998L155.422 651.945C155.481 651.249 156.173 650.791 156.837 651.007Z" fill="#FEB546"/>
<path d="M156.837 651.005C156.172 650.791 155.481 651.249 155.421 651.945L153.616 672.969C153.577 673.421 153.846 673.844 154.272 674.003L158.842 675.694L160.264 675.909L160.546 676.323L167.92 679.052C169.616 678.724 171.3 678.409 171.3 678.409L172.469 656.065L156.837 651.005Z" fill="#F4A640"/>
<path d="M174.802 658.63L184.55 654.37L184.239 658.798L174.685 663.224L174.802 658.63Z" fill="#F4A640"/>
<path d="M180.067 695.073C180.067 695.073 213.074 694.031 220.573 701.11C228.072 708.188 220.783 760.449 219.532 765.334C219.532 765.334 214.948 769.594 209.532 767.93C204.116 766.265 206.199 742.95 206.199 742.95C206.199 742.95 206.824 720.677 205.991 717.554C205.157 714.432 193.699 712.142 193.699 712.142C193.699 712.142 175.992 699.861 177.033 699.861C178.075 699.861 180.067 695.073 180.067 695.073Z" fill="#2B1C35"/>
<path d="M150.765 694.07C150.765 694.07 194.95 688.827 200.991 708.81C207.033 728.793 211.616 768.344 211.616 768.344C211.616 768.344 205.783 771.883 197.866 768.344C197.866 768.344 186.67 725.88 182.477 721.715C178.284 717.553 150.765 720.091 150.765 720.091V694.07Z" fill="#3A2645"/>
<path d="M162.121 681.366C161.953 680.411 161.714 679.473 161.444 678.546C161.169 677.617 160.865 676.704 160.5 675.802L160.459 675.701L160.348 675.695L130.866 674.219C130.976 673.325 131.249 672.448 131.546 671.588C131.859 670.696 132.216 669.819 132.59 668.947C133.343 667.208 134.168 665.502 135.022 663.808C136.737 660.426 138.56 657.096 140.459 653.813L140.429 653.794C138.507 657.066 136.66 660.382 134.921 663.757C134.055 665.444 133.217 667.149 132.45 668.886C132.069 669.756 131.705 670.635 131.383 671.529C131.067 672.425 130.774 673.339 130.664 674.3L130.652 674.395L130.752 674.401L160.216 676.037C160.554 676.885 160.848 677.762 161.109 678.643C161.376 679.56 161.611 680.489 161.776 681.427C161.938 682.367 162.074 683.313 162.077 684.263C162.088 685.168 162.017 686.08 161.778 686.947L153.052 686.694L148.624 686.57L144.194 686.495L144.192 686.537L148.618 686.713L153.044 686.902L161.896 687.268L162.018 687.273L162.053 687.157C162.344 686.213 162.433 685.229 162.428 684.257C162.425 683.283 162.286 682.32 162.121 681.366Z" fill="white"/>
<path d="M171.453 655.758L170.322 679.301L172.048 679.051L173.263 655.758C173.263 655.758 172.351 655.124 171.453 655.758Z" fill="#ED9935"/>
<path d="M172.711 678.029C170.523 678.992 166.085 678.292 166.085 678.292L162.724 677.125C162.254 677.444 161.776 677.768 161.303 678.084C161.35 678.237 161.398 678.391 161.444 678.546C161.714 679.473 161.953 680.411 162.121 681.366C162.285 682.319 162.425 683.282 162.428 684.257C162.429 684.417 162.423 684.575 162.418 684.735L162.891 684.56C163.463 684.674 164.498 684.577 165.933 684.356C167.57 684.146 170.159 683.786 171.29 683.46C172.106 683.225 172.46 682.707 172.61 682.224C173.255 681.831 173.315 681.099 173.237 680.516C173.256 680.477 173.272 680.441 173.284 680.403C173.598 679.421 173.423 679.166 173.262 679.066C173.377 678.948 173.457 678.819 173.492 678.679C173.857 677.223 172.711 678.029 172.711 678.029Z" fill="#FFC0BB"/>
<path d="M173.262 680.437C172.999 680.744 172.659 680.976 172.304 681.173C171.949 681.369 171.564 681.51 171.173 681.619C170.779 681.718 170.377 681.785 169.972 681.802C169.771 681.815 169.568 681.804 169.367 681.808C169.166 681.792 168.965 681.773 168.766 681.75C169.168 681.729 169.566 681.716 169.961 681.667C170.356 681.619 170.745 681.548 171.128 681.449C171.51 681.348 171.883 681.217 172.244 681.053C172.602 680.887 172.95 680.69 173.262 680.437Z" fill="#F99893"/>
<path d="M172.615 682.228C172.329 682.512 171.971 682.718 171.603 682.886C171.232 683.054 170.838 683.165 170.44 683.241C170.039 683.308 169.633 683.344 169.228 683.329C169.026 683.327 168.825 683.3 168.624 683.287C168.425 683.256 168.226 683.222 168.029 683.182C168.432 683.193 168.83 683.212 169.228 683.193C169.625 683.176 170.019 683.138 170.408 683.069C170.797 682.997 171.179 682.896 171.552 682.76C171.922 682.623 172.285 682.455 172.615 682.228Z" fill="#F99893"/>
<path d="M173.262 679.066C172.999 679.373 172.659 679.606 172.304 679.802C171.949 679.999 171.564 680.14 171.173 680.248C170.779 680.346 170.377 680.412 169.972 680.429C169.771 680.445 169.568 680.433 169.367 680.435C169.166 680.42 168.965 680.403 168.766 680.378C169.168 680.359 169.566 680.346 169.961 680.296C170.356 680.246 170.745 680.178 171.128 680.079C171.51 679.976 171.883 679.844 172.244 679.682C172.602 679.514 172.95 679.318 173.262 679.066Z" fill="#F99893"/>
<path d="M147.634 624.441C148.551 624.548 149.444 624.704 150.341 624.83C151.239 624.959 152.127 625.068 153.049 625.104C152.15 625.345 151.2 625.301 150.291 625.177C149.379 625.038 148.48 624.814 147.634 624.441Z" fill="#F99893"/>
<path d="M96.2283 782.294H92.8926L101.212 749.629L104.345 750.426L96.2283 782.294Z" fill="#3D3A55"/>
<path d="M157.393 782.294H154.058L162.377 749.629L165.51 750.426L157.393 782.294Z" fill="#3D3A55"/>
<path d="M136.861 782.294H140.196L131.877 749.629L128.744 750.426L136.861 782.294Z" fill="#3D3A55"/>
<path d="M620.923 526.975H518.425V521.111H620.923V526.975Z" fill="#4188E4"/>
<path d="M635.998 576.911H533.498V571.048H635.998V576.911Z" fill="#4188E4"/>
<path d="M264.123 754.488H261.217V517.236H264.123V754.488Z" fill="#09083C"/>
<path d="M295.251 754.488H292.345V517.236H295.251V754.488Z" fill="#09083C"/>
<path d="M293.798 523.304H262.67V520.846H293.798V523.304Z" fill="#09083C"/>
<path d="M293.798 539.225H262.67V536.769H293.798V539.225Z" fill="#09083C"/>
<path d="M293.798 555.148H262.67V552.692H293.798V555.148Z" fill="#09083C"/>
<path d="M293.798 571.072H262.67V568.616H293.798V571.072Z" fill="#09083C"/>
<path d="M293.798 586.996H262.67V584.54H293.798V586.996Z" fill="#09083C"/>
<path d="M293.798 602.92H262.67V600.464H293.798V602.92Z" fill="#09083C"/>
<path d="M293.798 618.844H262.67V616.388H293.798V618.844Z" fill="#09083C"/>
<path d="M293.798 634.768H262.67V632.31H293.798V634.768Z" fill="#09083C"/>
<path d="M293.798 650.691H262.67V648.234H293.798V650.691Z" fill="#09083C"/>
<path d="M293.798 666.616H262.67V664.158H293.798V666.616Z" fill="#09083C"/>
<path d="M293.798 682.536H262.67V680.08H293.798V682.536Z" fill="#09083C"/>
<path d="M293.798 698.46H262.67V696.004H293.798V698.46Z" fill="#09083C"/>
<path d="M293.798 714.385H262.67V711.929H293.798V714.385Z" fill="#09083C"/>
<path d="M683.917 486.942C683.917 502.471 671.319 515.058 655.778 515.058C640.238 515.058 627.64 502.471 627.64 486.942C627.64 471.413 640.238 458.824 655.778 458.824C671.319 458.824 683.917 471.413 683.917 486.942Z" fill="#4188E4"/>
<path d="M680.515 485.389C681.373 499.041 670.993 510.802 657.331 511.659C643.668 512.515 631.898 502.144 631.04 488.491C630.183 474.84 640.564 463.079 654.226 462.223C667.889 461.365 679.657 471.738 680.515 485.389Z" fill="white"/>
<path d="M639.78 486.494V487.135H631.436V486.494H639.78Z" fill="#B0C1EC"/>
<path d="M680.169 486.494V487.135H671.825V486.494H680.169Z" fill="#B0C1EC"/>
<path d="M656.063 471.125H655.422V462.788H656.063V471.125Z" fill="#B0C1EC"/>
<path d="M656.063 511.324H655.422V502.988H656.063V511.324Z" fill="#B0C1EC"/>
<path d="M656.467 486.942C656.467 487.323 656.159 487.632 655.777 487.632C655.396 487.632 655.087 487.323 655.087 486.942C655.087 486.56 655.396 486.251 655.777 486.251C656.159 486.251 656.467 486.56 656.467 486.942Z" fill="#B0C1EC"/>
<path d="M655.778 487.249C655.698 487.249 655.62 487.219 655.559 487.158L643.148 474.758C643.028 474.637 643.028 474.441 643.148 474.321C643.27 474.201 643.464 474.201 643.584 474.321L655.996 486.721C656.116 486.843 656.116 487.037 655.996 487.158C655.937 487.219 655.857 487.249 655.778 487.249Z" fill="#B0C1EC"/>
<path d="M659.766 499.473C659.717 499.449 659.675 499.403 659.656 499.344L655.644 487.238C655.604 487.119 655.668 486.992 655.787 486.953C655.903 486.913 656.031 486.978 656.069 487.096L660.081 499.203C660.121 499.321 660.056 499.449 659.938 499.487C659.879 499.506 659.818 499.5 659.766 499.473Z" fill="#B0C1EC"/>
<path d="M747.268 667.411H721.975C719.789 667.411 718.017 665.638 718.017 663.454C718.017 661.269 719.789 659.495 721.975 659.495H747.268C747.504 659.495 747.695 659.305 747.695 659.068C747.695 658.83 747.504 658.638 747.268 658.638H721.975C719.313 658.638 717.158 660.791 717.158 663.454C717.158 666.112 719.313 668.271 721.975 668.271H747.268C747.504 668.271 747.695 668.078 747.695 667.842C747.695 667.607 747.504 667.411 747.268 667.411Z" fill="#23ADE0"/>
<path d="M747.051 659.495H723.01C720.826 659.495 719.053 661.269 719.053 663.455C719.053 665.638 720.826 667.415 723.01 667.415H747.051V659.495Z" fill="#D4D0CE"/>
<path d="M747.051 666.43H722.443C720.1 666.43 719.053 664.612 719.053 663.455C719.053 661.269 720.826 659.495 723.01 659.495H721.977C719.792 659.495 718.019 661.269 718.019 663.455C718.019 665.638 719.792 667.415 721.977 667.415H747.051V666.43Z" fill="#BDB9B3"/>
<path d="M724.314 661.04C730.651 661.126 736.987 661.126 743.324 661.04C736.987 660.954 730.651 660.954 724.314 661.04Z" fill="#9E9798"/>
<path d="M720.177 663.454L727.428 663.511L734.679 663.454L727.428 663.398L720.177 663.454Z" fill="#9E9798"/>
<path d="M728.094 665.584L737.572 665.637L747.051 665.584L737.572 665.527L728.094 665.584Z" fill="#9E9798"/>
<path d="M726.822 664.33L736.936 664.383L747.051 664.33L736.936 664.273L726.822 664.33Z" fill="#9E9798"/>
<path d="M726.822 662.105C733.565 662.212 740.308 662.212 747.051 662.105C740.308 661.999 733.565 661.999 726.822 662.105Z" fill="#9E9798"/>
<path d="M739.031 660.265L743.041 660.321L747.051 660.265L743.041 660.209L739.031 660.265Z" fill="#9E9798"/>
<path d="M723.878 666.702L734.757 666.758L745.635 666.702L734.757 666.646L723.878 666.702Z" fill="#9E9798"/>
<path d="M723.185 662.612C725.795 662.719 728.404 662.719 731.015 662.612C728.404 662.506 725.795 662.506 723.185 662.612Z" fill="#9E9798"/>
<path d="M748.809 669.799H720.318C718.678 669.799 717.351 671.133 717.351 672.786C717.351 674.435 718.678 675.775 720.318 675.775H748.809V669.799Z" fill="#D4D0CE"/>
<path d="M749.042 675.775H719.535C717.899 675.757 716.575 674.423 716.575 672.786C716.575 671.148 717.899 669.814 719.535 669.799H749.042C749.462 669.799 749.806 669.455 749.806 669.034C749.806 668.615 749.462 668.271 749.042 668.271H719.169C716.866 668.473 715.05 670.431 715.05 672.786C715.05 675.141 716.866 677.101 719.169 677.3H749.042C749.462 677.3 749.806 676.956 749.806 676.538C749.806 676.117 749.462 675.775 749.042 675.775Z" fill="#2EB054"/>
<path d="M723.895 670.905C731.137 670.98 738.379 670.98 745.62 670.905C738.379 670.831 731.137 670.831 723.895 670.905Z" fill="#9E9798"/>
<path d="M720.359 672.785L728.037 672.833L735.714 672.785L728.037 672.737L720.359 672.785Z" fill="#9E9798"/>
<path d="M727.131 674.138L737.97 674.186L748.809 674.138L737.97 674.088L727.131 674.138Z" fill="#9E9798"/>
<path d="M726.043 673.335L737.426 673.382L748.809 673.335L737.426 673.287L726.043 673.335Z" fill="#9E9798"/>
<path d="M726.043 671.818C733.631 671.907 741.22 671.91 748.809 671.818C741.22 671.726 733.631 671.726 726.043 671.818Z" fill="#9E9798"/>
<path d="M741.949 670.244L745.379 670.291L748.809 670.244L745.379 670.196L741.949 670.244Z" fill="#9E9798"/>
<path d="M723.526 674.601L735.561 674.648L747.598 674.601L735.561 674.554L723.526 674.601Z" fill="#9E9798"/>
<path d="M722.932 672.249C726.149 672.34 729.365 672.34 732.581 672.249C729.365 672.157 726.149 672.159 722.932 672.249Z" fill="#9E9798"/>
<path d="M720.191 674.945C718.012 674.945 717.351 673.405 717.351 672.786C717.351 671.133 718.678 669.799 720.318 669.799H719.543C717.905 669.799 716.574 671.133 716.574 672.786C716.574 674.435 717.905 675.775 719.543 675.775H748.809V674.945H720.191Z" fill="#BDB9B3"/>
<path d="M747.234 678.259H722.116C720.318 678.259 718.862 679.727 718.862 681.533C718.862 683.342 720.318 684.811 722.116 684.811H747.234V678.259Z" fill="#D4D0CE"/>
<path d="M747.323 684.804H721.247C719.462 684.783 718.012 683.318 718.012 681.532C718.012 679.747 719.462 678.285 721.247 678.267H747.323C747.589 678.267 747.807 678.05 747.807 677.783C747.807 677.513 747.589 677.3 747.323 677.3H720.899C719.855 677.394 718.887 677.875 718.169 678.658C717.445 679.447 717.047 680.467 717.047 681.532C717.047 682.6 717.445 683.62 718.169 684.412C718.887 685.189 719.855 685.676 720.899 685.768H747.323C747.589 685.768 747.807 685.554 747.807 685.284C747.807 685.02 747.589 684.804 747.323 684.804Z" fill="#EE7936"/>
<path d="M727.63 679.471C731.96 679.551 736.289 679.551 740.619 679.471C736.289 679.391 731.96 679.391 727.63 679.471Z" fill="#9E9798"/>
<path d="M722.16 681.533L729.733 681.583L737.306 681.533L729.733 681.479L722.16 681.533Z" fill="#9E9798"/>
<path d="M731.175 683.016L739.205 683.069L747.234 683.016L739.205 682.962L731.175 683.016Z" fill="#9E9798"/>
<path d="M729.984 682.137L738.609 682.19L747.234 682.137L738.609 682.083L729.984 682.137Z" fill="#9E9798"/>
<path d="M729.984 680.47C735.734 680.568 741.484 680.571 747.234 680.47C741.484 680.369 735.734 680.369 729.984 680.47Z" fill="#9E9798"/>
<path d="M736.592 678.746L741.914 678.8L747.234 678.746L741.914 678.693L736.592 678.746Z" fill="#9E9798"/>
<path d="M727.224 683.526L734.14 683.579L741.055 683.526L734.14 683.476L727.224 683.526Z" fill="#9E9798"/>
<path d="M726.574 680.945C729.007 681.042 731.44 681.042 733.874 680.945C731.44 680.844 729.007 680.844 726.574 680.945Z" fill="#9E9798"/>
<path d="M721.975 683.903C719.588 683.903 718.862 682.212 718.862 681.533C718.862 679.727 720.318 678.259 722.116 678.259H721.266C719.469 678.259 718.012 679.727 718.012 681.533C718.012 683.342 719.469 684.811 721.266 684.811H747.234V683.903H721.975Z" fill="#BDB9B3"/>
<path d="M745.819 693.731C745.819 693.731 746.66 692.022 746.66 689.807C746.66 687.591 745.819 685.883 745.819 685.883H718.658C718.658 685.883 718.195 686.826 718.195 689.807C718.195 692.788 718.658 693.731 718.658 693.731H745.819Z" fill="#6BBE5E"/>
<path d="M724.196 691.723C725.255 691.723 726.109 690.863 726.109 689.807C726.109 688.749 725.255 687.892 724.196 687.892C723.138 687.892 722.279 688.749 722.279 689.807C722.279 690.863 723.138 691.723 724.196 691.723Z" fill="#89C65D"/>
<path d="M719.467 689.807C719.467 686.826 719.929 685.883 719.929 685.883H721.784C721.784 685.883 721.321 686.826 721.321 689.807C721.321 692.788 721.784 693.731 721.784 693.731H719.929C719.929 693.731 719.467 692.788 719.467 689.807Z" fill="#89C65D"/>
<path d="M743.771 689.807C743.771 686.826 743.306 685.883 743.306 685.883H741.452C741.452 685.883 741.917 686.826 741.917 689.807C741.917 692.788 741.452 693.731 741.452 693.731H743.306C743.306 693.731 743.771 692.788 743.771 689.807Z" fill="#89C65D"/>
<path d="M745.467 689.807C745.467 686.826 745.002 685.883 745.002 685.883H744.075C744.075 685.883 744.54 686.826 744.54 689.807C744.54 692.788 744.075 693.731 744.075 693.731H745.002C745.002 693.731 745.467 692.788 745.467 689.807Z" fill="#89C65D"/>
<path d="M752.151 701.576C752.151 701.576 752.992 699.868 752.992 697.652C752.992 695.44 752.151 693.731 752.151 693.731H712.325C712.325 693.731 711.863 694.671 711.863 697.652C711.863 700.63 712.325 701.576 712.325 701.576H752.151Z" fill="#35426B"/>
<path d="M750.102 697.652C750.102 694.671 749.638 693.731 749.638 693.731H747.784C747.784 693.731 748.247 694.671 748.247 697.652C748.247 700.63 747.784 701.576 747.784 701.576H749.638C749.638 701.576 750.102 700.63 750.102 697.652Z" fill="#435789"/>
<path d="M751.797 697.652C751.797 694.671 751.334 693.731 751.334 693.731H750.407C750.407 693.731 750.868 694.671 750.868 697.652C750.868 700.63 750.407 701.576 750.407 701.576H751.334C751.334 701.576 751.797 700.63 751.797 697.652Z" fill="#435789"/>
<path d="M750.355 709.416C750.355 709.416 751.198 707.704 751.198 705.492C751.198 703.279 750.355 701.567 750.355 701.567H714.122C714.122 701.567 713.657 702.511 713.657 705.492C713.657 708.472 714.122 709.416 714.122 709.416H750.355Z" fill="#22ADE4"/>
<path d="M770.164 788.625H710.342V724.008H770.164V788.625Z" fill="#F89D5F"/>
<path d="M800.086 709.326H770.163C766.109 709.326 762.822 712.61 762.822 716.664C762.822 720.722 766.109 724.008 770.163 724.008V788.625H807.428V716.664C807.428 712.61 804.141 709.326 800.086 709.326Z" fill="#EE7936"/>
<path d="M762.822 716.664C762.822 712.61 766.11 709.326 770.164 709.326H710.342C706.287 709.326 703 712.61 703 716.664C703 720.722 706.287 724.008 710.342 724.008H770.164C766.11 724.008 762.822 720.722 762.822 716.664Z" fill="#FBB363"/>
<path d="M767.068 745.619H712.846V727.95H767.068V745.619Z" fill="#FBB363"/>
<path d="M767.068 765.403H712.846V747.74H767.068V765.403Z" fill="#FBB363"/>
<path d="M767.068 784.681H712.846V767.019H767.068V784.681Z" fill="#FBB363"/>
<path d="M749.993 733.076C749.993 733.954 749.286 734.66 748.408 734.66H731.505C730.631 734.66 729.922 733.954 729.922 733.076C729.922 732.204 730.631 731.495 731.505 731.495H748.408C749.286 731.495 749.993 732.204 749.993 733.076Z" fill="#F89D5F"/>
<path d="M749.993 753.146C749.993 754.021 749.286 754.733 748.408 754.733H731.505C730.631 754.733 729.922 754.021 729.922 753.146C729.922 752.274 730.631 751.562 731.505 751.562H748.408C749.286 751.562 749.993 752.274 749.993 753.146Z" fill="#F89D5F"/>
<path d="M749.993 773.22C749.993 774.092 749.286 774.804 748.408 774.804H731.505C730.631 774.804 729.922 774.092 729.922 773.22C729.922 772.343 730.631 771.637 731.505 771.637H748.408C749.286 771.637 749.993 772.343 749.993 773.22Z" fill="#F89D5F"/>
<path d="M738.289 689.722H777.227C778.941 689.722 780.333 688.331 780.333 686.617C780.333 684.902 778.941 683.511 777.227 683.511H738.289C738.102 683.511 737.952 683.36 737.952 683.176C737.952 682.989 738.102 682.838 738.289 682.838H777.227C779.314 682.838 781.004 684.529 781.004 686.617C781.004 688.702 779.314 690.396 777.227 690.396H738.289C738.102 690.396 737.952 690.244 737.952 690.057C737.952 689.873 738.102 689.722 738.289 689.722Z" fill="#F68B41"/>
<path d="M738.457 683.511H776.413C778.127 683.511 779.518 684.902 779.518 686.616C779.518 688.331 778.127 689.722 776.413 689.722H738.457V683.511Z" fill="#D4D0CE"/>
<path d="M738.457 688.953H776.858C778.697 688.953 779.518 687.527 779.518 686.616C779.518 684.902 778.127 683.511 776.413 683.511H777.223C778.938 683.511 780.328 684.902 780.328 686.616C780.328 688.331 778.938 689.722 777.223 689.722H738.457V688.953Z" fill="#BDB9B3"/>
<path d="M775.393 684.723L763.581 684.664L751.77 684.723L763.581 684.78L775.393 684.723Z" fill="#9E9798"/>
<path d="M778.634 686.616L768.594 686.568L758.553 686.616L768.594 686.666L778.634 686.616Z" fill="#9E9798"/>
<path d="M772.427 688.286L755.442 688.238L738.457 688.286L755.442 688.334L772.427 688.286Z" fill="#9E9798"/>
<path d="M773.423 687.304L755.939 687.257L738.457 687.304L755.939 687.351L773.423 687.304Z" fill="#9E9798"/>
<path d="M773.423 685.556L755.939 685.482L738.457 685.556L755.939 685.631L773.423 685.556Z" fill="#9E9798"/>
<path d="M755.138 684.116L746.797 684.065L738.457 684.116L746.797 684.164L755.138 684.116Z" fill="#9E9798"/>
<path d="M775.732 689.164L757.651 689.116L739.569 689.164L757.651 689.214L775.732 689.164Z" fill="#9E9798"/>
<path d="M776.274 685.955C771.325 685.863 766.376 685.863 761.427 685.955C766.376 686.049 771.325 686.047 776.274 685.955Z" fill="#9E9798"/>
<path d="M770.353 664.496C770.353 664.496 771.006 665.825 771.006 667.548C771.006 669.271 770.353 670.6 770.353 670.6H749.219C749.219 670.6 748.86 669.867 748.86 667.548C748.86 665.229 749.219 664.496 749.219 664.496H770.353Z" fill="#6BBE5E"/>
<path d="M753.528 666.056C754.353 666.056 755.018 666.726 755.018 667.548C755.018 668.369 754.353 669.036 753.528 669.036C752.704 669.036 752.038 668.369 752.038 667.548C752.038 666.726 752.704 666.056 753.528 666.056Z" fill="#89C65D"/>
<path d="M749.849 667.548C749.849 669.867 750.21 670.6 750.21 670.6H751.653C751.653 670.6 751.292 669.867 751.292 667.548C751.292 665.229 751.653 664.496 751.653 664.496H750.21C750.21 664.496 749.849 665.229 749.849 667.548Z" fill="#89C65D"/>
<path d="M768.758 667.548C768.758 669.867 768.397 670.6 768.397 670.6H766.955C766.955 670.6 767.315 669.867 767.315 667.548C767.315 665.229 766.955 664.496 766.955 664.496H768.397C768.397 664.496 768.758 665.229 768.758 667.548Z" fill="#89C65D"/>
<path d="M770.075 667.548C770.075 669.867 769.716 670.6 769.716 670.6H768.993C768.993 670.6 769.354 669.867 769.354 667.548C769.354 665.229 768.993 664.496 768.993 664.496H769.716C769.716 664.496 770.075 665.229 770.075 667.548Z" fill="#89C65D"/>
<path d="M772.205 639C772.205 639 772.976 640.566 772.976 642.595C772.976 644.626 772.205 646.189 772.205 646.189H747.316C747.316 646.189 746.892 645.327 746.892 642.595C746.892 639.866 747.316 639 747.316 639H772.205Z" fill="#919598"/>
<path d="M750.321 639C750.321 639 750.201 639.246 750.084 639.886C749.436 640.275 748.969 641.34 748.969 642.595C748.969 643.846 749.436 644.911 750.084 645.302C750.201 645.943 750.321 646.189 750.321 646.189H752.019C752.019 646.189 751.835 645.816 751.709 644.784C752.068 644.256 752.298 643.473 752.298 642.595C752.298 641.717 752.068 640.931 751.709 640.406C751.835 639.37 752.019 639 752.019 639H750.321Z" fill="#AFB3B2"/>
<path d="M770.327 642.595C770.327 645.327 769.9 646.189 769.9 646.189H768.202C768.202 646.189 768.628 645.327 768.628 642.595C768.628 639.866 768.202 639 768.202 639H769.9C769.9 639 770.327 639.866 770.327 642.595Z" fill="#AFB3B2"/>
<path d="M771.881 642.595C771.881 645.327 771.458 646.189 771.458 646.189H770.606C770.606 646.189 771.032 645.327 771.032 642.595C771.032 639.866 770.606 639 770.606 639H771.458C771.458 639 771.881 639.866 771.881 642.595Z" fill="#AFB3B2"/>
<path d="M775.277 658.392C775.277 658.392 775.935 659.72 775.935 661.443C775.935 663.167 775.277 664.496 775.277 664.496H744.294C744.294 664.496 743.933 663.763 743.933 661.443C743.933 659.127 744.294 658.392 744.294 658.392H775.277Z" fill="#35426B"/>
<path d="M744.922 661.443C744.922 663.763 745.285 664.496 745.285 664.496H746.727C746.727 664.496 746.365 663.763 746.365 661.443C746.365 659.127 746.727 658.392 746.727 658.392H745.285C745.285 658.392 744.922 659.127 744.922 661.443Z" fill="#435789"/>
<path d="M773.685 661.443C773.685 663.763 773.323 664.496 773.323 664.496H771.88C771.88 664.496 772.241 663.763 772.241 661.443C772.241 659.127 771.88 658.392 771.88 658.392H773.323C773.323 658.392 773.685 659.127 773.685 661.443Z" fill="#435789"/>
<path d="M775.006 661.443C775.006 663.763 774.643 664.496 774.643 664.496H773.921C773.921 664.496 774.282 663.763 774.282 661.443C774.282 659.127 773.921 658.392 773.921 658.392H774.643C774.643 658.392 775.006 659.127 775.006 661.443Z" fill="#435789"/>
<path d="M770.353 646.189C770.353 646.189 771.006 647.518 771.006 649.242C771.006 650.964 770.353 652.294 770.353 652.294H749.219C749.219 652.294 748.86 651.558 748.86 649.242C748.86 646.922 749.219 646.189 749.219 646.189H770.353Z" fill="#F68B41"/>
<path d="M751.409 649.242C751.409 651.558 751.771 652.294 751.771 652.294H753.215C753.215 652.294 752.852 651.558 752.852 649.242C752.852 646.922 753.215 646.189 753.215 646.189H751.771C751.771 646.189 751.409 646.922 751.409 649.242Z" fill="#FAB683"/>
<path d="M756.907 649.242C756.907 651.558 757.269 652.294 757.269 652.294H764.047C764.047 652.294 764.294 651.558 764.294 649.242C764.294 646.922 764.047 646.189 764.047 646.189H757.269C757.269 646.189 756.907 646.922 756.907 649.242Z" fill="#FAB683"/>
<path d="M750.091 649.242C750.091 651.558 750.453 652.294 750.453 652.294H751.173C751.173 652.294 750.813 651.558 750.813 649.242C750.813 646.922 751.173 646.189 751.173 646.189H750.453C750.453 646.189 750.091 646.922 750.091 649.242Z" fill="#FAB683"/>
<path d="M773.882 652.294C773.882 652.294 774.537 653.623 774.537 655.346C774.537 657.072 773.882 658.398 773.882 658.398H745.692C745.692 658.398 745.33 657.666 745.33 655.346C745.33 653.026 745.692 652.294 745.692 652.294H773.882Z" fill="#22ADE4"/>
<path d="M746.318 655.346C746.318 657.666 746.679 658.398 746.679 658.398H748.122C748.122 658.398 747.761 657.666 747.761 655.346C747.761 653.026 748.122 652.294 748.122 652.294H746.679C746.679 652.294 746.318 653.026 746.318 655.346Z" fill="#4FC0E9"/>
<path d="M743.441 682.838C743.441 682.838 742.757 681.453 742.757 679.646C742.757 677.846 743.441 676.458 743.441 676.458H775.827C775.827 676.458 776.205 677.223 776.205 679.646C776.205 682.073 775.827 682.838 775.827 682.838H743.441Z" fill="#35426B"/>
<path d="M775.172 679.647C775.172 677.223 774.795 676.458 774.795 676.458H773.288C773.288 676.458 773.662 677.223 773.662 679.647C773.662 682.073 773.288 682.838 773.288 682.838H774.795C774.795 682.838 775.172 682.073 775.172 679.647Z" fill="#435789"/>
<path d="M745.107 679.647C745.107 677.223 745.485 676.458 745.485 676.458H746.993C746.993 676.458 746.615 677.223 746.615 679.647C746.615 682.073 746.993 682.838 746.993 682.838H745.485C745.485 682.838 745.107 682.073 745.107 679.647Z" fill="#435789"/>
<path d="M743.728 679.647C743.728 677.223 744.106 676.458 744.106 676.458H744.859C744.859 676.458 744.484 677.223 744.484 679.647C744.484 682.073 744.859 682.838 744.859 682.838H744.106C744.106 682.838 743.728 682.073 743.728 679.647Z" fill="#435789"/>
<path d="M746.735 676.458C746.735 676.458 746.108 675.185 746.108 673.53C746.108 671.872 746.735 670.6 746.735 670.6H773.794C773.794 670.6 774.141 671.303 774.141 673.53C774.141 675.751 773.794 676.458 773.794 676.458H746.735Z" fill="#22ADE4"/>
<path d="M773.191 673.53C773.191 671.303 772.845 670.6 772.845 670.6H771.461C771.461 670.6 771.807 671.303 771.807 673.53C771.807 675.751 771.461 676.458 771.461 676.458H772.845C772.845 676.458 773.191 675.751 773.191 673.53Z" fill="#4FC0E9"/>
<path d="M759.515 696.546H759.365V690.997H759.515C759.681 690.997 759.816 690.863 759.816 690.697C759.816 690.531 761.512 690.395 761.345 690.395H741.783C739.918 690.395 738.406 691.907 738.406 693.773C738.406 695.632 739.918 697.145 741.783 697.145H761.152C761.318 697.145 759.816 697.015 759.816 696.848C759.816 696.682 759.681 696.546 759.515 696.546Z" fill="#1085A6"/>
<path d="M777.823 696.546H760.09C758.56 696.546 757.315 695.303 757.315 693.773C757.315 692.236 758.56 690.997 760.09 690.997H777.823C777.988 690.997 778.124 690.863 778.124 690.697C778.124 690.531 777.988 690.395 777.823 690.395H760.09C758.226 690.395 756.714 691.907 756.714 693.773C756.714 695.632 758.226 697.145 760.09 697.145H777.823C777.988 697.145 778.124 697.015 778.124 696.848C778.124 696.682 777.988 696.546 777.823 696.546Z" fill="#23ADE0"/>
<path d="M777.671 690.997H760.819C759.287 690.997 758.045 692.237 758.045 693.773C758.045 695.307 759.287 696.549 760.819 696.549H777.671V690.997Z" fill="#D4D0CE"/>
<path d="M777.671 695.858H760.42C758.778 695.858 758.045 694.583 758.045 693.773C758.045 692.237 759.287 690.997 760.819 690.997H760.094C758.563 690.997 757.32 692.237 757.32 693.773C757.32 695.307 758.563 696.549 760.094 696.549H777.671V695.858Z" fill="#BDB9B3"/>
<path d="M761.73 692.079C766.174 692.171 770.615 692.174 775.059 692.079C770.615 691.984 766.174 691.984 761.73 692.079Z" fill="#9E9798"/>
<path d="M758.83 693.773C762.22 693.85 765.608 693.85 768.997 693.773C765.608 693.696 762.22 693.696 758.83 693.773Z" fill="#9E9798"/>
<path d="M764.382 695.265C768.811 695.342 773.242 695.342 777.671 695.265C773.242 695.188 768.811 695.188 764.382 695.265Z" fill="#9E9798"/>
<path d="M763.49 694.384C768.217 694.461 772.944 694.461 777.671 694.384C772.944 694.31 768.217 694.31 763.49 694.384Z" fill="#9E9798"/>
<path d="M763.49 692.827C768.217 692.943 772.944 692.943 777.671 692.827C772.944 692.711 768.217 692.711 763.49 692.827Z" fill="#9E9798"/>
<path d="M772.047 691.534C773.922 691.611 775.797 691.611 777.671 691.534C775.797 691.46 773.922 691.46 772.047 691.534Z" fill="#9E9798"/>
<path d="M761.427 696.051C766.51 696.125 771.593 696.125 776.676 696.051C771.593 695.974 766.51 695.974 761.427 696.051Z" fill="#9E9798"/>
<path d="M760.942 693.18C762.771 693.295 764.599 693.295 766.429 693.18C764.599 693.064 762.771 693.064 760.942 693.18Z" fill="#9E9798"/>
<path d="M763.785 702.41H763.623V698.219H763.785C764.082 698.219 764.319 697.976 764.319 697.682C764.319 697.389 764.082 697.146 763.785 697.146H736.199C734.584 697.291 733.311 698.661 733.311 700.313C733.311 701.965 734.584 703.338 736.199 703.478H763.785C764.082 703.478 764.319 703.24 764.319 702.944C764.319 702.648 764.082 702.41 763.785 702.41Z" fill="#1D7040"/>
<path d="M781.933 698.219H761.958C760.81 698.219 759.879 699.156 759.879 700.313C759.879 701.473 760.81 702.41 761.958 702.41H781.933V698.219Z" fill="#D4D0CE"/>
<path d="M782.095 702.41H761.409C760.262 702.398 759.334 701.461 759.334 700.313C759.334 699.165 760.262 698.231 761.409 698.219H782.095C782.387 698.219 782.628 697.976 782.628 697.682C782.628 697.389 782.387 697.146 782.095 697.146H761.153C759.537 697.291 758.265 698.661 758.265 700.313C758.265 701.965 759.537 703.338 761.153 703.478H782.095C782.387 703.478 782.628 703.24 782.628 702.944C782.628 702.648 782.387 702.41 782.095 702.41Z" fill="#2EB054"/>
<path d="M764.466 698.994C769.543 699.073 774.62 699.073 779.696 698.994C774.62 698.916 769.543 698.916 764.466 698.994Z" fill="#9E9798"/>
<path d="M761.988 700.313L767.369 700.367L772.749 700.313L767.369 700.26L761.988 700.313Z" fill="#9E9798"/>
<path d="M766.734 701.259L774.334 701.31L781.933 701.259L774.334 701.209L766.734 701.259Z" fill="#9E9798"/>
<path d="M765.97 700.699L773.951 700.749L781.933 700.699L773.951 700.646L765.97 700.699Z" fill="#9E9798"/>
<path d="M765.97 699.633C771.291 699.734 776.612 699.734 781.933 699.633C776.612 699.535 771.291 699.535 765.97 699.633Z" fill="#9E9798"/>
<path d="M764.206 701.589L772.643 701.639L781.081 701.589L772.643 701.535L764.206 701.589Z" fill="#9E9798"/>
<path d="M763.792 699.933C766.047 700.033 768.301 700.033 770.555 699.933C768.301 699.835 766.047 699.835 763.792 699.933Z" fill="#9E9798"/>
<path d="M761.87 701.828C760.342 701.828 759.879 700.749 759.879 700.313C759.879 699.156 760.81 698.219 761.958 698.219H761.417C760.265 698.219 759.334 699.156 759.334 700.313C759.334 701.473 760.265 702.41 761.417 702.41H781.933V701.828H761.87Z" fill="#BDB9B3"/>
<path d="M762.767 704.154C762.954 704.154 763.105 703.999 763.105 703.813C763.105 703.631 762.954 703.478 762.767 703.478H744.241C743.512 703.543 742.831 703.881 742.329 704.43C741.821 704.984 741.542 705.699 741.542 706.447C741.542 707.194 741.821 707.909 742.329 708.46C742.831 709.009 743.512 709.35 744.241 709.416H762.767C762.954 709.416 763.105 709.261 763.105 709.077C763.105 708.891 762.954 708.736 762.767 708.736H762.705V704.154H762.767Z" fill="#4D5B8D"/>
<path d="M777.085 704.151H763.403C762.142 704.151 761.123 705.178 761.123 706.447C761.123 707.714 762.142 708.743 763.403 708.743H777.085V704.151Z" fill="#D4D0CE"/>
<path d="M777.146 708.736H762.796C761.545 708.725 760.529 707.695 760.529 706.447C760.529 705.195 761.545 704.169 762.796 704.154H777.146C777.333 704.154 777.484 703.999 777.484 703.813C777.484 703.631 777.333 703.478 777.146 703.478H762.553C761.82 703.543 761.141 703.881 760.638 704.43C760.132 704.984 759.853 705.699 759.853 706.447C759.853 707.194 760.132 707.909 760.638 708.46C761.141 709.009 761.82 709.35 762.553 709.416H777.146C777.333 709.416 777.484 709.261 777.484 709.077C777.484 708.891 777.333 708.736 777.146 708.736Z" fill="#5F74B7"/>
<path d="M767.27 705.002C768.995 705.089 770.72 705.091 772.444 705.002C770.72 704.913 768.995 704.913 767.27 705.002Z" fill="#9E9798"/>
<path d="M763.435 706.447C765.665 706.518 767.895 706.518 770.125 706.447C767.895 706.373 765.665 706.376 763.435 706.447Z" fill="#9E9798"/>
<path d="M769.755 707.482C772.198 707.556 774.642 707.556 777.085 707.482C774.642 707.411 772.198 707.411 769.755 707.482Z" fill="#9E9798"/>
<path d="M768.919 706.868C771.641 706.942 774.363 706.942 777.085 706.868C774.363 706.797 771.641 706.797 768.919 706.868Z" fill="#9E9798"/>
<path d="M768.919 705.703C771.641 705.809 774.363 705.809 777.085 705.703C774.363 705.593 771.641 705.593 768.919 705.703Z" fill="#9E9798"/>
<path d="M769.623 704.495C772.109 704.566 774.598 704.566 777.085 704.495C774.598 704.421 772.109 704.421 769.623 704.495Z" fill="#9E9798"/>
<path d="M766.985 707.84C768.906 707.912 770.828 707.912 772.749 707.84C770.828 707.769 768.906 707.769 766.985 707.84Z" fill="#9E9798"/>
<path d="M766.529 706.031C768.236 706.141 769.942 706.141 771.648 706.031C769.942 705.924 768.236 705.924 766.529 706.031Z" fill="#9E9798"/>
<path d="M763.305 708.108C761.632 708.108 761.123 706.922 761.123 706.447C761.123 705.178 762.142 704.151 763.403 704.151H762.809C761.547 704.151 760.528 705.178 760.528 706.447C760.528 707.714 761.547 708.743 762.809 708.743H777.085V708.108H763.305Z" fill="#BDB9B3"/>
<path d="M852.979 743.845L854.612 767.896L865.694 767.418L865.309 743.064L852.979 743.845Z" fill="#F9AA89"/>
<path d="M853.788 765.224L833.591 774.435C832.268 775.098 831.572 776.583 831.91 778.024H867.536L866.212 765.076L853.788 765.224Z" fill="#040606"/>
<path d="M868.164 781.856H831.455V778.024H868.164V781.856Z" fill="white"/>
<path d="M847.566 767.53L849.757 769.392" stroke="white" stroke-width="1.3642" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M844.628 768.943L846.835 770.819" stroke="white" stroke-width="1.3642" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M841.679 770.423L844.011 772.411" stroke="white" stroke-width="1.3642" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M889.062 743.845L890.696 767.896L901.778 767.418L901.394 743.064L889.062 743.845Z" fill="#F9AA89"/>
<path d="M889.871 765.224L869.673 774.435C868.35 775.098 867.655 776.583 867.993 778.024H903.619L902.295 765.076L889.871 765.224Z" fill="#040606"/>
<path d="M904.25 781.856H867.539V778.024H904.25V781.856Z" fill="white"/>
<path d="M883.652 767.53L885.842 769.392" stroke="white" stroke-width="1.3642" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M880.713 768.943L882.92 770.819" stroke="white" stroke-width="1.3642" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M877.764 770.423L880.096 772.411" stroke="white" stroke-width="1.3642" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M859.379 630.902L901.894 634.142L905.425 753.582H884.245L876.701 663.494L866.591 701.99L870.034 755.04L850.199 755.096L843.355 696.44L859.379 630.902Z" fill="#BFAA98"/>
<path d="M867.191 658.303L876.701 663.494" stroke="#A08573" stroke-miterlimit="10"/>
<path d="M859.929 594.462L860.203 606.186L853.549 606.271L854.039 593.653L859.929 594.462Z" fill="#F79390"/>
<path d="M859.519 574.567C859.519 574.567 850.621 580.418 851.553 595.257L860.205 596.231L859.519 574.567Z" fill="#707EC7"/>
<path d="M880.962 567.964C891.663 567.964 903.792 571.663 903.792 571.663L903.331 639.73L858.131 636.258L858.61 576.725C858.619 575.672 859.199 574.705 860.124 574.204L872.626 568.856C872.626 568.856 878.778 567.964 880.962 567.964Z" fill="#707EC7"/>
<path d="M858.447 596.033V581.692" stroke="#586DBE" stroke-width="1.01863" stroke-miterlimit="10"/>
<path d="M898.438 594.6L901.344 628.267C901.344 628.267 904.555 635.039 910.235 627.996C915.913 620.954 911.052 593.442 911.052 593.442L898.438 594.6Z" fill="#F9AA89"/>
<path d="M895.679 597.926C895.679 597.926 893.254 573.071 901.12 571.611C909.276 570.098 914.014 585.472 914.77 596.49L895.679 597.926Z" fill="#707EC7"/>
<path d="M898.704 597.698L895.679 597.926C895.679 597.926 894.792 589.42 895.327 583.507" stroke="#586DBE" stroke-width="1.01863" stroke-miterlimit="10"/>
<path d="M879.132 596.744C879.132 596.744 877.494 590.808 871.552 590.229C865.61 589.651 863.864 594.314 864.982 597.386C866.101 600.457 869.966 605.459 875.822 602.901C881.678 600.344 879.132 596.744 879.132 596.744Z" fill="#F9AA89"/>
<path d="M869.582 590.236C869.582 590.236 863.748 590.906 859.404 593.022C858.963 593.236 858.722 593.722 858.786 594.21C858.872 594.866 859.494 595.316 860.146 595.195L868.199 593.69L869.582 590.236Z" fill="#F9AA89"/>
<path d="M902.602 629.983L875.822 602.901L879.132 596.743L905.178 613.293L902.602 629.983Z" fill="#F9AA89"/>
<path d="M899.754 609.845L905.179 613.293" stroke="#EF9676" stroke-width="1.01863" stroke-miterlimit="10"/>
<path d="M842.562 603.558L853.826 636.99C854.213 638.139 855.359 638.855 856.562 638.697L883.937 635.101C885.531 634.893 886.531 633.272 886.003 631.752L874.41 598.362C874.015 597.225 872.875 596.521 871.681 596.677L844.638 600.229C843.051 600.437 842.051 602.042 842.562 603.558Z" fill="#0B0C0D"/>
<path d="M843.043 601.08L841.611 602.937L884.261 635.866L885.79 633.873L843.043 601.08Z" fill="#0B0C0D"/>
<path d="M841.272 605.218L852.536 638.65C852.923 639.801 854.07 640.516 855.272 640.358L882.647 636.762C884.242 636.553 885.242 634.932 884.715 633.412L873.12 600.024C872.726 598.885 871.586 598.181 870.391 598.338L843.348 601.89C841.763 602.098 840.763 603.702 841.272 605.218Z" fill="#34474F"/>
<path d="M857.781 616.031C857.793 617.659 859.123 618.97 860.751 618.958C862.379 618.947 863.688 617.618 863.677 615.99C863.665 614.362 862.336 613.051 860.709 613.063C859.081 613.074 857.771 614.403 857.781 616.031Z" fill="#739095"/>
<path d="M842.549 614.934L845.113 621.851C845.427 622.695 846.28 623.21 847.172 623.093C849.8 622.747 851.483 620.119 850.696 617.589L849.975 615.269C849.397 613.41 847.637 612.177 845.693 612.27L844.267 612.338C842.963 612.399 842.096 613.71 842.549 614.934Z" fill="#F9AA89"/>
<path d="M870.715 524.954C870.715 524.954 896.2 517.581 886.908 543.822L882.782 534.644L870.715 524.954Z" fill="#3B161B"/>
<path d="M860.136 534.969C860.136 534.969 853.866 537.801 860.867 546.559L863.104 534.544L860.136 534.969Z" fill="#3B161B"/>
<path d="M866.492 548.162C866.935 550.465 865.487 552.688 863.258 553.126C861.028 553.565 858.862 552.053 858.419 549.75C857.978 547.446 859.426 545.224 861.655 544.786C863.883 544.348 866.05 545.858 866.492 548.162Z" fill="#EF9676"/>
<path d="M871.091 557.843L872.451 568.814C872.922 572.667 875.471 574.438 879.14 573.946C882.272 573.525 885.527 571.578 884.968 568.198L883.351 550.973L871.091 557.843Z" fill="#F9AA89"/>
<path d="M872.24 567.322C872.24 567.322 884.6 562.837 883.56 551.765C883.251 548.466 870.931 556.721 870.931 556.721L872.24 567.322Z" fill="#EF9676"/>
<path d="M874.778 562.052C867.972 563.258 863.41 557.802 863.104 555.02L860.183 542.112C859.134 535.519 863.335 529.296 869.68 528.048C876.175 526.771 883.624 530.951 884.914 537.662L886.128 546.26C887.231 554 882.21 560.591 874.778 562.052Z" fill="#F9AA89"/>
<path d="M868.141 551.133L868.175 553.647L869.701 553.519" stroke="#14191C" stroke-width="0.704101" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M873.789 543.871C873.789 543.871 871.247 543.969 871.353 545.03C871.353 545.03 871.442 545.744 873.655 545.616C875.867 545.488 876.418 545.253 876.537 544.554C876.654 543.858 874.97 543.733 873.789 543.871Z" fill="#14191C"/>
<path d="M863.667 545.165C863.667 545.165 865.716 544.688 866.008 545.66C866.008 545.66 866.189 546.321 864.389 546.697C862.591 547.072 861.969 546.906 861.731 546.385C861.46 545.793 862.681 545.302 863.667 545.165Z" fill="#14191C"/>
<path d="M865.783 550.03C865.878 550.63 865.482 551.19 864.9 551.281C864.32 551.373 863.774 550.961 863.68 550.361C863.588 549.762 863.983 549.201 864.563 549.11C865.144 549.02 865.69 549.43 865.783 550.03Z" fill="#14191C"/>
<path d="M874.997 548.574C875.09 549.172 874.696 549.732 874.115 549.824C873.535 549.915 872.988 549.504 872.894 548.904C872.801 548.304 873.197 547.744 873.777 547.652C874.357 547.562 874.904 547.972 874.997 548.574Z" fill="#14191C"/>
<path d="M868.129 555.561L874.629 554.842C874.629 554.842 874.436 557.125 871.04 557.126C868.834 557.127 868.129 555.561 868.129 555.561Z" fill="white"/>
<path d="M887.458 534.134L886.908 543.822L885.032 545.918C883.584 545.423 881.712 545.454 880.512 543.822C879.625 542.617 878.744 540.365 878.713 538.869L878.669 536.782L873.564 540.551C872.764 538.683 871.858 536.199 871.858 536.199C871.858 536.199 870.641 536.285 868.982 540.333C868.982 540.333 855.816 544.313 855.822 536.285C855.829 527.811 870.714 524.954 870.714 524.954L883.525 529.326L887.458 534.134Z" fill="#3B161B"/>
<path d="M891.86 546.277C892.337 548.763 890.773 551.16 888.369 551.633C885.964 552.106 883.627 550.474 883.149 547.989C882.672 545.505 884.235 543.106 886.64 542.633C889.047 542.16 891.383 543.791 891.86 546.277Z" fill="#F9AA89"/>
<path d="M886.24 548.771C886.24 548.771 885.612 545.508 888.731 545.428" stroke="#14191C" stroke-width="0.718219" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M869.699 570.106L875.033 567.626L884.438 567.895L889.954 568.666C889.954 568.666 892.01 576.929 878.059 577.389C866.907 577.757 869.699 570.106 869.699 570.106Z" fill="#F9AA89"/>
<path d="M787.24 566.06H831.583C832.82 566.06 833.823 565.057 833.823 563.82V549.046C833.823 547.81 832.82 546.808 831.583 546.808H787.24C786.003 546.808 785 547.81 785 549.046V563.82C785 565.057 786.003 566.06 787.24 566.06Z" fill="white"/>
<path d="M825.229 554.185H792.784" stroke="#B4A19A" stroke-width="1.43531" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M804.002 559.301H792.893" stroke="#B4A19A" stroke-width="1.43531" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M826.962 563.497V572.205L815.864 563.497H826.962Z" fill="white"/>
</svg>

After

Width:  |  Height:  |  Size: 92 KiB

View File

@ -0,0 +1,455 @@
<svg width="923" height="404" viewBox="0 0 923 404" fill="none" xmlns="http://www.w3.org/2000/svg">
<ellipse cx="478.5" cy="381" rx="444.5" ry="23" fill="white" fill-opacity="0.37"/>
<path d="M239.178 351.508H124.396C122.395 351.508 120.773 349.885 120.773 347.885V100.231C120.773 98.2313 122.395 96.6105 124.396 96.6105H239.178C241.178 96.6105 242.801 98.2313 242.801 100.231V347.885C242.801 349.885 241.178 351.508 239.178 351.508Z" fill="#4188E4"/>
<path d="M235.509 174.918H128.093V117.397H235.509V174.918Z" fill="#142666"/>
<path d="M235.509 237.676H128.093V180.155H235.509V237.676Z" fill="#142666"/>
<path d="M235.509 300.433H128.093V242.914H235.509V300.433Z" fill="#142666"/>
<path d="M480.017 351.508H269.18C267.179 351.508 265.559 349.885 265.559 347.885V100.231C265.559 98.2313 267.179 96.6105 269.18 96.6105H480.017C482.017 96.6105 483.639 98.2313 483.639 100.231V347.885C483.639 349.885 482.017 351.508 480.017 351.508Z" fill="#4188E4"/>
<path d="M470.608 174.918H278.637V117.397H470.608V174.918Z" fill="#142666"/>
<path d="M470.608 237.676H278.637V180.155H470.608V237.676Z" fill="#142666"/>
<path d="M470.608 300.433H278.637V242.914H470.608V300.433Z" fill="#142666"/>
<path d="M397.667 294.522V300.433H365.406V294.522H397.667Z" fill="#AFDBFE"/>
<path d="M398.72 289.266V294.521H369.864V289.266H398.72Z" fill="white"/>
<path d="M394.27 284.01V289.267H365.416V284.01H394.27Z" fill="#70C0FD"/>
<path d="M426.02 300.433H419.455V264.411H426.02V300.433Z" fill="#AFDBFE"/>
<path d="M432.758 300.433H427.575V270.511H432.758V300.433Z" fill="#70C0FD"/>
<path d="M410.845 300.433H404.28V264.411H410.845V300.433Z" fill="#AFDBFE"/>
<path d="M417.581 300.433H412.398V270.511H417.581V300.433Z" fill="#70C0FD"/>
<path d="M308.475 300.433H297.015V271.661H308.475V300.433Z" fill="#AFDBFE"/>
<path d="M295.056 300.433H291.832V274.481H295.056V300.433Z" fill="white"/>
<path d="M290.794 300.433H285.669V270.338H290.794V300.433Z" fill="#70C0FD"/>
<path d="M359.846 300.433H354.721V270.338H359.846V300.433Z" fill="#70C0FD"/>
<path d="M328.227 300.433H317.805V274.481H328.227V300.433Z" fill="white"/>
<path d="M335.887 300.433H329.322V264.411H335.887V300.433Z" fill="#AFDBFE"/>
<path d="M342.626 300.433H337.443V270.511H342.626V300.433Z" fill="#70C0FD"/>
<path d="M315.846 300.433H309.8V268.381H315.846V300.433Z" fill="#70C0FD"/>
<path d="M353.166 300.433H343.662V273.446H353.166V300.433Z" fill="white"/>
<path d="M143.311 300.413H140.086V274.46H143.311V300.413Z" fill="white"/>
<path d="M139.049 300.413H133.924V270.316H139.049V300.413Z" fill="#A2CFF6"/>
<path d="M232.17 300.413H220.71V271.639H232.17V300.413Z" fill="#AFDBFE"/>
<path d="M218.752 300.413H215.527V274.46H218.752V300.413Z" fill="white"/>
<path d="M214.491 300.413H209.365V270.316H214.491V300.413Z" fill="#70C0FD"/>
<path d="M189.44 300.413H182.875V264.39H189.44V300.413Z" fill="#AFDBFE"/>
<path d="M177.329 294.502V300.413H145.067V294.502H177.329Z" fill="#B0C1EC"/>
<path d="M178.381 289.246V294.503H149.526V289.246H178.381Z" fill="white"/>
<path d="M173.931 283.99V289.247H145.076V283.99H173.931Z" fill="#A2CFF6"/>
<path d="M196.178 300.413H190.995V270.49H196.178V300.413Z" fill="#70C0FD"/>
<path d="M207.811 300.413H198.31V273.424H207.811V300.413Z" fill="white"/>
<path d="M291.267 174.918H288.043V148.964H291.267V174.918Z" fill="white"/>
<path d="M287.006 174.918H281.881V144.821H287.006V174.918Z" fill="#70C0FD"/>
<path d="M380.129 174.918H368.669V146.144H380.129V174.918Z" fill="#AFDBFE"/>
<path d="M366.711 174.918H363.486V148.964H366.711V174.918Z" fill="white"/>
<path d="M362.449 174.918H357.323V144.821H362.449V174.918Z" fill="#70C0FD"/>
<path d="M337.399 174.918H330.834V138.895H337.399V174.918Z" fill="#AFDBFE"/>
<path d="M325.287 169.007V174.918H293.025V169.007H325.287Z" fill="#AFDBFE"/>
<path d="M326.339 163.75V169.007H297.483V163.75H326.339Z" fill="white"/>
<path d="M321.889 158.493V163.75H293.035V158.493H321.889Z" fill="#70C0FD"/>
<path d="M344.136 174.918H338.953V144.995H344.136V174.918Z" fill="#70C0FD"/>
<path d="M355.769 174.918H346.268V147.929H355.769V174.918Z" fill="white"/>
<path d="M523.886 171.653H520.66V145.702H523.886V171.653Z" fill="white"/>
<path d="M519.624 171.653H514.499V141.558H519.624V171.653Z" fill="#70C0FD"/>
<path d="M595.065 171.653H589.939V141.558H595.065V171.653Z" fill="#70C0FD"/>
<path d="M570.015 171.653H563.45V135.632H570.015V171.653Z" fill="#AFDBFE"/>
<path d="M557.904 165.742V171.653H525.643V165.742H557.904Z" fill="#AFDBFE"/>
<path d="M558.955 160.488V165.743H530.1V160.488H558.955Z" fill="white"/>
<path d="M554.505 155.23V160.487H525.651V155.23H554.505Z" fill="#A2CFF6"/>
<path d="M576.754 171.653H571.569V141.732H576.754V171.653Z" fill="#70C0FD"/>
<path d="M588.385 171.653H578.884V144.666H588.385V171.653Z" fill="white"/>
<path d="M448.439 174.918H441.874V138.895H448.439V174.918Z" fill="#AFDBFE"/>
<path d="M455.178 174.918H449.995V144.995H455.178V174.918Z" fill="#70C0FD"/>
<path d="M466.812 174.918H457.309V147.929H466.812V174.918Z" fill="white"/>
<path d="M156.729 174.918H145.269V146.144H156.729V174.918Z" fill="#AFDBFE"/>
<path d="M143.311 174.918H140.086V148.964H143.311V174.918Z" fill="white"/>
<path d="M139.049 174.918H133.924V144.821H139.049V174.918Z" fill="#70C0FD"/>
<path d="M226.871 174.918H215.411V146.144H226.871V174.918Z" fill="#AFDBFE"/>
<path d="M213.453 174.918H210.229V148.964H213.453V174.918Z" fill="white"/>
<path d="M209.192 174.918H204.066V144.821H209.192V174.918Z" fill="#70C0FD"/>
<path d="M176.482 174.918H166.059V148.964H176.482V174.918Z" fill="white"/>
<path d="M184.141 174.918H177.576V138.895H184.141V174.918Z" fill="#AFDBFE"/>
<path d="M190.879 174.918H185.696V144.995H190.879V174.918Z" fill="#70C0FD"/>
<path d="M164.1 174.918H158.054V142.865H164.1V174.918Z" fill="#70C0FD"/>
<path d="M405.853 174.918H394.392V146.144H405.853V174.918Z" fill="#AFDBFE"/>
<path d="M392.434 174.918H389.208V148.964H392.434V174.918Z" fill="white"/>
<path d="M388.173 174.918H383.048V144.821H388.173V174.918Z" fill="#70C0FD"/>
<path d="M425.605 174.918H415.181V148.964H425.605V174.918Z" fill="white"/>
<path d="M433.265 174.918H426.7V138.895H433.265V174.918Z" fill="#AFDBFE"/>
<path d="M440.004 174.918H434.819V144.995H440.004V174.918Z" fill="#70C0FD"/>
<path d="M413.225 174.918H407.177V142.865H413.225V174.918Z" fill="#70C0FD"/>
<path d="M541.8 120.109H535.235V84.0861H541.8V120.109Z" fill="#AFDBFE"/>
<path d="M548.537 120.109H543.354V90.186H548.537V120.109Z" fill="#70C0FD"/>
<path d="M560.171 120.109H550.669V93.1205H560.171V120.109Z" fill="white"/>
<path d="M518.965 120.109H508.542V94.1578H518.965V120.109Z" fill="white"/>
<path d="M526.625 120.109H520.06V84.0861H526.625V120.109Z" fill="#AFDBFE"/>
<path d="M533.362 120.109H528.18V90.186H533.362V120.109Z" fill="#70C0FD"/>
<path d="M506.584 120.109H500.537V88.056H506.584V120.109Z" fill="#70C0FD"/>
<path d="M428.479 237.676H417.02V208.902H428.479V237.676Z" fill="#AFDBFE"/>
<path d="M415.061 237.676H411.837V211.722H415.061V237.676Z" fill="white"/>
<path d="M410.799 237.676H405.674V207.579H410.799V237.676Z" fill="#70C0FD"/>
<path d="M454.204 237.676H442.744V208.902H454.204V237.676Z" fill="#AFDBFE"/>
<path d="M440.786 237.676H437.56V211.722H440.786V237.676Z" fill="white"/>
<path d="M436.524 237.676H431.398V207.579H436.524V237.676Z" fill="#70C0FD"/>
<path d="M461.575 237.676H455.528V205.622H461.575V237.676Z" fill="#70C0FD"/>
<path d="M202.511 174.918H193.01V147.929H202.511V174.918Z" fill="white"/>
<path d="M308.475 237.676H297.015V208.902H308.475V237.676Z" fill="#AFDBFE"/>
<path d="M295.056 237.676H291.832V211.722H295.056V237.676Z" fill="white"/>
<path d="M290.794 237.676H285.669V207.579H290.794V237.676Z" fill="#70C0FD"/>
<path d="M378.618 237.676H367.158V208.902H378.618V237.676Z" fill="#AFDBFE"/>
<path d="M365.2 237.676H361.974V211.722H365.2V237.676Z" fill="white"/>
<path d="M360.938 237.676H355.812V207.579H360.938V237.676Z" fill="#70C0FD"/>
<path d="M328.227 237.676H317.805V211.722H328.227V237.676Z" fill="white"/>
<path d="M335.887 237.676H329.322V201.652H335.887V237.676Z" fill="#AFDBFE"/>
<path d="M342.626 237.676H337.443V207.752H342.626V237.676Z" fill="#70C0FD"/>
<path d="M315.846 237.676H309.8V205.622H315.846V237.676Z" fill="#70C0FD"/>
<path d="M354.259 237.676H344.756V210.687H354.259V237.676Z" fill="white"/>
<path d="M156.729 237.676H145.269V206.271H156.729V237.676Z" fill="white"/>
<path d="M143.311 237.676H140.086V211.722H143.311V237.676Z" fill="#70C0FD"/>
<path d="M139.049 237.676H133.924V207.579H139.049V237.676Z" fill="#AFDBFE"/>
<path d="M213.453 237.676H210.229V211.722H213.453V237.676Z" fill="#70C0FD"/>
<path d="M209.192 237.676H204.066V204.33H209.192V237.676Z" fill="white"/>
<path d="M176.482 237.676H166.059V204.33H176.482V237.676Z" fill="#70C0FD"/>
<path d="M184.141 237.676H177.576V208.902H184.141V237.676Z" fill="white"/>
<path d="M190.879 237.676H185.696V199.801H190.879V237.676Z" fill="#AFDBFE"/>
<path d="M164.1 237.676H158.054V209.669H164.1V237.676Z" fill="#AFDBFE"/>
<path d="M202.511 237.676H193.01V205.622H202.511V237.676Z" fill="#70C0FD"/>
<path d="M231.731 234.589L222.783 237.783L211.992 207.599L220.941 204.405L231.731 234.589Z" fill="white"/>
<path d="M397.911 234.589L388.962 237.783L378.174 207.599L387.122 204.405L397.911 234.589Z" fill="white"/>
<path d="M403.485 236.078L399.011 237.676L388.221 207.491L392.696 205.893L403.485 236.078Z" fill="#70C0FD"/>
<path d="M574.239 118.378L569.763 119.976L558.975 89.7909L563.448 88.193L574.239 118.378Z" fill="#70C0FD"/>
<path d="M533.651 363.873L532.451 373.5L525.991 374L526.09 365.072L533.651 363.873Z" fill="#FFC0BB"/>
<path d="M419.771 272.434H482.291L475.461 319.671L423.861 311.271L419.771 272.434Z" fill="#F9537F"/>
<path d="M516.174 381.047L533.824 381.165C534.209 381.169 534.518 380.866 534.516 380.488L534.51 379.981C534.508 379.603 534.192 379.296 533.806 379.294L516.157 379.174C515.772 379.172 515.461 379.476 515.465 379.851L515.469 380.36C515.472 380.736 515.787 381.045 516.174 381.047Z" fill="#3D3A55"/>
<path d="M533.584 373.605L534.261 378.817C534.343 379.459 533.981 380.039 533.499 380.037L516.715 379.923C516.278 379.921 515.846 379.652 515.613 379.15C515.373 378.637 515.319 377.865 516.061 376.832C517.546 374.769 522.479 374.296 524.878 372.541L532.696 372.593C533.133 372.597 533.508 373.026 533.584 373.605Z" fill="#09083C"/>
<path d="M526.09 375.571C526.212 375.501 526.254 375.3 526.181 375.148C525.846 374.433 524.801 372.688 522.709 373.031C522.587 373.052 522.507 373.209 522.528 373.371L522.53 373.374C522.551 373.533 522.661 373.636 522.778 373.617C524.654 373.317 525.542 374.854 525.815 375.453C525.872 375.581 525.99 375.632 526.09 375.571Z" fill="white"/>
<path d="M524.352 376.231C524.472 376.158 524.516 375.958 524.444 375.807C524.108 375.09 523.063 373.347 520.97 373.689C520.85 373.71 520.769 373.866 520.79 374.028L520.792 374.034C520.813 374.19 520.924 374.293 521.04 374.274C522.917 373.975 523.805 375.512 524.076 376.11C524.135 376.238 524.253 376.29 524.352 376.231Z" fill="white"/>
<path d="M522.738 376.844C522.858 376.772 522.9 376.574 522.829 376.421C522.494 375.704 521.449 373.961 519.355 374.305C519.235 374.324 519.153 374.48 519.176 374.642V374.648C519.199 374.804 519.307 374.907 519.425 374.89C521.3 374.589 522.19 376.126 522.461 376.726C522.52 376.854 522.637 376.904 522.738 376.844Z" fill="white"/>
<path d="M533.502 380.037C533.501 380.037 533.5 380.037 533.499 380.037L529.02 380.007C530.204 376.136 532.231 375.453 533.518 375.453C533.624 375.453 533.729 375.457 533.825 375.466L534.261 378.817C534.261 378.83 534.263 378.841 534.265 378.855C534.265 378.855 534.265 378.855 534.265 378.857C534.265 378.862 534.267 378.868 534.267 378.874C534.322 379.492 533.97 380.037 533.502 380.037Z" fill="#090730"/>
<path d="M562.422 363.272L562.97 373.368L556.395 373.412L555.768 364.078L562.422 363.272Z" fill="#FFC0BB"/>
<path d="M546.953 381.22L564.6 381.34C564.987 381.342 565.296 381.039 565.294 380.661L565.288 380.154C565.285 379.778 564.97 379.469 564.585 379.467L546.935 379.347C546.55 379.345 546.239 379.649 546.243 380.026L546.247 380.533C546.251 380.911 546.565 381.218 546.953 381.22Z" fill="#3D3A55"/>
<path d="M564.362 373.777L565.037 378.987C565.121 379.629 564.758 380.211 564.276 380.207L547.492 380.095C547.056 380.091 546.623 379.822 546.39 379.32C546.15 378.807 546.097 378.035 546.838 377.004C548.322 374.939 553.255 374.466 555.655 372.711L563.473 372.765C563.91 372.767 564.286 373.196 564.362 373.777Z" fill="#09083C"/>
<path d="M556.868 375.743C556.988 375.671 557.032 375.471 556.959 375.318C556.624 374.603 555.579 372.86 553.485 373.201C553.365 373.222 553.285 373.379 553.306 373.541L553.308 373.547C553.329 373.703 553.438 373.806 553.556 373.787C555.43 373.487 556.321 375.024 556.592 375.623C556.651 375.751 556.769 375.802 556.868 375.743Z" fill="white"/>
<path d="M555.131 376.403C555.251 376.33 555.295 376.132 555.222 375.98C554.887 375.265 553.842 373.52 551.748 373.863C551.628 373.882 551.548 374.039 551.569 374.201L551.571 374.206C551.592 374.363 551.7 374.468 551.819 374.448C553.693 374.147 554.583 375.684 554.854 376.285C554.913 376.412 555.03 376.462 555.131 376.403Z" fill="white"/>
<path d="M553.515 377.016C553.635 376.944 553.677 376.746 553.607 376.593C553.271 375.878 552.224 374.133 550.132 374.477C550.012 374.496 549.93 374.652 549.953 374.814V374.82C549.974 374.978 550.085 375.081 550.201 375.062C552.077 374.761 552.966 376.298 553.238 376.898C553.296 377.026 553.414 377.077 553.515 377.016Z" fill="white"/>
<path d="M564.28 380.207C564.278 380.207 564.276 380.207 564.276 380.207L559.797 380.177C560.981 376.306 563.008 375.623 564.293 375.623C564.402 375.623 564.505 375.629 564.602 375.636L565.037 378.987C565.039 379 565.041 379.013 565.042 379.025V379.027C565.042 379.032 565.042 379.038 565.044 379.042C565.056 379.168 565.05 379.292 565.029 379.406C565.029 379.408 565.029 379.408 565.029 379.408C565.029 379.41 565.029 379.412 565.029 379.414C565.029 379.416 565.027 379.418 565.027 379.42C565.027 379.42 565.027 379.42 565.027 379.421V379.423C564.945 379.87 564.648 380.207 564.28 380.207Z" fill="#090730"/>
<path d="M645.394 348.717H431.535C431.137 348.717 430.814 348.395 430.814 347.996V345.799C430.814 345.401 431.137 345.077 431.535 345.077H645.394C645.793 345.077 646.115 345.401 646.115 345.799V347.996C646.115 348.395 645.793 348.717 645.394 348.717Z" fill="#3D3A55"/>
<path d="M659.106 240.707C658.301 240.764 519.861 240.726 474.382 240.712C466.488 240.709 460.091 247.104 460.091 254.992V313.287H631.234L657.78 286.76L659.106 240.707Z" fill="#FF5B7E"/>
<path d="M654.875 295.484H663.335C664.868 295.484 666.11 294.243 666.11 292.71V243.482C666.11 241.949 664.868 240.708 663.335 240.708H654.875C653.342 240.708 652.099 241.949 652.099 243.482V292.71C652.099 294.243 653.342 295.484 654.875 295.484Z" fill="#E03268"/>
<path d="M423.861 339.538H599.71V304.571H423.861V339.538Z" fill="#E03268"/>
<path d="M560.773 291.452C560.773 291.452 528.346 291.57 523.342 298.07C518.339 304.57 514.535 348.471 523.342 367.672C523.342 367.672 534.753 368.073 537.353 366.473C537.353 366.473 536.553 334.071 536.953 325.471C537.353 316.869 543.358 315.67 544.159 314.871C544.96 314.07 560.773 291.452 560.773 291.452Z" fill="#2B1C35"/>
<path d="M610.445 224.141L611.675 234.115L601.78 233.776L602.064 222.362L610.445 224.141Z" fill="#FFC0BB"/>
<path d="M610.806 227.054L610.562 225.084H610.567L610.806 227.054Z" fill="#E8B5B5"/>
<path d="M605.265 228.072C604.18 228.072 603.047 227.945 601.936 227.617L602.065 222.361L610.562 225.084L610.806 227.054C609.536 227.529 607.498 228.072 605.265 228.072Z" fill="#FDA19A"/>
<path d="M590.136 208.346L591.417 215.15L592.653 215.516L592.344 206.885L590.136 208.346Z" fill="#FEE4CB"/>
<path d="M593.211 213.909C593.918 215.333 593.568 216.949 592.425 217.515C591.281 218.081 589.781 217.385 589.073 215.961C588.364 214.536 588.717 212.923 589.859 212.357C591.001 211.789 592.502 212.485 593.211 213.909Z" fill="#F99893"/>
<path d="M594.268 222.473C593.855 221.867 593.496 221.216 593.195 220.532C592.35 218.694 591.847 216.714 591.547 214.977C591.482 214.604 591.397 214.236 591.305 213.87C590.93 212.388 590.817 210.798 591.05 209.135C591.797 203.786 596.059 199.481 601.411 198.682C608.623 197.606 615.039 202.871 615.562 209.932C616.3 209.448 617.156 209.286 617.941 209.568C619.45 210.109 620.119 212.075 619.44 213.955C618.759 215.835 616.984 216.922 615.478 216.381C615.268 216.305 615.077 216.2 614.9 216.074C614.73 222.128 610.141 227.131 604.216 227.475C601.318 227.642 598.61 226.664 596.499 224.921C596.358 224.82 596.211 224.702 596.055 224.563C595.367 223.951 594.777 223.241 594.268 222.473Z" fill="#FFC0BB"/>
<path d="M604.597 211.819C604.629 212.412 605.138 212.864 605.731 212.829C606.326 212.795 606.78 212.288 606.746 211.695C606.711 211.104 606.202 210.65 605.609 210.684C605.016 210.718 604.562 211.228 604.597 211.819Z" fill="#333333"/>
<path d="M595.401 212.957C595.436 213.55 595.945 214.002 596.538 213.968C597.131 213.934 597.585 213.424 597.552 212.833C597.518 212.24 597.009 211.788 596.416 211.823C595.821 211.857 595.367 212.364 595.401 212.957Z" fill="#333333"/>
<path d="M603.176 209.768C603.691 209.522 604.183 209.319 604.68 209.171C605.178 209.024 605.676 208.944 606.169 208.942C606.661 208.944 607.163 208.99 607.655 209.146L607.844 209.194C607.907 209.211 607.966 209.239 608.029 209.26L608.404 209.392C608.658 209.487 608.898 209.613 609.178 209.703C609.007 209.48 608.818 209.26 608.604 209.066C608.374 208.9 608.156 208.694 607.884 208.58C607.371 208.288 606.759 208.162 606.16 208.162C605.555 208.168 604.959 208.328 604.444 208.61C603.933 208.896 603.477 209.278 603.176 209.768Z" fill="#07085B"/>
<path d="M598.865 210.237C598.467 209.821 597.938 209.547 597.378 209.377C596.815 209.215 596.197 209.184 595.606 209.31C595.021 209.44 594.451 209.693 594.012 210.088C593.772 210.262 593.602 210.508 593.412 210.721C593.246 210.956 593.108 211.209 592.99 211.465C593.244 211.318 593.45 211.143 593.679 210.996L594.018 210.786C594.075 210.752 594.125 210.712 594.184 210.681L594.357 210.593C594.806 210.334 595.284 210.183 595.765 210.073C596.249 209.97 596.752 209.941 597.267 209.978C597.786 210.014 598.31 210.107 598.865 210.237Z" fill="#07085B"/>
<path d="M588.416 200.257C588.416 200.257 584.73 200.558 588.452 197.252C592.174 193.945 602.397 189.781 609.235 192.963C609.235 192.963 610.428 190.071 612.388 190.65C614.349 191.23 611.263 193.333 611.263 193.333C611.263 193.333 613.721 193.131 614.53 194.3C615.128 195.162 613.624 195.276 612.798 195.276C614.211 195.444 618.915 197.919 616.747 208.858C615.781 208.694 608.045 202.354 608.045 202.354C608.045 202.354 597.925 209.102 599.113 205.51C599.113 205.51 587.043 212.376 588.553 205.632C588.553 205.632 583.569 206.244 588.416 200.257Z" fill="#07085B"/>
<path d="M600.528 209.953C600.804 210.678 600.96 211.439 601.027 212.217C601.06 212.606 601.062 213 601.02 213.405C600.97 213.807 600.888 214.223 600.644 214.629L600.537 214.776L600.44 214.903C600.4 214.963 600.337 215.014 600.31 215.077C600.234 215.195 600.188 215.321 600.173 215.451C600.127 215.714 600.259 215.994 600.455 216.242C600.88 216.74 601.609 216.999 602.364 217.129C601.62 217.298 600.73 217.232 600.049 216.648C599.717 216.368 599.454 215.912 599.477 215.407C599.483 215.283 599.498 215.159 599.54 215.043C599.568 214.921 599.626 214.816 599.683 214.709C599.734 214.596 599.818 214.516 599.887 214.421C599.931 214.368 599.938 214.35 599.961 214.32L600.02 214.238C600.175 213.992 600.263 213.651 600.329 213.305C600.404 212.958 600.417 212.59 600.453 212.222C600.495 211.481 600.503 210.726 600.528 209.953Z" fill="#F99893"/>
<path d="M608.044 202.355C608.044 202.355 612.321 209.107 612.416 213.1C612.416 213.1 614.222 209.522 617.2 209.431C617.2 209.431 618.169 202.706 616.35 198.503L609.623 199.943L608.044 202.355Z" fill="#07085B"/>
<path d="M599.406 229.967C599.406 229.967 602.409 234.667 612.416 229.967C612.416 229.967 630.53 224.967 631.932 246.468L632.634 266.468C632.634 266.468 623.275 266.501 618.472 266.678L618.321 270.867L590.999 293.068C590.999 293.068 574.785 291.669 571.482 290.069C571.482 290.069 577.289 278.569 578.189 275.968C579.089 273.369 579.739 248.268 580.69 245.667C581.642 243.068 584.435 230.323 599.406 229.967Z" fill="#FEB546"/>
<path d="M585.951 245.018C585.586 245.617 585.295 246.25 585.045 246.9C584.908 247.218 584.803 247.55 584.679 247.876L584.368 248.87C583.973 250.202 583.682 251.564 583.474 252.939C583.226 254.308 583.115 255.698 582.997 257.084C582.947 257.78 582.919 258.476 582.879 259.172C582.858 259.87 582.848 260.568 582.816 261.268C582.77 260.57 582.749 259.87 582.715 259.17C582.721 258.472 582.721 257.771 582.738 257.071C582.803 255.671 582.917 254.272 583.142 252.885C583.378 251.503 583.668 250.124 584.12 248.793C584.576 247.468 585.115 246.149 585.951 245.018Z" fill="#452B52"/>
<path d="M570.465 259.91C570.219 259.919 560.311 253.919 560.311 253.919L558.46 254.311L559.118 254.798L558.01 254.519L556.208 254.798C556.208 254.798 562.163 261.819 562.264 262.019C562.363 262.219 564.966 263.22 565.166 263.319C565.366 263.418 570.465 259.91 570.465 259.91Z" fill="#DAEEF7"/>
<path d="M586.32 255.118L585.42 254.555L585.006 254.837V254.311L584.444 253.918L570.032 259.618C570.032 259.618 574.649 262.545 574.799 262.43C574.948 262.32 583.168 260.819 583.317 260.594C583.468 260.369 586.32 255.118 586.32 255.118Z" fill="#DAEEF7"/>
<path d="M586.093 254.853L569.757 260.139L556.585 254.409C555.786 254.06 554.909 254.706 555.006 255.572L557.516 278.007C557.556 278.381 557.781 278.709 558.113 278.883L570.76 285.545L582.216 281.308L582.512 280.875L583.996 280.65L588.801 278.873C589.23 278.713 589.499 278.288 589.46 277.832L587.571 255.833C587.508 255.107 586.785 254.628 586.093 254.853Z" fill="#E03268"/>
<path d="M571.771 285.05L569.758 260.139L586.093 254.854C586.097 254.852 586.103 254.85 586.109 254.848C586.219 254.814 586.332 254.798 586.44 254.796H586.442C586.448 254.796 586.452 254.796 586.456 254.796C587.02 254.804 587.52 255.235 587.571 255.834L589.457 277.804C589.499 278.277 589.219 278.717 588.772 278.883L583.996 280.651L582.512 280.876L582.217 281.309L571.771 285.05Z" fill="#D21E49"/>
<path d="M567.321 262.82L557.135 258.369L557.459 262.995L567.443 267.619L567.321 262.82Z" fill="#C1215B"/>
<path d="M591.549 277.41C591.593 277.262 591.682 277.048 591.48 276.898C591.425 276.861 591.37 276.823 591.314 276.787C590.508 276.247 589.957 275.593 589.545 274.714C589.453 274.52 589.35 274.205 589.24 274.076C589.161 273.984 589.14 274.114 589.14 274.114L589.322 276.211L586.887 277.098C586.887 277.098 582.621 277.769 580.52 276.844C580.52 276.844 579.42 276.07 579.769 277.47C579.803 277.605 579.879 277.727 579.99 277.841C579.835 277.937 579.668 278.183 579.969 279.127C579.98 279.163 579.995 279.197 580.015 279.233C579.938 279.794 579.997 280.498 580.617 280.875C580.76 281.339 581.101 281.838 581.885 282.063C582.972 282.376 585.458 282.723 587.032 282.923C588.41 283.135 589.406 283.23 589.955 283.119L590.534 283.213C590.529 283.06 592.029 280.923 592.188 280.008C592.348 279.09 591.289 278.301 591.549 277.41Z" fill="#FFC0BB"/>
<path d="M591.48 276.898C591.48 276.898 606.259 276.145 610.389 274.72C614.517 273.294 618.32 270.868 618.32 270.868V266.67L632.342 266.46C632.342 266.46 634.108 279.295 630.13 280.795C626.151 282.294 598.811 284.695 589.954 283.12L591.48 276.898Z" fill="#FFC0BB"/>
<path d="M579.989 279.159C580.243 279.455 580.569 279.678 580.91 279.867C581.252 280.055 581.621 280.191 581.997 280.296C582.375 280.389 582.762 280.454 583.151 280.471C583.343 280.484 583.538 280.473 583.732 280.475C583.925 280.461 584.117 280.444 584.31 280.419C583.923 280.402 583.54 280.389 583.162 280.341C582.783 280.294 582.407 280.227 582.039 280.132C581.673 280.034 581.314 279.908 580.967 279.752C580.624 279.592 580.289 279.401 579.989 279.159Z" fill="#F99893"/>
<path d="M580.611 280.879C580.888 281.152 581.231 281.35 581.586 281.511C581.94 281.673 582.32 281.779 582.703 281.854C583.086 281.917 583.477 281.951 583.866 281.936C584.061 281.936 584.253 281.909 584.446 281.896C584.638 281.865 584.829 281.835 585.018 281.797C584.631 281.808 584.249 281.825 583.866 281.806C583.485 281.791 583.107 281.753 582.732 281.688C582.36 281.619 581.992 281.52 581.633 281.392C581.279 281.259 580.93 281.097 580.611 280.879Z" fill="#F99893"/>
<path d="M579.989 277.841C580.243 278.135 580.569 278.36 580.91 278.548C581.252 278.737 581.621 278.873 581.997 278.976C582.375 279.071 582.762 279.136 583.151 279.151C583.343 279.164 583.538 279.155 583.732 279.157C583.925 279.141 584.117 279.124 584.31 279.101C583.923 279.082 583.54 279.071 583.162 279.021C582.783 278.976 582.407 278.909 582.039 278.813C581.673 278.716 581.314 278.588 580.967 278.432C580.624 278.272 580.289 278.083 579.989 277.841Z" fill="#F99893"/>
<path d="M628.853 266.482C627.594 266.482 626.334 266.479 625.076 266.461L621.3 266.408C620.101 266.385 618.901 266.355 617.704 266.313C617.826 265.083 617.923 263.851 617.984 262.617C618.041 261.321 618.097 260.026 618.091 258.731C618.093 257.435 618.076 256.14 618.038 254.845C617.986 253.552 617.929 252.258 617.82 250.969C617.851 252.261 617.875 253.556 617.87 254.849C617.877 256.142 617.864 257.435 617.83 258.727C617.793 260.018 617.752 261.311 617.675 262.6C617.605 263.889 617.488 265.176 617.351 266.458L617.332 266.641L617.513 266.644C618.775 266.679 620.034 266.7 621.294 266.713C622.555 266.725 623.815 266.736 625.076 266.719C627.596 266.694 630.117 266.627 632.632 266.469C631.372 266.475 630.113 266.492 628.853 266.482Z" fill="#452B52"/>
<path d="M559.514 265.935C559.344 265.582 556.37 266.095 556.339 265.883C556.307 265.672 559.266 264.188 559.19 263.835C559.104 263.443 555.975 264.499 555.765 264.354C555.556 264.209 558.341 261.913 557.817 261.622C557.418 261.4 555.527 262.703 554.635 263.347C554.348 263.553 554.207 263.906 554.274 264.253L555.479 271.396C555.584 272.021 556.147 272.468 556.782 272.429L556.888 272.424L556.719 268.553C557.615 268.522 559.291 268.419 559.146 268.089C559.013 267.784 557.569 267.556 556.669 267.443L556.665 267.373C556.681 267.231 559.667 266.253 559.514 265.935Z" fill="#FFC0BB"/>
<path d="M518.157 328.369H440.681C433.664 328.369 427.978 322.687 427.978 315.677V280.632C427.978 276.103 424.304 272.433 419.771 272.433C415.239 272.433 411.564 276.103 411.564 280.632V316.579C411.564 332.318 424.332 345.076 440.084 345.076H460.327H477.122H496.671H498.473H518.49C518.065 339.575 517.981 333.858 518.157 328.369Z" fill="#FF85A5"/>
<path d="M536.873 328.369C536.806 332.547 536.854 338.818 536.942 345.076H576.386V328.369H536.873Z" fill="#FF85A5"/>
<path d="M600.872 272.534L659.223 272.951C664.86 272.951 669.431 277.518 669.431 283.151V319.115C669.431 333.452 657.799 345.076 643.448 345.076H582.961C582.961 345.076 594.97 324.153 594.97 323.554C594.97 322.953 600.872 272.534 600.872 272.534Z" fill="#F9537F"/>
<path d="M601.607 272.433C597.074 272.433 593.4 276.103 593.4 280.632V315.677C593.4 315.917 593.392 316.158 593.379 316.394L593.381 316.402H593.379C593.003 323.074 587.47 328.369 580.697 328.369H563.356C563.871 333.359 564.516 339.306 565.151 345.076H581.296C597.046 345.076 609.814 332.318 609.814 316.579V280.632C609.814 276.103 606.139 272.433 601.607 272.433Z" fill="#FF85A5"/>
<path d="M564.438 338.558C564.146 335.855 563.767 332.342 563.357 328.368C562.621 320.564 561.86 315.433 562.678 315.98C565.494 314.962 582.957 315.818 593.379 316.401H593.381C593.444 314.676 593.377 288.061 593.4 286.672C524.94 292.37 540.025 304.091 546.445 344.557C546.481 344.731 546.518 344.904 546.552 345.076C549.338 358.458 551.965 369.471 551.965 369.471C551.965 369.471 561.974 369.872 567.779 368.472C567.786 368.533 565.975 352.728 564.438 338.558Z" fill="#3A2645"/>
<path d="M449.05 377.793L457.295 372.709L464.417 377.009L461.928 378.779L453.292 379.995C453.292 379.995 449.923 379.564 449.774 379.465C449.626 379.364 449.05 377.793 449.05 377.793Z" fill="#F7AEAA"/>
<path d="M449.05 377.793L446.96 379.137C445.991 379.747 446.42 381.242 447.566 381.248L463.385 381.322C463.944 381.324 464.398 380.876 464.401 380.317L464.417 377.009C453.865 380.312 450.23 379.274 449.05 377.793Z" fill="#FF6088"/>
<path d="M458.046 377.793L466.291 372.709L473.413 377.009L470.924 378.779L462.289 379.995C462.289 379.995 458.919 379.564 458.77 379.465C458.622 379.364 458.046 377.793 458.046 377.793Z" fill="#FFC0BB"/>
<path d="M458.046 377.793L455.956 379.137C454.987 379.747 455.416 381.242 456.562 381.248L472.381 381.322C472.94 381.324 473.394 380.876 473.398 380.317L473.413 377.009C462.861 380.312 459.226 379.274 458.046 377.793Z" fill="#FF6088"/>
<path d="M502.259 232.556C506.511 229.577 504.254 228.382 506.751 225.792C508.696 223.775 509.303 222.267 509.265 220.791C509.312 219.315 508.719 217.803 506.79 215.77C504.311 213.164 506.576 211.985 502.349 208.974C498.119 205.965 493.625 213.263 493.625 213.263L488.988 218.993L489.855 221.964L488.038 227.753C488.038 227.753 498.009 235.532 502.259 232.556Z" fill="#07085B"/>
<path d="M462.525 289.27C462.525 289.27 444.91 295.871 443.909 301.071C442.908 306.271 450.114 372.275 453.216 375.475C453.216 375.475 459.636 377.275 464.684 374.474C469.731 371.674 467.328 349.874 467.328 349.273C467.328 348.673 472.982 316.673 472.957 315.471C472.932 314.272 482.138 299.872 484.341 297.872C486.545 295.871 490.097 286.122 490.097 286.122L462.525 289.27Z" fill="#030321"/>
<path d="M514.417 284.324C514.417 284.324 515.788 301.584 510.964 307.736C506.139 313.885 478.838 314.02 478.838 314.02L473.413 377.008C473.413 377.008 466.158 376.56 461.503 375.66C461.503 375.66 457.67 306.22 462.624 301.569C467.578 296.92 490.097 286.12 490.097 286.12L514.417 284.324Z" fill="#09083C"/>
<path d="M485.996 201.731C485.996 201.731 478.663 198.934 474.33 205.099C471.012 209.82 471.707 216.278 475.745 220.401L477.379 222.069C477.379 222.069 484.053 214.892 484.126 214.547C484.198 214.2 485.996 201.731 485.996 201.731Z" fill="#07085B"/>
<path d="M481.025 237.165C481.025 237.165 491.35 235.266 496.098 235.426C500.846 235.586 493.221 247.923 493.221 247.923L485.466 248.095C485.466 248.095 480.712 242.79 481.025 242.172C481.338 241.554 481.01 237.508 481.01 237.508L481.025 237.165Z" fill="#FFC0BB"/>
<path d="M492.647 226.858L494.5 235.354C494.5 235.354 491.633 239.982 484.631 237.128C484.631 237.128 485.632 235.513 484.892 231.893C484.135 228.196 492.647 226.858 492.647 226.858Z" fill="#FFC0BB"/>
<path d="M485.115 235.318C485.18 234.712 485.19 233.949 485.077 233.015V233.017C485.192 233.949 485.182 234.712 485.117 235.318H485.115Z" fill="#E8B5B5"/>
<path d="M493.514 230.836L493.287 229.795C493.289 229.793 493.289 229.793 493.291 229.791L493.518 230.826C493.518 230.83 493.516 230.832 493.514 230.836Z" fill="#9A5874"/>
<path d="M485.117 235.318C485.182 234.712 485.192 233.949 485.077 233.017C485.329 233.034 485.579 233.044 485.828 233.044C488.706 233.044 491.364 231.814 493.288 229.796L493.515 230.837C492.464 233.558 489.808 235.208 485.117 235.318Z" fill="#FDA19A"/>
<path d="M476.752 219.124C477.198 220.518 476.657 221.939 475.539 222.297C474.422 222.654 473.154 221.813 472.708 220.417C472.26 219.021 472.803 217.602 473.921 217.244C475.038 216.887 476.306 217.728 476.752 219.124Z" fill="#F99893"/>
<path d="M476.526 227.065C476.234 226.455 475.998 225.814 475.821 225.149C475.306 223.36 475.123 221.486 475.09 219.863C475.085 219.514 475.058 219.167 475.024 218.822C474.888 217.421 475.006 215.956 475.449 214.475C476.868 209.71 481.337 206.382 486.314 206.397C493.018 206.418 498.121 212.103 497.617 218.603C498.355 218.265 499.158 218.237 499.833 218.603C501.128 219.305 501.465 221.187 500.586 222.804C499.707 224.422 497.945 225.164 496.651 224.461C496.469 224.363 496.311 224.241 496.168 224.102C495.177 229.59 490.31 233.51 484.876 232.999C482.22 232.749 479.894 231.483 478.216 229.603C478.101 229.493 477.985 229.363 477.861 229.214C477.321 228.564 476.885 227.836 476.526 227.065Z" fill="#FFC0BB"/>
<path d="M483.787 217.422C483.937 218.055 483.981 218.705 483.951 219.359C483.933 219.687 483.891 220.015 483.811 220.347C483.726 220.675 483.613 221.011 483.365 221.323L483.258 221.434L483.165 221.527C483.125 221.573 483.068 221.607 483.037 221.657C482.961 221.747 482.909 221.848 482.883 221.954C482.814 222.168 482.892 222.414 483.03 222.643C483.327 223.104 483.903 223.402 484.515 223.594C483.878 223.652 483.146 223.497 482.646 222.936C482.402 222.666 482.234 222.258 482.309 221.84C482.328 221.737 482.355 221.636 482.402 221.545C482.438 221.445 482.499 221.363 482.557 221.281C482.614 221.196 482.692 221.138 482.759 221.066C482.803 221.026 482.81 221.012 482.831 220.99L482.89 220.927C483.045 220.74 483.157 220.465 483.251 220.187C483.352 219.907 483.403 219.601 483.474 219.3C483.592 218.688 483.682 218.063 483.787 217.422Z" fill="#F99893"/>
<path d="M487.391 218.798C487.34 219.342 487.738 219.824 488.284 219.875C488.827 219.927 489.309 219.526 489.361 218.983C489.412 218.44 489.012 217.957 488.469 217.906C487.925 217.854 487.441 218.255 487.391 218.798Z" fill="#333333"/>
<path d="M478.876 218.56C478.824 219.103 479.223 219.586 479.768 219.637C480.311 219.689 480.794 219.288 480.845 218.745C480.897 218.201 480.496 217.717 479.953 217.667C479.409 217.616 478.925 218.014 478.876 218.56Z" fill="#333333"/>
<path d="M484.286 228.359C484.232 228.359 484.179 228.359 484.126 228.356C481.757 228.254 481.456 226.069 481.456 226.069C481.774 225.877 482.101 225.804 482.408 225.804C483.281 225.804 484.013 226.376 484.013 226.376C484.52 226.113 485.022 226.029 485.455 226.029C486.227 226.029 486.784 226.296 486.784 226.296C486.784 226.296 486.507 228.359 484.286 228.359Z" fill="#FDA8A3"/>
<path d="M488.095 225.663C487.807 225.852 487.51 226.021 487.199 226.165C486.892 226.313 486.577 226.443 486.255 226.546C485.611 226.752 484.941 226.874 484.27 226.86C483.599 226.851 482.937 226.698 482.316 226.435C481.698 226.165 481.128 225.781 480.598 225.343C480.826 225.598 481.078 225.838 481.351 226.054C481.622 226.271 481.923 226.452 482.232 226.616C482.544 226.773 482.876 226.897 483.218 226.983C483.561 227.065 483.914 227.11 484.264 227.12C484.972 227.127 485.674 226.99 486.322 226.733C486.97 226.475 487.58 226.124 488.095 225.663Z" fill="#F99893"/>
<path d="M486.473 216.414C486.995 216.33 487.481 216.278 487.956 216.273C488.429 216.267 488.887 216.318 489.321 216.435C489.752 216.557 490.183 216.713 490.582 216.967C490.797 217.068 490.977 217.23 491.19 217.358C491.396 217.499 491.581 217.669 491.812 217.812C491.722 217.566 491.61 217.323 491.47 217.096C491.31 216.885 491.163 216.652 490.952 216.479C490.568 216.09 490.054 215.827 489.516 215.682C488.976 215.537 488.402 215.539 487.876 215.666C487.35 215.8 486.854 216.038 486.473 216.414Z" fill="#07085B"/>
<path d="M482.087 216.288C481.74 215.884 481.265 215.604 480.754 215.426C480.239 215.253 479.669 215.201 479.118 215.299C478.57 215.398 478.035 215.617 477.619 215.972C477.394 216.126 477.226 216.346 477.051 216.542C476.893 216.757 476.759 216.99 476.648 217.225C476.891 217.103 477.089 216.95 477.306 216.828C477.531 216.719 477.722 216.572 477.947 216.489C478.365 216.271 478.807 216.151 479.247 216.067C479.692 215.987 480.151 215.976 480.622 216.021C481.095 216.069 481.576 216.161 482.087 216.288Z" fill="#07085B"/>
<path d="M469.291 257.265C469.291 257.265 468.351 280.659 465.718 284.324L480.198 281.035V255.573L469.291 257.265Z" fill="#FFC0BB"/>
<path d="M475.461 260.458C475.461 260.458 477.476 266.346 477.843 269.475C478.752 277.242 477.764 282.72 476.155 287.142C473.897 293.343 492.327 291.087 492.704 290.9C493.08 290.711 508.876 284.604 508.876 284.604L511.885 275.867V260.458L511.038 253.413L475.461 260.458Z" fill="#02CCC0"/>
<path d="M519.596 253.414L507.998 257.36C507.998 257.36 510.004 275.899 509.377 278.531C508.841 280.779 500.432 285.25 495.103 287.754C494.245 288.156 493.299 288.328 492.355 288.252C489.319 288.002 483.938 287.533 483.094 287.474C481.767 287.382 478.119 287.476 478.003 287.941C477.894 288.372 480.851 287.897 482.77 288.294C483.04 288.349 482.895 288.709 482.832 288.711C481.814 288.749 479.194 288.86 478.332 289.148C477.276 289.499 481.013 289.22 483.033 289.592C483.176 289.617 483.288 290.017 483.185 290.12C482.945 290.357 482.066 290.565 479.654 290.811C475.629 291.222 479.566 291.72 479.566 291.72C479.566 291.72 479.928 291.617 483.385 291.144C483.513 291.127 483.654 291.486 483.464 291.653C483.13 291.945 482.356 292.523 481.317 292.83C480.022 293.211 480.964 293.547 480.964 293.547C480.964 293.547 483.414 292.818 484.789 292.716C485.818 292.637 490.669 293.032 492.658 293.146L492.811 292.805C495.509 292.727 517.023 292.168 519.094 278.844C521.224 265.126 519.596 253.414 519.596 253.414Z" fill="#FFC0BB"/>
<path d="M435.302 266.69H472.257L482.735 292.247H500.537C501.035 292.247 501.439 292.649 501.439 293.147C501.439 293.645 501.035 294.047 500.537 294.047H447.583L435.302 266.69Z" fill="#07085B"/>
<path d="M453.627 281.275C453.845 282.364 454.794 283.092 455.748 282.901C456.703 282.711 457.298 281.673 457.081 280.585C456.863 279.496 455.912 278.767 454.958 278.958C454.005 279.149 453.408 280.186 453.627 281.275Z" fill="#DAEEF7"/>
<path d="M481.025 237.165C481.025 237.165 488.044 245.35 496.098 235.426C496.098 235.426 504.898 234.71 511.385 239.313C517.874 243.917 521.758 254.257 521.758 254.257C521.758 254.257 510.004 260.176 507.089 260.458H474.462C474.462 260.458 469.479 260.082 464.684 257.64C464.684 257.64 465.511 241.203 481.025 237.165Z" fill="#02CCC0"/>
<path d="M501.864 248.094C502.202 249.099 502.499 250.115 502.799 251.13C503.102 252.144 503.374 253.168 503.645 254.192C503.905 255.22 504.164 256.248 504.389 257.285C504.612 258.32 504.831 259.362 504.997 260.412L504.749 260.164C505.07 260.197 505.464 260.185 505.827 260.157C506.197 260.132 506.568 260.079 506.938 260.025C507.678 259.894 508.42 259.752 509.148 259.547L509.696 259.402L510.239 259.236C510.599 259.123 510.964 259.018 511.322 258.891L512.397 258.519L513.46 258.109C514.171 257.84 514.867 257.527 515.57 257.239L517.651 256.292L519.712 255.296C520.391 254.945 521.071 254.596 521.758 254.257C521.112 254.665 520.457 255.066 519.803 255.462C519.142 255.849 518.476 256.225 517.805 256.597C517.128 256.955 516.446 257.304 515.759 257.647L514.714 258.132C514.365 258.294 514.018 258.458 513.66 258.597C512.249 259.207 510.794 259.722 509.303 260.132L508.744 260.283L508.178 260.41C507.802 260.506 507.415 260.563 507.034 260.63C506.647 260.683 506.261 260.736 505.869 260.759C505.47 260.786 505.096 260.803 504.656 260.754L504.442 260.729L504.408 260.504C504.091 258.427 503.668 256.356 503.228 254.291L502.556 251.193L501.864 248.094Z" fill="white"/>
<path d="M477.058 245.716C476.597 246.918 476.179 248.125 475.808 249.343C475.44 250.562 475.115 251.79 474.9 253.035C474.78 253.654 474.702 254.28 474.65 254.907C474.585 255.533 474.58 256.162 474.602 256.789C474.648 258.044 476.509 263.949 477.058 265.118C476.284 264.081 474.259 258.126 474.122 256.827C473.964 255.523 474.072 254.206 474.292 252.926C474.414 252.287 474.557 251.652 474.734 251.029C474.919 250.407 475.115 249.789 475.352 249.187C475.817 247.982 476.368 246.807 477.058 245.716Z" fill="white"/>
<path d="M497.618 218.602C497.618 218.602 485.929 214.464 481.052 205.727C481.052 205.727 481.376 198.06 492.119 201.21C499.561 203.393 502.16 213.467 497.618 218.602Z" fill="#07085B"/>
<path d="M606.748 219.142C605.873 219.285 605.007 219.379 604.144 219.501C603.28 219.619 602.431 219.754 601.571 219.966C602.336 219.504 603.226 219.293 604.098 219.165C604.977 219.052 605.867 219.02 606.748 219.142Z" fill="#F99893"/>
<path d="M434.912 381.36H431.427L440.12 347.229L443.394 348.06L434.912 381.36Z" fill="#3D3A55"/>
<path d="M641.258 381.34H644.743L636.05 347.206L632.778 348.039L641.258 381.34Z" fill="#3D3A55"/>
<path d="M604.25 381.34H600.765L609.458 347.206L612.732 348.039L604.25 381.34Z" fill="#3D3A55"/>
<path d="M570.501 259.721L571.771 285.05C571.79 285.425 571.473 285.73 571.098 285.698L569.917 285.595C569.603 285.566 569.36 285.309 569.351 284.996L568.602 259.533C568.602 259.533 569.563 259.06 570.501 259.721Z" fill="#C1215B"/>
<path d="M195.72 333.264H121.728V302.829H195.72V333.264Z" fill="#E03268"/>
<path d="M64.8848 238.682C65.8071 238.746 139.018 238.682 139.018 238.682V308.141H91.5598L66.1541 282.755L64.8848 238.682Z" fill="#FF5B7E"/>
<path d="M194.234 277.706C194.234 277.706 143.461 280.738 143.461 277.706C143.461 274.676 143.461 290.914 143.461 290.914C143.461 290.914 168.293 295.365 171.087 295.365C173.881 295.365 186.891 302.254 188.615 302.828C190.339 303.404 194.043 288.018 194.234 287.886C194.427 287.755 194.234 277.706 194.234 277.706Z" fill="#F9537F"/>
<path d="M68.7554 291.105H61.0151C59.4496 291.105 58.1807 289.837 58.1807 288.27V241.517C58.1807 239.952 59.4496 238.682 61.0151 238.682H68.7554C70.3207 238.682 71.5897 239.952 71.5897 241.517V288.27C71.5897 289.837 70.3207 291.105 68.7554 291.105Z" fill="#E03268"/>
<path d="M119.911 277.706H59.9531C54.5576 277.706 50.1836 282.076 50.1836 287.468V321.884C50.1836 335.608 61.3165 346.73 75.0492 346.73L136.784 347.109C136.784 347.109 132.499 345.967 131.794 344.735C128.888 339.656 121.443 326.594 121.443 326.133C121.443 325.559 119.911 277.706 119.911 277.706Z" fill="#F9537F"/>
<path d="M186.381 285.554V319.091C186.381 325.801 180.938 331.239 174.224 331.239H139.921C133.207 331.239 127.764 325.801 127.764 319.091V285.554C127.764 281.22 124.248 277.706 119.911 277.706C115.573 277.706 112.057 281.22 112.057 285.554V319.956C112.057 335.018 124.276 347.228 139.35 347.228H174.796C189.87 347.228 202.089 335.018 202.089 319.956V285.554C202.089 281.22 198.572 277.706 194.234 277.706C189.898 277.706 186.381 281.22 186.381 285.554Z" fill="#FF85A5"/>
<path d="M187.361 363.182L188.61 373.2L195.335 373.723L195.23 364.431L187.361 363.182Z" fill="#FFC0BB"/>
<path d="M205.551 381.057L187.182 381.181C186.78 381.183 186.457 380.868 186.461 380.475L186.466 379.947C186.469 379.554 186.797 379.236 187.199 379.232L205.568 379.108C205.968 379.106 206.292 379.421 206.289 379.813L206.283 380.342C206.281 380.734 205.951 381.055 205.551 381.057Z" fill="#3D3A55"/>
<path d="M187.432 373.312L186.727 378.735C186.641 379.404 187.018 380.009 187.521 380.005L204.989 379.887C205.443 379.885 205.893 379.604 206.137 379.084C206.384 378.548 206.442 377.745 205.669 376.67C204.123 374.521 198.99 374.029 196.494 372.204L188.356 372.258C187.902 372.261 187.51 372.708 187.432 373.312Z" fill="#E03268"/>
<path d="M195.229 375.358C195.103 375.284 195.06 375.076 195.134 374.918C195.483 374.172 196.572 372.359 198.749 372.716C198.875 372.737 198.959 372.899 198.936 373.067V373.072C198.913 373.236 198.799 373.345 198.677 373.324C196.726 373.011 195.799 374.611 195.517 375.235C195.456 375.368 195.334 375.421 195.229 375.358Z" fill="white"/>
<path d="M197.037 376.044C196.911 375.968 196.867 375.762 196.942 375.602C197.292 374.858 198.379 373.043 200.557 373.399C200.683 373.42 200.767 373.582 200.744 373.752V373.758C200.721 373.92 200.606 374.028 200.484 374.009C198.534 373.697 197.607 375.294 197.325 375.92C197.264 376.053 197.142 376.105 197.037 376.044Z" fill="white"/>
<path d="M198.72 376.683C198.594 376.608 198.55 376.4 198.624 376.242C198.973 375.497 200.062 373.681 202.239 374.04C202.365 374.059 202.449 374.223 202.426 374.391V374.396C202.403 374.56 202.289 374.667 202.167 374.648C200.216 374.335 199.29 375.935 199.007 376.559C198.946 376.692 198.824 376.746 198.72 376.683Z" fill="white"/>
<path d="M174.556 363.395L177.528 373.063L184.371 373.11L183.179 366.051L174.556 363.395Z" fill="#FFC0BB"/>
<path d="M113.927 216.753C113.927 216.753 111.883 206.446 117.856 202.822C123.829 199.197 129.984 199.839 134.097 202.278C138.211 204.719 140.414 212.802 138.351 217.306L124.569 212.457L113.927 216.753Z" fill="#07085B"/>
<path d="M194.2 381.236L175.831 381.36C175.43 381.362 175.107 381.048 175.11 380.655L175.115 380.127C175.119 379.734 175.447 379.413 175.848 379.412L194.217 379.288C194.62 379.286 194.942 379.6 194.938 379.993L194.932 380.521C194.93 380.914 194.602 381.234 194.2 381.236Z" fill="#3D3A55"/>
<path d="M176.081 373.491L175.377 378.914C175.29 379.583 175.667 380.187 176.17 380.184L193.638 380.065C194.092 380.064 194.544 379.783 194.786 379.263C195.034 378.727 195.091 377.924 194.319 376.849C192.774 374.7 187.64 374.208 185.142 372.383L177.006 372.438C176.551 372.44 176.16 372.886 176.081 373.491Z" fill="#F9537F"/>
<path d="M183.879 375.535C183.753 375.461 183.709 375.253 183.783 375.095C184.133 374.349 185.221 372.536 187.399 372.892C187.525 372.913 187.609 373.076 187.586 373.245L187.585 373.249C187.563 373.413 187.448 373.52 187.327 373.501C185.374 373.188 184.449 374.788 184.166 375.411C184.106 375.545 183.983 375.598 183.879 375.535Z" fill="white"/>
<path d="M185.687 376.223C185.562 376.146 185.517 375.94 185.592 375.78C185.941 375.036 187.03 373.221 189.208 373.578C189.333 373.599 189.417 373.761 189.394 373.931L189.394 373.936C189.371 374.098 189.257 374.207 189.135 374.188C187.183 373.875 186.258 375.473 185.975 376.099C185.914 376.232 185.792 376.284 185.687 376.223Z" fill="white"/>
<path d="M187.368 376.862C187.243 376.788 187.198 376.58 187.273 376.422C187.622 375.676 188.71 373.861 190.887 374.218C191.013 374.239 191.097 374.403 191.074 374.57V374.576C191.051 374.74 190.937 374.847 190.815 374.828C188.864 374.515 187.938 376.115 187.655 376.738C187.595 376.872 187.472 376.925 187.368 376.862Z" fill="white"/>
<path d="M176.165 380.184C175.713 380.184 175.364 379.694 175.363 379.108C175.363 379.043 175.367 378.98 175.376 378.914L175.829 375.426C175.93 375.419 176.037 375.413 176.149 375.413C177.487 375.413 179.598 376.124 180.831 380.153L176.169 380.184C176.168 380.184 176.166 380.184 176.165 380.184Z" fill="#F24665"/>
<path d="M120.242 226.131L119.243 237.641L129.691 237.154L128.486 226.964L120.242 226.131Z" fill="#FFC0BB"/>
<path d="M129.059 231.81L128.486 226.965L120.241 226.131L119.896 230.117C121.535 231.705 124.483 233.35 129.059 231.81Z" fill="#F99893"/>
<path d="M135.465 218.378C134.837 219.64 135.17 221.061 136.209 221.549C137.249 222.037 138.6 221.41 139.229 220.148C139.857 218.883 139.524 217.465 138.484 216.975C137.445 216.487 136.093 217.114 135.465 218.378Z" fill="#F99893"/>
<path d="M134.588 225.938C134.956 225.398 135.276 224.822 135.541 224.216C136.288 222.588 136.726 220.837 136.981 219.302C137.036 218.972 137.11 218.648 137.191 218.322C137.516 217.014 137.602 215.609 137.377 214.146C136.65 209.436 132.753 205.682 127.901 205.03C121.364 204.153 115.605 208.857 115.198 215.088C114.526 214.669 113.749 214.533 113.04 214.791C111.681 215.283 111.092 217.022 111.725 218.673C112.359 220.324 113.975 221.264 115.334 220.772C115.523 220.704 115.695 220.608 115.853 220.496C116.063 225.833 120.265 230.202 125.631 230.446C128.255 230.564 130.696 229.675 132.592 228.117C132.718 228.028 132.851 227.921 132.991 227.797C133.607 227.252 134.134 226.621 134.588 225.938Z" fill="#FFC0BB"/>
<path d="M125.14 216.644C125.115 217.166 124.659 217.571 124.121 217.546C123.584 217.521 123.168 217.079 123.193 216.556C123.219 216.032 123.675 215.629 124.212 215.654C124.75 215.677 125.165 216.121 125.14 216.644Z" fill="#333333"/>
<path d="M133.473 217.559C133.448 218.081 132.992 218.486 132.454 218.461C131.917 218.436 131.501 217.994 131.526 217.471C131.552 216.947 132.008 216.544 132.545 216.569C133.083 216.592 133.498 217.036 133.473 217.559Z" fill="#333333"/>
<path d="M126.363 214.505C125.867 214.356 125.4 214.242 124.938 214.173C124.477 214.105 124.025 214.091 123.585 214.145C123.147 214.202 122.707 214.293 122.283 214.48C122.058 214.547 121.862 214.677 121.635 214.77C121.416 214.875 121.212 215.01 120.967 215.115C121.09 214.896 121.233 214.68 121.399 214.484C121.583 214.305 121.759 214.103 121.989 213.967C122.417 213.651 122.956 213.47 123.499 213.403C124.046 213.34 124.604 213.416 125.1 213.611C125.593 213.807 126.045 214.099 126.363 214.505Z" fill="#07085B"/>
<path d="M186.5 349.973H71.6079C71.201 349.973 70.8711 349.643 70.8711 349.235V347.227C70.8711 346.819 71.201 346.489 71.6079 346.489H186.5C186.907 346.489 187.237 346.819 187.237 347.227V349.235C187.237 349.643 186.907 349.973 186.5 349.973Z" fill="#3D3A55"/>
<path d="M130.656 214.976C131.05 214.636 131.551 214.434 132.075 214.335C132.6 214.24 133.163 214.268 133.687 214.434C134.206 214.602 134.698 214.882 135.055 215.273C135.253 215.451 135.386 215.681 135.53 215.891C135.654 216.116 135.752 216.352 135.828 216.591C135.608 216.442 135.436 216.272 135.242 216.127C135.037 215.994 134.871 215.828 134.664 215.719C134.286 215.456 133.872 215.285 133.454 215.145C133.032 215.01 132.587 214.938 132.12 214.919C131.653 214.899 131.173 214.922 130.656 214.976Z" fill="#07085B"/>
<path d="M115.353 215.24C114.734 214.678 114.241 214.699 114.241 214.699L114.664 211.406L115.8 209.455C115.8 209.455 120.152 204.257 120.303 204.129C120.454 204.003 123.681 202.39 123.879 202.308C124.077 202.228 128.474 203.044 128.474 203.044C128.474 203.044 136.315 201.793 134.843 205.699C133.372 209.602 127.608 211.459 127.324 211.272C128.282 210.422 128.478 207.909 128.478 207.909C124.286 211.995 116.556 214.817 115.353 215.24Z" fill="#07085B"/>
<path d="M128.585 216.567C128.87 217.013 129.113 217.48 129.333 217.958C129.553 218.437 129.746 218.927 129.897 219.438C129.966 219.696 130.029 219.955 130.048 220.237C130.05 220.308 130.05 220.38 130.041 220.456C130.037 220.495 130.025 220.535 130.017 220.575C130 220.617 129.989 220.659 129.958 220.702C129.942 220.723 129.925 220.744 129.907 220.765L129.865 220.8C129.837 220.822 129.81 220.847 129.781 220.868C129.722 220.908 129.664 220.95 129.603 220.983C129.363 221.126 129.11 221.229 128.853 221.314C128.596 221.4 128.335 221.471 128.068 221.515C128.554 221.292 129.043 221.068 129.459 220.775C129.512 220.739 129.558 220.699 129.606 220.66L129.672 220.599L129.704 220.569L129.713 220.552C129.745 220.5 129.749 220.371 129.736 220.256C129.711 220.018 129.651 219.768 129.579 219.524C129.44 219.03 129.263 218.542 129.094 218.05C128.921 217.56 128.745 217.068 128.585 216.567Z" fill="#F99893"/>
<path d="M130.789 234.803C130.789 234.803 138.97 235.148 143.247 240.354C147.523 245.558 159.653 296.61 159.653 296.61L146.012 295.152C146.012 295.152 128.273 270.901 128.273 270.277C128.273 269.652 130.789 234.803 130.789 234.803Z" fill="#050849"/>
<path d="M114.711 234.885C114.711 234.885 130.371 234.852 130.613 234.87C130.855 234.885 132.056 234.757 132.498 235.22C132.941 235.682 133.704 238.233 131.525 239.482C129.347 240.731 133.977 240.783 128.068 241.824C122.16 242.865 123.93 244.268 119.452 242.447C114.973 240.626 114.396 241.406 114.241 239.793C114.087 238.18 114.711 234.885 114.711 234.885Z" fill="#FFC0BB"/>
<path d="M145.835 258.06C144.927 249.867 142.729 244.373 140.265 240.691C138.423 237.94 135.634 236.027 132.498 235.221C132.484 235.274 131.705 238.184 127.681 238.649C123.618 239.118 114.867 234.876 114.711 234.885L114.711 234.883C110.19 235.165 106.281 236.014 104.244 238.39C100.182 243.124 86.7446 276.194 87.0571 280.866C87.3696 285.537 90.9638 285.537 90.9638 285.537L127.764 285.555V294.019L154.459 295.842C153.715 295.35 148.409 281.27 145.835 258.06Z" fill="#07085B"/>
<path d="M148.793 254.846C149.028 254.853 158.51 249.112 158.51 249.112L160.282 249.488L159.653 249.951L160.713 249.686L162.437 249.951C162.437 249.951 156.738 256.673 156.642 256.863C156.547 257.056 154.056 258.013 153.865 258.108C153.673 258.204 148.793 254.846 148.793 254.846Z" fill="#DAEEF7"/>
<path d="M133.618 250.259L134.48 249.721L134.875 249.99V249.486L135.414 249.111L149.206 254.566C149.206 254.566 144.788 257.365 144.645 257.257C144.501 257.15 136.635 255.714 136.492 255.499C136.348 255.283 133.618 250.259 133.618 250.259Z" fill="#DAEEF7"/>
<path d="M133.837 250.007L149.469 255.065L162.075 249.579C162.84 249.248 163.68 249.865 163.587 250.695L161.186 272.165C161.146 272.522 160.931 272.837 160.613 273.003L148.509 279.379L137.546 275.323L137.264 274.909L135.843 274.694L131.246 272.993C130.835 272.84 130.577 272.432 130.614 271.998L132.422 250.945C132.481 250.249 133.173 249.791 133.837 250.007Z" fill="#FEB546"/>
<path d="M133.837 250.005C133.172 249.791 132.481 250.249 132.421 250.945L130.616 271.969C130.577 272.421 130.846 272.844 131.272 273.003L135.842 274.694L137.264 274.909L137.546 275.323L144.92 278.052C146.616 277.724 148.3 277.409 148.3 277.409L149.469 255.065L133.837 250.005Z" fill="#F4A640"/>
<path d="M151.802 257.63L161.55 253.37L161.239 257.798L151.685 262.224L151.802 257.63Z" fill="#F4A640"/>
<path d="M157.067 294.073C157.067 294.073 190.074 293.031 197.573 300.11C205.072 307.188 197.783 359.449 196.532 364.334C196.532 364.334 191.948 368.594 186.532 366.93C181.116 365.265 183.199 341.95 183.199 341.95C183.199 341.95 183.824 319.677 182.991 316.554C182.157 313.432 170.699 311.142 170.699 311.142C170.699 311.142 152.992 298.861 154.033 298.861C155.075 298.861 157.067 294.073 157.067 294.073Z" fill="#2B1C35"/>
<path d="M127.765 293.07C127.765 293.07 171.95 287.827 177.991 307.81C184.033 327.793 188.616 367.344 188.616 367.344C188.616 367.344 182.783 370.883 174.866 367.344C174.866 367.344 163.67 324.88 159.477 320.715C155.284 316.553 127.765 319.091 127.765 319.091V293.07Z" fill="#3A2645"/>
<path d="M139.121 280.366C138.953 279.411 138.714 278.473 138.444 277.546C138.169 276.617 137.865 275.704 137.5 274.802L137.459 274.701L137.348 274.695L107.866 273.219C107.976 272.325 108.249 271.448 108.546 270.588C108.859 269.696 109.216 268.819 109.59 267.947C110.343 266.208 111.168 264.502 112.022 262.808C113.737 259.426 115.56 256.096 117.459 252.813L117.429 252.794C115.507 256.066 113.66 259.382 111.921 262.757C111.055 264.444 110.217 266.149 109.45 267.886C109.069 268.756 108.705 269.635 108.383 270.529C108.067 271.425 107.774 272.339 107.664 273.3L107.652 273.395L107.752 273.401L137.216 275.037C137.554 275.885 137.848 276.762 138.109 277.643C138.376 278.56 138.611 279.489 138.776 280.427C138.938 281.367 139.074 282.313 139.077 283.263C139.088 284.168 139.017 285.08 138.778 285.947L130.052 285.694L125.624 285.57L121.194 285.495L121.192 285.537L125.618 285.713L130.044 285.902L138.896 286.268L139.018 286.273L139.053 286.157C139.344 285.213 139.433 284.229 139.428 283.257C139.425 282.283 139.286 281.32 139.121 280.366Z" fill="white"/>
<path d="M148.453 254.758L147.322 278.301L149.048 278.051L150.263 254.758C150.263 254.758 149.351 254.124 148.453 254.758Z" fill="#ED9935"/>
<path d="M149.711 277.029C147.523 277.992 143.085 277.292 143.085 277.292L139.724 276.125C139.254 276.444 138.776 276.768 138.303 277.084C138.35 277.237 138.398 277.391 138.444 277.546C138.714 278.473 138.953 279.411 139.121 280.366C139.285 281.319 139.425 282.282 139.428 283.257C139.429 283.417 139.423 283.575 139.418 283.735L139.891 283.56C140.463 283.674 141.498 283.577 142.933 283.356C144.57 283.146 147.159 282.786 148.29 282.46C149.106 282.225 149.46 281.707 149.61 281.224C150.255 280.831 150.315 280.099 150.237 279.516C150.256 279.477 150.272 279.441 150.284 279.403C150.598 278.421 150.423 278.166 150.262 278.066C150.377 277.948 150.457 277.819 150.492 277.679C150.857 276.223 149.711 277.029 149.711 277.029Z" fill="#FFC0BB"/>
<path d="M150.262 279.437C149.999 279.744 149.659 279.976 149.304 280.173C148.949 280.369 148.564 280.51 148.173 280.619C147.779 280.718 147.377 280.785 146.972 280.802C146.771 280.815 146.568 280.804 146.367 280.808C146.166 280.792 145.965 280.773 145.766 280.75C146.168 280.729 146.566 280.716 146.961 280.667C147.356 280.619 147.745 280.548 148.128 280.449C148.51 280.348 148.883 280.217 149.244 280.053C149.602 279.887 149.95 279.69 150.262 279.437Z" fill="#F99893"/>
<path d="M149.615 281.228C149.329 281.512 148.971 281.718 148.603 281.886C148.232 282.054 147.838 282.165 147.44 282.241C147.039 282.308 146.633 282.344 146.228 282.329C146.026 282.327 145.825 282.3 145.624 282.287C145.425 282.256 145.226 282.222 145.029 282.182C145.432 282.193 145.83 282.212 146.228 282.193C146.625 282.176 147.019 282.138 147.408 282.069C147.797 281.997 148.179 281.896 148.552 281.76C148.922 281.623 149.285 281.455 149.615 281.228Z" fill="#F99893"/>
<path d="M150.262 278.066C149.999 278.373 149.659 278.606 149.304 278.802C148.949 278.999 148.564 279.14 148.173 279.248C147.779 279.346 147.377 279.412 146.972 279.429C146.771 279.445 146.568 279.433 146.367 279.435C146.166 279.42 145.965 279.403 145.766 279.378C146.168 279.359 146.566 279.346 146.961 279.296C147.356 279.246 147.745 279.178 148.128 279.079C148.51 278.976 148.883 278.844 149.244 278.682C149.602 278.514 149.95 278.318 150.262 278.066Z" fill="#F99893"/>
<path d="M124.634 223.441C125.551 223.548 126.444 223.704 127.341 223.83C128.239 223.959 129.127 224.068 130.049 224.104C129.15 224.345 128.2 224.301 127.291 224.177C126.379 224.038 125.48 223.814 124.634 223.441Z" fill="#F99893"/>
<path d="M73.2283 381.294H69.8926L78.212 348.629L81.3448 349.426L73.2283 381.294Z" fill="#3D3A55"/>
<path d="M134.393 381.294H131.058L139.377 348.629L142.51 349.426L134.393 381.294Z" fill="#3D3A55"/>
<path d="M113.861 381.294H117.196L108.877 348.629L105.744 349.426L113.861 381.294Z" fill="#3D3A55"/>
<path d="M597.923 125.975H495.425V120.111H597.923V125.975Z" fill="#4188E4"/>
<path d="M612.998 175.911H510.498V170.048H612.998V175.911Z" fill="#4188E4"/>
<path d="M241.123 353.488H238.217V116.236H241.123V353.488Z" fill="#09083C"/>
<path d="M272.251 353.488H269.345V116.236H272.251V353.488Z" fill="#09083C"/>
<path d="M270.798 122.304H239.67V119.846H270.798V122.304Z" fill="#09083C"/>
<path d="M270.798 138.225H239.67V135.769H270.798V138.225Z" fill="#09083C"/>
<path d="M270.798 154.148H239.67V151.692H270.798V154.148Z" fill="#09083C"/>
<path d="M270.798 170.072H239.67V167.616H270.798V170.072Z" fill="#09083C"/>
<path d="M270.798 185.996H239.67V183.54H270.798V185.996Z" fill="#09083C"/>
<path d="M270.798 201.92H239.67V199.464H270.798V201.92Z" fill="#09083C"/>
<path d="M270.798 217.844H239.67V215.388H270.798V217.844Z" fill="#09083C"/>
<path d="M270.798 233.768H239.67V231.31H270.798V233.768Z" fill="#09083C"/>
<path d="M270.798 249.691H239.67V247.234H270.798V249.691Z" fill="#09083C"/>
<path d="M270.798 265.616H239.67V263.158H270.798V265.616Z" fill="#09083C"/>
<path d="M270.798 281.536H239.67V279.08H270.798V281.536Z" fill="#09083C"/>
<path d="M270.798 297.46H239.67V295.004H270.798V297.46Z" fill="#09083C"/>
<path d="M270.798 313.385H239.67V310.929H270.798V313.385Z" fill="#09083C"/>
<path d="M660.917 85.9418C660.917 101.471 648.319 114.058 632.778 114.058C617.238 114.058 604.64 101.471 604.64 85.9418C604.64 70.4128 617.238 57.8242 632.778 57.8242C648.319 57.8242 660.917 70.4128 660.917 85.9418Z" fill="#4188E4"/>
<path d="M657.515 84.3886C658.373 98.0413 647.993 109.802 634.331 110.659C620.668 111.515 608.898 101.144 608.04 87.491C607.183 73.8402 617.564 62.079 631.226 61.2229C644.889 60.3648 656.657 70.7378 657.515 84.3886Z" fill="white"/>
<path d="M616.78 85.4941V86.1348H608.436V85.4941H616.78Z" fill="#B0C1EC"/>
<path d="M657.169 85.4941V86.1348H648.825V85.4941H657.169Z" fill="#B0C1EC"/>
<path d="M633.063 70.125H632.422V61.7885H633.063V70.125Z" fill="#B0C1EC"/>
<path d="M633.063 110.324H632.422V101.988H633.063V110.324Z" fill="#B0C1EC"/>
<path d="M633.467 85.9416C633.467 86.3229 633.159 86.6318 632.777 86.6318C632.396 86.6318 632.087 86.3229 632.087 85.9416C632.087 85.5602 632.396 85.2513 632.777 85.2513C633.159 85.2513 633.467 85.5602 633.467 85.9416Z" fill="#B0C1EC"/>
<path d="M632.778 86.249C632.698 86.249 632.62 86.2185 632.559 86.1575L620.148 73.7576C620.028 73.6374 620.028 73.441 620.148 73.3209C620.27 73.2008 620.464 73.2008 620.584 73.3209L632.996 85.7208C633.116 85.8429 633.116 86.0374 632.996 86.1575C632.937 86.2185 632.857 86.249 632.778 86.249Z" fill="#B0C1EC"/>
<path d="M636.766 98.4735C636.717 98.4487 636.675 98.4029 636.656 98.3438L632.644 86.2375C632.604 86.1193 632.668 85.9916 632.787 85.9534C632.903 85.9134 633.031 85.9782 633.069 86.0964L637.081 98.2027C637.121 98.3209 637.056 98.4487 636.938 98.4868C636.879 98.5059 636.818 98.5002 636.766 98.4735Z" fill="#B0C1EC"/>
<path d="M724.268 266.411H698.975C696.789 266.411 695.017 264.638 695.017 262.454C695.017 260.269 696.789 258.495 698.975 258.495H724.268C724.504 258.495 724.695 258.305 724.695 258.068C724.695 257.83 724.504 257.638 724.268 257.638H698.975C696.313 257.638 694.158 259.791 694.158 262.454C694.158 265.112 696.313 267.271 698.975 267.271H724.268C724.504 267.271 724.695 267.078 724.695 266.842C724.695 266.607 724.504 266.411 724.268 266.411Z" fill="#23ADE0"/>
<path d="M724.051 258.495H700.01C697.826 258.495 696.053 260.269 696.053 262.455C696.053 264.638 697.826 266.415 700.01 266.415H724.051V258.495Z" fill="#D4D0CE"/>
<path d="M724.051 265.43H699.443C697.1 265.43 696.053 263.612 696.053 262.455C696.053 260.269 697.826 258.495 700.01 258.495H698.977C696.792 258.495 695.019 260.269 695.019 262.455C695.019 264.638 696.792 266.415 698.977 266.415H724.051V265.43Z" fill="#BDB9B3"/>
<path d="M701.314 260.04C707.651 260.126 713.987 260.126 720.324 260.04C713.987 259.954 707.651 259.954 701.314 260.04Z" fill="#9E9798"/>
<path d="M697.177 262.454L704.428 262.511L711.679 262.454L704.428 262.398L697.177 262.454Z" fill="#9E9798"/>
<path d="M705.094 264.584L714.572 264.637L724.051 264.584L714.572 264.527L705.094 264.584Z" fill="#9E9798"/>
<path d="M703.822 263.33L713.936 263.383L724.051 263.33L713.936 263.273L703.822 263.33Z" fill="#9E9798"/>
<path d="M703.822 261.105C710.565 261.212 717.308 261.212 724.051 261.105C717.308 260.999 710.565 260.999 703.822 261.105Z" fill="#9E9798"/>
<path d="M716.031 259.265L720.041 259.321L724.051 259.265L720.041 259.209L716.031 259.265Z" fill="#9E9798"/>
<path d="M700.878 265.702L711.757 265.758L722.635 265.702L711.757 265.646L700.878 265.702Z" fill="#9E9798"/>
<path d="M700.185 261.612C702.795 261.719 705.404 261.719 708.015 261.612C705.404 261.506 702.795 261.506 700.185 261.612Z" fill="#9E9798"/>
<path d="M725.809 268.799H697.318C695.678 268.799 694.351 270.133 694.351 271.786C694.351 273.435 695.678 274.775 697.318 274.775H725.809V268.799Z" fill="#D4D0CE"/>
<path d="M726.042 274.775H696.535C694.899 274.757 693.575 273.423 693.575 271.786C693.575 270.148 694.899 268.814 696.535 268.799H726.042C726.462 268.799 726.806 268.455 726.806 268.034C726.806 267.615 726.462 267.271 726.042 267.271H696.169C693.866 267.473 692.05 269.431 692.05 271.786C692.05 274.141 693.866 276.101 696.169 276.3H726.042C726.462 276.3 726.806 275.956 726.806 275.538C726.806 275.117 726.462 274.775 726.042 274.775Z" fill="#2EB054"/>
<path d="M700.895 269.905C708.137 269.98 715.379 269.98 722.62 269.905C715.379 269.831 708.137 269.831 700.895 269.905Z" fill="#9E9798"/>
<path d="M697.359 271.785L705.037 271.833L712.714 271.785L705.037 271.737L697.359 271.785Z" fill="#9E9798"/>
<path d="M704.131 273.138L714.97 273.186L725.809 273.138L714.97 273.088L704.131 273.138Z" fill="#9E9798"/>
<path d="M703.043 272.335L714.426 272.382L725.809 272.335L714.426 272.287L703.043 272.335Z" fill="#9E9798"/>
<path d="M703.043 270.818C710.631 270.907 718.22 270.91 725.809 270.818C718.22 270.726 710.631 270.726 703.043 270.818Z" fill="#9E9798"/>
<path d="M718.949 269.244L722.379 269.291L725.809 269.244L722.379 269.196L718.949 269.244Z" fill="#9E9798"/>
<path d="M700.526 273.601L712.561 273.648L724.598 273.601L712.561 273.554L700.526 273.601Z" fill="#9E9798"/>
<path d="M699.932 271.249C703.149 271.34 706.365 271.34 709.581 271.249C706.365 271.157 703.149 271.159 699.932 271.249Z" fill="#9E9798"/>
<path d="M697.191 273.945C695.012 273.945 694.351 272.405 694.351 271.786C694.351 270.133 695.678 268.799 697.318 268.799H696.543C694.905 268.799 693.574 270.133 693.574 271.786C693.574 273.435 694.905 274.775 696.543 274.775H725.809V273.945H697.191Z" fill="#BDB9B3"/>
<path d="M724.234 277.259H699.116C697.318 277.259 695.862 278.727 695.862 280.533C695.862 282.342 697.318 283.811 699.116 283.811H724.234V277.259Z" fill="#D4D0CE"/>
<path d="M724.323 283.804H698.247C696.462 283.783 695.012 282.318 695.012 280.532C695.012 278.747 696.462 277.285 698.247 277.267H724.323C724.589 277.267 724.807 277.05 724.807 276.783C724.807 276.513 724.589 276.3 724.323 276.3H697.899C696.855 276.394 695.887 276.875 695.169 277.658C694.445 278.447 694.047 279.467 694.047 280.532C694.047 281.6 694.445 282.62 695.169 283.412C695.887 284.189 696.855 284.676 697.899 284.768H724.323C724.589 284.768 724.807 284.554 724.807 284.284C724.807 284.02 724.589 283.804 724.323 283.804Z" fill="#EE7936"/>
<path d="M704.63 278.471C708.96 278.551 713.289 278.551 717.619 278.471C713.289 278.391 708.96 278.391 704.63 278.471Z" fill="#9E9798"/>
<path d="M699.16 280.533L706.733 280.583L714.306 280.533L706.733 280.479L699.16 280.533Z" fill="#9E9798"/>
<path d="M708.175 282.016L716.205 282.069L724.234 282.016L716.205 281.962L708.175 282.016Z" fill="#9E9798"/>
<path d="M706.983 281.137L715.609 281.19L724.234 281.137L715.609 281.083L706.983 281.137Z" fill="#9E9798"/>
<path d="M706.983 279.47C712.734 279.568 718.484 279.571 724.234 279.47C718.484 279.369 712.734 279.369 706.983 279.47Z" fill="#9E9798"/>
<path d="M713.592 277.746L718.914 277.8L724.234 277.746L718.914 277.693L713.592 277.746Z" fill="#9E9798"/>
<path d="M704.224 282.526L711.14 282.579L718.055 282.526L711.14 282.476L704.224 282.526Z" fill="#9E9798"/>
<path d="M703.574 279.945C706.007 280.042 708.44 280.042 710.874 279.945C708.44 279.844 706.007 279.844 703.574 279.945Z" fill="#9E9798"/>
<path d="M698.975 282.903C696.588 282.903 695.862 281.212 695.862 280.533C695.862 278.727 697.318 277.259 699.116 277.259H698.266C696.469 277.259 695.012 278.727 695.012 280.533C695.012 282.342 696.469 283.811 698.266 283.811H724.234V282.903H698.975Z" fill="#BDB9B3"/>
<path d="M722.819 292.731C722.819 292.731 723.66 291.022 723.66 288.807C723.66 286.591 722.819 284.883 722.819 284.883H695.658C695.658 284.883 695.195 285.826 695.195 288.807C695.195 291.788 695.658 292.731 695.658 292.731H722.819Z" fill="#6BBE5E"/>
<path d="M701.196 290.723C702.255 290.723 703.109 289.863 703.109 288.807C703.109 287.749 702.255 286.892 701.196 286.892C700.138 286.892 699.279 287.749 699.279 288.807C699.279 289.863 700.138 290.723 701.196 290.723Z" fill="#89C65D"/>
<path d="M696.467 288.807C696.467 285.826 696.929 284.883 696.929 284.883H698.784C698.784 284.883 698.321 285.826 698.321 288.807C698.321 291.788 698.784 292.731 698.784 292.731H696.929C696.929 292.731 696.467 291.788 696.467 288.807Z" fill="#89C65D"/>
<path d="M720.771 288.807C720.771 285.826 720.306 284.883 720.306 284.883H718.452C718.452 284.883 718.917 285.826 718.917 288.807C718.917 291.788 718.452 292.731 718.452 292.731H720.306C720.306 292.731 720.771 291.788 720.771 288.807Z" fill="#89C65D"/>
<path d="M722.467 288.807C722.467 285.826 722.002 284.883 722.002 284.883H721.075C721.075 284.883 721.54 285.826 721.54 288.807C721.54 291.788 721.075 292.731 721.075 292.731H722.002C722.002 292.731 722.467 291.788 722.467 288.807Z" fill="#89C65D"/>
<path d="M729.151 300.576C729.151 300.576 729.992 298.868 729.992 296.652C729.992 294.44 729.151 292.731 729.151 292.731H689.325C689.325 292.731 688.863 293.671 688.863 296.652C688.863 299.63 689.325 300.576 689.325 300.576H729.151Z" fill="#35426B"/>
<path d="M727.102 296.652C727.102 293.671 726.638 292.731 726.638 292.731H724.784C724.784 292.731 725.247 293.671 725.247 296.652C725.247 299.63 724.784 300.576 724.784 300.576H726.638C726.638 300.576 727.102 299.63 727.102 296.652Z" fill="#435789"/>
<path d="M728.797 296.652C728.797 293.671 728.334 292.731 728.334 292.731H727.407C727.407 292.731 727.868 293.671 727.868 296.652C727.868 299.63 727.407 300.576 727.407 300.576H728.334C728.334 300.576 728.797 299.63 728.797 296.652Z" fill="#435789"/>
<path d="M727.355 308.416C727.355 308.416 728.198 306.704 728.198 304.492C728.198 302.279 727.355 300.567 727.355 300.567H691.122C691.122 300.567 690.657 301.511 690.657 304.492C690.657 307.472 691.122 308.416 691.122 308.416H727.355Z" fill="#22ADE4"/>
<path d="M747.164 387.625H687.342V323.008H747.164V387.625Z" fill="#F89D5F"/>
<path d="M777.086 308.326H747.163C743.109 308.326 739.822 311.61 739.822 315.664C739.822 319.722 743.109 323.008 747.163 323.008V387.625H784.428V315.664C784.428 311.61 781.141 308.326 777.086 308.326Z" fill="#EE7936"/>
<path d="M739.822 315.664C739.822 311.61 743.11 308.326 747.164 308.326H687.342C683.287 308.326 680 311.61 680 315.664C680 319.722 683.287 323.008 687.342 323.008H747.164C743.11 323.008 739.822 319.722 739.822 315.664Z" fill="#FBB363"/>
<path d="M744.068 344.619H689.846V326.95H744.068V344.619Z" fill="#FBB363"/>
<path d="M744.068 364.403H689.846V346.74H744.068V364.403Z" fill="#FBB363"/>
<path d="M744.068 383.681H689.846V366.019H744.068V383.681Z" fill="#FBB363"/>
<path d="M726.993 332.076C726.993 332.954 726.286 333.66 725.408 333.66H708.505C707.631 333.66 706.922 332.954 706.922 332.076C706.922 331.204 707.631 330.495 708.505 330.495H725.408C726.286 330.495 726.993 331.204 726.993 332.076Z" fill="#F89D5F"/>
<path d="M726.993 352.146C726.993 353.021 726.286 353.733 725.408 353.733H708.505C707.631 353.733 706.922 353.021 706.922 352.146C706.922 351.274 707.631 350.562 708.505 350.562H725.408C726.286 350.562 726.993 351.274 726.993 352.146Z" fill="#F89D5F"/>
<path d="M726.993 372.22C726.993 373.092 726.286 373.804 725.408 373.804H708.505C707.631 373.804 706.922 373.092 706.922 372.22C706.922 371.343 707.631 370.637 708.505 370.637H725.408C726.286 370.637 726.993 371.343 726.993 372.22Z" fill="#F89D5F"/>
<path d="M715.289 288.722H754.227C755.941 288.722 757.333 287.331 757.333 285.617C757.333 283.902 755.941 282.511 754.227 282.511H715.289C715.102 282.511 714.952 282.36 714.952 282.176C714.952 281.989 715.102 281.838 715.289 281.838H754.227C756.314 281.838 758.004 283.529 758.004 285.617C758.004 287.702 756.314 289.396 754.227 289.396H715.289C715.102 289.396 714.952 289.244 714.952 289.057C714.952 288.873 715.102 288.722 715.289 288.722Z" fill="#F68B41"/>
<path d="M715.457 282.511H753.413C755.127 282.511 756.518 283.902 756.518 285.616C756.518 287.331 755.127 288.722 753.413 288.722H715.457V282.511Z" fill="#D4D0CE"/>
<path d="M715.457 287.953H753.858C755.697 287.953 756.518 286.527 756.518 285.616C756.518 283.902 755.127 282.511 753.413 282.511H754.223C755.938 282.511 757.328 283.902 757.328 285.616C757.328 287.331 755.938 288.722 754.223 288.722H715.457V287.953Z" fill="#BDB9B3"/>
<path d="M752.393 283.723L740.581 283.664L728.77 283.723L740.581 283.78L752.393 283.723Z" fill="#9E9798"/>
<path d="M755.634 285.616L745.594 285.568L735.553 285.616L745.594 285.666L755.634 285.616Z" fill="#9E9798"/>
<path d="M749.427 287.286L732.442 287.238L715.457 287.286L732.442 287.334L749.427 287.286Z" fill="#9E9798"/>
<path d="M750.423 286.304L732.939 286.257L715.457 286.304L732.939 286.351L750.423 286.304Z" fill="#9E9798"/>
<path d="M750.423 284.556L732.939 284.482L715.457 284.556L732.939 284.631L750.423 284.556Z" fill="#9E9798"/>
<path d="M732.138 283.116L723.797 283.065L715.457 283.116L723.797 283.164L732.138 283.116Z" fill="#9E9798"/>
<path d="M752.732 288.164L734.651 288.116L716.569 288.164L734.651 288.214L752.732 288.164Z" fill="#9E9798"/>
<path d="M753.274 284.955C748.325 284.863 743.376 284.863 738.427 284.955C743.376 285.049 748.325 285.047 753.274 284.955Z" fill="#9E9798"/>
<path d="M747.353 263.496C747.353 263.496 748.006 264.825 748.006 266.548C748.006 268.271 747.353 269.6 747.353 269.6H726.219C726.219 269.6 725.86 268.867 725.86 266.548C725.86 264.229 726.219 263.496 726.219 263.496H747.353Z" fill="#6BBE5E"/>
<path d="M730.528 265.056C731.353 265.056 732.018 265.726 732.018 266.548C732.018 267.369 731.353 268.036 730.528 268.036C729.704 268.036 729.038 267.369 729.038 266.548C729.038 265.726 729.704 265.056 730.528 265.056Z" fill="#89C65D"/>
<path d="M726.849 266.548C726.849 268.867 727.21 269.6 727.21 269.6H728.653C728.653 269.6 728.292 268.867 728.292 266.548C728.292 264.229 728.653 263.496 728.653 263.496H727.21C727.21 263.496 726.849 264.229 726.849 266.548Z" fill="#89C65D"/>
<path d="M745.758 266.548C745.758 268.867 745.397 269.6 745.397 269.6H743.955C743.955 269.6 744.315 268.867 744.315 266.548C744.315 264.229 743.955 263.496 743.955 263.496H745.397C745.397 263.496 745.758 264.229 745.758 266.548Z" fill="#89C65D"/>
<path d="M747.075 266.548C747.075 268.867 746.716 269.6 746.716 269.6H745.993C745.993 269.6 746.354 268.867 746.354 266.548C746.354 264.229 745.993 263.496 745.993 263.496H746.716C746.716 263.496 747.075 264.229 747.075 266.548Z" fill="#89C65D"/>
<path d="M749.205 238C749.205 238 749.976 239.566 749.976 241.595C749.976 243.626 749.205 245.189 749.205 245.189H724.316C724.316 245.189 723.892 244.327 723.892 241.595C723.892 238.866 724.316 238 724.316 238H749.205Z" fill="#919598"/>
<path d="M727.321 238C727.321 238 727.201 238.246 727.084 238.886C726.436 239.275 725.969 240.34 725.969 241.595C725.969 242.846 726.436 243.911 727.084 244.302C727.201 244.943 727.321 245.189 727.321 245.189H729.019C729.019 245.189 728.835 244.816 728.709 243.784C729.068 243.256 729.298 242.473 729.298 241.595C729.298 240.717 729.068 239.931 728.709 239.406C728.835 238.37 729.019 238 729.019 238H727.321Z" fill="#AFB3B2"/>
<path d="M747.327 241.595C747.327 244.327 746.9 245.189 746.9 245.189H745.202C745.202 245.189 745.628 244.327 745.628 241.595C745.628 238.866 745.202 238 745.202 238H746.9C746.9 238 747.327 238.866 747.327 241.595Z" fill="#AFB3B2"/>
<path d="M748.881 241.595C748.881 244.327 748.458 245.189 748.458 245.189H747.606C747.606 245.189 748.032 244.327 748.032 241.595C748.032 238.866 747.606 238 747.606 238H748.458C748.458 238 748.881 238.866 748.881 241.595Z" fill="#AFB3B2"/>
<path d="M752.277 257.392C752.277 257.392 752.935 258.72 752.935 260.443C752.935 262.167 752.277 263.496 752.277 263.496H721.294C721.294 263.496 720.933 262.763 720.933 260.443C720.933 258.127 721.294 257.392 721.294 257.392H752.277Z" fill="#35426B"/>
<path d="M721.922 260.443C721.922 262.763 722.285 263.496 722.285 263.496H723.727C723.727 263.496 723.365 262.763 723.365 260.443C723.365 258.127 723.727 257.392 723.727 257.392H722.285C722.285 257.392 721.922 258.127 721.922 260.443Z" fill="#435789"/>
<path d="M750.685 260.443C750.685 262.763 750.323 263.496 750.323 263.496H748.88C748.88 263.496 749.241 262.763 749.241 260.443C749.241 258.127 748.88 257.392 748.88 257.392H750.323C750.323 257.392 750.685 258.127 750.685 260.443Z" fill="#435789"/>
<path d="M752.006 260.443C752.006 262.763 751.643 263.496 751.643 263.496H750.921C750.921 263.496 751.282 262.763 751.282 260.443C751.282 258.127 750.921 257.392 750.921 257.392H751.643C751.643 257.392 752.006 258.127 752.006 260.443Z" fill="#435789"/>
<path d="M747.353 245.189C747.353 245.189 748.006 246.518 748.006 248.242C748.006 249.964 747.353 251.294 747.353 251.294H726.219C726.219 251.294 725.86 250.558 725.86 248.242C725.86 245.922 726.219 245.189 726.219 245.189H747.353Z" fill="#F68B41"/>
<path d="M728.409 248.242C728.409 250.558 728.771 251.294 728.771 251.294H730.215C730.215 251.294 729.852 250.558 729.852 248.242C729.852 245.922 730.215 245.189 730.215 245.189H728.771C728.771 245.189 728.409 245.922 728.409 248.242Z" fill="#FAB683"/>
<path d="M733.907 248.242C733.907 250.558 734.269 251.294 734.269 251.294H741.047C741.047 251.294 741.294 250.558 741.294 248.242C741.294 245.922 741.047 245.189 741.047 245.189H734.269C734.269 245.189 733.907 245.922 733.907 248.242Z" fill="#FAB683"/>
<path d="M727.091 248.242C727.091 250.558 727.453 251.294 727.453 251.294H728.173C728.173 251.294 727.813 250.558 727.813 248.242C727.813 245.922 728.173 245.189 728.173 245.189H727.453C727.453 245.189 727.091 245.922 727.091 248.242Z" fill="#FAB683"/>
<path d="M750.882 251.294C750.882 251.294 751.537 252.623 751.537 254.346C751.537 256.072 750.882 257.398 750.882 257.398H722.692C722.692 257.398 722.33 256.666 722.33 254.346C722.33 252.026 722.692 251.294 722.692 251.294H750.882Z" fill="#22ADE4"/>
<path d="M723.318 254.346C723.318 256.666 723.679 257.398 723.679 257.398H725.122C725.122 257.398 724.761 256.666 724.761 254.346C724.761 252.026 725.122 251.294 725.122 251.294H723.679C723.679 251.294 723.318 252.026 723.318 254.346Z" fill="#4FC0E9"/>
<path d="M720.441 281.838C720.441 281.838 719.757 280.453 719.757 278.646C719.757 276.846 720.441 275.458 720.441 275.458H752.827C752.827 275.458 753.205 276.223 753.205 278.646C753.205 281.073 752.827 281.838 752.827 281.838H720.441Z" fill="#35426B"/>
<path d="M752.172 278.647C752.172 276.223 751.795 275.458 751.795 275.458H750.288C750.288 275.458 750.662 276.223 750.662 278.647C750.662 281.073 750.288 281.838 750.288 281.838H751.795C751.795 281.838 752.172 281.073 752.172 278.647Z" fill="#435789"/>
<path d="M722.107 278.647C722.107 276.223 722.485 275.458 722.485 275.458H723.993C723.993 275.458 723.615 276.223 723.615 278.647C723.615 281.073 723.993 281.838 723.993 281.838H722.485C722.485 281.838 722.107 281.073 722.107 278.647Z" fill="#435789"/>
<path d="M720.728 278.647C720.728 276.223 721.106 275.458 721.106 275.458H721.859C721.859 275.458 721.484 276.223 721.484 278.647C721.484 281.073 721.859 281.838 721.859 281.838H721.106C721.106 281.838 720.728 281.073 720.728 278.647Z" fill="#435789"/>
<path d="M723.735 275.458C723.735 275.458 723.108 274.185 723.108 272.53C723.108 270.872 723.735 269.6 723.735 269.6H750.794C750.794 269.6 751.141 270.303 751.141 272.53C751.141 274.751 750.794 275.458 750.794 275.458H723.735Z" fill="#22ADE4"/>
<path d="M750.191 272.53C750.191 270.303 749.845 269.6 749.845 269.6H748.461C748.461 269.6 748.807 270.303 748.807 272.53C748.807 274.751 748.461 275.458 748.461 275.458H749.845C749.845 275.458 750.191 274.751 750.191 272.53Z" fill="#4FC0E9"/>
<path d="M736.515 295.546H736.365V289.997H736.515C736.681 289.997 736.816 289.863 736.816 289.697C736.816 289.531 738.512 289.395 738.345 289.395H718.783C716.918 289.395 715.406 290.907 715.406 292.773C715.406 294.632 716.918 296.145 718.783 296.145H738.152C738.318 296.145 736.816 296.015 736.816 295.848C736.816 295.682 736.681 295.546 736.515 295.546Z" fill="#1085A6"/>
<path d="M754.823 295.546H737.09C735.56 295.546 734.315 294.303 734.315 292.773C734.315 291.236 735.56 289.997 737.09 289.997H754.823C754.988 289.997 755.124 289.863 755.124 289.697C755.124 289.531 754.988 289.395 754.823 289.395H737.09C735.226 289.395 733.714 290.907 733.714 292.773C733.714 294.632 735.226 296.145 737.09 296.145H754.823C754.988 296.145 755.124 296.015 755.124 295.848C755.124 295.682 754.988 295.546 754.823 295.546Z" fill="#23ADE0"/>
<path d="M754.671 289.997H737.819C736.287 289.997 735.045 291.237 735.045 292.773C735.045 294.307 736.287 295.549 737.819 295.549H754.671V289.997Z" fill="#D4D0CE"/>
<path d="M754.671 294.858H737.42C735.778 294.858 735.045 293.583 735.045 292.773C735.045 291.237 736.287 289.997 737.819 289.997H737.094C735.563 289.997 734.32 291.237 734.32 292.773C734.32 294.307 735.563 295.549 737.094 295.549H754.671V294.858Z" fill="#BDB9B3"/>
<path d="M738.73 291.079C743.174 291.171 747.615 291.174 752.059 291.079C747.615 290.984 743.174 290.984 738.73 291.079Z" fill="#9E9798"/>
<path d="M735.83 292.773C739.22 292.85 742.608 292.85 745.997 292.773C742.608 292.696 739.22 292.696 735.83 292.773Z" fill="#9E9798"/>
<path d="M741.382 294.265C745.811 294.342 750.242 294.342 754.671 294.265C750.242 294.188 745.811 294.188 741.382 294.265Z" fill="#9E9798"/>
<path d="M740.49 293.384C745.217 293.461 749.944 293.461 754.671 293.384C749.944 293.31 745.217 293.31 740.49 293.384Z" fill="#9E9798"/>
<path d="M740.49 291.827C745.217 291.943 749.944 291.943 754.671 291.827C749.944 291.711 745.217 291.711 740.49 291.827Z" fill="#9E9798"/>
<path d="M749.047 290.534C750.922 290.611 752.797 290.611 754.671 290.534C752.797 290.46 750.922 290.46 749.047 290.534Z" fill="#9E9798"/>
<path d="M738.427 295.051C743.51 295.125 748.593 295.125 753.676 295.051C748.593 294.974 743.51 294.974 738.427 295.051Z" fill="#9E9798"/>
<path d="M737.942 292.18C739.771 292.295 741.599 292.295 743.429 292.18C741.599 292.064 739.771 292.064 737.942 292.18Z" fill="#9E9798"/>
<path d="M740.785 301.41H740.623V297.219H740.785C741.082 297.219 741.319 296.976 741.319 296.682C741.319 296.389 741.082 296.146 740.785 296.146H713.199C711.584 296.291 710.311 297.661 710.311 299.313C710.311 300.965 711.584 302.338 713.199 302.478H740.785C741.082 302.478 741.319 302.24 741.319 301.944C741.319 301.648 741.082 301.41 740.785 301.41Z" fill="#1D7040"/>
<path d="M758.933 297.219H738.958C737.81 297.219 736.879 298.156 736.879 299.313C736.879 300.473 737.81 301.41 738.958 301.41H758.933V297.219Z" fill="#D4D0CE"/>
<path d="M759.095 301.41H738.409C737.262 301.398 736.334 300.461 736.334 299.313C736.334 298.165 737.262 297.231 738.409 297.219H759.095C759.387 297.219 759.628 296.976 759.628 296.682C759.628 296.389 759.387 296.146 759.095 296.146H738.153C736.537 296.291 735.265 297.661 735.265 299.313C735.265 300.965 736.537 302.338 738.153 302.478H759.095C759.387 302.478 759.628 302.24 759.628 301.944C759.628 301.648 759.387 301.41 759.095 301.41Z" fill="#2EB054"/>
<path d="M741.466 297.994C746.543 298.073 751.62 298.073 756.696 297.994C751.62 297.916 746.543 297.916 741.466 297.994Z" fill="#9E9798"/>
<path d="M738.988 299.313L744.369 299.367L749.749 299.313L744.369 299.26L738.988 299.313Z" fill="#9E9798"/>
<path d="M743.734 300.259L751.334 300.31L758.933 300.259L751.334 300.209L743.734 300.259Z" fill="#9E9798"/>
<path d="M742.97 299.699L750.951 299.749L758.933 299.699L750.951 299.646L742.97 299.699Z" fill="#9E9798"/>
<path d="M742.97 298.633C748.291 298.734 753.612 298.734 758.933 298.633C753.612 298.535 748.291 298.535 742.97 298.633Z" fill="#9E9798"/>
<path d="M741.206 300.589L749.643 300.639L758.081 300.589L749.643 300.535L741.206 300.589Z" fill="#9E9798"/>
<path d="M740.792 298.933C743.047 299.033 745.301 299.033 747.555 298.933C745.301 298.835 743.047 298.835 740.792 298.933Z" fill="#9E9798"/>
<path d="M738.87 300.828C737.342 300.828 736.879 299.749 736.879 299.313C736.879 298.156 737.81 297.219 738.958 297.219H738.417C737.265 297.219 736.334 298.156 736.334 299.313C736.334 300.473 737.265 301.41 738.417 301.41H758.933V300.828H738.87Z" fill="#BDB9B3"/>
<path d="M739.767 303.154C739.954 303.154 740.105 302.999 740.105 302.813C740.105 302.631 739.954 302.478 739.767 302.478H721.241C720.512 302.543 719.831 302.881 719.329 303.43C718.821 303.984 718.542 304.699 718.542 305.447C718.542 306.194 718.821 306.909 719.329 307.46C719.831 308.009 720.512 308.35 721.241 308.416H739.767C739.954 308.416 740.105 308.261 740.105 308.077C740.105 307.891 739.954 307.736 739.767 307.736H739.705V303.154H739.767Z" fill="#4D5B8D"/>
<path d="M754.085 303.151H740.403C739.142 303.151 738.123 304.178 738.123 305.447C738.123 306.714 739.142 307.743 740.403 307.743H754.085V303.151Z" fill="#D4D0CE"/>
<path d="M754.146 307.736H739.796C738.545 307.725 737.529 306.695 737.529 305.447C737.529 304.195 738.545 303.169 739.796 303.154H754.146C754.333 303.154 754.484 302.999 754.484 302.813C754.484 302.631 754.333 302.478 754.146 302.478H739.553C738.82 302.543 738.141 302.881 737.638 303.43C737.132 303.984 736.853 304.699 736.853 305.447C736.853 306.194 737.132 306.909 737.638 307.46C738.141 308.009 738.82 308.35 739.553 308.416H754.146C754.333 308.416 754.484 308.261 754.484 308.077C754.484 307.891 754.333 307.736 754.146 307.736Z" fill="#5F74B7"/>
<path d="M744.27 304.002C745.995 304.089 747.72 304.091 749.444 304.002C747.72 303.913 745.995 303.913 744.27 304.002Z" fill="#9E9798"/>
<path d="M740.435 305.447C742.665 305.518 744.895 305.518 747.125 305.447C744.895 305.373 742.665 305.376 740.435 305.447Z" fill="#9E9798"/>
<path d="M746.755 306.482C749.198 306.556 751.642 306.556 754.085 306.482C751.642 306.411 749.198 306.411 746.755 306.482Z" fill="#9E9798"/>
<path d="M745.919 305.868C748.641 305.942 751.363 305.942 754.085 305.868C751.363 305.797 748.641 305.797 745.919 305.868Z" fill="#9E9798"/>
<path d="M745.919 304.703C748.641 304.809 751.363 304.809 754.085 304.703C751.363 304.593 748.641 304.593 745.919 304.703Z" fill="#9E9798"/>
<path d="M746.623 303.495C749.109 303.566 751.598 303.566 754.085 303.495C751.598 303.421 749.109 303.421 746.623 303.495Z" fill="#9E9798"/>
<path d="M743.985 306.84C745.906 306.912 747.828 306.912 749.749 306.84C747.828 306.769 745.906 306.769 743.985 306.84Z" fill="#9E9798"/>
<path d="M743.529 305.031C745.236 305.141 746.942 305.141 748.648 305.031C746.942 304.924 745.236 304.924 743.529 305.031Z" fill="#9E9798"/>
<path d="M740.305 307.108C738.632 307.108 738.123 305.922 738.123 305.447C738.123 304.178 739.142 303.151 740.403 303.151H739.809C738.547 303.151 737.528 304.178 737.528 305.447C737.528 306.714 738.547 307.743 739.809 307.743H754.085V307.108H740.305Z" fill="#BDB9B3"/>
<path d="M829.979 342.845L831.612 366.896L842.694 366.418L842.309 342.064L829.979 342.845Z" fill="#F9AA89"/>
<path d="M830.788 364.224L810.591 373.435C809.268 374.098 808.572 375.583 808.91 377.024H844.536L843.212 364.076L830.788 364.224Z" fill="#040606"/>
<path d="M845.164 380.856H808.455V377.024H845.164V380.856Z" fill="white"/>
<path d="M824.566 366.53L826.757 368.392" stroke="white" stroke-width="1.3642" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M821.628 367.943L823.835 369.819" stroke="white" stroke-width="1.3642" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M818.679 369.423L821.011 371.411" stroke="white" stroke-width="1.3642" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M866.062 342.845L867.696 366.896L878.778 366.418L878.394 342.064L866.062 342.845Z" fill="#F9AA89"/>
<path d="M866.871 364.224L846.673 373.435C845.35 374.098 844.655 375.583 844.993 377.024H880.619L879.295 364.076L866.871 364.224Z" fill="#040606"/>
<path d="M881.25 380.856H844.539V377.024H881.25V380.856Z" fill="white"/>
<path d="M860.652 366.53L862.842 368.392" stroke="white" stroke-width="1.3642" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M857.713 367.943L859.92 369.819" stroke="white" stroke-width="1.3642" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M854.764 369.423L857.096 371.411" stroke="white" stroke-width="1.3642" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M836.379 229.902L878.894 233.142L882.425 352.582H861.245L853.701 262.494L843.591 300.99L847.034 354.04L827.199 354.096L820.355 295.44L836.379 229.902Z" fill="#BFAA98"/>
<path d="M844.191 257.303L853.701 262.494" stroke="#A08573" stroke-miterlimit="10"/>
<path d="M836.929 193.462L837.203 205.186L830.549 205.271L831.039 192.653L836.929 193.462Z" fill="#F79390"/>
<path d="M836.519 173.567C836.519 173.567 827.621 179.418 828.553 194.257L837.205 195.231L836.519 173.567Z" fill="#707EC7"/>
<path d="M857.962 166.964C868.663 166.964 880.792 170.663 880.792 170.663L880.331 238.73L835.131 235.258L835.61 175.725C835.619 174.672 836.199 173.705 837.124 173.204L849.626 167.856C849.626 167.856 855.778 166.964 857.962 166.964Z" fill="#707EC7"/>
<path d="M835.447 195.033V180.692" stroke="#586DBE" stroke-width="1.01863" stroke-miterlimit="10"/>
<path d="M875.438 193.6L878.344 227.267C878.344 227.267 881.555 234.039 887.235 226.996C892.913 219.954 888.052 192.442 888.052 192.442L875.438 193.6Z" fill="#F9AA89"/>
<path d="M872.679 196.926C872.679 196.926 870.254 172.071 878.12 170.611C886.276 169.098 891.014 184.472 891.77 195.49L872.679 196.926Z" fill="#707EC7"/>
<path d="M875.704 196.698L872.679 196.926C872.679 196.926 871.792 188.42 872.327 182.507" stroke="#586DBE" stroke-width="1.01863" stroke-miterlimit="10"/>
<path d="M856.132 195.744C856.132 195.744 854.494 189.808 848.552 189.229C842.61 188.651 840.864 193.314 841.982 196.386C843.101 199.457 846.966 204.459 852.822 201.901C858.678 199.344 856.132 195.744 856.132 195.744Z" fill="#F9AA89"/>
<path d="M846.582 189.236C846.582 189.236 840.748 189.906 836.404 192.022C835.963 192.236 835.722 192.722 835.786 193.21C835.872 193.866 836.494 194.316 837.146 194.195L845.199 192.69L846.582 189.236Z" fill="#F9AA89"/>
<path d="M879.602 228.983L852.822 201.901L856.132 195.743L882.178 212.293L879.602 228.983Z" fill="#F9AA89"/>
<path d="M876.754 208.845L882.179 212.293" stroke="#EF9676" stroke-width="1.01863" stroke-miterlimit="10"/>
<path d="M819.562 202.558L830.826 235.99C831.213 237.139 832.359 237.855 833.562 237.697L860.937 234.101C862.531 233.893 863.531 232.272 863.003 230.752L851.41 197.362C851.015 196.225 849.875 195.521 848.681 195.677L821.638 199.229C820.051 199.437 819.051 201.042 819.562 202.558Z" fill="#0B0C0D"/>
<path d="M820.043 200.08L818.611 201.937L861.261 234.866L862.79 232.873L820.043 200.08Z" fill="#0B0C0D"/>
<path d="M818.272 204.218L829.536 237.65C829.923 238.801 831.07 239.516 832.272 239.358L859.647 235.762C861.242 235.553 862.242 233.932 861.715 232.412L850.12 199.024C849.726 197.885 848.586 197.181 847.391 197.338L820.348 200.89C818.763 201.098 817.763 202.702 818.272 204.218Z" fill="#34474F"/>
<path d="M834.781 215.031C834.793 216.659 836.123 217.97 837.751 217.958C839.379 217.947 840.688 216.618 840.677 214.99C840.665 213.362 839.336 212.051 837.709 212.063C836.081 212.074 834.771 213.403 834.781 215.031Z" fill="#739095"/>
<path d="M819.549 213.934L822.113 220.851C822.427 221.695 823.28 222.21 824.172 222.093C826.8 221.747 828.483 219.119 827.696 216.589L826.975 214.269C826.397 212.41 824.637 211.177 822.693 211.27L821.267 211.338C819.963 211.399 819.096 212.71 819.549 213.934Z" fill="#F9AA89"/>
<path d="M847.715 123.954C847.715 123.954 873.2 116.581 863.908 142.822L859.782 133.644L847.715 123.954Z" fill="#3B161B"/>
<path d="M837.136 133.969C837.136 133.969 830.866 136.801 837.867 145.559L840.104 133.544L837.136 133.969Z" fill="#3B161B"/>
<path d="M843.492 147.162C843.935 149.465 842.487 151.688 840.258 152.126C838.028 152.565 835.862 151.053 835.419 148.75C834.978 146.446 836.426 144.224 838.655 143.786C840.883 143.348 843.05 144.858 843.492 147.162Z" fill="#EF9676"/>
<path d="M848.091 156.843L849.451 167.814C849.922 171.667 852.471 173.438 856.14 172.946C859.272 172.525 862.527 170.578 861.968 167.198L860.351 149.973L848.091 156.843Z" fill="#F9AA89"/>
<path d="M849.24 166.322C849.24 166.322 861.6 161.837 860.56 150.765C860.251 147.466 847.931 155.721 847.931 155.721L849.24 166.322Z" fill="#EF9676"/>
<path d="M851.778 161.052C844.972 162.258 840.41 156.802 840.104 154.02L837.183 141.112C836.134 134.519 840.335 128.296 846.68 127.048C853.175 125.771 860.624 129.951 861.914 136.662L863.128 145.26C864.231 153 859.21 159.591 851.778 161.052Z" fill="#F9AA89"/>
<path d="M845.141 150.133L845.175 152.647L846.701 152.519" stroke="#14191C" stroke-width="0.704101" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M850.789 142.871C850.789 142.871 848.247 142.969 848.353 144.03C848.353 144.03 848.442 144.744 850.655 144.616C852.867 144.488 853.418 144.253 853.537 143.554C853.654 142.858 851.97 142.733 850.789 142.871Z" fill="#14191C"/>
<path d="M840.667 144.165C840.667 144.165 842.716 143.688 843.008 144.66C843.008 144.66 843.189 145.321 841.389 145.697C839.591 146.072 838.969 145.906 838.731 145.385C838.46 144.793 839.681 144.302 840.667 144.165Z" fill="#14191C"/>
<path d="M842.783 149.03C842.878 149.63 842.482 150.19 841.9 150.281C841.32 150.373 840.774 149.961 840.68 149.361C840.588 148.762 840.983 148.201 841.563 148.11C842.144 148.02 842.69 148.43 842.783 149.03Z" fill="#14191C"/>
<path d="M851.997 147.574C852.09 148.172 851.696 148.732 851.115 148.824C850.535 148.915 849.988 148.504 849.894 147.904C849.801 147.304 850.197 146.744 850.777 146.652C851.357 146.562 851.904 146.972 851.997 147.574Z" fill="#14191C"/>
<path d="M845.129 154.561L851.629 153.842C851.629 153.842 851.436 156.125 848.04 156.126C845.834 156.127 845.129 154.561 845.129 154.561Z" fill="white"/>
<path d="M864.458 133.134L863.908 142.822L862.032 144.918C860.584 144.423 858.712 144.454 857.512 142.822C856.625 141.617 855.744 139.365 855.713 137.869L855.669 135.782L850.564 139.551C849.764 137.683 848.858 135.199 848.858 135.199C848.858 135.199 847.641 135.285 845.982 139.333C845.982 139.333 832.816 143.313 832.822 135.285C832.829 126.811 847.714 123.954 847.714 123.954L860.525 128.326L864.458 133.134Z" fill="#3B161B"/>
<path d="M868.86 145.277C869.337 147.763 867.773 150.16 865.369 150.633C862.964 151.106 860.627 149.474 860.149 146.989C859.672 144.505 861.235 142.106 863.64 141.633C866.047 141.16 868.383 142.791 868.86 145.277Z" fill="#F9AA89"/>
<path d="M863.24 147.771C863.24 147.771 862.612 144.508 865.731 144.428" stroke="#14191C" stroke-width="0.718219" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M846.699 169.106L852.033 166.626L861.438 166.895L866.954 167.666C866.954 167.666 869.01 175.929 855.059 176.389C843.907 176.757 846.699 169.106 846.699 169.106Z" fill="#F9AA89"/>
<path d="M764.24 165.06H808.583C809.82 165.06 810.823 164.057 810.823 162.82V148.046C810.823 146.81 809.82 145.808 808.583 145.808H764.24C763.003 145.808 762 146.81 762 148.046V162.82C762 164.057 763.003 165.06 764.24 165.06Z" fill="white"/>
<path d="M802.229 153.185H769.784" stroke="#B4A19A" stroke-width="1.43531" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M781.002 158.301H769.893" stroke="#B4A19A" stroke-width="1.43531" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M803.962 162.497V171.205L792.864 162.497H803.962Z" fill="white"/>
</svg>

After

Width:  |  Height:  |  Size: 91 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 51 KiB

View File

@ -0,0 +1,45 @@
<svg width="611" height="521" viewBox="0 0 611 521" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M417.706 482.151C400.468 384.075 372.095 381.337 372.095 381.337L278.435 377.276C240.03 425.344 233.393 521 233.393 521H321.991H423.828L417.706 482.151Z" fill="#BFAA98"/>
<path d="M385.357 81.3175C385.357 81.3175 383.33 113.066 392.797 129.925C402.268 146.774 409.464 153.721 411.989 172.027C411.989 172.027 332.577 195.717 253.049 169.353L284.295 81.3175H385.357Z" fill="#3B161B"/>
<path d="M284.445 44.9603C284.445 44.9603 358.851 24.8054 379.892 62.1114C395.156 89.1843 377.118 138.199 342.256 152.011C309.046 165.167 318.469 56.9517 318.469 56.9517L284.445 44.9603Z" fill="#3B161B"/>
<path d="M291.535 112.257C292.282 121.187 285.651 129.044 276.717 129.796C267.782 130.553 259.93 123.917 259.177 114.983C258.425 106.048 265.056 98.1956 273.991 97.4387C282.925 96.6865 290.782 103.322 291.535 112.257Z" fill="#EF9676"/>
<path d="M298.826 157.621L301.586 192.895C302.529 205.284 310.669 211.33 322.857 210.3C333.262 209.424 342.581 203.229 343.002 192.804L335.988 137.499L298.826 157.621Z" fill="#F9AA89"/>
<path d="M300.766 183.103L341.483 146.027L298.466 154.013L300.766 183.103Z" fill="#EF9676"/>
<path d="M309.653 163.169C288.794 163.538 271.327 147.359 270.455 130.342L268.639 90.1568C267.547 68.8233 283.577 50.4649 304.867 48.6684C326.66 46.8335 349.642 62.6911 351.477 84.4844L352.583 116.813C353.441 141.821 334.584 161.07 309.653 163.169Z" fill="#F9AA89"/>
<path d="M328.462 65.9584C320.916 84.1539 343.84 112.046 343.84 112.046L371.44 78.8696C371.44 78.8696 333.799 53.0807 328.462 65.9584Z" fill="#3B161B"/>
<path d="M371.991 111.931C372.743 120.866 366.113 128.718 357.173 129.47C348.243 130.222 340.386 123.587 339.634 114.657C338.882 105.722 345.512 97.8652 354.452 97.1131C363.382 96.3609 371.239 102.996 371.991 111.931Z" fill="#F9AA89"/>
<path d="M350.567 118.581C350.567 118.581 349.575 106.848 360.948 107.753" stroke="#14191C" stroke-width="0.718219" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M291.812 119.577L291.079 126.811L296.517 127.031" stroke="#14191C" stroke-width="0.718219" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M316.662 92.5234C316.662 92.5234 307.65 91.7377 307.55 95.5272C307.55 95.5272 307.554 98.0903 315.416 98.6221C323.278 99.149 325.324 98.5598 326.047 96.15C326.775 93.7403 320.892 92.5569 316.662 92.5234Z" fill="#14191C"/>
<path d="M278.983 93.5199C278.983 93.5199 286.423 92.7438 287.022 96.3033C287.022 96.3033 287.372 98.7131 280.856 99.24C274.341 99.7718 272.223 98.9095 271.615 96.9644C270.92 94.7606 275.442 93.5678 278.983 93.5199Z" fill="#14191C"/>
<path d="M284.295 111.615C284.358 113.775 282.714 115.577 280.626 115.639C278.537 115.706 276.793 114.01 276.726 111.854C276.664 109.698 278.307 107.897 280.396 107.83C282.484 107.768 284.228 109.459 284.295 111.615Z" fill="#14191C"/>
<path d="M317.444 110.561C317.506 112.717 315.863 114.518 313.774 114.585C311.685 114.647 309.946 112.951 309.879 110.8C309.817 108.635 311.455 106.833 313.549 106.771C315.633 106.704 317.382 108.405 317.444 110.561Z" fill="#14191C"/>
<path d="M287.027 134.529H314.459C314.459 134.529 310.123 143.09 298.827 143.047C288.531 143.009 287.027 134.529 287.027 134.529Z" fill="white"/>
<path d="M333.062 65.9584C333.062 65.9584 316.658 93.9894 264.036 84.1539C264.036 84.1539 251.244 55.4426 284.445 44.9603C317.64 34.4828 355.813 52.1897 355.813 52.1897V75.794L333.062 65.9584Z" fill="#3B161B"/>
<path d="M288.757 198.165C288.757 198.165 241.706 209.323 233.404 271.541L263.586 297.373L288.757 198.165Z" fill="#707EC7"/>
<path d="M214.25 374.39C215.098 372.996 214.552 384.47 215.069 382.918C215.069 382.918 229.083 359.098 249.808 309.211C255.106 296.449 247.963 257.403 234.189 256.316C224.071 255.521 212.066 274.377 209.656 284.232L184.538 347.404L214.25 374.39Z" fill="#F9AA89"/>
<path d="M206.517 352.932L108.607 300.137L99.5906 310.097L178.696 388.557C190.185 400.083 209.707 396.193 215.897 381.14C220.185 370.711 216.194 358.715 206.517 352.932Z" fill="#F9AA89"/>
<path d="M71.9428 296.061C65.365 304.761 68.7665 318.424 79.5506 326.588C90.3347 334.746 104.41 334.311 110.993 325.61C117.57 316.92 114.169 303.252 103.385 295.093C92.6007 286.929 78.5254 287.37 71.9428 296.061Z" fill="#F9AA89"/>
<path d="M385.502 388.576C381.526 388.653 265.536 387.234 265.536 387.234L274.169 215.915L359.929 230.518L385.502 388.576Z" fill="white"/>
<path d="M359.928 196.393L325.515 190.361L300.105 194.946L280.453 234.858C280.453 234.858 274.575 253.13 305.892 256.029C337.214 258.927 358.965 236.89 364.182 223.26C369.404 209.63 359.928 196.393 359.928 196.393Z" fill="#F9AA89"/>
<path d="M300.106 194.946C300.106 194.946 274.351 249.192 280.732 305.221C287.113 361.24 255.293 420.435 255.293 420.435V265.859C255.293 265.859 255.633 201.347 300.106 194.946Z" fill="#707EC7"/>
<path d="M258.517 241.704C258.517 241.704 248.011 267.493 255.293 310.836" stroke="#5168BB" stroke-width="1.01863" stroke-miterlimit="10"/>
<path d="M359.928 196.393C359.928 196.393 281.479 293.306 403.227 427.937L390.369 204.446L359.928 196.393Z" fill="#707EC7"/>
<path d="M390.168 204.374C390.168 204.374 448.041 216.605 450.887 333.295L381.626 326.755L372.14 231.864L390.168 204.374Z" fill="#707EC7"/>
<path d="M383.495 355.227C383.495 355.227 368.399 340.442 381.626 326.755C381.626 326.755 430.962 319.08 459.707 337.137C459.707 337.137 471.741 357.665 456.363 368.794C456.363 368.794 435.638 355.227 383.495 355.227Z" fill="#8F9ED8"/>
<path d="M381.627 326.755L370.167 256.048" stroke="#5168BB" stroke-width="1.01863" stroke-miterlimit="10"/>
<path d="M383.494 355.227L275.835 368.795L281.819 389.965L427.34 393.558C441.913 393.918 454.427 383.249 456.362 368.795C456.362 368.795 424.13 345.626 383.494 355.227Z" fill="#F9AA89"/>
<path d="M233.423 379.775C233.983 393.213 247.944 403.542 264.601 402.848C281.264 402.158 294.314 390.698 293.753 377.265C293.193 363.822 279.232 353.493 262.575 354.187C245.912 354.882 232.862 366.337 233.423 379.775Z" fill="#F9AA89"/>
<path d="M380.591 367.252H265.659V354.283H380.591C384.169 354.283 387.072 357.186 387.072 360.765C387.072 364.344 384.169 367.252 380.591 367.252Z" fill="#111719"/>
<path d="M280.788 367.252H115.783C107.011 367.252 99.3126 361.402 96.9603 352.951L67.2621 246.265C64.6368 236.832 71.732 227.494 81.5244 227.494H234.111C239.966 227.494 245.082 231.442 246.572 237.105L280.788 367.252Z" fill="#1F2A30"/>
<path d="M181.706 303.343C181.706 311.3 175.257 317.753 167.3 317.753C159.342 317.753 152.894 311.3 152.894 303.343C152.894 295.39 159.342 288.937 167.3 288.937C175.257 288.937 181.706 295.39 181.706 303.343Z" fill="white"/>
<path d="M91.4662 145.184H17.8076C7.9721 145.184 0.000239619 137.212 0.000239619 127.376C0.000239619 117.546 7.9721 109.579 17.8076 109.579H91.4662C101.302 109.579 109.274 117.546 109.274 127.376C109.274 137.212 101.302 145.184 91.4662 145.184Z" fill="white"/>
<path d="M39.006 127.429C39.0156 130.055 36.8933 132.186 34.2679 132.191C31.6425 132.201 29.5106 130.083 29.501 127.458C29.4914 124.833 31.6138 122.701 34.2391 122.691C36.8645 122.681 38.9964 124.804 39.006 127.429Z" fill="#8D8D8D"/>
<path d="M59.3878 127.367C59.3974 129.987 57.2751 132.124 54.6497 132.134C52.0292 132.143 49.8925 130.016 49.8877 127.391C49.8781 124.77 52.0004 122.634 54.621 122.629C57.2464 122.619 59.3831 124.742 59.3878 127.367Z" fill="#8D8D8D"/>
<path d="M79.7707 127.3C79.7802 129.925 77.6579 132.057 75.0325 132.067C72.4072 132.076 70.2753 129.959 70.2657 127.333C70.2561 124.708 72.3785 122.576 75.0038 122.567C77.6244 122.557 79.7611 124.675 79.7707 127.3Z" fill="#8D8D8D"/>
<path d="M598.74 82.6414H450.133C443.542 82.6414 438.2 77.2368 438.2 70.5712V12.0738C438.2 5.40828 443.542 3.7767e-05 450.133 3.7767e-05H598.74C605.331 3.7767e-05 610.669 5.40828 610.669 12.0738V70.5712C610.669 77.2368 605.331 82.6414 598.74 82.6414Z" fill="#7383CA"/>
<path d="M459.759 71.8621V93.4804C459.759 96.6205 463.83 98.1955 466.214 95.9747L492.097 71.8621H459.759Z" fill="#7383CA"/>
<path d="M466.945 21.5587H581.924" stroke="white" stroke-width="1.36499" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M466.945 39.5242H506.469" stroke="white" stroke-width="1.36499" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M466.945 61.0828H549.586" stroke="white" stroke-width="1.36499" stroke-miterlimit="10" stroke-linecap="round" stroke-linejoin="round"/>
</svg>

After

Width:  |  Height:  |  Size: 8.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 542 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 378 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 152 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 85 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 143 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 137 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 238 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 80 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 168 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 132 KiB

View File

@ -0,0 +1 @@
<svg width="621" height="534" viewBox="0 0 621 534" fill="none" xmlns="http://www.w3.org/2000/svg"><path d="M83.345 135.773c1.65.161 3.41.338 5.271.534 13.266 1.403 31.642 3.728 52.066 7.408 41.444 7.469 89.062 20.148 120.238 40.609 7.176 4.709 16.183 11.603 23.623 17.524 3.67 2.92 6.867 5.53 9.145 7.409 1.137.938 2.042 1.693 2.659 2.208l.701.588.175.146.041.035.009.007 9.381 7.923 9.619-7.63.001-.001.01-.007.046-.037.194-.153.775-.61a729 729 0 0 1 13.025-9.962c8.195-6.122 18.138-13.262 26.052-18.119 31.497-19.335 78.593-31.802 119.244-39.383 20.057-3.74 38.053-6.205 51.029-7.734a735 735 0 0 1 4.574-.524l-.001 238.627a500 500 0 0 0-6.636-.007c-13.727.081-32.753.75-53.959 3.112-41.695 4.645-94.713 16.115-131.392 45.065-10.617 8.38-21.807 20.668-29.965 30.272q-.937 1.104-1.83 2.171-.563-.731-1.143-1.48c-7.41-9.534-17.541-21.757-27.134-30.357-33.76-30.266-88.312-41.668-131.296-46.127-22.015-2.284-42.05-2.837-56.571-2.823-2.87.003-5.53.029-7.951.067z" stroke="#fff" stroke-width="30"/><path d="M307.203 64.55c4.463 0 10.383 3.198 15.744 12.443 5.212 8.99 8.756 22.069 8.756 37.057s-3.544 28.068-8.756 37.057c-5.361 9.245-11.281 12.443-15.744 12.443-4.464 0-10.384-3.198-15.745-12.443-5.212-8.989-8.755-22.069-8.755-37.057s3.543-28.068 8.755-37.057c5.361-9.245 11.281-12.443 15.745-12.443Z" stroke="#fff" stroke-width="20"/><path d="M291.703 276.55c0 8.284 6.715 15 15 15s15-6.716 15-15zm15-60h-15v60h30v-60z" fill="#fff"/></svg>

After

Width:  |  Height:  |  Size: 1.4 KiB

File diff suppressed because one or more lines are too long

After

Width:  |  Height:  |  Size: 7.7 KiB

20
public/index.php Normal file
View File

@ -0,0 +1,20 @@
<?php
use Illuminate\Foundation\Application;
use Illuminate\Http\Request;
define('LARAVEL_START', microtime(true));
// Determine if the application is in maintenance mode...
if (file_exists($maintenance = __DIR__.'/../storage/framework/maintenance.php')) {
require $maintenance;
}
// Register the Composer autoloader...
require __DIR__.'/../vendor/autoload.php';
// Bootstrap Laravel and handle the request...
/** @var Application $app */
$app = require_once __DIR__.'/../bootstrap/app.php';
$app->handleRequest(Request::capture());

View File

@ -0,0 +1,83 @@
// public/js/dashboard-charts.js
document.addEventListener('DOMContentLoaded', function () {
// Ambil elemen canvas Bar Chart
const barChartEl = document.getElementById('barChart');
if (barChartEl) {
const statistikData = JSON.parse(barChartEl.dataset.stats);
new Chart(barChartEl.getContext('2d'), {
type: 'bar',
data: {
labels: statistikData.labels,
datasets: [{
label: 'Buku Dibaca',
backgroundColor: '#0C5495',
data: statistikData.data,
borderRadius: 8
}]
},
options: {
responsive: true,
maintainAspectRatio: false,
scales: {
y: {
beginAtZero: true,
grid: {
color: 'rgba(0,0,0,0.05)',
},
ticks: {
color: '#6c757d',
font: {
size: 12
}
}
},
x: {
grid: {
display: false,
},
ticks: {
color: '#6c757d',
font: {
size: 12
}
}
}
},
plugins: {
legend: {
display: false
}
}
}
});
}
const donutChartEl = document.getElementById('donutChart');
if (donutChartEl) {
const progressData = JSON.parse(donutChartEl.dataset.progress);
new Chart(donutChartEl.getContext('2d'), {
type: 'doughnut',
data: {
labels: ['Telah Dibaca', 'Belum Dibaca'],
datasets: [{
data: [progressData.selesai, progressData.sisa],
backgroundColor: ['#0C5495', '#fbb716'],
borderColor: ['#ffffff'],
borderWidth: 3,
}]
},
options: {
responsive: true,
maintainAspectRatio: false,
plugins: {
legend: {
display: false
}
},
cutout: '75%'
}
});
}
});

2
public/robots.txt Normal file
View File

@ -0,0 +1,2 @@
User-agent: *
Disallow:

11
resources/js/app.js Normal file
View File

@ -0,0 +1,11 @@
import './bootstrap';
import './peminjaman-form.js';
import * as bootstrap from 'bootstrap';
window.bootstrap = bootstrap;
import Alpine from 'alpinejs';
window.Alpine = Alpine;
document.addEventListener('DOMContentLoaded', () => {
Alpine.start();
});

4
resources/js/bootstrap.js vendored Normal file
View File

@ -0,0 +1,4 @@
import axios from 'axios';
window.axios = axios;
window.axios.defaults.headers.common['X-Requested-With'] = 'XMLHttpRequest';

View File

@ -0,0 +1,188 @@
const formPeminjamanElement = document.getElementById('formPeminjaman');
if (formPeminjamanElement) {
// Ambil data yang sudah disimpan di elemen HTML
const semuaBuku = JSON.parse(formPeminjamanElement.dataset.semuaBuku);
const bukuAwal = JSON.parse(formPeminjamanElement.dataset.bukuAwal);
let bukuTerpilih = [bukuAwal.id];
const maxBuku = 2;
document.addEventListener('DOMContentLoaded', function () {
updateCounter();
updateSelectedBooks();
updateCheckboxes();
updateBtnTambahBuku();
updateDaftarBuku();
});
function updateCounter() {
document.getElementById('counterBuku').textContent = bukuTerpilih.length;
document.getElementById('sisaSlot').textContent = maxBuku - bukuTerpilih.length;
}
function updateBtnTambahBuku() {
const btnTambah = document.getElementById('btnTambahBuku');
if (bukuTerpilih.length >= maxBuku) {
btnTambah.classList.add('disabled');
btnTambah.innerHTML = '<i class="bi bi-check-circle me-1"></i>Maksimal Buku Tercapai';
} else {
btnTambah.classList.remove('disabled');
btnTambah.innerHTML = '<i class="bi bi-plus-circle me-1"></i>Tambah Buku';
}
}
function updateSelectedBooks() {
const container = document.getElementById('selectedBooks');
const selected = semuaBuku.filter(book => bukuTerpilih.includes(book.id));
container.innerHTML = selected.map(book => `<li>${book.judul}</li>`).join('');
}
function updateCheckboxes() {
document.querySelectorAll('.book-checkbox').forEach(checkbox => {
const bookId = parseInt(checkbox.value);
checkbox.checked = bukuTerpilih.includes(bookId);
if (bukuTerpilih.length >= maxBuku && !bukuTerpilih.includes(bookId)) {
checkbox.disabled = true;
} else if (bookId !== bukuAwal.id) {
checkbox.disabled = false;
}
});
}
window.toggleBookSelection = function (bookId) {
if (bookId === bukuAwal.id) return;
const checkbox = document.getElementById('book' + bookId);
if (!checkbox.disabled) {
checkbox.checked = !checkbox.checked;
handleCheckboxChange(checkbox);
}
}
function handleCheckboxChange(checkbox) {
const bookId = parseInt(checkbox.value);
if (checkbox.checked) {
if (bukuTerpilih.length < maxBuku && !bukuTerpilih.includes(bookId)) {
bukuTerpilih.push(bookId);
} else {
checkbox.checked = false;
return;
}
} else {
bukuTerpilih = bukuTerpilih.filter(id => id !== bookId);
}
updateCounter();
updateSelectedBooks();
updateCheckboxes();
updateBtnTambahBuku();
}
document.addEventListener('change', function (e) {
if (e.target.classList.contains('book-checkbox')) {
if (e.target.value != bukuAwal.id) {
handleCheckboxChange(e.target);
}
}
});
document.getElementById('searchBuku')?.addEventListener('input', function (e) {
const searchTerm = e.target.value.toLowerCase();
document.querySelectorAll('.book-option').forEach(option => {
const title = option.getAttribute('data-book-title');
const author = option.getAttribute('data-book-author');
if (title.includes(searchTerm) || author.includes(searchTerm)) {
option.style.display = 'block';
} else {
option.style.display = 'none';
}
});
});
function updateDaftarBuku() {
const container = document.getElementById('daftarBukuPinjam');
const hiddenInputs = document.getElementById('hiddenInputs');
const selected = semuaBuku.filter(book => bukuTerpilih.includes(book.id));
container.innerHTML = selected.map((book) => `
<div class="book-item border rounded p-3 mb-3 shadow-sm" data-book-id="${book.id}">
<div class="d-flex align-items-start">
<img src="/${book.cover}" alt="Cover"
class="rounded me-3 form-book-cover"
style="width: 60px; height: 80px; object-fit: cover;">
<div class="flex-grow-1">
<h6 class="fw-bold mb-1">${book.judul}</h6>
<p class="text-muted small mb-1">${book.penulis}</p>
<span class="badge bg-info">${book.kategori}</span>
</div>
<div class="d-flex flex-column align-items-end gap-2">
${book.id === bukuAwal.id
? '<span class="badge bg-success">Buku Utama</span>'
: '<span class="badge bg-primary">Tambahan</span>'}
${book.id !== bukuAwal.id
? `<button type="button" class="btn btn-sm btn-outline-danger remove-book"
onclick="removeBuku(${book.id})"
title="Hapus Buku">
<i class="bi bi-trash"></i>
</button>`
: ''}
</div>
</div>
</div>
`).join('');
hiddenInputs.innerHTML = bukuTerpilih.map(id =>
`<input type="hidden" name="buku_ids[]" value="${id}">`
).join('');
}
window.removeBuku = function (bookId) {
if (bookId !== bukuAwal.id) {
bukuTerpilih = bukuTerpilih.filter(id => id !== bookId);
updateDaftarBuku();
updateCounter();
updateSelectedBooks();
updateCheckboxes();
updateBtnTambahBuku();
}
}
window.konfirmasiPilihanBuku = function () {
updateDaftarBuku();
const modal = bootstrap.Modal.getInstance(document.getElementById('pilihBukuModal'));
modal.hide();
}
document.getElementById('konfirmasiModal')?.addEventListener('show.bs.modal', function () {
const selected = semuaBuku.filter(book => bukuTerpilih.includes(book.id));
const ringkasan = selected.map((book, index) =>
`<div class="d-flex justify-content-between">
<span>${index + 1}. ${book.judul}</span>
<small class="text-muted">${book.penulis}</small>
</div>`
).join('');
document.getElementById('ringkasanBuku').innerHTML = ringkasan;
});
window.kirimForm = function () {
document.getElementById('formPeminjaman').submit();
}
document.getElementById('pilihBukuModal')?.addEventListener('hidden.bs.modal', function () {
const searchInput = document.getElementById('searchBuku');
if (searchInput) {
searchInput.value = '';
document.querySelectorAll('.book-option').forEach(option => {
option.style.display = 'block';
});
}
});
}

1043
resources/scss/_custom.scss Normal file

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,47 @@
@use "sass:color";
// ===================================//
// VARIABLES & MAPS
// ===================================//
// Theme Colors Map
$theme-colors: (
"primary": #0C5495,
"secondary": #92D0F0,
"success": #14b8a6,
"info": #7BBDE8,
"warning": #fbb716,
"danger": #f43f5e,
);
// Gray Colors Map
$grays: (
"light": #f9f9f9,
"dark": #696e82,
);
// Spacing & Sizing
$border-radius: 0.5rem;
$border-radius-sm: 0.25rem;
$border-radius-lg: 1rem;
// Shadows & Transitions
$card-box-shadow: 0 0 1.25rem rgba(33, 37, 41, 0.05);
$shadow-sm: 0 2px 4px rgba(0, 0, 0, 0.08);
$shadow-md: 0 4px 8px rgba(0, 0, 0, 0.12);
$shadow-lg: 0 8px 20px rgba(0, 0, 0, 0.15);
$transition: all 0.3s ease;
// =============================
// CUSTOM BOOTSTRAP VARIABLES
// =============================
$primary: map-get($theme-colors, "primary");
// Tombol utama
$btn-primary-color: #fff;
$btn-primary-bg: $primary;
$btn-primary-border-color: $primary;
$btn-primary-hover-bg: darken($primary, 5%);
$btn-primary-hover-border-color: darken($primary, 5%);
$btn-focus-shadow-rgb: to-rgb($primary);
$btn-primary-active-bg: darken($primary, 7%);
$btn-primary-active-border-color: darken($primary, 7%);

5
resources/scss/app.scss Normal file
View File

@ -0,0 +1,5 @@
@import "bootstrap/scss/functions";
@import "variables";
@import "bootstrap/scss/bootstrap";
@import "custom";

View File

@ -0,0 +1,126 @@
<x-app-layout>
@section('page-title', $pageTitle)
<div class="d-flex align-items-center mb-4">
<a href="{{ route('admin.buku.index') }}" class="btn btn-outline-secondary me-3">
<i class="bi bi-arrow-left"></i>
</a>
<h3 class="my-0 fw-bold">Formulir Tambah Buku</h3>
</div>
<div class="row justify-content-center">
<div class="col-md-11">
<div class="card border-0 shadow-sm">
<div class="card-body p-4">
<form action="#" method="POST" id="formTambahBuku">
<div class="row">
<div class="col-md-8">
{{-- JUDUL --}}
<div class="mb-3">
<label for="judul" class="form-label">Judul Buku</label>
<input type="text" class="form-control" id="judul" placeholder="Masukkan judul buku" required>
</div>
{{-- PENULIS --}}
<div class="mb-3">
<label for="penulis" class="form-label">Penulis</label>
<input type="text" class="form-control" id="penulis" placeholder="Masukkan nama penulis" required>
</div>
<div class="row">
{{-- KATEGORI --}}
<div class="col-md-3 mb-3">
<label for="kategori" class="form-label">Kategori</label>
<input type="text" class="form-control" id="kategori" placeholder="Contoh: Fiksi" required>
</div>
{{-- TAHUN TERBIT (SOLUSI DROPDOWN / SELECT) --}}
<div class="col-md-3 mb-3">
<label for="tahun" class="form-label">Tahun Terbit</label>
<div class="input-group">
<span class="input-group-text bg-white border-end-0"><i class="bi bi-calendar-event"></i></span>
<select class="form-select border-start-0 ps-0" id="tahun" required>
<option value="" selected disabled>Pilih Tahun</option>
@php
$tahunSekarang = date('Y');
$tahunMulai = 1900;
@endphp
@for ($i = $tahunSekarang; $i >= $tahunMulai; $i--)
<option value="{{ $i }}">{{ $i }}</option>
@endfor
</select>
</div>
</div>
{{-- KODE BUKU --}}
<div class="col-md-3 mb-3">
<label for="kode_buku" class="form-label">Kode Buku</label>
<input type="text" class="form-control" id="kode_buku" placeholder="Contoh: 330" required>
</div>
{{-- STOK BUKU --}}
<div class="col-md-3 mb-3">
<label for="stok_buku" class="form-label">Stok Buku</label>
<input type="number" class="form-control" id="stok_buku" min="0" oninput="this.value = Math.abs(this.value)" placeholder="Contoh: 15" required>
</div>
</div>
{{-- TIPE AKSES --}}
<div class="mb-3">
<label class="form-label">Tipe Akses</label>
<div class="d-flex gap-3">
<div class="form-check">
<input class="form-check-input" type="checkbox" id="tipe_offline" checked>
<label class="form-check-label" for="tipe_offline">Peminjaman Offline</label>
</div>
<div class="form-check">
<input class="form-check-input" type="checkbox" id="tipe_online">
<label class="form-check-label" for="tipe_online">Baca Online</label>
</div>
</div>
</div>
</div>
{{-- UPLOAD FILE --}}
<div class="col-md-4">
<div class="mb-3">
<label for="cover" class="form-label">Cover Buku</label>
<input type="file" class="form-control" id="cover">
<div class="form-text small">Format: JPG, PNG. Maks: 2MB</div>
</div>
<div class="mb-3">
<label for="file_pdf" class="form-label">File PDF (untuk buku online)</label>
<input type="file" class="form-control" id="file_pdf">
<div class="form-text small">Format: PDF. Maks: 10MB</div>
</div>
</div>
</div>
<hr class="my-4">
<div class="d-flex justify-content-end">
<button type="submit" class="btn btn-primary px-4 fw-bold">
<i class="bi bi-save me-2"></i>Simpan Buku
</button>
</div>
</form>
</div>
</div>
</div>
</div>
@push('scripts')
<script>
document.addEventListener('DOMContentLoaded', function() {
// LOGIC SIMPAN
document.getElementById('formTambahBuku').addEventListener('submit', function(e) {
e.preventDefault();
modernSwal.fire({
title: 'Menyimpan...', timer: 1500, didOpen: () => Swal.showLoading()
}).then(() => {
Toast.fire({ icon: 'success', title: 'Berhasil', text: 'Buku baru berhasil ditambahkan.' });
setTimeout(() => { window.location.href = "{{ route('admin.buku.index') }}"; }, 1500);
});
});
});
</script>
@endpush
</x-app-layout>

View File

@ -0,0 +1,112 @@
<x-app-layout>
@section('page-title', $pageTitle)
<div class="d-flex align-items-center mb-4">
<a href="{{ route('admin.buku.index') }}" class="btn btn-outline-secondary me-3">
<i class="bi bi-arrow-left"></i>
</a>
<h3 class="my-0 fw-bold">Formulir Edit Buku</h3>
</div>
<div class="row justify-content-center">
<div class="col-md-11">
<div class="card border-0 shadow-sm">
<div class="card-body p-4">
<div class="card-body">
{{-- TAMBAHKAN ID PADA FORM --}}
<form action="#" method="POST" id="formEditBuku">
<div class="row">
<div class="col-md-8">
<div class="mb-3">
<label for="judul" class="form-label">Judul Buku</label>
<input type="text" class="form-control" id="judul" value="{{ $buku['judul'] }}" required>
</div>
<div class="mb-3">
<label for="penulis" class="form-label">Penulis</label>
<input type="text" class="form-control" id="penulis" value="{{ $buku['penulis'] }}" required>
</div>
<div class="row">
<div class="col-md-6 mb-3">
<label for="kategori" class="form-label">Kategori</label>
<input type="text" class="form-control" id="kategori" value="{{ $buku['kategori'] }}" required>
</div>
<div class="col-md-6 mb-3">
<label for="tahun" class="form-label">Tahun Terbit</label>
<input type="number" class="form-control" id="tahun" value="{{ $buku['tahun'] }}" min="1000" max="2099" oninput="this.value = Math.abs(this.value)" required>
</div>
</div>
@php
$tipe_akses = is_array($buku['tipe_akses']) ? $buku['tipe_akses'] : [$buku['tipe_akses']];
$isOffline = in_array('offline', $tipe_akses);
@endphp
@if($isOffline)
<div class="row">
<div class="col-md-6 mb-3">
<label for="kode_buku" class="form-label">Kode Buku</label>
<input type="text" class="form-control" id="kode_buku" value="{{ $buku['kode_buku'] ?? '' }}" placeholder="Masukkan kode buku" required>
</div>
<div class="col-md-6 mb-3">
<label for="stok_buku" class="form-label">Stok Buku</label>
<input type="number" class="form-control" id="stok_buku" value="{{ $buku['stok'] ?? 0 }}" min="0" oninput="this.value = Math.abs(this.value)" required>
</div>
</div>
@endif
<div class="mb-3">
<label class="form-label">Tipe Akses (Tidak dapat diubah)</label>
<div class="form-check">
<input class="form-check-input" type="checkbox" id="tipe_offline" @if (in_array('offline', $tipe_akses)) checked @endif disabled>
<label class="form-check-label" for="tipe_offline">Peminjaman Offline</label>
</div>
<div class="form-check">
<input class="form-check-input" type="checkbox" id="tipe_online" @if (in_array('online', $tipe_akses)) checked @endif disabled>
<label class="form-check-label" for="tipe_online">Baca Online</label>
</div>
</div>
</div>
<div class="col-md-4">
<div class="mb-3">
<label for="cover" class="form-label">Cover Buku</label>
<input type="file" class="form-control" id="cover">
<img src="{{ asset($buku['cover']) }}" alt="Cover saat ini" class="img-thumbnail mt-2" width="150">
</div>
</div>
</div>
<hr>
<div class="d-flex justify-content-end">
<button type="submit" class="btn btn-primary">Simpan Perubahan</button>
</div>
</form>
</div>
</div>
</div>
</div>
</div>
@push('scripts')
<script>
document.getElementById('formEditBuku').addEventListener('submit', function(e) {
e.preventDefault();
modernSwal.fire({
title: 'Menyimpan Perubahan...',
timer: 800,
didOpen: () => Swal.showLoading()
}).then(() => {
Toast.fire({
icon: 'success',
title: 'Berhasil',
text: 'Data buku berhasil diperbarui.'
});
setTimeout(() => {
window.location.href = "{{ route('admin.buku.index') }}";
}, 1500);
});
});
</script>
@endpush
</x-app-layout>

View File

@ -0,0 +1,368 @@
<x-app-layout>
@section('page-title', $pageTitle)
<div class="card shadow-sm border-0">
<div class="card-header bg-white d-flex justify-content-between align-items-center">
<h5 class="my-0 fw-bold">Daftar Buku</h5>
<a href="{{ route('admin.buku.create') }}" class="btn btn-primary">
<i class="bi bi-plus-circle-fill me-2"></i>Tambah Buku
</a>
</div>
<div class="card-body">
{{-- NAV TABS --}}
<ul class="nav nav-tabs" id="bukuTab" role="tablist">
<li class="nav-item" role="presentation">
<button class="nav-link active" id="offline-tab" data-bs-toggle="tab"
data-bs-target="#offline-tab-pane" type="button" role="tab">Peminjaman Offline (<span
id="countOffline">{{ $bukuOffline->count() }}</span>)</button>
</li>
<li class="nav-item" role="presentation">
<button class="nav-link" id="online-tab" data-bs-toggle="tab" data-bs-target="#online-tab-pane"
type="button" role="tab">Baca Online (<span id="countOnline">{{ $bukuOnline->count()
}}</span>)</button>
</li>
<li class="nav-item" role="presentation">
<button class="nav-link text-warning" id="arsip-tab" data-bs-toggle="tab"
data-bs-target="#arsip-tab-pane" type="button" role="tab">
<i class="bi bi-archive-fill me-1"></i>Diarsipkan (<span id="countArsip">0</span>)
</button>
</li>
</ul>
<div class="tab-content" id="bukuTabContent">
{{-- BUKU OFFLINE --}}
<div class="tab-pane fade show active" id="offline-tab-pane" role="tabpanel">
<div class="table-responsive mt-3">
<table class="table table-hover align-middle" id="tableOffline">
<thead class="table-light">
<tr>
<th>No</th>
<th>Cover</th>
<th>Judul</th>
<th>Kode Buku</th>
<th>Penulis</th>
<th>Stok</th>
<th>Status</th>
<th class="text-center">Aksi</th>
</tr>
</thead>
<tbody>
@forelse($bukuOffline as $buku)
<tr data-tipe="offline" data-id="{{ $buku['id'] }}">
<td class="row-number">{{ $loop->iteration }}</td>
<td><img src="{{ asset($buku['cover']) }}" alt="{{ $buku['judul'] }}" width="40"
class="rounded shadow-sm"></td>
<td class="fw-bold">{{ $buku['judul'] }}</td>
<td>{{ $buku['kode_buku'] }}</td>
<td>{{ $buku['penulis'] }}</td>
<td><span class="badge bg-secondary">{{ $buku['stok'] ?? 0 }}</span></td>
<td>
@if ($buku['status'] == 'Tersedia')
<span class="badge bg-success-subtle text-success-emphasis">Tersedia</span>
@else
<span class="badge bg-warning-subtle text-warning-emphasis">Dipinjam</span>
@endif
</td>
<td class="text-center">
<div class="d-flex justify-content-center gap-2">
<button class="btn btn-sm btn-outline-secondary btn-detail"
data-bs-toggle="modal" data-bs-target="#detailBukuModal"
data-buku='@json($buku)'>
<i class="bi bi-eye-fill"></i> Detail
</button>
<button class="btn btn-sm btn-outline-warning btn-arsipkan"
data-judul="{{ $buku['judul'] }}" title="Arsipkan Buku">
<i class="bi bi-archive-fill"></i> Arsip
</button>
</div>
</td>
</tr>
@empty
<tr class="empty-row">
<td colspan="8" class="text-center py-4 text-muted">Tidak ada data buku offline.
</td>
</tr>
@endforelse
</tbody>
</table>
</div>
</div>
{{-- BUKU ONLINE --}}
<div class="tab-pane fade" id="online-tab-pane" role="tabpanel">
<div class="table-responsive mt-3">
<table class="table table-hover align-middle" id="tableOnline">
<thead class="table-light">
<tr>
<th>No</th>
<th>Cover</th>
<th>Judul</th>
<th>Penulis</th>
<th>File PDF</th>
<th class="text-center">Aksi</th>
</tr>
</thead>
<tbody>
@forelse($bukuOnline as $buku)
<tr data-tipe="online" data-id="{{ $buku['id'] }}">
<td class="row-number">{{ $loop->iteration }}</td>
<td><img src="{{ asset($buku['cover']) }}" alt="{{ $buku['judul'] }}" width="40"
class="rounded shadow-sm"></td>
<td class="fw-bold">{{ $buku['judul'] }}</td>
<td>{{ $buku['penulis'] }}</td>
<td><span class="badge bg-info-subtle text-info-emphasis">PDF Available</span></td>
<td class="text-center">
<div class="d-flex justify-content-center gap-2">
<button class="btn btn-sm btn-outline-secondary btn-detail"
data-bs-toggle="modal" data-bs-target="#detailBukuModal"
data-buku='@json($buku)'>
<i class="bi bi-eye-fill"></i> Detail
</button>
<button class="btn btn-sm btn-outline-warning btn-arsipkan"
data-judul="{{ $buku['judul'] }}" title="Arsipkan Buku">
<i class="bi bi-archive-fill"></i> Arsip
</button>
</div>
</td>
</tr>
@empty
<tr class="empty-row">
<td colspan="6" class="text-center py-4 text-muted">Tidak ada data buku online.</td>
</tr>
@endforelse
</tbody>
</table>
</div>
</div>
{{-- ARSIP --}}
<div class="tab-pane fade" id="arsip-tab-pane" role="tabpanel">
<div class="table-responsive mt-3">
<table class="table table-hover align-middle" id="tableArsip">
<thead class="table-light">
<tr>
<th>No</th>
<th>Cover</th>
<th>Judul</th>
<th>Penulis</th>
<th>Tipe Asal</th>
<th class="text-center">Aksi</th>
</tr>
</thead>
<tbody>
<tr class="empty-row-arsip">
<td colspan="6" class="text-center py-5 text-muted">
<i class="bi bi-inbox fs-1 d-block mb-2 text-secondary opacity-50"></i>
Belum ada buku yang diarsipkan.
</td>
</tr>
</tbody>
</table>
</div>
</div>
</div>
</div>
</div>
{{-- MODAL DETAIL BUKU --}}
<div class="modal fade" id="detailBukuModal" tabindex="-1">
<div class="modal-dialog modal-lg">
<div class="modal-content border-0 shadow">
<div class="modal-header border-0">
<h5 class="modal-title fw-bold" id="modalJudul">Detail Buku</h5>
<button type="button" class="btn-close" data-bs-dismiss="modal"></button>
</div>
<div class="modal-body">
<div class="row">
<div class="col-md-4 text-center mb-3">
<img src="" id="modalCover" class="img-fluid rounded shadow"
style="max-height: 250px; object-fit: cover;">
</div>
<div class="col-md-8">
<h3 id="modalJudulContent" class="fw-bold text-dark mb-1"></h3>
<p class="text-muted mb-3" id="modalPenulis"></p>
<div class="bg-light p-3 rounded-3">
<table class="table table-sm table-borderless mb-0">
<tr>
<td class="text-secondary" width="130">Kategori</td>
<td id="modalKategori" class="fw-bold"></td>
</tr>
<tr id="rowKodeBuku">
<td class="text-secondary">Kode Buku</td>
<td id="modalKode" class="fw-bold font-monospace"></td>
</tr>
<tr>
<td class="text-secondary">Tahun Terbit</td>
<td id="modalTahun" class="fw-bold"></td>
</tr>
<tr>
<td class="text-secondary">Stok</td>
<td id="modalStok" class="fw-bold"></td>
</tr>
<tr>
<td class="text-secondary">Status</td>
<td><span id="modalStatus" class="badge"></span></td>
</tr>
</table>
</div>
</div>
</div>
</div>
<div class="modal-footer border-0 bg-light">
<button type="button" class="btn btn-secondary rounded-pill px-4"
data-bs-dismiss="modal">Tutup</button>
<a href="#" id="modalEditButton" class="btn btn-primary rounded-pill px-4">
<i class="bi bi-pencil-square me-2"></i>Edit Buku
</a>
</div>
</div>
</div>
</div>
@push('scripts')
<script>
document.addEventListener('DOMContentLoaded', function() {
function updateTableNumbers() {
['#tableOffline', '#tableOnline', '#tableArsip'].forEach(tableId => {
let count = 0;
$(tableId + ' tbody tr').not('[class^="empty-row"]').each(function(index) {
$(this).find('.row-number').text(index + 1);
count++;
});
if (tableId === '#tableOffline') $('#countOffline').text(count);
if (tableId === '#tableOnline') $('#countOnline').text(count);
if (tableId === '#tableArsip') {
$('#countArsip').text(count);
if(count === 0) $('.empty-row-arsip').show(); else $('.empty-row-arsip').hide();
}
});
}
// LOGIC MODAL DETAIL
$('#detailBukuModal').on('show.bs.modal', function(event) {
const button = $(event.relatedTarget);
const buku = button.data('buku');
$('#modalCover').attr('src', "{{ asset('') }}" + buku.cover);
$('#modalJudulContent').text(buku.judul);
$('#modalPenulis').text('Penulis: ' + buku.penulis);
$('#modalKategori').text(buku.kategori);
$('#modalTahun').text(buku.tahun);
$('#modalStok').text(buku.stok ? buku.stok + ' Buku' : '-');
if (buku.kode_buku) {
$('#rowKodeBuku').show();
$('#modalKode').text(buku.kode_buku);
} else {
$('#rowKodeBuku').hide();
}
// Status Badge
const statusBadge = $('#modalStatus');
statusBadge.removeClass().addClass('badge');
if (buku.status === 'Tersedia' || !buku.status) {
statusBadge.addClass('bg-success-subtle text-success-emphasis').text('Tersedia / Online');
} else {
statusBadge.addClass('bg-warning-subtle text-warning-emphasis').text('Dipinjam');
}
$('#modalEditButton').attr('href', "{{ url('admin/buku') }}/" + buku.id + "/edit");
});
// LOGIC ARSIPKAN BUKU
$(document).on('click', '.btn-arsipkan', function() {
const row = $(this).closest('tr');
const judul = $(this).data('judul');
const tipe = row.data('tipe');
const rowData = row.prop('outerHTML');
modernSwal.fire({
title: 'Arsipkan Buku?',
text: `Buku "${judul}" akan dipindahkan ke tab Arsip.`,
icon: 'warning',
showCancelButton: true,
confirmButtonText: 'Ya, Arsipkan',
cancelButtonText: 'Batal',
confirmButtonColor: '#ffc107',
}).then((result) => {
if (result.isConfirmed) {
row.fadeOut(300, function() {
const coverHtml = row.find('td:eq(1)').html();
const penulis = row.find('td:eq(3)').text();
const badgeTipe = tipe === 'offline'
? '<span class="badge bg-secondary"><i class="bi bi-book me-1"></i>Offline</span>'
: '<span class="badge bg-info"><i class="bi bi-globe me-1"></i>Online</span>';
const originalDataEncoded = encodeURIComponent(rowData);
const arsipRow = `
<tr data-origin="${originalDataEncoded}">
<td class="row-number"></td>
<td>${coverHtml}</td>
<td class="fw-bold text-muted">${judul}</td>
<td class="text-muted">${penulis}</td>
<td>${badgeTipe}</td>
<td class="text-center">
<button class="btn btn-sm btn-outline-success btn-pulihkan"
data-judul="${judul}" title="Kembalikan ke Daftar Aktif">
<i class="bi bi-arrow-counterclockwise me-1"></i>Kembalikan
</button>
</td>
</tr>
`;
$('#tableArsip tbody').append(arsipRow);
$(this).remove();
updateTableNumbers();
Toast.fire({ icon: 'success', title: 'Diarsipkan', text: `Buku "${judul}" berhasil diarsipkan.` });
});
}
});
});
// LOGIC PULIHKAN BUKU
$(document).on('click', '.btn-pulihkan', function() {
const row = $(this).closest('tr');
const judul = $(this).data('judul');
const originalDataEncoded = row.data('origin');
modernSwal.fire({
title: 'Kembalikan Buku?',
text: `Buku "${judul}" akan dikembalikan ke daftar aktif.`,
icon: 'question',
showCancelButton: true,
confirmButtonText: 'Ya, Kembalikan',
cancelButtonText: 'Batal',
confirmButtonColor: '#198754',
}).then((result) => {
if (result.isConfirmed) {
row.fadeOut(300, function() {
const originalRowHtml = decodeURIComponent(originalDataEncoded);
const $originalRow = $(originalRowHtml);
const tipe = $originalRow.data('tipe');
const targetTable = tipe === 'offline' ? '#tableOffline' : '#tableOnline';
$originalRow.removeAttr('style');
$(targetTable + ' tbody').append($originalRow);
$(this).remove();
updateTableNumbers();
Toast.fire({ icon: 'success', title: 'Dipulihkan', text: `Buku "${judul}" aktif kembali.` });
});
}
});
});
});
</script>
@endpush
</x-app-layout>

View File

@ -0,0 +1,182 @@
<x-app-layout>
@section('page-title', 'Beranda')
{{-- Welcome card Section --}}
<div class="card border-0 shadow-sm rounded-4 my-4 p-4 position-relative" style="background-color: #CEDEFF;">
<div class="row">
<div class="col-12 col-md-8 p-4 p-md-5" style="z-index: 2;">
<h2 class="fw-bold text-dark mb-2">{{ $greeting }}, {{ $user->nama_lengkap }}!</h2>
<p class="fs-5 mb-0" style="color: #696E82;">Berikut adalah ringkasan aktivitas perpustakaan hari ini.</p>
</div>
</div>
<div class="position-absolute d-none d-md-block"
style="top: -35px; right: 40px; width: 30%; max-width: 300px; z-index: 1;">
<img src="{{ asset('images/assets/vector-dashboard.svg') }}" alt="Ilustrasi Dashboard" class="img-fluid">
</div>
</div>
{{-- Kartu Statistik --}}
<div class="row g-4 mb-4">
@foreach ($stats as $stat)
<div class="col-xl-3 col-lg-6 col-md-6">
<div class="card rounded-2 bg-{{ $stat['color'] }}-light border-0 h-100">
<div class="card-body p-4">
<div class="d-flex justify-content-between align-items-start">
<div class="flex-grow-1">
<h6 class="text-muted fw-normal mb-2 text-uppercase small">{{ $stat['label'] }}</h6>
<h3 class="fw-bold mb-0 text-dark">{{ $stat['value'] }}</h3>
</div>
<div class="icon-wrapper">
<div class="icon-circle bg-{{ $stat['color'] }}-light">
<i class="bi {{ $stat['icon'] }} text-{{ $stat['color'] }} fs-4"></i>
</div>
</div>
</div>
</div>
</div>
</div>
@endforeach
</div>
<div class="row g-4 mb-4">
<div class="col-lg-7">
<div class="card border-0 shadow-sm h-100">
<div class="card-header bg-white border-0 py-3">
<h6 class="m-0 fw-bold text-dark"><i class="bi bi-bar-chart-fill text-primary me-2"></i>Total Peminjaman per Bulan</h6>
</div>
<div class="card-body p-4">
<canvas id="barChart" style="max-height: 300px;" data-stats='@json($statistikBulanan)'></canvas>
</div>
</div>
</div>
<div class="col-lg-5">
<div class="card border-0 shadow-sm h-100">
<div class="card-header bg-white border-0 py-3">
<h6 class="m-0 fw-bold text-dark"><i class="bi bi-pie-chart-fill text-primary me-2"></i>Komposisi Status Buku</h6>
</div>
<div class="card-body text-center d-flex justify-content-center align-items-center p-4">
<div style="position: relative; height: 200px; width: 200px;">
<canvas id="donutChartAdmin" data-progress='@json($komposisiBuku)'></canvas>
</div>
</div>
<div class="text-center py-3 border-top">
<div class="d-flex justify-content-center gap-4">
<span class="badge bg-success-soft text-success px-3 py-2"><i class="bi bi-circle-fill me-1"></i> Tersedia</span>
<span class="badge bg-warning-soft text-warning px-3 py-2"><i class="bi bi-circle-fill me-1"></i> Dipinjam</span>
</div>
</div>
</div>
</div>
</div>
<div class="row g-4 mb-4">
<div class="col-lg-6">
<div class="card border-0 shadow-sm h-100">
<div class="card-header bg-white border-0 d-flex justify-content-between align-items-center py-3">
<h6 class="m-0 fw-bold text-dark"><i class="bi bi-megaphone-fill text-warning me-2"></i>Pengumuman</h6>
<a href="{{ route('admin.pengumuman.index') }}" class="btn btn-sm btn-outline-primary rounded-pill px-3">
Kelola Semua
</a>
</div>
<div class="card-body p-4">
@forelse(collect($pengumuman)->take(2) as $item)
<div class="alert alert-{{ $item['type'] }} border-0 d-flex align-items-start mb-3 shadow-sm">
<i class="{{ $item['icon'] }} fs-5 me-3 mt-1"></i>
<div>
<div class="fw-bold mb-1">{{ $item['title'] }}!</div>
<div class="small">{{ $item['content'] }}</div>
</div>
</div>
@empty
<div class="text-center py-4"><i class="bi bi-inbox text-muted fs-2 mb-3"></i><p class="text-muted mb-0">Tidak ada pengumuman baru.</p></div>
@endforelse
</div>
</div>
</div>
<div class="col-lg-6">
<div class="card border-0 shadow-sm h-100">
<div class="card-header bg-white border-0 d-flex justify-content-between align-items-center py-3">
<h6 class="m-0 fw-bold text-dark"><i class="bi bi-bell-fill text-info me-2"></i>Aktivitas Peminjaman Terkini</h6>
</div>
<div class="card-body p-0">
<div class="table-responsive">
<table class="table table-hover mb-0">
<tbody>
@forelse($aktivitasTerakhir as $aktivitas)
<tr>
<td class="ps-4 py-3">
<div class="fw-semibold text-dark">{{ $aktivitas['nama'] }}</div>
<div class="text-muted small truncate-text" style="max-width: 200px;">{{ $aktivitas['tipe'] }} buku "{{ $aktivitas['judul_buku'] }}"</div>
</td>
<td class="text-end pe-4 py-3">
@if($aktivitas['status'] == 'Dikembalikan' || $aktivitas['status'] == 'Selesai')
<span class="badge bg-success-subtle text-success-emphasis">{{$aktivitas['status']}}</span>
@else
<span class="badge bg-warning-subtle text-warning-emphasis">{{$aktivitas['status']}}</span>
@endif
<div class="text-muted small mt-1">{{ $aktivitas['waktu'] }}</div>
</td>
</tr>
@empty
<tr><td class="text-center py-5"><p class="text-muted">Tidak ada aktivitas terkini.</p></td></tr>
@endforelse
</tbody>
</table>
</div>
</div>
</div>
</div>
</div>
@push('scripts')
<script src="https://cdn.jsdelivr.net/npm/chart.js"></script>
<script>
// Script untuk menginisialisasi chart di dashboard admin
document.addEventListener('DOMContentLoaded', function() {
if (window.myBarChart) window.myBarChart.destroy();
if (window.myDonutChart) window.myDonutChart.destroy();
// Bar Chart
const barCtx = document.getElementById('barChart');
if (barCtx) {
const barData = JSON.parse(barCtx.dataset.stats);
window.myBarChart = new Chart(barCtx, {
type: 'bar',
data: {
labels: barData.labels,
datasets: [{
label: 'Jumlah Peminjaman',
data: barData.data,
backgroundColor: '#0C5495',
borderColor: '#0C5495',
borderWidth: 1,
borderRadius: 5
}]
},
options: { scales: { y: { beginAtZero: true } }, responsive: true, maintainAspectRatio: false }
});
}
// Donut Chart
const donutCtx = document.getElementById('donutChartAdmin');
if (donutCtx) {
const donutData = JSON.parse(donutCtx.dataset.progress);
window.myDonutChart = new Chart(donutCtx, {
type: 'doughnut',
data: {
labels: ['Tersedia', 'Dipinjam'],
datasets: [{
data: [donutData.tersedia, donutData.dipinjam],
backgroundColor: ['#198754', '#ffc107'],
borderWidth: 0,
}]
},
options: { responsive: true, maintainAspectRatio: false, cutout: '75%' }
});
}
});
</script>
@endpush
</x-app-layout>

View File

@ -0,0 +1,260 @@
<x-app-layout>
@section('page-title', 'Manajemen Denda')
<div class="d-flex justify-content-between align-items-center mb-4">
<div>
<h3 class="my-0 fw-bold">Manajemen Denda & Sanksi</h3>
<p class="text-muted mb-0">Pantau pengguna terlambat dan berikan sanksi jika diperlukan.</p>
</div>
</div>
{{-- FILTER SECTION --}}
<div class="card border-0 shadow-sm mb-4">
<div class="card-body py-3">
<div class="row g-3 align-items-center">
<div class="col-md-auto">
<span class="fw-bold text-muted"><i class="bi bi-funnel-fill me-1"></i> Filter Data:</span>
</div>
<div class="col-md-3">
<select id="filterKelas" class="form-select form-select-sm">
<option value="">Semua Kelas/Golongan</option>
@foreach ($listKelas as $kelas)
<option value="{{ $kelas }}">{{ $kelas }}</option>
@endforeach
</select>
</div>
<div class="col-md-3">
<select id="filterBesaran" class="form-select form-select-sm">
<option value="">Semua Nominal</option>
<option value="ringan">Denda Ringan (< Rp 10.000)</option>
<option value="berat">Denda Berat (> Rp 10.000)</option>
</select>
</div>
<div class="col-md-auto ms-auto">
<button id="resetFilter" class="btn btn-sm btn-light border text-muted">
<i class="bi bi-arrow-counterclockwise"></i> Reset
</button>
</div>
</div>
</div>
</div>
<div class="card border-0 shadow-sm">
<div class="card-body">
<div class="table-responsive">
<table id="dendaTable" class="table table-striped table-hover align-middle" style="width:100%">
<thead class="table-light">
<tr>
<th class="text-center" width="5%">NO</th>
<th width="25%">NAMA</th>
<th width="25%">BUKU TERLAMBAT</th>
<th width="15%">STATUS</th>
<th width="15%">DENDA</th>
<th width="15%">AKSI</th>
</tr>
</thead>
<tbody>
@forelse ($siswaTelat as $item)
<tr>
<td class="text-center">{{ $loop->iteration }}</td>
<td>
<div class="fw-bold text-dark">{{ $item['peminjam'] }}</div>
<span class="badge bg-light text-secondary border mt-1 mb-1">{{ $item['kelas'] }}</span>
<div class="small text-muted">
<i class="bi bi-telephone me-1"></i>{{ $item['nomor_hp'] }}
</div>
</td>
<td>
<ul class="mb-0 ps-3 small text-muted">
@foreach ($item['books'] as $buku)
<li>{{ $buku['judul'] }}</li>
@endforeach
</ul>
</td>
{{-- KOLOM STATUS --}}
<td data-order="{{ $item['tenggat_kembali']->timestamp }}">
@if(isset($item['role']) && strtolower($item['role']) === 'guru')
<div class="fw-bold text-muted">-</div>
@else
<span class="badge bg-danger-subtle text-danger border border-danger-subtle rounded-pill px-3">
Telat {{ $item['hari_terlambat'] }} Hari
</span>
<div class="small text-muted mt-1">
Tenggat: {{ $item['tenggat_kembali']->format('d/m/Y') }}
</div>
@endif
</td>
{{-- KOLOM DENDA --}}
<td data-order="{{ isset($item['role']) && strtolower($item['role']) === 'guru' ? 0 : $item['total_denda'] }}">
@if(isset($item['role']) && strtolower($item['role']) === 'guru')
<div class="fw-bold text-muted">-</div>
@else
<div class="fw-bold text-danger">Rp {{ number_format($item['total_denda'], 0, ',', '.') }}</div>
<small class="text-muted" style="font-size: 0.75rem;">Rp 1.000/hari</small>
@endif
</td>
{{-- KOLOM AKSI --}}
<td>
<div class="d-flex gap-2">
{{-- Tombol WA (Muncul untuk semua) --}}
<a href="{{ $item['wa_link'] }}" target="_blank"
class="btn btn-sm btn-success text-white" title="Tagih via WhatsApp">
<i class="bi bi-whatsapp"></i>
</a>
@if(!isset($item['role']) || strtolower($item['role']) !== 'guru')
@if ($item['is_banned'])
{{-- Jika sudah dibekukan (Otomatis/Manual), muncul tombol AKTIFKAN --}}
<button class="btn btn-sm btn-outline-success btn-aktifkan"
data-nama="{{ $item['peminjam'] }}" title="Aktifkan Kembali Akun">
<i class="bi bi-shield-check"></i> Aktifkan
</button>
@else
{{-- Jika belum dibekukan, muncul tombol SANKSI (Manual) --}}
<button class="btn btn-sm btn-outline-danger btn-sanksi"
data-nama="{{ $item['peminjam'] }}" title="Berikan Sanksi">
<i class="bi bi-slash-circle"></i> Sanksi
</button>
@endif
@endif
</div>
</td>
</tr>
@empty
<tr>
<td colspan="6" class="text-center py-5">
<div class="text-muted opacity-50">
<i class="bi bi-emoji-smile fs-1 mb-2 d-block"></i>
<p class="mb-0">Tidak ada buku terlambat hari ini.</p>
</div>
</td>
</tr>
@endforelse
</tbody>
</table>
</div>
</div>
</div>
@push('scripts')
<script>
$(document).ready(function() {
var table = $('#dendaTable').DataTable({
order: [
[3, 'desc']
],
columnDefs: [{
"searchable": false,
"orderable": false,
"targets": 0
}],
language: {
search: "_INPUT_",
searchPlaceholder: "Cari nama peminjam..."
},
dom: 'rtip'
});
table.on('order.dt search.dt', function() {
table.column(0, {
search: 'applied',
order: 'applied'
}).nodes().each(function(cell, i) {
cell.innerHTML = i + 1;
});
}).draw();
$.fn.dataTable.ext.search.push(
function(settings, data, dataIndex) {
var filterKelas = $('#filterKelas').val();
var filterBesaran = $('#filterBesaran').val();
var dataSiswa = data[1] || "";
var dataDendaRaw = data[4] || "0";
var dataDenda = parseInt(dataDendaRaw.replace(/[^0-9]/g, ''), 10);
if (filterKelas !== "" && !dataSiswa.includes(filterKelas)) return false;
if (filterBesaran === "ringan" && dataDenda >= 10000) return false;
if (filterBesaran === "berat" && dataDenda < 10000) return false;
return true;
}
);
$('#filterKelas, #filterBesaran').change(function() {
table.draw();
});
$('#resetFilter').click(function() {
$('#filterKelas').val('');
$('#filterBesaran').val('');
table.draw();
});
});
// --- LOGIC TOMBOL SANKSI ---
$(document).on('click', '.btn-sanksi', function() {
const nama = $(this).data('nama');
modernSwal.fire({
title: 'Nonaktifkan Akun?',
text: `Apakah Anda yakin ingin memberikan sanksi pembekuan akun kepada ${nama}?`,
icon: 'warning',
showCancelButton: true,
confirmButtonText: 'Ya, Bekukan',
confirmButtonColor: '#dc3545',
cancelButtonText: 'Batal'
}).then((result) => {
if (result.isConfirmed) {
modernSwal.fire({
title: 'Memproses...',
timer: 1000,
didOpen: () => Swal.showLoading()
})
.then(() => {
Toast.fire({
icon: 'success',
title: 'Sanksi Diterapkan',
text: `Akun ${nama} berhasil dibekukan.`
});
});
}
});
});
// Logic Tombol Aktifkan (Unban)
$(document).on('click', '.btn-aktifkan', function() {
const nama = $(this).data('nama');
modernSwal.fire({
title: 'Aktifkan Akun?',
text: `Pastikan ${nama} sudah melunasi denda. Akun akan diaktifkan kembali.`,
icon: 'question',
showCancelButton: true,
confirmButtonText: 'Ya, Aktifkan',
confirmButtonColor: '#198754',
cancelButtonText: 'Batal'
}).then((result) => {
if (result.isConfirmed) {
// Simulasi Loading & Sukses
modernSwal.fire({
title: 'Memproses...',
timer: 1000,
didOpen: () => Swal.showLoading()
})
.then(() => {
Toast.fire({
icon: 'success',
title: 'Akun Diaktifkan',
text: `Status sanksi pada ${nama} telah dicabut.`
});
$(this).closest('td').html('<span class="badge bg-success">Aktif</span>');
});
}
});
});
</script>
@endpush
</x-app-layout>

View File

@ -0,0 +1,304 @@
<x-app-layout>
@section('page-title', $pageTitle)
<div class="d-flex align-items-center mb-4">
<a href="{{ route('admin.peminjaman.index') }}" class="btn btn-outline-secondary me-3">
<i class="bi bi-arrow-left"></i>
</a>
<h3 class="my-0 fw-bold">Formulir Peminjaman Manual</h3>
</div>
<form action="#" method="POST" id="formPeminjaman" autocomplete="off"> @csrf
<div class="row g-4">
<div class="col-lg-7">
<div class="card border-0 shadow-sm">
<div class="card-body p-4">
<h5 class="fw-bold mb-3">Data Peminjaman</h5>
<div class="mb-3">
<label for="peminjam_id" class="form-label">Pilih Peminjam (Siswa/Guru)</label>
<select class="form-control" id="peminjam_id" name="peminjam_id" placeholder="Cari nama atau email...">
<option value="">Pilih...</option>
@foreach ($groupedUsers as $role => $users)
<optgroup label="{{ ucfirst($role) }}">
@foreach ($users as $user)
<option value="{{ $user['id'] }}"
data-role="{{ strtolower($role) }}"
data-identitas="{{ $user['nip'] ?? $user['nisn'] ?? '-' }}"
data-kontak="{{ $user['no_hp'] ?? '-' }}"
data-info="{{ strtolower($role) == 'guru' ? ($user['jabatan'] ?? 'Guru') : ($user['kelas'] ?? 'Siswa') }}"
{{ $user['disabled'] ? 'disabled' : '' }}>
{{ $user['nama_lengkap'] }} {{ $user['status_text'] }}
</option>
@endforeach
</optgroup>
@endforeach
</select>
</div>
<div id="detailPeminjamCard" class="alert alert-secondary d-none mb-3">
<h6 class="fw-bold mb-2 border-bottom pb-1"><i class="bi bi-person-badge me-2"></i>Detail Identitas</h6>
<div class="row small">
<div class="col-6 mb-1"><span class="text-muted">NIP/NISN:</span> <strong id="lblIdentitas">-</strong></div>
<div class="col-6 mb-1"><span class="text-muted">No. HP:</span> <strong id="lblKontak">-</strong></div>
<div class="col-6"><span class="text-muted">Jabatan/Kelas:</span> <strong id="lblInfo">-</strong></div>
<div class="col-6"><span class="text-muted">Role:</span> <strong id="lblRole" class="text-uppercase">-</strong></div>
</div>
</div>
<div class="row g-3">
<div class="col-md-6">
<label for="tanggal_pinjam" class="form-label">Tanggal Pinjam</label>
<input type="text" class="form-control" id="tanggal_pinjam" name="tanggal_pinjam" placeholder="Pilih tanggal pinjam">
</div>
<div class="col-md-6">
<label for="tanggal_kembali" class="form-label">Tenggat Kembali</label>
<input type="text" class="form-control" id="tanggal_kembali" name="tanggal_kembali" placeholder="Pilih tenggat kembali">
</div>
</div>
<hr class="my-4">
<div class="d-flex justify-content-between align-items-center mb-3">
<h5 class="fw-bold m-0">Buku Terpilih</h5>
<span class="badge bg-primary-soft" id="counterBuku">0 Buku</span>
</div>
<div id="daftarBukuPinjam" class="mb-3">
<div id="emptyStateBuku" class="text-center text-muted py-4">
<i class="bi bi-collection fs-1" style="opacity: 0.25;"></i>
<p class="mb-0 mt-2">Belum ada buku yang dipilih.</p>
</div>
</div>
<div id="hiddenInputs"></div>
<div class="d-grid">
<button type="submit" class="btn btn-primary">
<i class="bi bi-save me-1"></i> Simpan Peminjaman
</button>
</div>
</div>
</div>
</div>
<div class="col-lg-5">
<div class="card border-0 shadow-sm">
<div class="card-header bg-white py-3">
<h5 class="fw-bold m-0">Pilih Buku</h5>
</div>
<div class="card-body p-4">
<div class="mb-3">
<div class="input-group">
<span class="input-group-text bg-white"><i class="bi bi-search"></i></span>
<input type="text" class="form-control border-start-0" id="searchBuku" placeholder="Cari judul atau penulis...">
</div>
</div>
<div id="bookSelectionList" style="max-height: 600px; overflow-y: auto;">
@foreach ($daftarBuku as $buku)
<div class="book-option p-2" data-book-id="{{ $buku['id'] }}"
data-book-title="{{ strtolower($buku['judul']) }}"
data-book-author="{{ strtolower($buku['penulis']) }}"
data-book-cover="{{ asset($buku['cover']) }}"
data-book-kategori="{{ $buku['kategori'] }}">
<div class="d-flex align-items-center book-item-list"
onclick="toggleBookSelection(this, {{ $buku['id'] }})" style="cursor: pointer;">
<img src="{{ asset($buku['cover']) }}" alt="Cover" class="rounded me-3" style="width: 50px; height: 70px; object-fit: cover;">
<div class="flex-grow-1">
<h6 class="fw-bold mb-1 line-clamp-2">{{ $buku['judul'] }}</h6>
<p class="text-muted small mb-1">{{ $buku['penulis'] }}</p>
<span class="badge bg-info-soft">{{ $buku['kategori'] }}</span>
</div>
<div class="form-check ms-3">
<input class="form-check-input book-checkbox" type="checkbox" value="{{ $buku['id'] }}" id="book-check-{{ $buku['id'] }}" style="pointer-events: none;">
</div>
</div>
</div>
@endforeach
</div>
</div>
</div>
</div>
</div>
</form>
@push('scripts')
<script>
document.addEventListener("DOMContentLoaded", function() {
const tomSelect = new TomSelect("#peminjam_id", {
create: false,
sortField: { field: "text", direction: "asc" },
onChange: function(value) {
// Munculkan Kartu Detail Peminjam saat Dropdown Berubah
const selectedOption = this.options[value];
const detailCard = document.getElementById('detailPeminjamCard');
if(selectedOption && value !== "") {
document.getElementById('lblRole').textContent = selectedOption.dataset.role;
document.getElementById('lblIdentitas').textContent = selectedOption.dataset.identitas;
document.getElementById('lblKontak').textContent = selectedOption.dataset.kontak;
document.getElementById('lblInfo').textContent = selectedOption.dataset.info;
detailCard.classList.remove('d-none');
} else {
detailCard.classList.add('d-none');
}
}
});
const tglPinjam = flatpickr("#tanggal_pinjam", {
dateFormat: "Y-m-d", altInput: true, altFormat: "d/m/Y", defaultDate: "today", locale: "id",
onChange: function(selectedDates, dateStr) {
if (selectedDates.length > 0) tglKembali.set("minDate", new Date(selectedDates[0]).fp_incr(1));
}
});
const tglKembali = flatpickr("#tanggal_kembali", {
dateFormat: "Y-m-d", altInput: true, altFormat: "d/m/Y", defaultDate: new Date().fp_incr(7), locale: "id", minDate: new Date().fp_incr(1)
});
const MAX_BOOKS_SISWA = 2;
let selectedBookIds = new Set();
const allBooks = new Map();
document.querySelectorAll('.book-option').forEach(el => {
const id = el.dataset.bookId;
allBooks.set(id, { id: id, title: el.querySelector('h6').textContent, author: el.querySelector('p').textContent, cover: el.dataset.bookCover });
});
const daftarBukuPinjamEl = document.getElementById('daftarBukuPinjam');
const hiddenInputsEl = document.getElementById('hiddenInputs');
const counterBukuEl = document.getElementById('counterBuku');
const emptyStateBukuEl = document.getElementById('emptyStateBuku');
function renderSelectedBooks() {
daftarBukuPinjamEl.querySelectorAll('.selected-book-item').forEach(el => el.remove());
hiddenInputsEl.innerHTML = '';
emptyStateBukuEl.style.display = selectedBookIds.size === 0 ? 'block' : 'none';
selectedBookIds.forEach(id => {
const book = allBooks.get(String(id));
if (!book) return;
const itemHtml = `
<div class="selected-book-item book-item d-flex align-items-start p-3 mb-2 rounded" data-selected-id="${id}">
<img src="${book.cover}" alt="Cover" class="rounded me-3" style="width: 45px; height: 60px; object-fit: cover;">
<div class="flex-grow-1">
<h6 class="fw-bold mb-0 line-clamp-1">${book.title}</h6>
<p class="text-muted small mb-0">${book.author}</p>
</div>
<button type="button" class="btn btn-sm btn-outline-danger remove-book" onclick="removeBook(${id})"><i class="bi bi-trash"></i></button>
</div>`;
daftarBukuPinjamEl.insertAdjacentHTML('beforeend', itemHtml);
hiddenInputsEl.insertAdjacentHTML('beforeend', `<input type="hidden" name="buku_ids[]" value="${id}">`);
});
counterBukuEl.textContent = `${selectedBookIds.size} Buku`;
}
// Global function untuk toggle selection
window.toggleBookSelection = function(itemElement, id) {
const selectEl = document.getElementById('peminjam_id');
if(selectEl.value === "") {
alert("Silakan pilih Peminjam (Siswa/Guru) terlebih dahulu sebelum memilih buku!");
return;
}
const selectedOption = selectEl.options[selectEl.selectedIndex];
const roleUser = selectedOption.dataset.role;
const checkbox = itemElement.querySelector('.book-checkbox');
const stringId = String(id);
if (selectedBookIds.has(stringId)) {
selectedBookIds.delete(stringId);
checkbox.checked = false;
itemElement.style.background = 'transparent';
} else {
if (roleUser === 'siswa' && selectedBookIds.size >= MAX_BOOKS_SISWA) {
alert(`Maaf, role Siswa hanya dapat meminjam maksimal ${MAX_BOOKS_SISWA} buku secara bersamaan.`);
return;
}
selectedBookIds.add(stringId);
checkbox.checked = true;
itemElement.style.background = 'rgba(var(--bs-primary-rgb), 0.05)';
}
renderSelectedBooks();
}
window.removeBook = function(id) {
selectedBookIds.delete(String(id));
const itemElement = document.querySelector(`.book-option[data-book-id="${id}"] .book-item-list`);
if (itemElement) {
itemElement.querySelector('.book-checkbox').checked = false;
itemElement.style.background = 'transparent';
}
renderSelectedBooks();
}
// Pencarian
document.getElementById('searchBuku').addEventListener('keyup', function() {
const searchTerm = this.value.toLowerCase();
document.querySelectorAll('.book-option').forEach(el => {
const title = el.dataset.bookTitle;
const author = el.dataset.bookAuthor;
el.style.display = (title.includes(searchTerm) || author.includes(searchTerm)) ? 'block' : 'none';
});
});
document.getElementById('formPeminjaman').addEventListener('submit', function(e) {
e.preventDefault();
const peminjam = document.getElementById('peminjam_id').value;
const jumlahBuku = selectedBookIds.size;
// Validasi
if (!peminjam) {
Toast.fire({ icon: 'warning', title: 'Perhatian', text: 'Pilih peminjam terlebih dahulu!' });
return;
}
if (jumlahBuku === 0) {
Toast.fire({ icon: 'warning', title: 'Perhatian', text: 'Pilih minimal 1 buku!' });
return;
}
modernSwal.fire({
title: 'Proses Peminjaman?',
text: `Anda akan memproses ${jumlahBuku} buku.`,
icon: 'question',
showCancelButton: true,
confirmButtonText: 'Ya, Proses',
cancelButtonText: 'Batal'
}).then((result) => {
if (result.isConfirmed) {
// Loading
modernSwal.fire({
title: 'Memproses...',
timer: 1000,
didOpen: () => Swal.showLoading()
}).then(() => {
Toast.fire({
icon: 'success',
title: 'Berhasil',
text: 'Transaksi peminjaman berhasil disimpan.'
});
setTimeout(() => {
window.location.href = "{{ route('admin.peminjaman.index') }}";
}, 1500);
});
}
});
});
document.getElementById('formPeminjaman').reset();
tomSelect.clear();
selectedBookIds.clear();
renderSelectedBooks();
});
</script>
@endpush
</x-app-layout>

View File

@ -0,0 +1,294 @@
<x-app-layout>
@section('page-title', $pageTitle)
<div class="d-flex justify-content-between align-items-center mb-4 flex-wrap gap-3">
<div>
<h3 class="my-0 fw-bold">Manajemen Peminjaman</h3>
<p class="text-muted mb-0">Daftar ini hanya menampilkan buku yang masih berstatus "Dipinjam".</p>
</div>
<div class="d-flex align-items-center gap-2">
<form action="#" method="GET" class="d-flex m-0 p-0 bg-white border rounded p-1" onsubmit="alert('Fitur download Excel sedang disiapkan tim Backend'); return false;">
<input type="month" name="bulan_laporan" class="form-control form-control-sm border-0 me-1" required>
<button type="submit" class="btn btn-sm btn-success text-nowrap">
<i class="bi bi-file-earmark-excel-fill me-1"></i>Excel
</button>
</form>
<a href="{{ route('admin.peminjaman.create') }}" class="btn btn-primary text-nowrap">
<i class="bi bi-plus-circle-fill me-1"></i>Peminjaman Manual
</a>
</div>
</div>
<div class="card border-0 shadow-sm">
<div class="card-body">
<div class="table-responsive">
<table id="peminjamanTable" class="table table-striped table-hover nowrap dt-responsive" style="width:100%">
<thead class="table-light">
<tr>
<th>NO</th>
<th>ID PEMINJAMAN</th>
<th>PEMINJAM (JABATAN/KELAS)</th>
<th>JUDUL BUKU</th>
<th>TGL. PINJAM</th>
<th>TENGGAT KEMBALI</th>
<th>STATUS</th>
<th>AKSI</th>
</tr>
</thead>
<tbody>
@php
$now = \Carbon\Carbon::now();
$counter = 1;
@endphp
@forelse ($peminjamanAktif as $transaksi)
@php
$tenggat = $transaksi['tenggat_kembali'];
$isTerlambat = $now->startOfDay()->isAfter($tenggat->startOfDay());
$isHariIni = $now->startOfDay()->isSameDay($tenggat->startOfDay());
$selisihHari = $now->startOfDay()->diffInDays($tenggat->startOfDay(), false);
$isGuru = isset($transaksi['role']) && strtolower($transaksi['role']) == 'guru';
if ($isTerlambat) {
if ($isGuru) {
$statusClass = 'badge rounded-pill bg-info-subtle text-info-emphasis';
$statusText = 'Terlambat (Bebas Denda)';
} else {
$statusClass = 'badge rounded-pill bg-danger-subtle text-danger-emphasis';
$statusText = 'Terlambat ' . $tenggat->startOfDay()->diffInDays($now->startOfDay()) . ' hari';
}
} elseif ($isHariIni) {
$statusClass = 'badge rounded-pill bg-warning-subtle text-warning-emphasis';
$statusText = 'Jatuh Tempo Hari Ini';
} else {
$statusClass = 'badge rounded-pill bg-success-subtle text-success-emphasis';
$statusText = 'Sisa ' . abs($selisihHari) . ' hari';
}
@endphp
<tr>
<td>{{ $counter++ }}</td>
<td>
<span class="badge bg-primary-subtle text-primary fw-bold">{{ $transaksi['id_peminjaman'] }}</span>
</td>
<td>
<div class="fw-bold">{{ $transaksi['peminjam'] }}</div>
<div class="small text-muted">{{ $transaksi['nomor_hp'] }}</div>
</td>
<td>
<ul class="mb-0 ps-3 small">
@foreach ($transaksi['books'] as $buku)
<li>{{ $buku['judul'] }}</li>
@endforeach
</ul>
</td>
<td>{{ $transaksi['tanggal_pinjam']->format('d/m/Y') }}</td>
<td>{{ $transaksi['tenggat_kembali']->format('d/m/Y') }}</td>
<td>
<span class="{{ $statusClass }}">{{ $statusText }}</span>
</td>
<td>
<button class="btn btn-sm btn-outline-primary" data-bs-toggle="modal"
data-bs-target="#modalPengembalian-{{ $transaksi['id_peminjaman'] }}">
Proses Pengembalian
</button>
</td>
</tr>
{{-- MODAL PENGEMBALIAN --}}
<div class="modal fade" id="modalPengembalian-{{ $transaksi['id_peminjaman'] }}" tabindex="-1" aria-hidden="true">
<div class="modal-dialog modal-lg modal-dialog-centered">
<div class="modal-content border-0 shadow-lg rounded-3">
<div class="modal-header p-4">
<h5 class="modal-title fw-bold">Proses Pengembalian ({{ count($transaksi['books']) }} Buku)</h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body p-4">
<div class="alert alert-light border mb-4">
<div class="d-flex justify-content-between">
<span>Peminjam: <strong>{{ $transaksi['peminjam'] }}</strong></span>
<span>ID: <strong>{{ $transaksi['id_peminjaman'] }}</strong></span>
</div>
</div>
@if($isGuru)
<div class="alert alert-info py-2 small mb-3">
<i class="bi bi-shield-check me-1"></i> Role Guru: Bebas dari beban denda keterlambatan dan catatan denda/sanksi.
</div>
@endif
<h6 class="fw-bold mb-3">Daftar Buku yang Dikembalikan:</h6>
@foreach ($transaksi['books'] as $buku)
<div class="card mb-3 border bg-light">
<div class="card-body p-3">
<h6 class="fw-bold text-primary mb-2">{{ $buku['judul'] }}</h6>
<div class="row">
@if(!$isGuru)
<div class="col-md-6">
<label class="form-label small text-muted mb-1">Kondisi Buku</label>
<div class="d-flex gap-3">
<div class="form-check">
<input class="form-check-input radio-kondisi" type="radio" name="kondisi_{{ $buku['id'] }}_{{ $transaksi['id_peminjaman'] }}" value="baik" checked>
<label class="form-check-label small">Baik</label>
</div>
<div class="form-check">
<input class="form-check-input radio-kondisi" type="radio" name="kondisi_{{ $buku['id'] }}_{{ $transaksi['id_peminjaman'] }}" value="rusak">
<label class="form-check-label small">Rusak/Hilang</label>
</div>
</div>
</div>
<div class="col-md-6 denda-rusak-input-wrapper d-none">
<label class="form-label small text-muted mb-1">Denda Kerusakan</label>
<input type="number" class="form-control form-control-sm denda-rusak-input" placeholder="0">
</div>
<div class="col-12">
<label class="form-label small text-muted mb-1"><i class="bi bi-pencil-square me-1"></i>Catatan Petugas</label>
<textarea class="form-control form-control-sm" rows="2" placeholder="Contoh: Ada coretan di halaman 10, Cover sedikit terlipat..."></textarea>
</div>
@else
<div class="col-12">
<span class="badge bg-success-subtle text-success-emphasis border"><i class="bi bi-check-circle me-1"></i> Buku dikembalikan oleh Guru</span>
</div>
@endif
</div>
</div>
</div>
@endforeach
<hr>
@if(!$isGuru)
<div class="d-flex justify-content-between align-items-center mb-3">
<span>Denda Keterlambatan ({{ $statusText }})</span>
@php
$dendaTelat = 0;
if ($isTerlambat && !$isGuru) {
$hari = $tenggat->startOfDay()->diffInDays($now->startOfDay());
$dendaTelat = $hari * 1000;
}
@endphp
<strong class="text-danger denda-keterlambatan-display" data-denda-keterlambatan="{{ $dendaTelat }}">
Rp {{ number_format($dendaTelat, 0, ',', '.') }}
</strong>
</div>
<div class="d-flex justify-content-between align-items-center mb-3 bg-danger bg-opacity-10 p-2 rounded">
<span class="fw-bold text-danger">TOTAL YANG HARUS DIBAYAR</span>
<strong class="text-danger fs-5 total-denda-display">Rp {{ number_format($dendaTelat, 0, ',', '.') }}</strong>
</div>
@endif
<div class="form-check form-switch mb-0 mt-3">
<input class="form-check-input" type="checkbox" role="switch" checked id="waStrukToggle-{{ $transaksi['id_peminjaman'] }}">
<label class="form-check-label small" for="waStrukToggle-{{ $transaksi['id_peminjaman'] }}">
Kirim <strong>Bukti Pengembalian</strong> ke WhatsApp
</label>
</div>
<div class="form-check form-switch mb-0">
<input class="form-check-input email-toggle" type="checkbox" role="switch" checked id="emailStrukToggle-{{ $transaksi['id_peminjaman'] }}">
<label class="form-check-label small" for="emailStrukToggle-{{ $transaksi['id_peminjaman'] }}">
Kirim <strong>Bukti Pengembalian</strong> ke Email
</label>
</div>
</div>
<div class="modal-footer p-3 bg-light">
<button type="button" class="btn btn-outline-secondary" data-bs-dismiss="modal">Batal</button>
<button type="button" class="btn btn-primary btn-konfirmasi-kembali" data-nama-peminjam="{{ $transaksi['peminjam'] }}">
Konfirmasi & Selesai
</button>
</div>
</div>
</div>
</div>
@empty
<tr><td colspan="8" class="text-center py-5">Tidak ada data.</td></tr>
@endforelse
</tbody>
</table>
</div>
</div>
</div>
@push('scripts')
<script>
$(document).ready(function() {
$('#peminjamanTable').DataTable({ pageLength: 10, order: [[0, 'asc']] });
});
document.addEventListener('DOMContentLoaded', function() {
function formatRupiah(angka) {
return new Intl.NumberFormat('id-ID', { style: 'currency', currency: 'IDR', minimumFractionDigits: 0 }).format(angka).replace(/\s/g, '');
}
function hitungTotalDenda(modal) {
const dendaKeterlambatanEl = modal.querySelector('.denda-keterlambatan-display');
const totalDendaEl = modal.querySelector('.total-denda-display');
if(!dendaKeterlambatanEl || !totalDendaEl) return;
let dendaKeterlambatan = parseInt(dendaKeterlambatanEl.dataset.dendaKeterlambatan) || 0;
let totalDendaRusak = 0;
modal.querySelectorAll('.denda-rusak-input').forEach(input => {
if (!input.closest('.denda-rusak-input-wrapper').classList.contains('d-none')) {
totalDendaRusak += parseInt(input.value) || 0;
}
});
totalDendaEl.textContent = formatRupiah(dendaKeterlambatan + totalDendaRusak);
}
document.querySelectorAll('.radio-kondisi').forEach(radio => {
radio.addEventListener('change', function() {
const cardBody = this.closest('.card-body');
const dendaRusakWrapper = cardBody.querySelector('.denda-rusak-input-wrapper');
const dendaRusakInput = cardBody.querySelector('.denda-rusak-input');
if(this.value === 'rusak') {
dendaRusakWrapper.classList.remove('d-none');
} else {
dendaRusakWrapper.classList.add('d-none');
dendaRusakInput.value = 0;
}
hitungTotalDenda(this.closest('.modal'));
});
});
document.querySelectorAll('.denda-rusak-input').forEach(input => {
input.addEventListener('input', function() { hitungTotalDenda(this.closest('.modal')); });
});
});
$(document).on('click', '.btn-konfirmasi-kembali', function() {
const nama = $(this).data('nama-peminjam');
const modalEl = $(this).closest('.modal');
const modalInstance = bootstrap.Modal.getInstance(modalEl[0]);
const isEmailChecked = modalEl.find('.email-toggle').is(':checked');
modalInstance.hide();
modernSwal.fire({
title: 'Selesaikan Transaksi?', text: `Buku dari ${nama} akan ditandai sudah kembali.`, icon: 'question',
showCancelButton: true, confirmButtonText: 'Ya, Selesaikan', cancelButtonText: 'Batal'
}).then((result) => {
if (result.isConfirmed) {
modernSwal.fire({
title: 'Menyimpan Data...', timer: 800, timerProgressBar: true, didOpen: () => Swal.showLoading()
}).then(() => {
if (isEmailChecked) {
const dummyEmail = nama.replace(/\s+/g, '.').toLowerCase() + '@sekolah.sch.id';
modernSwal.fire({
title: 'Mengirim Email...', html: `Mengirim nota ke: <b>${dummyEmail}</b>`, timer: 2000, timerProgressBar: true, didOpen: () => Swal.showLoading()
}).then(() => { finishTransaction(true); });
} else { finishTransaction(false); }
});
} else { modalInstance.show(); }
});
function finishTransaction(withEmail) {
Toast.fire({ icon: 'success', title: 'Berhasil', text: withEmail ? 'Buku kembali & Email terkirim.' : 'Buku berhasil dikembalikan.' });
setTimeout(() => location.reload(), 1500);
}
});
</script>
@endpush
</x-app-layout>

View File

@ -0,0 +1,177 @@
<x-app-layout>
@section('page-title', $pageTitle)
<div class="d-flex align-items-center mb-4">
<a href="{{ route('admin.pengguna.index') }}" class="btn btn-outline-secondary me-3">
<i class="bi bi-arrow-left"></i>
</a>
<h3 class="my-0 fw-bold">Formulir Tambah Pengguna</h3>
</div>
<div class="row justify-content-center">
<div class="col-md-10">
<div class="card border-0 shadow-sm">
<div class="card-body p-4">
<form action="{{ route('admin.pengguna.store') }}" method="POST" id="formPengguna">
@csrf
<div class="mb-3">
<label for="role" class="form-label">Role <span class="text-danger">*</span></label>
<select class="form-select @error('role') is-invalid @enderror" id="role" name="role"
required onchange="toggleFields()">
<option value="" selected disabled>Pilih role terlebih dahulu...</option>
<option value="siswa" {{ old('role')=='siswa' ? 'selected' : '' }}>Siswa</option>
<option value="guru" {{ old('role')=='guru' ? 'selected' : '' }}>Guru</option>
<option value="penjaga perpus" {{ old('role')=='penjaga perpus' ? 'selected' : '' }}>
Penjaga Perpustakaan</option>
</select>
@error('role')
<div class="invalid-feedback">{{ $message }}</div>
@enderror
</div>
{{-- Bagian Form Dinamis --}}
<div id="dynamic-form" class="d-none">
<div class="mb-3">
<label for="nama_lengkap" class="form-label">Nama Lengkap</label>
<input type="text" class="form-control @error('nama_lengkap') is-invalid @enderror"
id="nama_lengkap" name="nama_lengkap" value="{{ old('nama_lengkap') }}" required>
</div>
<div class="mb-3">
<label for="nomor_induk" class="form-label" id="label_nomor_induk">NISN / NIP</label>
<input type="number" class="form-control @error('nomor_induk') is-invalid @enderror"
id="nomor_induk" name="nomor_induk" value="{{ old('nomor_induk') }}"
placeholder="Masukkan Nomor Induk">
@error('nomor_induk')
<div class="invalid-feedback">{{ $message }}</div>
@enderror
</div>
<div class="row">
<div class="col-md-6 mb-3">
<label for="email" class="form-label">Email</label>
<input type="email" class="form-control @error('email') is-invalid @enderror"
id="email" name="email" value="{{ old('email') }}" required>
@error('email')
<div class="invalid-feedback">{{ $message }}</div>
@enderror
</div>
<div class="col-md-6 mb-3">
<label for="no_hp" class="form-label">No. Handphone</label>
<input type="text" class="form-control" id="no_hp" name="no_hp"
value="{{ old('no_hp') }}" placeholder="Contoh: 08123456789">
</div>
</div>
<div class="row" id="field_siswa_only" style="display: none;">
<div class="col-md-6 mb-3">
<label for="kelas" class="form-label">Kelas</label>
<input type="text" class="form-control" id="kelas" name="kelas"
value="{{ old('kelas') }}" placeholder="Contoh: XII RPL 1">
</div>
<div class="col-md-6 mb-3">
<label for="golongan" class="form-label">Golongan</label>
<input type="text" class="form-control" id="golongan" name="golongan"
value="{{ old('golongan') }}" placeholder="Contoh: A/B">
</div>
</div>
<hr>
<div class="row">
<div class="col-md-6 mb-3">
<label for="password" class="form-label">Password</label>
<div class="input-group has-validation">
<input type="password"
class="form-control @error('password') is-invalid @enderror" id="password"
name="password">
<button class="btn btn-outline-secondary toggle-password" type="button"
data-target="password">
<i class="bi bi-eye" id="icon-password"></i>
</button>
@error('password')
<div class="invalid-feedback">{{ $message }}</div>
@enderror
</div>
</div>
<div class="col-md-6 mb-3">
<label for="password_confirmation" class="form-label">Konfirmasi Password</label>
<div class="input-group">
<input type="password" class="form-control" id="password_confirmation"
name="password_confirmation">
<button class="btn btn-outline-secondary toggle-password" type="button"
data-target="password_confirmation">
<i class="bi bi-eye" id="icon-password_confirmation"></i>
</button>
</div>
</div>
</div>
<div class="d-flex justify-content-end mt-3">
<button type="submit" class="btn btn-primary px-4">Simpan Pengguna</button>
</div>
</div>
</form>
</div>
</div>
</div>
</div>
@push('scripts')
<script>
function toggleFields() {
const role = document.getElementById('role').value;
const dynamicForm = document.getElementById('dynamic-form');
const labelInduk = document.getElementById('label_nomor_induk');
const inputInduk = document.getElementById('nomor_induk');
const fieldSiswaOnly = document.getElementById('field_siswa_only');
if (role) dynamicForm.classList.remove('d-none');
if (role === 'siswa') {
labelInduk.innerHTML = 'NISN <span class="text-danger">*</span>';
inputInduk.placeholder = 'Masukkan NISN Siswa';
fieldSiswaOnly.style.display = 'flex';
} else if (role === 'guru') {
labelInduk.innerHTML = 'NIP / NIK <span class="text-danger">*</span>';
inputInduk.placeholder = 'Masukkan NIP/NIK Guru';
fieldSiswaOnly.style.display = 'none';
} else if (role === 'penjaga perpus') {
labelInduk.innerHTML = 'NIP / NIK <span class="text-danger">*</span>';
inputInduk.placeholder = 'Masukkan NIP/NIK Petugas';
fieldSiswaOnly.style.display = 'none';
}
}
document.addEventListener('DOMContentLoaded', toggleFields);
document.querySelectorAll('.toggle-password').forEach(function(button) {
button.addEventListener('click', function() {
const targetId = this.getAttribute('data-target');
const input = document.getElementById(targetId);
const icon = document.getElementById('icon-' + targetId);
if (input.type === 'password') {
input.type = 'text'; icon.classList.replace('bi-eye', 'bi-eye-slash');
} else {
input.type = 'password'; icon.classList.replace('bi-eye-slash', 'bi-eye');
}
});
});
document.getElementById('formPengguna').addEventListener('submit', function() {
modernSwal.fire({
title: 'Menyimpan Data...',
allowOutsideClick: false,
didOpen: () => Swal.showLoading()
});
});
@if(session('success'))
Toast.fire({ icon: 'success', title: 'Berhasil', text: '{{ session("success") }}' });
@endif
</script>
@endpush
</x-app-layout>

View File

@ -0,0 +1,128 @@
<x-app-layout>
@section('page-title', $pageTitle)
<div class="d-flex align-items-center mb-4">
<a href="{{ route('admin.pengguna.index') }}" class="btn btn-outline-secondary me-3">
<i class="bi bi-arrow-left"></i>
</a>
<h3 class="my-0 fw-bold">Formulir Edit Pengguna</h3>
</div>
<div class="row justify-content-center">
<div class="col-md-10">
<div class="card border-0 shadow-sm">
<div class="card-body p-4">
<form action="{{ route('admin.pengguna.update', $pengguna->id) }}" method="POST" id="formEditPengguna">
@csrf
@method('PATCH')
<div class="mb-3">
<label for="role" class="form-label">Role <span class="text-danger">*</span></label>
<select class="form-select @error('role') is-invalid @enderror" id="role" name="role" required onchange="toggleFields()">
<option value="siswa" {{ old('role', $pengguna->role) == 'siswa' ? 'selected' : '' }}>Siswa</option>
<option value="guru" {{ old('role', $pengguna->role) == 'guru' ? 'selected' : '' }}>Guru</option>
<option value="penjaga perpus" {{ old('role', $pengguna->role) == 'penjaga perpus' ? 'selected' : '' }}>Penjaga Perpustakaan</option>
</select>
@error('role') <div class="invalid-feedback">{{ $message }}</div> @enderror
</div>
<div id="dynamic-form">
<div class="mb-3">
<label for="nama_lengkap" class="form-label">Nama Lengkap</label>
<input type="text" class="form-control @error('nama_lengkap') is-invalid @enderror"
id="nama_lengkap" name="nama_lengkap" value="{{ old('nama_lengkap', $pengguna->name) }}" required>
</div>
<div class="mb-3">
@php $oldNomorInduk = old('nomor_induk', $pengguna->role == 'siswa' ? $pengguna->nisn : $pengguna->nip); @endphp
<label for="nomor_induk" class="form-label" id="label_nomor_induk">NISN / NIP</label>
<input type="number" class="form-control @error('nomor_induk') is-invalid @enderror"
id="nomor_induk" name="nomor_induk" value="{{ $oldNomorInduk }}" placeholder="Masukkan Nomor Induk">
@error('nomor_induk') <div class="invalid-feedback fw-bold">{{ $message }}</div> @enderror
</div>
<div class="row">
<div class="col-md-6 mb-3">
<label for="email" class="form-label">Email</label>
<input type="email" class="form-control @error('email') is-invalid @enderror"
id="email" name="email" value="{{ old('email', $pengguna->email) }}" required>
@error('email') <div class="invalid-feedback">{{ $message }}</div> @enderror
</div>
<div class="col-md-6 mb-3">
<label for="no_hp" class="form-label">No. Handphone</label>
<input type="text" class="form-control" id="no_hp" name="no_hp" value="{{ old('no_hp', $pengguna->no_hp) }}">
</div>
</div>
<div class="row" id="field_siswa_only" style="display: none;">
<div class="col-md-6 mb-3">
<label for="kelas" class="form-label">Kelas</label>
<input type="text" class="form-control" id="kelas" name="kelas" value="{{ old('kelas', $pengguna->kelas) }}">
</div>
<div class="col-md-6 mb-3">
<label for="golongan" class="form-label">Golongan</label>
<input type="text" class="form-control" id="golongan" name="golongan" value="{{ old('golongan', $pengguna->golongan) }}">
</div>
</div>
<hr>
<div class="row">
<div class="col-md-6 mb-3">
<label for="password" class="form-label">Password Baru <span class="small text-muted">(opsional)</span></label>
<input type="password" class="form-control @error('password') is-invalid @enderror" id="password" name="password" placeholder="Kosongkan jika tidak diubah">
@error('password') <div class="invalid-feedback">{{ $message }}</div> @enderror
</div>
<div class="col-md-6 mb-3">
<label for="password_confirmation" class="form-label">Konfirmasi Password Baru</label>
<input type="password" class="form-control" id="password_confirmation" name="password_confirmation" placeholder="Ulangi password baru">
</div>
</div>
<div class="d-flex justify-content-end mt-3">
<button type="submit" class="btn btn-primary px-4">Simpan Perubahan</button>
</div>
</div>
</form>
</div>
</div>
</div>
</div>
@push('scripts')
<script>
function toggleFields() {
const role = document.getElementById('role').value;
const labelInduk = document.getElementById('label_nomor_induk');
const inputInduk = document.getElementById('nomor_induk');
const fieldSiswaOnly = document.getElementById('field_siswa_only');
if (role === 'siswa') {
labelInduk.innerHTML = 'NISN <span class="text-danger">*</span>';
inputInduk.placeholder = 'Masukkan NISN Siswa';
fieldSiswaOnly.style.display = 'flex';
} else if (role === 'guru') {
labelInduk.innerHTML = 'NIP / NIK <span class="text-danger">*</span>';
inputInduk.placeholder = 'Masukkan NIP/NIK Guru';
fieldSiswaOnly.style.display = 'none';
} else if (role === 'penjaga perpus') {
labelInduk.innerHTML = 'NIP / NIK <span class="text-danger">*</span>';
inputInduk.placeholder = 'Masukkan NIP/NIK Petugas';
fieldSiswaOnly.style.display = 'none';
}
}
document.addEventListener('DOMContentLoaded', toggleFields);
document.getElementById('formEditPengguna').addEventListener('submit', function() {
modernSwal.fire({
title: 'Menyimpan Perubahan...',
allowOutsideClick: false,
didOpen: () => Swal.showLoading()
});
});
@if(session('success'))
Toast.fire({ icon: 'success', title: 'Berhasil', text: '{{ session("success") }}' });
@endif
</script>
@endpush
</x-app-layout>

Some files were not shown because too many files have changed in this diff Show More