This commit is contained in:
2025-12-26 10:27:02 +07:00
parent fd9b5a3819
commit 7fc0be90b8
48 changed files with 5818 additions and 34 deletions

View File

@@ -0,0 +1,112 @@
'use client';
import React from 'react';
import { menuData } from '../menuData'; // Đảm bảo file này export menuData
import Link from 'next/link';
import { FaCaretDown } from 'react-icons/fa';
const HeaderBottomRight: React.FC = () => {
// 1. Lọc các ID danh mục hiển thị trên Header (Cấp 1)
const allowedIds = ['407', '408', '3300', '281', '3431', '410', '3403'];
// 2. Hàm lấy Icon và Title dựa theo ID
const getCategoryInfo = (id: string) => {
switch (id) {
case '407':
return { icon: 'sprite-laptop', title: 'Laptop' };
case '408':
return { icon: 'sprite-PC', title: 'PC' };
case '3300':
return { icon: 'sprite-PC', title: 'PC AI' };
case '281':
return { icon: 'sprite-manhinh', title: 'Màn hình' };
case '3431':
return { icon: 'sprite-linhkien', title: 'Linh kiện PC' };
case '410':
return { icon: 'sprite-phimchuot', title: 'Phím chuột ghế gear' };
case '3403':
return { icon: 'sprite-thietbi', title: 'Thiết bị văn phòng' };
default:
return { icon: '', title: '' };
}
};
// Lấy danh sách all_category từ menuData[0]
const allCategories = menuData[0]?.product?.all_category || [];
return (
<>
{allCategories.map((item) => {
if (!allowedIds.includes(item.id)) return null;
const info = getCategoryInfo(item.id);
return (
<li key={item.id} className="item-category-header" data-id={item.id}>
<Link href={item.id === '408' ? '#' : item.url} className="flex items-center gap-2">
<i className={`sprite-more ${info.icon}`}></i>
<span className="title-header-bottom">{info.title}</span>
<FaCaretDown size="16" className="text-white" />
</Link>
<div className="list-category-child flex justify-between">
<div className="box-left">
<ul className="grid grid-cols-4 gap-5">
{item.isParent === '1' && (
<>
{item.id === '408'
? allCategories
.filter((c) => ['408', '3201', '1829', '3300', '3691'].includes(c.id))
.map((child1) => (
<li key={child1.id} className="sub-menu">
<Link href={child1.url} className="child-lv2 block font-bold">
{child1.title}
</Link>
{child1.isParent === '1' && (
<div className="list-child-lv3 mt-10 flex flex-col">
{child1.children?.map((child2) => (
<Link key={child2.id} href={child2.url} className="child-lv3">
{child2.title}
</Link>
))}
</div>
)}
</li>
))
: item.children?.map((_item_child) => (
<li key={_item_child.id} className="sub-menu">
<Link href={_item_child.url} className="child-lv2 block font-bold">
{_item_child.title}
</Link>
{_item_child.isParent === '1' && (
<div className="list-child-lv3 mt-10 flex flex-col">
{_item_child.children?.map((_item_childtwo) => (
<Link
key={_item_childtwo.id}
href={_item_childtwo.url}
className="child-lv3"
>
{_item_childtwo.title}
</Link>
))}
</div>
)}
</li>
))}
</>
)}
</ul>
</div>
<div className={`box-right flex-1 product-category-${item.id}`}>
<p className="title font-bold">Bán chạy nhất</p>
<div className="list-product-bestsale" id={`product-category-${item.id}`}></div>
</div>
</div>
</li>
);
})}
</>
);
};
export default HeaderBottomRight;

View File

@@ -0,0 +1,68 @@
'use client';
import React, { useState } from 'react';
import { FaBars } from 'react-icons/fa';
import { menuData } from '../menuData';
import Image from 'next/image';
import Link from 'next/link';
import HeaderBottomRight from './HeaderBottomRight';
const HeaderBottom: React.FC = () => {
return (
<>
<div className="header-bottom">
<div className="container flex">
<div className="global-menu-container">
<div className="group-title flex items-center justify-center gap-2">
<FaBars size="16" /> <span className="text-[13px]">Danh mục sản phẩm</span>
</div>
<div className="global-menu-holder">
{menuData[0].product.all_category.map((item) => (
<div key={item.id} className="item">
<Link href={item.url} className="cat-1">
<Image
src={item.thumnail}
className="lazy icon-menu entered"
alt={item.title}
width="1"
height="1"
/>
<span className="cat-title line-clamp-1">{item.title}</span>
</Link>
{/* Cấp 2 & Cấp 3 */}
{item.children && item.children.length > 0 && (
<div className="sub-menu-list">
{item.children.map((_children2) => (
<div className="sub-cat-2" key={_children2.id}>
<Link href={_children2.url} className="cat-2">
{_children2.title}
</Link>
{/* Cấp 3 */}
{_children2.children && _children2.children.length > 0 && (
<>
{_children2.children.map((_children3) => (
<Link key={_children3.id} href={_children3.url}>
{_children3.title}
</Link>
))}
</>
)}
</div>
))}
</div>
)}
</div>
))}
</div>
</div>
<ul className="list-category-header relative flex w-[calc(100%_-220px)] items-center justify-between gap-5">
<HeaderBottomRight />
</ul>
</div>
</div>
</>
);
};
export default HeaderBottom;

View File

@@ -0,0 +1,132 @@
'use client';
import React, { useState } from 'react';
import Image from 'next/image';
import Link from 'next/link';
import { FaMapMarkerAlt, FaBars } from 'react-icons/fa';
import BoxShowroom from '@components/common/BoxShowroom';
const HeaderMid: React.FC = () => {
const PopupAddress = () => {
const modal = document.getElementById('boxShowroom') as HTMLDialogElement;
modal?.showModal();
};
return (
<div className="header-middle">
<div className="container flex items-center justify-between">
<div className="header-middle-left flex items-center">
<Link href="/">
<Image
src="https://nguyencongpc.vn/media/lib/18-02-2025/logowhite-dfvefb.png"
width="170"
height="38"
alt="logo"
className="logo-header"
/>
</Link>
<button className="icon-showroom flex items-center justify-center" onClick={PopupAddress}>
<FaMapMarkerAlt size={16} />
</button>
</div>
<div className="header-middle-right flex items-center">
<div className="header-menu-category">
<div className="box-title flex items-center justify-center gap-8">
<FaBars size={16} />
<p className="title-menu font-weight-500">Danh mục sản phẩm</p>
</div>
<div className="cau-noi"></div>
</div>
<div className="header-search-group">
<form method="get" action="/tim" name="searchForm">
<div className="box-search-input">
<input
type="text"
id="js-search-box"
name="q"
className="form-group-input"
placeholder="Bạn cần tìm gì?"
/>
</div>
<button
type="submit"
id="js-search-button"
aria-label="submit-search"
className="search-btn-header"
>
<i className="sprite sprite-search-header icon-search"></i>
</button>
</form>
<div className="search-results">
<div className="search-results-list"></div>
</div>
</div>
<div className="box-tabs-header flex items-center">
<Link href="/buildpc" className="item-tab-header flex-column flex items-center gap-4">
<p className="icon-item-tab flex items-center justify-center">
<i className="sprite sprite-buildpc-header"></i>
</p>
<span className="font-500">Xây dựng cấu hình</span>
</Link>
<Link
href="javascript:void(0)"
className="item-tab-header flex-column flex items-center gap-4"
>
<p className="icon-item-tab flex items-center justify-center">
<i className="sprite sprite-lienhe-header"></i>
</p>
<span className="font-500">Khách hàng liên hệ</span>
</Link>
<Link href="/tin-tuc" className="item-tab-header flex-column flex items-center gap-4">
<p className="icon-item-tab flex items-center justify-center">
<i className="sprite sprite-article-header"></i>
</p>
<span className="font-weight-500">Tin tức công nghệ</span>
</Link>
<div id="js-header-cart" className="position-relative">
<Link href="/cart" className="item-tab-header flex-column flex items-center gap-4">
<p className="icon-item-tab icon-cart-header flex items-center justify-center">
<i className="sprite sprite-cart-header"></i>
<u className="cart-count header-features-cart-amount">1</u>
</p>
<span className="font-weight-500">Giỏ hàng</span>
</Link>
<div className="cau-noi"></div>
<div className="cart-ttip" id="js-cart-tooltip">
<div className="cart-ttip-item-container"></div>
<div className="cart-ttip-price justify-content-end flex items-center gap-6">
<p>Tổng tiền hàng</p>
<p id="js-header-cart-quantity" className="font-weight-500"></p>
<p id="js-header-cart-total-price" className="font-weight-700"></p>
</div>
<Link
href="/cart"
className="cart-ttip-price-button flex items-center justify-center"
>
<p className="font-weight-700">THANH TOÁN NGAY </p>
</Link>
</div>
</div>
<Link
href="/taikhoan"
className="user-header item-tab-header flex-column flex items-center gap-4"
>
<p className="icon-item-tab flex items-center justify-center">
<i className="sprite sprite-account-header"></i>
</p>
<span className="font-weight-500">Tài khoản</span>
</Link>
</div>
</div>
</div>
<BoxShowroom />
</div>
);
};
export default HeaderMid;

View File

@@ -0,0 +1,63 @@
'use client';
import React from 'react';
import { Swiper, SwiperSlide } from 'swiper/react';
import { Autoplay, Navigation, Pagination } from 'swiper/modules';
import Image from 'next/image';
import Link from 'next/link';
// Định nghĩa kiểu dữ liệu cho mỗi Banner
interface BannerItem {
id: number;
link: string;
imageSrc: string;
altText: string;
}
// Dữ liệu mẫu (Bạn có thể fetch từ API)
const BANNER_DATA: BannerItem[] = [
{
id: 429,
link: '/ad.php?id=429',
imageSrc: 'https://nguyencongpc.vn/media/banner/01_Decc0f3e158e61fabaf09a74d48e1c357bd.webp',
altText: 'banner 1',
},
{
id: 392,
link: '/ad.php?id=392',
imageSrc: 'https://nguyencongpc.vn/media/banner/01_Dec383fdcbc6361363bd6d14f05d2c88ee2.webp',
altText: 'banner 2',
},
];
const HeaderSlider: React.FC = () => {
return (
<div className="header-top">
<Swiper
modules={[Autoplay, Navigation, Pagination]}
spaceBetween={12}
slidesPerView={1}
loop={true}
className="mySwiper"
>
{BANNER_DATA.map((banner) => (
<SwiperSlide key={banner.id}>
<div className="item">
<Link href={banner.link} className="item-banner boder-radius-10">
<Image
src={banner.imageSrc}
width={1909}
height={57}
alt={banner.altText}
priority={true}
className="h-auto w-full object-cover"
/>
</Link>
</div>
</SwiperSlide>
))}
</Swiper>
</div>
);
};
export default HeaderSlider;

View File

@@ -0,0 +1,15 @@
import HeaderSlider from './HeaderTop';
import HeaderMid from './HeaderMid';
import HeaderBottom from './HeaderBottom';
const Header: React.FC = () => {
return (
<div className="header">
<HeaderSlider />
<HeaderMid />
<HeaderBottom />
</div>
);
};
export default Header;

File diff suppressed because it is too large Load Diff