diff --git a/src/components/layout/InterestHero.astro b/src/components/layout/InterestHero.astro index fc8f301..c50a900 100644 --- a/src/components/layout/InterestHero.astro +++ b/src/components/layout/InterestHero.astro @@ -2,16 +2,14 @@ /** * InterestHero.astro * --------------------------------------------------------------------------- - * Shared header for every interest sub-page, implementing the spec's - * per-interest template (Header: title + tagline; Overview: narrative). Uses the - * warm "interest" surface tone via InterestLayout. + * Shared header for every interest sub-page. Compact hero on the animated + * Milky Way field: a back-to-hub breadcrumb, a small icon mark, the title, and + * the italic tagline. * - * The decorative icon and the tagline (in mono, as a pull quote) give each page - * a consistent rhythm while the page supplies its own title + overview copy. - * - * An optional `image` prop renders a wide celestial-framed banner behind / above - * the heading so each interest page leads with a vibe-matched photo. A faint - * starfield + alchemical accent reinforces the esoteric mood. + * Tuned for the dark starfield: text uses bright cream tones (not the dim + * --color-text-subtle/--color-text which vanish on the deep sky). The title is + * h2-sized (the page is a sub-page, not Home) so it doesn't dominate. An + * optional banner image sits above the heading. */ import Icon from '@components/Icon.astro'; import Reveal from '@components/motion/Reveal.astro'; @@ -46,20 +44,57 @@ const { Carries the per-page morph name (one .vt-sky per page snapshot). --> -
- - - - {eyebrow} - - + {/* Two-column layout: text on the left, image on the right. Putting the image + BESIDE the text (instead of stacked above it) means the hero height is + driven by the text column and stays consistent across interest pages + regardless of image presence. On small screens it stacks (image below). */} +
+ {/* --- Left: text column --- */} +
+ + + + {eyebrow} + + + + + + + +

+ {title} +

+
+ + +

+ {tagline} +

+
+
+ + {/* --- Right: image column (only when an image is provided). A fixed + aspect keeps every interest hero the same height. --- */} {image && ( - +
)} - - - - - - -

{title}

-
- - -

- {tagline} -

-
diff --git a/src/components/professional/Certifications.astro b/src/components/professional/Certifications.astro new file mode 100644 index 0000000..152c9a4 --- /dev/null +++ b/src/components/professional/Certifications.astro @@ -0,0 +1,77 @@ +--- +/** + * Certifications.astro + * --------------------------------------------------------------------------- + * Card grid for the Certifications section of the Professional page. Each entry + * is a cert with name, issuer, year, and optional status. Seeded with SAP/cloud + * placeholders (Greg to fill); swap the array below. + * + * Card aesthetic matches EducationHistory / ProjectCard. + */ +import Icon from "@components/Icon.astro"; + +interface CertEntry { + icon: string; + name: string; + issuer: string; + year: string; + status?: "Active" | "Expired" | "In progress"; +} + +// Placeholder entries — replace with Greg's real certifications. +const entries: CertEntry[] = [ + /*{ + icon: "microsoft-azure-devops", + name: "SAP BTP Certification", + issuer: "SAP", + year: "[Year]", + status: "Active", + },*/ + { + icon: "cloud", + name: "Planet 9 Devlopment", + issuer: "Neptune", + year: "2019", + status: "Active", + }, + /*{ + icon: "robot", + name: "[AI / ML cert]", + issuer: "[Issuer]", + year: "[Year]", + },*/ +]; +--- + +
+ { + entries.map((c) => ( +
+
+ + {c.status && {c.status}} +
+
+

+ {c.name} +

+

+ {c.issuer} +

+ + {c.year} + +
+
+ )) + } +
diff --git a/src/components/professional/EducationHistory.astro b/src/components/professional/EducationHistory.astro new file mode 100644 index 0000000..3c4c488 --- /dev/null +++ b/src/components/professional/EducationHistory.astro @@ -0,0 +1,76 @@ +--- +/** + * EducationHistory.astro + * --------------------------------------------------------------------------- + * Card grid for the Education section of the Professional page. Each entry is a + * degree/diploma with institution, period, and optional detail. Data is seeded + * with placeholder rows (Greg to fill); swap the array below with real entries. + * + * Mirrors the Timeline/ProjectCard card aesthetic: raised surface, hairline + * border, gold accent for the credential, mono period label. + */ +import Icon from "@components/Icon.astro"; + +interface EduEntry { + icon: string; + credential: string; + institution: string; + period: string; + detail?: string; +} + +// Placeholder entries — replace with Greg's real education history. +const entries: EduEntry[] = [ + { + icon: "school", + credential: "B.S., Computer Science", + institution: "Drexel University", + period: "2014 – 2018", + detail: + "Foundational coursework in software engineering, algorithms, and systems. Focuses in AI and human-computer interaction.", + }, +]; +--- + +
+ { + entries.map((e) => ( +
+
+ +
+

+ {e.credential} +

+

+ {e.institution} +

+ + {e.period} + +
+
+ {e.detail && ( +

+ {e.detail} +

+ )} +
+ )) + } +
diff --git a/src/components/professional/SectionNav.astro b/src/components/professional/SectionNav.astro index b735bcc..aa91501 100644 --- a/src/components/professional/SectionNav.astro +++ b/src/components/professional/SectionNav.astro @@ -2,15 +2,23 @@ /** * SectionNav.astro * --------------------------------------------------------------------------- - * Fixed LEFT-SIDE vertical rail for the Professional page. Shows the six - * sections as a stacked icon+label list, highlights the section currently in - * view, and lets the user click any item to smooth-scroll to it. A vertical - * progress line beside the items fills as the user scrolls down the page. + * Fixed LEFT-SIDE vertical rail for the Professional page. Six sections as a + * stacked icon+label list; highlights the current section; click to smooth- + * scroll. A vertical progress line LEFT of the icons fills as you scroll. * - * Stylistically it mirrors the page's `.card` language (same raised surface, - * border, radius) so it reads as a sibling of the content cards rather than a - * separate chrome element. Icons + labels use bright tokens so they pop on the - * dark surface. Hidden below `lg`. + * Three bugs previously fixed here: + * 1. Contrast: the rail used surface-relative tokens (--color-surface-raised / + * --color-cream) which collapsed to the same tone on light surfaces (the + * interest-surface cream made icons/text invisible). The rail now uses + * FIXED dark colors regardless of the page's surface tone. + * 2. Progress line clipping: the line sat at the icon column's horizontal + * center, running THROUGH the circles. It now sits in a dedicated left + * gutter, clear of the icons. + * 3. Last section (Contact) not activating: the IntersectionObserver band was + * too thin for the short final section to land in. The rootMargin is + * widened + click handlers set active immediately so feedback is instant. + * + * Hidden below `lg`. */ import Icon from "@components/Icon.astro"; const sections = [ @@ -28,70 +36,79 @@ const sections = [ class="pro-section-nav fixed left-4 top-1/2 z-40 hidden -translate-y-1/2 flex-col lg:flex" data-pro-nav > - {/* Rail container — matches the .card aesthetic: raised surface, hairline - border, 1rem radius. Bright icons + labels inside. */} + {/* Rail container. FIXED dark colors (not surface tokens) so it's always + legible regardless of the page's data-surface tone. Layout: a left gutter + for the progress line, then the icon+label list. */}
- {/* Vertical progress track behind the dots. */} - - {/* The fill bar — height set by JS as the user scrolls. */} -