feat(phasefinal-web): corporate site stack on ana-docker
Single static page (nginx) fronted by Traefik at www.phasefinal.com, built from the design brief. Site markup/CSS checked in verbatim from the design session; fonts self-hosted (SIL OFL) with the @font-face block uncommented, which every fresh export re-comments. Routed via a Traefik file-provider config rather than the container labels: the docker provider on ana-docker was not registering newly-created containers, so the file router avoids restarting shared ingress. Labels are retained in compose so the file can be dropped once that is fixed.
This commit is contained in:
@@ -0,0 +1,255 @@
|
||||
/* Phase Final, Inc. — single-page site
|
||||
Brand: Volt #90C73E over cool slate neutrals, per Phase Final tokens.
|
||||
Zero external requests; no JavaScript.
|
||||
|
||||
FONTS: the brand faces are Space Grotesk (display), IBM Plex Sans (body),
|
||||
IBM Plex Mono (labels). To keep this zip free of external requests they are
|
||||
referenced by local name only, with system fallbacks. To ship the exact
|
||||
faces, place woff2 files in fonts/ and uncomment the @font-face blocks. */
|
||||
|
||||
@font-face { font-family: "Space Grotesk"; src: url("fonts/SpaceGrotesk-Var.woff2") format("woff2"); font-weight: 300 700; font-display: swap; }
|
||||
@font-face { font-family: "IBM Plex Sans"; src: url("fonts/IBMPlexSans-Var.woff2") format("woff2"); font-weight: 100 700; font-display: swap; }
|
||||
@font-face { font-family: "IBM Plex Mono"; src: url("fonts/IBMPlexMono-Regular.woff2") format("woff2"); font-weight: 400; font-display: swap; }
|
||||
@font-face { font-family: "IBM Plex Mono"; src: url("fonts/IBMPlexMono-SemiBold.woff2") format("woff2"); font-weight: 600; font-display: swap; }
|
||||
|
||||
:root {
|
||||
--ink: #0f1318;
|
||||
--ink-2: #181d22;
|
||||
--text: #0f1318;
|
||||
--text-secondary: #4d5763;
|
||||
--text-tertiary: #6b7682;
|
||||
--paper: #f6f8f9;
|
||||
--border: #c2cad2;
|
||||
--border-subtle: #dde2e7;
|
||||
--accent: #90c73e;
|
||||
--accent-text: #588021; /* AA on light */
|
||||
--volt-200: #d0e8a0;
|
||||
--volt-300: #b8db72;
|
||||
--volt-400: #a3d052;
|
||||
--volt-500: #90c73e;
|
||||
--slate-300: #c2cad2;
|
||||
--slate-400: #97a2ad;
|
||||
--slate-700: #394149;
|
||||
--slate-800: #262c33;
|
||||
--display: "Space Grotesk", "IBM Plex Sans", -apple-system, "Segoe UI", Helvetica, sans-serif;
|
||||
--sans: "IBM Plex Sans", -apple-system, BlinkMacSystemFont, "Segoe UI", Helvetica, Arial, sans-serif;
|
||||
--mono: "IBM Plex Mono", ui-monospace, "SF Mono", Menlo, Consolas, monospace;
|
||||
}
|
||||
|
||||
@media (prefers-color-scheme: dark) {
|
||||
:root {
|
||||
--text: #f6f8f9;
|
||||
--text-secondary: #c2cad2;
|
||||
--text-tertiary: #97a2ad;
|
||||
--paper: #0f1318;
|
||||
--border: #394149;
|
||||
--border-subtle: #262c33;
|
||||
--accent-text: #b8db72;
|
||||
--ink: #0a0d11;
|
||||
--ink-2: #181d22;
|
||||
}
|
||||
}
|
||||
|
||||
* { box-sizing: border-box; }
|
||||
|
||||
body {
|
||||
margin: 0;
|
||||
background: var(--paper);
|
||||
color: var(--text);
|
||||
font-family: var(--sans);
|
||||
font-size: 16.5px;
|
||||
line-height: 1.65;
|
||||
-webkit-font-smoothing: antialiased;
|
||||
}
|
||||
|
||||
::selection { background: var(--volt-200); color: #0f1318; }
|
||||
|
||||
a { color: var(--accent-text); text-decoration: underline; text-underline-offset: 3px; }
|
||||
p { margin: 0; text-wrap: pretty; }
|
||||
|
||||
/* ---- Hero: ink console surface with engineering grid ---- */
|
||||
#hero {
|
||||
background: var(--ink);
|
||||
color: #f6f8f9;
|
||||
position: relative;
|
||||
overflow: hidden;
|
||||
background-image:
|
||||
linear-gradient(rgba(246,248,249,0.05) 1px, transparent 1px),
|
||||
linear-gradient(90deg, rgba(246,248,249,0.05) 1px, transparent 1px);
|
||||
background-size: 48px 48px;
|
||||
border-bottom: 3px solid var(--volt-500);
|
||||
}
|
||||
|
||||
.hero-inner {
|
||||
max-width: 920px;
|
||||
margin: 0 auto;
|
||||
padding: clamp(56px, 9vw, 104px) 28px clamp(56px, 8vw, 96px);
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: clamp(40px, 6vw, 64px);
|
||||
}
|
||||
|
||||
.wordmark { height: clamp(48px, 7.5vw, 72px); width: auto; display: block; align-self: flex-start; }
|
||||
|
||||
.hero-copy { max-width: 800px; }
|
||||
|
||||
.lede {
|
||||
font-family: var(--display);
|
||||
font-size: clamp(32px, 5.6vw, 54px);
|
||||
line-height: 1.1;
|
||||
letter-spacing: -0.02em;
|
||||
font-weight: 500;
|
||||
color: #ffffff;
|
||||
text-wrap: balance;
|
||||
}
|
||||
.sublede {
|
||||
margin-top: 24px;
|
||||
font-size: clamp(16.5px, 2vw, 19px);
|
||||
color: var(--slate-300);
|
||||
max-width: 62ch;
|
||||
}
|
||||
.intro-note {
|
||||
margin-top: 20px;
|
||||
font-size: 16px;
|
||||
color: var(--slate-400);
|
||||
max-width: 62ch;
|
||||
}
|
||||
|
||||
.spec-bar {
|
||||
font-family: var(--mono);
|
||||
font-size: 12.5px;
|
||||
letter-spacing: 0.07em;
|
||||
text-transform: uppercase;
|
||||
color: var(--slate-400);
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
gap: 10px 0;
|
||||
}
|
||||
.spec-bar span { padding: 0 18px; border-left: 1px solid var(--slate-700); }
|
||||
.spec-bar span:first-child { padding-left: 0; border-left: none; }
|
||||
.spec-bar .spec-accent { color: var(--volt-300); }
|
||||
|
||||
/* ---- Body ---- */
|
||||
main {
|
||||
max-width: 920px;
|
||||
margin: 0 auto;
|
||||
padding: 0 28px 72px;
|
||||
}
|
||||
|
||||
section {
|
||||
border-top: 1px solid var(--border);
|
||||
padding: 52px 0 64px;
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
gap: 32px;
|
||||
}
|
||||
#services { border-top: none; padding-top: clamp(52px, 7vw, 76px); }
|
||||
|
||||
h2 {
|
||||
margin: 0;
|
||||
flex: 0 0 208px;
|
||||
font-family: var(--mono);
|
||||
font-size: 12px;
|
||||
font-weight: 600;
|
||||
letter-spacing: 0.15em;
|
||||
text-transform: uppercase;
|
||||
color: var(--text-tertiary);
|
||||
}
|
||||
h2 .num { color: var(--accent-text); margin-right: 12px; }
|
||||
|
||||
.section-body { flex: 1 1 380px; max-width: 620px; }
|
||||
|
||||
/* Services */
|
||||
.service-list {
|
||||
list-style: none;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 30px;
|
||||
}
|
||||
.service-list h3 {
|
||||
margin: 0 0 6px;
|
||||
font-family: var(--display);
|
||||
font-size: 22px;
|
||||
line-height: 1.3;
|
||||
letter-spacing: -0.01em;
|
||||
font-weight: 600;
|
||||
}
|
||||
.service-list p { color: var(--text-secondary); }
|
||||
|
||||
/* Engagement */
|
||||
#engagement .section-body p + p { margin-top: 18px; }
|
||||
.referral-note { color: var(--text-secondary); }
|
||||
|
||||
/* Track record */
|
||||
.record-list { margin: 0; }
|
||||
.record { padding: 24px 0 26px; }
|
||||
.record:first-child { padding-top: 0; }
|
||||
.record + .record { border-top: 1px solid var(--border-subtle); }
|
||||
.record dt {
|
||||
font-family: var(--mono);
|
||||
font-size: 12.5px;
|
||||
letter-spacing: 0.05em;
|
||||
text-transform: uppercase;
|
||||
color: var(--text-tertiary);
|
||||
margin-bottom: 6px;
|
||||
}
|
||||
.record .idx { color: var(--accent-text); margin-right: 6px; }
|
||||
.record dd { margin: 0; font-size: 17.5px; }
|
||||
.record strong { font-family: var(--display); font-weight: 600; }
|
||||
|
||||
/* Contact — ink console panel */
|
||||
#contact {
|
||||
display: block;
|
||||
border-top: none;
|
||||
background: var(--ink-2);
|
||||
background-image:
|
||||
linear-gradient(rgba(246,248,249,0.05) 1px, transparent 1px),
|
||||
linear-gradient(90deg, rgba(246,248,249,0.05) 1px, transparent 1px);
|
||||
background-size: 48px 48px;
|
||||
border-left: 3px solid var(--volt-500);
|
||||
border-radius: 16px;
|
||||
padding: clamp(40px, 6vw, 72px);
|
||||
color: #f6f8f9;
|
||||
}
|
||||
#contact h2 { color: var(--slate-400); margin-bottom: 20px; }
|
||||
#contact h2 .num { color: var(--volt-400); }
|
||||
.contact-address {
|
||||
font-size: clamp(23px, 4vw, 38px);
|
||||
line-height: 1.25;
|
||||
}
|
||||
.contact-address a {
|
||||
font-family: var(--display);
|
||||
font-weight: 600;
|
||||
letter-spacing: -0.015em;
|
||||
color: var(--volt-300);
|
||||
text-decoration: none;
|
||||
border-bottom: 2px solid var(--volt-500);
|
||||
}
|
||||
.contact-address a:hover { color: var(--volt-200); }
|
||||
.contact-note {
|
||||
margin-top: 20px;
|
||||
color: var(--slate-300);
|
||||
max-width: 56ch;
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
/* Footer */
|
||||
footer {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: baseline;
|
||||
gap: 16px;
|
||||
flex-wrap: wrap;
|
||||
padding-top: 28px;
|
||||
font-family: var(--mono);
|
||||
font-size: 12.5px;
|
||||
color: var(--text-tertiary);
|
||||
}
|
||||
|
||||
@media (max-width: 480px) {
|
||||
main { padding: 0 20px 56px; }
|
||||
.hero-inner { padding-left: 20px; padding-right: 20px; }
|
||||
section { padding: 40px 0 48px; }
|
||||
}
|
||||
Reference in New Issue
Block a user