Skeetendo

’Cause all games were better on the GBC

You are not logged in.

#1 2021-08-18 10:32:31

nightbringer
New member
Registered: 2021-08-18
Post 1/4

Adding Exp. Block item

Thanks in advance for any help with this.

So in Pokecrystal I am trying to create a held item that works like Lucky Egg except rather than boosting the exp. gained by the holder, it reduces the holder's exp. awarded to 0.

I have been trying to figure how to modify the code for the Lucky Egg to achieve this but it seems above my paygrade.

The relevant lucky egg code is in engine/battle/core.asm.

There are two main sequences. Firstly:

.no_boost
; Boost experience for a Trainer Battle
ld [wStringBuffer2 + 2], a
ld a, [wBattleMode]
dec a
call nz, BoostExp
; Boost experience for Lucky Egg
push bc
ld a, MON_ITEM
call GetPartyParamLocation
ld a, [hl]
cp LUCKY_EGG
call z, BoostExp
ldh a, [hQuotient + 3]
ld [wStringBuffer2 + 1], a
ldh a, [hQuotient + 2]
ld [wStringBuffer2], a
ld a, [wCurPartyMon]
ld hl, wPartyMonNicknames
call GetNickname
ld hl, Text_MonGainedExpPoint
call BattleTextbox
ld a, [wStringBuffer2 + 1]
ldh [hQuotient + 3], a
ld a, [wStringBuffer2]
ldh [hQuotient + 2], a
pop bc
call AnimateExpBar
push bc
call LoadTilemapToTempTilemap
pop bc
ld hl, MON_EXP + 2
add hl, bc
ld d, [hl]
ldh a, [hQuotient + 3]
add d
ld [hld], a
ld d, [hl]
ldh a, [hQuotient + 2]
adc d
ld [hl], a
jr nc, .no_exp_overflow
dec hl
inc [hl]
jr nz, .no_exp_overflow
ld a, $ff
ld [hli], a
ld [hli], a
ld [hl], a

And secondly:

BoostExp:
; Multiply experience by 1.5x
push bc
; load experience value
ldh a, [hProduct + 2]
ld b, a
ldh a, [hProduct + 3]
ld c, a
; halve it
srl b
rr c
; add it back to the whole exp value
add c
ldh [hProduct + 3], a
ldh a, [hProduct + 2]
adc b
ldh [hProduct + 2], a
pop bc
ret

My thought has been that the key may lie in the second sequence. Perhaps I could load the experience value, then subtract it from itself to get 0 total exp. But I don't know how to do that. I don't really know Assembly, all my fun with Pokecrystal comes with following tutorials or recombining parts of previously existing code rather than creating it new.

Can anyone lend a hand?

Last edited by nightbringer (2021-08-18 10:32:54)

Offline

#2 2021-08-19 07:24:23

UmaDestinyMax
New member
From: Chicago
Registered: 2021-08-19
Post 1/1
Website

Re: Adding Exp. Block item

Have you searched it on google?

Offline

#3 2021-08-20 00:31:45

Mateo
Member
Registered: 2009-11-25
Post 3,664/3,664

Re: Adding Exp. Block item

ok so after this part

ld a, [hl]
cp LUCKY_EGG
call z, BoostExp

you would wanna add something like

cp YOUR_NEW_ITEM_HERE
call z, NoExp

Then you would need to add a routine that looks like this:

NoExp:
; Set EXP to Zero
xor a
ldh [hProduct + 3], a
ldh [hProduct + 2], a
ret

I have not tried this out yet, but that should work. Give it a try and let me know.


I am not very active on this forum. I only pop in from time to time.

Offline

#4 2021-08-20 08:39:36

nightbringer
New member
Registered: 2021-08-18
Post 3/4

Re: Adding Exp. Block item

Thanks Mateo, I will give it a shot!

Offline

#5 2021-08-20 18:11:22

nightbringer
New member
Registered: 2021-08-18
Post 4/4

Re: Adding Exp. Block item

It seems to be working! Thanks so much, Mateo. Very much appreciate your help.

Without wanting to take liberties, maybe there is another issue you wouldn't mind helping with - also related to exp manipulation? No pressure though.

I'm trying to add level caps that depend on the badges the player has. I have cobbled something together by taking cues from the tutorial on skipping exp gains on lv100 pokemon and from the structure of the code that runs obedience checks based on badges.

The code seems to be working but with one limitation. At present, I cannot set a cap on the player if they have no badges at all. Caps only kick in once some badge or other is earned. Here is my edit to the .stat.exp.awarded sequence in engine/core.asm

.stat_exp_awarded
inc de
inc de
dec c
jr nz, .stat_exp_loop
ld hl, wJohtoBadges

; risingbadge
bit RISINGBADGE, [hl]
pop bc
ld hl, MON_LEVEL
add hl, bc
ld a, [hl]
cp GYM8_LEVEL
jp nc, .next_mon
push bc

; glacierbadge
bit GLACIERBADGE, [hl]
pop bc
ld hl, MON_LEVEL
add hl, bc
ld a, [hl]
cp GYM7_LEVEL
jp nc, .next_mon
push bc

; mineralbadge
bit MINERALBADGE, [hl]
pop bc
ld hl, MON_LEVEL
add hl, bc
ld a, [hl]
cp GYM6_LEVEL
jp nc, .next_mon
push bc

; stormbadge
bit STORMBADGE, [hl]
pop bc
ld hl, MON_LEVEL
add hl, bc
ld a, [hl]
cp GYM5_LEVEL
jp nc, .next_mon
push bc

; fogbadge
bit FOGBADGE, [hl]
pop bc
ld hl, MON_LEVEL
add hl, bc
ld a, [hl]
cp GYM4_LEVEL
jp nc, .next_mon
push bc

; plainbadge
bit PLAINBADGE, [hl]
pop bc
ld hl, MON_LEVEL
add hl, bc
ld a, [hl]
cp GYM3_LEVEL
jp nc, .next_mon
push bc

; hivebadge
bit HIVEBADGE, [hl]
pop bc
ld hl, MON_LEVEL
add hl, bc
ld a, [hl]
cp GYM2_LEVEL
jp nc, .next_mon
push bc

; zephyrbadge
bit ZEPHYRBADGE, [hl]
pop bc
ld hl, MON_LEVEL
add hl, bc
ld a, [hl]
cp GYM1_LEVEL
jp nc, .next_mon
push bc

xor a
ldh [hMultiplicand + 0], a
ldh [hMultiplicand + 1], a
ld a, [wEnemyMonBaseExp]
ldh [hMultiplicand + 2], a
ld a, [wEnemyMonLevel]
ldh [hMultiplier], a
call Multiply
ld a, 7
ldh [hDivisor], a
ld b, 4
call Divide

One work-around I tried is adding an additional, hidden badge that the player would be awarded in the background at the very start of the game. But when I tried that and added a check for the dummy badge into this sequence, the game would not compile. There was some error to do with the badge checks not conforming to 8 bits or something. I've tried a few other things but no success.

If you have any thoughts on a fix, I'd appreciate it!

P.S. I've tried searching for previous threads on badge level caps but couldn't find anything. Surprised by that to be honest.

Last edited by nightbringer (2021-08-20 18:12:34)

Offline

Board footer

Powered by FluxBB