Add LHB Engineering case study with reusable header/footer partials and scrollable hero screenshots

This commit is contained in:
Ovidiu U
2026-03-13 13:39:55 +00:00
parent f2d497db9a
commit 484066a80e
11 changed files with 328 additions and 107 deletions

View File

@@ -182,8 +182,8 @@
.cs-meta-bar {
list-style: none;
display: flex;
flex-wrap: wrap;
gap: 0 2rem;
flex-direction: column;
gap: 0;
padding: 0.75rem 1rem;
background: var(--grey-dark);
border-left: 6px solid var(--grey-text);
@@ -304,6 +304,37 @@
border-bottom: 2px solid var(--accent);
}
.screenshot-hero-scroll {
position: relative;
max-height: 600px;
overflow-y: scroll;
scrollbar-width: thin;
scrollbar-color: var(--accent) #1a1a1a;
}
.screenshot-hero-scroll--no-hint::before {
display: none;
}
.screenshot-hero-scroll::before {
content: '↓ scroll to view whole page';
position: sticky;
top: 0;
display: flex;
justify-content: center;
align-items: flex-start;
padding-top: 1.5rem;
height: 120px;
margin-bottom: -120px;
background: linear-gradient(to top, transparent, rgba(10, 10, 10, 0.9));
font-family: var(--mono);
font-size: 1rem;
letter-spacing: 0.12em;
color: var(--white);
pointer-events: none;
z-index: 1;
}
.screenshot-hero {
display: block;
width: 100%;

View File

@@ -70,6 +70,12 @@ a {
box-shadow: var(--shadow);
}
.nav-left {
display: flex;
align-items: center;
gap: 1.25rem;
}
.nav-logo {
font-family: var(--mono);
font-weight: 800;
@@ -78,6 +84,18 @@ a {
color: var(--accent);
}
.nav-back {
font-family: var(--mono);
font-size: 1rem;
color: var(--white);
opacity: 0.5;
transition: opacity 0.15s;
}
.nav-back:hover {
opacity: 1;
}
.nav-links {
display: flex;
gap: 2rem;
@@ -132,6 +150,10 @@ a {
color: var(--white);
}
.hero h1 .h1-sub {
font-size: 0.6em;
}
.hero-sub {
font-size: 1.25rem;
color: var(--white);

38
data/projects.php Normal file
View File

@@ -0,0 +1,38 @@
<?php
$projects = [
'thompson' => [
'num' => '01',
'code' => 'WEB_DEV',
'title' => 'Thompson Service Centre',
'desc' => 'Trust-first redesign for a 25-year Peterborough garage. Bold credibility signals, booking flow, zero clichés.',
'year' => '2025',
'thumb' => '/img/thompson/hero.jpg',
'live' => true,
'h1' => ['Thompson', 'Service Centre'],
'sub' => 'Website Redesign · 2025',
'stack' => 'HTML · Tailwind CSS v4 · GSAP',
'location' => 'Thompson Service Centre, Peterborough',
'domain' => 'thompsonservicecentre.co.uk',
'page_title' => 'Thompson Service Centre — Case Study',
'page_desc' => 'How we built a trust-first digital presence for a 25-year Peterborough garage.',
],
'lhbeng' => [
'num' => '02',
'code' => 'WEB_DEV',
'title' => 'LHB Eng',
'desc' => 'Structural Engineers designing projects that build strong communities.',
'year' => '2022',
'thumb' => '/img/lhbeng/hero.jpg',
'live' => true,
'h1' => ['LHB', 'Lynch, Harrison & Brumleve, Inc.'],
'sub' => 'Website Redesign · 2022',
'stack' => 'HTML · CSS',
'location' => 'LHB Eng, Indianapolis',
'domain' => 'lhb-eng.com',
'page_title' => 'LHB Engineering — Case Study',
'page_desc' => 'Full website redesign for LHB Engineering with a self-service CMS for portfolio, team, and job listings.',
],
];

12
includes/cs_footer.php Normal file
View File

@@ -0,0 +1,12 @@
<section class="section section-cta">
<div class="section-label"> Next</div>
<div class="section-content">
<a href="/portfolio" class="cs-back cs-back--lg"> Back to All Work</a>
<p class="large-text">Got a project in mind?</p>
<a href="mailto:hello@uovidiu.com" class="btn">Get in Touch </a>
</div>
</section>
<script src="/js/screenshot-scroll-hint.js"></script>
<?php require __DIR__ . '/footer.php'; ?>

38
includes/cs_header.php Normal file
View File

@@ -0,0 +1,38 @@
<?php
/*
* Case Study Header Partial
* ─────────────────────────────────────────────────────────────────
* Requires the following variables set by the calling page BEFORE
* requiring this file:
*
* $cs_slug string Key into $projects, e.g. 'thompson'
*
* Everything else ($title, $description, hero content) is read from
* $projects[$cs_slug] in data/projects.php.
* ─────────────────────────────────────────────────────────────────
*/
$extra_css = '/css/portfolio.css';
require __DIR__ . '/../data/projects.php';
$p = $projects[$cs_slug];
$title = $p['page_title'];
$description = $p['page_desc'];
require __DIR__ . '/header.php';
?>
<div class="cs-breadcrumb">
<a href="/portfolio" class="cs-back">← All Work</a>
<span class="cs-breadcrumb-label">[<?= htmlspecialchars($p['num']) ?> / <?= htmlspecialchars($p['code']) ?>]</span>
</div>
<header class="hero">
<div class="hero-label">Case Study — <?= htmlspecialchars($p['num']) ?></div>
<h1><?= htmlspecialchars($p['h1'][0]) ?><br><span class="h1-sub"><?= htmlspecialchars($p['h1'][1]) ?></span></h1>
<p class="hero-sub"><?= htmlspecialchars($p['sub']) ?></p>
<ul class="cs-meta-bar">
<li><?= htmlspecialchars($p['stack']) ?></li>
<li><?= htmlspecialchars($p['location']) ?></li>
<li><?= htmlspecialchars($p['year']) ?></li>
</ul>
</header>

View File

@@ -17,7 +17,12 @@
<?php $current = parse_url($_SERVER['REQUEST_URI'], PHP_URL_PATH); ?>
<nav class="nav">
<div class="nav-left">
<a href="/" class="nav-logo">OU</a>
<?php if (str_starts_with($current, '/portfolio/')): ?>
<a href="/portfolio" class="nav-back">←(back)</a>
<?php endif; ?>
</div>
<div class="nav-links">
<a href="/#about">About</a>
<a href="/#services">Services</a>

View File

@@ -0,0 +1,13 @@
document.querySelectorAll('.screenshot-hero-scroll').forEach(function (el) {
var img = el.querySelector('img');
function check() {
if (el.scrollHeight <= el.clientHeight) {
el.classList.add('screenshot-hero-scroll--no-hint');
}
}
if (img && !img.complete) {
img.addEventListener('load', check);
} else {
check();
}
});

71
portfolio.php Normal file
View File

@@ -0,0 +1,71 @@
<?php
$title = 'Portfolio — Ovidiu Ungureanu';
$description = 'Selected web development projects by Ovidiu Ungureanu.';
$extra_css = '/css/portfolio.css';
require __DIR__.'/includes/header.php';
require __DIR__ . '/data/projects.php';
?>
<header class="hero">
<div class="hero-label">Portfolio — Selected Work</div>
<h1>Selected<br>Work</h1>
<p class="hero-sub">Client projects and builds.</p>
</header>
<section class="section">
<div class="section-label">001 — <?php
echo count($projects); ?> Projects
</div>
<div class="portfolio-grid">
<?php
foreach ($projects as $slug => $p): ?>
<a href="/portfolio/<?php
echo htmlspecialchars($slug); ?>/"
class="project-card<?php
echo $p['live'] ? '' : ' project-card--wip'; ?>">
<div class="project-card__thumb">
<span class="project-card__label">[<?php
echo htmlspecialchars($p['num']); ?> / <?php
echo htmlspecialchars($p['code']); ?>]</span>
<?php
if ($p['thumb']): ?>
<img src="<?php
echo htmlspecialchars($p['thumb']); ?>"
alt="<?php
echo htmlspecialchars($p['title']); ?>"
loading="lazy">
<?php
endif; ?>
</div>
<div class="project-card__body">
<h3 class="project-card__title"><?php
echo htmlspecialchars($p['title']); ?></h3>
<p class="project-card__desc"><?php
echo htmlspecialchars($p['desc']); ?></p>
<div class="project-card__footer">
<span class="project-card__year"><?php
echo htmlspecialchars($p['year']); ?></span>
<span class="project-card__arrow">→</span>
</div>
</div>
</a>
<?php
endforeach; ?>
</div>
</section>
<section class="section section-cta">
<div class="section-label">002 — Contact</div>
<div class="section-content">
<p class="large-text">Got a project in mind?</p>
<a href="mailto:hello@uovidiu.com" class="btn">Get in Touch →</a>
</div>
</section>
<?php
require __DIR__.'/includes/footer.php'; ?>

View File

@@ -9,7 +9,7 @@
* ──────────
* 1. Copy this folder to portfolio/{slug}/
* 2. Fill in every TODO below — nothing should say TODO when live
* 3. Add the project to the $projects array in portfolio.php
* 3. Add an entry to $projects in data/projects.php (including page_title, page_desc)
* 4. Drop screenshots into /img/{slug}/
*
* IMAGES
@@ -25,42 +25,19 @@
* · Hero screenshot — always include
* · Feature section — include if there's a flow / feature worth showing
* · Craft & Execution — include if the build has something worth saying
* · CTA — always include, do not change
* · CTA — always include, comes from cs_footer.php
* ═══════════════════════════════════════════════════════════════════
*/
// ── Page config ───────────────────────────────────────────────────
$title = 'TODO Client Name — Case Study'; // e.g. 'Northgate Motors — Case Study'
$description = 'TODO One sentence about what you built and for whom.';
$extra_css = '/css/portfolio.css';
require __DIR__ . '/../../includes/header.php';
// ── Project config (matches portfolio/index.php entry) ────────────
$cs_num = 'TODO'; // e.g. '02'
$cs_code = 'TODO'; // e.g. 'WEB_DEV' / 'E_COMMERCE' / 'BOOKING' / 'LANDING' / 'FULL_BUILD'
$cs_domain = 'TODO'; // e.g. 'example.co.uk' (no https://)
// ── Set the slug — everything else lives in data/projects.php ─────
$cs_slug = 'TODO'; // e.g. 'northgate'
require __DIR__ . '/../../includes/cs_header.php';
?>
<div class="cs-breadcrumb">
<a href="/portfolio" class="cs-back">← All Work</a>
<span class="cs-breadcrumb-label">[<?= htmlspecialchars($cs_num) ?> / <?= htmlspecialchars($cs_code) ?>]</span>
</div>
<header class="hero">
<div class="hero-label">Case Study — <?= htmlspecialchars($cs_num) ?></div>
<h1>TODO<br>Client Name</h1> <!-- break the name naturally across 2 lines -->
<p class="hero-sub">TODO Type · TODO Year</p> <!-- e.g. Website Redesign · 2025 -->
<ul class="cs-meta-bar">
<li>TODO Stack</li> <!-- e.g. PHP · MySQL · Tailwind CSS -->
<li>TODO Client, Location</li> <!-- e.g. Northgate Motors, Peterborough -->
<li>TODO Year</li> <!-- e.g. 2025 -->
</ul>
</header>
<!-- ── HERO SCREENSHOT ───────────────────────────────────────────── -->
<section class="section">
<div class="section-label">Project Overview</div><!-- e.g. Homepage / Dashboard / Listings -->
<div class="section-label">Project Overview</div>
<div class="section-content">
<p>TODO What problem did the client have and what did you build to fix it? Keep it to 23 sentences. Be specific — name the feature, the constraint, the outcome.</p>
@@ -71,22 +48,24 @@ $cs_domain = 'TODO'; // e.g. 'example.co.uk' (no https://)
<div class="browser-dots">
<span></span><span></span><span></span>
</div>
<span class="browser-url"><?= htmlspecialchars($cs_domain) ?></span>
<span class="browser-url"><?= htmlspecialchars($p['domain']) ?></span>
</div>
<div class="screenshot-hero-scroll">
<img
src="/img/TODO-slug/hero.jpg"
src="/img/<?= htmlspecialchars($cs_slug) ?>/hero.jpg"
alt="TODO Client Name — TODO description"
class="screenshot-hero"
loading="lazy"
>
</div>
</div>
</section>
<!-- ── FEATURE / FLOW SCREENSHOTS (2-col) ────────────────────────── -->
<!-- Delete this section if you don't have feature screenshots -->
<section class="section">
<div class="section-label">Project Overview</div><!-- e.g. Booking Flow / Admin Panel / Listings -->
<div class="section-label">TODO Section Label</div><!-- e.g. Booking Flow / Admin Panel / Listings -->
<div class="services-grid">
<div class="service-item screenshot-card">
@@ -96,10 +75,10 @@ $cs_domain = 'TODO'; // e.g. 'example.co.uk' (no https://)
<div class="browser-dots">
<span></span><span></span><span></span>
</div>
<span class="browser-url"><?= htmlspecialchars($cs_domain) ?>/TODO-path</span>
<span class="browser-url"><?= htmlspecialchars($p['domain']) ?>/TODO-path</span>
</div>
<img
src="/img/TODO-slug/feature-1.jpg"
src="/img/<?= htmlspecialchars($cs_slug) ?>/feature-1.jpg"
alt="TODO description"
class="screenshot-screen"
loading="lazy"
@@ -113,10 +92,10 @@ $cs_domain = 'TODO'; // e.g. 'example.co.uk' (no https://)
<div class="browser-dots">
<span></span><span></span><span></span>
</div>
<span class="browser-url"><?= htmlspecialchars($cs_domain) ?>/TODO-path</span>
<span class="browser-url"><?= htmlspecialchars($p['domain']) ?>/TODO-path</span>
</div>
<img
src="/img/TODO-slug/feature-2.jpg"
src="/img/<?= htmlspecialchars($cs_slug) ?>/feature-2.jpg"
alt="TODO description"
class="screenshot-screen"
loading="lazy"
@@ -136,15 +115,4 @@ $cs_domain = 'TODO'; // e.g. 'example.co.uk' (no https://)
</div>
</section>
<!-- ── CTA — DO NOT CHANGE ───────────────────────────────────────── -->
<section class="section section-cta">
<div class="section-label">— Next</div>
<div class="section-content">
<a href="/portfolio" class="cs-back cs-back--lg">← Back to All Work</a>
<p class="large-text">Got a project in mind?</p>
<a href="mailto:hello@uovidiu.com" class="btn">Get in Touch →</a>
</div>
</section>
<?php require __DIR__ . '/../../includes/footer.php'; ?>
<?php require __DIR__ . '/../../includes/cs_footer.php'; ?>

View File

@@ -0,0 +1,64 @@
<?php
$cs_slug = 'lhbeng';
require __DIR__ . '/../../includes/cs_header.php';
?>
<!-- ── HERO SCREENSHOT ───────────────────────────────────────────── -->
<section class="section">
<div class="section-label">Project Overview</div>
<div class="section-content">
<p>Full website redesign with a simple content manager — so you can update your portfolio, team profiles, and job listings yourself without needing a developer every time.</p>
</div>
<div class="screenshot-hero-wrap">
<div class="browser-chrome">
<div class="browser-dots">
<span></span><span></span><span></span>
</div>
<span class="browser-url"><?= htmlspecialchars($p['domain']) ?></span>
</div>
<img
src="/img/lhbeng/hero.jpg"
alt="LHB Engineering — Homepage"
class="screenshot-hero"
loading="lazy"
>
</div>
</section>
<!-- ── FEATURE / FLOW SCREENSHOTS (2-col) ────────────────────────── -->
<section class="section">
<div class="section-label">Website CMS</div>
<div class="services-grid">
<div class="service-item screenshot-card">
<span class="service-num">Website CMS</span>
<p class="screenshot-card__desc">Full-fledged CMS for content.</p>
<div class="browser-chrome browser-chrome--sm">
<div class="browser-dots">
<span></span><span></span><span></span>
</div>
<span class="browser-url"><?= htmlspecialchars($p['domain']) ?>/admin</span>
</div>
<img
src="/img/lhbeng/admin.jpg"
alt="LHB Engineering CMS admin panel"
class="screenshot-screen"
loading="lazy"
>
</div>
</div>
</section>
<!-- ── CRAFT & EXECUTION ─────────────────────────────────────────── -->
<section class="section">
<div class="section-label">Craft & Execution</div>
<div class="section-content">
<p>Built a full redesign for LHB Engineering, replacing their outdated site with a clean, modern layout that better reflects the scale and quality of their work. <br/>The new site is fast, fully responsive, and structured so visitors can quickly find services, past projects, and contact details. <br/>
Alongside the redesign, I built a simple CMS so the team can manage their portfolio, staff profiles, and job listings themselves — no developer needed for day-to-day updates.</p>
</div>
</section>
<?php require __DIR__ . '/../../includes/cs_footer.php'; ?>

View File

@@ -1,41 +1,8 @@
<?php
/*
* CASE STUDY PAGE TEMPLATE
* ─────────────────────────────────────────────────────────────────
* Each project gets its own directory under portfolio/{slug}/
* Copy this file as a starting point for new case studies.
*
* Required: $title, $description, $extra_css before require header.
* Back link: always points to /portfolio via .cs-back anchor.
* Images: store in /img/{slug}/ — see naming convention in CLAUDE.md.
* ─────────────────────────────────────────────────────────────────
*/
require __DIR__.'/../../data/projects.php';
$p = $projects['thompson'];
$title = 'Thompson Service Centre — Case Study';
$description = 'How we built a trust-first digital presence for a 25-year Peterborough garage.';
$extra_css = '/css/portfolio.css';
require __DIR__.'/../../includes/header.php';
$cs_slug = 'thompson';
require __DIR__ . '/../../includes/cs_header.php';
?>
<div class="cs-breadcrumb">
<a href="/portfolio" class="cs-back">← All Work</a>
<span class="cs-breadcrumb-label">[<?= htmlspecialchars($p['num']) ?> / <?= htmlspecialchars($p['code']) ?>]</span>
</div>
<header class="hero">
<div class="hero-label">Case Study — <?= htmlspecialchars($p['num']) ?></div>
<h1>Thompson<br>Service Centre</h1>
<p class="hero-sub">Website Redesign - 2025</p>
<ul class="cs-meta-bar">
<li>HTML - Tailwind CSS v4 - GSAP</li>
<li>Thompson Service Centre, Peterborough</li>
<li>2025</li>
</ul>
</header>
<section class="section">
<div class="section-label">Project Overview</div>
@@ -51,8 +18,9 @@ require __DIR__.'/../../includes/header.php';
<div class="browser-dots">
<span></span><span></span><span></span>
</div>
<span class="browser-url">thompsonservicecentre.co.uk</span>
<span class="browser-url"><?= htmlspecialchars($p['domain']) ?></span>
</div>
<div class="screenshot-hero-scroll">
<img
src="/img/thompson/hero.jpg"
alt="Thompson Service Centre — Homepage"
@@ -60,6 +28,7 @@ require __DIR__.'/../../includes/header.php';
loading="lazy"
>
</div>
</div>
</section>
<section class="section">
@@ -72,7 +41,7 @@ require __DIR__.'/../../includes/header.php';
<div class="browser-dots">
<span></span><span></span><span></span>
</div>
<span class="browser-url">thompsonservicecentre.co.uk/book</span>
<span class="browser-url"><?= htmlspecialchars($p['domain']) ?>/book</span>
</div>
<img
src="/img/thompson/booking-lookup.jpg"
@@ -88,7 +57,7 @@ require __DIR__.'/../../includes/header.php';
<div class="browser-dots">
<span></span><span></span><span></span>
</div>
<span class="browser-url">thompsonservicecentre.co.uk/book</span>
<span class="browser-url"><?= htmlspecialchars($p['domain']) ?>/book</span>
</div>
<img
src="/img/thompson/booking-confirm.jpg"
@@ -109,14 +78,4 @@ require __DIR__.'/../../includes/header.php';
</div>
</section>
<section class="section section-cta">
<div class="section-label">— Next</div>
<div class="section-content">
<a href="/portfolio" class="cs-back cs-back--lg">← Back to All Work</a>
<p class="large-text">Got a project in mind?</p>
<a href="mailto:hello@uovidiu.com" class="btn">Get in Touch →</a>
</div>
</section>
<?php
require __DIR__.'/../../includes/footer.php'; ?>
<?php require __DIR__ . '/../../includes/cs_footer.php'; ?>