Hello! Welcome back to our journey into building a JRPG combat system.
In our last lesson, we designed the architectural "flow" of combat using a Finite State Machine (FSM). We now have a blueprint for managing the different phases of a battle: starting the fight, taking input, executing actions, and checking for victory or defeat. However, this state machine is currently just an empty shell. It knows what to do, but it doesn't have anyone to do it to or with.
Today, we'll breathe life into our system by defining the combatants themselves. This lesson focuses on our next learning outcome: Create a data structure for combatants (actors and enemies) with core stats (HP, MP, ATK, DEF, AGI). We will design the data "models" that represent our heroes and monsters, a task that should feel familiar given your experience with data modeling in web applications.
1. The "Database": The Heart of JRPG Data
In tools like RPG Maker, and in the design of many classic JRPGs, game data isn't hard-coded. Instead, it's stored in a collection of data files, collectively called the "database". This is conceptually similar to using a set of JSON files or a NoSQL database to define the entities in a web app.
This database contains definitions for everything: items, skills, and most importantly for us today, actors and enemies.
HELP DOCUMENTATION for version 1.7.0 / PC
The RPG Maker MZ help documentation provides a great overview of this database concept. Let's start by looking at how it organizes game data.
Read the section 'What is the Database?'. Pay attention to the list of data types it manages (Actors, Enemies, Classes, etc.). This illustrates the data-driven approach we are taking.
As you can see, actors and enemies are just two types of data within a larger, interconnected system. Today, we'll focus on designing the structure for these two specific types.
2. Core Combatant Stats: Quantifying Power
At their core, both player characters (Actors) and monsters (Enemies) are defined by a set of numerical attributes, or "stats". These stats govern their effectiveness in battle. Let's look at the standard set used in many JRPGs.
RPG Maker MV Tutorial #9 - Stat Explanation
The video 'RPG Maker MV Tutorial #9 - Stat Explanation' gives a quick and clear breakdown of the fundamental stats used in the RPG Maker engine. These form a great starting point for our own design.
Watch the segment from 00:37 to 01:06, which explains the eight basic parameters.
As the video explains, the most common stats are:
- Max HP (Hit Points): A combatant's health. If it reaches 0, they are knocked out.
- Max MP (Magic Points): The resource used to cast spells or use special skills.
- ATK (Attack): Governs how much physical damage a combatant deals.
- DEF (Defense): Reduces incoming physical damage.
- Magic Attack (MAT): Governs the power of magical spells.
- Magic Defense (MDF): Reduces incoming magical damage.
- Agility (AGI): Determines who acts first and can influence evasion.
- Luck (LUK): A wildcard stat that often influences critical hit rates, evasion, and the chance of inflicting status effects.
These eight stats provide a solid foundation for any classic JRPG.
3. Designing the Actor Data Structure
Actors are the characters in the player's party. Their data structure needs to hold not only their stats but also information about their identity, progression, and appearance.
In a system like RPG Maker, this is often split into two parts: the Class, which defines stat growth and learnable skills, and the Actor, which ties a name and visual representation to a Class.
Let's see how the documentation lays this out.
HELP DOCUMENTATION for version 1.7.0 / PC
Now, let's dive deeper into the RPG Maker documentation to see the specific parameters for Actors and their Classes. This shows how stats are tied to progression.
First, skim the 'Actor Settings' section to see properties like Name, Nickname, and Images. Then, focus on the 'Class Settings' section, particularly the 'Parameter Curves'. This shows how stats like Max HP and Attack are defined for each level from 1 to 99. This curve is the core data for a character's potential.
Based on this, we can envision a JavaScript class or JSON object for an actor's "definition" in our database:
// Example: In our database/actors.json
{
"id": "actor001",
"name": "Reid",
"classId": "class001", // Link to a class definition
"initialLevel": 1,
"maxLevel": 99,
"faceImage": "path/to/reid_face.png",
"characterSprite": "path/to/reid_char.png",
"battlerSprite": "path/to/reid_battler.png"
}
// Example: In our database/classes.json
{
"id": "class001",
"name": "Swordsman",
"expCurve": { /* ...parameters... */ },
"paramCurves": {
"maxHp": [/* value at lvl 1, value at lvl 2, ... */],
"atk": [/* value at lvl 1, value at lvl 2, ... */]
// ...and so on for all 8 stats
},
"learnableSkills": [
{ "level": 5, "skillId": "skill010" }
]
}
This structure separates the constant definition (the class) from the specific instance (the actor). During gameplay, your engine would create an instance of an actor that also tracks their current HP, MP, status effects, and equipped gear.
4. Designing the Enemy Data Structure
Enemies share the same core combat stats as actors, but their data structure is simpler in that they don't typically have levels or classes. Instead, their stats are fixed. They do, however, have unique properties related to the rewards they give upon defeat.
The Final Fantasy - Game Mechanics Guide provides an incredibly detailed look at how the original Final Fantasy defined its enemies. This is a perfect reference for the style of game you want to build.
Final Fantasy - Game Mechanics Guide - NES - By AstralEsper
Let's examine a true classic. This FAQ for Final Fantasy on the NES provides an exhaustive list of every enemy and their stats. It's a masterclass in minimalist but effective enemy design.
Read the introduction to the 'ENEMY DATA' section to understand the stat abbreviations. Then, look at the stat blocks for the first few enemies, like the 'IMP', 'WOLF', and 'GrWOLF'. Notice what data is stored: HP, ATK, DEF, but also EXP, GOLD, and resistances (RESI).
As you can see from the FF guide and the RPG Maker documentation (in the "Enemy Settings" section), an enemy data structure needs:
- Core Stats: HP, MP, ATK, DEF, MAT, MDF, AGI, LUK.
- Rewards: How much Experience (EXP) and Gold the party receives.
- Drop Items: A list of items that might be dropped, each with a specific probability.
- Action Patterns: A list of skills the enemy can use. (We will design the AI for this in a later lesson, but the data belongs here).
- Elemental/Status Traits: Weaknesses and resistances.
A JSON representation for an enemy in our database could look like this:
// Example: In our database/enemies.json
{
"id": "enemy001",
"name": "Slime",
"battlerImage": "path/to/slime.png",
"stats": {
"maxHp": 20,
"maxMp": 0,
"atk": 8,
"def": 15,
"mat": 5,
"mdf": 5,
"agi": 10,
"luk": 10
},
"rewards": {
"exp": 5,
"gold": 10
},
"dropItems": [
{ "itemId": "item001", "chance": 0.1 } // 10% chance to drop a Potion
],
"actionPatterns": [ /* ... to be defined later ... */ ]
}
Test your understanding!
Using the structure above, design a JSON object for a "Goblin" enemy. It's a standard early-game foe.
- It has 45 HP.
- It's primarily a physical attacker (20 ATK) with moderate defense (12 DEF).
- It's fairly quick (18 AGI).
- It has no magic (0 MP, low MAT/MDF).
- It gives 12 EXP and 20 Gold.
- It has a 5% chance of dropping a "Leather Cap" (let's say
itemId: "armor005").
Show answer
{
"id": "enemy002",
"name": "Goblin",
"battlerImage": "path/to/goblin.png",
"stats": {
"maxHp": 45,
"maxMp": 0,
"atk": 20,
"def": 12,
"mat": 5,
"mdf": 8,
"agi": 18,
"luk": 12
},
"rewards": {
"exp": 12,
"gold": 20
},
"dropItems": [
{ "itemId": "armor005", "chance": 0.05 } // 5% chance
],
"actionPatterns": []
}
5. An Alternative Design: Primary vs. Derived Stats
The model we've discussed, used by Final Fantasy and RPG Maker, can be called a Direct Stat Model. Stats like ATK and DEF are fundamental values that grow directly upon leveling up.
There is another common approach: the Derived Stat Model. In this design, you have a smaller set of primary stats, and the combat stats are calculated from them.
Stat System Design - Creating Rpg Game
The video 'Stat System Design' offers a great explanation of this alternative model. This is a crucial concept for a game designer to understand, as it significantly changes the feel of character progression.
Watch from 02:31 to 03:10. The creator outlines a system with four primary stats: Strength, Agility, Intelligence, and Vitality. Notice how secondary stats like 'Physical Damage' and 'Max Health' are influenced by these primary stats.
In a derived model:
- Primary Stats: Strength (STR), Agility (AGL), Intelligence (INT), Vitality (VIT). Players often allocate points into these on level-up.
- Derived Stats:
Max HPmight beVIT * 10 + BaseHP.ATKmight beBaseWeaponDamage + (STR / 2).Evasionmight be directly based onAGL.
Which model to choose?
- Direct Model (our current plan): Simpler to balance and understand. The effect of a level-up is very clear. This is authentic to the FF1-5 and BoF1-2 style you're aiming for.
- Derived Model: Allows for more complex character builds. A player might create a "Strength-based Mage" who uses a magical sword whose damage scales with STR. It offers more player choice but is harder to balance.
For our project, we will stick to the Direct Stat Model as it aligns perfectly with our JRPG inspirations. However, knowing this alternative is a key piece of RPG design theory.
Conclusion
We have now defined the "nouns" of our combat system. We have a clear plan for the data structures that will represent both our heroes and our enemies.
Key Takeaways:
- Combatants are defined as data objects within a larger game "database".
- Actors (player characters) and Enemies share a set of core combat stats: HP, MP, ATK, DEF, MAT, MDF, AGI, and LUK.
- Actor stats are often defined by their Class, which dictates their growth over levels via parameter curves.
- Enemy stats are typically fixed and include additional data for rewards (EXP, Gold) and drop items.
- We are using a Direct Stat Model, where stats like ATK and DEF are fundamental, which is authentic to classic JRPGs like Final Fantasy.
Preview of the next lesson:
Now that we have combatants with an Agility (AGI) stat, we can use it. In the next lesson, we will begin implementing the logic of our combat FSM, starting with one of its most critical jobs: "Implement a turn-ordering system based on character agility." We'll explore different ways to decide who goes next, from simple turn-based rounds to more dynamic systems.
Can't find a good explanation? Sign up and we'll make it for you
Sign up