Forums

Sega Master System / Mark III / Game Gear
SG-1000 / SC-3000 / SF-7000 / OMV
Home - Forums - Games - Scans - Maps - Cheats - Credits
Music - Videos - Development - Hacks - Translations - Homebrew

View topic - Need help with understanding palette and attribute tables

Reply to topic
Author Message
  • Joined: 25 Feb 2023
  • Posts: 99
Reply with quote
Need help with understanding palette and attribute tables
Post Posted: Tue Apr 25, 2023 3:25 am
As the title says, I'm struggling to understand what the attribute table actually is with regards to SMS hardware. Looking at documentation and the various tutorials in Getting Started isn't helping much either since it just looks like a big grid with hex numbers in it and a mysterious "empty space" in the middle. It probably sounds silly to more experienced folks on this forum but I'm just confused about how to use attribute tables on this system compared to the (relatively) straightforward approach the NES has (which is important because I'm trying to adapt an NES game to the Master System).

My question about the palette is a little simpler. I would just like to know how color indexes affect the code. For example, I need to fill the background with one solid color, then have text fade in from invisible to dark gray to gray to white. That's only 4 colors but the SMS has 16 available for sprites and backgrounds for 32 total at a time. Do I need to format this in any particular way with filler color values or can I just load up the 4 I need? I ask because the Hello World example only uses black and white as background colors and doesn't use sprites.
  View user's profile Send private message
  • Joined: 01 Feb 2014
  • Posts: 877
Reply with quote
Post Posted: Tue Apr 25, 2023 7:47 am
I’m not quite sure what you mean by attribute table. There are two tables in the vdp that are relevant for displaying something on screen. One is the name table, the other one is the sprite table.

The name table defines which tiles go where on the screen. Each entry is two bytes with one defining the tile number and the other one the attributes like xy-fllipping, which palette (bg or sprites) to use, etc.

The sprite table contains the information for each of the 64 sprites: sprite tile number, x,y. There’s a hole of 64 bytes in the middle of the sprite table.


As for your palette question, you only need to define the colors you’re actually using. For a fade effect like the one you describe, you actually need only two entries, text and background. Then just change the entry for the text color from black gradually to white.
  View user's profile Send private message
  • Joined: 06 Mar 2022
  • Posts: 670
  • Location: London, UK
Reply with quote
Post Posted: Tue Apr 25, 2023 8:18 am
Last edited by willbritton on Tue Apr 25, 2023 8:32 am; edited 4 times in total
Hi CerezaSaturn64,

Let's see if we can fill in some blanks!

CerezaSaturn64 wrote
I'm struggling to understand what the attribute table actually is with regards to SMS hardware.


Every line that the screen displays (it's easiest to think about it happening just before the next line is displayed) the first 64 bytes of the Sprite Attribute Table (henceforth SAT) are parsed in order to decide whether or not there are sprites to display on this line. The first 64 bytes in the table contain the Vertical Positions (VPOS) of the sprites. These vertical positions differ from screen positions by 1, so for example if you have a VPOS of 0 in the SAT it means that a sprite will be displayed on line 1, which is the second line from the top.

The parsing of the VPOS values stops when one of the following is true:
1. It has checked all 64 VPOS values.
2. It has found 8 sprites on the line in question (the SMS can't display more)
3. It reads the special stop symbol 0xD0 on 192 line display only.

At this point, we now have up to 8 sprites which we might display on this line.

Then when the line is being drawn to screen we read the second 128 bytes of the table to decide which sprite to draw (IDX) and what horizontal position it should start to display at (HPOS).
These bytes alternate like HPOS, IDX, HPOS, IDX, HPOS, IDX, etc. and they correspond to the VPOS values based on the order in which they are found in the table.

So an example:

At byte 0 of the table we have the value 53
At byte 1 of the table we have the value 79
At byte 2 of the table we have the value 254
At byte 3 of the table we have the value 208
At byte 128 of the table we have the value 22
At byte 129 of the table we have the value 1
At byte 130 of the table we have the value 250
At byte 131 of the table we have the value 2
At byte 132 of the table we have the value 64
At byte 133 of the table we have the value 3
At byte 134 of the table we have the value 32
At byte 135 of the table we have the value 4

What will happen?

Bytes 0, 128 and 129 instruct the VDP to draw sprite with tile index 1 at vertical position 54 (remembering to +1) and horizontal position 22

Bytes 1, 130 and 131 instruct the VDP to draw sprite with tile index 2 at vertical position 80 and horizontal position 250. This is interesting because 3 pixels of the sprite will be off-screen to the right.

Bytes 2, 132 and 133 instruct the VDP to draw sprite with tile index 3 at vertical position -1 and horizontal position 64. This is quite interesting because the VPOS is "negative" - we count back from 255 - so the first row of pixels of the sprite will be off-screen to the top.

Byte 3 is actually hex 0xD0 so it stops sprite processing and the bytes at locations 134 and 135 never get read.

Some further notes:
- Register 5 controls where the SAT is in memory. So when I say "byte 0" above I mean the address of the SAT + 0. For example if register 5 is 0xFF then the SAT will be at VRAM address 0x3F00.
- Register 6 controls whether or not the single byte sprite tile index IDX in the SAT comes from the first half of VRAM or the second. If register 6 is 0xFB, an index value of 0 will draw the tile with data starting at VRAM address 0x0000. If register 6 is 0xFF, and index value of 0 will draw the tile with data starting at VRAM address 0x2000.
- Bytes 64 to 127 of the SAT are not used in the above process, so the SAT only has 192 "useful" bytes in it, but consumes 256 of space in the VDP memory map. You can still use the 64 byte "gap" for whatever you want - for example you can keep 2 tiles worth of tile data there.
- If more than 8 VPOS positions are hit in a single line, only 8 sprites will be displayed, I would say the first 8. Games typically suffer from flickering in this situation. Also bit 6 of the VDP status register is set if this happens and stays set until you read the value.

CerezaSaturn64 wrote
I need to fill the background with one solid color, then have text fade in from invisible to dark gray to gray to white.

There are quite a few fade algorithms knocking around this site, but essentially, by the time you display what you need to on screen, you will need that colour to exist in the palette, so you have two options:
1. Change the palette colours
2. Change the tilemap definitions (I'm assuming you're not using sprites here) so that they reference different palette colours.

Changing the palette colours is the quickest way to do it, so for example you could reserve one of the palette indexes for your fading text, draw the text and then periodically change the palette colour (with writes to 0xC? on the VDP command port). That is how most fading algorithms you will find here work.

Other things you could do are set up your colours in advance and re-define your text character tiles to use a different index. This will take max. 32 write operations per character so is very very slow. Probably avoid this.

Finally another option to change colours is to toggle bit 3 of the "attribute" byte of each tile in the tilemap/name table. This switches between the lower (background) palette and upper (sprite) palette for each tile and only takes a single write per character and so is fairly quick and useful sometimes. Although in your case this isn't super useful as you need four colour transitions and this trick only works for two colours.

Hope some of that helps!
  View user's profile Send private message Visit poster's website
  • Joined: 25 Feb 2023
  • Posts: 99
Reply with quote
Post Posted: Tue Apr 25, 2023 8:19 am
Kagesan wrote
I’m not quite sure what you mean by attribute table. There are two tables in the vdp that are relevant for displaying something on screen. One is the name table, the other one is the sprite table.

The name table defines which tiles go where on the screen. Each entry is two bytes with one defining the tile number and the other one the attributes like xy-fllipping, which palette (bg or sprites) to use, etc.

The sprite table contains the information for each of the 64 sprites: sprite tile number, x,y. There’s a hole of 64 bytes in the middle of the sprite table.


As for your palette question, you only need to define the colors you’re actually using. For a fade effect like the one you describe, you actually need only two entries, text and background. Then just change the entry for the text color from black gradually to white.


I believe the thing I'm talking about is Sprite tables. It's confusing because of that big hole in the middle, and looking at charts like the one used in Racer aren't helping me understand what's going on.

Thank you for the help with the palette question though :)
Sat_buffer_map.png (31.8 KB)
Sat_buffer_map.png

  View user's profile Send private message
  • Joined: 06 Mar 2022
  • Posts: 670
  • Location: London, UK
Reply with quote
Post Posted: Tue Apr 25, 2023 8:28 am
P.S. This is actually a pretty good explanation in the official docs:

https://www.smspower.org/Development/SMSOfficialDocs#SPRITEATTRIBUTETABLE
  View user's profile Send private message Visit poster's website
  • Joined: 25 Feb 2023
  • Posts: 99
Reply with quote
Post Posted: Tue Apr 25, 2023 8:29 am
willbritton wrote
Every line that the screen displays (it's easiest to think about it happening just before the next line is displayed) the first 64 bytes of the Sprite Attribute Table (henceforth SAT) are parsed in order to decide whether or not there are sprites to display on this line. The first 64 bytes in the table contain the Vertical Positions (VPOS) of the sprites. These vertical positions differ from screen positions by 1, so for example if you have a VPOS of 0 in the SAT it means that a sprite will be displayed on line 1, which is the second line from the top.

The parsing of the VPOS values stops when one of the following is true:
1. It has checked all 64 VPOS values.
2. It has found 8 sprites on the line in question (the SMS can't display more)
3. It reads the special stop symbol 0xD0 on 192 line display only.

At this point, we now have up to 8 sprites which we might display on this line.

Then when the line is being drawn to screen we read the second 128 bytes of the table to decide which sprite to draw (IDX) and what horizontal position it should start to display at (HPOS).
These bytes alternate like HPOS, IDX, HPOS, IDX, HPOS, IDX, etc. and they correspond to the VPOS values based on the order in which they are found in the table.

So an example:

At byte 0 of the table we have the value 53
At byte 1 of the table we have the value 79
At byte 2 of the table we have the value 254
At byte 3 of the table we have the value 208
At byte 128 of the table we have the value 22
At byte 129 of the table we have the value 1
At byte 130 of the table we have the value 250
At byte 131 of the table we have the value 2
At byte 132 of the table we have the value 64
At byte 133 of the table we have the value 3
At byte 134 of the table we have the value 32
At byte 135 of the table we have the value 4

What will happen?

Bytes 0, 128 and 129 instruct the VDP to draw sprite with tile index 1 at vertical position 54 (remembering to +1) and horizontal position 22

Bytes 1, 130 and 131 instruct the VDP to draw sprite with tile index 2 at vertical position 80 and horizontal position 250. This is interesting because 3 pixels of the sprite will be off-screen to the right.

Bytes 2, 132 and 133 instruct the VDP to draw sprite with tile index 3 at vertical position -1 and horizontal position 64. This is quite interesting because the VPOS is "negative" - we count back from 255.

Byte 3 is actually hex 0xD0 so it stops sprite processing and the bytes at locations 134 and 135 never get read.


Thank you so much for this because everything finally clicked into place for me. You did a great job explaining and now I understand what's going on in the SAT tables lol. This is very different from what the NES calls an attribute table, which probably contributed so much to my confusion. Curse that Ni****do!
  View user's profile Send private message
  • Joined: 14 Oct 2008
  • Posts: 510
Reply with quote
Post Posted: Tue Apr 25, 2023 4:57 pm
What NES calls an "attribute table" is how it assigns background tile palettes. 2 bits for each 16x16 block on the screen. (yes, every 2x2 square of 8x8 tiles are forced to use the same palette) They were really looking to squeeze as much out of the RAM as they could in 1983.
  View user's profile Send private message
  • Joined: 05 Dec 2019
  • Posts: 56
  • Location: USA
Reply with quote
Post Posted: Tue Apr 25, 2023 7:15 pm
SMS nametables behave more like MMC5, GBC, or SNES nametables, with 8x8-pixel attributes and 9-bit tile numbers. The SMS counterpart to the NES nametable's "attribute tables" is values at odd addresses in the nametable.

If your tiles are stored in the ROM with 2 bits per pixel (blank, color 1, color 2, or color 3), you'll need to convert them to 4 bits per pixel when copying them to VRAM through the VDP data port. It turns out that this upconversion can be done at the same time as horizontal flipping, which you'll need to do in software on SMS. See my previous topic "Sprite loading, flipping, and expansion routines" and my reply to "alternate color sprites on SMS?".
  View user's profile Send private message Visit poster's website
Reply to topic



Back to the top of this page

Back to SMS Power!