libra/resources/views/livewire/admin/clients/individual/index.blade.php

213 lines
10 KiB
PHP

<?php
use App\Enums\UserStatus;
use App\Models\User;
use Livewire\Volt\Component;
use Livewire\WithPagination;
new class extends Component {
use WithPagination;
public string $search = '';
public string $statusFilter = '';
public int $perPage = 10;
public function updatedSearch(): void
{
$this->resetPage();
}
public function updatedStatusFilter(): void
{
$this->resetPage();
}
public function updatedPerPage(): void
{
$this->resetPage();
}
public function clearFilters(): void
{
$this->search = '';
$this->statusFilter = '';
$this->resetPage();
}
public function with(): array
{
return [
'clients' => User::individual()
->when($this->search, fn ($q) => $q->where(function ($q) {
$q->where('full_name', 'like', "%{$this->search}%")
->orWhere('email', 'like', "%{$this->search}%")
->orWhere('national_id', 'like', "%{$this->search}%");
}))
->when($this->statusFilter, fn ($q) => $q->where('status', $this->statusFilter))
->latest()
->paginate($this->perPage),
'statuses' => UserStatus::cases(),
];
}
}; ?>
<div>
<div class="page-header mb-6">
<div>
<flux:heading size="xl" class="text-xl sm:text-2xl">{{ __('clients.individual_clients') }}</flux:heading>
<flux:text class="mt-1 text-zinc-500 dark:text-zinc-400">{{ __('clients.clients') }}</flux:text>
</div>
<div class="header-actions">
<flux:button :href="route('admin.users.export')" wire:navigate icon="arrow-down-tray" class="w-full sm:w-auto justify-center">
{{ __('export.export_users') }}
</flux:button>
<flux:button variant="primary" :href="route('admin.clients.individual.create')" wire:navigate icon="plus" class="w-full sm:w-auto justify-center">
{{ __('clients.create_client') }}
</flux:button>
</div>
</div>
<div class="mb-6 rounded-lg border border-zinc-200 bg-white p-4 dark:border-zinc-700 dark:bg-zinc-800">
<div class="flex flex-col gap-4 sm:flex-row sm:items-end">
<div class="flex-1">
<flux:input
wire:model.live.debounce.300ms="search"
:placeholder="__('clients.search_placeholder')"
icon="magnifying-glass"
/>
</div>
<div class="w-full sm:w-48">
<flux:select wire:model.live="statusFilter">
<flux:select.option value="">{{ __('clients.all_statuses') }}</flux:select.option>
@foreach ($statuses as $status)
<flux:select.option value="{{ $status->value }}">
{{ __('clients.' . $status->value) }}
</flux:select.option>
@endforeach
</flux:select>
</div>
<div class="w-full sm:w-32">
<flux:select wire:model.live="perPage">
<flux:select.option value="10">10 {{ __('clients.per_page') }}</flux:select.option>
<flux:select.option value="25">25 {{ __('clients.per_page') }}</flux:select.option>
<flux:select.option value="50">50 {{ __('clients.per_page') }}</flux:select.option>
</flux:select>
</div>
@if ($search || $statusFilter)
<flux:button wire:click="clearFilters" variant="ghost" icon="x-mark">
{{ __('clients.clear_filters') }}
</flux:button>
@endif
</div>
</div>
<div class="overflow-hidden rounded-lg border border-zinc-200 bg-white dark:border-zinc-700 dark:bg-zinc-800">
<div class="table-scroll-wrapper">
<table class="min-w-full divide-y divide-zinc-200 dark:divide-zinc-700">
<thead class="bg-zinc-50 dark:bg-zinc-900">
<tr>
<th class="px-6 py-3 text-start text-xs font-medium uppercase tracking-wider text-zinc-500 dark:text-zinc-400">
{{ __('clients.full_name') }}
</th>
<th class="px-6 py-3 text-start text-xs font-medium uppercase tracking-wider text-zinc-500 dark:text-zinc-400">
{{ __('clients.email') }}
</th>
<th class="px-6 py-3 text-start text-xs font-medium uppercase tracking-wider text-zinc-500 dark:text-zinc-400">
{{ __('clients.national_id') }}
</th>
<th class="px-6 py-3 text-start text-xs font-medium uppercase tracking-wider text-zinc-500 dark:text-zinc-400">
{{ __('clients.phone') }}
</th>
<th class="px-6 py-3 text-start text-xs font-medium uppercase tracking-wider text-zinc-500 dark:text-zinc-400">
{{ __('clients.status') }}
</th>
<th class="px-6 py-3 text-start text-xs font-medium uppercase tracking-wider text-zinc-500 dark:text-zinc-400">
{{ __('clients.created_at') }}
</th>
<th class="px-6 py-3 text-end text-xs font-medium uppercase tracking-wider text-zinc-500 dark:text-zinc-400">
{{ __('clients.actions') }}
</th>
</tr>
</thead>
<tbody class="divide-y divide-zinc-200 bg-white dark:divide-zinc-700 dark:bg-zinc-800">
@forelse ($clients as $client)
<tr wire:key="client-{{ $client->id }}">
<td class="whitespace-nowrap px-6 py-4">
<div class="flex items-center gap-3">
<flux:avatar size="sm" :name="$client->full_name" />
<span class="font-medium text-zinc-900 dark:text-zinc-100">{{ $client->full_name }}</span>
</div>
</td>
<td class="whitespace-nowrap px-6 py-4 text-zinc-600 dark:text-zinc-400">
{{ $client->email }}
</td>
<td class="whitespace-nowrap px-6 py-4 text-zinc-600 dark:text-zinc-400">
{{ $client->national_id }}
</td>
<td class="whitespace-nowrap px-6 py-4 text-zinc-600 dark:text-zinc-400">
{{ $client->phone }}
</td>
<td class="whitespace-nowrap px-6 py-4">
@if ($client->status === UserStatus::Active)
<flux:badge color="green" size="sm">{{ __('clients.active') }}</flux:badge>
@else
<flux:badge color="red" size="sm">{{ __('clients.deactivated') }}</flux:badge>
@endif
</td>
<td class="whitespace-nowrap px-6 py-4 text-zinc-600 dark:text-zinc-400">
{{ $client->created_at->format('Y-m-d') }}
</td>
<td class="whitespace-nowrap px-6 py-4 text-end">
<div class="flex items-center justify-end gap-2">
<flux:button
variant="ghost"
size="sm"
icon="eye"
:href="route('admin.clients.individual.show', $client)"
wire:navigate
:title="__('clients.view')"
/>
<flux:button
variant="ghost"
size="sm"
icon="pencil"
:href="route('admin.clients.individual.edit', $client)"
wire:navigate
:title="__('clients.edit')"
/>
</div>
</td>
</tr>
@empty
<tr>
<td colspan="7" class="px-6 py-12 text-center">
<div class="flex flex-col items-center">
<flux:icon name="users" class="mb-4 h-12 w-12 text-zinc-400" />
<flux:text class="text-zinc-500 dark:text-zinc-400">
@if ($search || $statusFilter)
{{ __('clients.no_clients_match') }}
@else
{{ __('clients.no_clients_found') }}
@endif
</flux:text>
@if ($search || $statusFilter)
<flux:button wire:click="clearFilters" variant="ghost" class="mt-4">
{{ __('clients.clear_filters') }}
</flux:button>
@endif
</div>
</td>
</tr>
@endforelse
</tbody>
</table>
</div>
@if ($clients->hasPages())
<div class="border-t border-zinc-200 bg-zinc-50 px-6 py-4 dark:border-zinc-700 dark:bg-zinc-900">
{{ $clients->links() }}
</div>
@endif
</div>
</div>