News:

11 March 2016 - Forum Rules

Main Menu

Zelda 1 level text

Started by gzip, September 19, 2020, 06:41:40 PM

Previous topic - Next topic

gzip

Quote from: ShadowOne333 on September 20, 2020, 07:23:48 PM
The reason why the moved number doesn't show up is because you need a sprite there that the number can replace. Try putting $09 in the PPU Transfer for LEVEL and then make the number change, you'll see the number in red now moved two tiles to the right.

So close! Is there any way around this without having to relocate the string? Maybe a palette change for the blue tile?


ShadowOne333

Maybe the Number code could be modified to send the dash AND the number to RAM, so the dash replaces the current glitchy tile?
It's dirty, but a possibility for sure.

gzip

I changed the FF to 24 and it works, as does 62. How critical is that FF, is it going to bite me somewhere?

ShadowOne333

#23
Quote from: gzip on September 20, 2020, 07:40:44 PM
I changed the FF to 24 and it works, as does 62. How critical is that FF, is it going to bite me somewhere?
The FF I'm not sure.
From my experience, most PPU Transfers use FF as an END command, to let the code know that's where the transfer finishes, but I've seen some instances of some transfers coupled together one after the other, where they don't use FF, but the very last one does have it. Better to test it well enough in-game to be sure.

As for the 64, DON'T touch that one. That's part of a pointer table for some palette or dungeon stuff iIrc.

Just do the FF change for now (you can put the dash back there if you want), and test thoroughly in-game that it doesn't alter anything else.

Also, you might want to move the other thread you made here about the pushable rock.

gzip

So far so good. It does fill a bit dirty to modify the FF but it is a hack after all. :laugh: We'll see if it holds up. Thanks for all the help!

ultimaweapon

Quote from: The3Dude on September 20, 2020, 12:29:47 AM
This

to this



That modernized title is nice. It would be even better if you found a way to include the Triforce and the Sword in the picture.
Trust in the Heart of the Cards

abw

Quote from: gzip on September 20, 2020, 08:19:02 PM
So far so good. It does fill a bit dirty to modify the FF but it is a hack after all. :laugh: We'll see if it holds up. Thanks for all the help!
This might actually work out to be safe enough as long as you don't change certain other things. Normally the FF is used to kick out of the outer PPU transfer loop, but the code really only cares about whether the PPU address is < $8000 (that's the "BPL $A0A2") and it just so happens that the byte following the "DUNGEON 0" string appears to always have its high bit set, so you won't end up accidentally setting off an extra PPU transfer loop and getting garbled graphics.

As for positioning the number at $6827, overwriting other data is normally also bad, but in this case $6827-$6828 are dynamically updated *after* the "DUNGEON #" text is displayed, so all that happens is you get your # displayed and then the # at $6827 gets overwritten with the value the game wants to be there anyway. So... no harm no foul?

ShadowOne333

Hope you don't mind, gzip, but I also implemented the change for Redux :P
So it now says "DUNGEON-X" above the Dungeon map.
Though for me, the whole map is in the right side of the screen, since I flipped the hearts and Map stuff for Redux.

@abw, if I were to repoint just the $20,$42,$09 "LEVEL-0" $FF PPU transfer somewhere else, is it possible? And if so, what would be needed to do so?

gzip

Quote from: ShadowOne333 on September 21, 2020, 07:41:18 PM
Hope you don't mind, gzip, but I also implemented the change for Redux :P

:thumbsup: Yep, I figured as much. Glad to be able to contribute again.

abw

Quote from: ShadowOne333 on September 21, 2020, 07:41:18 PM
@abw, if I were to repoint just the $20,$42,$09 "LEVEL-0" $FF PPU transfer somewhere else, is it possible? And if so, what would be needed to do so?
It's definitely possible, and it doesn't look to even be that much work. The existing routine for copying data from ROM to RAM and that routine's associated sections of variable setup code cover $06:$8047-$06:$8106 and are pretty bloated, so you could easily optimize them to free up at least 20 bytes for new code,
Spoiler


.org $180FC
; frees up 14 bytes right here
INC $02
BNE @done_write_addr_INC
INC $03
@done_write_addr_INC:
INC $00
BNE @done_read_addr_INC
INC $01
@done_read_addr_INC:
JMP $80D9

[close]
which is more than enough space for a simple copy loop (you're already in bank 6, so no need to worry about swapping banks).
Spoiler


LDX #$0D ; or however long your new string is
@loop:
LDA $9D70,X ; or wherever else you want to read it from
STA $6780,X ; or wherever else you want to write it to
DEX
BPL @loop
RTS

[close]
After that, just update $06:$A00C to point to the start of your new string, update the level number write address at $05:$B02F, and it should all work out.

ShadowOne333

Quote from: abw on September 21, 2020, 11:17:33 PM
It's definitely possible, and it doesn't look to even be that much work. The existing routine for copying data from ROM to RAM and that routine's associated sections of variable setup code cover $06:$8047-$06:$8106 and are pretty bloated, so you could easily optimize them to free up at least 20 bytes for new code,
Spoiler


.org $180FC
; frees up 14 bytes right here
INC $02
BNE @done_write_addr_INC
INC $03
@done_write_addr_INC:
INC $00
BNE @done_read_addr_INC
INC $01
@done_read_addr_INC:
JMP $80D9

[close]
which is more than enough space for a simple copy loop (you're already in bank 6, so no need to worry about swapping banks).
Spoiler


LDX #$0D ; or however long your new string is
@loop:
LDA $9D70,X ; or wherever else you want to read it from
STA $6780,X ; or wherever else you want to write it to
DEX
BPL @loop
RTS

[close]
After that, just update $06:$A00C to point to the start of your new string, update the level number write address at $05:$B02F, and it should all work out.

Oh interesting.
You saved up quite a bit of space for new code, amazing.

I implemented the code in xkas for Redux, and while the "DUNGEON-0" text does appear, I cannot seem to be able to make the actual dungeon number to load now. It simply stays as "0" at all times. This is the code itself:


// LEVEL-X text changed to "DUNGEON-X"
org $80EC // 0x180FC
inc.b $02
bne write_INC
inc.b $03
write_INC:
inc.b $00
bne read_INC
inc.b $01
read_INC:
jmp $80D9

ldx.b #$09 // New text length
loop:
lda.w $9D70,x
sta.w $6780,x
dex
bpl loop
rts
fillto $8109, $EA

org $A00C // 0x1A01C
dw $83C0 // New string for Dungeons
//org $A02E // 0x1A03E
// dw $83C0 // New string for Dungeons

//org $9D04 // $19D14 - Original location
org $83C0 // 0x183D0
db $20,$56,$09 // Originally $20,$56,$07
db "DUNGEON-0" // Originally "LEVEL-0"
db $FF

bank 5;
// Move Dungeon numeral two tiles to the right (DUNGEON-X)
org $B02F // 0x1703F
    sta $6827 // Originally STA $6825


I tried looking around in RAM around $6780 up to $6840, but I couldn't find anything, other than "LEVEL-X" still being loaded in RAM at $681F.
Did I do something wrong?

abw

Yeah, you missed a few things - I was just sketching the outline of one possible solution and left it up to you to fill in the details :P.

Here's a fully-implemented version including ASM source code.

ShadowOne333

#32
Quote from: abw on September 22, 2020, 07:36:35 PM
Yeah, you missed a few things - I was just sketching the outline of one possible solution and left it up to you to fill in the details :P.

Here's a fully-implemented version including ASM source code.

Oh nice!
I just downloaded the source and tried it out myself.
However, I'm having issues with this in particular:

!level_string_ram_addr = $6C80

The issue is that:
1) xkas doesn't recognize "!", it can only do defines for what I know. So I ditched it and made a "define" for it.
2) Using $6C80 directly in place of "!level_string_ram_addr" makes the game behave in a really glitchy way as soon as you get into the File Select menu. I changed the level_string+11 to $6C8B as well, but it still glitches out the entire game in Redux.

abw

Quote from: ShadowOne333 on September 23, 2020, 12:48:11 PM
1) xkas doesn't recognize "!", it can only do defines for what I know. So I ditched it and made a "define" for it.
That *is* a define :P. I was actually using Asar (a fork of xkas), and as far as I can tell based on their respective documentation xkas has the exact same syntax for defines, so I don't know why it wouldn't recognize "!level_string_ram_addr = $6C80" as a define.

Quote from: ShadowOne333 on September 23, 2020, 12:48:11 PM
2) Using $6C80 directly in place of "!level_string_ram_addr" makes the game behave in a really glitchy way as soon as you get into the File Select menu. I changed the level_string+11 to $6C8B as well, but it still glitches out the entire game in Redux.
How does the patch generated by xkas differ from the .ips I provided? What happens if you apply it to a clean ROM? I guess I should have also mentioned that I was using the US PRG0 dump as my base, so it's possible there could be a conflict with a different dump or with any other changes you've made for Redux, in which case you'll have to resolve those conflicts (which would probably just mean picking a different address for level_string_ram_addr or level_text, but could potentially be almost anything).

ShadowOne333

I found the issue. I had this:
lda.w $8028,x
lda.b $00


Instead of this:
lda.w $8028,x
sta.b $00


Now the game boots.
However, I did find another issue. It seems that the Automap hack is colliding in some form with this implementation.
The Automap seems to be filling sporadically and randomly, like if I go up, normally it should just make the screen you are visible in the Automap, but with this implemented, suddenly I get like 4 screens appearing at once in the Automap tiles. The whole code for it is here:
https://github.com/ShadowOne333/The-Legend-of-Zelda-Redux/blob/master/code/automap.asm

And I noticed it does some writes into $6C00 in RAM, so maybe some things are colliding there.

Aside from that, I noticed that the code you have in .asm file has one byte that differs from the IPS.
In the .asm file, you have the following:
jsr copy_level_text
But apparently, in the IPS this very part has a JMP ($20) in its place, instead of JSR ($4C)
jmp copy_level_text

Which one of the two is it? JMP or JSR?

abw

Quote from: ShadowOne333 on September 23, 2020, 06:01:05 PM
I found the issue. [...]
Ha, yes, that would definitely cause some problems - glad to see you got it sorted out :thumbsup:!

Quote from: ShadowOne333 on September 23, 2020, 06:01:05 PM
However, I did find another issue. It seems that the Automap hack is colliding in some form with this implementation.
Looking at that Automap source code, Automap writes a bunch of code to previously unused space starting at 0x19D80, which is where I stuck the new "DUNGEON-0" string. Switching my "org $19D80" to someplace else in bank 6 that still has at least 13 bytes of free space in your hack should be enough to fix that conflict.

Quote from: ShadowOne333 on September 23, 2020, 06:01:05 PM
In the .asm file, you have the following:
jsr copy_level_text
But apparently, in the IPS this very part has a JMP ($20) in its place, instead of JSR ($4C)
jmp copy_level_text

Which one of the two is it? JMP or JSR?
It should definitely be JSR, but if you consult an opcode chart, I think you'll find that you've got things backwards and $20 is the opcode for JSR while $4C is the opcode for JMP, so the .asm and the .ips files are both saying the same thing.

ShadowOne333

Oh I forgot to say, I did move the location of the DUNGEON-0 text to around 19DA0, so it didn't overwrite code there. But the issue still happens even with the text moved to proper free space.

abw

Okay, in that case my next guess is 0x18099 - I see Automap changes that to a JMP $FFC0, which conflicts with my patch rearranging 0x18095-0x1809A to save space by avoiding duplication with code starting at 0x180AF. You'll need to do some further optimization to free up space for the "JSR copy_level_text", but that should be pretty easy since (as I said earlier) the original code is pretty bloated.

Any decent IPS patch conflict finder should have been able to point both of those conflicts out immediately.

ShadowOne333

Oh you're right, I completely overlooked that part of the Automap code.
I did look at it with Advanced Patch Conflict Finder, and indeed, there's a conflict in $18085-$1808B due to a collision between the repoint code and Automap, Automap's being the jmp $FFC0 that should go at $18089.

I tried doing some JMPs and JSRs to $83C0 (free space) to try to make the code there without having to worry about space, but I can't seem to place the Automap's 'jmp $FFC0' in a good enough way to make it work without glitching stuff to oblivion lol.

In the meanwhile, I'll keep the old method of having DUNGEON-0 without the final FF in the original location.
Still, I'll post the xkas code I had here for reference sake.

//*************************************
// Change "LEVEL-0" to "DUNGEON-0"
//*************************************

define level_string_ram_addr $6C80

// LEVEL-X text changed to "DUNGEON-X" for text that appears above the Dungeon maps
// Re-arrange existing code to free up space for a JSR to new code
org $8085 // 0x18095
inc.b $11
clear_13_and_RTS:
lda.b #$00
sta.b $13 // jmp $FFC0 for Automap goes here originally
rts

// Original code
ldx.b #$00
lda.w $8028,x
sta.b $00
inx
lda.w $8028,x
sta.b $01
jsr $80C6 // Set up destination start ($02) and end ($04) variables
jsr $80D7 // Read data from ($00) and write it to ($02) through to ($04)
// JSR to call new code and then BRA to continue old code
jsr copy_level_text
bmi clear_13_and_RTS

// Optimize existing code to free up space for a new routine
org $80EC // 0x180FC
inc.b $02
bne write_INC
inc.b $03
write_INC:
inc.b $00
bne read_INC
inc.b $01
read_INC:
jmp $80D9

// New routine to copy the "DUNGEON-X" string from ROM to cartridge RAM
copy_level_text:
ldx.b #$0C // New text length, including PPU address and byte length
// 12 = Length of PPU address (2) + text length (1) + text (9) + string end token (1) - 1 (since we're looping until X == -1)

loop:
lda.w dungeon_text,x
sta.w {level_string_ram_addr},x // $6780
dex
bpl loop
rts
fillto $8109, $EA

// The old "LEVEL-0" string still gets copied to RAM $681C, but is no longer used
org $9D04 // $19D14 - Original location
db $20,$56,$07 // Originally $20,$56,$07
db "LEVEL-0" // Originally "LEVEL-0"
db $FF

// String bytes
org $9D90 // 0x19DA0, Free Space
//dungeon_text:
db $20,$56,$09 // Originally $20,$56,$07
db "DUNGEON-0" // Originally "LEVEL-0"
db $FF

// Update pointer to new string for Dungeons
org $A00C // 0x1A01C
dw {level_string_ram_addr} // Originally $681C

bank 5;
// Move Dungeon numeral two tiles to the right (DUNGEON-X)
org $B02F // 0x1703F
// Update level number write address
sta.w $6827 // Originally STA $6825

abw

Quote from: ShadowOne333 on September 24, 2020, 01:33:19 PM
I tried doing some JMPs and JSRs to $83C0 (free space) to try to make the code there without having to worry about space, but I can't seem to place the Automap's 'jmp $FFC0' in a good enough way to make it work without glitching stuff to oblivion lol.
Or you could just free up some more space :P. I've updated the linked asm + patch to rewrite that entire section of code to free up 48 bytes and leave 0x18099 in its original state, so Automap's JMP won't conflict any more; even after fitting in the new "DUNGEON-0" text (so it no longer consumes 13 bytes of free space at 0x19D80) and the code for copying it, there's still an additional 24 bytes of free space left, so if you wanted to you could move some of Automap's $FFC0 code back to bank 6 and use up less free space from the fixed bank.