118 lines
4.6 KiB
TypeScript
118 lines
4.6 KiB
TypeScript
import { AdBannersSlot, AdIconsSlot, FriendLinksSlot, H5FriendLinksSlot } from "@/components/common/ads/slots";
|
|
import type { ReactNode } from "react";
|
|
|
|
import { ChannelHeader, H5ChannelHeader } from "@/components/common/channel-header";
|
|
import { Pagination } from "@/components/common/pagination";
|
|
import { buildPageHrefMap } from "@/components/common/pagination-map";
|
|
import { FloatingActions } from "@/components/home/floating-actions";
|
|
import { DownloadBanner } from "@/components/home/page-sections";
|
|
import { SeoBreadcrumb } from "@/components/seo/seo-breadcrumb";
|
|
import type { ShortDramaItem } from "@/components/short-drama/data";
|
|
import { H5ShortDramaCard, ShortDramaCard } from "@/components/short-drama/short-drama-card";
|
|
import { TopicListCard } from "@/components/topic/topic-list-card";
|
|
import { H5VideoCard, VideoCard } from "@/components/video/video-card";
|
|
|
|
import type { MorePageData } from "./data";
|
|
import { moreListHref } from "./route";
|
|
|
|
type CardRenderer = (item: ShortDramaItem) => ReactNode;
|
|
|
|
const layouts = {
|
|
短剧: {
|
|
gridClassName: "grid-cols-[repeat(auto-fill,266px)] gap-5",
|
|
h5GridClassName: "grid-cols-2 gap-x-[7px] gap-y-3",
|
|
renderCard: (item: ShortDramaItem) => <ShortDramaCard key={item.id} item={item} />,
|
|
renderH5Card: (item: ShortDramaItem) => <H5ShortDramaCard key={item.id} item={item} />,
|
|
},
|
|
视频: {
|
|
gridClassName: "grid-cols-[repeat(auto-fill,324px)] gap-5",
|
|
h5GridClassName: "grid-cols-2 gap-x-[7px] gap-y-3",
|
|
renderCard: (item: ShortDramaItem) => <VideoCard key={item.id} item={item} />,
|
|
renderH5Card: (item: ShortDramaItem) => <H5VideoCard key={item.id} item={item} />,
|
|
},
|
|
} satisfies Record<MorePageData["tab"], { gridClassName: string; h5GridClassName: string; renderCard: CardRenderer; renderH5Card: CardRenderer }>;
|
|
|
|
function TopicGrid({
|
|
topics,
|
|
dataType,
|
|
compact,
|
|
}: {
|
|
topics: MorePageData["topics"];
|
|
dataType: MorePageData["dataType"];
|
|
compact?: boolean;
|
|
}) {
|
|
if (!topics.length) return null;
|
|
return (
|
|
<div className={compact ? "grid grid-cols-2 gap-x-2.5 gap-y-4" : "grid grid-cols-2 gap-x-5 gap-y-7 lg:grid-cols-4"}>
|
|
{topics.map((topic) => (
|
|
<TopicListCard key={topic.id} topic={topic} dataType={dataType} compact={compact} />
|
|
))}
|
|
</div>
|
|
);
|
|
}
|
|
|
|
export function MorePage({ data }: { data: MorePageData }) {
|
|
const layout = layouts[data.tab];
|
|
const header = {
|
|
eyebrow: "MORE",
|
|
title: data.title,
|
|
subtitle: data.subtitle,
|
|
};
|
|
const hrefMap =
|
|
data.configId && data.totalPages > 1
|
|
? buildPageHrefMap(data.totalPages, (page) => moreListHref(data.configId, page))
|
|
: undefined;
|
|
|
|
return (
|
|
<>
|
|
<SeoBreadcrumb items={[{ name: "首页", href: "/" }, { name: data.title || "更多内容" }]} />
|
|
<main data-component="more-page" className="flex w-full min-w-0 flex-col gap-[18px] overflow-x-clip px-4 py-3 lg:hidden">
|
|
<H5ChannelHeader {...header} />
|
|
<AdIconsSlot variant="h5" />
|
|
|
|
<TopicGrid topics={data.topics} dataType={data.dataType} compact />
|
|
|
|
{data.items.length ? (
|
|
<div className={`grid ${layout.h5GridClassName}`}>{data.items.map((item) => layout.renderH5Card(item))}</div>
|
|
) : !data.topics.length ? (
|
|
<p className="py-16 text-center text-sm leading-5 text-white/45">暂无更多内容</p>
|
|
) : null}
|
|
|
|
{hrefMap ? <Pagination page={data.page} total={data.totalPages} hrefMap={hrefMap} className="[&_form]:hidden" /> : null}
|
|
|
|
<AdBannersSlot variant="h5" />
|
|
<H5FriendLinksSlot />
|
|
</main>
|
|
|
|
<main className="hidden lg:block">
|
|
<div className="design-frame flex flex-col gap-6 py-[43px]">
|
|
<ChannelHeader {...header} />
|
|
<AdIconsSlot variant="pc" />
|
|
|
|
<TopicGrid topics={data.topics} dataType={data.dataType} />
|
|
|
|
{data.items.length ? (
|
|
<div className={`grid scroll-mt-24 justify-between ${layout.gridClassName}`}>
|
|
{data.items.map((item) => layout.renderCard(item))}
|
|
</div>
|
|
) : !data.topics.length ? (
|
|
<p className="py-20 text-center text-sm leading-5 text-white/45">暂无更多内容</p>
|
|
) : null}
|
|
</div>
|
|
{/* 分页放在 design-frame 外,避免 Chrome CSS zoom 热区错位导致点击无响应 */}
|
|
{hrefMap ? (
|
|
<div className="flex justify-center px-6 py-6">
|
|
<Pagination page={data.page} total={data.totalPages} hrefMap={hrefMap} />
|
|
</div>
|
|
) : null}
|
|
<div className="design-frame flex flex-col gap-6 pb-[43px]">
|
|
<AdBannersSlot variant="pc" />
|
|
<DownloadBanner />
|
|
<FriendLinksSlot />
|
|
</div>
|
|
</main>
|
|
<FloatingActions />
|
|
</>
|
|
);
|
|
}
|