Files
Verde-Web/resources/views/store/dashboard.blade.php

156 lines
7.8 KiB
PHP

@extends('store.layouts.app', ['pageTitle' => 'Dashboard', 'pageSubtitle' => 'Business overview'])
@section('page')
<div class="space-y-8">
{{-- KPI Grid --}}
<div class="grid grid-cols-1 gap-4 sm:grid-cols-2 lg:grid-cols-4">
<div class="rounded-xl border border-neutral-200 bg-white p-6 shadow-sm">
<div class="flex items-center gap-4">
<div class="flex h-10 w-10 items-center justify-center rounded-lg bg-verde-50 text-verde-600">
<i data-lucide="package" class="h-5 w-5"></i>
</div>
<div>
<p class="text-xs font-medium text-neutral-500 uppercase tracking-wider">Inventory Balance</p>
<p id="kpi-inventory" class="text-2xl font-bold text-neutral-900">...</p>
</div>
</div>
</div>
<div class="rounded-xl border border-neutral-200 bg-white p-6 shadow-sm">
<div class="flex items-center gap-4">
<div class="flex h-10 w-10 items-center justify-center rounded-lg bg-blue-50 text-blue-600">
<i data-lucide="barcode" class="h-5 w-5"></i>
</div>
<div>
<p class="text-xs font-medium text-neutral-500 uppercase tracking-wider">Total Sales</p>
<p id="kpi-sales-count" class="text-2xl font-bold text-neutral-900">...</p>
</div>
</div>
</div>
<div class="rounded-xl border border-neutral-200 bg-white p-6 shadow-sm">
<div class="flex items-center gap-4">
<div class="flex h-10 w-10 items-center justify-center rounded-lg bg-emerald-50 text-emerald-600">
<i data-lucide="trending-up" class="h-5 w-5"></i>
</div>
<div>
<p class="text-xs font-medium text-neutral-500 uppercase tracking-wider">Commissions Earned</p>
<p id="kpi-commission" class="text-2xl font-bold text-neutral-900">...</p>
</div>
</div>
</div>
<div class="rounded-xl border border-neutral-200 bg-white p-6 shadow-sm">
<div class="flex items-center gap-4">
<div class="flex h-10 w-10 items-center justify-center rounded-lg bg-orange-50 text-orange-600">
<i data-lucide="wallet" class="h-5 w-5"></i>
</div>
<div>
<p class="text-xs font-medium text-neutral-500 uppercase tracking-wider">Amount Owed</p>
<p id="kpi-owed" class="text-2xl font-bold text-neutral-900">...</p>
</div>
</div>
</div>
</div>
{{-- Main Content Grid --}}
<div class="grid grid-cols-1 gap-8 lg:grid-cols-2">
{{-- Recent Sales --}}
<div class="rounded-xl border border-neutral-200 bg-white shadow-sm overflow-hidden">
<div class="border-b border-neutral-100 px-6 py-4 flex items-center justify-between bg-neutral-50/30">
<h3 class="font-semibold text-neutral-900">Recent Sales</h3>
<a href="/store/sales" class="text-xs font-medium text-verde-600 hover:text-verde-700">View all</a>
</div>
<div class="overflow-x-auto">
<table class="w-full text-left text-sm">
<thead>
<tr class="border-b border-neutral-100 bg-neutral-50/50 text-[10px] font-bold uppercase tracking-wider text-neutral-400">
<th class="px-6 py-3">Date</th>
<th class="px-6 py-3">Resident</th>
<th class="px-6 py-3">Qty</th>
<th class="px-6 py-3 text-right">Total</th>
</tr>
</thead>
<tbody id="recent-sales-body" class="divide-y divide-neutral-100">
<tr>
<td colspan="4" class="px-6 py-8 text-center text-neutral-400">Loading history...</td>
</tr>
</tbody>
</table>
</div>
</div>
{{-- Actions Card --}}
<div class="flex flex-col gap-4">
<div class="rounded-xl border border-neutral-200 bg-verde-700 p-6 text-white shadow-md">
<h3 class="text-lg font-bold">Record a New Sale</h3>
<p class="mt-1 text-sm text-verde-100">Instantly register QR code sales to residents.</p>
<a href="/store/sales" class="mt-6 inline-flex items-center gap-2 rounded-lg bg-white px-4 py-2 text-sm font-bold text-verde-700 shadow-sm transition-transform hover:scale-105 active:scale-95">
<i data-lucide="plus-circle" class="h-4 w-4"></i>
<span>Start Transaction</span>
</a>
</div>
<div class="rounded-xl border border-neutral-200 bg-white p-6 shadow-sm">
<h3 class="font-semibold text-neutral-900">Need Inventory?</h3>
<p class="mt-1 text-xs text-neutral-500">Contact your LGU Admin to issue new wholesale QR code batches to your store.</p>
<div class="mt-4 flex items-center gap-2 text-xs font-medium text-neutral-900">
<i data-lucide="info" class="h-4 w-4 text-neutral-400"></i>
<span>Inventory is currently admin-managed.</span>
</div>
</div>
</div>
</div>
</div>
<script type="module">
document.addEventListener('DOMContentLoaded', async () => {
const formatMoney = (centavos) => {
return new Intl.NumberFormat('en-PH', { style: 'currency', currency: 'PHP' }).format(centavos / 100);
};
try {
// Fetch Dashboard Stats
const dashRes = await window.Verde.apiFetch('/api/v1/store/dashboard');
const dash = dashRes.body?.data;
if (dash) {
document.getElementById('kpi-inventory').textContent = dash.inventory_balance;
document.getElementById('kpi-sales-count').textContent = dash.total_sales_count;
}
// Fetch Financials
const finRes = await window.Verde.apiFetch('/api/v1/store/analytics');
const fin = finRes.body?.data;
if (fin) {
document.getElementById('kpi-commission').textContent = formatMoney(fin.total_commission_earned_centavos);
document.getElementById('kpi-owed').textContent = formatMoney(fin.amount_owed_to_lgu_centavos);
}
// Fetch Recent Sales
const salesRes = await window.Verde.apiFetch('/api/v1/store/sales?limit=5');
const sales = salesRes.body?.data?.data || [];
const tbody = document.getElementById('recent-sales-body');
if (sales.length === 0) {
tbody.innerHTML = '<tr><td colspan="4" class="px-6 py-8 text-center text-neutral-400">No sales recorded yet.</td></tr>';
} else {
tbody.innerHTML = sales.map(sale => `
<tr class="hover:bg-neutral-50/50">
<td class="px-6 py-4 text-xs text-neutral-500">${new Date(sale.created_at).toLocaleDateString()}</td>
<td class="px-6 py-4 font-medium text-neutral-900">${sale.household?.head?.full_name || 'N/A'}</td>
<td class="px-6 py-4 text-neutral-600">${sale.quantity}</td>
<td class="px-6 py-4 text-right font-semibold text-neutral-900">${formatMoney(sale.retail_price_centavos)}</td>
</tr>
`).join('');
}
if (window.lucide) window.lucide.createIcons();
} catch (e) {
console.error('Dashboard load failed', e);
}
});
</script>
@endsection