Lecture 04

Graphics & Sound

The Apple II draws pictures by letting the video circuit read the same RAM your program writes — and makes sound with a speaker wired to a single bit. Both systems are full of Wozniak's cost-saving tricks, and both are places where the machine's soul lives.

1. Three display modes

ModeResolutionColorsMemoryBASIC command
Text40 × 24 characters1 (green/white)$0400–$07FF (1K)TEXT
Lo-res40 × 48 blocks16same 1K as text!GR
Hi-res280 × 192 pixels6$2000–$3FFF (8K)HGR

Lo-res and text share the same memory: a lo-res "pixel" is just half a character cell, with the byte's low nibble coloring the top block and the high nibble the bottom block. That's why GR costs no extra memory — it's a different way of displaying the same kilobyte.

2. The text screen and Woz's weird interleave

You'd expect row 0 of the screen at $0400, row 1 right after it at $0428, and so on. Not on an Apple II. To save a handful of chips in the video counter circuit, Wozniak laid the 24 rows out in an interleaved order: each 128-byte block of memory holds three screen rows that are 8 rows apart on screen, plus 8 leftover bytes (the famous "screen holes").

The animation shows memory being filled in address order — watch where the rows land on screen:

MEMORY (address order) SCREEN (row order) Each 128-byte block = 3 rows of 40 chars + 8 unused "hole" bytes.

Animated: how consecutive memory lands on the screen. Memory is filled top to bottom on the left; each 40-byte chunk lights up its true position on the right. Consecutive chunks are 8 screen rows apart — the interleave. Gray slots are the 8-byte screen holes (used as scratch space by peripheral cards, so don't count on them staying yours).

The formula, if you ever need to compute a row's base address yourself:

address = $0400 + (row MOD 8) × $80 + (row ÷ 8) × $28

row 0  → $0400      row 1  → $0480      row 2  → $0500
row 8  → $0428      row 9  → $04A8      row 10 → $0528
row 16 → $0450      row 17 → $04D0      row 18 → $0550

The hi-res screen uses the same trick twice over — its 192 rows are interleaved in three nested levels. In practice everyone uses a lookup table of row base addresses, and so will we in Lecture 06.

Screen codes: not quite ASCII

Bytes in text memory use screen codes, where the top two bits select a display style:

Byte rangeStyleExample: letter A
$00–$3FInverse (black on green)$01
$40–$7FFlashing$41
$80–$FFNormal$C1
TRY IT: POKE 1024,1 puts an inverse A in the top-left corner. Now try FOR I = 0 TO 39 : POKE 1024 + I, 65 + I : NEXT — a flashing alphabet across the top row.

3. Hi-res: seven pixels and a color bit

Hi-res mode gives 280×192 pixels in 8K. Each byte controls seven horizontal pixels (bits 0–6, drawn left to right), and bit 7 — the palette bit — selects which pair of colors the byte's pixels can show:

One hi-res byte: value %01011010 with palette bit 0 0 1 0 1 1 0 1 0 bit 7 palette bits 6…0 = seven pixels (bit 0 = leftmost on screen) On a color monitor: even columns tint purple, odd columns green (palette bit = 1 would give blue / orange instead)
Static: anatomy of a hi-res byte. Seven pixels per byte — which is why the 280-pixel row is 40 bytes wide, and why hi-res coordinates and colors behave so strangely: a pixel's possible colors depend on whether its column is even or odd and on its byte's palette bit. White comes from lighting two adjacent pixels.

The colors are an NTSC artifact: the Apple II outputs only a black-and-white dot stream, but the dots are timed so a color TV's decoder hallucinates purple, green, blue, and orange from their positions. Color for free — the trick that let a 1977 machine undercut everything else on the market. The cost is the strange rules above, which every Apple II artist simply learned to live with.

4. Sound: one bit, infinite cleverness

There is no sound chip. There is a speaker, a flip-flop, and soft switch $C030: every access flips the cone in or out. Everything you ever heard an Apple II do — music, speech synthesis in Castle Wolfenstein, four-voice chords — was software toggling that one bit with cycle-accurate timing.

; a square-wave tone in assembly: toggle, waste time, repeat
TONE    LDA $C030      ; click
        LDX #$60       ; pitch = delay length
DELAY   DEX
        BNE DELAY
        JMP TONE       ; (Ctrl+Reset to stop!)

From BASIC you only get clicks and buzzes (PEEK(-16336) in a loop) because BASIC is too slow to toggle at audio frequencies with precision — a first taste of why Lecture 06 exists.

5. Choosing a mode from BASIC

TEXT          : REM 40x24 text
GR            : REM lo-res 40x40 + 4 text lines
COLOR= 9      : REM orange
PLOT 20,20    : REM one block
HLIN 0,39 AT 10  : REM horizontal line
VLIN 0,39 AT 5   : REM vertical line

HGR           : REM hi-res page 1, mixed with text
HCOLOR= 3     : REM white
HPLOT 0,0 TO 279,159   : REM a diagonal line

Check your understanding

Q1. Why are the Apple II's screen rows interleaved in memory?

Q2. How many pixels does one hi-res byte control, and what does bit 7 do?

Q3. How does an Apple II play a musical note?

← Lecture 03: Memory Map Lecture 05: Applesoft BASIC →