diff --git a/app/Http/Controllers/admin/VenueController.php b/app/Http/Controllers/admin/VenueController.php new file mode 100644 index 0000000..c56cf88 --- /dev/null +++ b/app/Http/Controllers/admin/VenueController.php @@ -0,0 +1,114 @@ +user()->venue; + + if (!$venue) { + return redirect()->route('admin.dashboard')->with('error', 'Anda belum memiliki venue yang ditugaskan.'); + } + + return view('admin.venues.index', compact('venue')); + } + + /** + * Show the form for editing venue + */ + public function edit() + { + $venue = auth()->user()->venue; + + if (!$venue) { + return redirect()->route('admin.dashboard')->with('error', 'Anda belum memiliki venue yang ditugaskan.'); + } + + return view('admin.venues.edit', compact('venue')); + } + + /** + * Update venue information + */ + public function update(Request $request) + { + $venue = auth()->user()->venue; + + if (!$venue) { + return redirect()->route('admin.dashboard')->with('error', 'Anda belum memiliki venue yang ditugaskan.'); + } + + // Validation rules + $validator = Validator::make($request->all(), [ + 'name' => 'required|string|max:255', + 'address' => 'required|string|max:500', + 'phone' => 'nullable|string|max:20', + 'description' => 'nullable|string|max:1000', + 'open_time' => 'required|date_format:H:i', + 'close_time' => 'required|date_format:H:i', + 'image' => 'nullable|image|mimes:jpeg,png,jpg,gif|max:2048', // Max 2MB + ], [ + 'name.required' => 'Nama venue harus diisi.', + 'address.required' => 'Alamat venue harus diisi.', + 'open_time.required' => 'Jam buka harus diisi.', + 'open_time.date_format' => 'Format jam buka tidak valid (gunakan format HH:MM).', + 'close_time.required' => 'Jam tutup harus diisi.', + 'close_time.date_format' => 'Format jam tutup tidak valid (gunakan format HH:MM).', + 'image.image' => 'File yang diupload harus berupa gambar.', + 'image.mimes' => 'Gambar harus berformat: jpeg, png, jpg, atau gif.', + 'image.max' => 'Ukuran gambar maksimal 2MB.', + ]); + + if ($validator->fails()) { + return redirect()->back() + ->withErrors($validator) + ->withInput(); + } + + try { + // Handle image upload + $imagePath = $venue->image; // Keep current image by default + + if ($request->hasFile('image')) { + // Delete old image if exists + if ($venue->image && Storage::disk('public')->exists($venue->image)) { + Storage::disk('public')->delete($venue->image); + } + + // Store new image + $imagePath = $request->file('image')->store('venues', 'public'); + } + + // Update venue data + $venue->update([ + 'name' => $request->name, + 'address' => $request->address, + 'phone' => $request->phone, + 'description' => $request->description, + 'open_time' => $request->open_time, + 'close_time' => $request->close_time, + 'image' => $imagePath, + ]); + + return redirect()->route('admin.venue.index') + ->with('success', 'Informasi venue berhasil diperbarui!'); + + } catch (\Exception $e) { + return redirect()->back() + ->with('error', 'Terjadi kesalahan saat memperbarui venue: ' . $e->getMessage()) + ->withInput(); + } + } +} \ No newline at end of file diff --git a/app/Models/Venue.php b/app/Models/Venue.php index 22cf6b9..a57d6b7 100644 --- a/app/Models/Venue.php +++ b/app/Models/Venue.php @@ -9,7 +9,20 @@ class Venue extends Model { use HasFactory; - protected $fillable = ['name', 'location', 'address', 'image']; + protected $fillable = [ + 'name', + 'address', + 'image', + 'phone', // Pastikan field ini ada + 'description', // Pastikan field ini ada + 'open_time', // Pastikan field ini ada + 'close_time', // Pastikan field ini ada + ]; + + protected $casts = [ + 'open_time' => 'datetime', + 'close_time' => 'datetime', + ]; public function tables() { diff --git a/resources/views/admin/venues/edit.blade.php b/resources/views/admin/venues/edit.blade.php new file mode 100644 index 0000000..da8f180 --- /dev/null +++ b/resources/views/admin/venues/edit.blade.php @@ -0,0 +1,206 @@ +@extends('layouts.admin') + +@section('content') +
+ +
+
+ + + + + +
+

Edit Venue

+

Perbarui informasi venue Anda

+
+
+
+ + + @if(session('success')) +
+ {{ session('success') }} +
+ @endif + + @if(session('error')) +
+ {{ session('error') }} +
+ @endif + + +
+
+ @csrf + @method('PUT') + +
+ +
+ +
+ + + @error('name') +

{{ $message }}

+ @enderror +
+ + +
+ + + @error('address') +

{{ $message }}

+ @enderror +
+ + +
+ + + @error('phone') +

{{ $message }}

+ @enderror +
+ + +
+
+ + + @error('open_time') +

{{ $message }}

+ @enderror +
+
+ + + @error('close_time') +

{{ $message }}

+ @enderror +
+
+
+ + +
+ +
+ +
+ @if($venue->image) + {{ $venue->name }} + @else +
+ + + +
+ @endif +
+
+ + +
+ + + @error('image') +

{{ $message }}

+ @enderror +

Format: JPEG, PNG, JPG, GIF. Maksimal 2MB

+ + + +
+
+
+ + +
+ + + @error('description') +

{{ $message }}

+ @enderror +
+ + +
+ + Batal + + +
+
+
+
+ + +@endsection \ No newline at end of file diff --git a/resources/views/admin/venues/index.blade.php b/resources/views/admin/venues/index.blade.php index e69de29..5c337f5 100644 --- a/resources/views/admin/venues/index.blade.php +++ b/resources/views/admin/venues/index.blade.php @@ -0,0 +1,197 @@ +@extends('layouts.admin') + +@section('content') +
+ +
+
+
+

Kelola Venue

+

Kelola informasi venue Anda

+
+ + + + + Edit Venue + +
+
+ + + @if(session('success')) +
+ {{ session('success') }} +
+ @endif + + @if(session('error')) +
+ {{ session('error') }} +
+ @endif + + +
+
+
+ +
+

Foto Venue

+
+ @if($venue->image) + {{ $venue->name }} + @else +
+ + + +
+ @endif +
+
+ + +
+

Informasi Venue

+ +
+ +
+
+ Nama Venue: +
+
+ {{ $venue->name }} +
+
+ + +
+
+ Alamat: +
+
+ {{ $venue->address }} +
+
+ + +
+
+ Telepon: +
+
+ {{ $venue->phone ?: '-' }} +
+
+ + +
+
+ Jam Operasional: +
+
+ + {{ $venue->open_time ? \Carbon\Carbon::parse($venue->open_time)->format('H:i') : '-' }} + - + {{ $venue->close_time ? \Carbon\Carbon::parse($venue->close_time)->format('H:i') : '-' }} + +
+
+ + +
+
+ Deskripsi: +
+
+

{{ $venue->description ?: 'Belum ada deskripsi' }}

+
+
+ + +
+
+ Terakhir Diperbarui: +
+
+ {{ $venue->updated_at->format('d M Y, H:i') }} +
+
+
+
+
+
+
+ + +
+ +
+
+
+
+ + + +
+
+
+

Total Meja

+

{{ $venue->tables->count() }}

+
+
+
+ + +
+
+
+
+ + + +
+
+
+

Meja Tersedia

+

+ {{ $venue->tables->where('status', 'available')->count() }}

+
+
+
+ + +
+
+
+
+ + + +
+
+
+

Meja Terpakai

+

+ {{ $venue->tables->where('status', 'occupied')->count() }}

+
+
+
+
+
+@endsection \ No newline at end of file diff --git a/resources/views/layouts/admin.blade.php b/resources/views/layouts/admin.blade.php index c2ca03f..6177508 100644 --- a/resources/views/layouts/admin.blade.php +++ b/resources/views/layouts/admin.blade.php @@ -97,6 +97,16 @@ class="nav-item flex items-center px-3 py-2.5 rounded-lg {{ request()->routeIs(' Dashboard + + + + + Kelola Venue + +

{{ $venue['name'] }}

+

{{ $venue['location'] ?? 'Lokasi tidak tersedia' }}

Jam Operasional: {{ date('H:i', strtotime($venue['open_time'])) }} - @@ -182,12 +183,12 @@ function showToast(message, type = 'info', duration = 5000) { toast.className = `${bgColor} text-white px-6 py-4 rounded-lg shadow-lg flex items-center space-x-3 min-w-80 transform transition-all duration-300 translate-x-full opacity-0`; toast.innerHTML = ` - - ${message} - - `; + + ${message} + + `; toastContainer.appendChild(toast); @@ -223,20 +224,20 @@ function showModal(title, message, type = 'info', callback = null) { }[type] || 'fa-info-circle'; modal.innerHTML = ` -

-
- -

${title}

+
+
+ +

${title}

+
+

${message}

+
+ +
-

${message}

-
- -
-
- `; + `; document.body.appendChild(modal); @@ -255,22 +256,22 @@ function showConfirmModal(title, message, onConfirm, onCancel = null) { modal.className = 'fixed inset-0 bg-black bg-opacity-50 z-50 flex items-center justify-center p-4'; modal.innerHTML = ` -
-
- -

${title}

+
+
+ +

${title}

+
+

${message}

+
+ + +
-

${message}

-
- - -
-
- `; + `; document.body.appendChild(modal); diff --git a/routes/web.php b/routes/web.php index b774a5b..0b7fb27 100644 --- a/routes/web.php +++ b/routes/web.php @@ -9,6 +9,7 @@ use App\Http\Controllers\admin\TableController; use App\Http\Controllers\admin\RevenueController; use App\Http\Controllers\admin\AdminController; +use App\Http\Controllers\admin\VenueController as AdminVenueController; // Import admin venue controller use App\Http\Controllers\Auth\VerificationController; use App\Http\Controllers\superadmin\SuperAdminController; use App\Http\Controllers\superadmin\AdminManagementController; @@ -72,6 +73,8 @@ // Admin routes (admin tetap perlu verified untuk keamanan) Route::middleware(['auth', 'verified', 'is_admin'])->prefix('admin')->group(function () { Route::get('/', [AdminController::class, 'index'])->name('admin.dashboard'); + + // Booking management routes Route::get('/bookings', [BookingsController::class, 'index'])->name('admin.bookings.index'); Route::get('/bookings/export', [BookingsController::class, 'export'])->name('admin.bookings.export'); Route::get('/bookings/{id}', [BookingsController::class, 'show'])->name('admin.bookings.show'); @@ -80,7 +83,7 @@ Route::patch('/bookings/{id}/complete', [BookingsController::class, 'complete'])->name('admin.bookings.complete'); Route::patch('/bookings/{id}/cancel', [BookingsController::class, 'cancel'])->name('admin.bookings.cancel'); - // CRUD routes untuk manajemen meja + // Table management routes Route::get('/tables', [TableController::class, 'index'])->name('admin.tables.index'); Route::get('/tables/create', [TableController::class, 'create'])->name('admin.tables.create'); Route::post('/tables', [TableController::class, 'store'])->name('admin.tables.store'); @@ -88,7 +91,12 @@ Route::put('/tables/{id}', [TableController::class, 'update'])->name('admin.tables.update'); Route::delete('/tables/{id}', [TableController::class, 'destroy'])->name('admin.tables.destroy'); - // CRUD routes untuk revenue + // Venue management routes + Route::get('/venue', [AdminVenueController::class, 'index'])->name('admin.venue.index'); + Route::get('/venue/edit', [AdminVenueController::class, 'edit'])->name('admin.venue.edit'); + Route::put('/venue/update', [AdminVenueController::class, 'update'])->name('admin.venue.update'); + + // Revenue management routes Route::get('/revenues', [RevenueController::class, 'index'])->name('admin.revenues.index'); Route::get('/revenues/detail/{tableId}', [RevenueController::class, 'detail'])->name('admin.revenues.detail'); Route::get('/revenues/export', [RevenueController::class, 'export'])->name('admin.revenues.export'); @@ -98,7 +106,7 @@ Route::middleware(['auth', 'verified', 'is_superadmin'])->prefix('superadmin')->group(function () { Route::get('/', [App\Http\Controllers\superadmin\SuperAdminController::class, 'index'])->name('superadmin.dashboard'); - // Tambahkan route untuk manajemen Admin + // Admin management routes Route::get('/admin', [AdminManagementController::class, 'index'])->name('superadmin.admin.index'); Route::get('/admin/create', [AdminManagementController::class, 'create'])->name('superadmin.admin.create'); Route::post('/admin', [AdminManagementController::class, 'store'])->name('superadmin.admin.store'); @@ -106,11 +114,11 @@ Route::put('/admin/{id}', [AdminManagementController::class, 'update'])->name('superadmin.admin.update'); Route::delete('/admin/{id}', [AdminManagementController::class, 'destroy'])->name('superadmin.admin.destroy'); - // Tambahkan route untuk manajemen Venue + // Venue management routes (for superadmin) Route::get('/venue', [VenueManagementController::class, 'index'])->name('superadmin.venue.index'); Route::get('/venue/create', [VenueManagementController::class, 'create'])->name('superadmin.venue.create'); Route::post('/venue', [VenueManagementController::class, 'store'])->name('superadmin.venue.store'); Route::get('/venue/{id}/edit', [VenueManagementController::class, 'edit'])->name('superadmin.venue.edit'); Route::put('/venue/{id}', [VenueManagementController::class, 'update'])->name('superadmin.venue.update'); Route::delete('/venue/{id}', [VenueManagementController::class, 'destroy'])->name('superadmin.venue.destroy'); -}); +}); \ No newline at end of file