@extends('layouts.dashboard') @section('content') @php /** * Operation Analytics → Customers: who is ordering — new vs returning, guest * share, the channels they arrive through, and the restaurant's best customers. * * @var array $kpis @var array $dayChart @var array $dayMeta @var array $mixChart @var array $mixMeta * @var array $identityChart @var array $identityMeta @var array $sourceChart @var array $sourceMeta * @var array $spendChart @var array $spendMeta @var array $topCustomers @var array $custPager * @var int $rangeDays @var array $rangeLinks @var array $clientLocations */ $loyLabel = (string) ($restaurant['loyalty_points_label'] ?? 'points'); $clientPoints = []; foreach ($clientLocations as $cl) { if ($cl['delivery_lat'] === null || $cl['delivery_lng'] === null) { continue; } $addr = trim((string) ($cl['delivery_address'] ?? '')); $clientPoints[] = [ 'lat' => (float) $cl['delivery_lat'], 'lng' => (float) $cl['delivery_lng'], 'label' => $cl['name'] . ($addr !== '' ? ' — ' . $addr : ''), // The customer's own avatar (or initials monogram) - same brandmark // used everywhere else a person's avatar appears. 'iconHtml' => brandmark_html($cl['avatar'] ?? null, (string) $cl['name'], 'sm'), ]; } $clientMapCenter = $clientPoints ? $clientPoints[0] : ['lat' => 37.7749, 'lng' => -122.4194]; @endphp @php /* .qm-d2: the dashboard density standard (app.css §35) */ @endphp

{{ t_raw('dashboard.sec.snapshot') }}

{{ t_raw('vendor.analytics.subtitle_customers') }}

@foreach ($rangeLinks['options'] as $val => $text) @php $on = ((string) $val === $rangeLinks['selected']); @endphp {{ $text }} @endforeach
@partial('kpi-card', ['variant' => 'panel', 'accent' => 'blue', 'icon' => 'fa-users', 'label' => t_raw('common.customers'), 'value' => number_format($kpis['customers']['value']), 'spark' => $kpis['customers']['spark'], 'meta' => $kpis['customers']['meta']]) @partial('kpi-card', ['variant' => 'panel', 'accent' => 'green', 'icon' => 'fa-user-plus', 'label' => t_raw('vendor.analytics.kpi_new_customers'), 'value' => number_format($kpis['new']['value']), 'meta' => $kpis['new']['meta']]) @partial('kpi-card', ['variant' => 'panel', 'accent' => 'violet', 'icon' => 'fa-redo', 'label' => t_raw('common.returning'), 'value' => number_format($kpis['returning']['value']), 'meta' => $kpis['returning']['meta']]) @partial('kpi-card', ['variant' => 'panel', 'accent' => 'amber', 'icon' => 'fa-user-clock', 'label' => t_raw('common.guest_orders'), 'value' => number_format($kpis['guests']['value']), 'spark' => $kpis['guests']['spark'], 'meta' => $kpis['guests']['meta']]) @php /* Spend per head reads from the covers keyed in at the till; with none recorded the card shows an em-dash rather than dividing by nothing. */ @endphp @partial('kpi-card', ['variant' => 'panel', 'accent' => 'teal', 'icon' => 'fa-user-friends', 'label' => t_raw('vendor.analytics.kpi_spend_per_head'), 'value' => $kpis['perHead']['value'] !== null ? money($kpis['perHead']['value']) : '—', 'spark' => $kpis['perHead']['spark'], 'meta' => $kpis['perHead']['meta']])

{{ t_raw('dashboard.sec.trends') }}

@partial('chart-card', ['heading' => t_raw('vendor.analytics.chart_customers_per_day'), 'sub' => t_raw('vendor.analytics.chart_customers_per_day_caption'), 'cfg' => $dayChart, 'meta' => $dayMeta, 'accent' => 'blue', 'opts' => ['id' => 'custDayChart', 'url' => route('vendor.chart-series', ['chart' => 'custPerDay']), 'selected' => $rangeLinks['selected'], 'options' => $rangeLinks['options'], 'control' => 'compact']])
@partial('chart-card', ['heading' => t_raw('vendor.analytics.chart_new_vs_returning'), 'sub' => t_raw('vendor.analytics.chart_new_vs_returning_caption'), 'cfg' => $mixChart, 'meta' => $mixMeta, 'icon' => 'fa-chart-pie', 'accent' => 'green'])
@partial('chart-card', ['heading' => t_raw('vendor.analytics.chart_account_vs_guest'), 'sub' => t_raw('vendor.analytics.chart_account_vs_guest_sub'), 'cfg' => $identityChart, 'meta' => $identityMeta, 'icon' => 'fa-chart-pie', 'accent' => 'violet'])
@partial('chart-card', ['heading' => t_raw('vendor.analytics.chart_order_channels'), 'sub' => t_raw('vendor.analytics.chart_order_channels_sub'), 'cfg' => $sourceChart, 'meta' => $sourceMeta, 'icon' => 'fa-chart-pie', 'accent' => 'teal'])
@partial('chart-card', ['heading' => t_raw('vendor.analytics.chart_top_customers_spend'), 'sub' => t_raw('vendor.analytics.chart_collected_period_sub'), 'cfg' => $spendChart, 'meta' => $spendMeta, 'icon' => 'fa-chart-bar', 'accent' => 'amber', 'opts' => ['id' => 'custSpendChart', 'url' => route('vendor.chart-series', ['chart' => 'custTop']), 'selected' => $rangeLinks['selected'], 'options' => $rangeLinks['options'], 'control' => 'compact']])

{{ t_raw('dashboard.sec.breakdown') }}

{{ t_raw('vendor.analytics.heading_client_locations') }}

{{ t_raw('vendor.analytics.hint_client_locations') }}

@if ($clientPoints)
@else

{{ t_raw('vendor.analytics.empty_no_client_locations') }}

@endif

{{ t_raw('vendor.analytics.heading_best_customers') }}

@if ($topCustomers) @foreach ($topCustomers as $c) @php $orders = (int) $c['orders_c']; $covers = (int) $c['covers']; @endphp @endforeach @else @partial('table-empty', ['colspan' => 8, 'icon' => 'fa-users', 'msg' => t_raw('vendor.analytics.empty_no_account_customers')]) @endif
{{ t_raw('vendor.analytics.caption_best_customers') }}
{{ t_raw('common.customer') }} {{ t_raw('common.orders') }} {{ t_raw('admin.analytics_customers.col_spend') }} {{ t_raw('common.average_order') }} {{ t_raw('vendor.analytics.kpi_covers') }} {{ t_raw('vendor.analytics.col_per_head') }} {{ t_raw('vendor.analytics.col_loyalty_balance') }} {{ t_raw('vendor.analytics.col_last_order') }}
{!! brandmark_html($c['avatar'] ?? null, (string) $c['name'], 'md', 'qm-brandmark--round') !!}
{{ $c['name'] }} {{ $c['email'] }}
{{ number_format($orders) }} {{ money($c['spend']) }} {!! $orders > 0 ? money((float) $c['spend'] / $orders) : dash() !!} {!! $covers > 0 ? number_format($covers) : dash() !!} {!! $covers > 0 ? money((float) $c['spend'] / $covers) : dash() !!} {!! $c['points'] !== null ? number_format((int) $c['points']) . ' ' . e($loyLabel) : dash() !!} {!! fmt_datetime($c['last_order']) !!}
@partial('table-toolbar', ['pager' => $custPager, 'base' => '/vendor/analytics/customers'])
@php /* /.qm-d2 */ @endphp @endsection