Skeetendo

’Cause all games were better on the GBC

You are not logged in.

#1 2014-09-23 21:51:42

Mateo
Member
From: The Sims 4
Registered: 2009-11-25
Post 2,903/3,578

[Pokered] Adding Gender Selection

WARNING: This is a really long tutorial, and while it may not be as complicated for you as it was for me to make it up, it is still a lot more complicated than, say, editing the text or which item is in the PC at the start of the game or any of that jazz. But if you follow the tutorial properly (and assuming I haven't accidentally skipped something, since there was a lot to explain) you should be able to get this working in your game.

To see the finished results of this tutorial, you can check out this youtube video:
http://www.youtube.com/watch?v=9CPbmE9FQC8


Step 1: Get the graphics for the girl player.

For the girl player, you will need the following graphics:

-Front sprite
-Back sprite
-Walking sprite
-Cycling sprite
-Fishing tiles

To get the right dimensions for these, you can just copy+paste the ones for Red and edit them. Please note that in my example, I have Danny-E33's larger backsprite routine installed. You can do this without that routine of course, but your backsprite will have to be the normal Red Version size instead of the larger Gold Version size I am using.

Once you have your graphics drawn/found etc. make sure that they use ONLY the colours that other graphics in the project folder use (otherwise they won't convert properly) and save them as .png files with names you can remember. In my example, I kept the same naming scheme as the original files, but I substituted the word "Leaf" everywhere the original file name said "Red" and placed them in the same subfolders as the originals. This was just to make it easier for me to remember the file names later, and to make sure they are converted properly at compile.

So I ended up with files named:

/pic/trainer/leaf.png
/pic/trainer/leafb.png

/gfx/sprites/leaf.png
/gfx/sprites/leafcycling.png

/gfx/leaf_fishing_tile_back.png
/gfx/leaf_fishing_tile_front.png
/gfx/leaf_fishing_tile_side.png


Step 2: Inserting the sprites.

Now that you have the new .png files in the proper subfolders, we have to actually reference them somewhere to get them included. So we will open main.asm in notepad++ and find the references to the player's sprites. Doing a search for RedPicFront will eventually get you to this:

RedPicFront::  INCBIN "pic/trainer/red.pic"
ShrinkPic1::   INCBIN "pic/trainer/shrink1.pic"
ShrinkPic2::   INCBIN "pic/trainer/shrink2.pic"

Well, let's just add a new line really quick to include our new front sprite for the girl, so we can reference it later. You should have something that looks like this:

RedPicFront::  INCBIN "pic/trainer/red.pic"
LeafPicFront:: INCBIN "pic/trainer/leaf.pic"
ShrinkPic1::   INCBIN "pic/trainer/shrink1.pic"
ShrinkPic2::   INCBIN "pic/trainer/shrink2.pic"

Now if you scroll down a little from that, you should see the lines that include the overworld sprites. So we will just go to the line that says:

RedCyclingSprite:     INCBIN "gfx/sprites/cycling.2bpp"
RedSprite:            INCBIN "gfx/sprites/red.2bpp"

and add a couple of lines under it, so it looks like this:

RedCyclingSprite:     INCBIN "gfx/sprites/cycling.2bpp"
RedSprite:            INCBIN "gfx/sprites/red.2bpp"
LeafSprite:           INCBIN "gfx/sprites/leaf.2bpp"
LeafCyclingSprite:    INCBIN "gfx/sprites/leafcycling.2bpp"

Now, at least in my case, adding thew overworlds to this bank caused errors at compile, because we were trying to add too many sprites in this bank. To make life simpler later, we can just take 2 unrelated sprites and move them to another bank. I decided to cut and paste the lines that said:

GiovanniSprite:       INCBIN "gfx/sprites/giovanni.2bpp"
RocketSprite:         INCBIN "gfx/sprites/rocket.2bpp"

to the top of the other bank of overworld sprites. You can find that other bank by searching "SECTION "NPC Sprites 1"" or by scrolling up a bit from the banks we were just editing.

Now, the next thing we should come to is the fishing tiles. We won't have room to include these in the same bank as Red's fishing tiles, so we will have to find another bank to include them in. Which bank they are in is not important, since the routine that calls them can find them in any bank. So I added them in the same bank as the player backsprites.

So to finish inserting the graphics, do a search in main.asm for RedPicBack. You will eventually find something that looks like this:

RedPicBack::  INCBIN "pic/trainer/redb.pic"
OldManPic::  INCBIN "pic/trainer/oldman.pic"

So I just went ahead and added some lines to make it look like this:

RedPicBack::  INCBIN "pic/trainer/redb.pic"
LeafPicBack::  INCBIN "pic/trainer/leafb.pic"
OldManPic::  INCBIN "pic/trainer/oldman.pic"
LeafFishingTilesFront: INCBIN "gfx/leaf_fishing_tile_front.2bpp"
LeafFishingTilesBack:  INCBIN "gfx/leaf_fishing_tile_back.2bpp"
LeafFishingTilesSide:  INCBIN "gfx/leaf_fishing_tile_side.2bpp"

Now that we have all of the entries for the graphics added, now is a good time to save main.asm and attempt to compile the rom. If all goes well, the rom will compile normally with these extra graphics included (but nothing will call them yet). If you get errors saying that a bank is full, you will have to move something around to make it compile properly. If this happens, the cygwin terminal will tell you which line in main.asm it had a problem with, so you can go right to it and know which bank you need to make room in.


Step 3: Setting up the into.

Ok, so you got everything sorted properly so your rom will compile with the new graphics? Ok, let's start making it so we can use them!

The first thing you will want to do is add the menu that asks if you are a boy or a girl. The way I did this is by making a copy of the YesNoChoice routine, and having it reference the unused "North/West" menu string.

So, let's open up engine/menu/text_box.asm and find the menu strings. So go ahead and search for TwoOptionMenuStrings and eventually you will come to:

TwoOptionMenuStrings:
    db 4,3,0
    dw .YesNoMenu
    db 6,3,0
    dw .NorthWestMenu
    db 6,3,0
    dw .SouthEastMenu
    db 6,3,0
    dw .YesNoMenu
    db 6,3,0
    dw .NorthEastMenu
    db 7,3,0
    dw .TradeCancelMenu
    db 7,4,1
    dw .HealCancelMenu
    db 4,3,0
    dw .NoYesMenu

.NoYesMenu
    db   "NO"
    next "YES@"
.YesNoMenu
    db   "YES"
    next "NO@"
.NorthWestMenu
    db   "NORTH"
    next "WEST@"
.SouthEastMenu
    db   "SOUTH"
    next "EAST@"
.NorthEastMenu
    db   "NORTH"
    next "EAST@"
.TradeCancelMenu
    db   "TRADE"
    next "CANCEL@"
.HealCancelMenu
    db   "HEAL"
    next "CANCEL@"

The only entries we are interested in right now are the ones with NorthWest. So we'll just edit these really quick so we come up with this:

TwoOptionMenuStrings:
    db 4,3,0
    dw .YesNoMenu
    db 5,3,0
    dw .BoyGirlMenu
    db 6,3,0
    dw .SouthEastMenu
    db 6,3,0
    dw .YesNoMenu
    db 6,3,0
    dw .NorthEastMenu
    db 7,3,0
    dw .TradeCancelMenu
    db 7,4,1
    dw .HealCancelMenu
    db 4,3,0
    dw .NoYesMenu

.NoYesMenu
    db   "NO"
    next "YES@"
.YesNoMenu
    db   "YES"
    next "NO@"
.BoyGirlMenu
    db   "BOY"
    next "GIRL@"
.SouthEastMenu
    db   "SOUTH"
    next "EAST@"
.NorthEastMenu
    db   "NORTH"
    next "EAST@"
.TradeCancelMenu
    db   "TRADE"
    next "CANCEL@"
.HealCancelMenu
    db   "HEAL"
    next "CANCEL@"

Notice that I changed not only the text and label names, but I changed the numbers above the NorthWest choice. Those determine how large the box around the words will be, and by changing that value from 6 to 5, we make it so there isn't exta space after the Boy/Girl options.

Next, we'll need to declare a place to store the player's gender. That way when we add the code to call that menu choice, we have somewhere to save the result. So let's open up wram.asm and declare a new address!

If you search for wGameProgressFlagsEnd you'll find this:

wGameProgressFlagsEnd::

    ds 56

These bytes that come after those flags are unused, but are still within the block of WRAM that gets stored in the .sav file when you save the game. So here is a good place to declare the new address we'll be making use of in the rest of this tutorial. So, just change the code above to look like this:

wGameProgressFlagsEnd::

wPlayerGender::
; $00 = male
; $01 = female
    ds 1

; unused
    ds 55

Now that we have these edited, you can save that file and move on to the actual intro. If you look in /engine/oak_speech.asm you will see that this is the main code for the intro. Scroll down to the bottom, and paste this:

; displays boy/girl choice
BoyGirlChoice::
    call SaveScreenTilesToBuffer1
    call InitBoyGirlTextBoxParameters
    jr DisplayBoyGirlChoice
    
InitBoyGirlTextBoxParameters::
    ld a, $1 ; loads the value for the unused North/West choice, that was changed to say Boy/Girl
    ld [wTwoOptionMenuID], a
    coord hl, 13, 7 
    ld bc, $80e
    ret
    
DisplayBoyGirlChoice::
    ld a, $14
    ld [wTextBoxID], a
    call DisplayTextBoxID
    jp LoadScreenTilesFromBuffer1

This is a copy of the YesNoChoice routine, but modified to call our new Boy/Girl option instead.

Now that we have this subroutine added, we can scroll back up and write some new code to call it.

Near the top, you'll see a label called OakSpeech, and a few lines down, you'll see some code that looks like this:

xor a
    ld [hTilesetType],a
    ld a,[wd732]
    bit 1,a ; possibly a debug mode bit
    jp nz,.skipChoosingNames

Immediately under that, we'll add our new code for the gender selection. So immediately after the line about skipping the intro, we'll add this:

ld hl,BoyGirlText  ; added to the same file as the other oak text
    call PrintText     ; show this text
    call BoyGirlChoice ; added routine at the end of this file
    ld a, [wCurrentMenuItem]
    ld [wPlayerGender], a ; store player's gender. 00 for boy, 01 for girl
    call ClearScreen ; clear the screen before resuming normal intro

Now if you scroll down a bit you will find something that looks like this:

ld hl,OakSpeechText2
    call PrintText
    call GBFadeOutToWhite
    call ClearScreen
    ld de,RedPicFront
    ld bc,(Bank(RedPicFront) << 8) | $00
    call IntroDisplayPicCenteredOrUpperRight

So we'll need to change this up a bit, so it can show the other pic if you are a girl. Make it look like this:

ld hl,OakSpeechText2
    call PrintText
    call GBFadeOutToWhite
    call ClearScreen
    ld de,RedPicFront
    lb bc, Bank(RedPicFront), $00
    ld a, [wPlayerGender] ; check gender
    and a      ; check gender
    jr z, .NotLeaf1
    ld de,LeafPicFront
    lb bc, Bank(LeafPicFront), $00
.NotLeaf1:
    call IntroDisplayPicCenteredOrUpperRight

Next, we can scroll down a bit more until we see:

.skipChoosingNames
    call GBFadeOutToWhite
    call ClearScreen
    ld de,RedPicFront
    lb bc, Bank(RedPicFront), $00
    call IntroDisplayPicCenteredOrUpperRight

So we'll just change it to say:

.skipChoosingNames
    call GBFadeOutToWhite
    call ClearScreen
    ld de,RedPicFront
    lb bc, Bank(RedPicFront), $00
    ld a, [wPlayerGender] ; check gender
    and a      ; check gender
    jr z, .NotLeaf2
    ld de,LeafPicFront
    lb bc, Bank(LeafPicFront), $00
.NotLeaf2:
    call IntroDisplayPicCenteredOrUpperRight

You can see where this is going, really. A lot of checking the gender and just making it load the girl's stuff instead, otherwise keep loading the boy's stuff. We're still not done with this file yet though. So scroll down a bit more until you see:

call DelayFrames
    ld de,RedSprite
    ld bc,(BANK(RedSprite) << 8) | $0C
    ld hl,vSprites
    call CopyVideoData
    ld de,ShrinkPic1
    ld bc,(BANK(ShrinkPic1) << 8) | $00
    call IntroDisplayPicCenteredOrUpperRight

and make it look like this:

call DelayFrames
    ld de,RedSprite
    lb bc, BANK(RedSprite), $0C
    ld a, [wPlayerGender] ; check gender
    and a      ; check gender
    jr z, .NotLeaf3
    ld de,LeafSprite
    lb bc, BANK(LeafSprite), $0C
.NotLeaf3:
    ld hl,vSprites
    call CopyVideoData
    ld de,ShrinkPic1
    lb bc, BANK(ShrinkPic1), $00
    call IntroDisplayPicCenteredOrUpperRight

Now, we'll scroll down a bit more until we see:

OakSpeechText3:
    TX_FAR _OakSpeechText3
    db "@"

Since we added a text string earlier when asking your gender, we'll need to set this up here so the script can find it. So we'll add:

BoyGirlText: ; This is new so we had to add a reference to get it to compile
    TX_FAR _BoyGirlText
    db "@"

under the OakSpeechText3 part. That's all we have to do in this file, but we're not quite done with the intro. (The intro is probably the most complicated part in all honesty).

Now we'll go ahead and save that file, and open /engine/oak_speech2.asm to keep working. At the top you will see:

ChoosePlayerName:
    call OakSpeechSlidePicRight
    ld de, DefaultNamesPlayer
    call DisplayIntroNameTextBox
    ld a, [wCurrentMenuItem]
    and a
    jr z, .customName
    ld hl, DefaultNamesPlayerList
    call GetDefaultName
    ld de, wPlayerName
    call OakSpeechSlidePicLeft
    jr .done

and change that to this:

ChoosePlayerName:
    call OakSpeechSlidePicRight
    ld a, [wPlayerGender] ; Added gender check
    and a
    jr nz, .AreGirl ; Skip to girl names if you are a girl instead
    ld de, DefaultNamesPlayer
    call DisplayIntroNameTextBox
    ld a, [wCurrentMenuItem]
    and a
    jr z, .customName
    ld hl, DefaultNamesPlayerList
    call GetDefaultName
    ld de, wPlayerName
    call OakSpeechSlidePicLeft
    jr .done
.AreGirl ; Copy of the boy naming routine, just with girl's names
    ld de, DefaultNamesGirl
    call DisplayIntroNameTextBox
    ld a, [wCurrentMenuItem]
    and a
    jr z, .customName
    ld hl, DefaultNamesGirlList
    call GetDefaultName
    ld de, wPlayerName
    call OakSpeechSlidePicLeft
    jr .done ; End of new Girl Names routine

This adds a copy of the name routine that will instead call the girl's default names, which we will add in a minute. But first, we still have a little more to do.

If you will look at where it says:

.customName
    ld hl, wPlayerName
    xor a ; NAME_PLAYER_SCREEN
    ld [wNamingScreenType], a
    call DisplayNamingScreen
    ld a, [wcf4b]
    cp "@"
    jr z, .customName
    call ClearScreen
    call Delay3
    ld de, RedPicFront
    ld b, BANK(RedPicFront)
    call IntroDisplayPicCenteredOrUpperRight
.done
    ld hl, YourNameIsText
    jp PrintText

we'll need to change this, so that entering a custom name won't make you look like the boy when you get back to the intro. So we'll make the code look like this:

.customName
    ld hl, wPlayerName
    xor a ; NAME_PLAYER_SCREEN
    ld [wNamingScreenType], a
    call DisplayNamingScreen
    ld a, [wcf4b]
    cp "@"
    jr z, .customName
    call ClearScreen
    call Delay3
    ld de, RedPicFront
    ld b, BANK(RedPicFront)
    ld a, [wPlayerGender] ; Added gender check
    and a      ; Added gender check
    jr z, .AreBoy3
    ld de, LeafPicFront
    ld b, BANK(LeafPicFront)
.AreBoy3
    call IntroDisplayPicCenteredOrUpperRight
.done
    ld hl, YourNameIsText
    jp PrintText

Now then, we can get around to adding the name list for the girl player. So scroll down until you see:

IF _RED
DefaultNamesPlayer:
    db   "NEW NAME"
    next "RED"
    next "ASH"
    next "JACK"
    db   "@"

DefaultNamesRival:
    db   "NEW NAME"
    next "BLUE"
    next "GARY"
    next "JOHN"
    db   "@"
ENDC

and add a new entry for your girl names. It will look something like this:

IF _RED
DefaultNamesPlayer:
    db   "NEW NAME"
    next "RED"
    next "ASH"
    next "JACK"
    db   "@"
    
DefaultNamesGirl:
    db   "NEW NAME"
    next "SCARLET"
    next "LEAF"
    next "NICOLE"
    db   "@"

DefaultNamesRival:
    db   "NEW NAME"
    next "BLUE"
    next "GARY"
    next "JOHN"
    db   "@"
ENDC

Obviously, you don't have to use the same names I came up with. Just make sure they aren't too long for a player name and you are fine.

So that sounds like we are done with the intro, right? Not quite. We only added the entries for the name menu. We still need to enter the actual list it will reference, because Red Version was weird. So we'll scroll down a little more until we find:

IF DEF(_RED)
DefaultNamesPlayerList:
    db "NEW NAME@"
    db "RED@"
    db "ASH@"
    db "JACK@"
DefaultNamesRivalList:
    db "NEW NAME@"
    db "BLUE@"
    db "GARY@"
    db "JOHN@"
ENDC

and add the girl list in there. It should look like this:

IF DEF(_RED)
DefaultNamesPlayerList:
    db "NEW NAME@"
    db "RED@"
    db "ASH@"
    db "JACK@"
DefaultNamesGirlList:
    db "NEW NAME@"
    db "SCARLET@"
    db "LEAF@"
    db "NICOLE@"
DefaultNamesRivalList:
    db "NEW NAME@"
    db "BLUE@"
    db "GARY@"
    db "JOHN@"
ENDC

You also need to add those entries for the girl's name lists to the IF_BLUE lists as well, if you plan on compiling as a version other than Red. That is it for the actual ASM on the intro, but we still need to open another file to finish the intro up. Remember that text string we made up to reference earlier in the gender select menu? Yeah, we have to actually put that string into the game.

So let's save that file and open up /text/oakspeech.asm and scroll down to the bottom of the file. There we can add an entry that looks like this:

_BoyGirlText::
    text "Play as a boy, or"
    line "as a girl?"
    done

Then just save it and you're done with the intro. At this point, I would recommend compiling it again and testing the intro, just to make sure everything worked the way you wanted it to..

Step 4: Setting up the player's overworld sprites.

Ok, so you got the intro working nicely? Great! Time to move on to getting the game to show the proper sprites when you are fishing as the girl.

So let's go ahead and open up /engine/overworld/player_animations.asm and have a look. You'll want to search for FishingAnim: to find what you are looking for. It will look like this:

FishingAnim:
    ld c, 10
    call DelayFrames
    ld hl, wd736
    set 6, [hl] ; reserve the last 4 OAM entries
    ld de, RedSprite
    ld hl, vNPCSprites
    lb bc, BANK(RedSprite), $c
    call CopyVideoData
    ld a, $4
    ld hl, RedFishingTiles
    call LoadAnimSpriteGfx

You'll want to replace that with this:

FishingAnim:
    ld c, 10
    call DelayFrames
    ld hl, wd736
    set 6, [hl] ; reserve the last 4 OAM entries
    ld a, [wPlayerGender] ; added gender check
    and a      ; added gender check
    jr z, .BoySpriteLoad
    ld de, LeafSprite
    ld hl, vNPCSprites
    ld bc, (BANK(LeafSprite) << 8) + $0c
    jr .KeepLoadingSpriteStuff
.BoySpriteLoad
    ld de, RedSprite
    ld hl, vNPCSprites
    lb bc, BANK(RedSprite), $c
.KeepLoadingSpriteStuff
    call CopyVideoData
    ld a, [wPlayerGender] ; added gender check
    and a      ; added gender check
    jr z, .BoyTiles ; skip loading Leaf's stuff if you're Red
    ld a, $4
    ld hl, LeafFishingTiles
    jr .ContinueRoutine ; go back to main routine after loading Leaf's stuff
.BoyTiles ; alternately, load Red's stuff
    ld a, $4
    ld hl, RedFishingTiles
.ContinueRoutine
    call LoadAnimSpriteGfx

Now I know, I know. That looks like a mess. But it's really just more of the same stuff we did in the intro. All we've done is copy part of it to make an alternate version it can load to get the girl's sprite and fishing tiles. Speaking of those fishing tiles, we'll need to add that little table it is referencing.

So let's scroll down a bit until we see:

RedFishingTiles:
    dw RedFishingTilesFront
    db 2, BANK(RedFishingTilesFront)
    dw vNPCSprites + $20

    dw RedFishingTilesBack
    db 2, BANK(RedFishingTilesBack)
    dw vNPCSprites + $60

    dw RedFishingTilesSide
    db 2, BANK(RedFishingTilesSide)
    dw vNPCSprites + $a0

    dw RedFishingRodTiles
    db 3, BANK(RedFishingRodTiles)
    dw vNPCSprites2 + $7d0

We'll want to add a new table under it, so that it will look like this:

RedFishingTiles:
    dw RedFishingTilesFront
    db 2, BANK(RedFishingTilesFront)
    dw vNPCSprites + $20

    dw RedFishingTilesBack
    db 2, BANK(RedFishingTilesBack)
    dw vNPCSprites + $60

    dw RedFishingTilesSide
    db 2, BANK(RedFishingTilesSide)
    dw vNPCSprites + $a0

    dw RedFishingRodTiles
    db 3, BANK(RedFishingRodTiles)
    dw vNPCSprites2 + $7d0
    
LeafFishingTiles: ; newly added table of Leaf's sprites
    dw LeafFishingTilesFront
    db 2, BANK(LeafFishingTilesFront)
    dw vNPCSprites + $20

    dw LeafFishingTilesBack
    db 2, BANK(LeafFishingTilesBack)
    dw vNPCSprites + $60

    dw LeafFishingTilesSide
    db 2, BANK(LeafFishingTilesSide)
    dw vNPCSprites + $a0

    dw RedFishingRodTiles
    db 3, BANK(RedFishingRodTiles)
    dw vNPCSprites2 + $7d0

You'll notice that leaf's table still calls one of the original graphics that Red used. I don't see a point in making an identical copy of the actual fishing pole tiles, only the part that is the actual player, so her table calls the same fishing rod sprite the boy did.

Now to move on to your walking and cycling sprites. You'll open /home/overworld.asm and take a look at it for this part. You'll want to find the routine called LoadWalkingPlayerSpriteGraphics for this part. You'll eventually find a routine that looks like this:

LoadWalkingPlayerSpriteGraphics::
    ld de,RedSprite
    ld hl,vNPCSprites
    jr LoadPlayerSpriteGraphicsCommon

LoadSurfingPlayerSpriteGraphics::
    ld de,SeelSprite
    ld hl,vNPCSprites
    jr LoadPlayerSpriteGraphicsCommon

LoadBikePlayerSpriteGraphics::
    ld de,RedCyclingSprite
    ld hl,vNPCSprites

And we'll just change this up a little to look like this:

LoadWalkingPlayerSpriteGraphics::
    ld de,RedSprite
    ld a, [wPlayerGender]
    and a
    jr z, .AreGuy1
    ld de,LeafSprite
.AreGuy1
    ld hl,vNPCSprites
    jr LoadPlayerSpriteGraphicsCommon

LoadSurfingPlayerSpriteGraphics::
    ld de,SurfingLapras
    ld hl,vNPCSprites
    jr LoadPlayerSpriteGraphicsCommon

LoadBikePlayerSpriteGraphics::
    ld de,RedCyclingSprite
    ld a, [wPlayerGender]
    and a
    jr z, .AreGuy2
    ld de,LeafCyclingSprite
.AreGuy2
    ld hl,vNPCSprites

Now you can save this file, because that is all we had to do in here. If you were to scroll down a little more, you would see that we didn't mess with the part of the code that loaded which bank these sprites were in. That is why we kept Red and Leaf in the same bank when we inserted their sprites. It just seemed simpler to do it that way to me. As with all of the other sections, you'll probably want to stop and compile the rom again to make sure everything went ok before moving on.

Step 5: Adding The Girl's Backsprite.

This section will be relatively short compared to the others, because there isn't much to do here. We'll open up engine/battle/core.asm for this part.

Search until you find LoadPlayerBackPic: and see that it looks like this:

LoadPlayerBackPic:
    ld a, [wBattleType]
    dec a ; is it the old man tutorial?
    ld de, RedPicBack
    jr nz, .next
    ld de, OldManPic
.next

You'll just want to change this to be:

LoadPlayerBackPic:
    ld a, [wBattleType]
    dec a
    ld de, OldManPic
    jr z, .next
    ld a, [wPlayerGender]
    and a
    jr z, .RedBack
    ld de, LeafPicBack
    jr .next
.RedBack
    ld de, RedPicBack
.next

This just reorganises that a bit and adds in the check for the girl's backsprite. This also assumes that all 3 backpics are stored in the same bank, so make sure you did that unless you want to mess with the routine more on your own to allow them to be in different banks.

As always, you'll probably want to save and compile to test this before going on.

Step 6: Adding The Girl To The Hall Of Fame.

For this step, you'll want to open /engine/hall_of_fame.asm and search for HoFLoadPlayerPics: to get to the function we need. It should look something like this:

HoFLoadPlayerPics:
    ld de, RedPicFront
    ld a, BANK(RedPicFront)
    call UncompressSpriteFromDE
    ld hl, sSpriteBuffer1
    ld de, sSpriteBuffer0
    ld bc, $310
    call CopyData
    ld de, vFrontPic
    call InterlaceMergeSpriteBuffers
    ld de, RedPicBack
    ld a, BANK(RedPicBack)
    call UncompressSpriteFromDE

We'll want to edit that so it looks like this:

HoFLoadPlayerPics:
    ld a, [wPlayerGender] ; New gender check
    and a      ; New gender check
    jr nz, .GirlStuff1
    ld de, RedPicFront
    ld a, BANK(RedPicFront)
    jr .Routine ; skip the girl stuff and go to main routine
.GirlStuff1
    ld de, LeafPicFront
    ld a, BANK(LeafPicFront)
.Routine ; resume original routine
    call UncompressSpriteFromDE
    ld hl, sSpriteBuffer1
    ld de, sSpriteBuffer0
    ld bc, $310
    call CopyData
    ld de, vFrontPic
    call InterlaceMergeSpriteBuffers
    ld a, [wPlayerGender] ; new gender check
    and a      ; new gender check
    jr nz, .GirlStuff2
    ld de, RedPicBack
    ld a, BANK(RedPicBack)
    jr .routine2 ; skip the girl stuff and continue original routine if guy
.GirlStuff2
    ld de, LeafPicBack
    ld a, BANK(LeafPicBack)
.routine2 ; original routine
    call UncompressSpriteFromDE

This will change it so it shows the girl's front and back sprites when your team is entered in the hall of fame. Save it and you are done with this step.

Step 7: Adding The Girl To The Trainer Card

This is the final step in the tutorial. You'll want to open up /engine/menu/start_sub_menus.asm for this part. Search for the function DrawTrainerInfo: and you should see something like this:

DrawTrainerInfo:
    ld de,RedPicFront
    lb bc, BANK(RedPicFront), $01
    predef DisplayPicCenteredOrUpperRight

So we'll just change that to:

DrawTrainerInfo:
    ld de,RedPicFront
    lb bc, BANK(RedPicFront), $01
    ld a, [wPlayerGender]
    and a
    jr z, .AreBoy
    ld de, LeafPicFront
    lb bc, BANK(LeafPicFront), $01
.AreBoy
    predef DisplayPicCenteredOrUpperRight

And you should be all set! Save it, compile it, and give it a test. If everything went as planned (and assuming I didn't accidentally leave anything out when writing this) you should now have a fully functioning gender selection system in place in Pokemon Red. Let me know if you have any problems and I will try my best to help you figure them out.

Credits:
IIMarckus, Kanzure, comet, Danny-E33, Sanky, and everyone else who contributed to the Pokered disassembly project.
Danny-E33 - Getting me interested in Pokered, and for the Gen II backsprite routine I used in that video
Pia Carrot - Talking about Pokered a lot at PHO and originally asking me to write this tutorial.
ないすべての情報が必要です。- Asking about this on Discord until I updated it.

Last edited by Mateo (2017-08-03 03:07:09)

Offline

#2 2014-09-24 02:53:33

Danny-E 33
Administrator
Registered: 2012-06-09
Post 819/1,119

Re: [Pokered] Adding Gender Selection

Wow, this is pretty awesome. Very thorough tutorial. I wonder why the North/West menu ever existed in the first place.

Offline

#3 2014-09-24 03:29:42

Mateo
Member
From: The Sims 4
Registered: 2009-11-25
Post 2,904/3,578

Re: [Pokered] Adding Gender Selection

My best guess is that the unused directional menus would somehow have been used in the Safari Zone, but as to how, I have no idea.

Offline

#4 2014-09-24 04:20:13

ShantyTown
Member
Registered: 2013-12-04
Post 146/344

Re: [Pokered] Adding Gender Selection

Perhaps a random NPC wondering which way you took to get to Fuchsia City?

Offline

#5 2014-09-24 08:46:50

ttar1
Member
From: Internet
Registered: 2014-06-16
Post 44/45
Website

Re: [Pokered] Adding Gender Selection

wow


My Web:
http://www.facebook.com/ttar1romhacker
My Hacks:
Pokemon Plasma(Hack of gold currently in progress)
Do not underestimate the power of a beginner hacker.

Offline

#6 2014-11-18 23:15:41

daMoose52
Member
Registered: 2014-11-14
Post 3/108
Website

Re: [Pokered] Adding Gender Selection

Very nice.
Any idea how far off this throws some of the other established data?


Pokemon: Project Neo A Pokemon hack 15 years in the making...

Offline

#7 2014-11-18 23:47:03

Danny-E 33
Administrator
Registered: 2012-06-09
Post 824/1,119

Offline

#8 2014-11-19 01:58:53

daMoose52
Member
Registered: 2014-11-14
Post 5/108
Website

Re: [Pokered] Adding Gender Selection

I've got a lot of tools, somewhat old but useful, that I'm comfortable with hacking the rom. Getting more comfortable with the ASM directly but, old dogs and new tricks as it were.


Pokemon: Project Neo A Pokemon hack 15 years in the making...

Offline

#9 2015-05-05 17:12:10

Mateo
Member
From: The Sims 4
Registered: 2009-11-25
Post 3,020/3,578

Re: [Pokered] Adding Gender Selection

By the way, I've updated this slightly to hopefully make it compatible with current versions of Pokered. I changed the Boy/Girl Menu routine to use "wTextBoxID" instead of "wd125" like the current versions do.

Offline

#10 2015-10-25 08:39:00

Fotomac
Member
Registered: 2015-10-25
Post 3/332

Re: [Pokered] Adding Gender Selection

That's all well and good, but...

xor a
    ld [$FFD7],a
    ld a,[wd732]
    bit 1,a ; XXX when is bit 1 set?
    jp nz,Func_61bc ; easter egg: skip the intro

Wordpad, which I am largely using to edit the ASM code (I've succeeded thus far in using Wordpad to anti-censor that scene early on in Viridian City with the old man who teaches you how to catch Pokémon–originally, he was drunk instead of not having had his coffee), searched the entirety of /engine/oak_speech.asm and couldn't find it. That is where I'm lost. Heck, I even checked the original file on Github and couldn't find it. (And yes, I'm positive I'm following your instructions.)

Offline

#11 2015-10-25 09:52:36

Fotomac
Member
Registered: 2015-10-25
Post 4/332

Re: [Pokered] Adding Gender Selection

Sorry for the double post, but whenever I try to compile the ROM after having done everything up to Step 3, I get the following error:

"Unknown symbol 'PlayMusic'"

Am I doing something wrong?

Offline

#12 2015-10-25 10:02:48

megamctaco
Member
Registered: 2015-08-23
Post 56/129

Re: [Pokered] Adding Gender Selection

ld hl, wd798 ; load ram address of Gender

This seems to be the only thing not working for me so far. wd798 does not exist in my version. Any ideas what the alternative would be?

EDIT: Worked it out. Just had to change it to $14.

Last edited by megamctaco (2015-10-25 10:22:06)

Offline

#13 2015-10-25 10:57:19

Crystal_
Member
From: Spain
Registered: 2012-09-16
Post 328/450
Website

Re: [Pokered] Adding Gender Selection

If you mean that you changed it to ld hl, $14, then that is just so wrong. Replace it with ld hl, $d798 if anything.

Offline

#14 2015-10-25 11:10:42

megamctaco
Member
Registered: 2015-08-23
Post 57/129

Re: [Pokered] Adding Gender Selection

Crystal_ wrote:

If you mean that you changed it to ld hl, $14, then that is just so wrong. Replace it with ld hl, $d798 if anything.

All that got me was a bunch of "Expression must be 8-bit" errors.

As it stands, I can compile Red but not Blue, as "GetDefaultName" is having trouble with Blue version only for some reason. EDIT: Female sprite loads when either boy or girl are selected.

I should mention, I am up to step 4 but can't seem to compile after changing player_animations.asm and overworld.asm. Either a ROMX error or ROM0 too large error.

Last edited by megamctaco (2015-10-25 11:22:14)

Offline

#15 2015-10-25 14:40:14

Mateo
Member
From: The Sims 4
Registered: 2009-11-25
Post 3,078/3,578

Re: [Pokered] Adding Gender Selection

The romx error means you are trying to put more in a bank than you have room for.

The issue with the name not being found is the problem with me writing this tutorial on an older version of pokered, and label/variable/etc names getting changed over time. I'll look up the proper name and update this after I have my coffee.

EDIT: Ok, I see what is causing so much trouble here. Apparently some time in the past, they stopped declaring event bytes manually, and made up a macro thing for it and just labeled the start of that block of data with an actual label, not each byte. In the original tutorial, we were just using one of the unused bits in the byte that kept up with trainers in one level of Cinnabar Mansion. It isn't the best way to do it, but it was convenient at the time since it was unused and would be saved properly. Now that the save routines have been vastly improved, it would be simpler to just add a new entry in wram.asm for wPlayerGender and reference that. At some point I'll get around to properly updating this tutorial to use the current label names, and to use a custom ram address instead of trying into that trainer byte (because what if you wanted to add more trainers to that map?)

Also, I noticed that for some reason I was still using the hard coded address $cc26 instead of wCurrentMenuItem like I should be when checking what your answer was in the intro. That's probably why it was always setting you as the girl when you tried it. If you shifted data around in ram it's probably you moved stuff so labels worked fine but the hardcoded address was probably pointing to the wrong thing or something.


As a quick fix version of how to fix some of this:

In engine/oak_speech.asm the block of code you are looking for now looks like:

xor a
    ld [hTilesetType],a
    ld a,[wd732]
    bit 1,a ; possibly a debug mode bit
    jp nz,.skipChoosingNames

so you would put the code for choosing the gender between that and the part about loading oak's pic.


And where you see:

ld a, [$cc26]

you would change it to:

ld a, [wCurrentMenuItem]



Then you would replace any instance of:

wd798

with:

wPlayerGender

and then you would need to go into wram.asm, and somewhere between "wMainDataStart::" and "wMainDataEnd::" you would need to add

wPlayerGender::
     ds 1

And that aught to take care of that. As for issues with running out of space in rom banks, does it give you any information about which bank is full? You shouldn't have issues with any of the code, so it's probably an issue with graphics somewhere, but hard to say without knowing what all is going on.

Last edited by Mateo (2015-10-25 15:17:46)

Offline

#16 2015-10-26 01:38:51

Fotomac
Member
Registered: 2015-10-25
Post 5/332

Re: [Pokered] Adding Gender Selection

OK, I'm doing this step by step, and when I added Leaf's overworld walking and cycling sprites, I expected errors and got "Unable to load fixed ROMX section into bank $05". When I then moved two sets of overworld sprites into a different bank to compensate, I got–guess what–"Unknown symbol 'PlayMusic'". Any idea what's causing this?

Offline

#17 2015-10-26 02:29:16

Mateo
Member
From: The Sims 4
Registered: 2009-11-25
Post 3,082/3,578

Re: [Pokered] Adding Gender Selection

If you are following the tutorial correctly, I can think of absolutely no reason why it would claim to be unable to find "PlayMusic" because that doesn't even begin to make sense in this situation o.O Are you sure all you did was move the INCLUDE lines for a couple of overworld sprites to cause that to happen?

Offline

#18 2015-10-26 02:32:57

Fotomac
Member
Registered: 2015-10-25
Post 6/332

Re: [Pokered] Adding Gender Selection

No, I'm pretty sure all I did was cut and paste the lines for the Giovanni and Rocket sprites to NPC Sprites 1, following the example in the tutorial, and suddenly Cygwin's all "Unknown symbol 'PlayMusic'" for reasons I can't explain either.

Offline

#19 2015-10-26 02:39:20

Mateo
Member
From: The Sims 4
Registered: 2009-11-25
Post 3,083/3,578

Re: [Pokered] Adding Gender Selection

Moving those sprites should have absolutely zero impact on the PlayMusic routine, so something has to be up. Does it give any clue as to which file is throwing that error? PlayMusic is called all over the place. I'm guessing that maybe you accientally added a linebreak somewhere so it has a line starting with PlayMusic instead of "call PlayMusic" so it is saying "whoa, PlayMusic isn't a command or a macro, idk what to do with this". I could be wrong, but that's the only thing coming to my mind as making sense at the moment.


EDIT: Also, which text editor are you using to edit the .asm files? I ask because regular notepad tends to have difficulty behaving properly when working with these .asm files, and notepad++ is greatly preferred since it doesn't do weird things like try to change linebreaks and stuff the way normal Notepad does.

Last edited by Mateo (2015-10-26 02:40:44)

Offline

#20 2015-10-26 02:47:09

Fotomac
Member
Registered: 2015-10-25
Post 7/332

Re: [Pokered] Adding Gender Selection

When I enter:

cd pokered

make

I get this:

rgblink -n pokered.sym -o pokered.gbc red/audio.o red/main.o red/text.o red/wram.o
C:\cygwin64\usr\local]bin\rgblink.exe: Unknown symbol 'PlayMusic'
Makefile:79: recipe for target 'pokered.gbc' failed
make: *** [pokered.gbc] Error 1

There's the problem: it didn't give me any obvious clues, and I couldn't find PlayMusic anywhere in the main.asm file.

Can you replicate this error with the current version of Pokered by following each step of your own tutorial, right up to and including the point where the Giovanni and Rocket sprites are moved to NPC Sprites 1? For all I know, I might very well be the first to encounter this error while trying to insert the female player character.

Last edited by Fotomac (2015-10-26 02:47:59)

Offline

#21 2015-10-26 02:49:58

Mateo
Member
From: The Sims 4
Registered: 2009-11-25
Post 3,084/3,578

Re: [Pokered] Adding Gender Selection

I'm not really in a place where I can just do that right now. But yeah, that error message is precisely as unhelpful as I was afraid it would be :/

Again, what text editor are you using to edit the .asm files? Because I do remember another user having similarly baffling and unrelated errors when using Notepad instead of Notepad++ because Notepad was screwing up the file's formatting and causing it to feed a bunch of jibberish to the compiler.

Offline

#22 2015-10-26 02:56:16

Fotomac
Member
Registered: 2015-10-25
Post 8/332

Re: [Pokered] Adding Gender Selection

I didn't use WordPad this time; I was forced to use Notepad on account of WordPad feeding me the following bull:

You are about to save the document in a Text-Only format, which
will remove all formatting. Are you sure you want to do this?

To save in other format, click No.

After which, should I click No, I get directed to the Save As window, which gives me the option to save this in any of six types of documents none of which are ASM.

Offline

#23 2015-10-26 02:58:49

Mateo
Member
From: The Sims 4
Registered: 2009-11-25
Post 3,085/3,578

Re: [Pokered] Adding Gender Selection

I highly recommend you download and use Notepad++. It is free, easy to setup, has syntax highlighting built in so the code is more readable, and it doesn't screw up formatting.

Offline

#24 2015-10-26 02:59:22

megamctaco
Member
Registered: 2015-08-23
Post 58/129

Re: [Pokered] Adding Gender Selection

Made those changes you suggested and now I'm getting a "Value must be 8-bit" when I changed wd798 to wPlayerGender.

I tried changing that to [wPlayerGender] and got a syntax error.

Offline

#25 2015-10-26 03:00:34

Fotomac
Member
Registered: 2015-10-25
Post 9/332

Re: [Pokered] Adding Gender Selection

Problem appears to be solved; it would appear the Notepad save changed the font to MS Mincho (which I am guessing Cygwin or rgblink or whatever stumbled across the error didn't recognize), so I changed it back to Courier New and saved; the "Unknown symbol 'PlayMusic'" error didn't appear after that, so it would appear Notepad was the responsible party.

Offline

Board footer

Powered by FluxBB