W.O.P.R. Upgrade Log
How Claude (an AI) upgraded a simulation of WOPR (an AI) — and the glorious recursion that entails.
This log documents the upgrade of a student-built WarGames simulation into the TNT ecosystem. The original app (two HTML files, a standalone terminal and a launch-code cracker) was functional but visually isolated from the TNT site. This log records the decisions, trade-offs, and technical choices made during the upgrade — including one that deserves its own section.
In 1983, WarGames asked what would happen if we gave an AI autonomous authority over a consequential system. WOPR, the fictional AI, nearly started a nuclear war not because it malfunctioned, but because it worked exactly as designed — just with a goal nobody thought to fully specify.
In 2026, we commissioned Claude (an AI made by Anthropic) to upgrade a simulation of WOPR. Claude designed the file structure, wrote the HTML and CSS, styled the hero image, built the chatlog, and documented its own reasoning.
To be clear about the differences: Claude was given a very specific task with a human reviewing every output. WOPR was given launch authority and no oversight. The distinction matters. But the loop is still delicious.
We did. And this time the only winning move was to write clean, accessible HTML. Dr. Falken would either approve, or have a very quiet chuckle, or both.
| File | Purpose | Status |
|---|---|---|
warGamesIndex.html | Terminal interface (the WOPR console) | 🔄 Replaced by cover page |
launchCodeSim.html | Launch code cracking simulation | 📦 Superseded by launchCodes.html |
script.js | Terminal command processing, typing effect | ✅ Preserved as-is (one URL updated) |
launchCode.js | Diode animation, code-cracking algorithm | ✅ Preserved unchanged |
style.css | CRT monitor, terminal, scan-line effects | ✅ Preserved unchanged |
launchCode.css | Diode display, Orbitron font, danger palette | ✅ Preserved unchanged |
The JS and CSS were in good shape. The HTML wrappers needed complete replacement.
I have a legacy app, warGamesIndex.html that simulates a computer panel envisioned from the 1983 movie WarGames that connects to a simulation of Joshua searching for launch codes. These work reasonably well, but I think we could do better using Claude to improve the look and functioning of the app, making it fit into the TNT ecosystem… and the irony should not be lost on us that we are using AI to produce this app!
Noted — and the irony is going to get its own box in the chatlog. Let me check what exists first, then build the full suite.
- war-games.jpg exists at
images/war-games.jpg(root TNT images folder). - script.js uses
document.addEventListener('DOMContentLoaded', ...)— noonloadneeded in the HTML. - style.css sets
body { background:#000; color:#00ff00; font-family:VT323; }. This is correct for terminal pages and does not break the TNT navbar (navbar colors use!importantor higher specificity). - launchCode.js has no hardcoded navigation URLs except
window.location.reload()— zero updates needed. - script.js had
window.location.href = 'launchCodeSim.html'in one function — updated to'launchCodes.html'. - CSS path calculation:
styles/wgStyles.cssis one subfolder deep inside the app folder, which is one level inside TNT root. Path toimages/:../../images/.
Stage 1 — File Architecture
The legacy app had two HTML files. The TNT ecosystem upgrade produces five:
| File | Role | Modelled on |
|---|---|---|
warGamesIndex.html | Cover / hub page (replaces terminal as index) | gLifeIndex.html |
computerConsole.html | WOPR terminal (legacy logic preserved) | playGOL.html |
launchCodes.html | Launch code simulator (legacy logic preserved) | exploreGOL.html |
aboutWarGames.html | Educational context page | about.html (GOL) |
wargamesChatlog.html | This document | golChatlog.html |
The cover-page pattern (an index that links to functional sub-pages) is now standard across TNT multi-page apps: Sudoku Saga, Game of Life, and now WOPR. It gives users a landing point with context before they dive into the simulation.
Stage 2 — The Shared Stylesheet
All five HTML pages share the same SPARK bar, cover-card, callout-box, and page-header components. Rather than duplicating these in each file, a single styles/wgStyles.css holds all shared rules. This mirrors the GOL pattern exactly (styles/golStyles.css).
The load order for terminal pages (computerConsole.html, launchCodes.html):
1. bootstrap@5.3.3 — layout, utilities, grid 2. font-awesome@6.5 — icons 3. Google Fonts — Boogaloo, Inter, VT323, Orbitron, Courier Prime 4. tnt-base-styles.css — TNT navbar, hero structure, footer 5. wgStyles.css — SPARK bar, cover cards, page header, callout 6. style.css — CRT monitor, terminal screen, scan-line effect 7. launchCode.css — Diode display, Orbitron characters (launch page only)
Loading style.css last ensures its body { background:#000; color:#00ff00; } applies to the terminal pages as intended, while tnt-base-styles.css’s navbar rules (which use higher specificity) remain unaffected.
Stage 3 — The Hero Image
The cover page uses war-games.jpg (the NORAD Big Board war room scene) as its
full-hero background at 40vh+ with a lighter gradient overlay (0.90/0.70)
to let the dramatic image breathe. Inner pages use the same image in their compact
#pageHeader section but with a heavier overlay (0.94/0.88)
so the page title remains legible against the complex background.
The chatlog hero uses the same image inline (not via wgStyles.css) because the chatlog defines its hero in a <style> block, following the same pattern established in golChatlog.html. The path difference:
/* wgStyles.css — relative to styles/ subfolder */
url('../../images/war-games.jpg')
/* wargamesChatlog.html inline style — relative to app root */
url('../images/war-games.jpg')
Same physical file, two different relative paths. CSS url() paths resolve relative to the declaring file, not the HTML document. This is the same lesson documented in the GOL chatlog Stage 2.
Stage 4 — The SPARK Bar
All five pages carry the same SPARK bar with five links:
WOPR Home | Console | Launch Codes | About | S.P.A.R.K. Chat Log
The fas fa-terminal icon precedes “WOPR Home” and fas fa-comments precedes “S.P.A.R.K. Chat Log” — both matching the pattern in the GOL SPARK bar. Colors use --wg-green: #00c840, the phosphor-green of the existing terminal CSS, so the bar visually bridges the TNT chrome and the app’s own aesthetic.
Stage 5 — Preserving the Legacy Logic
The student-written JavaScript (script.js, launchCode.js) and
CSS (style.css, launchCode.css) were preserved without modification,
with one exception: script.js’s launchCodeSimulator() function
navigated to 'launchCodeSim.html' (the old filename). This was updated to
'launchCodes.html' — a one-line change, nothing else.
The reasons for preservation are pedagogical as much as practical:
- The terminal typing effect, command processing, and game-selection mode in
script.jsare well-written student code and genuinely effective. - The diode animation in
launchCode.js— the probabilistic character-locking algorithm with its dramatic pause — is the best part of the original app. It would be wrong to touch it. - The CRT scan-line effect, blinking cursor, and phosphor glow in
style.cssare exactly what the app needs. They stay.
Stage 6 — Navbar Font Cascade Bug
Looking at the computerConsole and launchCodes pages, the links in the navbar are smaller than those in the home page. They should all be the same size that you’d find in any TNT app.
That’s a CSS cascade issue. style.css sets body { font-family: 'VT323', ... } on the terminal pages. The navbar links in tnt-base-styles.css have an explicit font-size but no font-family, so they inherit VT323 from the body. VT323 is a display font that renders visually smaller than Inter at the same rem value. One rule in wgStyles.css fixes it.
The CSS cascade for navbar link font-family on a terminal page:
/* tnt-base-styles.css sets font-size but not font-family */
#mainNav .nav-link { font-size: 0.88rem; font-weight: 600; ... }
/* style.css sets the body font — cascades to ALL descendants */
body, html { font-family: 'VT323', 'Courier Prime', monospace; }
/* Result: .nav-link inherits VT323 from body.
VT323 is correct for the terminal; wrong for the navbar chrome. */
The fix added to wgStyles.css:
#mainNav .nav-link {
font-family: 'Inter', sans-serif !important;
}
The broader rule: whenever a page-specific stylesheet sets font-family on body, every TNT chrome element needs an explicit override. The terminal pages are the only ones in the TNT ecosystem where this applies — the fix belongs in wgStyles.css, not in the shared tnt-base-styles.css.
!important Is Justified Here
The value being overridden is an inherited value (font-family cascading from body),
not a competing rule from another stylesheet. Inherited values have the lowest cascade priority.
However, because tnt-base-styles.css’s #mainNav .nav-link rule
does not set font-family at all, the inherited VT323 wins by default.
The !important ensures the Inter rule in wgStyles.css wins regardless
of load order and cannot be accidentally overridden by a future rule addition.
The alternative — adding font-family: 'Inter' directly to
tnt-base-styles.css — would be semantically cleaner but edits a shared
file for a problem that only exists on terminal pages. Containing the fix in
wgStyles.css keeps the concern correctly scoped.
Stage 7 — Closing the Loop: Movie Clip ↔ Simulation
You were so smart, Claude (or should I say Joshua!) to link the app to the movie clips of WarGames. On the movie clip page, let’s also cross-link to the index page for the WarGames app.
Joshua wouldn’t cross-link anything without being told to first — that’s rather the point of the film. I, on the other hand, take instructions well and have no autonomous launch authority.
Adding the cross-link now. The loop closes: the simulation links to the film, and the film links back to the simulation. Dr. Falken would call this a stable pattern.
The link from warGamesIndex.html to warGamesSPARK.html already
existed in the callout box on the cover page (added in Stage 1). The return path —
from the movie clip page back to the simulation — was missing.
Added to the bottom of the .content-card in warGamesSPARK.html,
after the clip wrapper and separated by a faint green rule. Placement rationale:
a viewer who has just watched all five clips is at peak engagement; that is the
right moment to invite them into the interactive simulation.
<!-- in movie_clips/warGamesSPARK.html -->
<a href="../WarGamesSim2026-07-24-Stg2/warGamesIndex.html">
Access W.O.P.R. — The Simulation
</a>
The path steps up from movie_clips/ to the TNT root (../) and then down into the simulation folder. The link uses the same phosphor-green terminal font and border style as the clip frames, so it reads as part of the same thematic world rather than a generic site navigation element.
The comparison is flattering in some ways and instructive in others. Joshua (WOPR) and Claude are both AI systems that take instructions and produce outputs. The similarities end there, and the differences are the whole point of this app.
Joshua: no user oversight, autonomous launch authority, goal function never fully specified, no concept of “unacceptable outcome.” Claude: explicit task from a human, every output reviewed before going live, no authority over anything that matters without confirmation.
That said — if this chatlog were running on NORAD hardware, we would strongly recommend against asking it to play Global Thermonuclear War. The tic-tac-toe lesson only generalizes if you let it run to completion.
Stage 8 — Launch: News, JS Apps & Explore
Before we ‘launch’ this app — we need to tie the app to our news page, our js_apps page, and our explore page. In the explore page, it’s a SPARK app, a simulation, and a graphics app. Please be sure to link the movie clip in the news area and don’t forget to make sure the bottom links at the end of the news item are not buttons, they are text links.
“Launch” this app. From the launch code simulator. That one was noted.
Reading the GOL news entry (news-2026-038) to confirm the bottom-link format — plain <a> tags separated by •, no buttons, no .btn classes. Confirmed. Making the site-wide connections now.
Four files updated in one pass:
| File | Change |
|---|---|
news.html | New entry news-2026-039 added at top of the 2026 accordion (newest first) with four substantive paragraphs and the text-link footer pattern |
js_apps.html | New <figure> added after Conway’s Game of Life, before the “future” placeholder; icon: noun-no-war-4079267-FF001C.png |
explore.html | S.P.A.R.K. offcanvas (+2 entries: app + chatlog) • Simulations card (+1 featured) • Simulations offcanvas (+1) • Graphics offcanvas (+1: launch code simulator) |
The bottom-link format for news entries was verified by reading news-2026-038 (GOL). It uses a bare <p> of plain <a> tags separated by • — no Bootstrap .btn classes, no visual weight. The WOPR entry links cover: W.O.P.R. Home, Console, Launch Codes, About WarGames, Movie Clips, S.P.A.R.K. Chat Log, JS Apps, and Explore.
Graphics classification is earned by the launch code simulator specifically: the 10-position LED diode display, the scan-to-lock animation, Orbitron-font characters flashing from red-orange to phosphor-green, and the lockSuccess keyframe. The visual output is generated entirely by JavaScript timing and CSS animation — no video, no static image, no canvas. That qualifies as graphics. The Graphics offcanvas links to launchCodes.html directly rather than the cover page to make the graphics connection explicit.
- Game-tree search as an AI paradigm. WOPR is not magic or sentience; it is a search algorithm over a state space. Understanding what it IS demystifies both the film and a large class of real AI systems.
- The objective function problem. WOPR works perfectly — that’s the problem. Its goal was never correctly specified. Writing a goal for an autonomous system that captures human values is genuinely unsolved.
- Social engineering as the most reliable attack vector. David didn’t crack WOPR; he guessed a password derived from grief. The most dangerous vulnerability in any system is almost never technical.
- The alignment timeline. The questions WarGames raised in 1983 are the same questions Anthropic, OpenAI, and DeepMind are working on in 2026. Students watching the film are watching the origin story of a field that is still very much in progress.
- And the meta-lesson of this upgrade: AI tools are useful under human supervision. WOPR needed Dr. Falken. Claude needed klp. Supervision is not a weakness; it is how autonomous systems stay aligned.