Comment on page
Functions found in all versions of Persona 5.
These functions are automatically included when using the P5 library of AtlusScriptCompiler. They are also found in P5R & P5EX libraries.
These functions are a simple way to display information to the player. Try it out!
This function comes before a message box function. It lets the game know to open the message before a message is loaded.
This function comes after a message box function. It lets the game know to close the message box after messages are loaded.
MSG()function shows a basic message box onscreen. This is usually used for characters having a verbal conversation. The first argument is the index of the message in the .msg file. The second argument is always
0and serves no purpose. You can use the name of the message in place of the index, and AtlusScriptCompiler will automatically interpret it.
// Imports messages from a nearby .msg file
// Example of a basic text box
MSG(firstMessage, 0); // same as MSG(0,0);
MSG(secondMessage, 0); // Same as MSG(1,0);
MSG(thirdMessage, 0); // Same as MSG(2,0);
MSG_MIND()function shows a thought bubble containing some text onscreen. This is usually used for the protagonist's inner thoughts. This works exactly the same as
// Example of a thought bubble message
MSG_SYSTEM()function shows a square grey box containing some text onscreen. This is usually used for game-related messages, such as tutorials or settings confirmation. This works exactly the same as
MSG_MIND()but lacks the unused argument.
// Example of a system message
These functions allow you to get some input from the player.
SEL()function takes a message index as an argument, just like
MSG(). The message must be of type
[msg]/[dlg]. It returns an integer-- the index of the option the user selected.
If used after a message box function, and before
MSG_WND_CLS(), the message will stay onscreen in the background of the menu, providing context to the player.
The type of message box used will determine the appearance. For instance,
MSG()(or no messagebox) will display the protagonist's portrait on the side of the screen. Meanwhile,
MSG_MIND()will display the options as thought bubbles in the middle of the screen, and for
MSG_SYSTEM(), the options will appear in grey boxes next to the system message.
// Example of a basic menu
MSG(firstMessage, 0); // Shows dialog first
int selection = SEL(firstMenu); // Opens menu and records player's answer
// Use the selection variable to do different things
if (selection == 0)
// do stuff if player selected first option
else if (selection == 1)
// do stuff if player selected second option
// etc ...
This function has several variants that work the same with minor differences. It is used to display a large menu with a scrollbar that covers most of the screen, so it's not ideal to pair it with a
MSG()or similar function. It's best to use when you have a lot of options.
The first argument is the message index to use for the title, which is a small white box with black text that appears at the top of the menu. Use something short that describes the purpose of the menu. This message must be of type
The second argument, like other selection functions, is the index of the
[sel]type message where each line is a menu option.
// Example of a generic menu
int selection = SEL_GENERIC(firstMenuTitle, firstMenu);
if (selection == -1)
// do stuff if player cancelled selection
else if (selection == 0)
// do stuff if first option selected
Note that the user is able to press the cancel button on their gamepad to select nothing, resulting in the function returning
-1. You can prevent this behavior if it is unwanted by using a similar function, listed below.
SEL_GENERIC_NOT_HELP(), a cool feature of these functions is to display some extra text onscreen that describes the highlighted menu item. Each description is its own msg entry of type [dlg]/[msg].
However, it is a bit tricky to set this up properly. It seems that these msg entries must immediately follow the [sel] with the options that it's describing. The description entries must come in the same order as the options.
Not only that, but each menu option must end with a msg function with arguments denoting the index of the option and the message index of the description. See below for an example.
Finally, it seems that message description names must start with GENERIC_HELP_, but anything after that doesn't matter. It's recommended to name these after the message index to prevent your own confusion.
Phone/Auto-Recover[ref 0 1][e]
Player[ref 1 2][e]
Teleport[ref 2 3][e]
Call...[ref 3 4][e]
Calendar[ref 4 5][e]
Camera[ref 5 6][e]
Flags[ref 6 7][e]
Spawn[ref 7 8][e]
About[ref 8 9][e]
Royal[ref 9 10][e]
View your IM messages[n]or auto heal the party,
[n]just like the [clr 18]IM button[clr 0]
Change social stats, items,
[n]Personas, Skills, model,
[n]animations, money or name.[e]
In this example,
GENERIC_HELP_1is the description for the option
GENERIC_HELP_1is at message index
1, since it is the second msg entry in the file (indices start counting at
0). Therefore, the numbers in
[ref 0 1]refer to
Phone/Auto-Recoverbeing the 0th option of the menu (the first), and
GENERIC_HELP_1being at index
1(the second message entry). You can see how for the next option, these numbers increase by 1, and so on forth.
If this seems redundant, that's because it is! Unfortunately, if any of these conventions aren't followed, the menu will not display a description in-game and you'll be left with a blank white box where one should be. It's frustrating, but this is the best we can do.
CALL_BATTLE()function does exactly what you'd imagine-- start a battle using its index as the argument. You can find a battle's index in the game's
ENCOUNT.TBLfile (found in
You may also want to immediately follow this function with another function,
WAIT_BATTLE(), which takes no args and helps prevent softlocks. When the battle is over, you will return to the field the function was called from.
// starts encounter 25 and waits for battle to end before continuing
CALL_FIELD()func can be used to warp to another area in the game. This can be a town, dungeon, safe room, or even special places like the Velvet Room or title screen. Mementos and non-existant fields crash, so use caution.
Entrance refers to which spawn point to start the player's position at. These are usually set in the field's .FBN file. Use
0if you're not sure. The unknown value is usually set to
// Warp to the Velvet Room
CALL_EVENT()is a function for starting a story event scene (the kind where you can fast-forward and view the conversation log). Returns to the field the function was called from after the event is over.
There's a variant called
CALL_KF_EVENT()that takes an extra 2 arguments (usually
0?). This one is for field events where you often have a party member NPC following you around, for instance.
// Start the event where Ryuji takes you to the weapons shop
CALL_KF_EVENT( 701, 101, 0, 820);
// Start the event before the Morgana chase scene in Mementos
CALL_EVENT( 334, 1 );
The following are very self-explanatory.
There's a function that can add points to a player's social stats.
ADD_PC_ALL_PARAM(knowledge, charm, proficiency, guts, kindness);
Each argument listed above is an integer. It takes hundreds of points to max out a given stat, so usually a small number is awarded at a time. If
0is used, no points will be awarded for that type.
Follow the command with
DISP_PC_PARAM_METER();to bring up the visual that shows the points being added and the stat levelling up.
You can add or subtract yen from the player by using the following functions.
// Take 540 yen from the player
int yen = -540;
// Add 154,000 yen and show it being added
yen = 154000;
Unfortunately, there are no (known) ways to remove a specific Persona, check which Persona is equipped, change the equipped Persona, or change a party member's Persona using flowscript.
Use the function
PERSONA_SKILL_ADD(int partyMember, int personaID, int skillID);to give a desired skill to a character's Persona. Conversely, use
REMOVE_PERSONA_SKILLfor the opposite effect.
SKILL_ADD(int partyMember, int skillID);which will do the same thing without providing a persona ID. In the case of the protagonist, it'll add the skill to the currently equipped Persona.
// Give Joker's equipped Persona the skill Agi
// Show the skill being added
Giving the player items can seem a little complicated, but follow the table below and it should help.
// Receive 4 of the key item "Morgana's Scarf"
ItemGet(0x4000, 72, 4);
// Show the item type, name and amount being received
// You can borrow this procedure to easily add items
void ItemGet(int type, int itemId, int amount)
GET_ITEM_BUF_SET(type + itemId, amount);
SET_ITEM_NUM(type + itemId, GET_ITEM_NUM(type + itemId) + amount);