Skip to content
Merged

f #6

Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
63 changes: 63 additions & 0 deletions app/Console/Commands/MakeAdmin.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,63 @@
<?php

namespace App\Console\Commands;

use Illuminate\Console\Command;

class MakeAdmin extends Command
{
/**
* The name and signature of the console command.
*
* @var string
*/
protected $signature = 'admin:create {email?} {name?} {password?}';

/**
* The console command description.
*
* @var string
*/
protected $description = 'Create or update a user with admin privileges';

/**
* Execute the console command.
*/
public function handle()
{
$email = $this->argument('email') ?? $this->ask('Enter email address');
$name = $this->argument('name') ?? $this->ask('Enter name');
$password = $this->argument('password') ?? $this->secret('Enter password');

if (!filter_var($email, FILTER_VALIDATE_EMAIL)) {
$this->error('Invalid email address');
return 1;
}

if (strlen($password) < 8) {
$this->error('Password must be at least 8 characters');
return 1;
}

$user = \App\Models\User::where('email', $email)->first();

if ($user) {
$user->update([
'name' => $name,
'password' => bcrypt($password),
'is_admin' => true,
]);
$this->info("User {$email} has been updated and granted admin privileges.");
} else {
\App\Models\User::create([
'name' => $name,
'email' => $email,
'password' => bcrypt($password),
'is_admin' => true,
]);
$this->info("Admin user {$email} has been created successfully.");
}

return 0;
}
}
88 changes: 88 additions & 0 deletions app/Http/Controllers/Admin/ExperienceController.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,88 @@
<?php

namespace App\Http\Controllers\Admin;

use App\Http\Controllers\Controller;
use App\Models\Experience;
use Illuminate\Http\Request;

class ExperienceController extends Controller
{
/**
* Store a newly created experience.
*/
public function store(Request $request)
{
$validated = $request->validate([
'title' => 'required|string|max:255',
'description' => 'required|string',
'image' => 'required|image|max:5120', // 5MB max
'alt_text' => 'required|string|max:255',
'badge' => 'nullable|string|max:255',
'icon' => 'nullable|string',
'order' => 'required|integer|min:0',
]);

// Handle image upload
$image = $request->file('image');
$filename = time() . '_' . preg_replace('/[^a-z0-9_]/', '', str_replace(' ', '_', strtolower($validated['title']))) . '.' . $image->getClientOriginalExtension();
$image->move(public_path('images/experiences'), $filename);

Experience::create([
'title' => $validated['title'],
'description' => $validated['description'],
'image_url' => '/images/experiences/' . $filename,
'alt_text' => $validated['alt_text'],
'badge' => $validated['badge'] ?? null,
'icon' => $validated['icon'] ?? null,
'order' => $validated['order'],
]);

return redirect()->route('admin.experiences.index')->with('success', 'Experience created successfully.');
}

/**
* Update the specified experience.
*/
public function update(Request $request, $id)
{
$experience = Experience::findOrFail($id);

$rules = [
'title' => 'required|string|max:255',
'description' => 'required|string',
'alt_text' => 'required|string|max:255',
'badge' => 'nullable|string|max:255',
'icon' => 'nullable|string',
'order' => 'required|integer|min:0',
];

// Image is optional on update
if ($request->hasFile('image')) {
$rules['image'] = 'image|max:5120';
}

$validated = $request->validate($rules);

// Handle image upload if provided
$imageUrl = $experience->image_url;
if ($request->hasFile('image')) {
$image = $request->file('image');
$filename = time() . '_' . preg_replace('/[^a-z0-9_]/', '', str_replace(' ', '_', strtolower($validated['title']))) . '.' . $image->getClientOriginalExtension();
$image->move(public_path('images/experiences'), $filename);
$imageUrl = '/images/experiences/' . $filename;
}

$experience->update([
'title' => $validated['title'],
'description' => $validated['description'],
'image_url' => $imageUrl,
'alt_text' => $validated['alt_text'],
'badge' => $validated['badge'] ?? null,
'icon' => $validated['icon'] ?? null,
'order' => $validated['order'],
]);

return redirect()->route('admin.experiences.index')->with('success', 'Experience updated successfully.');
}
}
107 changes: 107 additions & 0 deletions app/Http/Controllers/Admin/MapPointController.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,107 @@
<?php

namespace App\Http\Controllers\Admin;

use App\Http\Controllers\Controller;
use App\Models\MapPoint;
use Illuminate\Http\Request;

class MapPointController extends Controller
{
/**
* Store a newly created map point.
*/
public function store(Request $request)
{
$validated = $request->validate([
'name' => 'required|string|max:255',
'description' => 'required|string',
'image' => 'required|image|max:5120',
'icon_file' => 'nullable|image|max:2048', // Uploaded icon
'center_x' => 'required|integer',
'center_y' => 'required|integer',
'coords' => 'required|string', // Will be auto-generated
]);

// Handle image upload
$image = $request->file('image');
$imageName = time() . '_point_' . preg_replace('/[^a-z0-9_]/', '', str_replace(' ', '_', strtolower($validated['name']))) . '.' . $image->getClientOriginalExtension();
$image->move(public_path('images/map-points'), $imageName);

// Handle icon upload
$iconHtml = null;
if ($request->hasFile('icon_file')) {
$icon = $request->file('icon_file');
$iconName = time() . '_icon_' . preg_replace('/[^a-z0-9_]/', '', str_replace(' ', '_', strtolower($validated['name']))) . '.' . $icon->getClientOriginalExtension();
$icon->move(public_path('images/icons'), $iconName);
// Create the HTML for the icon as expected by the frontend
$iconHtml = '<img src="/images/icons/' . $iconName . '" class="w-full h-full object-contain" alt="' . $validated['name'] . ' Icon">';
}

MapPoint::create([
'name' => $validated['name'],
'description' => $validated['description'],
'image_url' => '/images/map-points/' . $imageName,
'coords' => $validated['coords'],
'center_x' => $validated['center_x'],
'center_y' => $validated['center_y'],
'icon' => $iconHtml,
]);

return redirect()->route('admin.map-points.index')->with('success', 'Map point created successfully.');
}

/**
* Update the specified map point.
*/
public function update(Request $request, $id)
{
$mapPoint = MapPoint::findOrFail($id);

$rules = [
'name' => 'required|string|max:255',
'description' => 'required|string',
'center_x' => 'required|integer',
'center_y' => 'required|integer',
'coords' => 'required|string',
];

if ($request->hasFile('image')) {
$rules['image'] = 'image|max:5120';
}

if ($request->hasFile('icon_file')) {
$rules['icon_file'] = 'image|max:2048';
}

$validated = $request->validate($rules);

$data = [
'name' => $validated['name'],
'description' => $validated['description'],
'center_x' => $validated['center_x'],
'center_y' => $validated['center_y'],
'coords' => $validated['coords'],
];

// Handle image upload
if ($request->hasFile('image')) {
$image = $request->file('image');
$imageName = time() . '_point_' . preg_replace('/[^a-z0-9_]/', '', str_replace(' ', '_', strtolower($validated['name']))) . '.' . $image->getClientOriginalExtension();
$image->move(public_path('images/map-points'), $imageName);
$data['image_url'] = '/images/map-points/' . $imageName;
}

// Handle icon upload
if ($request->hasFile('icon_file')) {
$icon = $request->file('icon_file');
$iconName = time() . '_icon_' . preg_replace('/[^a-z0-9_]/', '', str_replace(' ', '_', strtolower($validated['name']))) . '.' . $icon->getClientOriginalExtension();
$icon->move(public_path('images/icons'), $iconName);
$data['icon'] = '<img src="/images/icons/' . $iconName . '" class="w-full h-full object-contain" alt="' . $validated['name'] . ' Icon">';
}

$mapPoint->update($data);

return redirect()->route('admin.map-points.index')->with('success', 'Map point updated successfully.');
}
}
117 changes: 117 additions & 0 deletions app/Http/Controllers/Admin/RoomController.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,117 @@
<?php

namespace App\Http\Controllers\Admin;

use App\Http\Controllers\Controller;
use App\Models\Room;
use Illuminate\Http\Request;

class RoomController extends Controller
{
/**
* Store a newly created room.
*/
public function store(Request $request)
{
$validated = $request->validate([
'floor_id' => 'required|string',
'floor_view' => 'required|string|max:255',
// 'floor_coords' => 'required|string', // Removed
// 'floor_name' => 'required|string', // Auto-generated
'room_number' => 'required|integer',
'room_name' => 'required|string|max:255',
'price' => 'required|string|max:255',
'description' => 'required|string',
'image' => 'required|image|max:5120',
'order' => 'required|integer|min:0',
]);

// Handle image upload
$image = $request->file('image');
$imageName = time() . '_room_' . $validated['room_number'] . '.' . $image->getClientOriginalExtension();
$image->move(public_path('images/rooms'), $imageName);

// Map floor_id to floor_name
$floorNames = [
'ground' => 'Ground Floor',
'first' => 'First Floor',
'second' => 'Second Floor',
'third' => 'Third Floor',
];
$floorName = $floorNames[$validated['floor_id']] ?? ucfirst($validated['floor_id']) . ' Floor';

// Default empty coords
$floorCoords = '';

Room::create([
'floor_id' => $validated['floor_id'],
'floor_name' => $floorName,
'floor_view' => $validated['floor_view'],
'floor_coords' => $floorCoords,
'room_number' => $validated['room_number'],
'room_name' => $validated['room_name'],
'price' => $validated['price'],
'description' => $validated['description'],
'image_url' => '/images/rooms/' . $imageName,
'order' => $validated['order'],
]);

return redirect()->route('admin.rooms.index')->with('success', 'Room created successfully.');
}

/**
* Update the specified room.
*/
public function update(Request $request, $id)
{
$room = Room::findOrFail($id);

$rules = [
'floor_id' => 'required|string',
'floor_view' => 'required|string|max:255',
'room_number' => 'required|integer',
'room_name' => 'required|string|max:255',
'price' => 'required|string|max:255',
'description' => 'required|string',
'order' => 'required|integer|min:0',
];

if ($request->hasFile('image')) {
$rules['image'] = 'image|max:5120';
}

$validated = $request->validate($rules);

// Map floor_id to floor_name if needed (though existing might be fine, let's update it to stay synced)
$floorNames = [
'ground' => 'Ground Floor',
'first' => 'First Floor',
'second' => 'Second Floor',
'third' => 'Third Floor',
];
$floorName = $floorNames[$validated['floor_id']] ?? ucfirst($validated['floor_id']) . ' Floor';

$data = [
'floor_id' => $validated['floor_id'],
'floor_name' => $floorName,
'floor_view' => $validated['floor_view'],
'room_number' => $validated['room_number'],
'room_name' => $validated['room_name'],
'price' => $validated['price'],
'description' => $validated['description'],
'order' => $validated['order'],
];

// Handle image upload
if ($request->hasFile('image')) {
$image = $request->file('image');
$imageName = time() . '_room_' . $validated['room_number'] . '.' . $image->getClientOriginalExtension();
$image->move(public_path('images/rooms'), $imageName);
$data['image_url'] = '/images/rooms/' . $imageName;
}

$room->update($data);

return redirect()->route('admin.rooms.index')->with('success', 'Room updated successfully.');
}
}
Loading
Loading