Added notes to V1
This commit is contained in:
3
404.html
3
404.html
@@ -62,8 +62,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="nf-actions">
|
<div class="nf-actions">
|
||||||
<a href="index.html" class="btn btn-primary">← Back home</a>
|
<a href="/" class="btn btn-primary">← Back home</a>
|
||||||
<a href="index.html#projects" class="btn btn-ghost">View projects</a>
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
</main>
|
</main>
|
||||||
|
|||||||
@@ -10,12 +10,12 @@
|
|||||||
<script src="/frameworks/jquery-3.3.1.min.js"></script>
|
<script src="/frameworks/jquery-3.3.1.min.js"></script>
|
||||||
<script src="/frameworks/bootstrap.min.js"></script>
|
<script src="/frameworks/bootstrap.min.js"></script>
|
||||||
<link rel='stylesheet prefetch' href='https://netdna.bootstrapcdn.com/bootstrap/3.1.0/css/bootstrap.css'>
|
<link rel='stylesheet prefetch' href='https://netdna.bootstrapcdn.com/bootstrap/3.1.0/css/bootstrap.css'>
|
||||||
<link rel="stylesheet" href="style.css" />
|
<link rel="stylesheet" href="style.css"/>
|
||||||
|
|
||||||
</head>
|
</head>
|
||||||
|
|
||||||
<body>
|
<body>
|
||||||
<div class="navbar navbar-inverse navbar-fixed-top" role="navigation">
|
<div class="navbar navbar-inverse navbar-fixed-top" role="navigation">
|
||||||
<div class="container">
|
<div class="container">
|
||||||
<div class="navbar-header">
|
<div class="navbar-header">
|
||||||
<button type="button" class="navbar-toggle" data-toggle="collapse" data-target=".navbar-collapse">
|
<button type="button" class="navbar-toggle" data-toggle="collapse" data-target=".navbar-collapse">
|
||||||
@@ -39,9 +39,9 @@
|
|||||||
</ul>
|
</ul>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="container-fluid big-logo-row">
|
<div class="container-fluid big-logo-row">
|
||||||
<div class="container">
|
<div class="container">
|
||||||
<div class="row">
|
<div class="row">
|
||||||
<div class="col-xs-12 big-logo-container">
|
<div class="col-xs-12 big-logo-container">
|
||||||
@@ -49,15 +49,17 @@
|
|||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="container">
|
<div class="container">
|
||||||
<div class="row">
|
<div class="row">
|
||||||
<div class="col-lg-9 col-md-8 col-sm-12">
|
<div class="col-lg-9 col-md-8 col-sm-12">
|
||||||
<h2>Welcome to my website</h2>
|
<h2>Welcome to my website</h2>
|
||||||
<div class="contents">
|
<div class="contents">
|
||||||
<div id="quoteJump" class="quoteDiv">
|
<div id="quoteJump" class="quoteDiv">
|
||||||
<h3>Quote of the day</h3>
|
<h3>Quote of the day</h3>
|
||||||
|
<p class="v4-margin-note">The original
|
||||||
|
python webscraper script no longer works, the below quote is just a placeholder.</p>
|
||||||
<p><b>Quote: </b>
|
<p><b>Quote: </b>
|
||||||
Try to keep your soul young and quivering right up to old age.
|
Try to keep your soul young and quivering right up to old age.
|
||||||
</p>
|
</p>
|
||||||
@@ -67,36 +69,9 @@
|
|||||||
</div>
|
</div>
|
||||||
<div class="intro">
|
<div class="intro">
|
||||||
<h3 id="introjump">About me</h3>
|
<h3 id="introjump">About me</h3>
|
||||||
|
<p class="v4-margin-note">The original
|
||||||
<p>The Union of the indestructible republics of the free ones
|
about me section was full of nonsense memes and has been removed.</p>
|
||||||
The Great Russia has forever consolidated itself.
|
<p>A cool website to show my projects</p>
|
||||||
Long live the people created by the will of the people
|
|
||||||
A single, mighty Soviet Union!</p>
|
|
||||||
|
|
||||||
<p>Be glorious, our free Fatherland,
|
|
||||||
Friendship, peoples a reliable stronghold!
|
|
||||||
The Soviet banner, the banner of the people
|
|
||||||
Let it lead from victory to victory!</p>
|
|
||||||
|
|
||||||
<p>Through the thunderstorms the sun of freedom shone,
|
|
||||||
And Lenin, the great one, illumined our way.
|
|
||||||
We were brought up by Stalin - to be faithful to the people.
|
|
||||||
We were inspired by work and deeds.</p>
|
|
||||||
|
|
||||||
<p>Be glorious, Fatherland freer,
|
|
||||||
Happiness of peoples reliable stronghold!
|
|
||||||
The Soviet banner, the banner of the people
|
|
||||||
Let it lead from victory to victory!</p>
|
|
||||||
|
|
||||||
<p>We raised our army in the battles,
|
|
||||||
The invaders of the vile from the road are estimated!
|
|
||||||
We are in the battles to decide the fate of generations,
|
|
||||||
We will lead our glory to our Fatherland!</p>
|
|
||||||
|
|
||||||
<p>Be glorious, our free Fatherland,
|
|
||||||
the glory of peoples is a reliable stronghold!
|
|
||||||
The Soviet banner, the banner of the people
|
|
||||||
Let it lead from victory to victory!</p>
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="projects">
|
<div class="projects">
|
||||||
@@ -192,10 +167,10 @@
|
|||||||
</div>
|
</div>
|
||||||
</div><!--/.col-xs-12 -->
|
</div><!--/.col-xs-12 -->
|
||||||
</div><!--/.row -->
|
</div><!--/.row -->
|
||||||
</div><!--/.container -->
|
</div><!--/.container -->
|
||||||
|
|
||||||
<script src="script.js">
|
<script src="script.js">
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
</body>
|
</body>
|
||||||
<footer>
|
<footer>
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
body{
|
body {
|
||||||
overflow-x: hidden;
|
overflow-x: hidden;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -8,7 +8,10 @@ body{
|
|||||||
border-bottom: none;
|
border-bottom: none;
|
||||||
}
|
}
|
||||||
|
|
||||||
a{font-family: 'Roboto Condensed', sans-serif;}
|
a {
|
||||||
|
font-family: 'Roboto Condensed', sans-serif;
|
||||||
|
}
|
||||||
|
|
||||||
.navbar-inverse .navbar-toggle {
|
.navbar-inverse .navbar-toggle {
|
||||||
border: 1px solid #333;
|
border: 1px solid #333;
|
||||||
border-color: rgba(0, 0, 0, 0.7);
|
border-color: rgba(0, 0, 0, 0.7);
|
||||||
@@ -61,35 +64,42 @@ a{font-family: 'Roboto Condensed', sans-serif;}
|
|||||||
background: white;
|
background: white;
|
||||||
color: black;
|
color: black;
|
||||||
}
|
}
|
||||||
|
|
||||||
.big-logo-row .big-logo-container {
|
.big-logo-row .big-logo-container {
|
||||||
padding-top: 50px;
|
padding-top: 50px;
|
||||||
}
|
}
|
||||||
|
|
||||||
.big-logo-row h1 {
|
.big-logo-row h1 {
|
||||||
font-size: 4em;
|
font-size: 4em;
|
||||||
margin: 0;
|
margin: 0;
|
||||||
padding: 0 0 15px 0;
|
padding: 0 0 15px 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@media (min-width: 400px) {
|
@media (min-width: 400px) {
|
||||||
.big-logo-row h1 {
|
.big-logo-row h1 {
|
||||||
font-size: 4.5em;
|
font-size: 4.5em;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@media (min-width: 440px) {
|
@media (min-width: 440px) {
|
||||||
.big-logo-row h1 {
|
.big-logo-row h1 {
|
||||||
font-size: 5.5em;
|
font-size: 5.5em;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@media (min-width: 500px) {
|
@media (min-width: 500px) {
|
||||||
.big-logo-row h1 {
|
.big-logo-row h1 {
|
||||||
font-size: 6.5em;
|
font-size: 6.5em;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@media (min-width: 630px) {
|
@media (min-width: 630px) {
|
||||||
.big-logo-row h1 {
|
.big-logo-row h1 {
|
||||||
font-size: 7.5em;
|
font-size: 7.5em;
|
||||||
overflow-x: hidden;
|
overflow-x: hidden;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@media (min-width: 768px) {
|
@media (min-width: 768px) {
|
||||||
.big-logo-row h1 {
|
.big-logo-row h1 {
|
||||||
font-size: 9em;
|
font-size: 9em;
|
||||||
@@ -97,6 +107,7 @@ a{font-family: 'Roboto Condensed', sans-serif;}
|
|||||||
overflow-x: hidden;
|
overflow-x: hidden;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@media (min-width: 1200px) {
|
@media (min-width: 1200px) {
|
||||||
.big-logo-row h1 {
|
.big-logo-row h1 {
|
||||||
font-size: 12em;
|
font-size: 12em;
|
||||||
@@ -104,38 +115,38 @@ a{font-family: 'Roboto Condensed', sans-serif;}
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
h2{
|
h2 {
|
||||||
font-size: 41px;
|
font-size: 41px;
|
||||||
font-weight: bold;
|
font-weight: bold;
|
||||||
font-family: 'Roboto Condensed', sans-serif;
|
font-family: 'Roboto Condensed', sans-serif;
|
||||||
color: black;
|
color: black;
|
||||||
}
|
}
|
||||||
|
|
||||||
p{
|
p {
|
||||||
font-size: 20px;
|
font-size: 20px;
|
||||||
font-family: 'Roboto Condensed', sans-serif;
|
font-family: 'Roboto Condensed', sans-serif;
|
||||||
color: #333;
|
color: #333;
|
||||||
text-decoration: none;
|
text-decoration: none;
|
||||||
}
|
}
|
||||||
|
|
||||||
h3{
|
h3 {
|
||||||
text-align: center;
|
text-align: center;
|
||||||
font-size: 30px;
|
font-size: 30px;
|
||||||
font-family: 'Roboto Condensed', sans-serif;
|
font-family: 'Roboto Condensed', sans-serif;
|
||||||
color: black;
|
color: black;
|
||||||
}
|
}
|
||||||
|
|
||||||
.projects, .intro{
|
.projects, .intro {
|
||||||
border-bottom: thin solid #333;
|
border-bottom: thin solid #333;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
.picturebox{
|
.picturebox {
|
||||||
list-style-type: none;
|
list-style-type: none;
|
||||||
float: left;
|
float: left;
|
||||||
}
|
}
|
||||||
|
|
||||||
footer{
|
footer {
|
||||||
padding: 20px;
|
padding: 20px;
|
||||||
background-color: #e0e0e0;
|
background-color: #e0e0e0;
|
||||||
font-family: 'Roboto Condensed', sans-serif;
|
font-family: 'Roboto Condensed', sans-serif;
|
||||||
@@ -167,7 +178,7 @@ ul {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#overlay {
|
#overlay {
|
||||||
background: rgba(0,0,0, .8);
|
background: rgba(0, 0, 0, .8);
|
||||||
width: 100%;
|
width: 100%;
|
||||||
height: 100%;
|
height: 100%;
|
||||||
position: absolute;
|
position: absolute;
|
||||||
@@ -191,3 +202,43 @@ ul {
|
|||||||
width: 100%;
|
width: 100%;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.v4-margin-note {
|
||||||
|
position: relative;
|
||||||
|
margin: 4px 0 20px 0;
|
||||||
|
padding: 30px 16px 12px 16px;
|
||||||
|
border-left: 2px solid rgba(243, 139, 168, 0.6);
|
||||||
|
background: linear-gradient(135deg, rgba(243, 139, 168, 0.07) 0%, rgba(243, 139, 168, 0.02) 60%, transparent 100%);
|
||||||
|
color: #3d3f53;
|
||||||
|
font-size: 13px;
|
||||||
|
line-height: 1.65;
|
||||||
|
font-family: 'JetBrains Mono', 'Courier New', monospace;
|
||||||
|
font-style: italic;
|
||||||
|
max-width: 680px;
|
||||||
|
border-radius: 0 6px 6px 0;
|
||||||
|
box-shadow: inset 0 0 0 1px rgba(243, 139, 168, 0.07), 2px 2px 8px rgba(0, 0, 0, 0.04);
|
||||||
|
}
|
||||||
|
|
||||||
|
.v4-margin-note::before {
|
||||||
|
content: '✎ archived note';
|
||||||
|
position: absolute;
|
||||||
|
top: 9px;
|
||||||
|
left: 16px;
|
||||||
|
color: rgba(243, 139, 168, 0.85);
|
||||||
|
font-size: 10px;
|
||||||
|
font-style: normal;
|
||||||
|
font-weight: 700;
|
||||||
|
text-transform: uppercase;
|
||||||
|
letter-spacing: 0.12em;
|
||||||
|
font-family: 'JetBrains Mono', 'Courier New', monospace;
|
||||||
|
}
|
||||||
|
|
||||||
|
.v4-margin-note::after {
|
||||||
|
content: '';
|
||||||
|
position: absolute;
|
||||||
|
top: 0;
|
||||||
|
left: 0;
|
||||||
|
right: 0;
|
||||||
|
height: 1px;
|
||||||
|
background: linear-gradient(90deg, rgba(243, 139, 168, 0.4), transparent);
|
||||||
|
border-radius: 0 6px 0 0;
|
||||||
|
}
|
||||||
4
icons/github.svg
Normal file
4
icons/github.svg
Normal file
@@ -0,0 +1,4 @@
|
|||||||
|
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24" aria-hidden="true">
|
||||||
|
<path d="M12 0C5.37 0 0 5.37 0 12c0 5.31 3.435 9.795 8.205 11.385.6.105.825-.255.825-.57 0-.285-.015-1.23-.015-2.235-3.015.555-3.795-.735-4.035-1.41-.135-.345-.72-1.41-1.23-1.695-.42-.225-1.02-.78-.015-.795.945-.015 1.62.87 1.845 1.23 1.08 1.815 2.805 1.305 3.495.99.105-.78.42-1.305.765-1.605-2.67-.3-5.46-1.335-5.46-5.925 0-1.305.465-2.385 1.23-3.225-.12-.3-.54-1.53.12-3.18 0 0 1.005-.315 3.3 1.23.96-.27 1.98-.405 3-.405s2.04.135 3 .405c2.295-1.56 3.3-1.23 3.3-1.23.66 1.65.24 2.88.12 3.18.765.84 1.23 1.905 1.23 3.225 0 4.605-2.805 5.625-5.475 5.925.435.375.81 1.095.81 2.22 0 1.605-.015 2.895-.015 3.3 0 .315.225.69.825.57A12.02 12.02 0 0 0 24 12c0-6.63-5.37-12-12-12z" />
|
||||||
|
</svg>
|
||||||
|
|
||||||
|
After Width: | Height: | Size: 769 B |
4
icons/linkedin.svg
Normal file
4
icons/linkedin.svg
Normal file
@@ -0,0 +1,4 @@
|
|||||||
|
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24" aria-hidden="true">
|
||||||
|
<path d="M20.447 20.452h-3.554v-5.569c0-1.328-.027-3.037-1.852-3.037-1.853 0-2.136 1.445-2.136 2.939v5.667H9.351V9h3.414v1.561h.046c.477-.9 1.637-1.85 3.37-1.85 3.601 0 4.267 2.37 4.267 5.455v6.286zM5.337 7.433a2.062 2.062 0 0 1-2.063-2.065 2.064 2.064 0 1 1 2.063 2.065zm1.782 13.019H3.555V9h3.564v11.452zM22.225 0H1.771C.792 0 0 .774 0 1.729v20.542C0 23.227.792 24 1.771 24h20.451C23.2 24 24 23.227 24 22.271V1.729C24 .774 23.2 0 22.222 0h.003z" />
|
||||||
|
</svg>
|
||||||
|
|
||||||
|
After Width: | Height: | Size: 541 B |
175
index.html
175
index.html
@@ -4,9 +4,9 @@
|
|||||||
<head>
|
<head>
|
||||||
<meta charset="UTF-8"/>
|
<meta charset="UTF-8"/>
|
||||||
<meta name="viewport" content="width=device-width, initial-scale=1.0"/>
|
<meta name="viewport" content="width=device-width, initial-scale=1.0"/>
|
||||||
<title>Havox — John Gatward</title>
|
<title>Havox</title>
|
||||||
<meta name="description"
|
<meta name="description"
|
||||||
content="John Gatward's portfolio: software engineering projects spanning backend systems, infrastructure, and creative developer experiments."/>
|
content="John Gatward's portfolio"/>
|
||||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||||
<link
|
<link
|
||||||
href="https://fonts.googleapis.com/css2?family=JetBrains+Mono:ital,wght@0,400;0,700;1,400&family=Fraunces:ital,opsz,wght@0,9..144,300;0,9..144,600;1,9..144,300&display=swap"
|
href="https://fonts.googleapis.com/css2?family=JetBrains+Mono:ital,wght@0,400;0,700;1,400&family=Fraunces:ital,opsz,wght@0,9..144,300;0,9..144,600;1,9..144,300&display=swap"
|
||||||
@@ -29,7 +29,7 @@
|
|||||||
|
|
||||||
<!-- ─── Hero ─────────────────────────────────────────────────── -->
|
<!-- ─── Hero ─────────────────────────────────────────────────── -->
|
||||||
<section id="hero">
|
<section id="hero">
|
||||||
<p class="hero-eyebrow">// havox.org — v4</p>
|
<p class="hero-eyebrow">// havox.org - v4</p>
|
||||||
<h1 class="hero-name">John <em>Gatward</em></h1>
|
<h1 class="hero-name">John <em>Gatward</em></h1>
|
||||||
<p class="hero-subtitle">Software Engineer</p>
|
<p class="hero-subtitle">Software Engineer</p>
|
||||||
<p class="hero-desc">
|
<p class="hero-desc">
|
||||||
@@ -39,7 +39,6 @@
|
|||||||
curiosity</span></span>
|
curiosity</span></span>
|
||||||
<span class="hero-by-line"><span class="hero-by">Unofficial family cloud engineer</span><span
|
<span class="hero-by-line"><span class="hero-by">Unofficial family cloud engineer</span><span
|
||||||
class="hero-by-role">by necessity</span></span>
|
class="hero-by-role">by necessity</span></span>
|
||||||
<span class="hero-by-footer">I like building useful things and understanding how they work.</span>
|
|
||||||
</p>
|
</p>
|
||||||
<div class="hero-links">
|
<div class="hero-links">
|
||||||
<a href="#projects" class="btn btn-primary">View projects</a>
|
<a href="#projects" class="btn btn-primary">View projects</a>
|
||||||
@@ -61,28 +60,26 @@
|
|||||||
<!-- Bio blocks -->
|
<!-- Bio blocks -->
|
||||||
<div class="about-grid reveal" style="transition-delay:0.05s">
|
<div class="about-grid reveal" style="transition-delay:0.05s">
|
||||||
|
|
||||||
|
<div class="about-block">
|
||||||
|
<p>Havox started in 2017 as a place to dump whatever projects I had written. Four redesigns and several
|
||||||
|
dead domains later, it's still going. Less a portfolio, more a scrapbook.</p>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="about-block">
|
<div class="about-block">
|
||||||
<span class="about-block-tag tag tag-blue">day job</span>
|
<span class="about-block-tag tag tag-blue">day job</span>
|
||||||
<p>Backend engineer at <strong>Sainsbury's</strong> Supply Chain & Logistics. Microservices,
|
<p>Backend engineer at <strong>Sainsbury's</strong> Supply Chain & Logistics. It's good fun.</p>
|
||||||
Spring Boot, Kafka, MongoDB, AWS. It's good fun.</p>
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="about-block">
|
<div class="about-block">
|
||||||
<span class="about-block-tag tag tag-teal">dev</span>
|
<span class="about-block-tag tag tag-teal">dev</span>
|
||||||
<p>Fascinated with new languages, frameworks, and shiny tech I probably don’t need. Constantly
|
<p>Fascinated with new languages, frameworks, and shiny tech I probably don’t need. Constantly
|
||||||
tinkering, breaking things, and learning just enough to build something cooler next time.</p>
|
learning just enough to build something slightly cooler next time.</p>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="about-block">
|
<div class="about-block">
|
||||||
<span class="about-block-tag tag tag-yellow">linux</span>
|
<span class="about-block-tag tag tag-yellow">linux</span>
|
||||||
<p>Long-time Linux user and recovering distro-hopper. Currently: Hyprland on Void. Home server
|
<p>Long-time Linux user and distro-hopper. Self-hosted server running 24/7 for friends and family who
|
||||||
running 24/7 for friends and family who didn't ask for it but appreciate it.</p>
|
didn't ask for it but <s>probably</s> definitely appreciate it.</p>
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="about-block">
|
|
||||||
<span class="about-block-tag tag tag-mauve">havox</span>
|
|
||||||
<p>Started in 2017 as a place to dump whatever I found interesting. Four redesigns and several dead
|
|
||||||
domains later, it's still going. Less a portfolio, more a paper trail.</p>
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
</div>
|
</div>
|
||||||
@@ -97,7 +94,7 @@
|
|||||||
<div class="v-content">
|
<div class="v-content">
|
||||||
<div class="v-title">Havox V4 <span class="v-current-badge">current</span></div>
|
<div class="v-title">Havox V4 <span class="v-current-badge">current</span></div>
|
||||||
<div class="v-year">2026 → present</div>
|
<div class="v-year">2026 → present</div>
|
||||||
<div class="v-desc">Catppuccin Mocha. Single page. Built to highlight projects and craft.</div>
|
<div class="v-desc">Catppuccin Mocha. Single page. Professional.</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
@@ -106,7 +103,9 @@
|
|||||||
<div class="v-content">
|
<div class="v-content">
|
||||||
<div class="v-title">Havox V3 <span class="v-link-arrow">↗</span></div>
|
<div class="v-title">Havox V3 <span class="v-link-arrow">↗</span></div>
|
||||||
<div class="v-year">2022 → 2025</div>
|
<div class="v-year">2022 → 2025</div>
|
||||||
<div class="v-desc">Borrowed a professional looking template. Wasn't very 'me'.</div>
|
<div class="v-desc">Borrowed a professional template and tried to make it suit my needs. Wasn't
|
||||||
|
very 'me'.
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</a>
|
</a>
|
||||||
|
|
||||||
@@ -115,7 +114,9 @@
|
|||||||
<div class="v-content">
|
<div class="v-content">
|
||||||
<div class="v-title">Umbra.cyou <span class="v-link-arrow">↗</span></div>
|
<div class="v-title">Umbra.cyou <span class="v-link-arrow">↗</span></div>
|
||||||
<div class="v-year">2019 → 2022</div>
|
<div class="v-year">2019 → 2022</div>
|
||||||
<div class="v-desc">Complete redesign using SCSS & Nord theme.</div>
|
<div class="v-desc">Built from the ground up focusing on a minimal clean design. Stole my code
|
||||||
|
VS Code theme for a colour palette.
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</a>
|
</a>
|
||||||
|
|
||||||
@@ -124,8 +125,7 @@
|
|||||||
<div class="v-content">
|
<div class="v-content">
|
||||||
<div class="v-title">Havox.org <span class="v-link-arrow">↗</span></div>
|
<div class="v-title">Havox.org <span class="v-link-arrow">↗</span></div>
|
||||||
<div class="v-year">2016 → 2019</div>
|
<div class="v-year">2016 → 2019</div>
|
||||||
<div class="v-desc">Entire site in one PHP file 🤣. Had a daily <s>trump</s>
|
<div class="v-desc">Wrote the entire site in one php file. Hosted on a £1/year VPS.
|
||||||
quote-of-the-day achieved via webscraping a site daily.
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</a>
|
</a>
|
||||||
@@ -147,8 +147,8 @@
|
|||||||
<div class="skill-card reveal">
|
<div class="skill-card reveal">
|
||||||
<span class="skill-card-icon">☕</span>
|
<span class="skill-card-icon">☕</span>
|
||||||
<h3>Backend</h3>
|
<h3>Backend</h3>
|
||||||
<p>Professional Java experience building microservices & RESTful APIs with Spring Boot. TDD with
|
<p>Professional experience designing, building and deploying services. Using a modern tech stack in the
|
||||||
JUnit & Mockito.</p>
|
Supply Chain & Logistics industry.</p>
|
||||||
<div class="tag-row">
|
<div class="tag-row">
|
||||||
<span class="tag tag-blue">Java</span>
|
<span class="tag tag-blue">Java</span>
|
||||||
<span class="tag tag-green">Spring Boot</span>
|
<span class="tag tag-green">Spring Boot</span>
|
||||||
@@ -160,8 +160,8 @@
|
|||||||
<div class="skill-card reveal" style="transition-delay:0.08s">
|
<div class="skill-card reveal" style="transition-delay:0.08s">
|
||||||
<span class="skill-card-icon">🎨</span>
|
<span class="skill-card-icon">🎨</span>
|
||||||
<h3>Frontend & Creative</h3>
|
<h3>Frontend & Creative</h3>
|
||||||
<p>Comfortable with react and CSS. I enjoy visualising algorithms interactively — it's more fun than
|
<p>Comfortable with React and CSS. I've always enjoyed visualising algorithms interactively - it's way more
|
||||||
a console output.</p>
|
fun than a console output.</p>
|
||||||
<div class="tag-row">
|
<div class="tag-row">
|
||||||
<span class="tag tag-teal">React</span>
|
<span class="tag tag-teal">React</span>
|
||||||
<span class="tag tag-green">TypeScript</span>
|
<span class="tag tag-green">TypeScript</span>
|
||||||
@@ -171,8 +171,8 @@
|
|||||||
<div class="skill-card reveal" style="transition-delay:0.16s">
|
<div class="skill-card reveal" style="transition-delay:0.16s">
|
||||||
<span class="skill-card-icon">🖥</span>
|
<span class="skill-card-icon">🖥</span>
|
||||||
<h3>Systems & Infra</h3>
|
<h3>Systems & Infra</h3>
|
||||||
<p>Long-term Linux user. Self-hosted web & media servers. Comfortable with networking, security
|
<p>Long-term Linux & Vim user. Self-hosted web & media servers. Using industry practices when it comes to
|
||||||
practices, and the command line.</p>
|
networks & security.</p>
|
||||||
<div class="tag-row">
|
<div class="tag-row">
|
||||||
<span class="tag tag-green">Linux</span>
|
<span class="tag tag-green">Linux</span>
|
||||||
<span class="tag tag-teal">Docker</span>
|
<span class="tag tag-teal">Docker</span>
|
||||||
@@ -204,7 +204,8 @@
|
|||||||
<p class="section-label reveal">projects</p>
|
<p class="section-label reveal">projects</p>
|
||||||
<h2 class="section-heading reveal" style="transition-delay:0.05s">Things I <em>built</em></h2>
|
<h2 class="section-heading reveal" style="transition-delay:0.05s">Things I <em>built</em></h2>
|
||||||
<p class="section-intro reveal" style="transition-delay:0.1s">
|
<p class="section-intro reveal" style="transition-delay:0.1s">
|
||||||
A timeline of fun projects used as an excuse to learn something new.
|
A timeline of my projects and an overview of my journey as a developer. Often times getting inspired and trying
|
||||||
|
to recreate something cool I saw.
|
||||||
</p>
|
</p>
|
||||||
|
|
||||||
<div class="projects-subheading reveal" style="transition-delay:0.12s">
|
<div class="projects-subheading reveal" style="transition-delay:0.12s">
|
||||||
@@ -215,8 +216,7 @@
|
|||||||
<a class="card" href="https://wordlesolver.umbra.mom">
|
<a class="card" href="https://wordlesolver.umbra.mom">
|
||||||
<span class="card-date">9 Feb 2025</span>
|
<span class="card-date">9 Feb 2025</span>
|
||||||
<span class="card-title">Wordle Solver</span>
|
<span class="card-title">Wordle Solver</span>
|
||||||
<span class="card-desc">Built after getting frustrated after one too many missed 3-guess games. Now it
|
<span class="card-desc">Built after one too many missed 3-guess games. Now it plays marginally better than me. Uses information theory to recommend the next best guess.</span>
|
||||||
plays marginally better than me. Uses information theory to recommend the next best guess.</span>
|
|
||||||
<span class="tag-row">
|
<span class="tag-row">
|
||||||
<span class="tag tag-yellow">Rust</span>
|
<span class="tag tag-yellow">Rust</span>
|
||||||
<span class="tag tag-teal">React</span>
|
<span class="tag tag-teal">React</span>
|
||||||
@@ -227,7 +227,7 @@
|
|||||||
<a class="card" href="https://crackthequote.umbra.mom">
|
<a class="card" href="https://crackthequote.umbra.mom">
|
||||||
<span class="card-date">13 Apr 2024</span>
|
<span class="card-date">13 Apr 2024</span>
|
||||||
<span class="card-title">Crack the Quote</span>
|
<span class="card-title">Crack the Quote</span>
|
||||||
<span class="card-desc">A substitution-cipher puzzle game with a daily challenge.</span>
|
<span class="card-desc">A substitution-cipher puzzle game with a daily challenge. Built for me and my family to play after getting bored with NYT games.</span>
|
||||||
<span class="tag-row">
|
<span class="tag-row">
|
||||||
<span class="tag tag-yellow">Rust</span>
|
<span class="tag tag-yellow">Rust</span>
|
||||||
<span class="tag tag-teal">React</span>
|
<span class="tag tag-teal">React</span>
|
||||||
@@ -254,16 +254,17 @@
|
|||||||
</fieldset>
|
</fieldset>
|
||||||
|
|
||||||
<div id="project-grid" class="card-grid reveal" style="transition-delay:0.2s">
|
<div id="project-grid" class="card-grid reveal" style="transition-delay:0.2s">
|
||||||
<a class="card project-card" data-tech="python" href="https://pubquiz.umbra.mom">
|
<article class="card project-card card-link" data-tech="python" data-href="https://pubquiz.umbra.mom">
|
||||||
<span class="card-date">03 Apr 2025</span>
|
<span class="card-date">03 Apr 2025</span>
|
||||||
<span class="card-title">Pub Quiz Dashboard</span>
|
<span class="card-title">Pub Quiz Dashboard</span>
|
||||||
<span class="card-desc">A Python dashboard to track quiz performance.</span>
|
<span class="card-desc">A Python dashboard to track our local pub quiz performances.</span>
|
||||||
<span class="tag-row">
|
<span class="tag-row">
|
||||||
<span class="tag tag-red">Python</span>
|
<span class="tag tag-red">Python</span>
|
||||||
</span>
|
</span>
|
||||||
<span class="card-arrow">→</span>
|
<span class="card-arrow">→</span>
|
||||||
</a>
|
</article>
|
||||||
<a class="card project-card" data-tech="cpp webassembly" href="projects/thin_ice/thin_ice.html">
|
<article class="card project-card card-link" data-tech="cpp webassembly"
|
||||||
|
data-href="projects/thin_ice/thin_ice.html">
|
||||||
<span class="card-date">14 Nov 2024</span>
|
<span class="card-date">14 Nov 2024</span>
|
||||||
<span class="card-title">Thin Ice</span>
|
<span class="card-title">Thin Ice</span>
|
||||||
<span class="card-desc">A small browser tile game inspired by one I played growing up.</span>
|
<span class="card-desc">A small browser tile game inspired by one I played growing up.</span>
|
||||||
@@ -273,90 +274,96 @@
|
|||||||
<span class="tag tag-peach">RayLib</span>
|
<span class="tag tag-peach">RayLib</span>
|
||||||
</span>
|
</span>
|
||||||
<span class="card-arrow">→</span>
|
<span class="card-arrow">→</span>
|
||||||
</a>
|
</article>
|
||||||
<a class="card project-card" data-tech="zig webassembly" href="projects/tsp/index.html">
|
<article class="card project-card card-link" data-tech="zig webassembly" data-href="projects/tsp/index.html">
|
||||||
<span class="card-date">20 Mar 2024</span>
|
<span class="card-date">20 Mar 2024</span>
|
||||||
<span class="card-title">Travelling Salesman Problem</span>
|
<span class="card-title">Travelling Salesman Problem</span>
|
||||||
<span class="card-desc">A nearest-neighbor + 2-opt visualiser.</span>
|
<span class="card-desc">A nearest-neighbor + 2-opt visualiser. Wanted to revisit one of my first projects but with a super optimised tech-stack & algorithm.</span>
|
||||||
<span class="tag-row">
|
<span class="tag-row">
|
||||||
<span class="tag tag-yellow">Zig</span>
|
<span class="tag tag-yellow">Zig</span>
|
||||||
<span class="tag tag-sky">WebGL</span>
|
<span class="tag tag-sky">WebGL</span>
|
||||||
<span class="tag tag-teal">WebAssembly</span>
|
<span class="tag tag-teal">WebAssembly</span>
|
||||||
</span>
|
</span>
|
||||||
<span class="card-arrow">→</span>
|
<span class="card-arrow">→</span>
|
||||||
</a>
|
</article>
|
||||||
<a class="card project-card" data-tech="rust" href="projects/flocking/index.html">
|
<article class="card project-card card-link" data-tech="rust" data-href="projects/flocking/index.html">
|
||||||
<span class="card-date">31 Jan 2024</span>
|
<span class="card-date">31 Jan 2024</span>
|
||||||
<span class="card-title">Flocking</span>
|
<span class="card-title">Flocking</span>
|
||||||
<span class="card-desc">A boids simulation showing emergent behaviour from three simple rules.</span>
|
<span class="card-desc">Rewrote the entire project in Rust from GoLang to compile to wasm. Was fun being able to use DOM controls to affect the simulation.</span>
|
||||||
<span class="tag-row">
|
<span class="tag-row">
|
||||||
<span class="tag tag-yellow">Rust</span>
|
<span class="tag tag-yellow">Rust</span>
|
||||||
<span class="tag tag-peach">Raylib</span>
|
<span class="tag tag-peach">Raylib</span>
|
||||||
</span>
|
</span>
|
||||||
<span class="card-arrow">→</span>
|
<span class="card-arrow">→</span>
|
||||||
</a>
|
</article>
|
||||||
<a class="card project-card" data-tech="javascript" href="https://samstoreymusic.com">
|
<article class="card project-card card-link" data-tech="javascript" data-href="https://samstoreymusic.com">
|
||||||
<span class="card-date">1 Nov 2023</span>
|
<span class="card-date">1 Nov 2023</span>
|
||||||
<span class="card-title">samstoreymusic.com</span>
|
<span class="card-title">samstoreymusic.com</span>
|
||||||
<span class="card-desc">A website design and build for a friend working in music.</span>
|
<span class="card-desc">A website design and build for a friend working in music. Saving him the hosting fees :)</span>
|
||||||
<span class="tag-row">
|
<span class="tag-row">
|
||||||
<span class="tag tag-mauve">HTML/CSS</span>
|
<span class="tag tag-mauve">HTML/CSS</span>
|
||||||
<span class="tag tag-green">JavaScript</span>
|
<span class="tag tag-green">JavaScript</span>
|
||||||
</span>
|
</span>
|
||||||
<span class="card-arrow">→</span>
|
<span class="card-arrow">→</span>
|
||||||
</a>
|
</article>
|
||||||
<a class="card project-card" data-tech="javascript react" href="projects/cellular_automata/index.html">
|
<article class="card project-card card-link" data-tech="javascript react"
|
||||||
|
data-href="projects/cellular_automata/index.html">
|
||||||
<span class="card-date">21 Jul 2023</span>
|
<span class="card-date">21 Jul 2023</span>
|
||||||
<span class="card-title">Game of Life</span>
|
<span class="card-title">Game of Life</span>
|
||||||
<span class="card-desc">After building Conway's Game of Life in p5.js, I expanded it into a generic automata simulator.</span>
|
<span class="card-desc">After building Conway's Game of Life in p5.js as one of my first projects, I expanded it into a generic automata simulator.</span>
|
||||||
<span class="tag-row">
|
<span class="tag-row">
|
||||||
<span class="tag tag-teal">React</span>
|
<span class="tag tag-teal">React</span>
|
||||||
<span class="tag tag-green">JavaScript</span>
|
<span class="tag tag-green">JavaScript</span>
|
||||||
</span>
|
</span>
|
||||||
<span class="card-arrow">→</span>
|
<span class="card-arrow">→</span>
|
||||||
</a>
|
</article>
|
||||||
<a class="card project-card" data-tech="cpp webassembly" href="projects/percolation/index.html">
|
<article class="card project-card card-link" data-tech="cpp webassembly"
|
||||||
|
data-href="projects/percolation/index.html">
|
||||||
<span class="card-date">5 Feb 2022</span>
|
<span class="card-date">5 Feb 2022</span>
|
||||||
<span class="card-title">Percolation</span>
|
<span class="card-title">Percolation</span>
|
||||||
<span class="card-desc">A visual demo of 'water' percolating through a medium, as it disappears.</span>
|
<span class="card-desc">Watched a brilliant video by <a target="_blank"
|
||||||
|
href="https://youtu.be/a-767WnbaCQ?si=f3NM95INeoZqzIi8">Spectral Collective</a> and just had to recreate it.</span>
|
||||||
<span class="tag-row">
|
<span class="tag-row">
|
||||||
<span class="tag tag-blue">C</span>
|
<span class="tag tag-blue">C</span>
|
||||||
<span class="tag tag-peach">RayLib</span>
|
<span class="tag tag-peach">RayLib</span>
|
||||||
<span class="tag tag-teal">WebAssembly</span>
|
<span class="tag tag-teal">WebAssembly</span>
|
||||||
</span>
|
</span>
|
||||||
<span class="card-arrow">→</span>
|
<span class="card-arrow">→</span>
|
||||||
</a>
|
</article>
|
||||||
<a class="card project-card" data-tech="javascript p5" href="projects/cubic_bezier_curve/index.html">
|
<article class="card project-card card-link" data-tech="javascript p5"
|
||||||
|
data-href="projects/cubic_bezier_curve/index.html">
|
||||||
<span class="card-date">1 Oct 2021</span>
|
<span class="card-date">1 Oct 2021</span>
|
||||||
<span class="card-title">Drawing Bézier curves</span>
|
<span class="card-title">Drawing Bézier curves</span>
|
||||||
<span class="card-desc">An interactive diagram for cubic Bézier curves.</span>
|
<span class="card-desc">An interactive animation for how cubic Bézier curves are constructed. Inspirated by this beautiful video by <a
|
||||||
|
target="_blank" href="https://youtu.be/aVwxzDHniEw?si=mCylw_p-fMSdhyvN">Fraya Holmér</a></span>
|
||||||
<span class="tag-row">
|
<span class="tag-row">
|
||||||
<span class="tag tag-green">JavaScript</span>
|
<span class="tag tag-green">JavaScript</span>
|
||||||
<span class="tag tag-red">p5.js</span>
|
<span class="tag tag-red">p5.js</span>
|
||||||
</span>
|
</span>
|
||||||
<span class="card-arrow">→</span>
|
<span class="card-arrow">→</span>
|
||||||
</a>
|
</article>
|
||||||
<a class="card project-card" data-tech="javascript p5" href="projects/marching_squares.html">
|
<article class="card project-card card-link" data-tech="javascript p5"
|
||||||
|
data-href="projects/marching_squares.html">
|
||||||
<span class="card-date">17 Sep 2021</span>
|
<span class="card-date">17 Sep 2021</span>
|
||||||
<span class="card-title">2D Marching Squares</span>
|
<span class="card-title">2D Marching Squares</span>
|
||||||
<span class="card-desc">Basic map rendering.</span>
|
<span class="card-desc">I saw the 3D version of this algorithm in a game dev log and was inspired to create this 2d land/sea map generator thing.</span>
|
||||||
<span class="tag-row">
|
<span class="tag-row">
|
||||||
<span class="tag tag-green">JavaScript</span>
|
<span class="tag tag-green">JavaScript</span>
|
||||||
<span class="tag tag-red">p5.js</span>
|
<span class="tag tag-red">p5.js</span>
|
||||||
</span>
|
</span>
|
||||||
<span class="card-arrow">→</span>
|
<span class="card-arrow">→</span>
|
||||||
</a>
|
</article>
|
||||||
<a class="card project-card" data-tech="javascript p5" href="projects/warping_lines.html">
|
<article class="card project-card card-link" data-tech="javascript p5" data-href="projects/warping_lines.html">
|
||||||
<span class="card-date">2 Apr 2020</span>
|
<span class="card-date">2 Apr 2020</span>
|
||||||
<span class="card-title">Müller-Lyer illusion</span>
|
<span class="card-title">Müller-Lyer illusion</span>
|
||||||
<span class="card-desc">A JavaScript visualisation of the Müller-Lyer optical illusion.</span>
|
<span class="card-desc">JavaScript visualisation of the Müller-Lyer optical illusion.</span>
|
||||||
<span class="tag-row">
|
<span class="tag-row">
|
||||||
<span class="tag tag-green">JavaScript</span>
|
<span class="tag tag-green">JavaScript</span>
|
||||||
<span class="tag tag-red">p5.js</span>
|
<span class="tag tag-red">p5.js</span>
|
||||||
</span>
|
</span>
|
||||||
<span class="card-arrow">→</span>
|
<span class="card-arrow">→</span>
|
||||||
</a>
|
</article>
|
||||||
<a class="card project-card" data-tech="javascript p5" href="projects/fourier_series.html">
|
<article class="card project-card card-link" data-tech="javascript p5" data-href="projects/fourier_series.html">
|
||||||
<span class="card-date">27 Feb 2019</span>
|
<span class="card-date">27 Feb 2019</span>
|
||||||
<span class="card-title">Fourier series</span>
|
<span class="card-title">Fourier series</span>
|
||||||
<span class="card-desc">Builds a square wave from sine components to show Fourier series in motion.</span>
|
<span class="card-desc">Builds a square wave from sine components to show Fourier series in motion.</span>
|
||||||
@@ -365,18 +372,21 @@
|
|||||||
<span class="tag tag-red">p5.js</span>
|
<span class="tag tag-red">p5.js</span>
|
||||||
</span>
|
</span>
|
||||||
<span class="card-arrow">→</span>
|
<span class="card-arrow">→</span>
|
||||||
</a>
|
</article>
|
||||||
<a class="card project-card" data-tech="javascript p5" href="projects/ellipse_construction.html">
|
<article class="card project-card card-link" data-tech="javascript p5"
|
||||||
|
data-href="projects/ellipse_construction.html">
|
||||||
<span class="card-date">23 Feb 2019</span>
|
<span class="card-date">23 Feb 2019</span>
|
||||||
<span class="card-title">Constructing an ellipse</span>
|
<span class="card-title">Constructing an ellipse</span>
|
||||||
<span class="card-desc">A geometric construction demo inspired by 3Blue1Brown.</span>
|
<span class="card-desc">A geometric construction demo inspired by <a target="_blank"
|
||||||
|
href="https://youtu.be/xdIjYBtnvZU?si=uI66LS_O_eAWqG4e">3Blue1Brown's video</a> on Feynman's lost lecture.</span>
|
||||||
<span class="tag-row">
|
<span class="tag-row">
|
||||||
<span class="tag tag-green">JavaScript</span>
|
<span class="tag tag-green">JavaScript</span>
|
||||||
<span class="tag tag-red">p5.js</span>
|
<span class="tag tag-red">p5.js</span>
|
||||||
</span>
|
</span>
|
||||||
<span class="card-arrow">→</span>
|
<span class="card-arrow">→</span>
|
||||||
</a>
|
</article>
|
||||||
<a class="card project-card" data-tech="javascript p5" href="projects/pi_approximation.html">
|
<article class="card project-card card-link" data-tech="javascript p5"
|
||||||
|
data-href="projects/pi_approximation.html">
|
||||||
<span class="card-date">18 Mar 2018</span>
|
<span class="card-date">18 Mar 2018</span>
|
||||||
<span class="card-title">Calculating PI</span>
|
<span class="card-title">Calculating PI</span>
|
||||||
<span class="card-desc">A Monte Carlo approximation of pi using random sampling.</span>
|
<span class="card-desc">A Monte Carlo approximation of pi using random sampling.</span>
|
||||||
@@ -385,8 +395,9 @@
|
|||||||
<span class="tag tag-red">p5.js</span>
|
<span class="tag tag-red">p5.js</span>
|
||||||
</span>
|
</span>
|
||||||
<span class="card-arrow">→</span>
|
<span class="card-arrow">→</span>
|
||||||
</a>
|
</article>
|
||||||
<a class="card project-card" data-tech="javascript p5" href="projects/oscillations_in_3d.html">
|
<article class="card project-card card-link" data-tech="javascript p5"
|
||||||
|
data-href="projects/oscillations_in_3d.html">
|
||||||
<span class="card-date">17 Dec 2017</span>
|
<span class="card-date">17 Dec 2017</span>
|
||||||
<span class="card-title">Oscillations in 3D</span>
|
<span class="card-title">Oscillations in 3D</span>
|
||||||
<span class="card-desc">A JavaScript recreation of a Bees and Bombs animation.</span>
|
<span class="card-desc">A JavaScript recreation of a Bees and Bombs animation.</span>
|
||||||
@@ -395,17 +406,19 @@
|
|||||||
<span class="tag tag-red">p5.js</span>
|
<span class="tag tag-red">p5.js</span>
|
||||||
</span>
|
</span>
|
||||||
<span class="card-arrow">→</span>
|
<span class="card-arrow">→</span>
|
||||||
</a>
|
</article>
|
||||||
<a class="card project-card" data-tech="javascript p5" href="projects/maze_generation/index.html">
|
<article class="card project-card card-link" data-tech="javascript p5"
|
||||||
|
data-href="projects/maze_generation/index.html">
|
||||||
<span class="card-date">13 Nov 2017</span>
|
<span class="card-date">13 Nov 2017</span>
|
||||||
<span class="card-title">Maze generator</span>
|
<span class="card-title">Maze generator</span>
|
||||||
<span class="card-desc">A p5.js maze generator using depth-first search and recursive backtracking.</span>
|
<span class="card-desc">Discovered the <a target="_blank"
|
||||||
|
href="https://youtu.be/HyK_Q5rrcr4?si=G6g8xDHK0cc_MwhG">Coding Train's channel</a> and learnt coding through following along.</span>
|
||||||
<span class="tag-row">
|
<span class="tag-row">
|
||||||
<span class="tag tag-green">JavaScript</span>
|
<span class="tag tag-green">JavaScript</span>
|
||||||
<span class="tag tag-red">p5.js</span>
|
<span class="tag tag-red">p5.js</span>
|
||||||
</span>
|
</span>
|
||||||
<span class="card-arrow">→</span>
|
<span class="card-arrow">→</span>
|
||||||
</a>
|
</article>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="projects-more-row reveal" style="transition-delay:0.22s">
|
<div class="projects-more-row reveal" style="transition-delay:0.22s">
|
||||||
@@ -423,30 +436,20 @@
|
|||||||
<h2>Let's <em>talk</em></h2>
|
<h2>Let's <em>talk</em></h2>
|
||||||
<p>
|
<p>
|
||||||
I am currently employed and open to the right software engineering opportunity, particularly
|
I am currently employed and open to the right software engineering opportunity, particularly
|
||||||
backend or full-stack roles with teams that value thoughtful delivery and technical quality.
|
backend or full-stack roles with friendly, close-knit teams.
|
||||||
</p>
|
</p>
|
||||||
<p>
|
<p>
|
||||||
For professional enquiries, please connect with me on LinkedIn.
|
For professional enquiries, please contact me on LinkedIn.
|
||||||
</p>
|
</p>
|
||||||
</div>
|
</div>
|
||||||
<div class="contact-links">
|
<div class="contact-links">
|
||||||
<a href="https://github.com/jayo60013" class="contact-link" target="_blank" rel="noopener">
|
<a href="https://github.com/jayo60013" class="contact-link" target="_blank" rel="noopener">
|
||||||
<span class="contact-link-icon">
|
<span class="contact-link-icon contact-link-icon--github" aria-hidden="true"></span>
|
||||||
<svg width="18" height="18" viewBox="0 0 24 24" fill="currentColor">
|
|
||||||
<path
|
|
||||||
d="M12 0C5.37 0 0 5.37 0 12c0 5.31 3.435 9.795 8.205 11.385.6.105.825-.255.825-.57 0-.285-.015-1.23-.015-2.235-3.015.555-3.795-.735-4.035-1.41-.135-.345-.72-1.41-1.23-1.695-.42-.225-1.02-.78-.015-.795.945-.015 1.62.87 1.845 1.23 1.08 1.815 2.805 1.305 3.495.99.105-.78.42-1.305.765-1.605-2.67-.3-5.46-1.335-5.46-5.925 0-1.305.465-2.385 1.23-3.225-.12-.3-.54-1.53.12-3.18 0 0 1.005-.315 3.3 1.23.96-.27 1.98-.405 3-.405s2.04.135 3 .405c2.295-1.56 3.3-1.23 3.3-1.23.66 1.65.24 2.88.12 3.18.765.84 1.23 1.905 1.23 3.225 0 4.605-2.805 5.625-5.475 5.925.435.375.81 1.095.81 2.22 0 1.605-.015 2.895-.015 3.3 0 .315.225.69.825.57A12.02 12.02 0 0 0 24 12c0-6.63-5.37-12-12-12z"/>
|
|
||||||
</svg>
|
|
||||||
</span>
|
|
||||||
<span class="contact-link-label">GitHub</span>
|
<span class="contact-link-label">GitHub</span>
|
||||||
<span class="contact-link-handle">jayo60013</span>
|
<span class="contact-link-handle">jayo60013</span>
|
||||||
</a>
|
</a>
|
||||||
<a href="https://www.linkedin.com/in/jaygatward" class="contact-link" target="_blank" rel="noopener">
|
<a href="https://www.linkedin.com/in/jaygatward" class="contact-link" target="_blank" rel="noopener">
|
||||||
<span class="contact-link-icon">
|
<span class="contact-link-icon contact-link-icon--linkedin" aria-hidden="true"></span>
|
||||||
<svg width="18" height="18" viewBox="0 0 24 24" fill="currentColor">
|
|
||||||
<path
|
|
||||||
d="M20.447 20.452h-3.554v-5.569c0-1.328-.027-3.037-1.852-3.037-1.853 0-2.136 1.445-2.136 2.939v5.667H9.351V9h3.414v1.561h.046c.477-.9 1.637-1.85 3.37-1.85 3.601 0 4.267 2.37 4.267 5.455v6.286zM5.337 7.433a2.062 2.062 0 0 1-2.063-2.065 2.064 2.064 0 1 1 2.063 2.065zm1.782 13.019H3.555V9h3.564v11.452zM22.225 0H1.771C.792 0 0 .774 0 1.729v20.542C0 23.227.792 24 1.771 24h20.451C23.2 24 24 23.227 24 22.271V1.729C24 .774 23.2 0 22.222 0h.003z"/>
|
|
||||||
</svg>
|
|
||||||
</span>
|
|
||||||
<span class="contact-link-label">LinkedIn</span>
|
<span class="contact-link-label">LinkedIn</span>
|
||||||
<span class="contact-link-handle">jaygatward</span>
|
<span class="contact-link-handle">jaygatward</span>
|
||||||
</a>
|
</a>
|
||||||
@@ -456,7 +459,7 @@
|
|||||||
|
|
||||||
<!-- ─── Footer ─────────────────────────────────────────────────── -->
|
<!-- ─── Footer ─────────────────────────────────────────────────── -->
|
||||||
<footer>
|
<footer>
|
||||||
<span>umbra.mom — John Gatward</span>
|
<span>umbra.mom - John Gatward</span>
|
||||||
<span>
|
<span>
|
||||||
Source code (self‑hosted): <a href="https://gitea.umbra.mom/jay/havox">repository</a>
|
Source code (self‑hosted): <a href="https://gitea.umbra.mom/jay/havox">repository</a>
|
||||||
</span>
|
</span>
|
||||||
|
|||||||
57
script.js
57
script.js
@@ -32,6 +32,22 @@ const DEFAULT_VISIBLE_PROJECTS = 9;
|
|||||||
if (filterChips.length > 0 && projectCards.length > 0) {
|
if (filterChips.length > 0 && projectCards.length > 0) {
|
||||||
let selectedFilter = 'all';
|
let selectedFilter = 'all';
|
||||||
let isExpanded = false;
|
let isExpanded = false;
|
||||||
|
const interactiveSelector = 'a, button, input, textarea, select, summary, [role="button"]';
|
||||||
|
|
||||||
|
const goToCardHref = (card, event) => {
|
||||||
|
const href = card.dataset.href;
|
||||||
|
if (!href) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const openInNewTab = event.metaKey || event.ctrlKey || event.button === 1;
|
||||||
|
if (openInNewTab) {
|
||||||
|
window.open(href, '_blank', 'noopener');
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
globalThis.location.href = href;
|
||||||
|
};
|
||||||
|
|
||||||
const applyFilter = () => {
|
const applyFilter = () => {
|
||||||
const visibleCards = [];
|
const visibleCards = [];
|
||||||
@@ -81,6 +97,47 @@ if (filterChips.length > 0 && projectCards.length > 0) {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
projectCards.forEach(card => {
|
||||||
|
if (!card.dataset.href) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
card.setAttribute('role', 'link');
|
||||||
|
card.setAttribute('tabindex', '0');
|
||||||
|
|
||||||
|
card.addEventListener('click', event => {
|
||||||
|
const target = event.target;
|
||||||
|
if (!(target instanceof Element)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Let inline links and other controls inside the card handle their own clicks.
|
||||||
|
if (target.closest(interactiveSelector) && target.closest(interactiveSelector) !== card) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
goToCardHref(card, event);
|
||||||
|
});
|
||||||
|
|
||||||
|
card.addEventListener('keydown', event => {
|
||||||
|
if (event.key !== 'Enter' && event.key !== ' ') {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const target = event.target;
|
||||||
|
if (!(target instanceof Element)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (target.closest(interactiveSelector) && target.closest(interactiveSelector) !== card) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
event.preventDefault();
|
||||||
|
goToCardHref(card, event);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
applyFilter();
|
applyFilter();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
85
style.css
85
style.css
@@ -39,7 +39,13 @@ html {
|
|||||||
}
|
}
|
||||||
|
|
||||||
body {
|
body {
|
||||||
background: var(--base);
|
background: radial-gradient(rgba(205, 214, 244, 0.028) 0.5px, transparent 0.6px),
|
||||||
|
radial-gradient(rgba(17, 17, 27, 0.032) 0.5px, transparent 0.6px),
|
||||||
|
radial-gradient(1200px 800px at 12% 8%, rgba(137, 180, 250, 0.07), transparent 62%),
|
||||||
|
radial-gradient(1000px 720px at 88% 92%, rgba(203, 166, 247, 0.07), transparent 64%),
|
||||||
|
linear-gradient(180deg, #1e1e2e 0%, #1b1b2b 55%, #1a1a29 100%);
|
||||||
|
background-size: 3px 3px, 3px 3px, auto, auto, auto;
|
||||||
|
background-position: 0 0, 1px 1px, 0 0, 0 0, 0 0;
|
||||||
color: var(--text);
|
color: var(--text);
|
||||||
font-family: 'JetBrains Mono', 'Apple Color Emoji', monospace;
|
font-family: 'JetBrains Mono', 'Apple Color Emoji', monospace;
|
||||||
font-size: 15px;
|
font-size: 15px;
|
||||||
@@ -52,25 +58,27 @@ body::before,
|
|||||||
body::after {
|
body::after {
|
||||||
content: '';
|
content: '';
|
||||||
position: fixed;
|
position: fixed;
|
||||||
width: 36rem;
|
width: 52rem;
|
||||||
height: 36rem;
|
height: 42rem;
|
||||||
border-radius: 50%;
|
border-radius: 58% 42% 55% 45% / 46% 54% 48% 52%;
|
||||||
pointer-events: none;
|
pointer-events: none;
|
||||||
z-index: -1;
|
z-index: -1;
|
||||||
filter: blur(70px);
|
filter: blur(90px);
|
||||||
opacity: 0.12;
|
opacity: 0.16;
|
||||||
}
|
}
|
||||||
|
|
||||||
body::before {
|
body::before {
|
||||||
top: -10rem;
|
top: -18rem;
|
||||||
right: -10rem;
|
right: -16rem;
|
||||||
background: radial-gradient(circle, var(--mauve), transparent 65%);
|
transform: rotate(14deg);
|
||||||
|
background: radial-gradient(closest-side at 38% 42%, rgba(203, 166, 247, 0.42), transparent 72%);
|
||||||
}
|
}
|
||||||
|
|
||||||
body::after {
|
body::after {
|
||||||
bottom: -14rem;
|
bottom: -20rem;
|
||||||
left: -12rem;
|
left: -18rem;
|
||||||
background: radial-gradient(circle, var(--blue), transparent 65%);
|
transform: rotate(-12deg);
|
||||||
|
background: radial-gradient(closest-side at 60% 58%, rgba(137, 180, 250, 0.36), transparent 72%);
|
||||||
}
|
}
|
||||||
|
|
||||||
::selection {
|
::selection {
|
||||||
@@ -269,11 +277,6 @@ section.full-width {
|
|||||||
opacity: 0.8;
|
opacity: 0.8;
|
||||||
}
|
}
|
||||||
|
|
||||||
.hero-by-role::before {
|
|
||||||
content: '— ';
|
|
||||||
opacity: 0.4;
|
|
||||||
}
|
|
||||||
|
|
||||||
.hero-by-footer {
|
.hero-by-footer {
|
||||||
display: block;
|
display: block;
|
||||||
margin-top: 1rem;
|
margin-top: 1rem;
|
||||||
@@ -373,6 +376,12 @@ section.full-width {
|
|||||||
gap: 1.25rem;
|
gap: 1.25rem;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.about-grid .about-block:first-child {
|
||||||
|
background: linear-gradient(90deg, rgba(203, 166, 247, 0.07), rgba(203, 166, 247, 0.03));
|
||||||
|
border-left: 2px solid rgba(203, 166, 247, 0.65);
|
||||||
|
box-shadow: inset 0 0 0 1px rgba(203, 166, 247, 0.08);
|
||||||
|
}
|
||||||
|
|
||||||
.about-block:last-child {
|
.about-block:last-child {
|
||||||
border-bottom: none;
|
border-bottom: none;
|
||||||
}
|
}
|
||||||
@@ -771,6 +780,15 @@ section.full-width {
|
|||||||
overflow: hidden;
|
overflow: hidden;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.card-link {
|
||||||
|
cursor: pointer;
|
||||||
|
}
|
||||||
|
|
||||||
|
.card-link:focus-visible {
|
||||||
|
outline: 1px solid var(--mauve);
|
||||||
|
outline-offset: -1px;
|
||||||
|
}
|
||||||
|
|
||||||
.card::before {
|
.card::before {
|
||||||
content: '';
|
content: '';
|
||||||
position: absolute;
|
position: absolute;
|
||||||
@@ -817,6 +835,16 @@ section.full-width {
|
|||||||
flex: 1;
|
flex: 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.card-desc a {
|
||||||
|
color: var(--sky);
|
||||||
|
text-decoration: underline;
|
||||||
|
text-underline-offset: 2px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.card-desc a:hover {
|
||||||
|
color: var(--mauve);
|
||||||
|
}
|
||||||
|
|
||||||
.card-arrow {
|
.card-arrow {
|
||||||
font-size: 0.8rem;
|
font-size: 0.8rem;
|
||||||
color: var(--overlay0);
|
color: var(--overlay0);
|
||||||
@@ -894,9 +922,26 @@ section.full-width {
|
|||||||
}
|
}
|
||||||
|
|
||||||
.contact-link-icon {
|
.contact-link-icon {
|
||||||
font-size: 1.1rem;
|
width: 1.125rem;
|
||||||
width: 1.5rem;
|
height: 1.125rem;
|
||||||
text-align: center;
|
flex: 0 0 1.125rem;
|
||||||
|
background: currentColor;
|
||||||
|
-webkit-mask-repeat: no-repeat;
|
||||||
|
-webkit-mask-position: center;
|
||||||
|
-webkit-mask-size: contain;
|
||||||
|
mask-repeat: no-repeat;
|
||||||
|
mask-position: center;
|
||||||
|
mask-size: contain;
|
||||||
|
}
|
||||||
|
|
||||||
|
.contact-link-icon--github {
|
||||||
|
-webkit-mask-image: url('icons/github.svg');
|
||||||
|
mask-image: url('icons/github.svg');
|
||||||
|
}
|
||||||
|
|
||||||
|
.contact-link-icon--linkedin {
|
||||||
|
-webkit-mask-image: url('icons/linkedin.svg');
|
||||||
|
mask-image: url('icons/linkedin.svg');
|
||||||
}
|
}
|
||||||
|
|
||||||
.contact-link-label {
|
.contact-link-label {
|
||||||
|
|||||||
Reference in New Issue
Block a user