File manager - Edit - /home/webapp69.cm.in.th/u69319090034/Shop 034/product.php
Back
<?php // หน้ารายละเอียดสินค้า (product.php) require_once 'auth.php'; require_once 'config.php'; $productId = isset($_GET['id']) ? intval($_GET['id']) : 0; if (!$productId) { header('Location: index.php'); exit; } try { // 1. ดึงรายละเอียดสินค้าหลัก $stmt = $conn->prepare(" SELECT p.*, c.name as category_name, sc.name as size_chart_name, sc.chart_html as size_chart_html FROM products p LEFT JOIN categories c ON p.category_id = c.id LEFT JOIN size_charts sc ON p.size_chart_id = sc.id WHERE p.id = :id AND p.status = 'active' "); $stmt->execute([':id' => $productId]); $product = $stmt->fetch(); if (!$product) { die("ขออภัย ไม่พบสินค้าชิ้นนี้หรือสินค้าถูกระงับการขาย"); } // 2. ดึงภาพแกลเลอรีทั้งหมด พร้อมชื่อสี $stmtImg = $conn->prepare(" SELECT pi.*, av.value as color_name FROM product_images pi LEFT JOIN attribute_values av ON pi.color_attribute_value_id = av.id WHERE pi.product_id = :id ORDER BY pi.sort_order ASC "); $stmtImg->execute([':id' => $productId]); $images = $stmtImg->fetchAll(); // 3. ดึงกลุ่ม Variants (SKU) ทั้งหมดของสินค้านี้ พร้อม Options ID $stmtVar = $conn->prepare(" SELECT pv.id, pv.sku, pv.price_modifier, pv.stock_quantity, GROUP_CONCAT(vov.attribute_value_id) as option_ids FROM product_variants pv JOIN variant_option_values vov ON pv.id = vov.variant_id WHERE pv.product_id = :id GROUP BY pv.id "); $stmtVar->execute([':id' => $productId]); $rawVariants = $stmtVar->fetchAll(); // แปลงรูปแบบเพื่อให้ส่งต่อไปที่ JavaScript ได้ง่าย $variants = []; foreach ($rawVariants as $v) { $variants[] = [ 'id' => intval($v['id']), 'sku' => $v['sku'], 'price_modifier' => floatval($v['price_modifier']), 'stock' => intval($v['stock_quantity']), 'options' => array_map('intval', explode(',', $v['option_ids'])) ]; } // 4. ดึงเฉพาะ สี ที่ใช้ได้ในสินค้านี้ $stmtColors = $conn->prepare(" SELECT DISTINCT av.id, av.value, av.color_code FROM product_variants pv JOIN variant_option_values vov ON pv.id = vov.variant_id JOIN attribute_values av ON vov.attribute_value_id = av.id WHERE pv.product_id = :id AND av.attribute_id = 1 "); $stmtColors->execute([':id' => $productId]); $colors = $stmtColors->fetchAll(); // 5. ดึงเฉพาะ ไซซ์ ที่ใช้ได้ในสินค้านี้ $stmtSizes = $conn->prepare(" SELECT DISTINCT av.id, av.value FROM product_variants pv JOIN variant_option_values vov ON pv.id = vov.variant_id JOIN attribute_values av ON vov.attribute_value_id = av.id WHERE pv.product_id = :id AND av.attribute_id = 2 ORDER BY av.id ASC "); $stmtSizes->execute([':id' => $productId]); $sizes = $stmtSizes->fetchAll(); // Fallbacks กรณีสินค้าไม่มีตัวเลือกสี/ไซซ์ (สินค้าทั่วไปที่ไม่ได้เซ็ต Matrix) if (empty($colors)) { $colors = [['id' => 15, 'value' => 'สีตามภาพ', 'color_code' => '#c5a880']]; } if (empty($sizes)) { $sizes = [['id' => 16, 'value' => 'Free Size']]; } if (empty($variants)) { $variants = [[ 'id' => 9999, 'sku' => 'SKU-PROD-' . $productId . '-DEF', 'price_modifier' => 0.00, 'stock' => 50, 'options' => [15, 16] ]]; } // ตรวจสอบว่าสินค้าชิ้นนี้ถูกกดถูกใจโดย User ปัจจุบันหรือไม่ $isLiked = isProductLiked($productId); } catch (PDOException $e) { die("เกิดข้อผิดพลาดในการโหลดข้อมูล: " . $e->getMessage()); } // นับจำนวนสินค้าในตะกร้า $cartCount = 0; if (isset($_SESSION['cart'])) { foreach ($_SESSION['cart'] as $item) { $cartCount += $item['qty']; } } ?> <!DOCTYPE html> <html lang="th"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title><?= htmlspecialchars($product['name']) ?> - AMARA STUDIO</title> <link rel="stylesheet" href="style.css"> <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/sweetalert2@11/dist/sweetalert2.min.css"> </head> <body> <!-- Header Navigation --> <header> <div class="nav-container"> <a href="index.php" class="logo">AMARA<span>STUDIO</span></a> <ul class="nav-menu"> <li><a href="index.php" class="nav-link">คอลเลกชันทั้งหมด</a></li> <li> <a href="cart.php" class="nav-link cart-icon-wrapper"> ตะกร้าสินค้า <span class="cart-count" id="cart-nav-count"><?= $cartCount ?></span> </a> </li> <li><a href="manual.php" class="nav-link">📖 คู่มือการใช้งาน</a></li> <?php if (isLoggedIn()): ?> <li><a href="favorites.php" class="nav-link">❤️ สินค้าที่ถูกใจ</a></li> <?php if (isSellerLoggedIn()): ?> <li><a href="seller_dashboard.php" class="nav-link admin-btn">🏪 แดชบอร์ดผู้ขาย</a></li> <?php endif; ?> <li style="display: flex; align-items: center; gap: 10px; margin-left: 10px;"> <span style="color: var(--primary); font-size: 14px; font-weight: 600;">👋 <?= htmlspecialchars(getAdminName()) ?></span> <a href="logout.php" class="nav-link" style="color: #e53e3e;">ออกจากระบบ</a> </li> <?php else: ?> <li><a href="login.php" class="nav-link admin-btn">เข้าสู่ระบบ</a></li> <?php endif; ?> </ul> </div> </header> <!-- Main Container --> <div class="container"> <div class="product-detail-layout"> <!-- 1. แกลเลอรีรูปภาพสินค้า (Image Gallery) --> <div class="gallery-container"> <!-- รูปหลัก (Main Preview) --> <div class="gallery-main-wrapper"> <?php $mainImage = ''; foreach ($images as $img) { if ($img['is_main']) { $mainImage = $img['image_url']; break; } } if (!$mainImage && !empty($images)) { $mainImage = $images[0]['image_url']; } ?> <img src="<?= htmlspecialchars($mainImage) ?>" alt="<?= htmlspecialchars($product['name']) ?>" class="gallery-main-img" id="main-preview-img" onerror="this.src='https://images.unsplash.com/photo-1490481651871-ab68de25d43d?w=800'" onclick="openLightbox()"> </div> <!-- แถบรูปย่อยแนวขวางพร้อมปุ่มเลื่อนซ้าย-ขวา (< >) แสดงสินค้าทุกสีและตารางไซซ์ --> <div class="gallery-thumbs-carousel-wrapper"> <button type="button" class="thumb-nav-btn prev" onclick="scrollThumbs(-1)" title="รูปก่อนหน้า"> ‹ </button> <div class="gallery-thumbs-scroll-container" id="gallery-thumbs-scroll"> <?php foreach ($images as $index => $img): $isSizeChart = (strpos($img['image_url'], 'size_chart') !== false); ?> <div class="gallery-thumb-item <?= $index === 0 ? 'active' : '' ?> <?= $isSizeChart ? 'size-chart-thumb' : '' ?>" data-img-url="<?= htmlspecialchars($img['image_url']) ?>" data-color-id="<?= $img['color_attribute_value_id'] ?>" title="<?= $isSizeChart ? 'ตารางขนาดสินค้า (Size Chart)' : (!empty($img['color_name']) ? 'สี' . htmlspecialchars($img['color_name']) : 'รูปสินค้า') ?>" onclick="switchMainImage(this)"> <img src="<?= htmlspecialchars($img['image_url']) ?>" alt="Thumbnail" onerror="this.src='https://images.unsplash.com/photo-1490481651871-ab68de25d43d?w=800'"> <?php if ($isSizeChart): ?> <span class="thumb-size-chart-badge">📏 ไซซ์</span> <?php endif; ?> </div> <?php endforeach; ?> </div> <button type="button" class="thumb-nav-btn next" onclick="scrollThumbs(1)" title="รูปถัดไป"> › </button> </div> </div> <!-- 2. ข้อมูลสินค้าและการซื้อ (Product Purchase Panel) --> <div class="product-info-panel"> <span class="product-info-cat"><?= htmlspecialchars($product['category_name']) ?></span> <h1><?= htmlspecialchars($product['name']) ?></h1> <div class="product-info-price"> <span id="display-price">฿<?= number_format($product['base_price']) ?></span> <span id="price-modifier-text" style="font-size: 14px; color: var(--text-muted); font-weight: normal; margin-left: 10px;"></span> </div> <!-- เลือกสี (Color Variant Selector) --> <div class="variant-selector-group"> <div class="variant-label"> <span>เลือกสี: <strong id="selected-color-name" style="color: var(--dark);">-</strong></span> </div> <div class="variant-options"> <?php foreach ($colors as $color): ?> <button type="button" class="color-option-btn" style="background-color: <?= $color['color_code'] ?>;" title="<?= htmlspecialchars($color['value']) ?>" data-color-id="<?= $color['id'] ?>" data-color-name="<?= htmlspecialchars($color['value']) ?>" onclick="selectColor(this)"> </button> <?php endforeach; ?> </div> </div> <!-- เลือกไซซ์ (Size Variant Selector) --> <div class="variant-selector-group"> <div class="variant-label"> <span>เลือกไซซ์: <strong id="selected-size-name" style="color: var(--dark);">-</strong></span> <span id="stock-badge" class="stock-status-tag"></span> </div> <div class="variant-options" id="size-options-container"> <?php foreach ($sizes as $size): ?> <button type="button" class="size-option-btn" data-size-id="<?= $size['id'] ?>" data-size-name="<?= htmlspecialchars($size['value']) ?>" onclick="selectSize(this)"> <?= htmlspecialchars($size['value']) ?> </button> <?php endforeach; ?> </div> </div> <!-- ปุ่มดู Size Chart --> <?php if (!empty($product['size_chart_html'])): ?> <button type="button" class="size-chart-link-btn" onclick="openSizeChart()"> 📏 ดูตารางขนาดสินค้า (Size Chart) </button> <?php endif; ?> <!-- ปุ่มหยิบใส่ตะกร้า & กดถูกใจ --> <div class="add-to-cart-form" style="display: flex; gap: 12px; align-items: center;"> <input type="hidden" id="selected-variant-id" value=""> <button type="button" class="add-to-cart-btn" id="add-to-cart-btn" disabled onclick="addToCart()" style="flex: 1;"> กรุณาเลือก สี และ ไซซ์ </button> <button type="button" class="btn-like-detail <?= $isLiked ? 'active' : '' ?>" onclick="toggleLikeDetail(<?= $product['id'] ?>, this)" style="padding: 16px 20px; border: 1.5px solid var(--border); background: white; border-radius: var(--radius); cursor: pointer; font-size: 20px; transition: all 0.2s;"> <?= $isLiked ? '❤️' : '🤍' ?> </button> </div> <div class="product-desc-box"> <h3>รายละเอียดสินค้า</h3> <p style="white-space: pre-wrap; font-size: 15px; color: #4a5568;"><?= htmlspecialchars($product['description']) ?></p> </div> <!-- 📐 ส่วนเปรียบเทียบสัดส่วนและขนาดตัวนางแบบ (Model Size & Body Fit Guide) --> <div class="model-fit-section" style="margin-top: 30px; padding: 22px; background: white; border: 1px solid var(--border); border-radius: var(--radius); box-shadow: var(--shadow);"> <h3 style="font-size: 17px; font-weight: 700; color: var(--dark); margin-bottom: 6px; display: flex; align-items: center; gap: 8px;"> 👗 ภาพเปรียบเทียบมุมมองสัดส่วน & การสวมใส่จริง (Model Fit & Angle Comparison) </h3> <p style="font-size: 13.5px; color: var(--text-muted); margin-bottom: 16px;"> คลิกเลือกดูรูปแต่ละมุมมอง เพื่อเปรียบเทียบทรวดทรง ความยาว และขนาดเมื่อสวมใส่จริงบนสรีระนางแบบ </p> <!-- Fit Cards Grid --> <div style="display: grid; grid-template-columns: repeat(auto-fill, minmax(110px, 1fr)); gap: 12px;"> <?php foreach ($images as $idx => $img): $isChart = (strpos($img['image_url'], 'size_chart') !== false); if ($isChart) { $label = '📏 ตารางไซซ์'; } elseif (!empty($img['color_name'])) { $label = '🎨 สี' . $img['color_name']; } else { $label = 'มุมมองสินค้า ' . ($idx + 1); } ?> <div class="fit-card-item" style="cursor: pointer; text-align: center; border: 1px solid var(--border); border-radius: 8px; padding: 6px; background: #fafafb; transition: all 0.2s;" onclick="switchMainImageByUrl('<?= htmlspecialchars($img['image_url']) ?>')"> <div style="width: 100%; aspect-ratio: 3/4; overflow: hidden; border-radius: 6px; background: #edf2f7;"> <img src="<?= htmlspecialchars($img['image_url']) ?>" alt="<?= htmlspecialchars($label) ?>" onerror="this.src='https://images.unsplash.com/photo-1490481651871-ab68de25d43d?w=800'" style="width: 100%; height: 100%; object-fit: contain; padding: 4px;"> </div> <span style="display: block; font-size: 11.5px; font-weight: 600; margin-top: 5px; color: var(--text-main);"> <?= htmlspecialchars($label) ?> </span> </div> <?php endforeach; ?> </div> <!-- Model Stats info banner --> <div style="margin-top: 16px; padding: 12px 15px; background: #f8fafc; border-left: 4px solid var(--primary); border-radius: 6px; font-size: 13px; color: #4a5568; line-height: 1.6;"> 📐 <strong>ข้อมูลสเปกสัดส่วนนางแบบในภาพ:</strong><br> • <strong>นางแบบไซซ์ S:</strong> ส่วนสูง 168 ซม. | อก 32" | เอว 25" | สะโพก 35"<br> • <strong>แนะนำการเลือกไซซ์:</strong> เสื้อรุ่นนี้ตัดเย็บทรงสวยเข้ารูปพอดีตัว หากต้องการลุคใส่สบายหรือชอบสวมใส่แบบหลวมๆ (Relaxed Fit) แนะนำเผื่อขึ้น 1 ไซซ์ </div> </div> </div> </div> </div> <!-- 1. Modal: Size Chart --> <div class="modal-backdrop" id="size-chart-modal" onclick="closeModalOnBackdrop(event, 'size-chart-modal')"> <div class="modal-content"> <button class="modal-close" onclick="closeSizeChart()">×</button> <h2 style="margin-bottom: 15px; font-size: 20px;">ตารางวัดขนาดสินค้า: <?= htmlspecialchars($product['size_chart_name']) ?></h2> <div style="overflow-x: auto;"> <?= $product['size_chart_html'] ?> </div> <div style="margin-top: 15px; padding: 10px 14px; background: #edf2f7; border-radius: 6px; font-size: 12.5px; color: #4a5568;"> 💡 <strong>คำแนะนำเพิ่มเติม:</strong> สามารถใช้ตารางสัดส่วนด้านบนเปรียบเทียบกับขนาดรอบอกและเอวของท่านได้โดยตรง </div> </div> </div> <!-- 2. Modal: Image Zoom (Lightbox) --> <div class="modal-backdrop" id="lightbox-modal" onclick="closeModalOnBackdrop(event, 'lightbox-modal')"> <div class="modal-content lightbox-content" style="background: none; box-shadow: none; max-width: 900px; padding: 0;"> <button class="modal-close" style="color: white; font-size: 36px; top: -40px; right: 0;" onclick="closeLightbox()">×</button> <img src="" id="lightbox-img" alt="Zoomed image"> </div> </div> <!-- Footer --> <footer style="background-color: white; border-top: 1px solid var(--border); padding: 40px 0; margin-top: 80px; text-align: center; color: var(--text-muted);"> <p>© 2026 AMARA STUDIO. All rights reserved. เว็บไซต์นี้จำลองสถาปัตยกรรม E-Commerce แฟชั่นพรีเมียม</p> </footer> <!-- JavaScript สำหรับ Logic Variant Matrix และการกรองรูปตามสี --> <script> // โหลดข้อมูลตัวเลือกสินค้าจาก PHP มารับช่วงต่อใน JavaScript const basePrice = <?= floatval($product['base_price']) ?>; const variants = <?= json_encode($variants) ?>; let selectedColorId = null; let selectedColorName = ''; let selectedSizeId = null; let selectedSizeName = ''; let activeVariant = null; // สลับรูปภาพหลักในแกลเลอรี function switchMainImage(element) { // รองรับกรณีคลิกที่ img ลูก ให้ขยับขึ้นไปที่ parent .gallery-thumb-item let thumbEl = element; if (element.tagName && element.tagName.toLowerCase() === 'img') { thumbEl = element.closest('.gallery-thumb-item') || element.parentElement; } document.querySelectorAll('.gallery-thumb-item').forEach(item => { item.classList.remove('active'); }); thumbEl.classList.add('active'); const imgUrl = thumbEl.getAttribute('data-img-url'); if (imgUrl) { document.getElementById('main-preview-img').src = imgUrl; } // ถ้า Thumbnail นี้มี data-color-id ผูกอยู่ ให้ sync เลือกปุ่มสีนั้นด้วย const colorId = thumbEl.getAttribute('data-color-id'); if (colorId && colorId !== '') { const colorBtn = document.querySelector(`.color-option-btn[data-color-id="${colorId}"]`); if (colorBtn && !colorBtn.classList.contains('active')) { // เลือกปุ่มสีโดยไม่เรียก loop switchMainImage ซ้ำ document.querySelectorAll('.color-option-btn').forEach(btn => btn.classList.remove('active')); colorBtn.classList.add('active'); selectedColorId = parseInt(colorId); selectedColorName = colorBtn.getAttribute('data-color-name'); document.getElementById('selected-color-name').innerText = selectedColorName; // อัปเดตสต็อกและไซซ์ let firstAvailableSizeBtn = null; document.querySelectorAll('.size-option-btn').forEach(btn => { const sizeId = parseInt(btn.getAttribute('data-size-id')); const matchedVariant = findVariant(selectedColorId, sizeId); if (matchedVariant && matchedVariant.stock > 0) { btn.disabled = false; btn.classList.remove('out-of-stock'); if (!firstAvailableSizeBtn) firstAvailableSizeBtn = btn; } else if (!variants || variants.length <= 1) { btn.disabled = false; btn.classList.remove('out-of-stock'); if (!firstAvailableSizeBtn) firstAvailableSizeBtn = btn; } else { btn.disabled = true; btn.classList.add('out-of-stock'); } }); if (firstAvailableSizeBtn && (!selectedSizeId || document.querySelector(`.size-option-btn[data-size-id="${selectedSizeId}"]`)?.disabled)) { document.querySelectorAll('.size-option-btn').forEach(btn => btn.classList.remove('active')); firstAvailableSizeBtn.classList.add('active'); selectedSizeId = parseInt(firstAvailableSizeBtn.getAttribute('data-size-id')); selectedSizeName = firstAvailableSizeBtn.getAttribute('data-size-name'); document.getElementById('selected-size-name').innerText = selectedSizeName; } updatePurchasePanel(); } } } // สลับรูปภาพหลักผ่าน URL สำหรับการ์ดมุมมองสัดส่วน function switchMainImageByUrl(url) { document.getElementById('main-preview-img').src = url; document.querySelectorAll('.gallery-thumb-item').forEach(thumb => { if (thumb.getAttribute('data-img-url') === url) { thumb.classList.add('active'); } else { thumb.classList.remove('active'); } }); document.getElementById('main-preview-img').scrollIntoView({ behavior: 'smooth', block: 'nearest' }); } // เปิดซูม Lightbox function openLightbox() { const mainImgSrc = document.getElementById('main-preview-img').src; document.getElementById('lightbox-img').src = mainImgSrc; document.getElementById('lightbox-modal').classList.add('open'); } function closeLightbox() { document.getElementById('lightbox-modal').classList.remove('open'); } // เปิด-ปิด Size Chart function openSizeChart() { document.getElementById('size-chart-modal').classList.add('open'); } function closeSizeChart() { document.getElementById('size-chart-modal').classList.remove('open'); } function closeModalOnBackdrop(event, modalId) { if (event.target === document.getElementById(modalId)) { document.getElementById(modalId).classList.remove('open'); } } // เลื่อนแถบรูปย่อยแนวนอนด้วยปุ่ม (< >) function scrollThumbs(direction) { const container = document.getElementById('gallery-thumbs-scroll'); if (container) { container.scrollBy({ left: direction * 180, behavior: 'smooth' }); } } // 1. เลือกสีสินค้า (Color Selection) function selectColor(element) { // สลับปุ่ม Active สี document.querySelectorAll('.color-option-btn').forEach(btn => { btn.classList.remove('active'); }); element.classList.add('active'); selectedColorId = parseInt(element.getAttribute('data-color-id')); selectedColorName = element.getAttribute('data-color-name'); document.getElementById('selected-color-name').innerText = selectedColorName; // ตรวจสอบสต็อกสำหรับแต่ละไซซ์ของสีนี้ เพื่ออัปเดตสไตล์ปุ่มไซซ์ (Disabled หากไม่มีสต็อก) let firstAvailableSizeBtn = null; document.querySelectorAll('.size-option-btn').forEach(btn => { const sizeId = parseInt(btn.getAttribute('data-size-id')); const matchedVariant = findVariant(selectedColorId, sizeId); if (matchedVariant && matchedVariant.stock > 0) { btn.disabled = false; btn.classList.remove('out-of-stock'); if (!firstAvailableSizeBtn) firstAvailableSizeBtn = btn; } else if (!variants || variants.length <= 1) { btn.disabled = false; btn.classList.remove('out-of-stock'); if (!firstAvailableSizeBtn) firstAvailableSizeBtn = btn; } else { btn.disabled = true; btn.classList.add('out-of-stock'); } }); // เลือกไซซ์แรกที่ใช้ได้ให้อัตโนมัติ เพื่อให้ผู้ซื้อกดสั่งซื้อได้ทันที if (firstAvailableSizeBtn) { document.querySelectorAll('.size-option-btn').forEach(btn => btn.classList.remove('active')); firstAvailableSizeBtn.classList.add('active'); selectedSizeId = parseInt(firstAvailableSizeBtn.getAttribute('data-size-id')); selectedSizeName = firstAvailableSizeBtn.getAttribute('data-size-name'); document.getElementById('selected-size-name').innerText = selectedSizeName; } // หาและสลับรูปภาพของสีที่เลือก พร้อมสกรอลล์แถบรูปย่อยไปที่รูปสีนั้น const thumbnails = document.querySelectorAll('.gallery-thumb-item'); let matchedThumb = null; thumbnails.forEach(thumb => { const colorId = thumb.getAttribute('data-color-id'); if (colorId && parseInt(colorId) === selectedColorId) { if (!matchedThumb) matchedThumb = thumb; } }); if (matchedThumb) { switchMainImage(matchedThumb); matchedThumb.scrollIntoView({ behavior: 'smooth', block: 'nearest', inline: 'center' }); } updatePurchasePanel(); } // 2. เลือกไซซ์สินค้า (Size Selection) function selectSize(element) { if (element.disabled) return; document.querySelectorAll('.size-option-btn').forEach(btn => { btn.classList.remove('active'); }); element.classList.add('active'); selectedSizeId = parseInt(element.getAttribute('data-size-id')); selectedSizeName = element.getAttribute('data-size-name'); document.getElementById('selected-size-name').innerText = selectedSizeName; updatePurchasePanel(); } // ค้นหา SKU / Variant ในคู่สีและไซซ์ที่เลือก function findVariant(colorId, sizeId) { if (!variants || variants.length === 0) return null; let exactMatch = variants.find(v => v.options.includes(colorId) && v.options.includes(sizeId)); if (exactMatch) return exactMatch; if (variants.length === 1) return variants[0]; let partialMatch = variants.find(v => v.options.includes(colorId) || v.options.includes(sizeId)); return partialMatch || variants[0]; } // 3. อัปเดตสถานะของกล่องข้อมูลซื้อสินค้า (ราคา, บาร์โค้ด, สต็อก) function updatePurchasePanel() { const btn = document.getElementById('add-to-cart-btn'); const stockBadge = document.getElementById('stock-badge'); const displayPriceEl = document.getElementById('display-price'); const priceModEl = document.getElementById('price-modifier-text'); if (!selectedColorId || !selectedSizeId) { btn.disabled = true; btn.innerText = 'กรุณาเลือก สี และ ไซซ์'; stockBadge.innerText = ''; stockBadge.className = 'stock-status-tag'; displayPriceEl.innerText = '฿' + basePrice.toLocaleString(); priceModEl.innerText = ''; return; } activeVariant = findVariant(selectedColorId, selectedSizeId); if (activeVariant) { document.getElementById('selected-variant-id').value = activeVariant.id; // อัปเดตราคา + price modifier const totalPrice = basePrice + activeVariant.price_modifier; displayPriceEl.innerText = '฿' + totalPrice.toLocaleString(); if (activeVariant.price_modifier > 0) { priceModEl.innerText = `(ไซซ์พิเศษ +฿${activeVariant.price_modifier})`; } else { priceModEl.innerText = ''; } // ตรวจสอบสต็อก if (activeVariant.stock === 0) { btn.disabled = true; btn.innerText = 'สินค้าหมด (Out of Stock)'; stockBadge.innerText = 'สินค้าหมด'; stockBadge.className = 'stock-status-tag out-stock'; } else if (activeVariant.stock <= 2) { btn.disabled = false; btn.innerText = 'หยิบใส่ตะกร้า'; stockBadge.innerText = `เหลือเพียง ${activeVariant.stock} ชิ้นสุดท้าย`; stockBadge.className = 'stock-status-tag low-stock'; } else { btn.disabled = false; btn.innerText = 'หยิบใส่ตะกร้า'; stockBadge.innerText = 'มีสินค้าพร้อมส่ง'; stockBadge.className = 'stock-status-tag in-stock'; } } else { // หากไม่มี Variant ในตาราง Matrix เลย btn.disabled = true; btn.innerText = 'ไม่มีสินค้าจำหน่าย'; stockBadge.innerText = 'ไม่มีสินค้า'; stockBadge.className = 'stock-status-tag out-stock'; document.getElementById('selected-variant-id').value = ''; } } // 4. หยิบใส่ตะกร้า (AJAX Add to Cart) function addToCart() { const variantId = document.getElementById('selected-variant-id').value; if (!variantId) return; const btn = document.getElementById('add-to-cart-btn'); btn.disabled = true; btn.innerText = 'กำลังเพิ่มลงตะกร้า...'; fetch('api.php?action=add_to_cart', { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ variant_id: parseInt(variantId), quantity: 1 }) }) .then(res => res.json()) .then(data => { if (data.success) { document.getElementById('cart-nav-count').innerText = data.total_count; Swal.fire({ icon: 'success', title: 'เพิ่มลงตะกร้าแล้ว! 🛒', text: 'สินค้าถูกเพิ่มในตะกร้าสินค้าของคุณเรียบร้อยแล้ว', confirmButtonText: 'ดูตะกร้าสินค้า', showCancelButton: true, cancelButtonText: 'ช้อปต่อ', confirmButtonColor: '#c5a880', cancelButtonColor: '#718096', timer: 4000, timerProgressBar: true }).then((result) => { if (result.isConfirmed) { window.location.href = 'cart.php'; } }); } else { Swal.fire({ icon: 'error', title: 'เกิดข้อผิดพลาด', text: data.message, confirmButtonColor: '#c5a880' }); } }) .catch(err => { console.error('Error:', err); Swal.fire({ icon: 'error', title: 'เชื่อมต่อเซิร์ฟเวอร์ไม่ได้', text: 'กรุณาตรวจสอบการเชื่อมต่ออินเทอร์เน็ตและลองใหม่อีกครั้ง', confirmButtonColor: '#c5a880' }); }) .finally(() => { updatePurchasePanel(); }); } function toggleLikeDetail(productId, btn) { fetch('api.php?action=toggle_like', { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ product_id: productId }) }) .then(res => res.json()) .then(data => { if (data.success) { if (data.liked) { btn.innerHTML = '❤️'; btn.classList.add('active'); } else { btn.innerHTML = '🤍'; btn.classList.remove('active'); } const Toast = Swal.mixin({ toast: true, position: 'top-end', showConfirmButton: false, timer: 2000 }); Toast.fire({ icon: 'success', title: data.message }); } else if (data.require_login) { Swal.fire({ title: 'กรุณาเข้าสู่ระบบ', text: data.message, icon: 'info', showCancelButton: true, confirmButtonText: 'เข้าสู่ระบบผู้ซื้อ', cancelButtonText: 'ยกเลิก', confirmButtonColor: '#c5a880' }).then((result) => { if (result.isConfirmed) { window.location.href = 'login.php?role=buyer&redirect=' + encodeURIComponent(window.location.pathname + window.location.search); } }); } else { Swal.fire({ icon: 'error', title: 'ข้อผิดพลาด', text: data.message }); } }) .catch(err => { console.error(err); }); } // เมื่อเปิดหน้าสินค้า: เลือกลำดับสีและไซซ์แรกให้อัตโนมัติ document.addEventListener('DOMContentLoaded', function() { // Auto-select สีแรกและไซซ์แรก เพื่อให้ผู้ซื้อกดสั่งซื้อได้ทันทีโดยไม่ติดปุ่มเทา const colorBtns = document.querySelectorAll('.color-option-btn'); if (colorBtns.length > 0) { colorBtns[0].click(); } const sizeBtns = document.querySelectorAll('.size-option-btn:not(:disabled)'); if (sizeBtns.length > 0) { sizeBtns[0].click(); } }); </script> <script src="https://cdn.jsdelivr.net/npm/sweetalert2@11"></script> </body> </html>
| ver. 1.4 |
Github
|
.
| PHP 7.4.33 | Generation time: 0.24 |
proxy
|
phpinfo
|
Settings