Note that x & y are tile coordinates, so the mugshot will be drawn at (8*x, 8*y).
3. Using mugshots in a script
Spoiler:
There are 3 new functions, which you can call with the callnative command: DrawMugshot: draws mugshot that's id is in VAR_0x8000 DrawMugshotAtPos: draws mugshot that's id is in VAR_0x8000, at coordinates stored in VAR_0x8001 and VAR_0x8002 ClearMugshot: clears drawn mugshot
If a mugshot is drawn while one is already on the screen, the previous one is automatically cleared.
This feature lets us use a flag to spawn the player invisible after warping, which is useful for cutscenes (using a flag instead of requiring messy map scripts)
Locktarget Overworld scripting command (Em)
About an hour ago, SBird in Pret's Discord server brought up how the
lock
scripting command locks the movement of all the event objects on screen instead of just locking the event object that the Player is interacting with.
I decided to take a stab at it since it sounded like a fairly easy thing to address.
Note: Depending on the feature branches you use in your project, you may need to adjust some of these values.
For example, if you added other new scripting commands to your project you'll need to change the internal ID of
Making Pokémon with Poison Heal be unaffected by poison in the overworld (Em) Note: Poison Heal is an ability introduced in Gen. 4 and it's naturally not present in Pokemon Emerald by default.
This is mainly an optional thing you can add to projects that make use of DizzyEgg's battle_engine.
Earlier, Meister_anon from this forums' Discord server asked some tips because they wanted to make Pokémon with the Poison Heal ability not be affected by poison in the overworld, an effect that should have been implemented in the official games since its introduction, imo.
I decided to take a stab at it since it sounded like a fairly easy thing to do.
There are no commits this time. I won't make a branch because it's so utterly simple it doesn't warrant making one.
All you need to do is to go to the
Remove the need to water berries on rainy Routes (Emerald)
Ever watered berry trees in the thunderstorm on Route 119 and thought "this makes no sense"?
This little tweak will make any berry trees on specified routes give out their maximum number of berries all the time, as if the weather watered them for you!
Moderator notice:
We highly recommend reviewing the pokeemerald tutorials at the pokeemerald wiki, viewable here, as they are much more regularly maintained: https://github.com/pret/pokeemerald/wiki/Tutorials
–––– Original post follows:
I noticed that despite being updated recently, the starting post is missing quite a few older modifications.
Here is a list of them:
Greetings everyone, I've got a pretty desirable fix I think, with credit and thanks to Buffel Saft, for helping me understand the function, I was able to figure a simple way of adding fairy type to hidden power.
It's just a simple C trick but this should work for firered and leaf green. Emerald doesn't seem to have mystery type so unfortunately this wouldn't work for it.
in pokefirered there's a line of code that essentially says, if hidden power type is greater or equal to type mystery add 1. (this is to remove mystery type from pool of possible results.
if (gBattleStruct->dynamicMoveType >= TYPE_MYSTERY)
gBattleStruct->dynamicMoveType++;
the ++ is the plus 1.
now from messing around with effect spore I learned a trick of replacing an effect by setting it equal to another field. And that's what I did to get fairy in.
I replaced the above with this...
if (gBattleStruct->dynamicMoveType == TYPE_MYSTERY)
gBattleStruct->dynamicMoveType = TYPE_FAIRY;
The A-non Team
Trevenant
Lv. 100 @ 306
Points: 70
Challenge: Souls of the Damned
Legendary: TBA
Originally Posted by Meister_anon~Master_o f_None
[ Original Post ]
Greetings everyone, I've got a pretty desirable fix I think, with credit and thanks to Buffel Saft, for helping me understand the function, I was able to figure a simple way of adding fairy type to hidden power.
It's just a simple C trick but this should work for firered and leaf green. Emerald doesn't seem to have mystery type so unfortunately this wouldn't work for it.
in pokefirered there's a line of code that essentially says, if hidden power type is greater or equal to type mystery add 1. (this is to remove mystery type from pool of possible results.
if (gBattleStruct->dynamicMoveType >= TYPE_MYSTERY)
gBattleStruct->dynamicMoveType++;
the ++ is the plus 1.
now from messing around with effect spore I learned a trick of replacing an effect by setting it equal to another field. And that's what I did to get fairy in.
I replaced the above with this...
if (gBattleStruct->dynamicMoveType == TYPE_MYSTERY)
gBattleStruct->dynamicMoveType = TYPE_FAIRY;
Emerald does have the Mystery Type. Every game up to HeartGold and SoulSilver have it, in fact, as it was removed in Black and White (1).
It's highly likely your modification will work on a clean copy of Pokeemerald normally, assuming Hidden Power's type can be set to Type Mystery normally.
Pretty confident about that, if you want to go over the explanations yourself you can check out my thread on the topic Here.
also making this change *may* affect the odds/conditions for certain types appearing I can't confirm that as its theory and I'm not good with bitwise anyway.
And a last note to cover all the bases , while the theory for this is sound, I haven't been able to test yet, so I don't recommend using the trick to try to add any more than 1 type.
Because of the way types have to be added, I am unsure if increasing the number would cause you to run afoul of the non-battle types.
There could be simple ways around that, if you're knowledgeable/savvy but I just didn't feel comfortable leaving people without that warning.
The A-non Team
Trevenant
Lv. 100 @ 306
Points: 70
Challenge: Souls of the Damned
Legendary: TBA
The level-scaling logic I used is in `src/pokemon.c` in GetPartyMonCurvedLevel(). You will probably want to edit it; the logic I have here was to demonstrate it works, not designed around game balance.
Locations that can have pokemon with a very wide range of levels will continue to do so; the level ranges are moved up so that the maximum level for wild pokemon is now either the max level in the encounter table, or (2 * curvedLevel + max)/3, whichever is higher. This weights the levels closer to the curve than the original, while maintaining a distinction between low-level areas and high-level ones.
Wonder Trade (Em)
I've been working on this for the past 8 days or so, and after so many small issues that I solved thanks to the help of the gang at ROM Hacking Hideout, I think it's finally good to go.
This is a Pokeemerald port of Deokishisu's Wonder Trade system for Pokeruby, modified to suit my personal tastes and made compatible with the Pokeemerald-expansion.
Everything is pretty easy to modify as there's a handful of comments here and there, and the code in itself is easy to read too, so y'all can edit the whole thing as you see fit.
To incorporate this into a project automatically, you'll have to track my repository via
I tried to test it as thoroughly as I could, but I wouldn't be surprised if for whatever reason invalid species or items could be generated.
I appreciate any and all tests.
Bugs:
-Pokémon who can Mega Evolve or who can evolve into a species that can Mega Evolve, can't carry Y Mega Stones. Yes, this only applies to the Charmander Line, but still. (Fixed!)
Provides control over most aspects of NPC trainers and homogenizes party types. Based off part of Syreldar's hack. Thanks to UltimaSoul for helping me get it to work.
src/data/trainer_parties.h will need all structs changed to TrainerMon and src/data/trainers.h needs to have .TrainerMon instead of .NoItemDefaultMoves et al. Those are both already applied to vanilla, but if you've done substantial edits, keep your versions and then do the find-replace to change structs and .party type.
This has recently had some refactoring to save space and fix bugs.
I also have made a simpler version that's more space-efficient and does not involve manually selecting IVs and EVs. Instead, you set .build, .hiddenPower, and .difficulty to get an effort and IV setup that does roughly what you want. It's more limited but I'm personally finding it much better suited to my needs.
.build can be TRAINER_MON_DEFENSES, TRAINER_MON_SPEED_PHYS, TRAINER_MON_SPEED_SPEC, TRAINER_MON_HP_DEF, TRAINER_MON_HP_SPDEF, TRAINER_MON_PHYS, TRAINER_MON_SPEC, and determines EV allocation. Both of the speed options raise the corresponding attack stat. A default build at high difficulty allocates effort points evenly.
.difficulty TRAINER_EASIEST, TRAINER_EASY, TRAINER_MEDIUM only decide amount of IVs; TRAINER_MEDIUM is maxed. TRAINER_HARD, TRAINER_HARDER, and TRAINER_HARDEST allocate EVs and have maxed IVs. TRAINER_MAX is not player legal and assigns 255 EVs to each stat.
.hiddenPower takes TYPE_ constants. TYPE_NORMAL is default and gives either worst, best, or average IVs, depending on difficulty. The IV spreads used can be found in include/pokemon_iv_spreads.h .
menu which allows you to move held items directly between Pokémon in your party, instead of having to use the bag as a middle man.
I've had this up in my pokeemerald fork for a while, but I never got around to writing it up here. Since I originally made it, the relevant functions got actual names in pokeemerald, so I'm taking this as an opportunity to update it and post it here.
There's going to be multiple changes required across multiple files, so I'm going to try to keep them in a logical order that minimizes jumping between files. Also, at the end of each step, pokeemerald will still be in a compilable state if done properly.
In the code blocks throughout this post, new lines of code are highlighted with the color green. Red highlights denote deleted lines of code. If a line of code isn't highlighted either color, it is only included for context.
void CursorCb_MoveItemCallback(u8 taskId)
{
u16 item1, item2;
u8 buffer[100];
if (gPaletteFade.active || sub_81221EC())
return;
switch (PartyMenuButtonHandler(&gPartyMenu.slotId2))
{
case 2: // User hit B or A while on Cancel
HandleChooseMonCancel(taskId, &gPartyMenu.slotId2);
break;
case 1: // User hit A on a Pokemon
// Pokemon can't give away items to eggs or themselves
if (GetMonData(&gPlayerParty[gPartyMenu.slotId2], MON_DATA_IS_EGG)
|| gPartyMenu.slotId == gPartyMenu.slotId2)
{
PlaySE(SE_HAZURE);
return;
}
PlaySE(SE_SELECT);
gPartyMenu.action = PARTY_ACTION_CHOOSE_MON;
// look up held items
item1 = GetMonData(&gPlayerParty[gPartyMenu.slotId], MON_DATA_HELD_ITEM);
item2 = GetMonData(&gPlayerParty[gPartyMenu.slotId2], MON_DATA_HELD_ITEM);
// swap the held items
SetMonData(&gPlayerParty[gPartyMenu.slotId], MON_DATA_HELD_ITEM, &item2);
SetMonData(&gPlayerParty[gPartyMenu.slotId2], MON_DATA_HELD_ITEM, &item1);
// update the held item icons
UpdatePartyMonHeldItemSprite(
&gPlayerParty[gPartyMenu.slotId],
&sPartyMenuBoxes[gPartyMenu.slotId]
);
UpdatePartyMonHeldItemSprite(
&gPlayerParty[gPartyMenu.slotId2],
&sPartyMenuBoxes[gPartyMenu.slotId2]
);
// create the string describing the move
if (item2 == ITEM_NONE)
{
GetMonNickname(&gPlayerParty[gPartyMenu.slotId2], gStringVar1);
CopyItemName(item1, gStringVar2);
StringExpandPlaceholders(gStringVar4, gText_PkmnWasGivenItem);
}
else
{
GetMonNickname(&gPlayerParty[gPartyMenu.slotId], gStringVar1);
CopyItemName(item1, gStringVar2);
StringExpandPlaceholders(buffer, gText_XsYAnd);
StringAppend(buffer, gText_XsYWereSwapped);
GetMonNickname(&gPlayerParty[gPartyMenu.slotId2], gStringVar1);
CopyItemName(item2, gStringVar2);
StringExpandPlaceholders(gStringVar4, buffer);
}
// display the string
DisplayPartyMenuMessage(gStringVar4, TRUE);
// update colors of selected boxes
AnimatePartySlot(gPartyMenu.slotId2, 0);
AnimatePartySlot(gPartyMenu.slotId, 1);
// return to the main party menu
schedule_bg_copy_tilemap_to_vram(2);
gTasks[taskId].func = Task_UpdateHeldItemSprite;
break;
}
}
void CursorCb_MoveItem(u8 taskId)
{
struct Pokemon *mon = &gPlayerParty[gPartyMenu.slotId];
PlaySE(SE_SELECT);
// delete old windows
PartyMenuRemoveWindow(&sPartyMenuInternal->windowId[1]);
PartyMenuRemoveWindow(&sPartyMenuInternal->windowId[0]);
if (GetMonData(mon, MON_DATA_HELD_ITEM) != ITEM_NONE)
{
gPartyMenu.action = PARTY_ACTION_SWITCH;
// show "Move item to where" in bottom left
DisplayPartyMenuStdMessage(PARTY_MSG_MOVE_ITEM_WHERE);
// update color of first selected box
AnimatePartySlot(gPartyMenu.slotId, 1);
// set up callback
gPartyMenu.slotId2 = gPartyMenu.slotId;
gTasks[taskId].func = CursorCb_MoveItemCallback;
}
else
{
// create and display string about lack of hold item
GetMonNickname(mon, gStringVar1);
StringExpandPlaceholders(gStringVar4, gText_PkmnNotHolding);
DisplayPartyMenuMessage(gStringVar4, TRUE);
// return to the main party menu
schedule_bg_copy_tilemap_to_vram(2);
gTasks[taskId].func = Task_UpdateHeldItemSprite;
}
}
Edit: Oh, since I forgot to mention, my code here is licensed under the 0BSD license. In short, use it for whatever. Attribution is appreciated, but not required.
Preset Playable Character Name (Em)
I was bored, so after seeing a post presenting a different way to achieve this result in "Whack a Hack", I was inspired to come up with a variant of it myself.
As the title suggests, this makes it so the game won't let you select a name for the playable characters of the game.
Instead, their names are forced set by us.
To incorporate this into a project automatically, you'll have to track my repository via
There might come a day where you want to fade the screen to black in a script and play a fanfare, print a message, or do something else, and immediately warp. If you try this in vanilla emerald, the screen will fade FROM black, and then back TO black. Instead, let's create a flag that removes the fadescreen part of the warp script commands and we can do something like this:
Global Field Tints (Em)
I was bored, so I ported what in Pokefirered is known as
gGlobalFieldTintMode
.
What does this let you do? It allows you to put a tint on the elements shown on screen.
It should be a nice complement for flashback scenes and stuff like that.
Normally, in FRLG it's purely used in the flashbacks of the Quest Log feature of the game, which plays when you resume a savefile.
To incorporate this into a project automatically, you'll have to track my repository via
Bugs:
-Palette glitches when walking in the tall grass
Fixed.
-The rain looks black in game
I've no idea how to solve this and I also don't feel like working on this any longer.
Any valuable information on how to fix this or ideas about what to try would be well received.
Now with:
-SOUND!!!
-easy way to run custom scripts
-poison all party mons
-max money & max coins
-trigger daycare egg (no more running like crazy to test daycare changes)
-completly fill pc with pokemon
[Pokeemerald] Fully functional debug menu with Flags, Vars, Items, custom scripts, Pokemon and more!
This is my implementation of a debug menu based on Ketsuban's tutorial and some code from Pyredrid, AsparagusEduardo and Ghoulslash.
Features:
Spoiler:
Utility:
Heal player party
Clock: check and set
Fly to all cities: ----------------------------Warp to any map warp: --------------Check saveblock space:
Check weekday: does nothing, left in as a simple spot to add some test stuff for you guys
Change Trainer name, gender and OIT:
Flags:
Added some usefull debug flags like ignore collision, no wild encounters (Inmortal) and no trainers attacking you.
Toggle any flag ingame: -------------Toggle specific usefull flags
Vars:
Read and change any vars ingame:
Give:
Items:
All TMs:
Pokemon in 2 versions:
---Simple: only takes the ID (source code, not ingame) and a level:
---Complex: ID, level, shiny?, nature and ability (including hidden with PE), individual IVs and up to 4 custom moves.
How to:
Add and clone it into your repo:
git remote add xaman https://github.com/TheXaman/pokeemerald/
git pull xaman tx_debug_system
make clean
make
Access ingame:
From now one if you want the menu to show up you have to define TX_DEBUGGING in debug.h and delete/uncomment the line if you don't want it to show up.
To access ingame press R + Start.
That it, now enjoy and if you find any bugs or if you write some cool additions you think others could profit from, please let me know in this threat, via pm or over on github!
Credits: If you use this, you have to give credit to all following people!
TheXaman
Ketsuban
Pyredrid
AsparagusEduardo
Ghoulslash
ExboSeed
Sierraffinity
Jaizu