File manager - Edit - /home/webapp69.cm.in.th/u69319090037/Shop/views/dashboard.php
Back
<?php /** * Dashboard & Statistics * CMTC Shopping */ require_once __DIR__ . '/../includes/header.php'; require_once __DIR__ . '/../includes/navbar.php'; require_login(); // Current Thai Year $current_year = date('Y'); $current_thai_year = $current_year + 543; // 1. Monthly Sales Chart Data (Jan - Dec of current year) $monthly_sales = array_fill(1, 12, 0); $stmt_monthly = $db->prepare(" SELECT MONTH(created_at) as m, COALESCE(SUM(net_amount), 0) as total FROM orders WHERE YEAR(created_at) = ? AND status IN ('approved', 'preparing', 'ready', 'received') GROUP BY MONTH(created_at) "); $stmt_monthly->execute([$current_year]); while ($row = $stmt_monthly->fetch()) { $monthly_sales[intval($row['m'])] = floatval($row['total']); } // 2. Category Share Data (Pie / Doughnut Chart) $stmt_cat = $db->query(" SELECT c.name as cat_name, COUNT(p.id) as count FROM categories c LEFT JOIN products p ON c.id = p.category_id GROUP BY c.id HAVING count > 0 ORDER BY count DESC "); $categories_share = $stmt_cat->fetchAll(); // 3. Top 10 Best Sellers $stmt_top = $db->query(" SELECT p.name as prod_name, p.sku, SUM(oi.quantity) as total_qty, SUM(oi.quantity * oi.price) as total_amount FROM order_items oi JOIN products p ON oi.product_id = p.id JOIN orders o ON oi.order_id = o.id WHERE o.status IN ('approved', 'preparing', 'ready', 'received') GROUP BY p.id ORDER BY total_qty DESC LIMIT 10 "); $top_sellers = $stmt_top->fetchAll(); // 4. Orders by Department $stmt_dept = $db->query(" SELECT COALESCE(d.name, 'ทั่วไป / ไม่ระบุ') as dept_name, COUNT(o.id) as order_count, COALESCE(SUM(o.net_amount), 0) as total_amount FROM orders o JOIN users u ON o.user_id = u.id LEFT JOIN departments d ON u.department_id = d.id WHERE o.status IN ('approved', 'preparing', 'ready', 'received') GROUP BY d.id ORDER BY total_amount DESC "); $dept_orders = $stmt_dept->fetchAll(); // 5. Stock by Size $stmt_size_stock = $db->query(" SELECT COALESCE(psz.size_name, 'Free Size') as size_name, COALESCE(SUM(ps.quantity), 0) as total_qty FROM product_stock ps LEFT JOIN product_sizes psz ON ps.size_id = psz.id GROUP BY size_name ORDER BY total_qty DESC "); $size_stocks = $stmt_size_stock->fetchAll(); // 6. Out of Stock Products $stmt_out_stock = $db->query(" SELECT p.sku, p.name as prod_name, pc.color_name, psz.size_name FROM product_stock ps JOIN products p ON ps.product_id = p.id LEFT JOIN product_colors pc ON ps.color_id = pc.id LEFT JOIN product_sizes psz ON ps.size_id = psz.id WHERE ps.quantity <= 0 ORDER BY p.name ASC "); $out_of_stock_items = $stmt_out_stock->fetchAll(); ?> <!-- Chart.js CDN --> <script src="https://cdn.jsdelivr.net/npm/chart.js"></script> <div class="d-flex"> <?php require_once __DIR__ . '/../includes/sidebar.php'; ?> <main class="flex-grow-1 p-4" style="background-color: var(--bs-body-bg);"> <div class="d-flex justify-content-between align-items-center mb-4"> <div> <h3 class="fw-bold mb-0"><i class="bi bi-speedometer2 text-primary me-2"></i>แดชบอร์ดจัดการและรายงานสถิติ</h3> <p class="text-muted small mb-0">ระบบบริหารจัดการร้านค้า CMTC Smart Outfit Shopping & Booking</p> </div> <div> <span class="badge bg-primary px-3 py-2"><i class="bi bi-calendar-check me-1"></i>ปี <?php echo $current_thai_year; ?></span> </div> </div> <!-- Row 1: Monthly Sales Chart & Category Ratio --> <div class="row g-4 mb-4"> <div class="col-lg-8"> <div class="card border-0 shadow-sm glass-card p-4 h-100"> <h5 class="fw-bold mb-3"><i class="bi bi-graph-up-arrow text-primary me-2"></i>กราฟยอดขายรายเดือนประจำปี <?php echo $current_thai_year; ?></h5> <div style="position: relative; height: 280px; width: 100%;"> <canvas id="monthlySalesChart"></canvas> </div> </div> </div> <div class="col-lg-4"> <div class="card border-0 shadow-sm glass-card p-4 h-100"> <h5 class="fw-bold mb-3"><i class="bi bi-pie-chart-fill text-success me-2"></i>สัดส่วนสินค้าตามหมวดหมู่</h5> <div style="position: relative; height: 280px; width: 100%;"> <canvas id="categoryChart"></canvas> </div> </div> </div> </div> <!-- Row 2: Top 10 Best Sellers & Orders by Department --> <div class="row g-4 mb-4"> <div class="col-lg-6"> <div class="card border-0 shadow-sm glass-card p-4 h-100"> <h5 class="fw-bold mb-3"><i class="bi bi-trophy-fill text-warning me-2"></i>สินค้าขายดี 10 อันดับแรก</h5> <div class="table-responsive"> <table class="table table-hover align-middle"> <thead class="table-light"> <tr> <th>#</th> <th>ชื่อสินค้า</th> <th class="text-center">จำนวนขาย</th> <th class="text-end">ยอดขายรวม</th> </tr> </thead> <tbody> <?php if (count($top_sellers) > 0): ?> <?php foreach ($top_sellers as $idx => $ts): ?> <tr> <td><span class="badge bg-primary rounded-pill"><?php echo $idx + 1; ?></span></td> <td> <div class="fw-semibold"><?php echo sanitize($ts['prod_name']); ?></div> <small class="text-muted"><?php echo sanitize($ts['sku']); ?></small> </td> <td class="text-center fw-bold"><?php echo number_format($ts['total_qty']); ?></td> <td class="text-end fw-bold text-success"><?php echo format_price($ts['total_amount']); ?></td> </tr> <?php endforeach; ?> <?php else: ?> <tr> <td colspan="4" class="text-center text-muted py-4">ยังไม่มีข้อมูลการขายสินค้า</td> </tr> <?php endif; ?> </tbody> </table> </div> </div> </div> <div class="col-lg-6"> <div class="card border-0 shadow-sm glass-card p-4 h-100"> <h5 class="fw-bold mb-3"><i class="bi bi-building-check text-info me-2"></i>ยอดสั่งซื้อแยกตามแผนกวิชา</h5> <div class="table-responsive"> <table class="table table-hover align-middle"> <thead class="table-light"> <tr> <th>แผนกวิชา</th> <th class="text-center">จำนวนคำสั่งซื้อ</th> <th class="text-end">ยอดรวม</th> </tr> </thead> <tbody> <?php if (count($dept_orders) > 0): ?> <?php foreach ($dept_orders as $d): ?> <tr> <td class="fw-semibold"><?php echo sanitize($d['dept_name']); ?></td> <td class="text-center fw-bold"><?php echo number_format($d['order_count']); ?> รายการ</td> <td class="text-end fw-bold text-primary"><?php echo format_price($d['total_amount']); ?></td> </tr> <?php endforeach; ?> <?php else: ?> <tr> <td colspan="3" class="text-center text-muted py-4">ยังไม่มีข้อมูลการขายสินค้าตามแผนก</td> </tr> <?php endif; ?> </tbody> </table> </div> </div> </div> </div> <!-- Row 3: Stock by Size & Out of Stock Alerts --> <div class="row g-4"> <div class="col-lg-6"> <div class="card border-0 shadow-sm glass-card p-4 h-100"> <h5 class="fw-bold mb-3"><i class="bi bi-tag-fill text-primary me-2"></i>จำนวนสินค้าคงเหลือแยกตามไซส์</h5> <div class="table-responsive"> <table class="table table-hover align-middle"> <thead class="table-light"> <tr> <th>ไซส์ / ขนาด</th> <th class="text-end">จำนวนคงเหลือรวม</th> </tr> </thead> <tbody> <?php if (count($size_stocks) > 0): ?> <?php foreach ($size_stocks as $sz): ?> <tr> <td><span class="badge bg-secondary"><?php echo sanitize($sz['size_name']); ?></span></td> <td class="text-end fw-bold <?php echo $sz['total_qty'] <= 5 ? 'text-danger' : 'text-success'; ?>"> <?php echo number_format($sz['total_qty']); ?> ชิ้น </td> </tr> <?php endforeach; ?> <?php else: ?> <tr> <td colspan="2" class="text-center text-muted py-3">ไม่มีข้อมูลไซส์</td> </tr> <?php endif; ?> </tbody> </table> </div> </div> </div> <div class="col-lg-6"> <div class="card border-0 shadow-sm glass-card p-4 h-100"> <div class="d-flex justify-content-between align-items-center mb-3"> <h5 class="fw-bold mb-0"><i class="bi bi-exclamation-octagon-fill text-danger me-2"></i>สินค้าที่หมดสต๊อก</h5> <span class="badge bg-danger"><?php echo count($out_of_stock_items); ?> รายการ</span> </div> <div class="table-responsive"> <table class="table table-hover align-middle"> <thead class="table-light"> <tr> <th>SKU</th> <th>ชื่อสินค้า</th> <th>ตัวเลือก (สี/ไซส์)</th> </tr> </thead> <tbody> <?php if (count($out_of_stock_items) > 0): ?> <?php foreach ($out_of_stock_items as $out): ?> <tr> <td><code><?php echo sanitize($out['sku']); ?></code></td> <td class="fw-semibold text-danger"><?php echo sanitize($out['prod_name']); ?></td> <td><small class="text-muted"><?php echo sanitize(($out['color_name'] ?? '-') . ' / ' . ($out['size_name'] ?? '-')); ?></small></td> </tr> <?php endforeach; ?> <?php else: ?> <tr> <td colspan="3" class="text-center text-success py-4"> <i class="bi bi-check-circle fs-3 d-block mb-1"></i> ไม่มีสินค้าที่หมดสต๊อก </td> </tr> <?php endif; ?> </tbody> </table> </div> </div> </div> </div> </main> </div> <script> document.addEventListener('DOMContentLoaded', function() { // 1. Line Chart: Monthly Sales var monthlyCtx = document.getElementById('monthlySalesChart').getContext('2d'); new Chart(monthlyCtx, { type: 'line', data: { labels: ['ม.ค.', 'ก.พ.', 'มี.ค.', 'เม.ย.', 'พ.ค.', 'มิ.ย.', 'ก.ค.', 'ส.ค.', 'ก.ย.', 'ต.ค.', 'พ.ย.', 'ธ.ค.'], datasets: [{ label: 'ยอดขาย (บาท)', data: <?php echo json_encode(array_values($monthly_sales)); ?>, borderColor: '#0d6efd', backgroundColor: 'rgba(13, 110, 253, 0.1)', borderWidth: 2, fill: true, tension: 0.3, pointBackgroundColor: '#0d6efd', pointRadius: 4 }] }, options: { responsive: true, maintainAspectRatio: false, plugins: { legend: { display: false } }, scales: { y: { beginAtZero: true, ticks: { callback: function(value) { return '฿' + value.toLocaleString(); } } } } } }); // 2. Doughnut Chart: Categories Share var catCtx = document.getElementById('categoryChart').getContext('2d'); var catLabels = <?php echo json_encode(array_column($categories_share, 'cat_name')); ?>; var catCounts = <?php echo json_encode(array_column($categories_share, 'count')); ?>; if (catLabels.length === 0) { catLabels = ['ไม่มีสินค้า']; catCounts = [1]; } new Chart(catCtx, { type: 'doughnut', data: { labels: catLabels, datasets: [{ data: catCounts, backgroundColor: [ '#0d6efd', '#20c997', '#ffc107', '#fd7e14', '#6610f2', '#d63384', '#6c757d' ], borderWidth: 1 }] }, options: { responsive: true, maintainAspectRatio: false, plugins: { legend: { position: 'bottom' } } } }); }); </script> <?php require_once __DIR__ . '/../includes/footer.php'; ?>
| ver. 1.4 |
Github
|
.
| PHP 7.4.33 | Generation time: 0.23 |
proxy
|
phpinfo
|
Settings