4 way scroll - vert scroll problem

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
User avatar
olddb
Posts: 188
Joined: Thu Oct 26, 2017 12:29 pm
Contact:

4 way scroll - vert scroll problem

Post by olddb »

I'm trying to do a simple four way scroll. NO sprite0 hit.
I'm using a "Vertical Mirror Type" as in the Mesen header editor.
The problem is I'm getting a "hiccup" in the vertical scrolling.

Nesdev wiki reads:
"Normal" vertical offsets range from 0 to 239, while values of 240 to 255 are treated as -16 through -1 in a way
So I guess a have to use modulus % 240 to the vert scroll value? If so, how can I do this efficiently.

Also, bit $2000.1 with this setup is not used, right?

Thank you.
...
User avatar
Controllerhead
Posts: 314
Joined: Tue Nov 13, 2018 4:58 am
Location: $4016
Contact:

Re: 4 way scroll - vert scroll problem

Post by Controllerhead »

olddb wrote: Mon May 24, 2021 10:44 pm So I guess a have to use modulus % 240 to the vert scroll value?
Pretty much, but, also account for "scrolling negatively"; y % 240 would only work in a positive direction.

The PPU doesn't like 240-255 for a Y value and shows the "other" attribute table as nametable data.

You can do something like:

Code: Select all

  LDA scrollPosY
  CLC
  ADC scrollVecY
  CMP #$F0
  BCC ++
    LDX scrollVecY
    BPL +
      AND #%11101111
      BMI ++
    +
    AND #%00001111
  ++
  STA scrollPosY
Last edited by Controllerhead on Tue May 25, 2021 2:14 am, edited 1 time in total.
Image
User avatar
tokumaru
Posts: 12427
Joined: Sat Feb 12, 2005 9:43 pm
Location: Rio de Janeiro - Brazil

Re: 4 way scroll - vert scroll problem

Post by tokumaru »

olddb wrote: Mon May 24, 2021 10:44 pmSo I guess a have to use modulus % 240 to the vert scroll value?
That's one way to do it, but I personally prefer to maintain two separate scroll values: an "ideal" one, that wraps around normally at 256, and a special one that wraps around at 240. You basically apply the same transformations to both every frame, taking care to handle the special cases of the alternate value (whenever it lands in the 240-255 range, check the sign of the movement and fix accordingly, like in Controllerhead's example).

The two scroll values don't even need to be perfectly aligned at start-up (only the lower 4 bits have to match!), you can, for example, have ScrollY start at 66 and NTScrollY start at 2 - as long as they're both updated in sync, the upper bits of NTScrollY can be initialized to any value outside of the "forbidden zone". You can then use the "ideal" scroll for everything relative to the game world (reading the level map, calculating sprite positions, etc.) and the alternate one for things related to the PPU (setting the scroll, calculating NT/AT addresses for updates).
Also, bit $2000.1 with this setup is not used, right?
If the game uses vertical mirroring, then $2000.1 indeed doesn't matter. I still prefer to keep my code 4-screen-compatible whenever possible though, so I normally will still treat the background area as being 480 pixels tall, if processing the extra bit doesn't cost me much.
User avatar
olddb
Posts: 188
Joined: Thu Oct 26, 2017 12:29 pm
Contact:

Re: 4 way scroll - vert scroll problem

Post by olddb »

I ended using 2 scrolls variables like advised by Tokumaru and Controllerhead's code.

Thank you. :D
...
Post Reply