diff --git a/app/(pages)/articles/page.tsx b/app/(pages)/articles/page.tsx deleted file mode 100644 index 6a0b4a06..00000000 --- a/app/(pages)/articles/page.tsx +++ /dev/null @@ -1,22 +0,0 @@ -import type { Metadata } from "next"; - -import { RssIcon } from "../../_components"; -import { ArticleList, UniversalLink } from "../../_features"; - -export default function Page() { - return ( -
-

- Articles - - - -

- -
- ); -} - -export const metadata: Metadata = { - title: "Articles", -}; diff --git a/app/_features/articles/ArticleList.tsx b/app/_features/articles/ArticleList.tsx index e41fe97f..555d2c58 100644 --- a/app/_features/articles/ArticleList.tsx +++ b/app/_features/articles/ArticleList.tsx @@ -12,10 +12,14 @@ export const ArticleList = ({ tag }: Props): JSX.Element => { const articlesMeta = getArticlesMeta({ tag }); return ( -
- {articlesMeta.map((article) => ( - - ))} +
+

All Writing

+ +
+ {articlesMeta.map((article) => ( + + ))} +
); }; diff --git a/app/_features/articles/ArticleListItem.tsx b/app/_features/articles/ArticleListItem.tsx index b0e646a1..dd68cee2 100644 --- a/app/_features/articles/ArticleListItem.tsx +++ b/app/_features/articles/ArticleListItem.tsx @@ -1,8 +1,8 @@ -import { ExternalLinkIcon, Time } from "../../_components"; +import { MoveUpRight } from "lucide-react"; +import { Time } from "../../_components"; import { format } from "../../_utils"; import { UniversalLink } from "../viewTransition"; -import { Tag } from "./Tag"; import type { ArticleMeta } from "./type"; type Props = ArticleMeta; @@ -12,26 +12,22 @@ export const ArticleListItem = ({ href, externalLink, publishedAt: _publishedAt, - tags, }: Props) => { const publishedAt = format(_publishedAt); return ( -
-

- +
+

+ {title} - {externalLink && } + {externalLink && ( + + )}

-
-
- {tags.map((tag) => ( - - ))} -
- -
+
); }; diff --git a/app/_features/articles/Tag.tsx b/app/_features/articles/Tag.tsx index e7059492..fd948ab9 100644 --- a/app/_features/articles/Tag.tsx +++ b/app/_features/articles/Tag.tsx @@ -1,5 +1,3 @@ -import { UniversalLink } from "../viewTransition"; - import { tagLabelMap } from "./constants"; import type { TagEnum } from "./type"; @@ -11,12 +9,8 @@ export const Tag = ({ tag }: Props) => { const label = tagLabelMap[tag]; return ( - + {label} - + ); }; diff --git a/app/_features/viewTransition/UniversalLink.tsx b/app/_features/viewTransition/UniversalLink.tsx index 17732210..b3511101 100644 --- a/app/_features/viewTransition/UniversalLink.tsx +++ b/app/_features/viewTransition/UniversalLink.tsx @@ -8,14 +8,27 @@ import { isSameOrigin } from "./isSameOrigin"; const animatedUnderline = "no-underline transition-colors duration-300 border-b border-solid border-zinc-200 hover:border-zinc-500 dark:border-zinc-700 dark:hover:border-zinc-500"; +const hoveredUnderline = + "no-underline hover:border-b hover:border-solid hover:border-zinc-200 dark:hover:border-zinc-700"; + type Props = LinkProps & { isExternal?: boolean; isEnabledUnderline?: boolean; + isEnabledHoveredUnderline?: boolean; }; export const UniversalLink = forwardRef( - ({ isExternal, isEnabledUnderline = false, className: _className, ...props }: Props, ref) => { - const className = `${_className || ""} ${isEnabledUnderline ? animatedUnderline : ""}`; + ( + { + isExternal, + isEnabledUnderline = false, + isEnabledHoveredUnderline = false, + className: _className, + ...props + }: Props, + ref, + ) => { + const className = `${_className || ""} ${isEnabledUnderline ? animatedUnderline : isEnabledHoveredUnderline ? hoveredUnderline : ""}`; if (isExternal || !isSameOrigin(props.href)) { return ( diff --git a/app/articles/[slug]/__tests__/page.e2e.ts b/app/articles/[slug]/__tests__/page.e2e.ts index b9132589..d0362027 100644 --- a/app/articles/[slug]/__tests__/page.e2e.ts +++ b/app/articles/[slug]/__tests__/page.e2e.ts @@ -40,7 +40,7 @@ test.describe("Command Palette", () => { await page.getByRole("option", { name: "All Writing" }).click(); await expect(page.getByRole("dialog")).not.toBeVisible(); - await expect(page.getByRole("heading", { name: "Articles RSS" })).toBeVisible(); + await expect(page.getByRole("heading", { name: "All Writing" })).toBeVisible(); }); test("Navigate to `Source of this site` on another tab", async ({ page }) => { @@ -63,7 +63,7 @@ test.describe("Command Palette", () => { await page.keyboard.press("Enter"); await expect(page.getByRole("dialog")).not.toBeVisible(); - await expect(page.getByRole("heading", { name: "Articles RSS" })).toBeVisible(); + await expect(page.getByRole("heading", { name: "All Writing" })).toBeVisible(); }); test("Navigate to `Source of this site` with Enter key", async ({ page }) => { diff --git a/app/articles/[slug]/_features/ArticleMetaDetail.tsx b/app/articles/[slug]/_features/ArticleMetaDetail.tsx index 1fa43f3d..f2c08995 100644 --- a/app/articles/[slug]/_features/ArticleMetaDetail.tsx +++ b/app/articles/[slug]/_features/ArticleMetaDetail.tsx @@ -1,7 +1,6 @@ import Image from "next/image"; import { MyAvatar, Time } from "@/app/_components"; -import { Tag } from "@/app/_features"; import { format } from "@/app/_utils"; import type { Article } from "contentlayer/generated"; import type { FC } from "react"; @@ -11,7 +10,7 @@ interface Props { } export const ArticleMetaDetail: FC = ({ - article: { headingImage, title, publishedAt: _publishedAt, tags }, + article: { headingImage, title, publishedAt: _publishedAt }, }) => { const publishedAt = format(new Date(_publishedAt)); @@ -45,11 +44,6 @@ export const ArticleMetaDetail: FC = ({ 5 min read

-
- {tags.map((tag) => ( - - ))} -
); }; diff --git a/app/articles/page.tsx b/app/articles/page.tsx new file mode 100644 index 00000000..bdc8d89f --- /dev/null +++ b/app/articles/page.tsx @@ -0,0 +1,15 @@ +import type { Metadata } from "next"; + +import { ArticleList } from "../_features"; + +export default function Page() { + return ( +
+ +
+ ); +} + +export const metadata: Metadata = { + title: "Articles", +}; diff --git a/app/globals.css b/app/globals.css index 1e29ac24..2e9bedfd 100644 --- a/app/globals.css +++ b/app/globals.css @@ -112,6 +112,10 @@ animation-delay: calc(var(--enter-initial) + var(--enter-stage) * var(--enter-step)); } + .blur-enter-content.enter-step-80 > * { + --enter-step: 80ms; + } + .blur-enter-content > *:nth-child(1) { --enter-stage: 1; }