nesdev.com
http://forums.nesdev.com/

Mapping screen coordinates to nametable addresses
http://forums.nesdev.com/viewtopic.php?f=2&t=15597
Page 1 of 1

Author:  dullahan [ Tue Feb 28, 2017 5:45 pm ]
Post subject:  Mapping screen coordinates to nametable addresses

I am having difficulty mapping screen coordinates to nametable addresses (only the currently visible one). I have read http://forums.nesdev.com/viewtopic.php?f=10&t=14788 which is going the other way, but I am missing something apparently. Here is what I am currently trying. Ideas or psuedo-code are welcome!

Code:
.export __gfx_schedule_tile
.proc __gfx_schedule_tile
  fory #0, #MAX_TILE_UPDATES
    lda tile_ids, y
    cmp #255
    beq cont
    nexty
   
    ; found an empty slot
    cont:
    lda #$35
    ;lda params::arg3
    sta tile_ids, y
   
    ; compute and save address
    lda params::arg2
    add params::arg2
    sta params::arg2

    lda params::arg1
    lsr a
    lsr a
    lsr a
    add params::arg2
   
    sta tile_ppu_lo, y
   
    ; hi byte
    ;lda __gfx_visible_nametable
    ;asl a
    ;asl a

    lda #0
    add #32
    add #2
    sta tile_ppu_hi, y
   
    rts
   
  endfory
  rts
.endproc

Author:  Dwedit [ Tue Feb 28, 2017 6:43 pm ]
Post subject:  Re: Mapping screen coordinates to nametable addresses

Write this out:
0010NNYYYYYXXXXX
It's in binary. Lowest 5 bits are tile X, then the next 5 bits are tile Y, then NN is which nametable you want to write to.

So if you want column 5 row 11 of nametable 0, you get 0010000101100101, or 0x2165.

Attributes are a bit more confusing though.

Author:  dullahan [ Wed Mar 01, 2017 2:27 pm ]
Post subject:  Re: Mapping screen coordinates to nametable addresses

Thanks Dwedit. Your response has helped me get closer to a solution. It seems that there is a bug in my implementation where when given the screen pixel coords (10, 145) I calculate the address as 0x2221 when it should be 0x2201. However, calculating the name-table address for (10, 161) and (10, 113) works as expected so its not a simple remove-an-ASL. Anyone spot something I am missing here; other than it being un-optimized?

Code:
 ; compute and save address

; calc the tile column
lda screen_x
lsr
lsr
lsr
sta tmp2

; calc the tile row
lda screen_y
lsr
lsr
lsr
sta tmp1

asl
asl
asl
asl
add tmp2
sta tile_ppu_lo

lda tmp1
lsr
lsr
lsr
add #%00100000
sta tile_ppu_hi


Author:  dougeff [ Wed Mar 01, 2017 3:09 pm ]
Post subject:  Re: Mapping screen coordinates to nametable addresses

Your math is wrong.

0020nnyy yyyx xxxx

yyyy yyyy
y, 3 lsr =
000y yyyy
4 asl =
yyyy 0000

Try one more asl here...

asl
asl
asl
asl
asl
add tmp2
sta tile_ppu_lo

EDIT: actually ORA tmp2 would be better, saves you the clc, does the same thing.

Author:  dullahan [ Wed Mar 01, 2017 3:22 pm ]
Post subject:  Re: Mapping screen coordinates to nametable addresses

Thanks for the reply. Yeah, for some reason the results are a little more correct without the extra ASL. However, either way the gap remains. The first screenshot has the correct number of ASLs and the second with one less. The goal is for the top left of each of the first three crystals to have an 'A'.

Attachment:
t1.png
t1.png [ 66.65 KiB | Viewed 856 times ]

Attachment:
t2.png
t2.png [ 67.36 KiB | Viewed 856 times ]

Author:  tokumaru [ Wed Mar 01, 2017 5:45 pm ]
Post subject:  Re: Mapping screen coordinates to nametable addresses

What is this "add" opcode you're using? Unless it's an alias/macro for CLC + ADC, the fact that the code works for some coordinates but not others could be because the shifts sometimes put ones into the carry, resulting in wrong values after the additions. ORA is still a better option than adding in this case, like dougeff said.

Author:  dullahan [ Fri Mar 03, 2017 6:05 pm ]
Post subject:  Re: Mapping screen coordinates to nametable addresses

tokumaru wrote:
What is this "add" opcode you're using? Unless it's an alias/macro for CLC + ADC, the fact that the code works for some coordinates but not others could be because the shifts sometimes put ones into the carry, resulting in wrong values after the additions. ORA is still a better option than adding in this case, like dougeff said.

The add macro is from the cc65 macpack generic and is indeed CLC + ADC. I have done some more debugging and it might be a one off error in my collision checking; although, it is bizarre because the collision checks with solid blocks have been fine (using the same screen coords), but with crystals I am getting one off errors. Thanks for the reply!

Author:  Myask [ Mon Mar 06, 2017 3:52 pm ]
Post subject:  Re: Mapping screen coordinates to nametable addresses

Dwedit wrote:
Write this out:
0010NNYYYYYXXXXX
It's in binary. Lowest 5 bits are tile X, then the next 5 bits are tile Y, then NN is which nametable you want to write to.

So if you want column 5 row 11 of nametable 0, you get 0010000101100101, or 0x2165.

Attributes are a bit more confusing though.

Maybe a little. (Underscores added just to separate nybbles)
10_NNYY_YyzX_XXxw is your nametable location, with YYYyz being tile Y and XXXxw being tile X, as above.
10_NT11_11YY_YXXX is your attribute table location with which bitpair of the attribute byte chosen by the yx combo. (bits 7-6 is yx = 11, 5-4 @ 10, 3-2 @ 01, 1-0 @ 00).

Page 1 of 1 All times are UTC - 7 hours
Powered by phpBB® Forum Software © phpBB Group
http://www.phpbb.com/