Registrarse

[ASM] R | Gen 6 Exp.Share

Andrea

Usuario mítico
Good evening to all.
Today I would like to explain how to implement the exp. sharing of sixth generation, whose peculiarity live in the fact that all the members of our team will receive experience, even if they haven't participated in the battle.
In this case, the pokémon in the field will receive half of the total amount of the experience they would normally receive without sharing experience, while to the others 1/6.

*NB: Before proceeding further, if you are not familiar with inserting asm routines, i suggest you to read some tutorial about it.

#1 - Tools needed
Before going into the insertion of the changes, it's necessary to define which tools we will need to arrive at the final result:
- HxD, available at the following link.
It will allow us to insert our compiled routines and make some hexadecimal changes necessary to "hook" our asm routines to the original code of the ROM.
- Compilatore, available at the following link.
As you can imagine, we will need it to convert our ASM routines into a binary file "readable" from the ROM.
- XSE, available at the following link.
It will help us to insert the messages that will be displayed during the interaction with the exp.share in the bag.
- Item Editor, available at the following link.
It will help us to change some "attributes" of the exp.share item.

#2 - ASM routines and general explanations
In order to implement this feature, we use 4 asm routines.
The first routine allows us to define which pokemon of the team will receive the experience:
.THUMB
.ALIGN 2

PUSH {R0,R2-R7}
LDR R0, = 0x1200
BL CHECK_FLAG
CMP R0, #0
BEQ RETURN

MOV R4, #0
MOV R5, #0

LOOP:
LDR R0, = 0x03004360
MOV R1, #0x64
MUL R1, R4
ADD R0, R0, R1
MOV R1, #0x56
LDRH R2, [R0, R1]
CMP R2, #0
BEQ COUNTER

IS_EGG:
MOV R1, #0x2D
PUSH {R4,R5}
BL GET_DATA
POP {R4, R5}
CMP R0, #1
BEQ COUNTER

MOV R1, #1
LSL R1, R1, R4
ORR R5, R1

COUNTER:
ADD R4, #1
CMP R4, #6
BNE LOOP

MOV R1, R5

POP {R0,R2-R7}
LDR R0, = 0x08020030+1
BX R0

RETURN:
POP {R0,R2-R7}
LDR R2, = 0x02024DEA
MOV R1, #2
LDR R3, = 0x08020026+1
BX R3

CHECK_FLAG:
LDR R2, = 0x08069340+1
BX R2

GET_DATA:
LDR R2, = 0x0803CB60+1
BX R2
In this case, the only pokémon that will be excluded will be the KO ones and the eggs.
After compiling the routine in a free ROM offset, you need to make some changes with the HxD.
Go to 0x20024 and overwrite the bytes with 10 47
Go to 0x20058 and overwrite the bytes with XXXXXX08.
Instead of the XX, will be entered the offset of previous routine + 1 and in Little Endian format (example: 08123456 -> 57 34 12 08).

*NB: Both in this routine and in those to follow, the flag 1200 was used to discriminate if the exp.share is active/inactive.
You can change the flag value, as long as your choice is consistent and is reported in all routines.
For convenience, i highlighted the flag value used by the routines in red.

The second routine is used to define the amount of experience that pokémon in the field will receive:
.THUMB
.ALIGN 2

PUSH {R0-R7}
LDR R0, = 0x1200
BL CHECK_FLAG
CMP R0, #0
BEQ NOT_EXP

POP {R0-R7}

LSR R0, R1, #1

BACK_TO:
LDR R1, = 0x080201A8+1
BX R1

NOT_EXP:
POP {R0-R7}
LDR R2, = 0x080201E0+1
BX R2

CHECK_FLAG:
LDR R2, = 0x08069340+1
BX R2
In this case, the value of the total experience contained in R1, is divided by 2 and saved in R0 through the LSR instruction.
To "hook" the routine open the ROM with the Hex Editor, go to 0x2019A and overwrite the bytes with 000000480047XXXXXX08.
The speech made previously for the XX is also valid in this case.

The next routine is used to determine which Pokémon are in the field at that time and will therefore receive more experience:
.THUMB
.ALIGN 2

LDRH R0, [R3]

LDR R2, = 0x02016018
LDRB R2, [R2]

LDR R5, = 0x02024A6A
LDRB R7, [R5]
CMP R7, R2
BEQ RETURN

LDR R7, = 0x020239F8
LDRB R7, [R7]
MOV R3, #1
AND R7, R3
CMP R7, #1
BEQ DOUBLE

DIVIDE:
PUSH {R1-R7}
MOV R1, #3
BL DIVISION
POP {R1-R7}

RETURN:
STRH R0, [R1]
MOV R8, R1
LDR R0, = 0x08020376+1
BX R0

DOUBLE:
LDRB R7, [R5, #4]
CMP R7, R2
BEQ RETURN
B DIVIDE

DIVISION:
LDR R2, = 0x081E0868+1
BX R2
To "hook" the routine open the ROM with the Hex Editor, go to 0x20344 and overwrite the bytes with 00480047xxxxxx08.
The speech made previously for the XX is also valid in this case.

The last routine is used to define the new behavior of the exp.share, allowing us to display a message containing the current "state" of it (active/inactive):
.THUMB
.ALIGN 2

PUSH {LR}
PUSH {R0-R6}
LDR R0, .FLAG
BL CHECK_FLAG
MOV R7, R0
POP {R0-R6}
LSL R0, R0, #0x18
LSR R0, R0, #0x18
LDR R2, = 0x03004B20
LSL R1, R0, #2
ADD R1, R1, R0
LSL R1, R1, #3
ADD R1, R1, R2
LDRB R1, [R1,#0xC]
CMP R7, #0
BEQ ACTIVE

PUSH {R0-R7}
LDR R0, .FLAG
BL CLEAR_FLAG
POP {R0-R7}
LDR R2, = 0x08YYYYYY @MSG DE-ACTIVE
B WRITE_MSG

ACTIVE:
PUSH {R0-R7}
LDR R0, .FLAG
BL SET_FLAG
POP {R0-R7}
LDR R2, = 0x08XXXXXX @MSG ACTIVE

WRITE_MSG:
BL MSG
POP {R0}
BX R0

MSG:
PUSH {LR}
LSL R0, R0, #0x18
LSR R0, R0, #0x18
LSL R1, R1, #0x18
LSR R1, R1, #0x18
BL TEXTBOX
POP {R0}
BX R0

TEXTBOX:
PUSH {R0}
LDR R0, = 0x080C9098+1
B CALL

CHECK_FLAG:
PUSH {R0}
LDR R0, = 0x08069340+1
B CALL

SET_FLAG:
PUSH {R0}
LDR R0, = 0x080692F0+1
B CALL

CLEAR_FLAG:
PUSH {R0}
LDR R0, = 0x08069318+1

CALL:
MOV R10, R0
POP {R0}
BX R10

.ALIGN 2
.FLAG: .word 0x1200
Before compiling the routine, it's necessary to define the offsets of the two messages that will appear during the interaction with the item.
The first message will indicate that the function is active, otherwise the second will indicate that the function is deactivated.
To do this, we use the XSE tool.
To insert a message into the ROM, we use the following script:
[align=center]
#dynamic 0x800000
#org @msg
= text message
[/align]
After clicking the button with the gears of the toolbar at the top, note the offset that will appear and replace it at XX in the asm routine.
Repeat the procedure described above also for the second message, this time replacing the YY.
After compiling the routine, insert it into the ROM and write down the offset.

#3 - From Normal item to Key Item
The last remaining step before completing the implementation is to change some "attributes" of the exp.share.
To do this, use the Item Editor tool and open your ROM.
After selecting the "EXP. SHARE" item from the list of tools on the left, edit the following fields like this:
- Mystery Values with 1 and 1
- Field Usade Code Pointer with the offset of the last routine + 1.

#4 - Final result
[align=center]

[/align]
 
Última edición:

jrlopes

Héroe de WaH
Respuesta: [RUBY] Gen 6 Exp.Share

Hice todo según el tutorial (incluso leí algunos comentarios donde dice que el error ocurre por no tomar el espacio) Hice lo que Versekr Dark explicó en la rutina a continuación:

El error te da por que no quitas todos los espacios de los dialogos nuevos, al final debe aparecerte esto

28 68 01 1C 53 31 08 78 07 B4 11 48 11 4A 0E B4 00 F0 1D F8 0E BC 01 28 15 D1 07 BC 78 B4 0E 4E 33 78 0E 4C 64 25 5D 43 64 5D 06 2C 01 D0 01 22 00 E0 00 22 01 33 06 2B 00 D1 00 23 33 80 78 BC 04 B4 07 4A 10 47 07 BC 01 22 02 40 F8 E7 10 47 00 02 00 00 D1 E6 06 08 D0 70 03 02 97 42 02 02 D1 1C 02 08


Y, sin embargo, el error aún se congela cuando pasa de la experiencia al pokemon.
 

Versekr Dark

Usuario mítico
Re: Respuesta: [RUBY] Gen 6 Exp.Share

Hice todo según el tutorial (incluso leí algunos comentarios donde dice que el error ocurre por no tomar el espacio) Hice lo que Versekr Dark explicó en la rutina a continuación:

El error te da por que no quitas todos los espacios de los dialogos nuevos, al final debe aparecerte esto

28 68 01 1C 53 31 08 78 07 B4 11 48 11 4A 0E B4 00 F0 1D F8 0E BC 01 28 15 D1 07 BC 78 B4 0E 4E 33 78 0E 4C 64 25 5D 43 64 5D 06 2C 01 D0 01 22 00 E0 00 22 01 33 06 2B 00 D1 00 23 33 80 78 BC 04 B4 07 4A 10 47 07 BC 01 22 02 40 F8 E7 10 47 00 02 00 00 D1 E6 06 08 D0 70 03 02 97 42 02 02 D1 1C 02 08


Y, sin embargo, el error aún se congela cuando pasa de la experiencia al pokemon.

Pusiste el +1?

A mi si me funciona.

Mensaje Activado:

#dynamic 0xXXXXXX

#org @msg
= El Repartir Experiencia está\nActivado.\l

Mensaje Apagado:

#dynamic 0xXXXXXX

#org @msg
= El Repartir Experiencia está\nApagado.\l

 
Última edición:
Arriba