The revolution begins now

View previous topic View next topic Go down

The revolution begins now

Post by Puzzledude on Sun 19 Feb 2017 - 16:16

After some thinking here's what I've been testing and Conn helped me out with the code. Now I can make 1 Rom to be able to load more than 1000 indoor rooms (but not at once). Here is how if anyone is interested in this:

At PC addresses 8745 and 883E there is this code for global room pointers:
BF 01 80 1F 85 B8 BF 00 80 1F

If you change this to
BF 01 80 3F 85 B8 BF 00 80 3F
you can repoint the data to anywhere else, in this case 1MB further, but what if you could load both.

First I made a jump at 8745 and 883E:
22 00 80 2A EA EA EA EA EA EA
jumps to 150000 (rom must be 4MB obviously)

code at 150000 is now this:
the code I made was this: at 150000
Code:
AF 41 F3 7E , = load ram for boomerang
29 FF 00    ; = isolate the first byte
C9 01 00    , = compare to 01 (is have boomerang)
F0 0B       , = branch $0B bytes if equal (to new pointers)
BF 01 80 1F , = if not equal (no boomerang)
85 B8       ,   load old pointers
BF 00 80 1F ,
6B          , = end of old pointers
BF 01 80 3F , = branch here if boomerang
85 B8       ,
BF 00 80 3F ,
6B          , = end of new pointers
This will load the old rooms if you don't have the boomerang. But if you do, then it will load new pointers (1MB further as sample) and will/can thus load new 295 rooms. I tested this out and it works. Of course the indoor sprites, items and header is not done yet, but is doable the same way. There is also a thing with entrance compatibility, but too can be done/fixed to be compatible between the 2 sets of dungeons (houses and caves don't really need the alternative rooms). There is also the issue with torches and blocks, but this still can be adopted to either not be used if multiple sets of dungeons are loaded, or adopted (simply use a remodel room for the other set) instead of brand new room.

For 3 sets of dungeons the code is this:
(also works, tested; but only for dungeon objects for now):
for 3 sets of dungeons:

Code:
150000:
AF 41 F3 7E , = load ram for boomerang
29 FF 00    , = isolate the first byte
C9 01 00    , = compare to 01 (is have boomerang)
F0 22       , = branch $22 bytes if equal (to dun-3)
AF 57 F3 7E , = load ram for moonpearl
29 FF 00    , = isolate the first byte
C9 01 00    , = compare to 01 (is have moonpearl)
F0 0B       , = branch $0B bytes if equal (to dun-2)
BF 01 80 1F , = dun-1 pointers
85 B8       ,
BF 00 80 1F ,
6B          ,
BF 01 80 3F , = dun-2 pointers
85 B8       ,
BF 00 80 3F ,
6B          ,
BF 01 80 5F , = dun-3 pointers
85 B8       ,
BF 00 80 5F ,
6B          ,
This will now load dungeon-1 rooms by default, dungeon-2 rooms if moopearl, and dungeon-3 rooms if boomerang.



And even for 4 sets of dungeons:
(note this now equals to 1200 rooms possible, but only 295 at one moment):

Code:
150000:
AF 41 F3 7E , = load ram for boomerang
29 FF 00    , = isolate the first byte
C9 01 00    , = compare to 01 (is have boomerang)
F0 39       , = branch $39 bytes if equal (to dun-4)
AF 57 F3 7E , = load ram for moonpearl
29 FF 00    , = isolate the first byte
C9 01 00    , = compare to 01 (is have moonpearl)
F0 22       , = branch $22 bytes if equal (to dun-3)
AF 53 F3 7E , = load ram for mirror
29 FF 00    , = isolate the first byte
C9 02 00    , = compare to 02 (is have mirror)
F0 0B       , = branch $0B bytes if equal (to dun-2)
BF 01 80 1F , = dun-1 pointers
85 B8       ,
BF 00 80 1F ,
6B          ,
BF 01 80 3F , = dun-2 pointers
85 B8       ,
BF 00 80 3F ,
6B          ,
BF 01 80 5F , = dun-3 pointers
85 B8       ,
BF 00 80 5F ,
6B          ,
BF 01 80 64 , = dun-4 pointers
85 B8       ,
BF 00 80 64 ,
6B          ,

The implications here are incredible: you can make a huge amount of dungeon rooms, you can make "dinamic" dungeons, which can "change" during the game, you can make a dungeon with the "time effect", ie "past" and "future" or even with "present" and thus in 3 time states; you can make the dungeon "change" while you are in the dungeon.

You can also "swap" between global dungeons, if the RAM is set to something which can be swapped, like light/dark world. You can thus load 295 rooms in light world, and another 295 in dark - while the entrances are compatible, since you can never enter an entrance in the light world, when in dark world. Thus a dinamic swap between 2 sets of dungeons with 295 rooms in each world.
avatar
Puzzledude
Elite ROM Hacker
Elite ROM Hacker

Since : 2012-06-20

Back to top Go down

Re: The revolution begins now

Post by Trovsky on Sun 19 Feb 2017 - 16:29

Neat, I'll add a note to this patch in the first post in the Zeldix Magic thread.

Trovsky
Rank: Blacksmith
Rank: Blacksmith

Since : 2014-04-10

Back to top Go down

Re: The revolution begins now

Post by Trovsky on Sun 19 Feb 2017 - 16:34

I think I'll have a bit of trouble with the dynamic dungeons part. This is because you are executing arbitrary code that can change the dungeon in any way.

Trovsky
Rank: Blacksmith
Rank: Blacksmith

Since : 2014-04-10

Back to top Go down

Re: The revolution begins now

Post by Puzzledude on Sun 19 Feb 2017 - 16:39

Yes, I actually never tested what happens if you are indoors, however if I now think about, it should not be allowed, since like you said if you change the palette and the gfx set, it will not reload correctly, if you are indoors. So when the swap appears you need to be in a "compatible" dungeon or outside.
Again the light/dark world comes to mind, since this automatically means the correct reload anytime and swaps back and forth (if the item is given, you can not swap "back"), while the entrance problem is also autofixed

Not sure how the editor could handle editing 2 (or more) sets of rooms, but if it can, then the word magic in Zeldix Magic would really fit. Otherwise this is doable in hex though and is similar with merging dungeons into one rom.
avatar
Puzzledude
Elite ROM Hacker
Elite ROM Hacker

Since : 2012-06-20

Back to top Go down

Re: The revolution begins now

Post by Puzzledude on Sun 19 Feb 2017 - 17:07

Here the light/dark world adopt:
Code:
light/dark world variant

(very useful, since it is entrance compatible and swaps dun-1 and dun-2, when you swap the light/dark world). So LW now holds 295 rooms (while having the same amount of entrances) and the DW has 295 rooms (also same amount of entrances).

RAM
7EF3CA
holds the LW/DW info
if it is 00, then you are in LW
if it is 40, then you are in DW


AF CA F3 7E , = load ram for light/dark world
29 FF 00    ; = isolate the first byte
C9 40 00    , = compare to 40 (is dark world)
F0 0B       , = branch $0B bytes if equal (to new pointers)
BF 01 80 1F , = if not equal (then LW)(load dun-1)
85 B8       ,
BF 00 80 1F ,
6B          ,
BF 01 80 3F , = branch here if dark world (load dun-2)
85 B8       ,
BF 00 80 3F ,
6B          ,



AF CA F3 7E 29 FF 00 C9 40 00 F0 0B BF 01 80 1F 85 B8 BF 00 80 1F 6B BF 01 80 3F 85 B8 BF 00 80 3F 6B

tested (works)
avatar
Puzzledude
Elite ROM Hacker
Elite ROM Hacker

Since : 2012-06-20

Back to top Go down

Re: The revolution begins now

Post by Trovsky on Sun 19 Feb 2017 - 20:09

Puzzledude wrote:Not sure how the editor could handle editing 2 (or more) sets of rooms, but if it can, then the word magic in Zeldix Magic would really fit. Otherwise this is doable in hex though and is similar with merging dungeons into one rom.

If I understand correctly, the easiest way to allow compatibility is to simply let the enduser specify where to read the room set. It's a similar concept with the monologue editor. The user has the option to enter a custom location to have the editor read.

Trovsky
Rank: Blacksmith
Rank: Blacksmith

Since : 2014-04-10

Back to top Go down

Re: The revolution begins now

Post by Puzzledude on Mon 20 Feb 2017 - 6:56

If I understand correctly, the easiest way to allow compatibility is to simply let the enduser specify where to read the room set. It's a similar concept with the monologue editor. The user has the option to enter a custom location to have the editor read.
This should work. Since the pointers are 3C0 long. So it just needs to know where the 2 (or more) sets are at. In my test Rom I've put them to +1MB and +2MB, but they can be anywhere. Default set is at F8000, but this too can be changed.

Of course this is only for dungeon objects. Dungeon sprites, items, header info, chest definitions and pit damage also needs to go through the same "expansion process" for this to work.
avatar
Puzzledude
Elite ROM Hacker
Elite ROM Hacker

Since : 2012-06-20

Back to top Go down

Re: The revolution begins now

Post by Puzzledude on Wed 22 Feb 2017 - 12:51

The revolution continues:

with this Entrance dependent loading of global dungeons we can achieve "unlimited" rooms:

Code:

2 sets of dungeons, entrance dependent


this works:
at 8745, and 883E, write:
22 00 80 2A EA EA EA EA EA EA
jumps to 150000,



at 150000,

AD 0E 01    , = load ram for entrances
29 FF 00    ; = isolate the first byte
C9 01 00    , = compare to 0001 (16bit=2bytes)(is entrance 01= your house)
F0 0B       , = branch $0B bytes if equal (to new pointers)
BF 01 80 1F , = if not equal (not your house) load old dungeons
85 B8       ,
BF 00 80 1F ,
6B          ,
BF 01 80 3F , = branch here if your house entrance
85 B8       ,
BF 00 80 3F ,
6B          ,


AD 0E 01 29 FF 00 C9 01 00 F0 0B BF 01 80 1F 85 B8 BF 00 80 1F 6B BF 01 80 3F 85 B8 BF 00 80 3F 6B

this means: load dungeons-1 by default, but only load dungeons-2 if you enter in the entrance 01 (your house).

tested (works)



-------------------------------------------


2 sets of dungeons, more entrance dependent

more entrances load dungeons-2
while default is dungeons-1


entrances 01 and 03 to load dungeons-2
AD 0E 01    , = load ram for entrances
29 FF 00    ; = isolate the first byte
C9 01 00    , = compare to 0001 (16bit=2bytes)(is entrance 01= your house)
F0 10       , = branch $10 bytes if equal (to new pointers)
C9 03 00    , = compare to 0003 (16bit=2bytes)(is entrance 03= castle, left)
F0 0B       , = branch $0B bytes if equal (to new pointers)
BF 01 80 1F , = if not equal (not 01 or 03) load old dungeons
85 B8       ,
BF 00 80 1F ,
6B          ,
BF 01 80 3F , = branch here if your house or castle, left entrance
85 B8       ,
BF 00 80 3F ,
6B          ,

AD 0E 01 29 FF 00 C9 01 00 F0 10 C9 03 00 F0 0B BF 01 80 1F 85 B8 BF 00 80 1F 6B BF 01 80 3F 85 B8 BF 00 80 3F 6B


tested (works)
you can add custom amount of compares, and always branch the correct
amount of bytes to where dungeons-2 start: branches are +5 dependent:
0B, 10, 15, 1A, 1F, 24 etc
this is so because every new compare+branch opcodes have 5 bytes.

-------------------------------------------


load one global set of dungeons for one entrance,
if more entrances:


entrance 03 to load dun-2 and entrance 05 to load dun-3
AD 0E 01    , = load ram for entrances
29 FF 00    ; = isolate the first byte
C9 03 00    , = compare to 0003 (16bit=2bytes)(is entrance 03= castle, left)
F0 10       , = branch $-- bytes if equal (to dun-2)
C9 05 00    , = compare to 0005 (16bit=2bytes)(is entrance 05= castle, right)
F0 16       , = branch $-- bytes if equal (to dun-3)
BF 01 80 1F , = dungeons-1 (default, if you do not enter 03 or 05)
85 B8       ,
BF 00 80 1F ,
6B          ,
BF 01 80 3F , = dungeons-2
85 B8       ,
BF 00 80 3F ,
6B          ,
BF 01 80 5F , = dungeons-3
85 B8       ,
BF 00 80 5F ,
6B          ,



AD 0E 01 29 FF 00 C9 03 00 F0 10 C9 05 00 F0 16 BF 01 80 1F 85 B8 BF 00 80 1F 6B BF 01 80 3F 85 B8 BF 00 80 3F 6B BF 01 80 5F 85 B8 BF 00 80 5F 6B


tested (works)



-------------------------------------------

light/dark world variant+ entrance dependent

(very useful, since it is entrance compatible and swaps dun-1 and dun-2, when you swap the light/dark world), and can also load dungeons-3 if a specific entrance is entered.

RAM
7EF3CA
holds the LW/DW info
if it is 00, then you are in LW
if it is 40, then you are in DW


AD 0E 01    , = load ram for entrances
29 FF 00    ; = isolate the first byte
C9 03 00    , = compare to 0003 (16bit=2bytes)(is entrance 03= castle, left)
F0 22       , = branch $-- bytes if equal (to dungeons-3)
AF CA F3 7E , = load ram for light/dark world
29 FF 00    ; = isolate the first byte
C9 40 00    , = compare to 40 (is dark world)
F0 0B       , = branch $0B bytes if equal (dungeons-2)
BF 01 80 1F , = if not equal (then LW)(load dungeons-1)
85 B8       ,
BF 00 80 1F ,
6B          ,
BF 01 80 3F , = branch here if dark world (load dungeons-2)
85 B8       ,
BF 00 80 3F ,
6B          ,
BF 01 80 5F , = branch here if entrance 03 (load dungeons-3)
85 B8       ,
BF 00 80 5F ,
6B          ,


AD 0E 01 29 FF 00 C9 03 00 F0 22 AF CA F3 7E 29 FF 00 C9 40 00 F0 0B BF 01 80 1F 85 B8 BF 00 80 1F 6B BF 01 80 3F 85 B8 BF 00 80 3F 6B BF 01 80 5F 85 B8 BF 00 80 5F 6B


tested (works)

-------------------------------------------

same as before, only more entrances also load dungeons-3

AD 0E 01    , = load ram for entrances
29 FF 00    ; = isolate the first byte
C9 03 00    , = compare to 0003 (16bit=2bytes)(is entrance 03= castle, left)
F0 27       , = branch $-- bytes if equal (to dungeons-3)
C9 05 00    , = compare to 0003 (16bit=2bytes)(is entrance 05= castle, right)
F0 22       , = branch $-- bytes if equal (to dungeons-3)
AF CA F3 7E , = load ram for light/dark world
29 FF 00    ; = isolate the first byte
C9 40 00    , = compare to 40 (is dark world)
F0 0B       , = branch $0B bytes if equal (dungeons-2)
BF 01 80 1F , = if not equal (then LW)(load dungeons-1)
85 B8       ,
BF 00 80 1F ,
6B          ,
BF 01 80 3F , = branch here if dark world (load dungeons-2)
85 B8       ,
BF 00 80 3F ,
6B          ,
BF 01 80 5F , = branch here if entrance 03 or 05 (load dungeons-3)
85 B8       ,
BF 00 80 5F ,
6B          ,



AD 0E 01 29 FF 00 C9 03 00 F0 27 C9 05 00 F0 22 AF CA F3 7E 29 FF 00 C9 40 00 F0 0B BF 01 80 1F 85 B8 BF 00 80 1F 6B BF 01 80 3F 85 B8 BF 00 80 3F 6B BF 01 80 5F 85 B8 BF 00 80 5F 6B



tested (works)

-------------------------------------------

avatar
Puzzledude
Elite ROM Hacker
Elite ROM Hacker

Since : 2012-06-20

Back to top Go down

Re: The revolution begins now

Post by Puzzledude on Wed 22 Feb 2017 - 12:58

Fixing the Chests:

while: objects, room header; sprites, items; pushable blocks, torches to be lit; and damage pits can follow the same method of doubling/multipling dungeons while switching between them; the chests can not.

The only remaining thing are the "telephatic messages"= this is fixable with no switching, as they are so rare, that only 1 such set of messages can be loaded per room on all global dungeon sets. But how to solve chests.

Chests are problematic, since once you open them, the game saves this to RAM and then to SRAM for one room. So if you for instance open 3 chests in room 97, the game will save that. When you visit the same room (ie 97) on global dungeons-2, the game will know to have 3 chests opened. So how to put in chests if needed in dungeons-2 mode?

This is how you do it:
you don't switch between chest definitions (would so you no good), you expand them.

Let's say there are 3 chests in room 97 on dungeons-1 and also 3 on dungeons-2. This is how you do it:

Code:
AF 41 F3 7E , = load ram for boomerang
29 FF 00    ; = isolate the first byte
C9 01 00    , = compare to 01 (is have boomerang)
F0 0B       , = branch $0B bytes if equal (to new pointers)
BF 01 80 1F , = if not equal (no boomerang)
85 B8       ,   load old pointers
BF 00 80 1F ,
6B          , = end of old pointers
BF 01 80 3F , = branch here if boomerang
85 B8       ,
BF 00 80 3F ,
6B          , = end of new pointers



AF 41 F3 7E 29 FF 00 C9 01 00 F0 0B BF 01 80 1F 85 B8 BF 00 80 1F 6B BF 01 80 3F 85 B8 BF 00 80 3F 6B


at E96E, define chest-treasure for all chests in 1 room (like room 97) in all dungeon variants!

So if in room 97, 3 chest in dun-1 and another 3 in dun-2, then room 97 needs 6 chest definitions:
61 00 4B
61 00 4A
61 00 47
61 00 47
61 00 47
61 00 47
thus expansion is welcome,

so we don't duplex-switch, but only expand!

1.) So chest definitions for room 97 (dun-1 and dun-2) is:
61 00 4B shoes
61 00 4A flute
61 00 47 20 rup
61 00 47 20 rup
61 00 47 20 rup
61 00 47 20 rup

2.) but dun-1 object code for chests is:
69 4A F9, this is 1 (shoes)
89 4A F9, this is 2 (flute)
99 4A F9, this is 3 (20 rup)

no chests 4, 5, 6
location of 1, 2, 3 is anywhere in the room


3.) but dun-2 object code for chests is:
69 42 F9, clone info of chest-4= this is opened chest-1 shoes
69 42 F9, clone info of chest-4= this is opened chest-2 flute
69 42 F9, clone info of chest-4= this is opened chest-3 20 rup
69 42 F9, (new location of chest-4= chest-1 in dun-2), 20 rup
89 42 F9, chest-5, 20 rup
99 42 F9, chest-6, 20 rup

location of 4, 5, 6 is anywhere in the room
chests 1, 2, 3 are cloning the location of chest 4,
so chests 1, 2, 3 are under chest 4 and are empty (picked up
already because they were opened in dungeons-1)

Irronically, even the reverse is true:
you can pick up chests 4, 5, 6 first (you can not open chests 1, 2, 3 which are under chest 4, despite the fact that 1, 2, 3 are unopened). You can then go to dun-1 and open 1, 2, 3.

tested (works)

The big chest factor:
also solvable, sinc in this case the big chest already opened in dungeons-1 is hidden under the roof in dungeons-2, if a small chest is needed in the same room in dungeons-2.

Big chests are thus:
Code:
1.) So chest definitions for room 97 (dun-1 and dun-2) is:
61 80 4B shoes
61 00 4A flute
61 00 47 20 rup
61 00 47 20 rup
61 00 47 20 rup
61 00 47 20 rup

2.) but dun-1 object code for chests is:
69 48 FB, this is 1 (big chest)(shoes)
89 4A F9, this is 2 (flute)
99 4A F9, this is 3 (20 rup)

no chests 4, 5, 6
location of 1, 2, 3 is anywhere in the room


3.) but dun-2 object code for chests is:
01 00 FB, opened big chest-1 shoes (position 00 00)
00 00 C0, roof to cover the chest (position 00 00)
69 42 F9, clone info of chest-4= this is opened chest-2 flute
69 42 F9, clone info of chest-4= this is opened chest-3 20 rup
69 42 F9, (new location of chest-4= chest-1 in dun-2), 20 rup
89 42 F9, chest-5, 20 rup
99 42 F9, chest-6, 20 rup


Last edited by Puzzledude on Wed 22 Feb 2017 - 14:23; edited 2 times in total
avatar
Puzzledude
Elite ROM Hacker
Elite ROM Hacker

Since : 2012-06-20

Back to top Go down

Re: The revolution begins now

Post by Puzzledude on Wed 22 Feb 2017 - 13:02

And this is how to expand chest definitions/chests (since now you will not switch between dun-1 and dun-2, you will have one set of definitions with no switch, but it will be double or triple the size, so obviously you need to relocate.

Code:
***********************************************
7.) CHEST DEFINITIONS
***********************************************


*Primary pointer at:
1. EBFB, 6E E9 01 = E96E
2. EC0A, 70 E9 01 = E970
3. EC10, 6E E9 01 = E96E   all for E96E

Repoint all 3 accordingly. 01 to 23 is 11E96E for instance.

max bank is 1F8 = 504 in dec : 3 for one chest = 168 chests possible in the game.


*No secondary pointers, but Data directly at:
E96E (block is 1F8)


*Code is (3 bytes for one chest definition)
04 00 23,  04 00 = room 4, 23 is a content of the chest.
                           23 in hex is 35 in dec is 35: Armor 3 in Hyrule magic.

04 80 23,  04 00 = room 4, but 80 is big chest, 23 is Armor 3.

04 01 23,  04 01 is 104 in hex is room 260, 23 is Armor 3.


*Definition will only work with the chest object in the same room!

*Problems
Sometimes the definition is set, but no chest object is inserted. Insert chest in the rooms
with chest definitions to solve this problem.



UPDATE on how to expand the chest definitions
*********************************************
I've just found the expansion for chests!  
It is at EBF6! just before EBFB (pointer). Currently it is F8 01, so reversed 01F8.
I've expanded this to 1C 02 is 21C, put the chest at the end, and it works.
Expanded spece must be dividable with 3. So 1F8+3+3+3+3...
Max with two bytes is FF FF= can be divided
with 3. FFFF= 65.535 :3, is 21.845 chests possible in theory.


Default 1F8, devided with 3= A8= 168 chests in the original game.
avatar
Puzzledude
Elite ROM Hacker
Elite ROM Hacker

Since : 2012-06-20

Back to top Go down

View previous topic View next topic Back to top


 
Permissions in this forum:
You cannot reply to topics in this forum