[FEAT] 合併商品統計報表與日期選擇器視覺修復

1. 重構並優化商品統計報表功能,新增利潤分析走勢圖表與大額數據處理。
2. 新增商品銷售排行前 5 名展示,並搭配精緻的尊榮徽章(Gold, Silver, Bronze)設計。
3. 優化資料導出引擎,支援多租戶隔離之 Excel/CSV 商品銷售數據匯出。
4. 全面修正日期選擇器(Flatpickr)排版,拓寬容器防水平滾動,對齊輸入框與下拉選單高度。
5. 重構日曆區間選擇樣式,實現區間中段無縫圓角拼接,並解決最右側「週六」欄位被裁切截斷的問題。
This commit is contained in:
sky121113 2026-05-18 15:09:09 +08:00
commit bb675a538a
7 changed files with 1447 additions and 13 deletions

View File

@ -26,11 +26,186 @@ class AnalysisController extends Controller
}
// 商品報表分析
public function productReports()
public function productReports(Request $request)
{
return view('admin.placeholder', [
$user = auth()->user();
$companyId = $user->company_id;
// 1. 取得篩選參數
$selectedCompanyId = $request->input('company_id');
$selectedProductId = $request->input('product_id', 'ALL');
$dateRange = $request->input('date_range');
// 2. 解析日期區間
if ($dateRange) {
$dates = explode(' to ', $dateRange);
if (count($dates) === 2) {
$startDate = \Illuminate\Support\Carbon::parse($dates[0])->startOfDay();
$endDate = \Illuminate\Support\Carbon::parse($dates[1])->endOfDay();
} else {
$startDate = \Illuminate\Support\Carbon::parse($dates[0])->startOfDay();
$endDate = \Illuminate\Support\Carbon::parse($dates[0])->endOfDay();
}
} else {
// 預設為最近 7 天 (含今日)
$startDate = now()->subDays(6)->startOfDay();
$endDate = now()->endOfDay();
$dateRange = $startDate->format('Y-m-d') . ' to ' . $endDate->format('Y-m-d');
}
// 3. 租戶隔離:非系統管理員強制限制為其所屬公司
if (!$user->isSystemAdmin()) {
$effectiveCompanyId = $companyId;
} else {
$effectiveCompanyId = $selectedCompanyId;
}
// 4. 加載下拉選單選項
// 公司選單 (僅限 Super Admin)
$companies = [];
if ($user->isSystemAdmin()) {
$companies = \App\Models\System\Company::active()->get(['id', 'name']);
}
// 商品選單
$productsQuery = \App\Models\Product\Product::query();
if ($effectiveCompanyId) {
$productsQuery->where('company_id', $effectiveCompanyId);
}
$products = $productsQuery->active()->get(['id', 'name', 'barcode']);
// 5. 執行主報表統計 SQL
// 計算各商品的銷售數量、銷售額、總成本、利潤
$mainQuery = \Illuminate\Support\Facades\DB::table('order_items as oi')
->join('orders as o', 'o.id', '=', 'oi.order_id')
->leftJoin('products as p', 'p.id', '=', 'oi.product_id')
->select([
'oi.product_id',
\Illuminate\Support\Facades\DB::raw('COALESCE(p.barcode, oi.barcode) as barcode'),
\Illuminate\Support\Facades\DB::raw('COALESCE(p.name, oi.product_name) as name'),
\Illuminate\Support\Facades\DB::raw('SUM(oi.quantity) as total_quantity'),
\Illuminate\Support\Facades\DB::raw('SUM(oi.subtotal) as total_sales'),
\Illuminate\Support\Facades\DB::raw('SUM(oi.quantity * COALESCE(p.cost, 0)) as total_cost'),
\Illuminate\Support\Facades\DB::raw('SUM(oi.subtotal) - SUM(oi.quantity * COALESCE(p.cost, 0)) as total_profit')
])
->where('o.payment_status', \App\Models\Transaction\Order::PAYMENT_STATUS_SUCCESS)
->whereNull('o.deleted_at')
->whereBetween('o.created_at', [$startDate, $endDate]);
// 套用公司篩選
if ($effectiveCompanyId) {
$mainQuery->where('o.company_id', $effectiveCompanyId);
}
// 套用特定商品篩選
if ($selectedProductId && $selectedProductId !== 'ALL') {
$mainQuery->where('oi.product_id', $selectedProductId);
}
$mainQuery->groupBy('oi.product_id')
->groupBy(\Illuminate\Support\Facades\DB::raw('COALESCE(p.barcode, oi.barcode)'))
->groupBy(\Illuminate\Support\Facades\DB::raw('COALESCE(p.name, oi.product_name)'));
$tableData = $mainQuery->get();
// 6. 計算總計 Summary
$totalQuantity = 0;
$totalSales = 0.0;
$totalCost = 0.0;
$totalProfit = 0.0;
foreach ($tableData as $row) {
$row->total_quantity = (int)$row->total_quantity;
$row->total_sales = (float)$row->total_sales;
$row->total_cost = (float)$row->total_cost;
$row->total_profit = (float)$row->total_profit;
$totalQuantity += $row->total_quantity;
$totalSales += $row->total_sales;
$totalCost += $row->total_cost;
$totalProfit += $row->total_profit;
}
$summary = [
'total_quantity' => $totalQuantity,
'total_sales' => round($totalSales, 2),
'total_cost' => round($totalCost, 2),
'total_profit' => round($totalProfit, 2),
];
// 7. 圖表日走勢統計 SQL
$trendQuery = \Illuminate\Support\Facades\DB::table('order_items as oi')
->join('orders as o', 'o.id', '=', 'oi.order_id')
->leftJoin('products as p', 'p.id', '=', 'oi.product_id')
->select([
\Illuminate\Support\Facades\DB::raw("DATE_FORMAT(o.created_at, '%Y-%m-%d') as date"),
\Illuminate\Support\Facades\DB::raw('SUM(oi.quantity) as total_quantity'),
\Illuminate\Support\Facades\DB::raw('SUM(oi.subtotal) as total_sales'),
\Illuminate\Support\Facades\DB::raw('SUM(oi.quantity * COALESCE(p.cost, 0)) as total_cost'),
])
->where('o.payment_status', \App\Models\Transaction\Order::PAYMENT_STATUS_SUCCESS)
->whereNull('o.deleted_at')
->whereBetween('o.created_at', [$startDate, $endDate]);
if ($effectiveCompanyId) {
$trendQuery->where('o.company_id', $effectiveCompanyId);
}
if ($selectedProductId && $selectedProductId !== 'ALL') {
$trendQuery->where('oi.product_id', $selectedProductId);
}
$trendQuery->groupBy('date')->orderBy('date', 'asc');
$trendData = $trendQuery->get();
// 補齊日期區間內所有空缺日走勢
$period = new \DatePeriod(
$startDate->copy()->startOfDay(),
new \DateInterval('P1D'),
$endDate->copy()->endOfDay()
);
$chartData = [];
foreach ($period as $date) {
$dateStr = $date->format('Y-m-d');
$chartData[$dateStr] = [
'date' => $dateStr,
'quantity' => 0,
'sales' => 0.0,
'cost' => 0.0,
];
}
foreach ($trendData as $row) {
if (isset($chartData[$row->date])) {
$chartData[$row->date]['quantity'] = (int)$row->total_quantity;
$chartData[$row->date]['sales'] = round((float)$row->total_sales, 2);
$chartData[$row->date]['cost'] = round((float)$row->total_cost, 2);
}
}
$chartData = array_values($chartData);
// 8. 判斷是否為 AJAX 請求,回傳 JSON 格式
if ($request->ajax()) {
return response()->json([
'success' => true,
'summary' => $summary,
'chart_data' => $chartData,
'table_data' => $tableData,
]);
}
// 9. 一般 GET 載入視圖
return view('admin.analysis.product-reports', [
'title' => '商品報表分析',
'description' => '商品銷售數據分析',
'companies' => $companies,
'products' => $products,
'selectedCompanyId' => $selectedCompanyId,
'selectedProductId' => $selectedProductId,
'dateRange' => $dateRange,
'summary' => $summary,
'chartData' => $chartData,
'tableData' => $tableData,
]);
}

View File

@ -1265,6 +1265,7 @@
"Quick Select": "Quick Select",
"Quick replenishment from this view": "Quick replenishment from this view",
"Quick search...": "Quick search...",
"Rank": "Rank",
"Real-time OEE analysis awaits": "Real-time OEE analysis awaits",
"Real-time Operation Logs (Last 50)": "Real-time Operation Logs (Last 50)",
"Real-time fleet efficiency and OEE metrics": "Real-time fleet efficiency and OEE metrics",
@ -1984,5 +1985,47 @@
"Please use our standard template to ensure data compatibility.": "Please use our standard template to ensure data compatibility.",
":count staff cards imported successfully": ":count staff cards imported successfully",
"Import failed": "Import failed",
"System restarting": "System restarting"
"System restarting": "System restarting",
"Product Report Analysis": "Product Report Analysis",
"Smart vending machine product sales, cost and profit analysis report": "Smart vending machine product sales, cost and profit analysis report",
"Real-time operational data synchronized": "Real-time operational data synchronized",
"Total Quantity Sold": "Total Quantity Sold",
"Product physical shipment count": "Product physical shipment count",
"Total Sales Amount": "Total Sales Amount",
"Sales Amount": "Sales Amount",
"Total transaction amount of successful payments": "Total transaction amount of successful payments",
"Total Product Cost": "Total Product Cost",
"Product Cost": "Product Cost",
"Sales Quantity": "Sales Quantity",
"Accumulated dynamic product purchase cost": "Accumulated dynamic product purchase cost",
"Total Sales Profit": "Total Sales Profit",
"Sales revenue minus product cost net value": "Sales revenue minus product cost net value",
"Current data indicates a loss": "Current data indicates a loss",
"Quick Filter": "Quick Filter",
"Last 7 Days": "Last 7 Days",
"Today": "Today",
"This Week": "This Week",
"Last Week": "Last Week",
"This Month": "This Month",
"Last Month": "Last Month",
"Select Product for Analysis": "Select Product for Analysis",
"All Products (ALL)": "All Products (ALL)",
"Tenant Company": "Tenant Company",
"Cross-Company / Headquarter Global Stats": "Cross-Company / Headquarter Global Stats",
"Product Sales & Profit Trend": "Product Sales & Profit Trend",
"Daily operational variance curve for selected timeframe": "Daily operational variance curve for selected timeframe",
"Detailed Analysis Data": "Detailed Analysis Data",
"Search product name, barcode...": "Search product name, barcode...",
"Export Report": "Export Report",
"Copy to Clipboard": "Copy to Clipboard",
"Export to CSV": "Export to CSV",
"Export to Excel": "Export to Excel",
"Print & PDF": "Print & PDF",
"Product Barcode": "Product Barcode",
"Quantity Sold": "Quantity Sold",
"Total Sales": "Total Sales",
"Total Net Profit": "Total Net Profit",
"Gross Margin": "Gross Margin",
"No product data matching search criteria": "No product data matching search criteria",
"Analyze Solely": "Analyze Solely"
}

View File

@ -1265,6 +1265,7 @@
"Quick Select": "クイック選択",
"Quick replenishment from this view": "この画面からクイック補充",
"Quick search...": "クイック検索...",
"Rank": "順位",
"Real-time OEE analysis awaits": "リアルタイムOEE分析待機中",
"Real-time Operation Logs (Last 50)": "リアルタイム操作ログ (直近50件)",
"Real-time fleet efficiency and OEE metrics": "全機器のリアルタイム効率とOEE指標",
@ -1984,5 +1985,47 @@
"Please use our standard template to ensure data compatibility.": "データの互換性を確保するために、標準テンプレートを使用してください。",
":count staff cards imported successfully": ":count 枚のスタッフカードが正常にインポートされました",
"Import failed": "インポート失敗",
"System restarting": "再起動中"
"System restarting": "再起動中",
"Product Report Analysis": "商品レポート分析",
"Smart vending machine product sales, cost and profit analysis report": "スマート自動販売機商品販売・コスト利益分析レポート",
"Real-time operational data synchronized": "リアルタイム運営データ同期完了",
"Total Quantity Sold": "販売総数",
"Product physical shipment count": "商品の実出荷数",
"Total Sales Amount": "販売総額",
"Sales Amount": "売上金額",
"Total transaction amount of successful payments": "支払い成功取引総額",
"Total Product Cost": "商品総コスト",
"Product Cost": "商品コスト",
"Sales Quantity": "販売数量",
"Accumulated dynamic product purchase cost": "リアルタイム仕入コスト累計",
"Total Sales Profit": "販売総利益",
"Sales revenue minus product cost net value": "販売額から商品コストを差し引いた純利益",
"Current data indicates a loss": "現在データは赤字を示しています",
"Quick Filter": "クイックフィルター",
"Last 7 Days": "過去7日間",
"Today": "今日",
"This Week": "今週",
"Last Week": "先週",
"This Month": "今月",
"Last Month": "先月",
"Select Product for Analysis": "分析対象商品の選択",
"All Products (ALL)": "全商品 (ALL)",
"Tenant Company": "所属テナント会社",
"Cross-Company / Headquarter Global Stats": "複数会社間 / 本部グローバル統計",
"Product Sales & Profit Trend": "商品販売・利益推移",
"Daily operational variance curve for selected timeframe": "選択期間における日次運営変動曲線",
"Detailed Analysis Data": "明細分析データ",
"Search product name, barcode...": "商品名、バーコードで検索...",
"Export Report": "レポートのエクスポート",
"Copy to Clipboard": "クリップボードにコピー",
"Export to CSV": "CSVエクスポート",
"Export to Excel": "Excelエクスポート",
"Print & PDF": "印刷 & PDF",
"Product Barcode": "商品バーコード",
"Quantity Sold": "販売数",
"Total Sales": "販売総額",
"Total Net Profit": "純利益総額",
"Gross Margin": "粗利益率",
"No product data matching search criteria": "検索条件に一致する商品データはありません",
"Analyze Solely": "個別分析"
}

View File

@ -1284,6 +1284,7 @@
"Quick Select": "快速選取",
"Quick replenishment from this view": "從此畫面快速補貨",
"Quick search...": "快速搜尋...",
"Rank": "排行",
"Real-time OEE analysis awaits": "即時 OEE 分析預備中",
"Real-time Operation Logs (Last 50)": "即時操作日誌 (最後 50 筆)",
"Real-time fleet efficiency and OEE metrics": "全機台即時效率與 OEE 指標",
@ -2033,5 +2034,47 @@
"Please use our standard template to ensure data compatibility.": "請使用標準範例檔以確保資料相容性。",
":count staff cards imported successfully": "成功匯入 :count 張員工識別卡",
"Import failed": "匯入失敗",
"System restarting": "重啟中"
"System restarting": "重啟中",
"Product Report Analysis": "商品報表分析",
"Smart vending machine product sales, cost and profit analysis report": "智慧型販賣機商品銷售與成本利潤分析報表",
"Real-time operational data synchronized": "即時營運數據已同步",
"Total Quantity Sold": "銷售總數量",
"Product physical shipment count": "商品實體出貨件數",
"Total Sales Amount": "銷售總金額",
"Sales Amount": "銷售金額",
"Total transaction amount of successful payments": "已付款成功之交易總額",
"Total Product Cost": "商品總成本",
"Product Cost": "商品成本",
"Sales Quantity": "銷售數量",
"Accumulated dynamic product purchase cost": "即時商品進貨成本累計",
"Total Sales Profit": "銷售總利潤",
"Sales revenue minus product cost net value": "銷售額扣除商品成本淨值",
"Current data indicates a loss": "當前數據出現虧損",
"Quick Filter": "快捷篩選",
"Last 7 Days": "近 7 日",
"Today": "今日",
"This Week": "本週",
"Last Week": "上週",
"This Month": "本月",
"Last Month": "上月",
"Select Product for Analysis": "選擇分析商品",
"All Products (ALL)": "全部商品 (ALL)",
"Tenant Company": "所屬租戶公司",
"Cross-Company / Headquarter Global Stats": "跨公司 / 總部全域統計",
"Product Sales & Profit Trend": "商品銷售利潤走勢",
"Daily operational variance curve for selected timeframe": "所選統計區間之每日營運變動曲線",
"Detailed Analysis Data": "明細分析數據",
"Search product name, barcode...": "搜尋商品名稱、條碼...",
"Export Report": "匯出報表",
"Copy to Clipboard": "複製至剪貼簿",
"Export to CSV": "匯出成 CSV",
"Export to Excel": "匯出成 Excel",
"Print & PDF": "列印與 PDF",
"Product Barcode": "商品條碼",
"Quantity Sold": "銷售數量",
"Total Sales": "銷售總額",
"Total Net Profit": "總淨利潤",
"Gross Margin": "毛利率",
"No product data matching search criteria": "沒有符合搜尋條件的商品資料",
"Analyze Solely": "單獨分析"
}

View File

@ -338,6 +338,7 @@
box-shadow: 0 25px 50px -12px rgba(0, 0, 0, 0.25) !important;
background: #ffffff !important;
padding: 4px !important;
width: 315.875px !important;
}
.dark .flatpickr-calendar {
@ -356,6 +357,23 @@
color: #cbd5e1 !important;
}
/* Standardize Flatpickr Date Range Continuity & Custom Borders */
.flatpickr-day.inRange {
border-radius: 0 !important;
}
.flatpickr-day.startRange {
border-radius: 12px 0 0 12px !important;
}
.flatpickr-day.endRange {
border-radius: 0 12px 12px 0 !important;
}
.flatpickr-day.startRange.endRange {
border-radius: 12px !important;
}
.flatpickr-day.prevMonthDay,
.flatpickr-day.nextMonthDay {
color: #cbd5e1 !important;
@ -412,7 +430,7 @@
}
.dark .flatpickr-weekday {
color: #475569 !important;
color: #94a3b8 !important;
}
.flatpickr-months .flatpickr-month {

File diff suppressed because it is too large Load Diff

View File

@ -222,9 +222,8 @@
@endcan
{{--
@can('menu.analysis')
8. 分析管理
{{-- 8. 分析管理 --}}
<li x-data="{ open: localStorage.getItem('menu_analysis') === 'true' || {{ request()->routeIs('admin.analysis.*') ? 'true' : 'false' }} }">
<button type="button" @click="if(sidebarCollapsed) { sidebarCollapsed = false; open = true; } else { open = !open; } localStorage.setItem('menu_analysis', open)" class="luxury-nav-item w-full text-start group">
<svg class="w-4 h-4 shrink-0 transition-colors {{ request()->routeIs('admin.analysis.*') ? 'text-cyan-500' : 'text-slate-600 group-hover:text-cyan-500 dark:text-slate-300 dark:group-hover:text-cyan-400' }}" xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2"><path stroke-linecap="round" stroke-linejoin="round" d="M7 12l3-3 3 3 4-4M8 21l4-4 4 4M3 4h18M4 4h16v12a1 1 0 01-1 1H5a1 1 0 01-1-1V4z" /></svg>
@ -235,15 +234,26 @@
</button>
<div x-show="open && !sidebarCollapsed" x-collapse>
<ul class="luxury-submenu" data-sidebar-sub>
<li><a class="flex items-center gap-x-3.5 py-2 px-2.5 text-sm transition-colors rounded-lg {{ request()->routeIs('admin.analysis.change-stock') ? 'text-slate-900 dark:text-white bg-slate-100 dark:bg-white/5' : 'text-slate-500 dark:text-slate-400 hover:text-slate-900 dark:hover:text-white' }}" href="{{ route('admin.analysis.change-stock') }}"><span class="whitespace-nowrap overflow-hidden transition-all duration-300" :class="sidebarCollapsed ? 'max-w-0 opacity-0' : 'max-w-[200px] opacity-100'">{{ __('Change Stock') }}</span></a></li>
<li><a class="flex items-center gap-x-3.5 py-2 px-2.5 text-sm transition-colors rounded-lg {{ request()->routeIs('admin.analysis.machine-reports') ? 'text-slate-900 dark:text-white bg-slate-100 dark:bg-white/5' : 'text-slate-500 dark:text-slate-400 hover:text-slate-900 dark:hover:text-white' }}" href="{{ route('admin.analysis.machine-reports') }}"><span class="whitespace-nowrap overflow-hidden transition-all duration-300" :class="sidebarCollapsed ? 'max-w-0 opacity-0' : 'max-w-[200px] opacity-100'">{{ __('Machine Reports') }}</span></a></li>
<li><a class="flex items-center gap-x-3.5 py-2 px-2.5 text-sm transition-colors rounded-lg {{ request()->routeIs('admin.analysis.product-reports') ? 'text-slate-900 dark:text-white bg-slate-100 dark:bg-white/5' : 'text-slate-500 dark:text-slate-400 hover:text-slate-900 dark:hover:text-white' }}" href="{{ route('admin.analysis.product-reports') }}"><span class="whitespace-nowrap overflow-hidden transition-all duration-300" :class="sidebarCollapsed ? 'max-w-0 opacity-0' : 'max-w-[200px] opacity-100'">{{ __('Product Reports') }}</span></a></li>
<li><a class="flex items-center gap-x-3.5 py-2 px-2.5 text-sm transition-colors rounded-lg {{ request()->routeIs('admin.analysis.survey-analysis') ? 'text-slate-900 dark:text-white bg-slate-100 dark:bg-white/5' : 'text-slate-500 dark:text-slate-400 hover:text-slate-900 dark:hover:text-white' }}" href="{{ route('admin.analysis.survey-analysis') }}"><span class="whitespace-nowrap overflow-hidden transition-all duration-300" :class="sidebarCollapsed ? 'max-w-0 opacity-0' : 'max-w-[200px] opacity-100'">{{ __('Survey Analysis') }}</span></a></li>
<li><a class="flex items-center gap-x-3.5 py-2 px-2.5 text-sm transition-colors rounded-lg {{ request()->routeIs('admin.analysis.change-stock') ? 'text-slate-900 dark:text-white bg-slate-100 dark:bg-white/5' : 'text-slate-500 dark:text-slate-400 hover:text-slate-900 dark:hover:text-white' }}" href="{{ route('admin.analysis.change-stock') }}">
<svg xmlns="http://www.w3.org/2000/svg" class="w-4 h-4 shrink-0 transition-colors" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><circle cx="8" cy="8" r="6"/><circle cx="16" cy="16" r="6"/></svg>
<span class="whitespace-nowrap overflow-hidden transition-all duration-300" :class="sidebarCollapsed ? 'max-w-0 opacity-0' : 'max-w-[200px] opacity-100'">{{ __('Change Stock') }}</span>
</a></li>
<li><a class="flex items-center gap-x-3.5 py-2 px-2.5 text-sm transition-colors rounded-lg {{ request()->routeIs('admin.analysis.machine-reports') ? 'text-slate-900 dark:text-white bg-slate-100 dark:bg-white/5' : 'text-slate-500 dark:text-slate-400 hover:text-slate-900 dark:hover:text-white' }}" href="{{ route('admin.analysis.machine-reports') }}">
<svg xmlns="http://www.w3.org/2000/svg" class="w-4 h-4 shrink-0 transition-colors" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><rect x="2" y="3" width="20" height="14" rx="2" ry="2" /><line x1="8" y1="21" x2="16" y2="21" /><line x1="12" y1="17" x2="12" y2="21" /><path d="M6 12l3-3 3 3 6-6" /></svg>
<span class="whitespace-nowrap overflow-hidden transition-all duration-300" :class="sidebarCollapsed ? 'max-w-0 opacity-0' : 'max-w-[200px] opacity-100'">{{ __('Machine Reports') }}</span>
</a></li>
<li><a class="flex items-center gap-x-3.5 py-2 px-2.5 text-sm transition-colors rounded-lg {{ request()->routeIs('admin.analysis.product-reports') ? 'text-slate-900 dark:text-white bg-slate-100 dark:bg-white/5' : 'text-slate-500 dark:text-slate-400 hover:text-slate-900 dark:hover:text-white' }}" href="{{ route('admin.analysis.product-reports') }}">
<svg xmlns="http://www.w3.org/2000/svg" class="w-4 h-4 shrink-0 transition-colors" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M6 2L3 6v14a2 2 0 0 0 2 2h14a2 2 0 0 0 2-2V6l-3-4z" /><line x1="3" y1="6" x2="21" y2="6" /><path d="M16 10a4 4 0 0 1-8 0" /></svg>
<span class="whitespace-nowrap overflow-hidden transition-all duration-300" :class="sidebarCollapsed ? 'max-w-0 opacity-0' : 'max-w-[200px] opacity-100'">{{ __('Product Reports') }}</span>
</a></li>
<li><a class="flex items-center gap-x-3.5 py-2 px-2.5 text-sm transition-colors rounded-lg {{ request()->routeIs('admin.analysis.survey-analysis') ? 'text-slate-900 dark:text-white bg-slate-100 dark:bg-white/5' : 'text-slate-500 dark:text-slate-400 hover:text-slate-900 dark:hover:text-white' }}" href="{{ route('admin.analysis.survey-analysis') }}">
<svg xmlns="http://www.w3.org/2000/svg" class="w-4 h-4 shrink-0 transition-colors" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M9 5H7a2 2 0 0 0-2 2v12a2 2 0 0 0 2 2h10a2 2 0 0 0 2-2V7a2 2 0 0 0-2-2h-2" /><rect x="9" y="3" width="6" height="4" rx="1" ry="1" /><path d="M9 14l2 2 4-4" /></svg>
<span class="whitespace-nowrap overflow-hidden transition-all duration-300" :class="sidebarCollapsed ? 'max-w-0 opacity-0' : 'max-w-[200px] opacity-100'">{{ __('Survey Analysis') }}</span>
</a></li>
</ul>
</div>
</li>
@endcan
--}}
{{--