feat: premium Layout.vue for content pages + competitive comparison section

This commit is contained in:
artale 2026-06-03 14:34:51 +02:00
parent 74a9c3cfe0
commit 1aac97759f
4 changed files with 294 additions and 267 deletions

View File

@ -109,6 +109,23 @@
</div>
</section>
<!-- Why FDSA -->
<section class="sec" id="why-fdsa">
<div class="sec-label">Compared To</div>
<h2 class="sec-title">Why FDSA vs Other Courses</h2>
<div class="compare-grid">
<div class="compare-c" v-for="c in comparisons" :key="c.name">
<div class="compare-name">{{ c.name }}</div>
<ul class="compare-pros">
<li v-for="pro in c.pros" :key="pro"><span class="material-symbols-outlined">check</span>{{ pro }}</li>
</ul>
<ul class="compare-cons">
<li v-for="con in c.cons" :key="con"><span class="material-symbols-outlined">close</span>{{ con }}</li>
</ul>
</div>
</div>
</section>
<!-- Pricing -->
<section class="sec pricing-sec" id="pricing">
<div class="sec-label">Investment</div>
@ -219,11 +236,19 @@ const testimonials = [
const faqs = [
{ q: 'Do I need API keys to run the labs?', a: 'No. All 13 labs include a mock LLM client that works offline. You only need API keys if you want to run against real models.', open: false },
{ q: 'What tools/CLIs does this course cover?', a: 'The course is tool-agnostic. The concepts apply to Claude Code, Pi Agent, OpenCode, Gemini CLI, and any agent harness. Labs use Python with an Anthropic-style API that\'s easy to adapt.', open: false },
{ q: 'How does FDSA compare to TAC or ClaudeFAST?', a: 'TAC ($97-147) focuses on tactical coding with 14 lessons. ClaudeFAST ($89-299) sells skill kits with 280 skills. FDSA ($97-247) gives you 65 lessons across 8 modules AND 20 skill kits — the most comprehensive single package for production agentic engineering.', open: false },
{ q: 'How long does the course take?', a: 'Self-paced: 40-60 hours total. Most students complete M1-M7 in 4-6 weeks. M8 capstone adds 1-2 weeks.', open: false },
{ q: 'What\'s the refund policy?', a: '30-day guarantee. If you\'re not satisfied, email artale@fdsa.agency for a full refund.', open: false },
{ q: 'Can I buy individual skill kits?', a: 'Yes. Security Foundation ($49), Multi-Agent Orch ($49), Verifier Pro ($39), and 4 more kits available individually on the pricing page.', open: false },
]
const comparisons = [
{ name: 'FDSA', pros: ['65 lessons + 13 labs', '20 skill kits included', '8 modules (foundations to capstone)', 'Mock LLM for offline work', 'Tool-agnostic (any CLI)', '30-day guarantee'], cons: ['Newer platform', 'No video content yet', 'Community still growing'] },
{ name: 'TAC', pros: ['14 focused lessons', '4 reference repos', 'Active YouTube channel', 'Proven track record'], cons: ['$97-147 for less content', 'No skill kits', 'No capstone project', 'Claude Code focused only'] },
{ name: 'ClaudeFAST', pros: ['280 skill files', '16 agent definitions', '$89 entry price', 'Active community'], cons: ['$299 for full access', 'No structured modules', 'No hands-on labs', 'Claude Code only'] },
{ name: 'Learn Harness', pros: ['Free (Anthropic)', '6 projects', '11 languages', 'Official Anthropic'], cons: ['No advanced patterns', 'No skill kits', 'No capstone', 'No security ladder'] },
]
onMounted(() => {
const observer = new IntersectionObserver((entries) => {
entries.forEach(entry => {
@ -265,7 +290,7 @@ onMounted(() => {
.hero-sec{min-height:90vh;display:flex;flex-direction:column;align-items:center;justify-content:center;padding:140px 24px 60px;text-align:center;position:relative;overflow:hidden}
.hero-grid{position:absolute;inset:0;background-image:linear-gradient(rgba(217,92,65,0.04) 1px,transparent 1px),linear-gradient(90deg,rgba(217,92,65,0.04) 1px,transparent 1px);background-size:40px 40px;pointer-events:none}
.hero-glow{position:absolute;inset:0;background:radial-gradient(ellipse at center,rgba(217,92,65,0.08) 0%,transparent 60%);pointer-events:none}
.hero-inner{position:relative;z-index:1;max-width:680px}
.hero-inner{position:relative;z-index:1;max-width:680px;width:100%;margin:0 auto}
.hero-pill{display:inline-flex;align-items:center;gap:8px;background:rgba(217,92,65,0.1);border:1px solid rgba(217,92,65,0.3);padding:6px 16px;border-radius:999px;font-size:11px;font-weight:700;letter-spacing:.15em;text-transform:uppercase;color:#d95c41;margin-bottom:24px}
.pill-dot{width:6px;height:6px;border-radius:50%;background:#d95c41;animation:pulse 2s ease-in-out infinite}
@keyframes pulse{0%,100%{opacity:1}50%{opacity:0.3}}
@ -280,7 +305,7 @@ onMounted(() => {
.btn-ghost:hover{border-color:#555}
/* Terminal */
.term-widget{margin-top:48px;max-width:460px;width:100%;background:rgba(17,17,17,0.9);backdrop-filter:blur(12px);border:1px solid #222;border-radius:12px;padding:20px;text-align:left;position:relative;overflow:hidden}
.term-widget{margin-top:48px;max-width:560px;width:100%;background:rgba(17,17,17,0.9);backdrop-filter:blur(12px);border:1px solid #222;border-radius:12px;padding:20px;text-align:left;position:relative;overflow:hidden}
.term-widget::before{content:'';position:absolute;top:0;left:0;right:0;height:2px;background:linear-gradient(90deg,transparent,#d95c41,transparent);opacity:.5}
.term-dots{display:flex;gap:8px;margin-bottom:16px}
.td{width:10px;height:10px;border-radius:50%}
@ -345,6 +370,18 @@ onMounted(() => {
.test-n{font-size:13px;font-weight:600;color:#e8e8e8}
.test-r{font-size:11px;color:#666}
/* Comparisons */
.compare-grid{display:grid;grid-template-columns:repeat(4,1fr);gap:16px}
.compare-c{background:rgba(17,17,17,0.85);backdrop-filter:blur(12px);border:1px solid rgba(255,255,255,0.06);border-radius:12px;padding:24px}
.compare-name{font-size:16px;font-weight:700;color:#f0f0f0;margin-bottom:16px;padding-bottom:12px;border-bottom:1px solid rgba(255,255,255,0.06)}
.compare-pros,.compare-cons{list-style:none;margin:0;padding:0;font-size:12px;line-height:1.6}
.compare-pros{color:#22c55e;margin-bottom:12px}
.compare-pros li,.compare-cons li{display:flex;align-items:flex-start;gap:6px;padding:4px 0}
.compare-pros .material-symbols-outlined,.compare-cons .material-symbols-outlined{font-size:14px;margin-top:2px}
.compare-pros .material-symbols-outlined{color:#22c55e}
.compare-cons .material-symbols-outlined{color:#ef4444}
.compare-cons{color:#888}
/* Pricing */
.pricing-grid{display:grid;grid-template-columns:repeat(3,1fr);gap:16px;max-width:960px;margin:0 auto}
.price-card{background:rgba(17,17,17,0.85);backdrop-filter:blur(12px);border:1px solid rgba(255,255,255,0.06);border-radius:12px;padding:32px 24px;text-align:center;transition:all .3s;display:flex;flex-direction:column}
@ -393,6 +430,7 @@ onMounted(() => {
.hero-sub{font-size:16px}
.feat-grid{grid-template-columns:1fr}
.test-grid{grid-template-columns:1fr}
.compare-grid{grid-template-columns:1fr}
.pricing-grid{grid-template-columns:1fr}
.stats-grid{grid-template-columns:repeat(2,1fr)}
.ft-grid{grid-template-columns:1fr 1fr;gap:24px}

View File

@ -0,0 +1,248 @@
<template>
<div class="fdsa-app">
<Layout>
<template #layout-top>
<!-- Site-wide banner could go here -->
</template>
</Layout>
</div>
</template>
<script setup>
import DefaultTheme from 'vitepress/theme'
const { Layout } = DefaultTheme
</script>
<style>
/* FDSA premium wrapper for all content pages */
.fdsa-app {
background: #0a0a0a;
min-height: 100vh;
}
/* Subtle gradient background on content pages */
.fdsa-app::before {
content: '';
position: fixed;
top: 0; left: 0; right: 0;
height: 600px;
background: radial-gradient(ellipse at 50% 0%, rgba(217,92,65,0.04) 0%, transparent 60%);
pointer-events: none;
z-index: 0;
}
/* Ensure VitePress elements sit above the gradient */
.VPNav, .VPSidebar, .VPContent {
position: relative;
z-index: 1;
}
/* Glass card around main content */
.VPDoc:not(.VPDoc--blank) > .container > .content {
background: rgba(17,17,17,0.6) !important;
backdrop-filter: blur(12px) !important;
border: 1px solid rgba(255,255,255,0.04) !important;
border-top: 1px solid rgba(255,255,255,0.08) !important;
border-radius: 12px !important;
}
/* Nav: match landing page */
.VPNav {
background: rgba(10,10,10,0.85) !important;
backdrop-filter: blur(16px) !important;
border-bottom: 1px solid rgba(255,255,255,0.06) !important;
}
/* FDSA brand in nav */
.VPNavBarTitle .title {
display: flex !important;
align-items: center !important;
gap: 8px !important;
font-family: 'DM Sans', sans-serif !important;
font-size: 20px !important;
font-weight: 800 !important;
letter-spacing: -0.5px !important;
color: #e8e8e8 !important;
}
.VPNavBarTitle .title::before {
content: 'terminal';
font-family: 'Material Symbols Outlined';
font-size: 22px;
color: #d95c41;
}
.VPNavBarTitle .logo {
display: none !important;
}
.VPNavBarMenuLink:hover, .VPNavBarMenuLink.active {
color: #d95c41 !important;
}
/* Sidebar: FDSA styling */
.VPSidebar {
background: transparent !important;
border-right: 1px solid rgba(255,255,255,0.04) !important;
}
.VPSidebar .item .text {
font-size: 13px !important;
font-weight: 500 !important;
}
.VPSidebar .item.active .text {
color: #d95c41 !important;
font-weight: 600 !important;
}
.VPSidebar .item .text:hover {
color: #d95c41 !important;
}
.VPSidebar .group + .group {
border-top: 1px solid rgba(255,255,255,0.04) !important;
}
/* Content area: padding inside glass card */
.vp-doc {
max-width: 800px;
margin: 0 auto;
padding: 32px 40px 48px;
}
/* Typography */
.vp-doc h1 {
font-size: 2.25rem !important;
font-weight: 800 !important;
letter-spacing: -0.5px !important;
line-height: 1.1 !important;
margin-bottom: 24px !important;
color: #f0f0f0 !important;
}
.vp-doc h2 {
font-size: 1.375rem !important;
font-weight: 700 !important;
letter-spacing: -0.3px !important;
padding-top: 32px !important;
margin-top: 40px !important;
margin-bottom: 16px !important;
border-top: 1px solid rgba(255,255,255,0.06) !important;
color: #f0f0f0 !important;
}
.vp-doc h3 {
font-size: 1.0625rem !important;
font-weight: 600 !important;
margin-top: 28px !important;
margin-bottom: 12px !important;
color: #f0f0f0 !important;
}
.vp-doc p {
font-size: 0.9375rem !important;
line-height: 1.7 !important;
color: #d0d0d0 !important;
margin-bottom: 16px !important;
}
.vp-doc a {
color: #d95c41 !important;
text-decoration: underline;
text-underline-offset: 2px;
}
.vp-doc a:hover { color: #e87d2f !important; }
/* Code blocks */
.vp-doc div[class*='language-'] {
border-radius: 10px !important;
border: 1px solid rgba(255,255,255,0.04) !important;
background: rgba(0,0,0,0.4) !important;
margin: 24px 0 !important;
}
.vp-code {
font-family: 'DM Mono', ui-monospace, monospace !important;
font-size: 13px !important;
line-height: 1.7 !important;
}
.vp-doc code {
font-family: 'DM Mono', ui-monospace, monospace !important;
font-size: 0.8125rem !important;
background: rgba(255,255,255,0.04) !important;
border: 1px solid rgba(255,255,255,0.06) !important;
padding: 2px 8px !important;
border-radius: 6px !important;
color: #e8e8e8 !important;
}
/* Tables */
.vp-doc table {
width: 100%;
border-collapse: collapse;
border: 1px solid rgba(255,255,255,0.06);
border-radius: 10px;
overflow: hidden;
font-size: 0.875rem !important;
margin: 24px 0 !important;
}
.vp-doc th {
background: rgba(255,255,255,0.03);
font-weight: 600;
font-size: 0.75rem !important;
text-transform: uppercase;
letter-spacing: 0.06em;
color: #888;
padding: 12px 16px;
border-bottom: 1px solid rgba(255,255,255,0.06);
}
.vp-doc td {
padding: 12px 16px;
border-bottom: 1px solid rgba(255,255,255,0.03);
font-size: 0.875rem !important;
color: #d0d0d0;
}
.vp-doc tr:last-child td { border-bottom: none; }
.vp-doc tr:hover td { background: rgba(255,255,255,0.02); }
/* Blockquotes */
.vp-doc blockquote {
border-left: 3px solid #d95c41 !important;
background: rgba(217,92,65,0.04) !important;
padding: 16px 24px !important;
border-radius: 0 10px 10px 0 !important;
margin: 24px 0 !important;
}
.vp-doc blockquote p {
font-size: 0.875rem !important;
color: #888 !important;
font-style: italic !important;
}
/* Dividers */
.vp-doc hr {
border: none;
border-top: 1px solid rgba(255,255,255,0.04);
margin: 48px 0;
}
/* Custom blocks */
.custom-block {
border-radius: 10px !important;
border: 1px solid rgba(255,255,255,0.04) !important;
padding: 16px 20px !important;
margin: 24px 0 !important;
background: rgba(255,255,255,0.02) !important;
}
.custom-block.tip {
border-color: rgba(217,92,65,0.3) !important;
background: rgba(217,92,65,0.04) !important;
}
/* Footer */
.VPFooter {
border-top: 1px solid rgba(255,255,255,0.04) !important;
background: transparent !important;
padding: 24px 0 !important;
}
.VPFooter .message {
font-size: 13px !important;
color: #666 !important;
}
/* Mobile responsive */
@media (max-width: 768px) {
.vp-doc { padding: 24px 20px; }
.vp-doc h1 { font-size: 1.75rem !important; }
.vp-doc h2 { font-size: 1.125rem !important; }
}
</style>

View File

@ -1,13 +1,12 @@
import DefaultTheme from 'vitepress/theme'
import Layout from './Layout.vue'
import LandingLayout from './LandingLayout.vue'
import FDocLayout from './FDocLayout.vue'
import './style.css'
export default {
extends: DefaultTheme,
// Keep the default VitePress Layout, override specific pages
Layout,
enhanceApp({ app }) {
app.component('LandingLayout', LandingLayout)
app.component('FDocLayout', FDocLayout)
},
}

View File

@ -1,5 +1,6 @@
/* FDSA Design System All Pages
Dark, sharp, typography-driven. Mechanical oranges on near-black. */
/* FDSA Design System Base Variables
Only CSS custom properties and font imports.
Page-level styling is in Layout.vue (content pages) and LandingLayout.vue (landing page). */
@import url('https://fonts.googleapis.com/css2?family=DM+Sans:opsz,wght@9..40,400;9..40,500;9..40,700;9..40,800&family=DM+Mono:wght@400;500&display=swap');
@import url('https://fonts.googleapis.com/css2?family=Material+Symbols+Outlined:opsz,wght,FILL,GRAD@20..48,100..700,0,0&display=swap');
@ -24,7 +25,7 @@
--vp-font-family-mono: 'DM Mono', ui-monospace, monospace;
}
/* Light mode (toggle - keep as is, most users see dark) */
/* Light mode toggle */
:root:not(.dark) {
--vp-c-bg: #f8f8f5;
--vp-c-bg-soft: #fff;
@ -47,7 +48,6 @@
line-height: 1;
}
/* Base */
body {
font-family: var(--vp-font-family-base);
font-weight: 400;
@ -57,261 +57,3 @@ body {
}
::selection { background: var(--vp-c-brand-1); color: #fff; }
/* === TOP NAV === */
.VPNav {
border-bottom: 1px solid var(--vp-c-divider) !important;
background: rgba(10,10,10,0.85) !important;
backdrop-filter: blur(16px) !important;
}
/* FDSA brand in nav — orange terminal icon */
.VPNavBarTitle .title {
display: flex !important;
align-items: center !important;
gap: 8px !important;
font-family: 'DM Sans', sans-serif !important;
font-size: 20px !important;
font-weight: 800 !important;
letter-spacing: -0.5px !important;
color: #e8e8e8 !important;
}
.VPNavBarTitle .title::before {
content: 'terminal';
font-family: 'Material Symbols Outlined';
font-size: 22px;
color: #d95c41;
}
.VPNavBarTitle .logo {
display: none !important;
}
/* Nav link hover */
.VPNavBarMenuLink:hover, .VPNavBarMenuLink.active {
color: var(--vp-c-brand-1) !important;
}
/* === SIDEBAR — FDSA style === */
.VPSidebar {
background: var(--vp-c-bg-alt) !important;
border-right: 1px solid var(--vp-c-divider) !important;
width: 240px !important;
padding-top: 8px !important;
}
.VPSidebar .item .text {
font-size: 13px !important;
font-weight: 500 !important;
transition: color 0.15s !important;
}
.VPSidebar .item .text:hover {
color: var(--vp-c-brand-1) !important;
}
.VPSidebar .group + .group {
border-top: 1px solid var(--vp-c-divider) !important;
margin-top: 8px !important;
padding-top: 8px !important;
}
/* Active sidebar item */
.VPSidebar .item.active .text {
color: var(--vp-c-brand-1) !important;
font-weight: 600 !important;
}
/* Sidebar link hover bg */
.VPSidebar .item:hover {
background: transparent !important;
}
/* === CONTENT AREA === */
.VPContent {
padding-left: 240px;
}
@media (max-width: 768px) {
.VPContent { padding-left: 0; }
}
/* === DOC PAGES — glass card wrapper === */
.VPDoc:not(.VPDoc--blank) > .container > .content {
background: rgba(17,17,17,0.5) !important;
backdrop-filter: blur(8px) !important;
border: 1px solid rgba(255,255,255,0.04) !important;
border-radius: 12px !important;
padding: 0 32px !important;
overflow: hidden;
}
.vp-doc {
max-width: 800px;
margin: 0 auto;
padding: 32px 0 48px;
}
.vp-doc h1 {
font-size: 2.25rem !important;
font-weight: 800 !important;
letter-spacing: -0.5px !important;
line-height: 1.1 !important;
margin-bottom: 24px !important;
color: var(--vp-c-text-1) !important;
}
.vp-doc h2 {
font-size: 1.375rem !important;
font-weight: 700 !important;
letter-spacing: -0.3px !important;
padding-top: 32px !important;
margin-top: 40px !important;
margin-bottom: 16px !important;
border-top: 1px solid var(--vp-c-divider) !important;
color: var(--vp-c-text-1) !important;
}
.vp-doc h3 {
font-size: 1.0625rem !important;
font-weight: 600 !important;
margin-top: 28px !important;
margin-bottom: 12px !important;
color: var(--vp-c-text-1) !important;
}
.vp-doc p {
font-size: 0.9375rem !important;
line-height: 1.7 !important;
color: var(--vp-c-text-1) !important;
margin-bottom: 16px !important;
}
/* Links */
.vp-doc a {
color: var(--vp-c-brand-1) !important;
text-decoration: underline;
text-underline-offset: 2px;
transition: color 0.2s;
}
.vp-doc a:hover { color: var(--vp-c-brand-2) !important; }
/* Code blocks — glass cards */
.vp-doc div[class*='language-'] {
border-radius: 10px !important;
border: 1px solid var(--vp-c-border) !important;
background: rgba(17,17,17,0.85) !important;
backdrop-filter: blur(12px) !important;
margin: 24px 0 !important;
}
.vp-code {
font-family: 'DM Mono', ui-monospace, monospace !important;
font-size: 13px !important;
line-height: 1.7 !important;
}
/* Inline code */
.vp-doc code {
font-family: 'DM Mono', ui-monospace, monospace !important;
font-size: 0.8125rem !important;
background: var(--vp-c-bg-mute) !important;
border: 1px solid var(--vp-c-border) !important;
padding: 2px 8px !important;
border-radius: 6px !important;
color: var(--vp-c-text-1) !important;
}
/* Tables */
.vp-doc table {
width: 100%;
border-collapse: collapse;
border: 1px solid var(--vp-c-border);
border-radius: 10px;
overflow: hidden;
font-size: 0.875rem !important;
margin: 24px 0 !important;
}
.vp-doc th {
background: var(--vp-c-bg-mute);
font-weight: 600;
font-size: 0.75rem !important;
text-transform: uppercase;
letter-spacing: 0.06em;
color: var(--vp-c-text-2);
padding: 12px 16px;
border-bottom: 1px solid var(--vp-c-border);
}
.vp-doc td {
padding: 12px 16px;
border-bottom: 1px solid var(--vp-c-divider);
font-size: 0.875rem !important;
}
.vp-doc tr:last-child td { border-bottom: none; }
.vp-doc tr:hover td { background: var(--vp-c-bg-soft); }
/* Blockquotes */
.vp-doc blockquote {
border-left: 3px solid var(--vp-c-brand-1) !important;
background: var(--vp-c-brand-soft) !important;
padding: 16px 24px !important;
border-radius: 0 10px 10px 0 !important;
margin: 24px 0 !important;
}
.vp-doc blockquote p {
font-size: 0.875rem !important;
color: var(--vp-c-text-2) !important;
font-style: italic !important;
}
/* Images */
.vp-doc img {
max-width: 100%;
height: auto;
border-radius: 10px;
margin: 24px 0;
border: 1px solid var(--vp-c-border);
}
/* Lists */
.vp-doc ul, .vp-doc ol {
font-size: 0.9375rem !important;
line-height: 1.7 !important;
padding-left: 1.5em !important;
margin-bottom: 16px !important;
}
.vp-doc li { margin: 6px 0 !important; }
/* Dividers */
.vp-doc hr {
border: none;
border-top: 1px solid var(--vp-c-divider);
margin: 48px 0;
}
/* Custom blocks (tips, warnings) */
.custom-block {
border-radius: 10px !important;
border: 1px solid var(--vp-c-border) !important;
padding: 16px 20px !important;
margin: 24px 0 !important;
}
.custom-block.tip {
border-color: rgba(217,92,65,0.3) !important;
background: rgba(217,92,65,0.06) !important;
}
/* Footer */
.VPFooter {
border-top: 1px solid var(--vp-c-divider) !important;
background: var(--vp-c-bg-alt) !important;
padding: 24px 0 !important;
}
.VPFooter .message {
font-size: 13px !important;
color: var(--vp-c-text-3) !important;
}
/* === RESPONSIVE === */
@media (max-width: 768px) {
.vp-doc { padding: 24px 16px; }
.vp-doc h1 { font-size: 1.75rem !important; }
.vp-doc h2 { font-size: 1.125rem !important; }
.vp-doc div[class*='language-'] { margin: 16px 0; }
}
/* Print */
@media print {
.VPNav, .VPSidebar, .VPFooter { display: none !important; }
}