diff options
author | Rangi <remy.oukaour+rangi42@gmail.com> | 2020-03-15 01:46:55 -0400 |
---|---|---|
committer | Rangi <remy.oukaour+rangi42@gmail.com> | 2020-03-15 01:46:55 -0400 |
commit | ac6bc67e43ce7f3be49cb2bfb101a56906bfbd1b (patch) | |
tree | 44be8f6c685dd5b721480af0e864e6f7f5e907a2 | |
parent | cc92a108567feabaf84d3450f68d08b817cd8a1f (diff) |
Use unique colors for each thrown Poké Ball
-rw-r--r-- | Tutorials.md | 1 | ||||
-rw-r--r-- | Use-unique-colors-for-each-thrown-Poké-Ball.md | 188 | ||||
-rw-r--r-- | screenshots/unique-ball-colors-list.png | bin | 0 -> 1029 bytes | |||
-rw-r--r-- | screenshots/unique-ball-colors.png | bin | 0 -> 3569 bytes |
4 files changed, 189 insertions, 0 deletions
diff --git a/Tutorials.md b/Tutorials.md index dbe4e50..8fb29e7 100644 --- a/Tutorials.md +++ b/Tutorials.md @@ -114,6 +114,7 @@ Tutorials may use diff syntax to show edits: - [Puddles that splash when you walk](Puddles-that-splash-when-you-walk) - [Use G/S SGB palettes for maps](Use-GS-SGB-palettes-for-maps) - [Gain experience from catching Pokémon](Gain-experience-from-catching-Pokémon) +- [Use unique colors for each thrown Poké Ball](Use-unique-colors-for-each-thrown-Poké-Ball) - [Smashing rocks has a chance to contain items](Smashing-rocks-has-a-chance-to-contain-items) diff --git a/Use-unique-colors-for-each-thrown-Poké-Ball.md b/Use-unique-colors-for-each-thrown-Poké-Ball.md new file mode 100644 index 0000000..a2453a9 --- /dev/null +++ b/Use-unique-colors-for-each-thrown-Poké-Ball.md @@ -0,0 +1,188 @@ +Gen 2 showed colored Poké Balls in battle, but the colors were picked from a limited set of six. Gen 3 started showing each Poké Ball with its unique graphics and colors. + +This tutorial will add unique colors for each type of Ball, although they'll all still use the same graphic. + + +## Contents + +1. [Define unique colors for each Ball](#1-define-unique-colors-for-each-ball) +2. [Make every Ball use `PAL_BATTLE_OB_RED`](#2-make-every-ball-use-pal_battle_ob_red) +3. [Load the unique colors into the palette](#3-load-the-unique-colors-into-the-palette) + + +## 1. Define unique colors for each Ball + +Edit [data/battle_anims/ball_colors.asm](../blob/master/data/battle_anims/ball_colors.asm): + +```diff + ; colors of balls thrown in battle + + BallColors: +- db MASTER_BALL, PAL_BATTLE_OB_GREEN +- db ULTRA_BALL, PAL_BATTLE_OB_YELLOW +- db GREAT_BALL, PAL_BATTLE_OB_BLUE +- db POKE_BALL, PAL_BATTLE_OB_RED +- db HEAVY_BALL, PAL_BATTLE_OB_GRAY +- db LEVEL_BALL, PAL_BATTLE_OB_BROWN +- db LURE_BALL, PAL_BATTLE_OB_BLUE +- db FAST_BALL, PAL_BATTLE_OB_BLUE +- db FRIEND_BALL, PAL_BATTLE_OB_YELLOW +- db MOON_BALL, PAL_BATTLE_OB_GRAY +- db LOVE_BALL, PAL_BATTLE_OB_RED +- db -1, PAL_BATTLE_OB_GRAY ++ db MASTER_BALL ++ RGB 31,31,31, 20,08,23 ++ db ULTRA_BALL ++ RGB 31,31,31, 10,10,12 ++ db GREAT_BALL ++ RGB 31,31,31, 09,13,30 ++ db POKE_BALL ++ RGB 31,31,31, 30,08,05 ++ db HEAVY_BALL ++ RGB 31,31,31, 06,10,12 ++ db LEVEL_BALL ++ RGB 31,31,31, 30,24,00 ++ db LURE_BALL ++ RGB 31,31,31, 04,14,30 ++ db FAST_BALL ++ RGB 31,31,31, 31,16,04 ++ db FRIEND_BALL ++ RGB 31,31,31, 04,17,04 ++ db MOON_BALL ++ RGB 31,31,31, 07,19,25 ++ db LOVE_BALL ++ RGB 31,31,31, 30,11,22 ++ db PARK_BALL ++ RGB 31,31,31, 18,18,05 ++ db -1 ; end ++ RGB 31,31,31, 16,16,16 +``` + +Each Ball used to use one of the palettes meant for move animations (since throwing a Ball is technically an animation): gray, yellow, red, green, blue, or brown. Here we've replaced each `PAL_BATTLE_OB_*` color index with a pair of RGB colors: the first for the bottom half of the Ball, the second for the top half. + +Here's how they'll look: + + + +We just changed the `BallColors` table to assign each Ball a pair of actual RGB colors, instead of a palette index. So putting back the palette index will be the next step. + + +## 2. Make every Ball use `PAL_BATTLE_OB_RED` + +Edit [engine/battle_anims/functions.asm](../blob/master/engine/battle_anims/functions.asm): + +```diff + GetBallAnimPal: +- ld hl, BallColors +- ldh a, [rSVBK] +- push af +- ld a, BANK(wCurItem) +- ldh [rSVBK], a +- ld a, [wCurItem] +- ld e, a +- pop af +- ldh [rSVBK], a +-.IsInArray: +- ld a, [hli] +- cp -1 +- jr z, .load +- cp e +- jr z, .load +- inc hl +- jr .IsInArray +- +-.load +- ld a, [hl] + ld hl, BATTLEANIMSTRUCT_PALETTE + add hl, bc +- ld [hl], a ++ ld [hl], PAL_BATTLE_OB_RED + ret +- +-INCLUDE "data/battle_anims/ball_colors.asm" +``` + +Since we know every Ball will use the same palette index, the next step is to replace that palette's colors with the correct Ball-specific ones at the right time. + + +## 3. Load the unique colors into the palette + +Edit [engine/battle_anims/helpers.asm](../blob/master/engine/battle_anims/helpers.asm): + +```diff + LoadBattleAnimGFX: + push hl ++ cp ANIM_GFX_POKE_BALL ++ call z, .LoadBallPalette + ld l, a + ld h, 0 + add hl, hl + add hl, hl + ld de, AnimObjGFX + add hl, de + ld c, [hl] + inc hl + ld b, [hl] + inc hl + ld a, [hli] + ld h, [hl] + ld l, a + pop de + push bc + call DecompressRequest2bpp + pop bc + ret ++ ++.LoadBallPalette: ++ ; save the current WRAM bank ++ ld a, [rSVBK] ++ push af ++ ; switch to the WRAM bank of wCurItem so we can read it ++ ld a, BANK(wCurItem) ++ ld [rSVBK], a ++ ; store the current item in b ++ ld a, [wCurItem] ++ ld b, a ++ ; seek for the BallColors entry matching the current item ++ ld hl, BallColors ++.loop ++ ld a, [hli] ++ cp b ; did we find the current ball? ++ jr z, .done ++ cp -1 ; did we reach the end of the list? ++ jr z, .done ++rept PAL_COLOR_SIZE * 2 ++ inc hl ; skip over the two RGB colors to the next entry ++endr ++ jr .loop ++.done ++ ; switch to the WRAM bank of wOBPals2 so we can write to it ++ ld a, BANK(wOBPals2) ++ ld [rSVBK], a ++ ; load the RGB colors into the middle two colors of PAL_BATTLE_OB_RED ++ ld de, wOBPals2 palette PAL_BATTLE_OB_RED color 1 ++rept PAL_COLOR_SIZE * 2 - 1 ++ ld a, [hli] ++ ld [de], a ++ inc de ++endr ++ ld a, [hl] ++ ld [de], a ++ ; apply the updated colors to the palette RAM ++ ld a, $1 ++ ld [hCGBPalUpdate], a ++ ; restore the previous WRAM bank ++ pop af ++ ld [rSVBK], a ++ ; restore the graphics index to be loaded ++ ld a, ANIM_GFX_POKE_BALL ++ ret ++ ++INCLUDE "data/battle_anims/ball_colors.asm" +``` + +`LoadBattleAnimGFX` is called with an `ANIM_GFX_*` constant in `a`; it loads the appropriate graphics for that constant in preparation for animating the move. If we inspect [data/moves/animations.asm](../blob/master/data/moves/animations.asm), we can see that `ANIM_GFX_POKE_BALL` is used for throwing Poké Balls, and only for throwing Poké Balls; so if we know it's being loaded, that's the right time to load our unique colors too. + +Now we can see the unique colors in action: + + diff --git a/screenshots/unique-ball-colors-list.png b/screenshots/unique-ball-colors-list.png Binary files differnew file mode 100644 index 0000000..04b324c --- /dev/null +++ b/screenshots/unique-ball-colors-list.png diff --git a/screenshots/unique-ball-colors.png b/screenshots/unique-ball-colors.png Binary files differnew file mode 100644 index 0000000..9079181 --- /dev/null +++ b/screenshots/unique-ball-colors.png |