Vertical nametable loading

Discuss technical or other issues relating to programming the Nintendo Entertainment System, Famicom, or compatible systems. See the NESdev wiki for more information.

Moderator: Moderators

Post Reply
DedGzus
Posts: 11
Joined: Sat Jan 07, 2023 10:11 am

Vertical nametable loading

Post by DedGzus »

I think I read somewhere in the hardware reference for the PPU that you can set it to accept nametable bytes vertically instead of horizontally. For example after sending in the byte to $2000 the next byte it will expect will be sent to $2020 followed by $2040, etc. Is this a good way of partially preloading nametables for scrolling? Sorry if this is a dumb or confusing question I don't think I quite have all of my terminology down yet.
Fiskbit
Posts: 891
Joined: Sat Nov 18, 2017 9:15 pm

Re: Vertical nametable loading

Post by Fiskbit »

Yes. When you read from or write to the PPU data register ($2007), the VRAM address is automatically incremented. That increment is either by 1 (for writing nametables horizontally by row) or 32 (vertically by column), controlled by bit 2 of the PPU control register ($2000). Typically, you'll want to increment in the direction perpendicular to your scroll direction so you can write the next column or row you intend to scroll in without having to manually change the address after each write, which is very slow, particularly in comparison to the limited vblank window for writing to VRAM.
DedGzus
Posts: 11
Joined: Sat Jan 07, 2023 10:11 am

Re: Vertical nametable loading

Post by DedGzus »

Thank you. I kinda wish I had realized this before I wrote my level data decompression algorithm but I guess it's all good practice to someone learning 6502asm. One question though. At what point does the PPU increment to accessing the attribute data? Does it come after every 30 bytes? Or is it still done sequentially after the nametable is loaded? Like, do I have to manually jump to the attribute bytes for the column I just added? I hope you understand what I am trying to ask. Thank again.
Fiskbit
Posts: 891
Joined: Sat Nov 18, 2017 9:15 pm

Re: Vertical nametable loading

Post by Fiskbit »

The increment behavior is the same regardless of the current VRAM address; it simply adds 1 or 32. This doesn't play nicely with attributes, which have 8 byte rows, and attributes in general are a real pain to deal with.
DedGzus
Posts: 11
Joined: Sat Jan 07, 2023 10:11 am

Re: Vertical nametable loading

Post by DedGzus »

So my guess is that I should write an algorithm to write four 30byte columns (skip 2 bytes after every 30) and then manually addresses and set the 8 bytes of attributes for that area. Correct?
Fiskbit
Posts: 891
Joined: Sat Nov 18, 2017 9:15 pm

Re: Vertical nametable loading

Post by Fiskbit »

4 columns is ambitious; I think you can make it work, but it's costly to write all of that at once. Doing 2 columns at a time is more reasonable, though it makes the attributes handling more difficult. You'll be updating the address after each column, but not to 'skip 2 bytes' because the columns aren't contiguous in that way; each column's starting address is 1 apart. For attributes, you can batch 2 writes together with the 32 byte increment mode so you only have to set the address 4 times.
User avatar
Dwedit
Posts: 4924
Joined: Fri Nov 19, 2004 7:35 pm
Contact:

Re: Vertical nametable loading

Post by Dwedit »

Regarding attributes and 32 increment mode, there actually is a use for that.
Attribute table is 8 bytes wide (8 * 32 pixels), and 8 bytes tall (8 * 32 pixels). 32 bytes ahead of the last attribute byte means you advance 4 'rows' (128 pixels) down.
So if you're trying to write attributes for a whole column of tiles, you can write two attribute bytes. One for your target position, one for 128 pixels lower.

I find it makes things easier if you keep a copy of the whole attribute table in RAM. It's 128 bytes for the two nametables.
Here come the fortune cookies! Here come the fortune cookies! They're wearing paper hats!
DedGzus
Posts: 11
Joined: Sat Jan 07, 2023 10:11 am

Re: Vertical nametable loading

Post by DedGzus »

Fiskbit wrote: Sat Jan 21, 2023 10:20 am 4 columns is ambitious; I think you can make it work, but it's costly to write all of that at once.
I meant do one column at a time, maybe two. But no need to update the attributes until after four rows are written because each attribute byte describes a 4 column by 4 row section.
Post Reply