aboutsummaryrefslogtreecommitdiffhomepage
path: root/src
diff options
context:
space:
mode:
authorKevin Hoerr <kjhoerr@protonmail.com>2022-11-21 18:19:16 -0500
committerGitHub <noreply@github.com>2022-11-21 18:19:16 -0500
commit651f019141b488a82fd42028bce5b0003abbfaf5 (patch)
tree5be06913d021752cb0a1d3f809f66b27359619c5 /src
parent6ec00afac5afc892dca5a184b66467d9408f14a5 (diff)
downloadsubmelon.dev-651f019141b488a82fd42028bce5b0003abbfaf5.tar.gz
submelon.dev-651f019141b488a82fd42028bce5b0003abbfaf5.tar.bz2
submelon.dev-651f019141b488a82fd42028bce5b0003abbfaf5.zip
Layout changes (#15)
* Layout refactor and standardization * Use split to condense short array * Fix verbage
Diffstat (limited to 'src')
-rw-r--r--src/components/Footer.tsx103
-rw-r--r--src/components/Layout.tsx30
-rw-r--r--src/components/index.ts4
-rw-r--r--src/pages/404.tsx35
-rw-r--r--src/pages/index.tsx113
-rw-r--r--src/util/timestamp.ts48
6 files changed, 147 insertions, 186 deletions
diff --git a/src/components/Footer.tsx b/src/components/Footer.tsx
deleted file mode 100644
index 3e6932b..0000000
--- a/src/components/Footer.tsx
+++ /dev/null
@@ -1,103 +0,0 @@
-import React from "react";
-import { Footer } from "../styles";
-
-const SHORT_CHARS = [
- "0",
- "1",
- "2",
- "3",
- "4",
- "5",
- "6",
- "7",
- "8",
- "9",
- "a",
- "b",
- "c",
- "d",
- "e",
- "f",
- "g",
- "h",
- "i",
- "j",
- "k",
- "l",
- "m",
- "n",
- "o",
- "p",
- "q",
- "r",
- "s",
- "t",
- "u",
- "v",
- "w",
- "x",
- "y",
- "z",
- "A",
- "B",
- "C",
- "D",
- "E",
- "F",
- "G",
- "H",
- "I",
- "J",
- "K",
- "L",
- "M",
- "N",
- "O",
- "P",
- "Q",
- "R",
- "S",
- "T",
- "U",
- "V",
- "W",
- "X",
- "Y",
- "Z",
-];
-
-function toShort(valu: number): string {
- return (
- valu
- .toString()
- .match(/.{1,2}/g)
- ?.map((s) => SHORT_CHARS[parseInt(s)])
- .join("") ?? ""
- );
-}
-
-function getTimestamp(seconds: number): string {
- const date = new Date(seconds * 1000);
- const dateArr = [
- date.getUTCFullYear(),
- date.getUTCMonth(),
- date.getUTCDate(),
- date.getUTCHours(),
- date.getUTCMinutes(),
- ];
-
- return dateArr.map(toShort).join(".") + "-0";
-}
-
-const FooterInfo = ({ timestamp }) => {
- return (
- <Footer>
- <span>
- &copy;2022 kjhoerr@https://submelon.dev/:
- {getTimestamp(parseInt(timestamp))}
- </span>
- </Footer>
- );
-};
-
-export default FooterInfo;
diff --git a/src/components/Layout.tsx b/src/components/Layout.tsx
new file mode 100644
index 0000000..6cc70ed
--- /dev/null
+++ b/src/components/Layout.tsx
@@ -0,0 +1,30 @@
+import React from "react";
+import { IconContext } from "react-icons/lib";
+import { Content, Footer } from "../styles";
+import package_json from "../../package.json";
+import { getTimestamp } from "../util/timestamp";
+
+const VERSION = package_json.version;
+
+const Layout = ({ children }) => {
+ return (
+ <React.StrictMode>
+ <main>
+ <IconContext.Provider
+ value={{ size: "20", style: { marginBottom: "-4px" } }}
+ >
+ <Content>{children}</Content>
+
+ <Footer>
+ <span>
+ &copy;2022 kjhoerr@https://submelon.dev/:
+ {getTimestamp(Number(VERSION))}
+ </span>
+ </Footer>
+ </IconContext.Provider>
+ </main>
+ </React.StrictMode>
+ );
+};
+
+export default Layout;
diff --git a/src/components/index.ts b/src/components/index.ts
new file mode 100644
index 0000000..6e7bcb7
--- /dev/null
+++ b/src/components/index.ts
@@ -0,0 +1,4 @@
+import BlockLink from "./BlockLink";
+import Layout from "./Layout";
+
+export { BlockLink, Layout };
diff --git a/src/pages/404.tsx b/src/pages/404.tsx
index 0a593d6..d8d27cb 100644
--- a/src/pages/404.tsx
+++ b/src/pages/404.tsx
@@ -1,26 +1,23 @@
-import * as React from "react";
-import BlockLink from "../components/BlockLink";
-import { BlockBody, BlockHeader, Content } from "../styles";
+import React from "react";
+import { BlockLink, Layout } from "../components";
+import { BlockBody, BlockHeader } from "../styles";
import "../styles/main.css";
-// markup
const NotFoundPage = (): React.ReactElement => {
return (
- <main>
- <Content>
- <BlockHeader>Not found</BlockHeader>
- <BlockBody>
- Sorry{" "}
- <span role="img" aria-label="Pensive emoji">
- 😔
- </span>{" "}
- we couldn&apos;t find what you were looking for.
- </BlockBody>
- <BlockLink href="/" aria-label="Return to the front page">
- Home
- </BlockLink>
- </Content>
- </main>
+ <Layout>
+ <BlockHeader>Not found</BlockHeader>
+ <BlockBody>
+ Sorry{" "}
+ <span role="img" aria-label="Pensive emoji">
+ 😔
+ </span>{" "}
+ we couldn&apos;t find what you were looking for.
+ </BlockBody>
+ <BlockLink href="/" aria-label="Return to the front page">
+ Home
+ </BlockLink>
+ </Layout>
);
};
diff --git a/src/pages/index.tsx b/src/pages/index.tsx
index e4b4ec6..370a10d 100644
--- a/src/pages/index.tsx
+++ b/src/pages/index.tsx
@@ -2,74 +2,59 @@ import React from "react";
import { StaticImage } from "gatsby-plugin-image";
import "../styles/main.css";
import { FaGithub, FaMastodon } from "react-icons/fa";
-import BlockLink from "../components/BlockLink";
-import Footer from "../components/Footer";
-import { BlockBody, BlockHeader, Content } from "../styles";
-import package_json from "../../package.json";
-import { IconContext } from "react-icons";
+import { BlockLink, Layout } from "../components";
+import { BlockBody, BlockHeader } from "../styles";
-const VERSION = package_json.version;
-
-// markup
const IndexPage = (): React.ReactElement => {
return (
- <main>
- <IconContext.Provider
- value={{ size: "20", style: { marginBottom: "-4px" } }}
+ <Layout>
+ <div>
+ <StaticImage
+ src="../images/main.png"
+ alt="Picture of Kevin Hoerr"
+ placeholder="tracedSVG"
+ layout="fixed"
+ width={350}
+ height={350}
+ />
+ </div>
+ <BlockHeader>Hello!</BlockHeader>
+ <BlockBody>
+ <p>
+ I&apos;m a computer science and math graduate from Millersville
+ University. I work as an IT consultant and specialize in development
+ operations and systems validation for web applications.
+ </p>
+ <p>
+ My most recent projects have been focused on full-stack development. I
+ use Kubernetes for orchestration and NextJS for the front-end. For
+ back-end development, I have built services enabled by Java with
+ Spring Boot, Quarkus, and rust+actix-web with a GraphQL serving public
+ API.
+ </p>
+ <p>
+ I run a personal Kubernetes cluster at home using MicroOS and k3d. I
+ have also run multiple clusters via DigitalOcean with deployments
+ dedicated for hosting git projects, CI/CD, and code coverage. Since
+ then all projects have been moved to GitHub.
+ </p>
+ <em>- Kevin H.</em>
+ </BlockBody>
+ <BlockLink
+ href="https://cybr.es/@kjhoerr"
+ rel="me"
+ aria-label="My Mastodon account"
>
- <Content>
- <div>
- <StaticImage
- src="../images/main.png"
- alt="Picture of Kevin Hoerr"
- placeholder="tracedSVG"
- layout="fixed"
- width={350}
- height={350}
- />
- </div>
- <BlockHeader>Hello!</BlockHeader>
- <BlockBody>
- <p>
- I&apos;m a computer science and math graduate from Millersville
- University. I work as an IT consultant and specialize in
- development operations and systems validation for web
- applications.
- </p>
- <p>
- My most recent projects have been focused on full-stack
- development. I use Kubernetes for orchestration and NextJS for the
- front-end. For back-end development, I have built services enabled
- by Java with Spring Boot, Quarkus, and rust+actix-web with a
- GraphQL serving public API.
- </p>
- <p>
- I run a personal Kubernetes cluster at home using MicroOS and k3d.
- I have also run multiple clusters via DigitalOcean with
- deployments dedicated for hosting git projects, CI/CD, and code
- coverage. Since then all projects have been moved to GitHub.
- </p>
- <em>- Kevin H.</em>
- </BlockBody>
- <BlockLink
- href="https://cybr.es/@kjhoerr"
- rel="me"
- aria-label="My Mastodon account"
- >
- <FaMastodon /> @kjhoerr@cybr.es
- </BlockLink>
- <BlockLink
- href="https://github.com/kjhoerr"
- rel="me"
- aria-label="My GitHub account with my most active personal projects"
- >
- <FaGithub /> kjhoerr on GitHub
- </BlockLink>
- </Content>
-
- <Footer timestamp={VERSION} />
- </IconContext.Provider>
- </main>
+ <FaMastodon /> @kjhoerr@cybr.es
+ </BlockLink>
+ <BlockLink
+ href="https://github.com/kjhoerr"
+ rel="me"
+ aria-label="My GitHub account with my most active personal projects"
+ >
+ <FaGithub /> kjhoerr on GitHub
+ </BlockLink>
+ </Layout>
);
};
diff --git a/src/util/timestamp.ts b/src/util/timestamp.ts
new file mode 100644
index 0000000..f53f5ad
--- /dev/null
+++ b/src/util/timestamp.ts
@@ -0,0 +1,48 @@
+const SHORT_CHARS =
+ "0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ".split("");
+
+/**
+ * Transforms a number into a custom 62 char expression of that number,
+ * effectively making a "short" version of that number (0-9a-zA-Z). This does
+ * NOT convert to a base-62 number.
+ *
+ * There are vast gaps in the effective translation of numbers, which is why
+ * this function is mostly for concisely translating dates prior to the year
+ * 2063. Since all other values associated with dates (month, day, hours,
+ * minutes, seconds) effectively fall within the range of a single character,
+ * this is an accepted shortcoming.
+ *
+ * Examples:
+ *
+ * 0 = 0
+ *
+ * 48 = M
+ *
+ * 2022 = km (in base-62 this would be wC)
+ */
+export function toShort(valu: number): string {
+ return (
+ valu
+ .toString()
+ .match(/.{1,2}/g)
+ ?.map((s) => SHORT_CHARS[parseInt(s)])
+ .join("") ?? ""
+ );
+}
+
+/**
+ * Translates a Unix EPOCH timestamp to a 62-char expression of the date. See
+ * the `toShort()` method for more details on the meaning of the final output.
+ */
+export function getTimestamp(seconds: number): string {
+ const date = new Date(seconds * 1000);
+ const dateArr = [
+ date.getUTCFullYear(),
+ date.getUTCMonth(),
+ date.getUTCDate(),
+ date.getUTCHours(),
+ date.getUTCMinutes(),
+ ];
+
+ return dateArr.map(toShort).join(".") + "-0";
+}