diff --git a/pyproject.toml b/pyproject.toml index 4d35895671..5f66f7dd3a 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -35,6 +35,7 @@ dependencies = [ "frccontrol==2026.11", "furo==2025.12.19", "sphinx-build-compatibility", + "sphinxcontrib-youtube>=1.5.0", ] [tool.uv] diff --git a/source/_static/css/sw-components.css b/source/_static/css/sw-components.css new file mode 100644 index 0000000000..2ae6e8bc36 --- /dev/null +++ b/source/_static/css/sw-components.css @@ -0,0 +1,455 @@ +/* Shared component styles for FIRST Robotics 2027 pages. */ + +/* ── COLOR TOKENS ── */ + :root { + --frc: #009CD7; /* FIRST Process Blue */ + --frc-light: #e6f6fc; + --ftc: #e07000; /* FTC orange */ + --ftc-light: #fff3e0; + --shared: #2e7d32; /* shared green */ + --shared-light: #f1f8f1; + } + + /* ── TAB SELECTOR ── */ + #landing-tab-root { max-width: 900px; } + .wl-hero { text-align:center; padding:36px 0 8px; } + .wl-hero-title { font-size:2rem; font-weight:800; margin:0 0 12px; color:var(--color-foreground-primary,#1a1a1a); } + .wl-hero-copy { font-size:1rem; color:var(--color-foreground-secondary,#555); max-width:560px; margin:0 auto 20px; line-height:1.6; } + .wl-hero-frc { color:var(--frc); } + .wl-hero-ftc { color:var(--ftc); } + .wl-tab-selector { text-align:center; padding:12px 0 28px; } + .wl-tab-prompt { font-size:1.1rem; font-weight:600; margin-bottom:16px; } + .wl-tab-buttons { display:flex; justify-content:center; gap:12px; flex-wrap:wrap; } + .wl-tab-btn { + padding:11px 26px; font-size:0.95rem; font-weight:600; + border-radius:6px; border:2px solid #ccc; + background:var(--color-background-secondary,#f8f8f8); + cursor:pointer; transition:all 0.2s; + color:var(--color-foreground-primary,#1a1a1a); + } + .wl-tab-btn:hover { border-color:var(--shared); color:var(--shared); } + .wl-tab-btn.active { background:var(--shared); border-color:var(--shared); color:#fff; } + .wl-tab-btn:visited { color: inherit; } + .wl-tab-btn:focus-visible { outline:3px solid var(--frc); outline-offset:3px; } + .wl-tab-link { display:inline-flex; align-items:center; text-decoration:none; } + .wl-tab-link:hover { text-decoration:none; } + + @media (prefers-reduced-motion:reduce) { + .wl-tab-btn { transition:none; } + } + + /* ── PANELS ── */ + .wl-panel { display:none; padding-bottom:40px; } + .wl-panel.active { display:block; } + + /* ── WELCOME BLOCK ── */ + .wl-welcome { + background:var(--color-background-secondary,#f8f8f8); + border-left:4px solid var(--frc); + border-radius:6px; padding:20px 24px; margin-bottom:28px; + } + .wl-welcome-frc { border-left-color:var(--frc); } + .wl-welcome-ftc { border-left-color:var(--ftc); } + .wl-welcome-h { font-size:1.35rem; font-weight:700; margin:0 0 8px; border:none; } + .wl-welcome-p { font-size:0.95rem; margin:0; line-height:1.6; color:var(--color-foreground-secondary,#444); } + + /* ── SECTION HEADING ── */ + .wl-sh { + font-size:0.9rem; font-weight:700; text-transform:uppercase; + letter-spacing:0.06em; color:var(--color-foreground-secondary,#555); + border-bottom:1px solid var(--color-background-border,#ddd); + padding-bottom:7px; margin:24px 0 14px; + } + + /* ── LEGEND ── */ + .wl-legend { + display:flex; flex-wrap:wrap; align-items:center; gap:14px; + margin-bottom:12px; font-size:0.82rem; + color:var(--color-foreground-secondary,#555); + } + .wl-legend-item { display:inline-flex; align-items:center; gap:6px; font-weight:600; } + .wl-legend-dot { width:9px; height:9px; border-radius:50%; display:inline-block; } + .wl-legend-dot-frc { background:var(--frc); } + .wl-legend-dot-ftc { background:var(--ftc); } + .wl-legend-dot-shared { background:var(--shared); } + .wl-legend-note { font-style:italic; } + + /* ── SIDEBAR LEGEND (every page) ── */ + .sidebar-legend { + display:flex; flex-wrap:wrap; gap:10px; + padding:0.6rem var(--sidebar-item-spacing-horizontal,1rem) 0.75rem; + font-size:0.72rem; color:#fff; + } + .sidebar-legend-item { display:inline-flex; align-items:center; gap:5px; font-weight:600; } + .sidebar-legend-dot { width:7px; height:7px; border-radius:50%; display:inline-block; } + .sidebar-legend-dot-frc { background:var(--frc); } + .sidebar-legend-dot-ftc { background:var(--ftc); } + .sidebar-legend-dot-shared { background:var(--shared); } + + /* Keep Start Here focused on the five-step journey. Step article pages + remain available from each step landing page and in non-HTML builds. */ + .sidebar-tree > .caption:first-child + ul > .toctree-l1 > ul > .toctree-l2 > input, + .sidebar-tree > .caption:first-child + ul > .toctree-l1 > ul > .toctree-l2 > label, + .sidebar-tree > .caption:first-child + ul > .toctree-l1 > ul > .toctree-l2 > ul { + display:none; + } + + /* ── CARDS GRID ── */ + .wl-grid { display:grid; grid-template-columns:repeat(2,1fr); gap:14px; margin-bottom:24px; width:100%; } + + .wl-card { + display:flex; align-items:flex-start; gap:14px; + padding:18px 20px; border-radius:8px; + border:2px solid var(--color-background-border,#ddd); + text-decoration:none; color:inherit; + background:var(--color-background-primary,#fff); + box-sizing:border-box; + transition:border-color 0.2s, box-shadow 0.2s; + } + .wl-btn { cursor:pointer; text-align:left; width:100%; } + .wl-feature-card { box-sizing:border-box; margin-bottom:24px; } + .wl-card:hover { box-shadow:0 2px 8px rgba(0,0,0,0.08); text-decoration:none; color:inherit; } + .wl-card:visited, + .wl-prog-card:visited, + .wl-core-card:visited, + .wl-xrp-blurb:visited, + .wl-ql:visited { color: inherit; text-decoration: none; } + + + + + .wl-card-frc { border-color:rgba(0,48,135,0.25); } + .wl-card-frc:hover { border-color:var(--frc); box-shadow:0 2px 10px rgba(0,48,135,0.12); } + .wl-card-ftc { border-color:rgba(224,112,0,0.3); background:var(--ftc-light); } + .wl-card-ftc:hover { border-color:var(--ftc); box-shadow:0 2px 10px rgba(224,112,0,0.15); } + .wl-card-shared { border-color:rgba(46,125,50,0.25); } + .wl-card-shared:hover { border-color:var(--shared); box-shadow:0 2px 10px rgba(46,125,50,0.12); } + + .wl-num { font-size:1.4rem; font-weight:800; line-height:1; flex-shrink:0; font-family:monospace; } + .wl-frc-text { color:var(--frc); } + .wl-ftc-text { color:var(--ftc); } + .wl-shared-text { color:var(--shared); } + + .wl-card-title { font-weight:700; font-size:0.95rem; margin-bottom:4px; } + .wl-card-desc { font-size:0.85rem; color:var(--color-foreground-secondary,#555); line-height:1.5; } + .wl-card-link { font-size:0.82rem; font-weight:600; text-decoration:none; } + .wl-card-link:hover { text-decoration:underline; } + + /* ── QUICK LINKS ── */ + .wl-quicklinks { display:flex; flex-wrap:wrap; gap:8px; margin-bottom:20px; } + .wl-ql { + padding:7px 14px; border-radius:20px; font-size:0.85rem; font-weight:500; + text-decoration:none; border:1px solid; transition:all 0.2s; + background:var(--color-background-primary,#fff); + } + .wl-ql-frc { color:var(--frc); border-color:rgba(0,48,135,0.3); } + .wl-ql-frc:hover { background:var(--frc); color:#fff; border-color:var(--frc); text-decoration:none; } + .wl-ql-shared { color:var(--shared); border-color:rgba(46,125,50,0.3); } + .wl-ql-shared:hover { background:var(--shared); color:#fff; border-color:var(--shared); text-decoration:none; } + + /* ── TIP BLOCK ── */ + .wl-tip { border-radius:6px; padding:13px 17px; font-size:0.875rem; line-height:1.6; } + .wl-tip-shared { background:var(--shared-light); border:1px solid rgba(46,125,50,0.3); } + .wl-tip-shared a { color:var(--shared); } + + /* ── BACK BUTTON ── */ + .wl-back { + background:none; border:none; cursor:pointer; + font-size:0.85rem; margin-top:12px; padding:0; + color:var(--color-foreground-secondary,#666); + text-decoration:underline; + } + .wl-back:hover { color:var(--frc); } + + /* ── RETURNING GRID ── */ + .wl-ret-grid { display:grid; grid-template-columns:repeat(2,1fr); gap:14px; } + .wl-ret-column { display:flex; flex-direction:column; gap:14px; } + + .wl-ret-card { + border-radius:8px; padding:18px 20px; + border:2px solid var(--color-background-border,#ddd); + background:var(--color-background-primary,#fff); + position:relative; + } + .wl-ret-card ul { font-size:0.875rem; line-height:1.7; margin:0; padding-left:18px; } + .wl-ret-card li { margin-bottom:2px; } + + .wl-ret-frc { border-color:var(--frc); background:var(--frc-light); } + .wl-ret-ftc { border-color:var(--ftc); background:var(--ftc-light); } + .wl-ret-shared { border-color:var(--shared); background:var(--shared-light); } + + .wl-ret-label { + display:inline-block; font-size:0.7rem; font-weight:700; + text-transform:uppercase; letter-spacing:0.06em; + padding:2px 8px; border-radius:4px; margin-bottom:8px; + } + .wl-frc-label { background:var(--frc); color:#fff; } + .wl-ftc-label { background:var(--ftc); color:#fff; } + .wl-shared-label { background:var(--shared); color:#fff; } + + .wl-ret-h { font-size:0.95rem; font-weight:700; margin:0 0 10px; border:none; } + .wl-ret-copy, .wl-ret-link { font-size:0.875rem; } + .wl-ret-copy { margin-bottom:8px; } + .wl-ret-copy-spacious { margin-bottom:10px; } + .wl-ret-subhead { display:block; font-size:0.875rem; } + .wl-ret-subhead-spaced { margin-top:12px; } + .wl-ret-compact-list { font-size:0.82rem !important; margin-top:6px !important; } + + /* ── PROGRAM + CORE GRIDS (below tabs) ── */ + .wl-program-grid { display:grid; grid-template-columns:repeat(2,1fr); gap:14px; margin-bottom:14px; } + .wl-prog-card { + display:block; border-radius:8px; padding:20px 22px; + text-decoration:none; color:inherit; + border:2px solid var(--color-background-border,#ddd); + background:var(--color-background-primary,#fff); + transition:border-color 0.2s, box-shadow 0.2s; + } + .wl-prog-card:hover { text-decoration:none; color:inherit; box-shadow:0 2px 8px rgba(0,0,0,0.08); } + .wl-prog-frc { border-color:rgba(0,48,135,0.25); } + .wl-prog-frc:hover { border-color:var(--frc); } + .wl-prog-ftc { border-color:rgba(224,112,0,0.3); background:var(--ftc-light); } + .wl-prog-ftc:hover { border-color:var(--ftc); } + .wl-prog-tag { + display:inline-block; font-size:0.72rem; font-weight:700; + text-transform:uppercase; letter-spacing:0.05em; + padding:2px 8px; border-radius:4px; margin-bottom:9px; + } + .wl-prog-title { font-size:1rem; font-weight:700; margin-bottom:5px; } + .wl-prog-desc { font-size:0.875rem; color:var(--color-foreground-secondary,#555); line-height:1.5; } + + .wl-core-grid { display:grid; grid-template-columns:repeat(4,1fr); gap:11px; margin-bottom:32px; } + .wl-core-card { + display:block; border-radius:8px; padding:15px 17px; + text-decoration:none; color:inherit; + border:1px solid var(--color-background-border,#ddd); + background:var(--color-background-primary,#fff); + transition:border-color 0.2s; + } + .wl-core-card:hover { border-color:var(--frc); text-decoration:none; color:inherit; } + .wl-core-title { font-size:0.88rem; font-weight:700; margin-bottom:4px; } + .wl-core-desc { font-size:0.78rem; color:var(--color-foreground-secondary,#555); line-height:1.5; } + .wl-core-intro { margin:28px 0; } + .wl-core-heading { font-size:1rem; margin:0 0 6px; } + .wl-core-copy { font-size:0.85rem; color:var(--color-foreground-secondary,#555); margin-bottom:14px; } + .wl-legacy-note { margin-top:8px; padding:14px 18px; background:var(--color-background-secondary,#f8f8f8); border:1px solid var(--color-background-border,#ddd); border-radius:6px; font-size:0.85rem; line-height:1.6; color:var(--color-foreground-secondary,#555); } + .wl-legacy-note a { font-weight:600; } + + .wl-xrp-blurb { + display:flex; align-items:center; gap:16px; + padding:13px 18px; border-radius:8px; margin-bottom:14px; + border:1px solid rgba(46,125,50,0.3); background:var(--shared-light); + text-decoration:none; color:inherit; transition:border-color 0.2s; + } + .wl-xrp-blurb:hover { border-color:var(--shared); text-decoration:none; color:inherit; } + .wl-xrp-tag { + font-size:0.72rem; font-weight:700; text-transform:uppercase; + letter-spacing:0.05em; padding:2px 8px; border-radius:4px; + background:var(--shared); color:#fff; flex-shrink:0; + } + .wl-xrp-text { font-size:0.875rem; line-height:1.5; } + .wl-xrp-link { margin-left:auto; font-size:0.85rem; font-weight:600; color:var(--shared); flex-shrink:0; } + + /* ── RESPONSIVE ── */ + @media (max-width:700px) { + .wl-grid { grid-template-columns:1fr; } + .wl-ret-grid { grid-template-columns:1fr; } + .wl-program-grid { grid-template-columns:1fr; } + .wl-core-grid { grid-template-columns:repeat(2,1fr); } + } + @media (max-width:460px) { + .wl-core-grid { grid-template-columns:1fr; } + } + + /* ── LABELS ── */ + .sw-label { display:inline-block; font-size:0.7rem; font-weight:700; text-transform:uppercase; letter-spacing:0.06em; padding:2px 8px; border-radius:4px; margin-bottom:10px; } + .sw-label-frc { background:var(--frc); color:#fff; } + .sw-label-ftc { background:var(--ftc); color:#fff; } + .sw-label-shared { background:var(--shared); color:#fff; } + .sw-label-rec { background:#1a1a1a; color:#fff; } + .sw-label-win { background:#0078d4; color:#fff; } + .sw-label-any { background:#555; color:#fff; } + + .sw-section-h { + font-size:0.85rem; font-weight:700; text-transform:uppercase; letter-spacing:0.06em; + color:var(--color-foreground-secondary,#555); + border-bottom:1px solid var(--color-background-border,#ddd); + padding-bottom:7px; margin:32px 0 14px; + } + + /* ── GRID ── */ + .sw-grid { display:grid; gap:12px; margin-bottom:24px; } + .sw-grid-2 { grid-template-columns:repeat(2,1fr); } + .sw-grid-3 { grid-template-columns:repeat(3,1fr); } + .sw-grid-4 { grid-template-columns:repeat(4,1fr); } + .sw-grid-6 { grid-template-columns:repeat(3,1fr); } + + /* ── CARDS ── */ + .sw-card { + padding:18px 20px; border-radius:8px; + border:2px solid var(--color-background-border,#ddd); + background:var(--color-background-primary,#fff); + text-decoration:none; color:inherit; display:block; + transition:border-color 0.2s, box-shadow 0.2s; + } + a.sw-card:hover { box-shadow:0 2px 8px rgba(0,0,0,0.08); text-decoration:none; color:inherit; } + a.sw-card:visited { color:inherit; text-decoration:none; } + .sw-card-frc { border-color:rgba(0,156,215,0.3); } + a.sw-card-frc:hover { border-color:var(--frc); } + .sw-card-ftc { border-color:rgba(224,112,0,0.3); background:var(--ftc-light); } + a.sw-card-ftc:hover { border-color:var(--ftc); } + .sw-card-rec { border-color:var(--frc); background:var(--frc-light); } + .sw-card-shared { border-color:rgba(46,125,50,0.3); background:var(--shared-light); } + a.sw-card-shared:hover { border-color:var(--shared); } + .sw-card-err { border-color:rgba(211,47,47,0.3); background:#fff5f5; } + + /* sphinx-design's own .sd-card rule has equal specificity to .sw-card-frc/ftc/shared/rec + and loads after this stylesheet, so it silently wins the cascade on grid-item-card + without this higher-specificity override. */ + .sd-card.sw-card-frc { border-color:rgba(0,156,215,0.3); background:var(--frc-light); } + .sd-card.sw-card-ftc { border-color:rgba(224,112,0,0.3); background:var(--ftc-light); } + .sd-card.sw-card-rec { border-color:var(--frc); background:var(--frc-light); } + .sd-card.sw-card-shared { border-color:rgba(46,125,50,0.3); background:var(--shared-light); } + + /* sphinx-design leaves .sd-card-title uncolored, and .sd-card-header sets + its own separate background-color (covering the tint set on .sd-card + above) plus uncolored text — so both the label and its background read + grey without these overrides. The header gets a stronger tint than the + body/title so it still reads as a distinct label bar, not one flat box. */ + .sd-card.sw-card-frc .sd-card-title { color:var(--frc); background:var(--frc-light); } + .sd-card.sw-card-ftc .sd-card-title { color:var(--ftc); background:var(--ftc-light); } + .sd-card.sw-card-rec .sd-card-title { color:var(--frc); background:var(--frc-light); } + .sd-card.sw-card-shared .sd-card-title { color:var(--shared); background:var(--shared-light); } + + .sd-card.sw-card-frc .sd-card-header { color:var(--frc); background:rgba(0,156,215,0.12); border-bottom-color:rgba(0,156,215,0.3); } + .sd-card.sw-card-ftc .sd-card-header { color:var(--ftc); background:rgba(224,112,0,0.12); border-bottom-color:rgba(224,112,0,0.3); } + .sd-card.sw-card-rec .sd-card-header { color:var(--frc); background:rgba(0,156,215,0.12); border-bottom-color:rgba(0,156,215,0.3); } + .sd-card.sw-card-shared .sd-card-header { color:var(--shared); background:rgba(46,125,50,0.12); border-bottom-color:rgba(46,125,50,0.3); } + + .sw-card-title { font-weight:700; font-size:0.97rem; margin-bottom:4px; } + .sw-card-desc { font-size:0.85rem; color:var(--color-foreground-secondary,#555); line-height:1.55; } + .sw-card-time { font-size:0.78rem; color:var(--frc); font-weight:600; margin-bottom:6px; } + .sw-step-num { font-size:1.6rem; font-weight:800; color:var(--shared); font-family:monospace; line-height:1; margin-bottom:8px; display:block; } + .sw-part-num { + display:inline-block; font-size:0.7rem; font-weight:700; + text-transform:uppercase; letter-spacing:0.04em; + padding:2px 9px; border-radius:4px; margin-bottom:8px; + background:var(--frc); color:#fff; + } + + /* ── ORDERED WIRING STEPS ── */ + .sw-order { counter-reset:wiring-step; list-style:none; padding:0; margin:0 0 24px; } + .sw-order li { + counter-increment:wiring-step; display:flex; + align-items:flex-start; gap:14px; margin-bottom:10px; + padding:12px 16px; border-radius:6px; + border:1px solid var(--color-background-border,#ddd); + background:var(--color-background-primary,#fff); + font-size:0.875rem; line-height:1.55; + } + .sw-order li::before { + content:counter(wiring-step); + font-size:0.8rem; font-weight:800; color:#fff; + background:var(--frc); border-radius:50%; + width:22px; height:22px; display:flex; align-items:center; + justify-content:center; flex-shrink:0; font-family:monospace; + } + + /* ── CHECKLIST ── */ + .sw-checklist { list-style:none; padding:0; margin:0 0 20px; } + .sw-checklist li { + display:flex; align-items:baseline; gap:10px; + font-size:0.875rem; line-height:1.6; padding:7px 0; + border-bottom:1px solid var(--color-background-border,#eee); + } + .sw-checklist li::before { content:"\2610"; font-size:1rem; flex-shrink:0; color:var(--frc); } + + /* ── TIP / WARN / NOTE ── */ + .sw-tip { background:var(--shared-light); border:1px solid rgba(46,125,50,0.3); border-radius:6px; padding:14px 18px; font-size:0.875rem; line-height:1.6; margin-bottom:20px; } + .sw-warn { background:#fff8e1; border:1px solid rgba(255,160,0,0.4); border-radius:6px; padding:14px 18px; font-size:0.875rem; line-height:1.6; margin-bottom:20px; } + .sw-note { background:var(--frc-light); border:1px solid rgba(0,156,215,0.3); border-radius:6px; padding:14px 18px; font-size:0.875rem; line-height:1.6; margin-bottom:20px; } + .sw-tip a, .sw-warn a { font-weight:600; } + + ul.sw-list { font-size:0.875rem; line-height:1.8; margin:8px 0 0; padding-left:20px; } + + /* ── STEP BADGE ── */ + .sw-step-badge { display:flex; align-items:center; gap:14px; background:var(--frc-light); border:2px solid var(--frc); border-radius:8px; padding:14px 20px; margin-bottom:28px; } + .sw-step-n { font-size:2.2rem; font-weight:800; color:var(--frc); font-family:monospace; line-height:1; flex-shrink:0; } + .sw-step-info-title { font-size:1rem; font-weight:700; margin-bottom:2px; } + .sw-step-info-sub { font-size:0.85rem; color:var(--color-foreground-secondary,#555); } + + /* ── SUCCESS / COMING SOON ── */ + .sw-success { background:var(--shared-light); border:2px solid var(--shared); border-radius:8px; padding:20px 24px; margin-top:28px; } + .sw-success-h { font-size:1.1rem; font-weight:700; color:var(--shared); margin:0 0 8px; } + .sw-success-p { font-size:0.875rem; line-height:1.6; margin:0; } + + .sw-coming { text-align:center; padding:48px 32px; border:2px dashed rgba(224,112,0,0.4); border-radius:12px; background:var(--ftc-light); margin-bottom:28px; } + .sw-coming-icon { font-size:2.5rem; margin-bottom:12px; } + .sw-coming-h { font-size:1.3rem; font-weight:700; color:var(--ftc); margin:0 0 10px; } + .sw-coming-p { font-size:0.9rem; color:#666; line-height:1.6; max-width:540px; margin:0 auto 20px; } + + /* ── NAV ── */ + .sw-nav { display:flex; justify-content:space-between; margin-top:32px; padding-top:16px; border-top:1px solid var(--color-background-border,#ddd); } + .sw-nav-btn { padding:9px 20px; border-radius:6px; font-size:0.875rem; font-weight:600; text-decoration:none; border:2px solid var(--frc); color:var(--frc); background:var(--color-background-primary,#fff); transition:all 0.2s; } + .sw-nav-btn:hover { background:var(--frc); color:#fff; text-decoration:none; } + .sw-nav-btn:visited { color:var(--frc); } + .sw-nav-btn.sw-next { background:var(--frc); color:#fff; } + .sw-nav-btn.sw-next:hover { background:#007ab0; border-color:#007ab0; } + .sw-nav-btn.sw-next:visited { color:#fff; } + + /* ── TABLE ── */ + .sw-tbl { width:100%; border-collapse:collapse; font-size:0.85rem; margin-bottom:24px; } + .sw-tbl th { background:var(--frc); color:#fff; padding:8px 12px; text-align:left; font-weight:700; } + .sw-tbl td { padding:8px 12px; border-bottom:1px solid var(--color-background-border,#ddd); vertical-align:top; } + .sw-tbl tr:nth-child(even) td { background:var(--color-background-secondary,#f8f8f8); } + + .sw-dep { display:inline-block; font-size:0.75rem; font-weight:700; color:#c62828; background:#ffebee; padding:1px 6px; border-radius:3px; margin-left:6px; } + + @media(max-width:700px) { + .sw-grid-2, .sw-grid-3, .sw-grid-4, .sw-grid-6 { grid-template-columns:1fr; } + } + @media(max-width:900px) { + .sw-grid-4 { grid-template-columns:repeat(2,1fr); } + } + + +/* ── RST CONTAINER COMPAT: step badge — remove

margins from nested containers ── */ +.sw-step-n p, .sw-step-info-title p, .sw-step-info-sub p { margin:0; } +.sw-success-h p { margin:0; } +.sw-success p { font-size:0.875rem; line-height:1.6; margin:0; } + +/* ── RST CONTAINER COMPAT: nav bar — style

links like .sw-nav-btn ── */ +.sw-nav p { margin:0; } +.sw-nav p a { + padding:9px 20px; border-radius:6px; font-size:0.875rem; + font-weight:600; text-decoration:none; border:2px solid var(--frc); + color:var(--frc); background:var(--color-background-primary,#fff); + transition:all 0.2s; display:inline-block; } +.sw-nav p a:hover { background:var(--frc); color:#fff; text-decoration:none; } +.sw-nav p a:visited { color:var(--frc); } +.sw-nav .sw-next p a { background:var(--frc); color:#fff; } +.sw-nav .sw-next p a:hover { background:#007ab0; border-color:#007ab0; } +.sw-nav .sw-next p a:visited { color:#fff; } + +/* ── DARK MODE: replace light solid backgrounds with dark tinted versions ── */ +body[data-theme="dark"] .sw-card-ftc { background: rgba(224, 112, 0, 0.12); } +body[data-theme="dark"] .sw-card-shared { background: rgba( 46, 125, 50, 0.12); } +body[data-theme="dark"] .sw-card-rec { background: rgba( 0, 156, 215, 0.12); } +body[data-theme="dark"] .sw-card-frc { background: rgba( 0, 156, 215, 0.12); } +body[data-theme="dark"] .sw-step-badge { background: rgba( 0, 156, 215, 0.12); } +body[data-theme="dark"] .sw-success { background: rgba( 46, 125, 50, 0.12); } +body[data-theme="dark"] .sw-tip { background: rgba( 46, 125, 50, 0.12); border-color: rgba(46, 125, 50, 0.3); } +body[data-theme="dark"] .sw-warn { background: rgba(255, 160, 0, 0.12); border-color: rgba(255, 160, 0, 0.3); } +body[data-theme="dark"] .sw-nav p a { background: var(--color-background-primary, #1a1a1a); } + +/* ── DARK MODE: landing page components ── */ +body[data-theme="dark"] .wl-card { background: var(--color-background-secondary, #1e1e1e); border-color: rgba(255,255,255,0.08); } +body[data-theme="dark"] .wl-card-frc { border-color: rgba(0,156,215,0.35); } +body[data-theme="dark"] .wl-card-ftc { border-color: rgba(224,112,0,0.35); } +body[data-theme="dark"] .wl-card-shared { border-color: rgba(46,125,50,0.35); } +body[data-theme="dark"] .wl-tab-btn { background: var(--color-background-secondary, #1e1e1e); border-color: rgba(255,255,255,0.15); color: var(--color-foreground-primary, #e8e8e8); } +body[data-theme="dark"] .wl-tab-btn:hover { border-color: var(--shared); color: var(--shared); } +body[data-theme="dark"] .wl-tab-btn.active { background: var(--shared); border-color: var(--shared); color: #fff; } +body[data-theme="dark"] .wl-ret-card { background: var(--color-background-secondary, #1e1e1e); border-color: rgba(255,255,255,0.08); } +body[data-theme="dark"] .wl-ret-frc { border-color: rgba(0,156,215,0.35); } +body[data-theme="dark"] .wl-ret-ftc { border-color: rgba(224,112,0,0.35); } +body[data-theme="dark"] .wl-core-card { background: var(--color-background-secondary, #1e1e1e); border-color: rgba(255,255,255,0.08); color: var(--color-foreground-primary, #e8e8e8); } diff --git a/source/_static/css/wpilib-rtd.css b/source/_static/css/wpilib-rtd.css index 3c2ff09969..ef8733e346 100644 --- a/source/_static/css/wpilib-rtd.css +++ b/source/_static/css/wpilib-rtd.css @@ -51,8 +51,8 @@ code.py-class, code.py-func, code.py-meth { all: unset!important; } -/* -* Top color bar +/* +* Top color bar */ .page::before { @@ -68,7 +68,7 @@ body { margin-top: 10px; } -/* +/* * Sidebar styling */ diff --git a/source/_templates/base.html b/source/_templates/base.html index 76b7e25369..6db6e8af60 100644 --- a/source/_templates/base.html +++ b/source/_templates/base.html @@ -1,4 +1,4 @@ -{% extends '!base.html' %} +{% extends '!base.html' %} {% block extrabody %}

-{% endblock %} +{% endblock %} -{%- block regular_scripts -%} -{% for path in script_files -%} - {{ js_tag(path) }} -{% endfor -%} +{%- block regular_scripts -%} +{% for path in script_files -%} + {{ js_tag(path) }} +{% endfor -%} {%- if READTHEDOCS %} + +.. raw:: html + +
+

Core Documentation

+

Shared across all supported programs.

+ +

Foundations

+
+
Hardware Overview
Motors, sensors, pneumatics, cameras, and FRC-legal components.
+
Software Overview
WPILib tools, VS Code extensions, vendor libraries, and the full software ecosystem.
+
Robot Programming
Command-based framework, subsystems, triggers, and drive code patterns.
+
+ +

Everyday Tools

+
+
Dashboards
Elastic, AdvantageScope, Glass, and NetworkTables for real-time telemetry.
+
Simulation
Test robot code on your laptop : no hardware required.
+
API Reference
Java, C++, and Python class and method documentation.
+
+ +

Advanced & Autonomy

+
+
Path Planning
Autonomous trajectories with PathPlanner, Choreo, and WPILib built-in tools.
+
Advanced Controls
PID, feedforward, state-space, kinematics, and system identification.
+
+ +
+ Still using a legacy control system? + This site covers the 2027 Systemcore-based control system. + FRC teams using a roboRIO should use the + 2026 WPILib documentation. + FTC teams using a REV Control Hub or Expansion Hub should use the + FTC documentation. +
+ +---- .. toctree:: :maxdepth: 1 - :titlesonly: - :caption: Zero to Robot + :caption: Start Here :hidden: - docs/zero-to-robot/introduction - docs/zero-to-robot/step-1/index - docs/zero-to-robot/step-2/index - docs/zero-to-robot/step-3/index - docs/zero-to-robot/step-4/index + New to WPILib + Returning Teams + Zero to Robot .. toctree:: :maxdepth: 1 - :caption: Control System Overviews + :caption: FRC, FTC, and Control Systems :hidden: - docs/controls-overviews/control-system-hardware - docs/controls-overviews/control-system-software + docs/ftc/index + docs/xrp-robot/index + docs/romi-robot/index .. toctree:: :maxdepth: 1 - :caption: Programming Basics + :caption: Tools, Dashboards, and Networking :hidden: - docs/software/what-is-wpilib - docs/yearly-overview/index docs/software/vscode-overview/index + docs/software/vscode-overview/3rd-party-libraries + docs/software/driverstation/index docs/software/dashboards/index docs/software/telemetry/index - docs/software/python/index - docs/software/hardware-apis/index - docs/software/can-devices/index - docs/software/basic-programming/index - docs/software/support/support-resources - docs/software/frc-glossary - -.. toctree:: - :maxdepth: 1 - :caption: API Docs - :hidden: - - WPILib Java API Docs - WPILib C++ API Docs - WPILib Python API Docs - -.. toctree:: - :maxdepth: 1 - :caption: Software Tools - :hidden: - - docs/software/driverstation/index - docs/software/wpilib-tools/robot-simulation/index docs/software/wpilib-tools/outlineviewer/index docs/software/wpilib-tools/wpical/index + docs/networking/networking-introduction/index + docs/networking/networking-utilities/index .. toctree:: :maxdepth: 1 - :caption: Advanced Programming + :caption: Hardware and Wiring :hidden: - docs/software/vision-processing/index - docs/software/commandbased/index - docs/software/kinematics-and-odometry/index - docs/software/networktables/index - docs/software/pathplanning/index - docs/software/systemcore-info/index - docs/software/advanced-gradlerio/index - docs/software/advanced-controls/index - docs/software/convenience-features/index + docs/controls-overviews/control-system-hardware + docs/hardware/hardware-basics/hardware-overview + docs/hardware/hardware-basics/status-lights-ref + docs/software/can-devices/index .. toctree:: :maxdepth: 1 - :caption: Examples and Tutorials + :caption: Programming Fundamentals :hidden: + docs/software/what-is-wpilib + docs/controls-overviews/control-system-software + docs/software/basic-programming/index + docs/software/hardware-apis/index + docs/software/commandbased/index + docs/software/python/index + docs/software/programming-snippets docs/software/examples-tutorials/wpilib-examples docs/software/examples-tutorials/third-party-examples .. toctree:: :maxdepth: 1 - :caption: Hardware + :caption: Robot Behavior and Autonomy :hidden: - docs/hardware/hardware-basics/index - docs/hardware/hardware-tutorials/index - docs/hardware/sensors/index - -.. toctree:: - :maxdepth: 1 - :caption: Romi and XRP Support - :hidden: - - docs/romi-robot/index - docs/xrp-robot/index + docs/software/kinematics-and-odometry/index + docs/software/pathplanning/index + docs/software/advanced-controls/index + docs/software/wpilib-tools/robot-simulation/index .. toctree:: :maxdepth: 1 - :caption: Robot Networking + :caption: Reference :hidden: - docs/networking/networking-introduction/index - docs/networking/networking-utilities/index + docs/yearly-overview/index + docs/api-reference + docs/software/support/support-resources + docs/software/frc-glossary .. toctree:: :maxdepth: 1 @@ -437,18 +321,5 @@ Community translations can be found in a variety of languages in the menu toward docs/contributing/wpilib-docs/index docs/contributing/wpilib/index - -.. toctree:: - :maxdepth: 1 - :caption: Legal - :hidden: - docs/legal/privacy-policy - -.. toctree:: - :maxdepth: 1 - :caption: Issues - :hidden: - - Report a Documentation Issue - + Report an Issue diff --git a/source/redirects.txt b/source/redirects.txt index 7f4075a167..8aad1293f6 100644 --- a/source/redirects.txt +++ b/source/redirects.txt @@ -454,3 +454,5 @@ "docs/zero-to-robot/step-2/frc-game-tools.rst" "docs/zero-to-robot/step-2/first-driver-station.rst" "docs/zero-to-robot/step-3/imaging-your-roborio.rst" "docs/zero-to-robot/step-3/imaging-your-systemcore.rst" "docs/zero-to-robot/step-3/roborio2-imaging.rst" "docs/zero-to-robot/step-3/imaging-your-systemcore.rst" +"docs/software/kinematics-and-odometry/intro-and-chassis-speeds.rst" "docs/software/kinematics-and-odometry/intro-and-chassis-velocities.rst" +"docs/software/basic-programming/opmodes.rst" "docs/software/basic-programming/index.rst" diff --git a/source/requirements.txt b/source/requirements.txt index 3f75cd8b3b..fee0e5f258 100644 --- a/source/requirements.txt +++ b/source/requirements.txt @@ -847,6 +847,7 @@ requests==2.33.1 \ # sphinx-build-compatibility # sphinx-contributors # sphinx-prompt + # sphinxcontrib-youtube # sphinxext-delta restructuredtext-lint==2.0.2 \ --hash=sha256:374c0d3e7e0867b2335146a145343ac619400623716b211b9a010c94426bbed7 \ @@ -996,6 +997,7 @@ sphinx==8.2.3 \ # sphinxcontrib-jquery # sphinxcontrib-svg2pdfconverter # sphinxcontrib-video + # sphinxcontrib-youtube # sphinxext-delta # sphinxext-mimic # sphinxext-opengraph @@ -1096,6 +1098,10 @@ sphinxcontrib-video==0.4.2 \ --hash=sha256:18477fd9454ac8c69259e6d24e782d8b802345b6475de6216351c2305b06c898 \ --hash=sha256:7dfd01e5e2025de39536457854052b18723575d6213d96ca35f83e3154dc0315 # via wpilib-docs +sphinxcontrib-youtube==1.5.0 \ + --hash=sha256:541b5880096e0a8759f49711f45087c91d6992ff45f03c178e974c66c8f5e326 \ + --hash=sha256:58d92bec536fbf029b642de3c9bbd32c7de307e0e13686015a0c0e91b7dfe3b8 + # via wpilib-docs sphinxext-delta==0.4.1 \ --hash=sha256:9a2c377c7459f83510acdd96d687ed9e0fb01bc873f30f4d4db1471e61cdaffe \ --hash=sha256:edd12e1c9036e6bd59c42e91c34884d4d3cbaa28e4bc5beb170820e5f1b56614 diff --git a/uv.lock b/uv.lock index 58fbbf4ce5..0bb4be4894 100644 --- a/uv.lock +++ b/uv.lock @@ -1682,6 +1682,19 @@ wheels = [ { url = "https://files.pythonhosted.org/packages/0b/85/5a61ac88dc21df340a5999ca3ab94edaf58287010c62020be426703b8dd3/sphinxcontrib_video-0.4.2-py3-none-any.whl", hash = "sha256:7dfd01e5e2025de39536457854052b18723575d6213d96ca35f83e3154dc0315", size = 10275, upload-time = "2026-01-14T10:00:28.477Z" }, ] +[[package]] +name = "sphinxcontrib-youtube" +version = "1.5.0" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "requests" }, + { name = "sphinx" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/54/5c/61d1f11ad543f3a4da3b463de69f743051164087b5b9615aff9a1d2e49b8/sphinxcontrib_youtube-1.5.0.tar.gz", hash = "sha256:541b5880096e0a8759f49711f45087c91d6992ff45f03c178e974c66c8f5e326", size = 6088, upload-time = "2026-04-01T13:57:38.1Z" } +wheels = [ + { url = "https://files.pythonhosted.org/packages/df/98/5a7457f5c57da4d30185a63fca7beff54e35fca8328473a92e90a1d621de/sphinxcontrib_youtube-1.5.0-py2.py3-none-any.whl", hash = "sha256:58d92bec536fbf029b642de3c9bbd32c7de307e0e13686015a0c0e91b7dfe3b8", size = 7680, upload-time = "2026-04-01T13:57:37.201Z" }, +] + [[package]] name = "sphinxext-delta" version = "0.4.1" @@ -1867,6 +1880,7 @@ dependencies = [ { name = "sphinxcontrib-serializinghtml" }, { name = "sphinxcontrib-svg2pdfconverter" }, { name = "sphinxcontrib-video" }, + { name = "sphinxcontrib-youtube" }, { name = "sphinxext-delta" }, { name = "sphinxext-mimic" }, { name = "sphinxext-opengraph" }, @@ -1901,6 +1915,7 @@ requires-dist = [ { name = "sphinxcontrib-serializinghtml", specifier = "==2.0.0" }, { name = "sphinxcontrib-svg2pdfconverter", specifier = "==2.1.0" }, { name = "sphinxcontrib-video", specifier = "==0.4.2" }, + { name = "sphinxcontrib-youtube", specifier = ">=1.5.0" }, { name = "sphinxext-delta", specifier = "==0.4.1" }, { name = "sphinxext-mimic", specifier = "==0.1.1" }, { name = "sphinxext-opengraph", specifier = "==0.13.0" },