News: 11 March 2016 - Forum Rules
Current Moderators - DarkSol, KingMike, MathOnNapkins, Azkadellia, Danke

Author Topic: How to do a "Ninja Gaiden" death behavior in SMB1?  (Read 1846 times)

lancuster

  • Jr. Member
  • **
  • Posts: 47
    • View Profile
How to do a "Ninja Gaiden" death behavior in SMB1?
« on: April 29, 2018, 09:07:36 am »
Who can tell how to be? I changed the values at address 5957 to A0 00, Mario froze on the screen with the death animation, but the game didn't go on. Goomba killed Mario and, standing a little, went behind the screen.
How to make Mario die just like in the Ninja Gaiden? Frozen in place > the music ended > the game continue from the beginning of the level or from the savestate.

PolishedTurd

  • Full Member
  • ***
  • Posts: 135
    • View Profile
Re: How to do a "Ninja Gaiden" death behavior in SMB1?
« Reply #1 on: April 29, 2018, 06:21:25 pm »
If I understand you correctly, you want to avoid how Mario flies up and then down when dying? So he would just stay in the exact place he died. I know how I would approach it generally... Set a breakpoint for a write to Mario's Y coordinate. I don't know what it is in the ROM, but it is probably easy to find if you watch the CPU memory while jumping. Then walk up to a guy and die. The debugger will snap, showing where the Y-coordinate register is written. You should be able to No-Op the write instruction (set to 0xEA ), so I presume it is a 2-byte change.

I could be wrong about how this ROM works, but this is the approach I would take. Post here if you try this and are still unable to get it working.

lancuster

  • Jr. Member
  • **
  • Posts: 47
    • View Profile
Re: How to do a "Ninja Gaiden" death behavior in SMB1?
« Reply #2 on: April 30, 2018, 09:02:42 am »
If I understand you correctly, you want to avoid how Mario flies up and then down when dying? So he would just stay in the exact place he died. I know how I would approach it generally... Set a breakpoint for a write to Mario's Y coordinate. I don't know what it is in the ROM, but it is probably easy to find if you watch the CPU memory while jumping. Then walk up to a guy and die. The debugger will snap, showing where the Y-coordinate register is written. You should be able to No-Op the write instruction (set to 0xEA ), so I presume it is a 2-byte change.

I could be wrong about how this ROM works, but this is the approach I would take. Post here if you try this and are still unable to get it working.
I tried, but no results. If I don't mistake, game goes on, if Mario go down, and his coordinate equal to FF. How to turn off this condition?


nesrocks

  • Hero Member
  • *****
  • Posts: 596
    • View Profile
    • nesrocks.com
Re: How to do a "Ninja Gaiden" death behavior in SMB1?
« Reply #3 on: April 30, 2018, 04:09:49 pm »
You're going to have to really understand the code and flow of the game state for the death event. There's no easy way, it's going to require good assembly knowledge.

lancuster

  • Jr. Member
  • **
  • Posts: 47
    • View Profile
Re: How to do a "Ninja Gaiden" death behavior in SMB1?
« Reply #4 on: April 30, 2018, 04:34:11 pm »
You're going to have to really understand the code and flow of the game state for the death event. There's no easy way, it's going to require good assembly knowledge.
I was able to find where it happens (addresses in RAM):

PolishedTurd

  • Full Member
  • ***
  • Posts: 135
    • View Profile
Re: How to do a "Ninja Gaiden" death behavior in SMB1?
« Reply #5 on: May 01, 2018, 08:28:39 am »
I poked around with it and got the same behavior you did, where Mario just stays on the screen. If you force the Y velocity to 0, Mario freezes when he dies, then slowly falls down the screen in a comical way. :laugh: Anyway, it looks like the sprite Y position is used not just for positioning the sprite, but also as a sort of timer or indicator for when to restart the level. So it's not as easy as I hoped.

The real challenge is that there is not enough space to add code to the ROM. I recommend starting with an expanded version of the ROM, such as this one https://www.romhacking.net/hacks/2432/. Then you have to manage bank switching, where you overwrite some code in the ROM to temporarily swap your new code into memory. I have done it, but I'm not wise enough to advise how to do it. There are others who can help, though. Search for posts from Disch and KingMike. You can also read about it at wiki.nesdev.com, although that site is rather technical for a beginner.

nesrocks

  • Hero Member
  • *****
  • Posts: 596
    • View Profile
    • nesrocks.com
Re: How to do a "Ninja Gaiden" death behavior in SMB1?
« Reply #6 on: May 01, 2018, 08:33:00 am »
Here's how I would do it:
1 - Use the expanded ROM.
2 - Find the ram address for the timer (low and high): 2 bytes
3 - JSR to your custom routine on an empty section of the ROM.
4 - Write a timer routine that branches to the game sequence when it's done.
« Last Edit: May 01, 2018, 08:41:50 am by nesrocks »

lancuster

  • Jr. Member
  • **
  • Posts: 47
    • View Profile
Re: How to do a "Ninja Gaiden" death behavior in SMB1?
« Reply #7 on: May 01, 2018, 08:41:33 am »
Here's how I would do:
1 - Use the expanded ROM.
2 - Find the ram address for the timer (low and high): 2 bytes
3 - JSR to your custom routine on an empty section of the ROM.
4 - Write a timer routine that branches to the game sequence when it's done.
But if I still have free space in the CHR-ROM is such a good option?

nesrocks

  • Hero Member
  • *****
  • Posts: 596
    • View Profile
    • nesrocks.com
Re: How to do a "Ninja Gaiden" death behavior in SMB1?
« Reply #8 on: May 01, 2018, 08:43:11 am »
I think you could transfer code from the CHR to RAM but that would still require you to have some free bytes on the ROM to write that routine, so it's just easier to use the expanded ROM.

Here's an example code out of the top of my head. This will NOT work as it is, it's for reference on how to program a timer. You need to adapt the addresses and values to the game in case, not to mention do the necessary jump to this at the player death animation state.
Code: [Select]
:mytimer ; start of the routine
LDA #$FF
STA $A2 ; reset timer low
LDA #$03
STA $A3 ; reset timer high

:loop ; loop here
DEC $A2 ; decrease timer low
BNE out ; if timer low is not zero exit, so it only decreases once this game frame

; in case timer low is zero:
LDA #$FF
STA $A2 ; reset timer low
DEC $A3 ; decrease timer high
BNE out ; timer high wasn't zero yet

; in case timer high was zero, finish
JMP $FFFF ; here you jump to the game progression (clearly not $FFFF)

:out
JMP $FFFF; here you need to find in the code where you have to jump to (clearly not $FFFF)
« Last Edit: May 01, 2018, 08:55:28 am by nesrocks »

lancuster

  • Jr. Member
  • **
  • Posts: 47
    • View Profile
Re: How to do a "Ninja Gaiden" death behavior in SMB1?
« Reply #9 on: May 13, 2018, 07:31:24 am »
nesrocks, how to remove this bug? I implemented a cheat on the player's control with a cross, without using a jump button. If you keep hold the up button, then Mario will fly up and the game will solidify on the current screen.
Here is it: http://my-files.ru/frrqcb