Update learn page

This commit is contained in:
adilallo
2026-05-20 22:17:00 -06:00
parent 7ee6282c1a
commit 1688ac85c9
45 changed files with 1203 additions and 350 deletions
@@ -1,13 +1,23 @@
"use client";
/**
* Figma: "Components" / ContentThumnailTemplate (19614-14838, 19041-13415).
* Vertical 260×390 (19060-15787); horizontal 320×225.5 (19041-13550).
*/
import { memo } from "react";
import { getAssetPath, ASSETS } from "../../../../lib/assetUtils";
import ContentThumbnailTemplateView from "./ContentThumbnailTemplate.view";
import type { ContentThumbnailTemplateProps } from "./ContentThumbnailTemplate.types";
const ContentThumbnailTemplateContainer = memo<ContentThumbnailTemplateProps>(
({ post, className = "", variant: variantProp = "vertical" }) => {
({
post,
className = "",
variant: variantProp = "vertical",
sizing: sizingProp = "fluid",
}) => {
const variant = variantProp;
const sizing = sizingProp;
// Get article-specific background image from frontmatter
const getBackgroundImage = (
post: ContentThumbnailTemplateProps["post"],
@@ -42,6 +52,7 @@ const ContentThumbnailTemplateContainer = memo<ContentThumbnailTemplateProps>(
post={post}
className={className}
variant={variant}
sizing={sizing}
backgroundImage={backgroundImage}
/>
);
@@ -2,6 +2,8 @@ import type { BlogPost } from "../../../../lib/content";
export type ContentThumbnailTemplateVariantValue = "vertical" | "horizontal";
export type ContentThumbnailTemplateSizingValue = "fluid" | "fixed";
export interface ContentThumbnailTemplateProps {
post: BlogPost;
className?: string;
@@ -9,6 +11,10 @@ export interface ContentThumbnailTemplateProps {
* Content thumbnail variant.
*/
variant?: ContentThumbnailTemplateVariantValue;
/**
* fluid — fill parent (Learn grid). fixed — Figma px dimensions (Related Articles).
*/
sizing?: ContentThumbnailTemplateSizingValue;
slugOrder?: string[];
}
@@ -16,5 +22,6 @@ export interface ContentThumbnailTemplateViewProps {
post: BlogPost;
className: string;
variant: "vertical" | "horizontal";
sizing: ContentThumbnailTemplateSizingValue;
backgroundImage: string;
}
@@ -7,55 +7,95 @@ function ContentThumbnailTemplateView({
post,
className,
variant,
sizing,
backgroundImage,
}: ContentThumbnailTemplateViewProps) {
if (variant === "vertical") {
if (sizing === "fixed") {
return (
<Link
href={`/blog/${post.slug}`}
className={`group block transition-transform duration-200 hover:scale-[1.02] ${className}`}
>
<div className="relative h-[390px] w-[260px] overflow-hidden">
<div className="absolute inset-0 z-0">
{/* eslint-disable-next-line @next/next/no-img-element */}
<img
src={backgroundImage}
alt=""
className="pointer-events-none size-full object-cover"
/>
</div>
<div className="absolute left-[18px] top-[18px] z-20 w-[200px]">
<ContentContainer post={post} width="200px" size="xs" />
</div>
</div>
</Link>
);
}
return (
<Link
href={`/blog/${post.slug}`}
className={`block transition-transform duration-200 hover:scale-[1.02] ${className}`}
className={`group block w-full transition-transform duration-200 hover:scale-[1.02] ${className}`}
>
<div className="relative w-full aspect-[2/3] overflow-hidden pt-[18px] pl-[18px] pr-[42px] pb-[212px]">
{/* Background SVG - fills container with maintained aspect */}
<div className="relative aspect-[260/390] w-full overflow-hidden">
<div className="absolute inset-0 z-0">
{/* eslint-disable-next-line @next/next/no-img-element */}
<img
src={backgroundImage}
alt={`Background for ${post.frontmatter.title}`}
className="w-full h-full object-cover"
alt=""
className="pointer-events-none size-full object-cover"
/>
{/* Gradient overlay for better text readability */}
<div className="absolute inset-0 bg-gradient-to-b from-transparent via-transparent to-black/60 z-10" />
</div>
{/* Content Section - positioned within the padding constraints */}
<ContentContainer post={post} width="200px" size="xs" />
<div className="absolute left-[6.923%] top-[4.615%] z-20 w-[76.923%]">
<ContentContainer post={post} size="xs" />
</div>
</div>
</Link>
);
}
if (sizing === "fixed") {
return (
<Link
href={`/blog/${post.slug}`}
className={`group block transition-transform duration-200 hover:scale-[1.02] ${className}`}
>
<div className="relative h-[225.5px] w-[320px] overflow-hidden">
<div className="absolute inset-0 z-0">
{/* eslint-disable-next-line @next/next/no-img-element */}
<img
src={backgroundImage}
alt=""
className="pointer-events-none size-full object-cover"
/>
</div>
<div className="absolute left-[14px] top-[13.75px] z-20 w-[230px]">
<ContentContainer post={post} width="230px" size="xs" />
</div>
</div>
</Link>
);
}
// Horizontal variant
return (
<Link
href={`/blog/${post.slug}`}
className={`block transition-transform duration-200 hover:scale-[1.02] ${className}`}
className={`group block w-full transition-transform duration-200 hover:scale-[1.02] ${className}`}
>
<div className="relative min-w-[320px] max-w-[800px] h-[225.5px] overflow-hidden pt-[13.75px] pr-[76px] pb-[73.75px] pl-[14px]">
{/* Background SVG - sized to fit the 320x225.5 container exactly */}
<div className="relative aspect-[320/225.5] w-full overflow-hidden">
<div className="absolute inset-0 z-0">
{/* eslint-disable-next-line @next/next/no-img-element */}
<img
src={backgroundImage}
alt={`Background for ${post.frontmatter.title}`}
className="w-full h-[225.5px] object-cover"
alt=""
className="pointer-events-none size-full object-cover"
/>
{/* Gradient overlay */}
<div className="absolute inset-0 bg-gradient-to-r from-transparent via-transparent to-black/70 z-10" />
</div>
{/* Content - positioned within the padding constraints */}
<ContentContainer post={post} width="230px" size="xs" />
<div className="absolute left-[4.375%] top-[6.099%] z-20 w-[71.875%]">
<ContentContainer post={post} size="xs" />
</div>
</div>
</Link>
);