• Our software update is now concluded. You will need to reset your password to log in. In order to do this, you will have to click "Log in" in the top right corner and then "Forgot your password?".
  • Welcome to PokéCommunity! Register now and join one of the best fan communities on the 'net to talk Pokémon and more! We are not affiliated with The Pokémon Company or Nintendo.

Simple Modifications Directory

Lunos

Random Uruguayan User
3,114
Posts
15
Years
  • Display Mugshots/Other Images In The Overworld (Emerald / Firered)

    This modification allows you to load images onto BG0 from a script. It can only show one 16-color image at a time.
    53dUjef.png
    XVCLIMD.png


    1. Installation
    Spoiler:


    2. Adding new mugshots
    Spoiler:


    3. Using mugshots in a script
    Spoiler:
    I made a quick macro to use this feature in a prettier and more convenient manner.
    Dropping it here in case anyone's interested:
    Code:
    	@ Calls a msgbox with a desired mugshot, string and msgbox type.
    	.macro msgbox_mugshot msgText:req, msgType:req, mugshot:req
    	setvar VAR_0x8000, \mugshot
    	callnative DrawMugshot
    	msgbox \msgText, \msgType
    	callnative ClearMugshot
    	.endm

    Example of usage:
    Code:
    InsideOfTruck_EventScript_MovingBox::
    	msgbox_mugshot InsideOfTruck_Text_BoxPrintedWithMonLogo, MSGBOX_SIGN, MUGSHOT_GREEN
    	end

    EDIT: It goes in asm/macros/event.inc like any other overworld scripting macro, by the way.

    EDIT2: I made a few additions for those who may want a way to retain the mugshots on screen:
    Code:
    	@ Calls a msgbox with a desired mugshot, string and msgbox type.
    	CLEAR_MUGSHOT = TRUE
    	DONT_CLEAR_MUGSHOT = FALSE
    	.macro msgbox_mugshot msgText:req, msgType:req, mugshot:req, clear=CLEAR_MUGSHOT
    	setvar VAR_0x8000, \mugshot
    	callnative DrawMugshot
    	msgbox \msgText, \msgType
    	.if \clear == CLEAR_MUGSHOT
    		callnative ClearMugshot
    	.endif
    	.endm

    Example of usage:
    Code:
    InsideOfTruck_EventScript_MovingBox::
    	msgbox_mugshot InsideOfTruck_Text_BoxPrintedWithMonLogo, MSGBOX_SIGN, MUGSHOT_GREEN, DONT_CLEAR_MUGSHOT
    	end

    oGOOZWl.gif
     
    Last edited:

    Jaizu

    Average rom hacker
    281
    Posts
    14
    Years
  • [pokéemerald] Checking how much ash you collected with the Soot Sack

    If you're looking to get all the items the glass workshop on route 113 can make, you'll have to walk through a lot of volcanic ash – the pretty desk requires 8000 steps! I remember back when I repeatedly walked back and forth collecting ash, I wish I had an easy way to check how much I've collected without going back to the workshop and talking to the glass maker. Well, thanks to disassembly, we can make that happen. It's real simple too, as the code is based on what is used for the coin case and powder jar.

    In scr/item_use.c, add the following functions (I added mine after ItemUseOutOfBattle_PowderJar). The first function displays the message when the soot sack is used and the second function gets the ash count for the first function to use.
    Code:
    void ItemUseOutOfBattle_SootSack(u8 taskId)
    {
    	ConvertIntToDecimalStringN(gStringVar1, GetAshCount(), STR_CONV_MODE_LEFT_ALIGN, 4);
    	StringExpandPlaceholders(gStringVar4, gText_AshQty);
    	if (!gTasks[taskId].tUsingRegisteredKeyItem)
    	{
    		DisplayItemMessage(taskId, 1, gStringVar4, BagMenu_InitListsMenu);
    	}
    	else
    	{
    		DisplayItemMessageOnField(taskId, gStringVar4, Task_CloseCantUseKeyItemMessage);
    	}
    }		
    
    u16 GetAshCount(void)
    {
    	u16 *ashGatherCount;
    	ashGatherCount = GetVarPointer(VAR_ASH_GATHER_COUNT);
    	return *ashGatherCount;
    }
    Then in include/item_use.h, declare the functions we just added:
    Code:
    void ItemUseOutOfBattle_SootSack(u8);
    u16 GetAshCount(void);

    Now in src/strings.c, add the following string. This is the message the 1st function will display.
    Code:
    const u8 gText_AshQty[] = _("ASH QTY:\n{STR_VAR_1}{PAUSE_UNTIL_PRESS}");

    Next, add the declaration for the new string in include/strings.h:
    Code:
    extern const u8 gText_AshQty[];

    Finally, in src/data/items.h change .fieldUseFunc for the Soot Sack to use the first new function we created. It should look like this when you're done:
    Code:
    [ITEM_SOOT_SACK] =
        {
            .name = _("SOOT SACK"),
            .itemId = ITEM_SOOT_SACK,
            .price = 0,
            .description = sSootSackDesc,
            .importance = 1,
            .pocket = POCKET_KEY_ITEMS,
            .type = 4,
            .fieldUseFunc = ItemUseOutOfBattle_SootSack,
            .secondaryId = 0,
        },

    And you're done! Pressing on use with the soot sack will show you the quantity of ash you have. It's simple but I'm proud of it cause I'm new to disassembly stuff and since I haven't seen it listed here yet so I thought, Wynaut add it?

    Video example:
    turns out I can't post links yet, but put this in your address bar on youtube, after the dot com /watch?v=E0rngXrOUb4

    This won't compile on an up-to-date repo.
    Use this function instead:
    Code:
    void ItemUseOutOfBattle_SootSack(u8 taskId)
    {
    	ConvertIntToDecimalStringN(gStringVar1, GetAshCount(), STR_CONV_MODE_LEFT_ALIGN, 4);
    	StringExpandPlaceholders(gStringVar4, gText_AshQty);
    	if (!gTasks[taskId].tUsingRegisteredKeyItem)
    		DisplayItemMessage(taskId, FONT_NORMAL, gStringVar4, CloseItemMessage);
    	else
    		DisplayItemMessageOnField(taskId, gStringVar4, Task_CloseCantUseKeyItemMessage);
    }
     

    Lunos

    Random Uruguayan User
    3,114
    Posts
    15
    Years
  • Adding Hyper Training Stats [Em]
    So, earlier, Jaizu was looking into adding the variables for Hyper Training to one of his projects.
    These values signal the function used for stat calculations that the IVs of a Pokémon should be calculated as if they were maxed out.
    The feature was originally added in Pokémon Sun/Moon.
    I decided to give it a go myself because I was bored enough.
    I got a working implementation, but I made some extra changes that were not needed at first.
    So, after optimizing that out with Jaizu's help, I decided to come and post what I made here because why not.
    It'd be a waste not to since I don't intend to use this myself anytime soon.

    It's hard to showcase it, but in the following sheet, you can see the stats of a Torchic and a Magikarp before (top) and after (bottom) their stats' HYPER_TRAINED variables were flipped to TRUE.
    ztUGIXn.png


    To implement this, you can track my GitHub repository via git remote and pull the branch hyperTraining which is where I'm hosting the code:
    Code:
    git remote add lunos https://github.com/LOuroboros/pokeemerald
    git pull lunos hyperTraining
    Or you can implement things manually.
    https://github.com/pret/pokeemerald/compare/master...LOuroboros:hyperTraining

    Setting each hyper trained stat's parameters to TRUE is naturally up to the user.
    For testing purposes, I made a field special that I invoked in a script via callnative to set the hyper trained stats for the 1st Pokémon in the party.
    Code:
    void HyperTrainPartyLeaderStats(void)
    {
        u8 value = TRUE;
        SetMonData(&gPlayerParty[0], MON_DATA_HYPER_TRAINED_HP, &value);
        SetMonData(&gPlayerParty[0], MON_DATA_HYPER_TRAINED_ATK, &value);
        SetMonData(&gPlayerParty[0], MON_DATA_HYPER_TRAINED_DEF, &value);
        SetMonData(&gPlayerParty[0], MON_DATA_HYPER_TRAINED_SPEED, &value);
        SetMonData(&gPlayerParty[0], MON_DATA_HYPER_TRAINED_SPATK, &value);
        SetMonData(&gPlayerParty[0], MON_DATA_HYPER_TRAINED_SPDEF, &value);
        CalculateMonStats(&gPlayerParty[0]);
    }

    And that's pretty much it.​
     
    Last edited:
    31
    Posts
    3
    Years
  • Increase bag item capacity(em)

    When I increase TMHM capacity,I discover this code:
    #define MAX_BAG_ITEM_CAPACITY 99
    So I try to increase bag item capacity.

    Firstly,open include/constants/items.h,and change MAX_BAG_ITEM_CAPACITY to 999,change BAG_ITEM_CAPACITY_DIGITS to 3.

    Then,open src/item.c,search AddPyramidBagItem,Change "*newquantities" in this function to u16.

    Finally,open include/shop.h,In the "shopdata",change maxquantity to u16.

    I haven't found any bugs yet.

    Hi Sir!!! i have a question on shopdata is it shopdata c or h?...and if its shop.c where is this "maxquantity" located...sorry im just a newbie... im having a hard time to find this because of quick or just shortcut guide... thanks!!!!
     
    31
    Posts
    3
    Years
  • in my rom there was this error according to the image because I'm using the expanded bag, I don't know if it would have a link or not, it's the only thing I think could cause a problem. Even when it disappears from this black screen, it goes straight to another screen and freezes the game, but if you register the item as in Key items, nothing happens.

    Hi Sir!!! how and where did you change the last part.. (Finally,open include/shop.h,In the "shopdata",change maxquantity to u16.) Thank you!!
     
    13
    Posts
    3
    Years
    • Seen yesterday
    Trainer Class-Based Poké Balls (Emerald)
    G4PC9Bn.gif
    Trainers in the gen VII games send out their Pokemon in different balls depending what class they are, so I've implemented that in Emerald.

    First, go to include\battle_main.h and add a new struct like so:
    Code:
    struct TrainerBall
    {
        u8 classId;
        u8 Ball; // make this a u16 if needed
    };
    Then add a table of these to src\battle_main.c:
    Spoiler:
    Finally, add the code in bold to the end of the first for loop in the function CreateNPCTrainerParty, which is also in src\battle_main.c, like so:
    Spoiler:

    Hello good! I tried this and the truth is that it works very well, I like it. But I found that for Battle Frontier battles this doesn't apply, and all trainers will still throw normal pokeballs. Would it be possible to make this addition?
     
    1,591
    Posts
    10
    Years
    • Seen Mar 20, 2024
    Hello good! I tried this and the truth is that it works very well, I like it. But I found that for Battle Frontier battles this doesn't apply, and all trainers will still throw normal pokeballs. Would it be possible to make this addition?
    It's 100% possible. The frontier trainers use separate trainer classes with the same names as the normal trainer classes (I don't know why), so that's why they're unaffected by this change. You could do something similar to this to the code that generates frontier Pokémon to get it working there too.
     

    Lunos

    Random Uruguayan User
    3,114
    Posts
    15
    Years
  • Generation III+ sets the power of these moves to 1 if the formula spits out 0. As it is implemented right now, the summary screen can report 0 as the power. Calculating the power first and then setting it to 1 if it's 0 before printing is the fix.
    Read the 2 posts below that one.
     

    Deokishisu

    Mr. Magius
    990
    Posts
    18
    Years
  • This has been fixed in ghoulslash's repo, so I've spoilered my original post to save people scrolling space.
    Spoiler:
     
    Last edited:

    PerceptioN95

    ポケモントレーナ とみい
    36
    Posts
    6
    Years
    • Seen Nov 11, 2023
    Faster Soft Resets (Emerald)

    This modification makes soft resetting faster by taking the player straight to the continue/new game screen after a soft reset.
    EMjILQx.gif


    How to:
    Spoiler:


    EDIT: updated sub_815355C to GetSaveBlocksPointersBaseOffset

    sorry to bump,

    i get the following error, after copying everything you did 1:1

    tools/agbcc/bin/agbcc <flags> -o build/emerald/src/main.o src/main.c
    agbcc: warnings being treated as errors
    src/main.c: In function `CB2_PostSoftResetInit':
    src/main.c:458: warning: implicit declaration of function `Save_LoadGameData'
    make: *** [Makefile:342: build/emerald/src/main.o] Error 1
    make: *** Deleting file 'build/emerald/src/main.o'


    edit: seem to have fixed the issue

    replaced
    Save_LoadGameData(SAVE_NORMAL);

    with
    LoadGameSave(SAVE_NORMAL);

    leaving this here incase anyone needs it :)
     
    Last edited:
    51
    Posts
    13
    Years
  • [pokeemerald] Berries grow faster

    Very simple edit, in "src/berry.c" go to:

    Code:
    static u16 GetStageDurationByBerryType(u8 berry)
    {
        return GetBerryInfo(berry)->stageDuration * [COLOR="Red"]60[/COLOR];
    }

    And replace 60 with the number of your choice (that's the number of minutes a growth stage lasts).

    (I usually change it to 10).
     
    5
    Posts
    8
    Years
    • Seen Jun 9, 2023
    [Pokeemerald] Rock Climb

    This adds the gen 4 rock climb field effect to scale cliffs.

    3gvFEHy.gif
    I8JW7Ok.gif


    How to add:
    How to use:
    • Give your rock-climbable metatile the MB_ROCK_CLIMB behavior. That's it!

    Please report any bugs.

    I'm trying to implement your rock climb branch and, mechanically, it works great. However I'm having some graphical glitches that I can't seem to figure out (See attachment). any ideas how I can fix this?
    f66pzGP.png
     

    Attachments

    • RockClimbDistortion.png
      RockClimbDistortion.png
      3.7 KB · Views: 3
    51
    Posts
    13
    Years
  • Spoiler:

    Extra code you can add (lines highlighted in RED):

    Code:
        if (sPartyMenuInternal->numActions < 5 && CanMonLearnTMHM(&mons[slotId], ITEM_HM02 - ITEM_TM01)
    		[COLOR="Red"]&& (Overworld_MapTypeAllowsTeleportAndFly(gMapHeader.mapType) == TRUE))[/COLOR] [COLOR="SeaGreen"]// If map allows FLY[/COLOR]
            AppendToList(sPartyMenuInternal->actions, &sPartyMenuInternal->numActions, 5 + MENU_FIELD_MOVES);
        if (sPartyMenuInternal->numActions < 5 && CanMonLearnTMHM(&mons[slotId], ITEM_HM05 - ITEM_TM01)
    		[COLOR="Red"]&& (gMapHeader.cave == TRUE) && (!FlagGet(FLAG_SYS_USE_FLASH)))[/COLOR] [COLOR="SeaGreen"]// If map allows FLASH and it wasn't used already[/COLOR]
            AppendToList(sPartyMenuInternal->actions, &sPartyMenuInternal->numActions, 1 + MENU_FIELD_MOVES);

    With this, you can use FLY/FLASH only where it's possible, otherwise they won't appear on the list.
     
    247
    Posts
    6
    Years
    • Seen May 2, 2024
    Display Mugshots/Other Images In The Overworld (Emerald / Firered)
    ............

    Is there anyway to place the mugshot with more precision? I've been working on a project that uses this code, but the mugshot is always a little above the message box, leaving some space between the box and the mugshot, or it's clipping into the box. Changing the y-position shifts it by a lot, it seems. I know of other sprite-displaying functions like CreateMonSprite_PicBox that have a lot more precision, but I haven't been able to get the mugshot to display properly using one of those functions.
     
    448
    Posts
    6
    Years
    • Seen May 6, 2024
    Is there anyway to place the mugshot with more precision? I've been working on a project that uses this code, but the mugshot is always a little above the message box, leaving some space between the box and the mugshot, or it's clipping into the box. Changing the y-position shifts it by a lot, it seems. I know of other sprite-displaying functions like CreateMonSprite_PicBox that have a lot more precision, but I haven't been able to get the mugshot to display properly using one of those functions.

    The mugshots are drawn to a tiled background, limiting you to the 8x8 tile grid. You could probably do some blitting to get more precision, or you could use sprites, but that might not be necessary if your only concern is the space above message boxes.

    The easiest solution is to edit the message box graphic so that it doesn't have empty pixels above the textbox.
    Another option is to use a HBlank callback:
    Code:
    --- a/src/mugshot.c
    +++ b/src/mugshot.c
    @@ -7,6 +7,8 @@
     #include "palette.h"
     #include "event_data.h"
     #include "constants/mugshots.h"
    +#include "main.h"
    +#include "gpu_regs.h"
     
     #define MUGSHOT_PALETTE_NUM 13
     
    @@ -42,6 +44,7 @@ void ClearMugshot(void){
             CopyWindowToVram(sMugshotWindow - 1, 3);
             RemoveWindow(sMugshotWindow - 1);
             sMugshotWindow = 0;
    +        DisableInterrupts(INTR_FLAG_HBLANK);
         }
     }
     
    @@ -76,3 +79,12 @@ void DrawMugshotAtPos(void){
         DrawMugshotCore(sMugshots + VarGet(VAR_0x8000), VarGet(VAR_0x8001), VarGet(VAR_0x8002));
     }
     
    +void HBlank_Mugshot(void){
    +    REG_BG0VOFS = REG_VCOUNT > 113 ? 0 : -3;
    +}
    +
    +void DrawShiftedMugshot(void){ //Use this in your script instead of DrawMugshot
    +    DrawMugshot();
    +    SetHBlankCallback(HBlank_Mugshot);
    +    EnableInterrupts(INTR_FLAG_HBLANK);
    +}

    gEwRp6k.png


    The DrawShiftedMugshot function basically shifts everything above the textbox on BG0 down by three pixels. Obviously this will only work if you're not already using the HBlank callback for something else, and your mugshot doesn't touch the top of the screen.
     
    54
    Posts
    1
    Years
    • Seen Apr 14, 2024
    Then, we go to src/data/party_menu.h and we add:
    Code:
    MENU_MOVES,
    Anywhere in the the enum section with the menus. It's the one with "MENU_SUMMARY".

    After that, we search for "[MENU_SUMMARY] = {gText_Summary5, CursorCb_Summary}," and we add underneath:
    Code:
    [MENU_MOVES] = {gText_Moves_Menu, CursorCb_Moves},

    The ENUM list no longer exists in party_menu.h
    Is there something else I should do instead or is this just dead?
     

    セケツ

    ポケハック初心者
    61
    Posts
    7
    Years
    • Seen May 2, 2024
    [PokeEmerald] Make Cycling Music not get itself faded when stepping into another map.

    It has been a long time since my last post here, and here is another tiny & little discovery of myself, which I couldn't find in either here or the Pret's wiki site.
    It's known to us that in the original PokeEmerald, when player rides the bike and steps into a new map. Despite the player him(her)self is still on the bike, the cycling music in the background has been faded & changed into nothing but the music of the newmap itself.
    And today here, for anyone who wants to keep it still playing in background (Just like how the SURFING music did in the original game). Here are some tiny & simple changes for getting it works.
    Since it's a change for the music, for anyone still can't get what I'm saying, please take a clear comparison of the difference of how the music playing in the background between the SURFING & the CYCLING. Sorry there is no way to put up a explanation picture here.
    First, open the source code file named "overworld.c" laid in the src folder. And find the function named "TransitionMapMusic" in here, which takes the control of the music when it comes to the map transition. Just as its name said.

    u3CP4Fx.png


    Next, do some changes at those two if & else lines, as the picture I showed below.

    PjF7w2w.png


    Then save your code & test.

    I haven't found any bug yet, Moreover, if anyone else found it had been posted in any other place, please leave a comment or at least send a message, Then I will delete it in time. And certainly, if you find any bug, glitch, or something wrong with this tutorial. Please contact me as well.
    Thanks everyone for reading & really sorry for my poor English.
     
    54
    Posts
    1
    Years
    • Seen Apr 14, 2024
    Adding Hyper Training Stats [Em]

    Or you can implement things manually.
    https://github.com/pret/pokeemerald/compare/master...LOuroboros:hyperTraining

    Setting each hyper trained stat's parameters to TRUE is naturally up to the user.
    For testing purposes, I made a field special that I invoked in a script via callnative to set the hyper trained stats for the 1st Pokémon in the party.
    Code:
    void HyperTrainPartyLeaderStats(void)
    {
        u8 value = TRUE;
        SetMonData(&gPlayerParty[0], MON_DATA_HYPER_TRAINED_HP, &value);
        SetMonData(&gPlayerParty[0], MON_DATA_HYPER_TRAINED_ATK, &value);
        SetMonData(&gPlayerParty[0], MON_DATA_HYPER_TRAINED_DEF, &value);
        SetMonData(&gPlayerParty[0], MON_DATA_HYPER_TRAINED_SPEED, &value);
        SetMonData(&gPlayerParty[0], MON_DATA_HYPER_TRAINED_SPATK, &value);
        SetMonData(&gPlayerParty[0], MON_DATA_HYPER_TRAINED_SPDEF, &value);
        CalculateMonStats(&gPlayerParty[0]);
    }

    And that's pretty much it.​

    Attempted to add manually and received errors

    Spoiler:


    and further

    Spoiler:
     

    Lunos

    Random Uruguayan User
    3,114
    Posts
    15
    Years
  • Attempted to add manually and received errors

    Spoiler:
    Make sure you did declare those MON_DATA variables at include/pokemon.h.
    and further

    Spoiler:
    That one's unrelated.
    Your project's struct RecordedBattleSave is bigger than its maximum allocated size, so the Assert put in place to notify the user of this prevents the compiler from building a ROM.
     
    Back
    Top