8x16 and whatever else unreg wants to know

Are you new to 6502, NES, or even programming in general? Post any of your questions here. Remember - the only dumb question is the question that remains unasked.

Moderator: Moderators

unregistered
Posts: 1318
Joined: Thu Apr 23, 2009 11:21 pm
Location: cypress, texas

Re: 8x16 sprite is really a 16x32 pixel image?

Post by unregistered »

tepples wrote:If the camera position has fallen below 0, then the high byte will have become 0xFF.
Thanks tepples!! :D
User avatar
Kasumi
Posts: 1293
Joined: Wed Apr 02, 2008 2:09 pm

Re: 8x16 sprite is really a 16x32 pixel image?

Post by Kasumi »

I noticed you branched if the carry was set right in the middle of the first question.
I did this because if the carry is set, we are guaranteed not below zero. (Remember that the carry will be cleared if the result of the subtraction would have been less than zero. So no need for another check.)

What you're doing now:

Code: Select all

lda CameraX+1
  bpl +abovezero
Will work, but it limits your level size. If you have a level that's $80 screens long, when you scroll to the $80th screen, the scrolling will be set to zero. This wouldn't happen by checking carry as I did, and your levels could be $FF screens long. There are some other reasons to use the carry instead of the minus bit for unsigned math, but I don't think they'd come up for scrolling.

There's not much need to change it (if your levels never get that big), but at least understanding this is important because it creates hard to find bugs. (My own scrolling had this issue at first. Actually... I think it still does... :oops: )

Edit:
This is wrong.

Code: Select all

 ;Is cameraposition > levellength-256
  lda cameraposition+1
  cmp levellength_high
  bcs +question3;If the carry is set, that means cameraposition is greater than levellength-256
;So... if it's greater, we don't fix it, if it's less we do.
 
    ;make cameraposition = levellength-256
   clc;Also, why do this? There isn't an add around.
   lda #$00
   sta CameraX+0
   lda levellength_high ;...is already set at levellength-256
   sta CameraX+1
unregistered
Posts: 1318
Joined: Thu Apr 23, 2009 11:21 pm
Location: cypress, texas

Re: 8x16 sprite is really a 16x32 pixel image?

Post by unregistered »

Kasumi wrote:
I noticed you branched if the carry was set right in the middle of the first question.
I did this because if the carry is set, we are guaranteed not below zero. (Remember that the carry will be cleared if the result of the subtraction would have been less than zero. So no need for another check.)
Ah SWEET! Thank you for your in-parenthesis help! :D
Kasumi wrote:What you're doing now:

Code: Select all

lda CameraX+1
  bpl +abovezero
Will work, but it limits your level size. If you have a level that's $80 screens long, when you scroll to the $80th screen, the scrolling will be set to zero. This wouldn't happen by checking carry as I did, and your levels could be $FF screens long. There are some other reasons to use the carry instead of the minus bit for unsigned math, but I don't think they'd come up for scrolling.

There's not much need to change it (if your levels never get that big)
Haha that's a crazy long level 128 screens
Kasumi wrote:, but at least understanding this is important because it creates hard to find bugs. (My own scrolling had this issue at first. Actually... I think it still does... :oops: )
YES. Thank you for noteing this... I hope I can remember. :oops:
Kasumi wrote:Edit:
This is wrong.

Code: Select all

 ;Is cameraposition > levellength-256
  lda cameraposition+1
  cmp levellength_high
  bcs +question3;If the carry is set, that means cameraposition is greater than levellength-256
;   so... if it's greater, we do fix it, if it's less we don't.
;   like I mean if cameraposition is greater than levellength-256... then we fix it.
;   We fix it like this  v 
    ;make cameraposition = levellength-256
;   cleared this unneeded clc away thank you Kasumi :)
   lda #$00
   sta CameraX+0
   lda levellength_high ;...is already set at levellength-256
   sta CameraX+1
User avatar
tokumaru
Posts: 12427
Joined: Sat Feb 12, 2005 9:43 pm
Location: Rio de Janeiro - Brazil

Re: 8x16 sprite is really a 16x32 pixel image?

Post by tokumaru »

unregistered wrote:Haha that's a crazy long level 128 screens
Depends on the type of the game... if it's more puzzle/obstacle oriented, then yes, 128 screens is pretty long, but in speed-oriented games 128 screens isn't so big. There aren't many games with such huge levels on the NES, but several levels in Sonic 3 (& Knuckles) were that big, and several screens tall as well.
User avatar
Kasumi
Posts: 1293
Joined: Wed Apr 02, 2008 2:09 pm

Re: 8x16 sprite is really a 16x32 pixel image?

Post by Kasumi »

like I mean if cameraposition is greater than levellength-256... then we fix it.
I know. That's the right logic, but the code you have isn't running that logic. That's what I'm saying.

Let's pretend these are our values.
Cameraposition+1 = #$03
levellength_high = #$02

Code: Select all

lda cameraposition+1
  cmp levellength_high
  bcs +question3
3-2 is not less than 0. Carry stays set. So you branch passed the code that would fix it in the wrong case.

Edit: Or it's possible I'm confused by cameraposition and camerax being separate. In which case, my apologies again.

More:

Code: Select all

 lda ladyposition+0 ;players position
  bpl +question2
That may not work either. (Unless you're doing Zelda Style scrolling, I suppose)

Lady position is at $0080. Okay. The screen will scroll with her until she gets to $0100. Then totally stop scrolling until she gets to $0180. You'd (probably) also want it to also scroll while she's traveling from $0100-$017F.

That said, I am indeed confused about cameraposition and camerax. The problem I see is that you're checking old values. At the very beginning, cameraposition is set to camerax. We then check cameraposition, but change cameraX. What this means is that if any of these conditionals changes cameraX to an out of bounds value, it won't be caught until the next frame, when cameraposition is set to cameraX again. At least that's my understanding of it.

It's actually not too big a problem with the current code, but if you change it to smooth scrolling (which may not even be your goal) it becomes a potential one. Apologies if I'm rambling about nothing. Like I said before, I tend to see things in just one way, so it's very possible you're doing something I'm not seeing.
unregistered
Posts: 1318
Joined: Thu Apr 23, 2009 11:21 pm
Location: cypress, texas

Re: 8x16 sprite is really a 16x32 pixel image?

Post by unregistered »

tokumaru wrote:
unregistered wrote:Haha that's a crazy long level 128 screens
Depends on the type of the game... if it's more puzzle/obstacle oriented, then yes, 128 screens is pretty long, but in speed-oriented games 128 screens isn't so big. There aren't many games with such huge levels on the NES, but several levels in Sonic 3 (& Knuckles) were that big, and several screens tall as well.
Oh yeah... I think I've watched my sister play Sonic 3 on our gamecube... yes, I can see how 128 screens just fly on by; thanks for pointing that out tokumaru! :D
Kasumi wrote:
like I mean if cameraposition is greater than levellength-256... then we fix it.
I know. That's the right logic, but the code you have isn't running that logic. That's what I'm saying.

Let's pretend these are our values.
Cameraposition+1 = #$03
levellength_high = #$02

Code: Select all

lda cameraposition+1
  cmp levellength_high
  bcs +question3
3-2 is not less than 0. Carry stays set. So you branch passed the code that would fix it in the wrong case.

Edit: Or it's possible I'm confused by cameraposition and camerax being separate.
cameraposition is given CameraX at the beginning... so they are the same. CameraX is always updated.
Kasumi wrote:In which case, my apologies again.

More:

Code: Select all

 lda ladyposition+0 ;players position
  bpl +question2
That may not work either. (Unless you're doing Zelda Style scrolling, I suppose)

Lady position is at $0080. Okay. The screen will scroll with her until she gets to $0100. Then totally stop scrolling until she gets to $0180. You'd (probably) also want it to also scroll while she's traveling from $0100-$017F.

That said, I am indeed confused about cameraposition and camerax. The problem I see is that you're checking old values. At the very beginning, cameraposition is set to camerax. We then check cameraposition, but change cameraX. What this means is that if any of these conditionals changes cameraX to an out of bounds value, it won't be caught until the next frame, when cameraposition is set to cameraX again.
And would that be a problem? ( I'm trying to understand my code too. :oops: )
Kasumi wrote:At least that's my understanding of it.

It's actually not too big a problem with the current code, but if you change it to smooth scrolling (which may not even be your goal) it becomes a potential one. Apologies if I'm rambling about nothing. Like I said before, I tend to see things in just one way, so it's very possible you're doing something I'm not seeing.
Yes, it's also very possible that you are alerting me to some of the problems with my code. Thank you for your help! :D
User avatar
Kasumi
Posts: 1293
Joined: Wed Apr 02, 2008 2:09 pm

Re: 8x16 sprite is really a 16x32 pixel image?

Post by Kasumi »

cameraposition is given CameraX at the beginning... so they are the same. CameraX is always updated.
Then indeed, the example stands and you have that branch wrong.
And would that be a problem? ( I'm trying to understand my code too. :oops: )
Yes. Depending on how your level data subroutines work, passing them out of bounds places to work with could crash your game at worst.

Like... CameraX is set to one tile outside the level boundary. The part of your code that draws tiles uses this value of CameraX to know what tile it's supposed to draw. It tries to load data that's not part of your level data. You could end up in an infinite loop loading whatever bytes happen to be passed the end of your level, since those bytes are not actually formatted by you to be used by that subroutine.

There are other lesser potential issues, like your scrolling would jerk backwards at the edge of the levels.
unregistered
Posts: 1318
Joined: Thu Apr 23, 2009 11:21 pm
Location: cypress, texas

Re: 8x16 sprite is really a 16x32 pixel image?

Post by unregistered »

Kasumi wrote:There are other lesser potential issues, like your scrolling would jerk backwards at the edge of the levels.
I'm happy you have had all these problems... it makes my problems seem like actual problems.
Ha ha... good night. :) :o yahning
unregistered
Posts: 1318
Joined: Thu Apr 23, 2009 11:21 pm
Location: cypress, texas

Re: 8x16 sprite is really a 16x32 pixel image?

Post by unregistered »

Kasumi wrote:
cameraposition is given CameraX at the beginning... so they are the same. CameraX is always updated.
Then indeed, the example stands and you have that branch wrong.
I am wondering if there is any book that I could buy that would teach me... it'd have a good 20 pages on scrolling. And other things about making an 8bit nintendo game. Just a generaly good book I could reread often because some days I forget things... :oops: I remember that someone said there was a snes book... maybe I could read that. Thank you Kasumi and everyone else! :)
tepples
Posts: 22708
Joined: Sun Sep 19, 2004 11:12 pm
Location: NE Indiana, USA (NTSC)
Contact:

Re: 8x16 sprite is really a 16x32 pixel image?

Post by tepples »

Google pygame book gave me a few results. If you work through one of those, you might be able to learn scrolling and other general game programming concepts in a more forgiving environment than the NES and then apply the concepts when porting your work in Pygame back to the NES.
unregistered
Posts: 1318
Joined: Thu Apr 23, 2009 11:21 pm
Location: cypress, texas

Re: 8x16 sprite is really a 16x32 pixel image?

Post by unregistered »

tepples wrote:Google pygame book gave me a few results. If you work through one of those, you might be able to learn scrolling and other general game programming concepts in a more forgiving environment than the NES and then apply the concepts when porting your work in Pygame back to the NES.
Thanks tepples! :D I followed your google search and ended up with a book in pdf form named Making Games with Python & Pygame by Al Sweigart. I read it through to page 69. (I think 69 was the last year we recieved an album release from the Beatles. :o :)) During my reading I was extreemly excited to read about their graphics using 8x8 tiles... JUST LIKE OUR NES! :D But then some disappointment surfaced as I read about the pygame tuples... but maybe that not-like-an-NESness is part of the reason Pygame is a more forgiving environment. I am enjoying the NES programming a bit more after pygame reading. It made me return to page 54 of this thread where I reread tokumaru's excellent scrolling is like a camera with a stationary level. I'm going to stay here in NES land. :)

edit:
Kasumi wrote:
cameraposition is given CameraX at the beginning... so they are the same. CameraX is always updated.
Then indeed, the example stands and you have that branch wrong.
Does this code fair better?

Code: Select all

camera_aim:

  
  
  ;determines how much to move based on the players position
  sta $ff
  
  ;set players position and cameraposition
  lda oX+0
  sta ladyposition+0
  lda oX+1
  sta ladyposition+1
  lda CameraX+0
  sta cameraposition+0
  lda CameraX+1
  sta cameraposition+1 
  
  
  ;Is our players position is greater than half the screen
  lda ladyposition+0 ;players position
  bpl +question2
  
    lda ladyposition+0
	sec
    sbc #128 ;cameraposition = ladyposition - 128.
    sta CameraX+0 
  
    lda ladyposition+1
    sbc #$00
    sta CameraX+1
  

+question2 ;problem: branch is incorrect

  ;Is cameraposition > levellength-256
  lda cameraposition+1
  cmp levellength_high
  bpl +question3;was bcs
  
    ;make cameraposition = levellength-256
	clc
	lda #$00
	sta CameraX+0
	lda levellength_high ;...is already set at levellength-256
	sta CameraX+1
    
+question3  
  
  ;Is cameraposition < 0,
  lda CameraX+1
  bpl +abovezero
      
	;cameraposition = 0
	lda #$00
    sta CameraX+1 ;cameraposition+1
    sta CameraX+0 ;cameraposition+0
    jmp +end
  
+abovezero: 

    ;move camera
    ;lda t12+0
    ;sta CameraX+0
    ;lda t12+1
    ;sta CameraX+1
  
+end  rts ;end of camera_aim
Changed the branch from bcs to bpl. We want to branch (skip the fix) for all the positive values... I think. It runs somewhat better now.

edit2.
unregistered
Posts: 1318
Joined: Thu Apr 23, 2009 11:21 pm
Location: cypress, texas

Re: 8x16 sprite is really a 16x32 pixel image?

Post by unregistered »

Ok I was able to figure this out!!! :mrgreen: :D
This is the code I need

Code: Select all

+question2 ;branch is now CORRECT!

  ;Is cameraposition > levellength-256
  sec
  lda cameraposition+1
  cmp levellength_high
  bmi +question3
It took a long time! :oops: I just needed to sit down with it and use a pencil (sp?) and most of an entire page of paper... and so now I can focus on the rest of the code on Monday! :D The code runs kind of differently now but it's not good yet.

edit.
unregistered
Posts: 1318
Joined: Thu Apr 23, 2009 11:21 pm
Location: cypress, texas

Re: 8x16 sprite is really a 16x32 pixel image?

Post by unregistered »

Kasumi wrote:More:

Code: Select all

 lda ladyposition+0 ;players position
  bpl +question2
That may not work either. (Unless you're doing Zelda Style scrolling, I suppose)

Lady position is at $0080. Okay. The screen will scroll with her until she gets to $0100.
Why will the screen scroll with her? This code is not scrolling code...it is camera movement code.
Kasumi wrote: Then totally stop scrolling until she gets to $0180. You'd (probably) also want it to also scroll while she's traveling from $0100-$017F.
Well... the comment above that code...

Code: Select all

;Is our players position is greater than half the screen
  lda ladyposition+0 ;players position
  bpl +question2
It guides the code... the bpl branches when the value of our players position is less than 128 (half the screen).
User avatar
Kasumi
Posts: 1293
Joined: Wed Apr 02, 2008 2:09 pm

Re: 8x16 sprite is really a 16x32 pixel image?

Post by Kasumi »

it is camera movement code.
I assumed you'd want the camera to center on your character. Even assuming this isn't scrolling code, the point of the camera is to have the screen scroll to it, right? And so if the camera is centered on the character, the screen would scroll to her. If you don't want that, cool. Let me know specifically what type of scrolling/camera movement you're after so I can help better.
It guides the code... the bpl branches when the value of our players position is less than 128 (half the screen)
It doesn't do that in the case I mentioned. You're assuming half the screen is always 128, but that's not true if you scroll. It's clear you know what you want to do but the code you're writing doesn't seem to be doing that. That's all I'm trying to point out. I could be misunderstanding, so here are some images.

The green and blue is the level, which the player can only see one screen worth of at a time. The white box is the camera's position in the level. This is what the player is currently seeing. i.e. what's on the screen.

The light colored box is the character. The Red line is the middle of the screen. (In between the bounds of what the player is seeing. So the middle of the white box)

So, here's the first image.
Image
The lady's x position is 14 in decimal. $000E. She's to the left of the center of the screen. We load her low byte (#$0E). Its high bit isn't set. So we would take that branch.

Here's the second image.
Image
The lady's x position is 142 in decimal. $008E. But note that the camera also moved. So she's to the left of the center of the screen. We load her low byte (#$8E). Its high bit is set. We would not take that branch.
In both images, she's to the left of the screen. In one we would take the branch, in the other we would not.

Here's both images together:
Image


(The second image is probably an impossible scenario with your current code, but hopefully you see where I'm going with them. See below for what I think will happen with the code you have now.)

Image
There's a new line. The black line represents 256. So when the lady crosses it, her low byte will be 00 again.

Note at the beginning, it works as expected. It doesn't scroll with her at the beginning, because it's branching based on her non negative low byte. Then, she reaches the center of the screen ($0080). Her low byte is now negative, and we start to scroll. Then she hits the black line($0100). At that point, her low byte is $00 again. So we stop scrolling because that's a positive low byte. The she reaches the edge of the screen. (Recall that the screen stopped scrolling with her at $00FF. Since the middle of the screen scrolls with her, this makes the right part of the level that the camera is showing $017F.) Then the camera JUMPS to her (from $00FF to $0180), because her low byte is non negative again. (Her full position is $0180).

From the player's point of view: Image

Does this make sense? This is what I think will happen with your current code.
unregistered
Posts: 1318
Joined: Thu Apr 23, 2009 11:21 pm
Location: cypress, texas

Re: 8x16 sprite is really a 16x32 pixel image?

Post by unregistered »

Kasumi wrote:
it is camera movement code.
I assumed you'd want the camera to center on your character.
Yes that would be good I think.
Kasumi wrote:Even assuming this isn't scrolling code, the point of the camera is to have the screen scroll to it, right? And so if the camera is centered on the character, the screen would scroll to her. If you don't want that, cool. Let me know specifically what type of scrolling/camera movement you're after so I can help better.
It guides the code... the bpl branches when the value of our players position is less than 128 (half the screen)
It doesn't do that in the case I mentioned. You're assuming half the screen is always 128, but that's not true if you scroll. It's clear you know what you want to do but the code you're writing doesn't seem to be doing that. That's all I'm trying to point out. I could be misunderstanding, so here are some images.

The green and blue is the level, which the player can only see one screen worth of at a time. The white box is the camera's position in the level. This is what the player is currently seeing. i.e. what's on the screen.

The light colored box is the character. The Red line is the middle of the screen. (In between the bounds of what the player is seeing. So the middle of the white box)

So, here's the first image.
Image
The lady's x position is 14 in decimal. $000E. She's to the left of the center of the screen. We load her low byte (#$0E). Its high bit isn't set. So we would take that branch.

Here's the second image.
Image
The lady's x position is 142 in decimal. $008E. But note that the camera also moved. So she's to the left of the center of the screen. We load her low byte (#$8E). Its high bit is set. We would not take that branch.
In both images, she's to the left of the screen. In one we would take the branch, in the other we would not.

Here's both images together:
Image


(The second image is probably an impossible scenario with your current code, but hopefully you see where I'm going with them. See below for what I think will happen with the code you have now.)

Image
There's a new line. The black line represents 256. So when the lady crosses it, her low byte will be 00 again.

Note at the beginning, it works as expected. It doesn't scroll with her at the beginning, because it's branching based on her non negative low byte. Then, she reaches the center of the screen ($0080). Her low byte is now negative, and we start to scroll. Then she hits the black line($0100). At that point, her low byte is $00 again. So we stop scrolling because that's a positive low byte. The she reaches the edge of the screen. (Recall that the screen stopped scrolling with her at $00FF. Since the middle of the screen scrolls with her, this makes the right part of the level that the camera is showing $017F.) Then the camera JUMPS to her (from $00FF to $0180), because her low byte is non negative again. (Her full position is $0180).

From the player's point of view: Image

Does this make sense? This is what I think will happen with your current code.
This does make sense, however on my screen it is kind of different. The camera doesn't center on the character... it still scrolls when she is past $80 and she eventually reaches the edge of the screen and appears on the other side. $80 is always middle of screen... I need to distroy that somehow. Your explaination of what my game should be doing with those images is good. I can read through your giant paragraph and understand everything... but then it all gets jumbled as I look at your graphic... this means I need to continue rereading and then stareing until it becomes unjumbled.

edit: Your graphic skills and brain skills are excellent Kasumi! :D I must reach an unjumbled state.
Post Reply