Skip to content

Commit 09a7d5b

Browse files
committed
project and project/[project] complete
1 parent 5131752 commit 09a7d5b

File tree

11 files changed

+282
-47
lines changed

11 files changed

+282
-47
lines changed

README.md

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,9 @@ bun install --frozen-lockfile
2020

2121
## TODO
2222

23-
<https://astro.build/integrations/2/?search=&categories%5B%5D=performance%2Bseo&categories%5B%5D=accessibility>
23+
style more
24+
a11y <https://astro.build/integrations/2/?search=&categories%5B%5D=performance%2Bseo&categories%5B%5D=accessibility>
25+
pagination https://code.vool.jp/blog/astro-pagination/
2426

2527
## 開発
2628

astro.config.ts

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -23,4 +23,9 @@ export default defineConfig({
2323
}),
2424
mdx(),
2525
],
26+
27+
prefetch: {
28+
prefetchAll: true,
29+
defaultStrategy: "hover",
30+
},
2631
});

src/components/Header.astro

Lines changed: 47 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,20 @@
11
---
22
import { Icon } from "astro-icon/components";
33
import Logo from "./Logo.astro";
4+
import { Focus } from "../schema.ts";
45
56
const links = [
6-
{ title: "プロジェクト", to: "/projects/" },
7-
{ title: "記事", to: "/articles/" },
8-
{ title: "メンバー", to: "/members/" },
9-
{ title: "参加", to: "/join/" },
10-
{ title: "お問い合わせ", to: "/contact/" },
7+
{ title: "プロジェクト", to: "/projects", focus: Focus.projects },
8+
{ title: "記事", to: "/articles", focus: Focus.articles },
9+
{ title: "メンバー", to: "/members", focus: Focus.members },
10+
{ title: "参加", to: "/join", focus: Focus.join },
11+
{ title: "お問い合わせ", to: "/contact", focus: Focus.contact },
1112
];
13+
14+
interface Props {
15+
focus: Focus;
16+
}
17+
const { focus } = Astro.props;
1218
---
1319

1420
<header class="sticky">
@@ -40,7 +46,10 @@ const links = [
4046
<li>
4147
<a
4248
href={link.to}
43-
class="flex items-center h-full px-6 hover:bg-gray-100"
49+
class:list={[
50+
"flex items-center h-full px-6 hover:bg-gray-100 navigation-bar",
51+
focus === link.focus && "bg-amber-50",
52+
]}
4453
>
4554
{link.title}
4655
</a>
@@ -57,28 +66,32 @@ const links = [
5766
<Icon name="feather:menu" class="w-6 h-6 text-gray-600" />
5867
</button>
5968
</div>
60-
</header>
61-
<div
62-
id="navigation_panel"
63-
popover
64-
class="w-full
69+
<div
70+
id="navigation_panel"
71+
popover
72+
class="w-full
6573
absolute
6674
top-16
6775
transition-opacity
6876
duration-300"
69-
>
70-
<ul class="">
71-
{
72-
links.map((link) => (
73-
<li>
74-
<a href={link.to} class="block px-4 py-2 hover:bg-gray-100">
75-
{link.title}
76-
</a>
77-
</li>
78-
))
79-
}
80-
</ul>
81-
</div>
77+
>
78+
<ul class="">
79+
{
80+
links.map((link) => (
81+
<li>
82+
<a
83+
href={link.to}
84+
class="block px-4 py-2 hover:bg-gray-100 transition-all duration-300"
85+
>
86+
{link.title}
87+
</a>
88+
</li>
89+
))
90+
}
91+
</ul>
92+
</div>
93+
</header>
94+
8295
<style>
8396
/* https://stackoverflow.com/questions/77042256/css-transition-animation-not-working-for-popover-attribute */
8497
/* TODO: not working now */
@@ -93,4 +106,14 @@ const links = [
93106
opacity 0.3s,
94107
display 0.3s allow-discrete;
95108
}
109+
110+
.navigation-bar {
111+
background: linear-gradient(currentColor 0 0) bottom left/
112+
var(--underline-width, 0%) 0.1em no-repeat;
113+
text-decoration: none;
114+
transition: background-size 0.5s;
115+
}
116+
.navigation-bar:hover {
117+
--underline-width: 100%;
118+
}
96119
</style>

src/components/ProjectList.astro

Lines changed: 12 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,9 @@ import { Image } from "astro:assets";
33
import type { Project } from "../schema";
44
55
interface Props {
6-
projects: Project[];
6+
projects: {
7+
data: Project;
8+
}[];
79
class?: string;
810
}
911
const props = Astro.props;
@@ -36,21 +38,21 @@ const { projects } = props;
3638
<li class="contents">
3739
<a
3840
class="hover:brightness-95 rounded-xl overflow-clip border border-gray-200 bg-white"
39-
href={`/projects/${project.slug}/`}
41+
href={`/projects/${project.data.slug}/`}
4042
>
4143
<Image
42-
width="100"
43-
height={48 * 4}
44+
width="800"
45+
height="600"
4446
alt="プロジェクトのイメージ画像"
45-
src={project.image}
46-
class="object-cover"
47+
src={project.data.image}
48+
class="w-full h-[16rem] object-cover"
4749
/>
4850
<div class="p-4">
49-
<h3 class="text-xl font-bold">{project.title}</h3>
51+
<h3 class="text-xl font-bold">{project.data.title}</h3>
5052
<p class="mt-2 prose">
51-
{project.description.length < 120
52-
? project.description
53-
: project.description.slice(0, 120)}
53+
{project.data.description.length < 120
54+
? project.data.description
55+
: project.data.description.slice(0, 120)}
5456
</p>
5557
</div>
5658
</a>

src/layouts/GlobalLayout.astro

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,10 +2,18 @@
22
import Meta from "./meta.astro";
33
import Header from "../components/Header.astro";
44
import Footer from "../components/Footer.astro";
5+
import type { Focus } from "../schema";
6+
7+
interface Props {
8+
title: string | null;
9+
description: string | null;
10+
focus: Focus;
11+
}
12+
const { title, description, focus } = Astro.props;
513
---
614

7-
<Meta title="ut.code();" url="http://localhost:4321">
8-
<Header />
15+
<Meta {title} {description} url="http://localhost:4321">
16+
<Header {focus} />
917
<slot />
1018
<Footer />
1119
</Meta>

src/layouts/meta.astro

Lines changed: 11 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,16 +1,24 @@
11
---
22
// import type { WithContext, Thing } from "schema-dts";
3+
import { getImage } from "astro:assets";
34
import "../global.css";
5+
import Favicon from "../images/favicon.png";
46
57
interface Props {
68
title: string | null;
7-
description?: string;
9+
description: string | null;
810
keywords?: string[];
911
image?: string; // URL of image
1012
// linkedData?: WithContext<Thing>;
1113
url: string; // absolute path starting with /
1214
}
1315
const { title, description, keywords = [], image, url } = Astro.props;
16+
17+
const favicon = await getImage({
18+
src: Favicon,
19+
height: 128,
20+
width: 128,
21+
});
1422
---
1523

1624
<html lang="ja" class="min-h-full">
@@ -19,10 +27,10 @@ const { title, description, keywords = [], image, url } = Astro.props;
1927
<meta charset="utf-8" />
2028
<meta
2129
name="description"
22-
content={description ||
30+
content={description ??
2331
"東京大学のソフトウェアエンジニアリングコミュニティ"}
2432
/>
25-
<link rel="icon" />
33+
<link rel="icon" href={favicon.src} />
2634
<meta property="og:site_name" content="ut.code();" />
2735
<meta property="og:title" content={title} />
2836
<!-- TODO: make the origin flexible -->

src/pages/index.astro

Lines changed: 3 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@ import { getCollection } from "astro:content";
33
import { Image } from "astro:assets";
44
import { Icon } from "astro-icon/components";
55
import nullthrows from "nullthrows";
6+
import { Focus } from "../schema.ts";
67
78
import ActionButton from "../components/ActionButton.astro";
89
import SectionHeader from "../components/per-page/SectionHeader.astro";
@@ -18,7 +19,7 @@ const projects = (await getCollection("projects")).slice(0, 6);
1819
const articles = (await getCollection("articles")).slice(0, 6);
1920
---
2021

21-
<GlobalLayout>
22+
<GlobalLayout title={null} description={null} focus={Focus.none}>
2223
<div
2324
class="h-screen grid grid-flow-col"
2425
style={{ gridTemplateRows: "max-content minmax(0, 1fr)" }}
@@ -117,10 +118,7 @@ const articles = (await getCollection("articles")).slice(0, 6);
117118
<section>
118119
<div class="container mx-auto px-4 py-12">
119120
<SectionHeader title="Projects" subtitle="実施中のプロジェクト" />
120-
<ProjectList
121-
class="mt-10"
122-
projects={projects.map((project) => project.data)}
123-
/>
121+
<ProjectList class="mt-10" {projects} />
124122
<ActionButton to="/projects/" class="mt-8 ml-auto">
125123
すべてのプロジェクト
126124
</ActionButton>

src/pages/members/[member].astro

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,6 @@
11
---
2+
import GlobalLayout from "../../layouts/GlobalLayout.astro";
3+
import { Focus } from "../../schema";
24
import { getCollection, render } from "astro:content";
35
46
export async function getStaticPaths() {
@@ -11,10 +13,13 @@ export async function getStaticPaths() {
1113
1214
const { member } = Astro.props;
1315
const { Content } = await render(member);
14-
import GlobalLayout from "../../layouts/GlobalLayout.astro";
1516
---
1617

17-
<GlobalLayout>
18+
<GlobalLayout
19+
title={member.data.nameJa}
20+
description="ut.code(); のメンバーです。"
21+
focus={Focus.members}
22+
>
1823
Member!
1924
<Content />
2025
</GlobalLayout>

src/pages/projects.astro

Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
---
2+
import GlobalLayout from "../layouts/GlobalLayout.astro";
3+
import ProjectList from "../components/ProjectList.astro";
4+
import { getCollection } from "astro:content";
5+
import { Focus } from "../schema";
6+
7+
`
8+
query ProjectsPage {
9+
allMdx(
10+
filter: {
11+
internal: { contentFilePath: { glob: "**/contents/projects/**" } }
12+
}
13+
sort: [{ frontmatter: { order: ASC } }, { frontmatter: { date: DESC } }]
14+
) {
15+
nodes {
16+
...ProjectListProject
17+
}
18+
}
19+
}
20+
`;
21+
22+
interface Props {}
23+
24+
const projects = await getCollection("projects");
25+
---
26+
27+
<GlobalLayout
28+
title="すべてのプロジェクト"
29+
description="ut.code(); で開発を行っているプロジェクト一覧です。"
30+
focus={Focus.projects}
31+
>
32+
<main class="container mx-auto px-4 py-24">
33+
<h1 class="text-4xl text-center">プロジェクト</h1>
34+
<ProjectList class="mt-16" {projects} />
35+
</main>
36+
</GlobalLayout>

0 commit comments

Comments
 (0)