sackey e3b2b220d2
Some checks are pending
linter / quality (push) Waiting to run
tests / ci (push) Waiting to run
Enhance UI and functionality across various components
- Increased icon sizes in service items, service orders, users, and technician management for better visibility.
- Added custom loading indicators with appropriate icons in search fields for vehicles, work orders, and technicians.
- Introduced invoice management routes for better organization and access control.
- Created a new test for the estimate PDF functionality to ensure proper rendering and data integrity.
2025-08-16 14:36:58 +00:00

231 lines
13 KiB
PHP

<div class="space-y-6">
<!-- Header -->
<div class="flex items-center justify-between">
<flux:heading size="xl">Vehicle Management</flux:heading>
<flux:button href="/vehicles/create" size="sm">
<flux:icon name="plus" class="size-4" />
Add New Vehicle
</flux:button>
</div>
<!-- Flash Messages -->
@if (session()->has('success'))
<div class="bg-green-50 border border-green-200 text-green-800 rounded-md p-4">
<div class="flex">
<flux:icon name="check-circle" class="h-5 w-5 text-green-400" />
<div class="ml-3">
<p class="text-sm font-medium">{{ session('success') }}</p>
</div>
</div>
</div>
@endif
@if (session()->has('error'))
<div class="bg-red-50 border border-red-200 text-red-800 rounded-md p-4">
<div class="flex">
<flux:icon name="exclamation-circle" class="h-5 w-5 text-red-400" />
<div class="ml-3">
<p class="text-sm font-medium">{{ session('error') }}</p>
</div>
</div>
</div>
@endif
<!-- Filters -->
<div class="bg-white dark:bg-zinc-800 rounded-lg border border-zinc-200 dark:border-zinc-700">
<div class="grid grid-cols-1 md:grid-cols-4 gap-4 p-4">
<div class="relative">
<flux:input
wire:model.live="search"
placeholder="Search vehicles..."
icon="magnifying-glass"
:loading="false"
/>
<!-- Custom loading indicator with truck icon -->
<div wire:loading wire:target="search" class="absolute right-3 top-1/2 transform -translate-y-1/2">
<flux:icon.truck class="w-6 h-6 text-zinc-400 animate-bounce" />
</div>
</div>
<select wire:model.live="customer_id" class="rounded-md border border-zinc-300 dark:border-zinc-600 bg-white dark:bg-zinc-800 px-3 py-2 text-sm focus:border-blue-500 focus:outline-none focus:ring-1 focus:ring-2 focus:ring-blue-500">
<option value="">All Customers</option>
@foreach($customers as $customer)
<option value="{{ $customer->id }}">{{ $customer->full_name }}</option>
@endforeach
</select>
<select wire:model.live="make" class="rounded-md border border-zinc-300 dark:border-zinc-600 bg-white dark:bg-zinc-800 px-3 py-2 text-sm focus:border-blue-500 focus:outline-none focus:ring-1 focus:ring-2 focus:ring-blue-500">
<option value="">All Makes</option>
@foreach($makes as $make)
<option value="{{ $make }}">{{ $make }}</option>
@endforeach
</select>
<select wire:model.live="status" class="rounded-md border border-zinc-300 dark:border-zinc-600 bg-white dark:bg-zinc-800 px-3 py-2 text-sm focus:border-blue-500 focus:outline-none focus:ring-1 focus:ring-2 focus:ring-blue-500">
<option value="">All Statuses</option>
<option value="active">Active</option>
<option value="inactive">Inactive</option>
<option value="sold">Sold</option>
</select>
</div>
</div>
<!-- Vehicles Table -->
<div class="bg-white dark:bg-zinc-800 rounded-lg border border-zinc-200 dark:border-zinc-700">
<div class="overflow-x-auto">
<table class="min-w-full">
<thead>
<tr class="border-b border-zinc-200 dark:border-zinc-700">
<th class="text-left py-3 px-4">
<button wire:click="sortBy('year')" class="flex items-center space-x-1 hover:text-blue-600">
<span>Vehicle</span>
@if($sortBy === 'year')
<flux:icon name="{{ $sortDirection === 'asc' ? 'chevron-up' : 'chevron-down' }}" class="size-3" />
@endif
</button>
</th>
<th class="text-left py-3 px-4">
<button wire:click="sortBy('customer_id')" class="flex items-center space-x-1 hover:text-blue-600">
<span>Owner</span>
@if($sortBy === 'customer_id')
<flux:icon name="{{ $sortDirection === 'asc' ? 'chevron-up' : 'chevron-down' }}" class="size-3" />
@endif
</button>
</th>
<th class="text-left py-3 px-4">VIN</th>
<th class="text-left py-3 px-4">License Plate</th>
<th class="text-left py-3 px-4">
<button wire:click="sortBy('mileage')" class="flex items-center space-x-1 hover:text-blue-600">
<span>Mileage</span>
@if($sortBy === 'mileage')
<flux:icon name="{{ $sortDirection === 'asc' ? 'chevron-up' : 'chevron-down' }}" class="size-3" />
@endif
</button>
</th>
<th class="text-left py-3 px-4">
<button wire:click="sortBy('last_service_date')" class="flex items-center space-x-1 hover:text-blue-600">
<span>Last Service</span>
@if($sortBy === 'last_service_date')
<flux:icon name="{{ $sortDirection === 'asc' ? 'chevron-up' : 'chevron-down' }}" class="size-3" />
@endif
</button>
</th>
<th class="text-left py-3 px-4">Status</th>
<th class="text-left py-3 px-4">Actions</th>
</tr>
</thead>
<tbody>
@forelse($vehicles as $vehicle)
<tr class="border-b border-zinc-200 dark:border-zinc-700 hover:bg-zinc-50 dark:hover:bg-zinc-700">
<td class="py-3 px-4">
<div class="flex items-center space-x-3">
<div>
<div class="font-medium">{{ $vehicle->display_name }}</div>
<div class="flex items-center space-x-2 text-sm text-zinc-500 dark:text-zinc-400">
<div
class="w-6 h-6 rounded border border-zinc-300 dark:border-zinc-600"
style="background-color: {{ $vehicle->color }}"
title="{{ $vehicle->color }}"
></div>
<span>{{ $vehicle->color }}</span>
</div>
</div>
</div>
</td>
<td class="py-3 px-4">
<div>
<div class="text-sm">{{ $vehicle->customer->full_name }}</div>
<div class="text-sm text-zinc-500 dark:text-zinc-400">ID: {{ $vehicle->customer->id }}</div>
</div>
</td>
<td class="py-3 px-4">
<div class="text-sm font-mono">{{ $vehicle->vin_display }}</div>
</td>
<td class="py-3 px-4">
<div class="text-sm">{{ $vehicle->license_plate }}</div>
</td>
<td class="py-3 px-4">
<div class="text-sm">{{ number_format($vehicle->mileage) }} mi</div>
</td>
<td class="py-3 px-4">
<div class="text-sm">
@if($vehicle->last_service_date)
{{ $vehicle->last_service_date->format('M j, Y') }}
@else
<span class="text-gray-400">Never</span>
@endif
</div>
</td>
<td class="py-3 px-4">
<flux:badge
:color="$vehicle->status === 'active' ? 'green' : ($vehicle->status === 'sold' ? 'blue' : 'gray')"
size="sm"
>
{{ ucfirst($vehicle->status) }}
</flux:badge>
</td>
<td class="py-3 px-4">
<div class="flex space-x-2">
<flux:button href="/vehicles/{{ $vehicle->id }}" variant="outline" size="sm">
View
</flux:button>
<flux:button href="/vehicles/{{ $vehicle->id }}/edit" variant="outline" size="sm">
Edit
</flux:button>
<flux:button href="/service-orders/create?vehicle={{ $vehicle->id }}" size="sm">
Service
</flux:button>
<flux:button
wire:click="deleteVehicle({{ $vehicle->id }})"
wire:confirm="Are you sure you want to delete {{ $vehicle->display_name }}? This action cannot be undone."
variant="danger"
size="sm"
>
Delete
</flux:button>
</div>
</td>
</tr>
@empty
<tr>
<td colspan="8" class="text-center py-8 text-zinc-500 dark:text-zinc-400">
@if($search)
No vehicles found matching "{{ $search }}"
@else
No vehicles found. <a href="/vehicles/create" class="text-blue-600 hover:underline">Add your first vehicle</a>
@endif
</td>
</tr>
@endforelse
</tbody>
</table>
</div>
@if($vehicles->hasPages())
<div class="mt-4 px-4 pb-4">
{{ $vehicles->links() }}
</div>
@endif
</div>
<!-- Quick Stats -->
<div class="grid grid-cols-1 md:grid-cols-4 gap-4">
<div class="bg-white dark:bg-zinc-800 rounded-lg border border-zinc-200 dark:border-zinc-700 p-4">
<div class="text-2xl font-bold text-blue-600">{{ $vehicles->total() }}</div>
<div class="text-sm text-zinc-600 dark:text-zinc-400">Total Vehicles</div>
</div>
<div class="bg-white dark:bg-zinc-800 rounded-lg border border-zinc-200 dark:border-zinc-700 p-4">
<div class="text-2xl font-bold text-green-600">{{ $vehicles->where('status', 'active')->count() }}</div>
<div class="text-sm text-zinc-600 dark:text-zinc-400">Active Vehicles</div>
</div>
<div class="bg-white dark:bg-zinc-800 rounded-lg border border-zinc-200 dark:border-zinc-700 p-4">
<div class="text-2xl font-bold text-orange-600">{{ $makes->count() }}</div>
<div class="text-sm text-zinc-600 dark:text-zinc-400">Different Makes</div>
</div>
<div class="bg-white dark:bg-zinc-800 rounded-lg border border-zinc-200 dark:border-zinc-700 p-4">
<div class="text-2xl font-bold text-purple-600">{{ $customers->count() }}</div>
<div class="text-sm text-zinc-600 dark:text-zinc-400">Vehicle Owners</div>
</div>
</div>
</div>