Page 3 of 8

Posted: Mon Sep 05, 2005 1:07 pm
by Bregalad
Oh, I see. But it will be on exact diagonals, right? Since your speed is fixed... I say that because, in a platformer, you can, really, move in any combination of vertical and horizontal speeds. I guess it's best described as an "all-way scroller" then an "8-way scroller"! =)
Well, in a platformer you basically don't directly control the vertical position, but only while jumping, falling, etc...
But the way you did before worked as you wanted, didn't it? That thing I wrote is more usefull if you do want to attack and keep moving, and I can see this is not your case. Not that it won't work for you or anything, you can do what you think is best, and I think your new way will work just as well! =)
Yeah, it works fine.
I didn't quite understand this... you can move towards one direction while facing another? I've never seen a game do this... Well, at least not in the NES, where we have limited controls... In newer games it is quite common beeing able to walk/move in one direction while shooting at the other and all...
Anyway, I just think I didn't understand what you said! =)
Well, the player just face a direction that is pressed, the first one detected. If you're walking diagonally, I didn't make my player's sprite have 8 frames, so of couse you can face left then go up-left, or face up then go up-left to. This will make the player moving in the same direction, but not facing exactly the same direction.

Posted: Mon Sep 05, 2005 1:12 pm
by Celius
Okay, I have to say something. I only did the Vblank wait because When I moved my player without it, She moved like 10000 miles an hour, and you saw 3 frames with her in it as she crossed the screen. That was stupid. How do you fix that? And I got the impression that I was using excuses saying that no one explained things well from you bregalad. I quote you "tepples and Disch wrote their posts while I was writing mine. So you have different approches at answering your questions. No excuse now ;)." Thank you for being so supportive, Bregalad, I appreciate it. Like now I HAVE to know how to do background collision, because there's no excuse for me now. I actually am still trying to understand this. I was going to mention that I don't know how to do RLE compression, and I just have 1 screen levels that were made with NSA. So I don't have a map in ram. Yeah, I'm at kind of an akward stage here, because I know all of 6502, and I know what the NES can do, but some how I just can't come up with good code. And everyone thinks that I'm some newbie who doesn't really know anything, and has to make new forums that end up being 9 pages long about every aspect of the NES, and I get forwarded to the 6502 for newbies documents. I really do need to get better at anding things and oring things, because I never really do that stuff. Well, I'll understand this some day, I'll come back and ask about it when I'm not so tired and in such a crap mood. so yeah, bye.

Posted: Mon Sep 05, 2005 1:23 pm
by -tokumaru-
Bregalad wrote:Well, in a platformer you basically don't directly control the vertical position, but only while jumping, falling, etc...
Yes, yes! Gravity (well, simulated gravity) takes care of positive Y speed, if there isn't anything (ground, platform, object, etc) right below the player. In my game, for the player to jump I do nothing more than just set the Y speed to a big negative number (of course I check if the player isn't already in the air -jumping or falling-, or I would have multiple jumps!), wich will cause the player to suddenlly move up, and deaccelerate back as an effect of the simulated gravity. It works quite well.
Well, the player just face a direction that is pressed, the first one detected. If you're walking diagonally, I didn't make my player's sprite have 8 frames, so of couse you can face left then go up-left, or face up then go up-left to. This will make the player moving in the same direction, but not facing exactly the same direction.
Oh, I got it now, you have 8 directions but graphics for 4 of them, so diagonals use the same graphics as when you move to the sides. So, there are 8 directions in wich you can move, but 4 directions in wich you can do the other stuff (face, attack)... did I get it right now?

Posted: Mon Sep 05, 2005 2:52 pm
by tokumaru
Celius wrote:Okay, I have to say something. I only did the Vblank wait because When I moved my player without it, She moved like 10000 miles an hour, and you saw 3 frames with her in it as she crossed the screen. That was stupid. How do you fix that?
That must be because you checked for the keypress multiple times during the same frame. Maybe you could undo that "wait two vblanks thing" and do the following:

-after you're done with all the calculations set a "frame done" flag;
-loop forever while this flag is set;
-in your NMI routine, you check if this flag is set. If it is, draw what you need to the PPU;
-clear the "frame done" flag and return from the NMI;

This will cause your loop to end, and the program will proced to the calculations for the next frame. This way your logic will only run once per frame, and the player will not move ridiculously fast! =)
And I got the impression that I was using excuses saying that no one explained things well from you bregalad. I quote you "tepples and Disch wrote their posts while I was writing mine. So you have different approches at answering your questions. No excuse now ;)." Thank you for being so supportive, Bregalad, I appreciate it. Like now I HAVE to know how to do background collision, because there's no excuse for me now. I actually am still trying to understand this. I was going to mention that I don't know how to do RLE compression, and I just have 1 screen levels that were made with NSA. So I don't have a map in ram.
NSA will take only care of the graphics. You must have a map in memory where you can check what is solid and what is not. If your game is REALLY simple, you can use NSA's output for that, but generally you won't. In fact, you should draw to the screen based on your RAM/ROM map, and avoid NSA alltogether. You said it is a pacman-like game. So you probably just have two cases: wall and no wall. Read your map and draw the appropriate tiles to the screen. You don't need NSA at all.

NSA is good when you have to draw that complex title/intro screen scene, where there is no actual logic behind, it's just a bunch of unrelated tiles placed in a order with no logic at all, so it would be difficult to draw it directlly with code.
Yeah, I'm at kind of an akward stage here, because I know all of 6502, and I know what the NES can do, but some how I just can't come up with good code. And everyone thinks that I'm some newbie who doesn't really know anything, and has to make new forums that end up being 9 pages long about every aspect of the NES, and I get forwarded to the 6502 for newbies documents. I really do need to get better at anding things and oring things, because I never really do that stuff. Well, I'll understand this some day, I'll come back and ask about it when I'm not so tired and in such a crap mood. so yeah, bye.
I don't think you're stupid or a newbie. In fact, I admire you. You are persistent and a person of action. I, for instance, am always talking about game logic and design, but it's all theory. I talk and think a lot, but have actually coded very little. But you, you go straight to the action, even not knowing how you're going to do some things, but you go and just try. That's why I admire you.

I probably have had much more contact with the game programming world than you have, but you're probably going to have much more to show as result of your work in the end.

I know you understand 6502 assembly, programming logic and you're not a newbie. The only problem is you're not thinking as a GAME programmer yet, you're still thinking in a very specific way, and refuse to find global solutions to your problems. You must not worry about "how will the player move correctly" and disregard completely all other things (as you did with the two vblank thing), you must worry about "how will ALL objects move correctly at once" wich is what happens in a real game. No enemy waits for the player to walk. Enemies walk at the same time as the player does.

Eventually you'll be used to thinking as a game programmer instead of as a game player. But KEEP ASKING, and reading carefully what we say to you! You must have contact with it, even if you don't understand everything we say.

-tokumaru-

Posted: Tue Sep 06, 2005 9:31 am
by Bregalad
-tokumaru- wrote: Yes, yes! Gravity (well, simulated gravity) takes care of positive Y speed, if there isn't anything (ground, platform, object, etc) right below the player. In my game, for the player to jump I do nothing more than just set the Y speed to a big negative number (of course I check if the player isn't already in the air -jumping or falling-, or I would have multiple jumps!), wich will cause the player to suddenlly move up, and deaccelerate back as an effect of the simulated gravity. It works quite well.
You man putting a value ($f8 for example) in vertical speed variable, so make the player goes up, then decrease it regulary, to eventually stop the decreasing stuff at the maximum value ($08 for exapmple) so the player won't be falling faster more and more, right ? Does it looks good ?
Oh, I got it now, you have 8 directions but graphics for 4 of them, so diagonals use the same graphics as when you move to the sides. So, there are 8 directions in wich you can move, but 4 directions in wich you can do the other stuff (face, attack)... did I get it right now?
Yeah, you got it. You'll show when the game will be released, anyway (I hope !).

Celius : You definitely needs some more experience at programming, but scince you got all basic stuff about coding, it would be easier. Just keep how a main game structure should optimally work, I actually also had problems like this stuff (however not at that point) in my beginning. I think a doccument should be written to hanlde optimal programming for begineers, instead of just technical stuff.

Posted: Tue Sep 06, 2005 2:46 pm
by blargg
Yes, yes! Gravity (well, simulated gravity) takes care of positive Y speed, if there isn't anything (ground, platform, object, etc) right below the player.
I swear that in games like Castlevania, when you are standing on something it's still increasing your Y velocity (up to some maximum) so that when you walk off a platform, you fall very quickly.

Posted: Tue Sep 06, 2005 3:51 pm
by tokumaru
Bregalad wrote:You man putting a value ($f8 for example) in vertical speed variable, so make the player goes up, then decrease it regulary, to eventually stop the decreasing stuff at the maximum value ($08 for exapmple) so the player won't be falling faster more and more, right ? Does it looks good ?
Hum.. not exactly... It works pretty much like in real life. Your feet give you the impulse to go up, but you deaccelerate because of gravity and get back down. In the game I just give the player that initial impulse. Gravity will deaccelerate him, and he will eventually stop and begin to fall, still under the effect of gravity. I don't specifically bring the player down after a jump, the game gravity does that. It looks really nice, very Sonic'ish or Mario'ish. I don't really know how do these games handle their jumping or running physics, but this way works very well.
Yeah, you got it. You'll show when the game will be released, anyway (I hope !).
Well, I hope to see it soon! Sounds promissing! =)

Posted: Tue Sep 06, 2005 3:54 pm
by tokumaru
blargg wrote:I swear that in games like Castlevania, when you are standing on something it's still increasing your Y velocity (up to some maximum) so that when you walk off a platform, you fall very quickly.
That is true! Castlevania brings you down very quickly! But then again, I think the (lack of?) physics in Castlevania games (at least the older ones) suck. It feels very unrealistic for the kind of game.

Posted: Tue Sep 06, 2005 7:02 pm
by Celius
I'm having some trouble understanding how to use this RLE compression methode, and yes, this is a very good one that our friend Disch told me about earlier. Observe:

map: .db $01,$00,$8C,$11.

That defines one line of tiles like with the right asm decompression code like so:

If high bit of first number is on, take the low byte, and place the following tile number to the name table that many times. If the high bit is off, then take the low byte, and write these following tile numbers to the name table as noncompressed tiles. Understand? Well, if you don't, here's a better explanation:

map:
.db $01 ;since the high bit is off, take the low byte
; and since it is 1, we leave the next 1
; hex number as an uncompressed tile #
.db $00 ;put tile #0 on the 1st tile of the name table
.db $8C ; since the high bit is on, take the low byte
; and since it is C (13), we take the next hex value
; and use it as a tile #, and paste it to the name table
; 13 times
.db $11 ; put to name table 13 times.

Is that too hard to understand? I don't think so. How could you decompress that? I was thinking some thing like this:

Code: Select all


loadmap:
          take the high byte of a value
          if it's 8
          take the low byte
         (let's just say that the letter L= Low byte for this next part)
          store the next value into the NT (name table) L times

ifzero:
          take the high byte of a value
          if it's 0
          take the low byte
          store the next L bytes to the NT as uncompressed tiles
          Do this for all bytes

The problem is I don't know how I could just have it automaticly check every byte for that kind of thing. Don't you have to do that for each and every byte?

Posted: Tue Sep 06, 2005 7:06 pm
by Celius
Oh, and I'm sorry, which one was the frame done flag again? :?

Posted: Tue Sep 06, 2005 8:55 pm
by tokumaru
Celius wrote:Oh, and I'm sorry, which one was the frame done flag again? :?
This is some flag YOU should set up, it doesn't exist. But did you understand the concept?

You have to declare a variable, call it whatever you want: "frame done", "waiting vblank", "draw frame"... no matter the name it means the same thing: if it is set (has a value of, say, 1) it means you finished all calculations (moved the players, checked for collisions, etc, etc) and must now wait for vblank to draw the frame.

It goes something like this:

Code: Select all

MAIN_LOOP:
	;here you check for keypresses,
	;move the objects, check for
	;collisions and everything else;

	;Now you've finished calculating,
	;and would like to update the graphics
	;of the player, the playfield, etc,
	;but you must wait for vblank.
	;The most reliable way of detecting
	;vblank is to use NMI's.

	;So, you set this flag to keep you
	;waiting while the NMI does not come.

	LDA #1
	STA FRAME_DONE

WAIT_NMI:
	LDA FRAME_DONE
	BNE WAIT_NMI

	;When you get here the new frame
	;will have been drawn, and you can
	;start calculating the next one.

	JMP MAIN_LOOP

NMI:
	;Here should be the code that renders
	;your new frame to the screen.

	;Clear the flag and return from the interrupt.

	LDA #0
	STA FRAME_DONE

	RTI
If you do it like this there is no way your player will move more than 1 pixel per frame.

EDIT: Of course you need to have NMI's enabled for this to work (bit 7 of $2000, I think). I heard the folks in here saying that NMI's are a much better way to "detect" vblank than the "traditional" way (checking bit 7 of $2002), since you could check the bit at the end of vblank (after all, you're still in vblank), and your drawing code could go over the vblank time and cause crap to show up on the screen. With NMI's you always assure you got full vblank time ahead.

Posted: Wed Sep 07, 2005 8:57 am
by Bregalad
Well, it's a way so see things, but not the only way.
Final Fantasy does call a subroutine that will enable NMI flag, then jump forever, while the NMI will disable it's onw flag, pull the 3 pushed value (processor status, programm counter old adress), then return from the soubroutine that looped forever before the NMI.
This way of doing things is not worse than the usual way, I thing, but still interessting.
All Konami games seems to constantly add a number to another out-of NMI, and *all* the game logic will be done in NMI. This is surely harder to do, and is overall pretty stupid (is the added number a reliable way to get random numbers ??).
Some games, such as Battletoads and NES Snake 2 seems to constantly do calcutions, and never do just waiting. I don't know how they work, trough, if the logic is done during or out of the NMI.

I think overall the best way is to have an NMI routine handle all the basic and very common graphic stuff, while all the rest of game logic would be done out of NMI. Doing everything in NMI is hard and overcomplicated, and doing everything out of NMI will waste a lot of ROM to do very common PPU stuff.

Posted: Wed Sep 07, 2005 9:46 am
by tokumaru
Bregalad wrote:Some games, such as Battletoads and NES Snake 2 seems to constantly do calcutions, and never do just waiting. I don't know how they work, trough, if the logic is done during or out of the NMI.
I'm working on a project where I never stop calculating... But I keep setting flags to tell what I can copy when the NMI comes. This game is drawn in "columns", and I keep a counter that tells how many columns I have ready for drawing. The NMI routine draws them and decrements the counter. But I nevert stop calculating columns. I don't think this could work for a plataformer though...
I think overall the best way is to have an NMI routine handle all the basic and very common graphic stuff, while all the rest of game logic would be done out of NMI. Doing everything in NMI is hard and overcomplicated, and doing everything out of NMI will waste a lot of ROM to do very common PPU stuff.
I plan on doing like I said in my platformer, but of course it is not the only way. The advantage is, if you by any chance go over the usual calculation time (a very complex frame, maybe), the game will slow down a little, like in Megaman for example, but you'll never risk drawing to the PPU at the wrong time.

Posted: Wed Sep 07, 2005 11:20 am
by Bregalad
Yeah, I'll use a method very close to your myself. I used the FF one earlier, but it overall shucked when precision for PPU writes were needed (no PPU string buffer !) -> waste of bytes, slower and harder to programm

I can just not know what the game can't stop calculating, exept maybe random number or a $4011 wave (like Battletoads... exept this ones also don't stop calculating even if there is nothing played in $4011). It is just senseless to me.

Posted: Wed Sep 07, 2005 2:24 pm
by Celius
Thanks. Any ideas about loading the map data???