Display: Difference between revisions
(→Components: rewrite the palette section too) |
|||
Line 82: | Line 82: | ||
byte 0 1 2 3 | byte 0 1 2 3 | ||
bits 7-4 3-0 7-4 3-0 7-4 3-0 7-4 3-0 | bits 7-4 3-0 7-4 3-0 7-4 3-0 7-4 3-0 | ||
pixel 0 1 2 3 4 5 6 7 | pixel 0 1 2 3 4 5 6 7 full tile | ||
--- --- --- --- --- --- --- --- | --- --- --- --- --- --- --- --- | ||
. 1 = 01 2 3 = 23 . 1 = 01 2 4 = 24 .123.124 | . 1 = 01 2 3 = 23 . 1 = 01 2 4 = 24 .123.124 = 01 23 01 24 | ||
4 5 = 45 6 7 = 67 . 1 = 01 2 4 = 24 4567.124 | 4 5 = 45 6 7 = 67 . 1 = 01 2 4 = 24 4567.124 = 45 67 01 24 | ||
8 9 = 89 A B = AB . 1 = 01 2 4 = 24 89AB.124 | 8 9 = 89 A B = AB . 1 = 01 2 4 = 24 89AB.124 = 89 AB 01 24 | ||
C D = CD E F = EF . 1 = 01 2 4 = 24 --\ CDEF.124 | C D = CD E F = EF . 1 = 01 2 4 = 24 --\ CDEF.124 = CD EF 01 24 | ||
. . = 00 . . = 00 . 1 = 01 2 4 = 24 --/ .....124 | . . = 00 . . = 00 . 1 = 01 2 4 = 24 --/ .....124 = 00 00 01 24 | ||
1 1 = 11 1 1 = 11 1 2 = 12 4 8 = 48 11111248 | 1 1 = 11 1 1 = 11 1 2 = 12 4 8 = 48 11111248 = 11 11 12 48 | ||
2 2 = 22 2 2 = 22 2 4 = 24 8 . = 80 2222248. | 2 2 = 22 2 2 = 22 2 4 = 24 8 . = 80 2222248. = 22 22 24 80 | ||
4 4 = 44 4 4 = 44 4 8 = 48 . . = 00 444448.. | 4 4 = 44 4 4 = 44 4 8 = 48 . . = 00 444448.. = 44 44 48 00 | ||
</pre> | </pre> | ||
Revision as of 19:38, 12 July 2024
The WonderSwan's display functionality generally consists of:
- a 224x144 display clocked at ~75.47 Hz by default, capable of displaying:
- up to sixteen distinct shades of gray
- 12-bit RGB444 color(color)
- two 32x32 background layers ("screens"), capable of displaying up to 512 (1024(color)) distinct tiles,
- a sprite layer, capable of displaying up to 128 8x8 sprites (up to 32 per line),
- six LCD icons to the bottom or right of the display, usable as additional indicators.
Components
Tiles
The WonderSwan can display up to 512 distinct tiles at a time, with two bits of palette index information for every pixel.
The WonderSwan Color expands this to 1024 distinct tiles for background (with 512 remaining the limit for sprites), while also introducing modes with four bits of palette index information for every pixel.
2 bits per pixel, planar
The tiles are stored in an interleaved planar format, with two bits total for every pixel. Odd bytes store the first plane (bit 0 of each pixel), while even bytes store the second plane (bit 1 of each pixel).
tile data (16 bytes) 01 7C 01 FC 00 C0 18 D8 18 D8 00 C0 00 00 C0 00 || \/ plane 0 plane 1 7 bit 0 7 bit 0 full tile ---- ---- ---- ---- .... ...1 = 01 .222 22.. = 7C .22222.1 .... ...1 = 01 2222 22.. = FC 222222.1 .... .... = 00 22.. .... = C0 22...... ...1 1... = 18 22.2 2... = D8 --\ 22.33... ...1 1... = 18 22.2 2... = D8 --/ 22.33... .... .... = 00 22.. .... = C0 22...... .... .... = 00 .... .... = 00 ........ 11.. .... = C0 .... .... = 00 11......
This matches the format used by the Game Boy.
4 bits per pixel, planar
This mode is stored in a manner similar to the 2 bits per pixel mode, but with an additional two planes for bit 2 and bit 3 of each pixel's palette index, expanding the tile data to 32 bytes.
tile data (32 bytes) 54 32 01 00 54 32 F1 00 54 32 01 F0 54 32 F1 F0 04 02 01 00 F8 04 02 01 00 F8 04 02 00 00 F8 04 || \/ plane 0 plane 1 plane 2 plane 3 7 bit 0 7 bit 0 7 bit 0 7 bit 0 full tile ---- ---- ---- ---- ---- ---- ---- ---- .1.1 .1.. = 54 ..22 ..2. = 32 .... ...4 = 01 .... .... = 00 .123.124 .1.1 .1.. = 54 ..22 ..2. = 32 4444 ...4 = F1 .... .... = 00 4567.124 .1.1 .1.. = 54 ..22 ..2. = 32 .... ...4 = 01 8888 .... = F0 89AB.124 .1.1 .1.. = 54 ..22 ..2. = 32 4444 ...4 = F1 8888 .... = F0 --\ CDEF.124 .... .1.. = 04 .... ..2. = 02 .... ...4 = 01 .... .... = 00 --/ .....124 1111 1... = F8 .... .2.. = 04 .... ..4. = 02 .... ...8 = 01 11111248 .... .... = 00 2222 2... = F8 .... .4.. = 04 .... ..8. = 02 2222248. .... .... = 00 .... .... = 00 4444 4... = F8 .... .8.. = 04 444448..
This format matches the one used by the Sega Master System and Game Gear family of consoles.
4 bits per pixel, packed
Unlike the previous two formats, in the packed format each byte stores the complete palette index of two pixels - the high four bits store the left pixel, while the low four bits store the right pixel. Four such bytes make up a row of eight pixels from left to right.
tile data (32 bytes) 01 23 01 24 45 67 01 24 89 AB 01 24 CD EF 01 24 00 00 01 24 11 11 12 48 22 22 24 80 44 44 48 00 || \/ byte 0 1 2 3 bits 7-4 3-0 7-4 3-0 7-4 3-0 7-4 3-0 pixel 0 1 2 3 4 5 6 7 full tile --- --- --- --- --- --- --- --- . 1 = 01 2 3 = 23 . 1 = 01 2 4 = 24 .123.124 = 01 23 01 24 4 5 = 45 6 7 = 67 . 1 = 01 2 4 = 24 4567.124 = 45 67 01 24 8 9 = 89 A B = AB . 1 = 01 2 4 = 24 89AB.124 = 89 AB 01 24 C D = CD E F = EF . 1 = 01 2 4 = 24 --\ CDEF.124 = CD EF 01 24 . . = 00 . . = 00 . 1 = 01 2 4 = 24 --/ .....124 = 00 00 01 24 1 1 = 11 1 1 = 11 1 2 = 12 4 8 = 48 11111248 = 11 11 12 48 2 2 = 22 2 2 = 22 2 4 = 24 8 . = 80 2222248. = 22 22 24 80 4 4 = 44 4 4 = 44 4 8 = 48 . . = 00 444448.. = 44 44 48 00
This format matches the one used by the Mega Drive console.
Palettes
The WonderSwan provides sixteen different palettes. Palettes 0-7 can be used for the two screens only, while palettes 8-15 can be used for both screens and sprites.
Mono
In mono modes, palettes are stored in I/O ports 0x20 through 0x3F. Each palette contains four three-bit entries, which are pointers into a global, four-bit shade lookup table:
Palette Global shade LUT 1 ===========> 2 ==========================> 5 ^ (0, 2, 4, 6) ^ (1, 3, 5, 7, 9, 11, 13, 15) ^ | | | Palette index Value Displayed shade
The shade value corresponds to the darkness of the pixel: shade 0 is the brightest, while shade 15 is the darkest.
Color
In color modes, palettes are stored as 16-bit words in memory addresses 0xFE00 through 0xFFFF, without additional lookup tables:
Address 15 bit 8 7 bit 0 ---- ---- ---- ---- 1111 111p pppi iii. | |||| ||| | |||+-+++- Index in palette (0-15) +--+++------ Palette number (0-15) Data 15 bit 8 7 bit 0 ---- ---- ---- ---- .... rrrr gggg bbbb |||| |||| |||| |||| |||| ++++- Blue (0-15) |||| ++++------ Green (0-15) ++++------------ Red (0-15)
In 2 bits per pixel color modes, palette entries 4 through 15 are not used.
Transparency
In two bit per pixel modes:
- Palettes 0-3 and 8-11 are opaque. For these, index zero is treated as opaque. - Palettes 4-7 and 12-15 are translucent. For these, index zero is treated as transparent. This means that the color/shade value set to it is ignored, and only three distinct colors/shades can be used for tiles.
In four bit per pixel modes, all palettes are translucent. Index zero is always treated as transparent, and fifteen different colors/shades can be used for tiles.
Background color
The background color is displayed if no opaque pixel from screens or sprites is drawn. This color is set in I/O port 0x01:
- In mono modes, it is set to an entry in the shade lookup table (0-7), - In color modes, it is set to an entry in the color palette (0-255). Note that this allows you to use the first color (color zero) of any palette, which is normally ignored and assumed to be transparent.
Screens
The WonderSwan can display up to two distinct 32x32 screens. These consist of 1024 two-byte cells:
15 bit 8 7 bit 0 ---- ---- ---- ---- vhbp pppt tttt tttt |||| |||| |||| |||| |||| |||+--++++-++++- Tile index (0-511) |||+-+++------------- Palette (0-15) ||+------------------ Tile bank (0-1) - color only |+------------------- Horizontal flip +-------------------- Vertical flip
Sprites
The WonderSwan can display up to 128 sprites at once. These are stored in a sprite table in RAM, which consists of up to 128 four-byte entries:
(Byte 1) (Byte 0) 15 bit 8 7 bit 0 ---- ---- ---- ---- vhPi pppt tttt tttt |||| |||| |||| |||| |||| |||+--++++-++++- Tile index (0-511) - only bank 0 |||| +++------------- Palette (0-7) - mapped to screen palettes 8-15 |||+----------------- Window location - 0 = inside, 1 = outside ||+------------------ Priority - 0 = behind Screen 2, 1 = in front of Screen 2 |+------------------- Horizontal flip +-------------------- Vertical flip (Byte 2) 7 bit 0 ---- ---- yyyy yyyy |||| |||| ++++-++++- Y coordinate (Byte 3) 7 bit 0 ---- ---- xxxx xxxx |||| |||| ++++-++++- X coordinate
For each row, the first 32 sprites for that row will be drawn - including sprites obscured by windows or outside of the visible range; only the Y coordinate determines this. The earlier among those sprites will be on top of the later ones.
Visibility priority
For display components, the visibility priority is as follows:
- Sprite 0, high priority
- Sprite 127, high priority
- Screen 2
- Sprite 0, low priority
- Sprite 127, low priority
- Screen 1
- Background color
Windows
Screen 2 and the sprite layer can optionally be restricted to a specific window.
In addition, one can control if a given element is rendered inside or outside that window. For Screen 2, this is controlled globally; for sprites, this is controlled per-sprite.
Icons
The WonderSwan features six LCD segment icons which are displayed to the right(color) or below(mono) the main display. These are, as follows:
- Aux 3 - large circle,
- Aux 2 - medium circle,
- Aux 1 - small circle,
- Horizontal orientation,
- Vertical orientation,
- Sleep.
Interrupts
The display circuit generates two interrupts of its own:
- Display Interrupt Line Match - when
Display Current Line
==Display Interrupt Line
, at the beginning of said line. - Display Vertical Blank - when
Display Current Line
==144
, at the beginning of said line.
It also provides a timing source for the two Horizontal and Vertical Blank Timers, which provide their own respective interrupts.
I/O ports
Display Control ($00)
7 bit 0 ---- ---- ..ow Ws21 || |||| || |||+- Enable Screen 1 layer || ||+-- Enable Screen 2 layer || |+--- Enable Sprite layer || +---- Enable Sprite window |+------ Enable Screen 2 window +------- Screen 2 window location: 0 = inside, 1 = outside
Display Background Color ($01)
(mono) (color) 7 bit 0 7 bit 0 ---- ---- ---- ---- .... .sss pppp iiii ||| |||| |||| +++- Value |||| ++++- Index in palette (0-15) (0-7) ++++------ Color palette (0-15)
Display Current Line ($02 read)
The current line being drawn by the display.
Note that lines are sent to the display with a one-line delay. This matters for color palette or shade LUT manipulation; changing these values when current line == 1
will actually affect line 0.
Display Interrupt Line ($03)
The line to emit an interrupt on.
Sprite Table Address ($04)
7 bit 0 ---- ---- ..Aa aaaa || |||| |+-++++- Address (bits 9-13) +------- Address (bit 14) - color only
Sprite Table First ($05)
7 bit 0 ---- ---- .iii iiii ||| |||| +++-++++- Index of first sprite entry to draw (0-127)
Sprite Table Count ($06)
7 bit 0 ---- ---- cccc cccc |||| |||| ++++-++++- Count of sprite entries to draw (1-128)
Screen Address ($07)
7 bit 0 ---- ---- 2222 1111 |||| |||| |||| |+++- Screen 1 address (bits 11-13) |||| +---- Screen 1 address (bit 14) - color only |+++------ Screen 2 address (bits 11-13) +--------- Screen 2 address (bit 14) - color only
Screen 2 Window Left ($08)
Screen 2 Window Top ($09)
Screen 2 Window Right ($0A)
Screen 2 Window Bottom ($0B)
Sprite Window Left ($0C)
Sprite Window Top ($0D)
Sprite Window Right ($0E)
Sprite Window Bottom ($0F)
Screen 1 Scroll X ($10)
Screen 1 Scroll Y ($11)
Screen 2 Scroll X ($12)
Screen 2 Scroll Y ($13)
LCD Control ($14)
7 bit 0 ---- ---- .... ..Ce || |+- LCD Enable: 0 = sleep, 1 = enabled +-- Contrast (WSC): 0 = low, 1 = high
LCD Icon Control ($15)
7 bit 0 ---- ---- ..32 1hvs || |||| || |||+- Sleep || ||+-- Vertical orientation || |+--- Horizontal orientation || +---- Aux 1 |+------ Aux 2 +------- Aux 3
LCD Mono Shade LUT ($1C-$1F)
$1C $1D $1E $1F 7 bit 0 7 bit 0 7 bit 0 7 bit 0 ---- ---- ---- ---- ---- ---- ---- ---- 1111 0000 3333 2222 5555 4444 7777 6666
LCD Mono Palette 0..15 ($20, $21 .. $3E, $3F)
The monochrome palette is laid out as sixteen words:
N+1 N 15 bit 8 7 bit 0 ---- ---- ---- ---- .333 .222 .111 .000 ||| ||| ||| ||| ||| ||| ||| +++- Shade LUT index for color 0 ||| ||| +++------ Shade LUT index for color 1 ||| +++------------ Shade LUT index for color 2 +++----------------- Shade LUT index for color 3
Internal I/O ports
These I/O ports are said to be internal and not intended for use by commercial games.
LCD Final Line ($16)
The final line preceding line counter restart and the beginning of active display. By default, this is set to 158, which equals 159 total lines per frame.
It is said setting this register to an odd value on SwanCrystal has an adverse effect to the LCD panel[1], but the exact mechanism is unknown.
LCD Back Porch Line ($17, WSC only)
This port is available on the WonderSwan Color only - not the SwanCrystal!
The final line preceding the vertical back porch; by default, this should be set to 155.
The vertical back porch of the LCD is assumed to be 4 lines by some hardware, including IPS mods, as well as the official "TV Swan" capture device. Given that the first visible line is sent to the LCD on the display's line 1, this should be generally set to LCD Final Line - 3
.
Conversely, it is said moving this value closer to vertical blank improves LCD visibility[2], but the exact mechanism is unknown.
LCD Status ($1A)
7 bit 0 ---- ---- ...v vv.s | || | | || +- LCD sleep: 0 = no, 1 = sleep | || | || Volume segments: | |+--- Volume B (medium, high) | +---- Volume A (low, high) +------ Speaker
TFT LCD Configuration ($70, $71, $72, $73, $74, $75, $76, $77 SwanCrystal only)
These eight bytes are read from internal EEPROM and configure unknown aspects of the console's TFT LCD panel.
They are only writable while the Boot ROM is unlocked - locking has the side effect of making them read-only.