80 lines
2.0 KiB
TypeScript
80 lines
2.0 KiB
TypeScript
"use client";
|
||
|
||
import Image from "next/image";
|
||
import Link from "next/link";
|
||
import { useRef } from "react";
|
||
|
||
type Article = {
|
||
title: string;
|
||
date: string;
|
||
image: string;
|
||
href?: string;
|
||
};
|
||
|
||
export function ArticleCarousel({
|
||
articles,
|
||
ariaLabel,
|
||
}: {
|
||
articles: Article[];
|
||
ariaLabel: string;
|
||
}) {
|
||
const carouselRef = useRef<HTMLDivElement>(null);
|
||
|
||
const scrollCarousel = (direction: "next" | "previous") => {
|
||
const amount = carouselRef.current
|
||
? carouselRef.current.clientWidth * 0.7
|
||
: 320;
|
||
carouselRef.current?.scrollBy({
|
||
left: direction === "next" ? -amount : amount,
|
||
behavior: "smooth",
|
||
});
|
||
};
|
||
|
||
return (
|
||
<div className="product-carousel-shell article-carousel-shell">
|
||
<button
|
||
className="carousel-chevron carousel-chevron-left"
|
||
type="button"
|
||
aria-label="مقالات بعدی"
|
||
onClick={() => scrollCarousel("next")}
|
||
>
|
||
‹
|
||
</button>
|
||
<div ref={carouselRef} className="carousel article-carousel" aria-label={ariaLabel}>
|
||
{articles.map((article) => (
|
||
<Link
|
||
className="article-card"
|
||
key={article.href || article.title}
|
||
href={article.href || "/blog"}
|
||
aria-label={article.title}
|
||
>
|
||
<div className="article-media">
|
||
<Image
|
||
src={article.image}
|
||
alt={article.title}
|
||
fill
|
||
sizes="(max-width: 960px) 50vw, 28vw"
|
||
/>
|
||
</div>
|
||
<div className="article-body">
|
||
<time className="article-date" dateTime={article.date}>
|
||
{article.date}
|
||
</time>
|
||
<h3>{article.title}</h3>
|
||
<p>ادامه</p>
|
||
</div>
|
||
</Link>
|
||
))}
|
||
</div>
|
||
<button
|
||
className="carousel-chevron carousel-chevron-right"
|
||
type="button"
|
||
aria-label="مقالات قبلی"
|
||
onClick={() => scrollCarousel("previous")}
|
||
>
|
||
›
|
||
</button>
|
||
</div>
|
||
);
|
||
}
|