Start using TailwindCSS

This commit is contained in:
DrMint 2022-01-01 20:04:48 +01:00
parent 7076b2d71e
commit 68f5a4f19e
17 changed files with 4930 additions and 195 deletions

1114
package-lock.json generated

File diff suppressed because it is too large Load Diff

View File

@ -8,15 +8,19 @@
"lint": "next lint" "lint": "next lint"
}, },
"dependencies": { "dependencies": {
"@fontsource/vollkorn": "^4.5.1",
"@fontsource/zen-maru-gothic": "^4.5.3",
"next": "12.0.2", "next": "12.0.2",
"react": "17.0.2", "react": "17.0.2",
"react-dom": "17.0.2" "react-dom": "17.0.2"
}, },
"devDependencies": { "devDependencies": {
"@tailwindcss/typography": "^0.5.0",
"@types/node": "16.11.6", "@types/node": "16.11.6",
"@types/react": "17.0.34", "@types/react": "17.0.34",
"eslint": "7.32.0", "eslint": "7.32.0",
"eslint-config-next": "12.0.2", "eslint-config-next": "12.0.2",
"tailwindcss": "^3.0.8",
"typescript": "4.4.4" "typescript": "4.4.4"
} }
} }

6
postcss.config.js Normal file
View File

@ -0,0 +1,6 @@
module.exports = {
plugins: {
tailwindcss: {},
autoprefixer: {},
}
}

View File

@ -1,14 +1,13 @@
import styles from "styles/Panels/ContentPanel.module.css";
import panelStyles from "styles/Panels/Panels.module.css";
type ContentPanelProps = { type ContentPanelProps = {
children: React.ReactNode; children: React.ReactNode;
}; };
export default function ContentPanel(props: ContentPanelProps): JSX.Element { export default function ContentPanel(props: ContentPanelProps): JSX.Element {
return ( return (
<div className={[panelStyles.panel, styles.panel].join(" ")}> <div className="w-full grid overflow-y-scroll max-h-screen py-20 px-10">
<main className={styles.panelInside}>{props.children}</main> <main className="prose lg:prose-lg place-self-center text-justify">
{props.children}
</main>
</div> </div>
); );
} }

View File

@ -5,7 +5,7 @@ import NavOption from "components/Panels/NavOption";
export default function MainPanel(): JSX.Element { export default function MainPanel(): JSX.Element {
return ( return (
<div className={[panelStyles.panel, styles.panel].join(" ")}> <div className={`${panelStyles.panel} ${styles.panel}`}>
<Link href="/" passHref> <Link href="/" passHref>
<div className={styles.topLogo}> <div className={styles.topLogo}>
<img src="/icons/accords.svg" alt="" /> <img src="/icons/accords.svg" alt="" />
@ -62,17 +62,17 @@ export default function MainPanel(): JSX.Element {
<hr /> <hr />
<div className={styles.menuFooter}> <div className="text-center">
<p> <p>
This website&rsquo;s content is made available under{" "} This website&rsquo;s content is made available under{" "}
<a href="https://creativecommons.org/licenses/by-sa/4.0/">CC-BY-SA</a>{" "} <a href="https://creativecommons.org/licenses/by-sa/4.0/">CC-BY-SA</a>{" "}
unless otherwise noted. unless otherwise noted.
</p> </p>
<a href="https://creativecommons.org/licenses/by-sa/4.0/"> <a href="https://creativecommons.org/licenses/by-sa/4.0/">
<div className={styles.menuFooterCC}> <div className="mt-4 mb-8 grid h-4 grid-flow-col place-content-center gap-1">
<img src="/icons/creative-commons-brands.svg" alt="" /> <img className="h-6" src="/icons/creative-commons-brands.svg" alt="" />
<img src="/icons/creative-commons-by-brands.svg" alt="" /> <img className="h-6" src="/icons/creative-commons-by-brands.svg" alt="" />
<img src="/icons/creative-commons-sa-brands.svg" alt="" /> <img className="h-6" src="/icons/creative-commons-sa-brands.svg" alt="" />
</div> </div>
</a> </a>
<p> <p>

View File

@ -1,6 +1,7 @@
import Link from "next/link"; import Link from "next/link";
import ContentPanel from "components/Panels/ContentPanel"; import ContentPanel from "components/Panels/ContentPanel";
import { applyCustomAppProps } from "./_app"; import { applyCustomAppProps } from "./_app";
import Head from "next/head";
applyCustomAppProps(FourOhFour, { applyCustomAppProps(FourOhFour, {
useSubPanel: false, useSubPanel: false,
@ -9,11 +10,16 @@ applyCustomAppProps(FourOhFour, {
export default function FourOhFour(): JSX.Element { export default function FourOhFour(): JSX.Element {
return ( return (
<>
<Head>
<title>Accord&rsquo;s Library - 404</title>
</Head>
<ContentPanel> <ContentPanel>
<h1>404 - Page Not Found</h1> <h1>404 - Page Not Found</h1>
<Link href="/"> <Link href="/">
<a>Go back home</a> <a>Go back home</a>
</Link> </Link>
</ContentPanel> </ContentPanel>
</>
); );
} }

View File

@ -1,7 +1,8 @@
import type { AppProps } from "next/app"; import type { AppProps } from "next/app";
import Head from "next/head";
import MainPanel from "components/Panels/MainPanel"; import MainPanel from "components/Panels/MainPanel";
import "styles/globals.css"; import "styles/index.css";
import "@fontsource/zen-maru-gothic/500.css";
import "@fontsource/vollkorn/700.css";
export type CustomAppProps = { export type CustomAppProps = {
useSubPanel: boolean; useSubPanel: boolean;
@ -16,39 +17,24 @@ export function applyCustomAppProps(
} }
export default function AccordsLibraryApp(appProps: AppProps) { export default function AccordsLibraryApp(appProps: AppProps) {
let additionalClasses = ""; // Apply a different style depending on the given CustomAppProps
if (appProps.Component.customAppProps.useSubPanel) let mainClasses = "grid min-h-screen grid-flow-col";
additionalClasses += " withSubPanel"; if (
if (appProps.Component.customAppProps.useContentPanel) appProps.Component.customAppProps.useSubPanel &&
additionalClasses += " withContentPanel"; appProps.Component.customAppProps.useContentPanel
) {
const siteTitle = mainClasses += " grid-cols-appUseSubContent";
"Accord's Library - Discover • Analyse • Translate • Archive"; } else if (appProps.Component.customAppProps.useSubPanel) {
const siteDescription = mainClasses += " grid-cols-appUseSub";
"Accord's Library aims at gathering and archiving all of Yoko Taros work. Yoko Taro is a Japanese video game director and scenario writer."; } else if (appProps.Component.customAppProps.useContentPanel) {
const siteFavicon = "/favicon.png"; mainClasses += " grid-cols-appUseContent";
const thumbnailImage = "/default_og.jpg"; } else {
mainClasses += " grid-cols-appDefault";
}
return ( return (
<div className={"appContainer" + additionalClasses}> <div className={mainClasses}>
<Head>
<title>{siteTitle}</title>
<meta name="description" content={siteDescription} />
<link rel="icon" href={siteFavicon} />
<meta property="og:image" content={thumbnailImage}></meta>
<meta property="og:image:secure_url" content={thumbnailImage}></meta>
<meta property="og:image:width" content="1200"></meta>
<meta property="og:image:height" content="630"></meta>
<meta property="og:image:alt" content="Accord's Library"></meta>
<meta property="og:image:type" content="image/jpeg"></meta>
<meta name="twitter:card" content="summary_large_image"></meta>
<meta name="twitter:title" content={siteTitle}></meta>
<meta name="twitter:description" content={siteDescription}></meta>
<meta name="twitter:image" content={thumbnailImage}></meta>
</Head>
<MainPanel /> <MainPanel />
<appProps.Component {...appProps.pageProps} /> <appProps.Component {...appProps.pageProps} />
</div> </div>
); );

49
src/pages/_document.tsx Normal file
View File

@ -0,0 +1,49 @@
import Document, {
Html,
Head,
Main,
NextScript,
DocumentContext,
} from "next/document";
class MyDocument extends Document {
static async getInitialProps(ctx: DocumentContext) {
const initialProps = await Document.getInitialProps(ctx);
return { ...initialProps };
}
render() {
// General info about the site
const siteTitle =
"Accord's Library - Discover • Analyse • Translate • Archive";
const siteDescription =
"Accord's Library aims at gathering and archiving all of Yoko Taros work. Yoko Taro is a Japanese video game director and scenario writer.";
const siteFavicon = "/favicon.png";
const thumbnailImage = "/default_og.jpg";
return (
<Html>
<Head>
<meta name="description" content={siteDescription} />
<link rel="icon" href={siteFavicon} />
<meta property="og:image" content={thumbnailImage}></meta>
<meta property="og:image:secure_url" content={thumbnailImage}></meta>
<meta property="og:image:width" content="1200"></meta>
<meta property="og:image:height" content="630"></meta>
<meta property="og:image:alt" content="Accord's Library"></meta>
<meta property="og:image:type" content="image/jpeg"></meta>
<meta name="twitter:card" content="summary_large_image"></meta>
<meta name="twitter:title" content={siteTitle}></meta>
<meta name="twitter:description" content={siteDescription}></meta>
<meta name="twitter:image" content={thumbnailImage}></meta>
</Head>
<body className="bg-light text-black">
<Main />
<NextScript />
</body>
</Html>
);
}
}
export default MyDocument;

View File

@ -8,14 +8,14 @@ import {
getChronologyItems, getChronologyItems,
getChronologyEras, getChronologyEras,
ChronologyItem, ChronologyItem,
ChronologyEra,
ChronologyItemsEvent, ChronologyItemsEvent,
} from "queries/chronology/overview"; } from "queries/chronology/overview";
import { applyCustomAppProps } from "pages/_app"; import { applyCustomAppProps } from "pages/_app";
import { ChronologyEraEntityResponseCollection } from "queries/types";
type Props = { type Props = {
chronologyItems: ChronologyItem[]; chronologyItems: ChronologyItem[];
chronologyEras: ChronologyEra[]; chronologyEras: ChronologyEraEntityResponseCollection;
}; };
applyCustomAppProps(ChronologyOverview, { applyCustomAppProps(ChronologyOverview, {
@ -37,14 +37,11 @@ export default function ChronologyOverview(props: Props): JSX.Element {
return ( return (
<> <>
<SubPanel> <SubPanel>
{props.chronologyEras.map((era: ChronologyEra) => {
if (era.id == undefined) console.warn(era);
})}
<ReturnButton url="/chronology" title="Chronology" /> <ReturnButton url="/chronology" title="Chronology" />
<hr /> <hr />
{props.chronologyEras.map((era: ChronologyEra) => ( {props.chronologyEras.data.map((era) => (
<NavOption <NavOption
key={era.id} key={era.id}
url={"#" + era.attributes.slug} url={"#" + era.attributes.slug}

View File

@ -1,4 +1,5 @@
import ContentPanel from "components/Panels/ContentPanel"; import ContentPanel from "components/Panels/ContentPanel";
import Head from "next/head";
import { applyCustomAppProps } from "./_app"; import { applyCustomAppProps } from "./_app";
applyCustomAppProps(Home, { applyCustomAppProps(Home, {
@ -9,25 +10,28 @@ applyCustomAppProps(Home, {
export default function Home(): JSX.Element { export default function Home(): JSX.Element {
return ( return (
<> <>
<Head>
<title>Accord&rsquo;s Library - Home</title>
</Head>
<ContentPanel> <ContentPanel>
<h2>Discover Analyse Translate Archive</h2> <h2>Discover Analyse Translate Archive</h2>
<h2>What is this?</h2> <h2>What is this?</h2>
<p> <p>
Accord&rsquo;s Library aims at gathering and archiving all of Yoko Accord&rsquo;s Library aims at gathering and archiving all of Yoko
Taros work. Yoko Taro is a Japanese video game director and scenario Taro&rsquo;s work. Yoko Taro is a Japanese video game director and
writer. He is best-known for his work on the NieR and Drakengard scenario writer. He is best-known for his work on the NieR and
(Drag-on Dragoon) franchises. To complement his games, Yoko Taro likes Drakengard (Drag-on Dragoon) franchises. To complement his games, Yoko
to publish side materials in the form of books, novellas, artbooks, Taro likes to publish side materials in the form of books, novellas,
stage plays, manga, drama CDs, and comics. Those side materials can be artbooks, stage plays, manga, drama CDs, and comics. Those side
very difficult to find. His work goes all the way back to 2003, and materials can be very difficult to find. His work goes all the way
most of them are out of print after having been released solely in back to 2003, and most of them are out of print after having been
Japan, sometimes in limited quantities. Their prices on the second released solely in Japan, sometimes in limited quantities. Their
hand market have skyrocketed, ranging all the way to hundreds if not prices on the second hand market have skyrocketed, ranging all the way
thousand of dollars for the rarest items.&nbsp; to hundreds if not thousand of dollars for the rarest items.&nbsp;
</p> </p>
<p> <p>
This is where this library takes its meaning, in trying to help the This is where this library takes its meaning, in trying to help the
community grow by providing translators, writers, and wikis community grow by providing translators, writers, and wiki&rsquo;s
contributors a simple way to access these records filled with stories, contributors a simple way to access these records filled with stories,
artworks, and knowledge. artworks, and knowledge.
</p> </p>
@ -124,12 +128,12 @@ export default function Home(): JSX.Element {
9S -Pods 9S -Pods
</a> </a>
</kbd> </kbd>
. Anyway, there is a lot more to it, you can click on "Syntax help" . Anyway, there is a lot more to it, you can click on &quot;Syntax
next to the Search button for even neater functions. Btw, you can help&quot; next to the Search button for even neater functions. Btw,
create an account to favorite, upvote/downvote posts, or if you want you can create an account to favorite, upvote/downvote posts, or if
to help tagging them. There isn&rsquo;t currently a way for new users you want to help tagging them. There isn&rsquo;t currently a way for
to upload images, you&rsquo;ll have to contact us first and we can new users to upload images, you&rsquo;ll have to contact us first and
decide to enable this function on your account. we can decide to enable this function on your account.
</p> </p>
</ContentPanel> </ContentPanel>
</> </>

View File

@ -20,7 +20,7 @@ export default function Library(props: Props): JSX.Element {
<SubPanel> <SubPanel>
<h2>Library</h2> <h2>Library</h2>
<p> <p>
A comprehensive list of all Yokoverses side materials (books, A comprehensive list of all Yokoverse&rsquo;s side materials (books,
novellas, artbooks, stage plays, manga, drama CDs, and comics). For novellas, artbooks, stage plays, manga, drama CDs, and comics). For
each, we provide photos and/or scans of the content, information about each, we provide photos and/or scans of the content, information about
what it is, when and how it was released, size, initial price what it is, when and how it was released, size, initial price

View File

@ -1,5 +1,6 @@
import { queryGraphQL } from "queries/helpers"; import { queryGraphQL } from "queries/helpers";
import { Source } from "queries/helpers"; import { Source } from "queries/helpers";
import { ChronologyEraEntityResponseCollection } from "queries/types";
export type ChronologyItem = { export type ChronologyItem = {
id: string; id: string;
@ -63,6 +64,7 @@ export async function getChronologyItems(
).chronologyItems.data; ).chronologyItems.data;
} }
/*
export type ChronologyEra = { export type ChronologyEra = {
id: string; id: string;
attributes: ChronologyEraAttributes; attributes: ChronologyEraAttributes;
@ -78,10 +80,11 @@ export type ChronologyEraAttributes = {
export type ChronologyEraTranslation = { export type ChronologyEraTranslation = {
title: string; title: string;
}; };
*/
export async function getChronologyEras( export async function getChronologyEras(
language_code: string | undefined language_code: string | undefined
): Promise<ChronologyEra[]> { ): Promise<ChronologyEraEntityResponseCollection> {
return ( return (
await queryGraphQL( await queryGraphQL(
` `
@ -102,5 +105,5 @@ export async function getChronologyEras(
} }
` `
) )
).chronologyEras.data; );
} }

3583
src/queries/types.ts Normal file

File diff suppressed because it is too large Load Diff

View File

@ -1,108 +0,0 @@
@import url('https://fonts.googleapis.com/css2?family=Vollkorn:wght@400;500;600;700;800;900&display=swap');
@import url('https://fonts.googleapis.com/css2?family=Zen+Maru+Gothic:wght@300;400;500;700;900&display=swap');
:root {
--color-main-light: #ffedd8;
--color-main-base: #e6ccb2;
--color-main-dark: #9c6644;
--color-main-black: #1B1811;
--filter-color-main-dark: invert(44%) sepia(29%) saturate(806%) hue-rotate(340deg) brightness(91%) contrast(85%);
}
html,
body {
padding: 0;
margin: 0;
background-color: var(--color-main-light);
color: var(--color-main-black);
}
.appContainer {
display: grid;
min-height: 100vh;
grid-auto-flow: column;
grid-template-columns: 20rem;
}
.appContainer.withSubPanel {
grid-template-columns: 20rem 20rem;
}
.appContainer.withContentPanel {
grid-template-columns: 20rem 1fr;
}
.appContainer.withSubPanel.withContentPanel {
grid-template-columns: 20rem 20rem 1fr;
}
h1, h2, h3, h4, h5, h6 {
font-family: "Vollkorn";
font-weight: 700;
}
a {
color: inherit;
text-decoration: underline dotted var(--color-main-dark);
transition: .1s color;
text-underline-offset: 0.15em;
}
a:hover {
color: var(--color-main-dark);
}
* {
box-sizing: border-box;
font-family: "Zen Maru Gothic";
font-weight: 500;
}
button {
display: grid;
place-content: center;
place-items: center;
border: .1rem solid var(--color-main-dark);
color: var(--color-main-dark);
background: var(--color-main-light);
border-radius: 100vmax;
padding: 0.4em 1em;
cursor: pointer;
transition: .1s color, .1s background-color;
}
button:hover {
background: var(--color-main-dark);
color: var(--color-main-light);
}
/* SCROLLBARS STYLING */
* {
scrollbar-color: var(--color-main-dark) transparent;
}
*::selection {
background-color: var(--color-main-dark);
color: var(--color-main-light);
border-radius: 1em;
}
*:target {
scroll-margin-top: 1em;
}
*::-webkit-scrollbar {
width: 12px; /* width of the entire scrollbar */
}
*::-webkit-scrollbar-track {
background: transparent; /* color of the tracking area */
}
*::-webkit-scrollbar-thumb {
background-color: var(--color-main-dark); /* color of the scroll thumb */
border-radius: 100vmax; /* roundness of the scroll thumb */
border: 3px solid var(--color-main-light); /* creates padding around scroll thumb */
}

94
src/styles/index.css Normal file
View File

@ -0,0 +1,94 @@
@tailwind base;
@tailwind components;
@tailwind utilities;
@layer base {
html,
body {
padding: 0;
margin: 0;
background-color: var(--color-main-light);
color: var(--color-main-black);
}
/* BUTTONS */
button {
display: grid;
place-content: center;
place-items: center;
border: 0.1rem solid theme("colors.dark");
color: theme("colors.dark");
background: theme("colors.light");
border-radius: 100vmax;
padding: 0.4em 1em;
cursor: pointer;
transition: 0.1s color, 0.1s background-color;
}
button:hover {
background: theme("colors.dark");
color: theme("colors.light");
}
/* FONT SETTING */
* {
box-sizing: border-box;
font-family: "Zen Maru Gothic";
font-weight: 500;
}
h1,
h2,
h3,
h4,
h5,
h6 {
font-family: "Vollkorn";
font-weight: 900;
}
/* LINKS */
a {
color: inherit;
text-decoration: underline dotted theme("colors.dark");
transition: 0.1s color;
text-underline-offset: 0.15em;
}
a:hover {
color: theme("colors.dark");
}
/* SCROLLBARS STYLING */
* {
scrollbar-color: theme("colors.dark") transparent;
scrollbar-width: thin;
}
*::selection {
background-color: theme("colors.dark");
color: theme("colors.light");
border-radius: 1em;
}
*:target {
scroll-margin-top: 1em;
}
*::-webkit-scrollbar {
width: 12px; /* width of the entire scrollbar */
}
*::-webkit-scrollbar-track {
background: transparent; /* color of the tracking area */
}
*::-webkit-scrollbar-thumb {
background-color: theme("colors.dark"); /* color of the scroll thumb */
border-radius: 100vmax; /* roundness of the scroll thumb */
border: 3px solid theme("colors.light"); /* creates padding around scroll thumb */
}
}

22
tailwind.config.js Normal file
View File

@ -0,0 +1,22 @@
module.exports = {
content: ["./src/**/*.{tsx,ts}"],
theme: {
colors: {
light: "#ffedd8",
base: "#e6ccb2",
dark: "#9c6644",
black: "#1B1811",
},
extend: {
gridTemplateColumns: {
appDefault: "20rem",
appUseSub: "20rem 20rem",
appUseContent: "20rem 1fr",
appUseSubContent: "20rem 20rem 1fr",
},
},
},
plugins: [
require("@tailwindcss/typography"),
],
};