RPG Maker MV

RPG Maker MV

224 ratings
Beginer's Guide to Making the Most of the Formula Box
By Hraesvelg
A detailed guide on how to use JavaScript to imporve the functionality of skills using basic functions and operators as well as example code on how to use these functions and operators.
2
10
2
   
Award
Favorite
Favorited
Unfavorite
Introduction
This guide is written for the sake of beginners. I haven't seen many sources discussing on
how to make the most of the formula box. So I'm making one. If this is redundant or unnecessary
I apologize. Those who are not familiar with JavaScriptor want a bit of help figuring out
how to use game data beyond basic actor parameters should use this guide. If you are experienced
with JavaScript and well versed with various game data you are welcome to correct errors and
make suggestions. If you find anything unclear just ask me. Thaaaaaaaanks.
Overview
The formula box can do so much more than 4*a.atk - 2*b.def. But there's not much help on how
to do this. This guide will go over useful JavaScript operators and functions to help you
make the most of the formula box. You do not even need plugins to make this work!
Establishing Limits
If you are already familiar with how to use Math.max(), Math.min() and number.clamp() feel
free to move on.

One thing you might want to do is establish a minimum or maximum value of your skills. Maybe
even both. Let's dive right in.

In order to establish a minimum value, you will use the Math.max() function. Simply insert
your formula and you minimum into the parentheses as follows:

Math.max(formula, min)

To establish a maximum value use Math.min() instead.

Math.min(formula, max)

Math.max() takes its parameters and chooses the highest value, Math.min() chooses the lowest
value among its parameters. This means that if the min value is greater than the formula Math.max()
will use it instead. If max is greater than the formula Math.min() will use the value for max
rather than the formula. But what if you want to establish a max AND a min? Typing out:

Math.min(Math.max(formula, min), max)

certainly works but is a bit messy. How about we using a different function instead.

(formula).clamp(min, max)

This code does the same exact thing but, is much easier to read and faster to type out.
Putting a number value (in our case a formula) in parentheses and typing .clamp() after allows
us to "clamp" the resulting value between two numbers.

Note 1: When using Math.max() or Math.min() it doesn't matter whether or not the formula
is the left or right value, when using number.clamp() please ensure the left value is smaller
than the right value.
Note 2: Because variance factors in after these functions establish limits you may see your
values going slightly above or slightly below established limits.


Examples

Ex 1: Attack dealing at least 1 damage

Let's make an attack that deals at least 1 damage, we will need to use Math.max().
We want our formula to be 4*a.atk - 2*b.def and our minimum value to be 1.

Math.max(4*a.atk - 2*b.def, 1)

And just like that our attack deals at least 1 damage! Good job!

Ex 2: Heal that does not exceed 30% max HP

We don't want our early heal spell to be too good and become a preferable alternative due to
low MP cost. Let's make a heal that heals no more than 30% of the target's max HP. We'll scale
our heal on Magic Defense. For the purposes of this example the formula will be 10*a.mdf.
To cap it at 30% of the target's max HP we can replace max with 0.3*b.mhp.

Math.min(10*a.mdf, 0.3*b.mhp)

Nicely done. Now we can keep that Heal1 in check.

Ex 3: Attack dealing between 1 and 9999 damage

Remember the format to use number.clamp() is a little different. But, if you paid attention
you should know where this is going. Let's just use our trusty basic attack formula and "clamp"
it between 1 and 9999.

(4*a.atk - 2*b.def).clamp(1, 9999)

Off to a good start. You should know all about how to establish all the limits your little
heart desires now.
Booleans And the ? Operator
If you are already familiar with how to use booleans and the ? operator feel free to move on.

Time to get to the good stuff. The ? operator is a powerful tool that will let you set up
all sorts of conditional calculations. But let's not get hasty now. First we need to know how
to properly write these conditions.

Boolean Operators

A boolean is a binary value that is either true or false. Many different operators can be
used to check various information and see if it meets the condition (true) or not (false).

=== equality operator, checkes if the values are equal

!== not equality operator, checks if the values are not equal

> greater than operator, checkes if the left value is greater than the right value

>= greater than or equal to operator, checkes if the left value is greater than or equal to
the right value

< less than operator, checkes if the left value is less than the right value

<= less than or equal to operator, checkes if the left value is less than or equal to
the right value

&& and operator, checks if the two values are true

|| or operator, checks if at least one value is true

Note: PLEASE, DO NOT type just & or | ! These are bitwise operators that function completely
differently and will not work the way you intend them to!


Examples

Ex 1: Equality

4 === 4 (true)
"blue" === "red" (false)

Ex 2: Not Equal

5 !== 5 (false)
6 !== "blue" (true)

Ex 3: Greater Than

5 > 7 (false)
6 > 3 (true)

Ex 4: Greater Than or Equal to

8 >= 9 (false)
4 >= 4 (true)
5 >= 1 (true)

Ex 5: Less Than

4 < 0 (false)
3 < 5 (true)

Ex 6: Less Than or Equal to

4 <= 5 (true)
6 <=2 (false)
3 <= 3 (true)

Ex 7: And

(4 === 4) && (6 > 3) (true)
(3 < 2) && (5 > 2) (false)
("red" === "blue") && (5 !== 5) (false)

Ex 8: Or

(4 !== 3) || (1 > 6) (true)
(4 === 4) || (7 < 9) (true)
("green" !== "green") || (2 >= 5) (false)

The ? Operator

Alright, we know what booleans are and how to use them. We should be ready to go on the ?
operator now, right? The format of this operator is:

boolean ? number1: number2

While the ? can lead to any number of possible expressions, for our purposes in using it in
the formula box means it will result in different number values. The boolean will be some
expression using the operators we just learned about. If the boolean is true number1 will
be used, if it is false, number2 will be used. Think you got it? Let's give some examples.

Examples

Ex 1: Crisis Strike

First we'll make an attack which deals more damage when the user is low on HP. As a personal
preference I make low level skills deal 20% more damage than a conventional attack. This skill
will deal 40% more damage when the user is at 25% of their max HP or lower.

a.hp <= a.mhp*0.25 ? (4*a.atk - 2*b.def)*1.4: (4*a.atk - 2*b.def)*1.2

Now that's a skill fitting of a berserker.

Ex 2: Overflow Bolt

Now let's make a spell which deals extra damage when the user has 50% or more of their max MP.
We can use a principle similar to that used in the previous example.

a.mp >= a.mmp*0.5 ? (4*a.mat - 2*b.mdf)*1.4: (4*a.mat - 2*b.mdf)*1.2

Maxes you think twice before wasting all your MP, huh?

Ex 3: Limit Breaker

Now let's make a skill which will break the limit when the conditions are just right.

a.hp === a.mhp ? (4*a.atk - 2*b.def)*1.2: Math.max((4*a.atk - 2*b.def)*1.2, 9999)

Normally this skill will cap at 9999 damage before variance. But, if you have max HP then it
won't cap at all! Cool!
Useful Game Data
There's much more data you can reference than just your basic parameters, but this might not be immediately obvious. If you dig around in the "rpg_objects.js" file contained within the
JS directory of your game you can find references to much more data. But, if you don't know
what you're looking for this can be intimidating. No worries though, I've done a bit of
digging already and will let you know how to access some more data and even give you some ideas
on what to do with it.

Extra/Special Paramaters

Extra and Special Paramaters are very easy to access! They can be accessed the same way basic
paramaters can be, you just need to know the proper abbreviation.

battler.hit Hit rate (chance of landing an attack on an enemy)
battler.eva Evade rate (chance of avoiding a physical attack)
battler.cri Critical rate (chance of landing a critical hit)
battler.cev Critical evasion rate (chance of avoiding a critical hit)
battler.mev Magic Evasion Rate (chance of avoiding a magical attack)
battler.mrf Magic Reflection Rate (chance of reflecting a magical hit attack back at the user)
battler.cnt Counter Rate (chance of avoiding a physical hit attack and attacking the user back)
battler.hrg HP Regen (HP regained at the end of the turn)
battler.mrg MP Regen (MP regained at the end of the turn)
battler.trg TP Regen (TP regained at the end of the turn)
battler.tgr Target Rate (chance of being the target of an enemy attack)
battler.grd Guard Effectiveness (multiplier for damage reduction when in the guard state)
battler.rec Recovery Rate (multiplier for HP or MP restored for recovery skills)
battler.pha Item effect rate (effectiveness of used items [called pharmacology])
battler.mcr MP Cost Rate (multipler for how much MP is cosumed by a skill)
battler.tcr TP Cost Rate (multiplier for how much TP is consumed by a skill)
battler.pdr Physical Damage Rate (multiplier for damage recieved by physical hit attacks)
battler.mdr Magic Damage Rate (multiplier for damage recieved by magical hit attacks)
battler.fdr Floor Damage Rate (multiplier for damage recieved from damaging tiles)
battler.exr Experience Rate (multiplier for experience gained in battle)


Variables

Variables can be used in your formula as well. Simply use the following format:

v[ID]

The ID simply refers to where the variable is defined in the database. So v[1] is the first
variable listed in your database.

Critical Note 1: your game will crash if you use an undefined variable in a formula. To
avoid this either set any variables used in formulas to 0 at the start of the game or use
the ? operator and isNaN() to check if the variable is undefined.

isNaN(v[1]) ? 0: v[1]

this will use 0 in your formula if the first variable is undefined but the actual variable if it
is defined. Be careful.

Critical Note 2: v[1] only retrieves the value of variable 1. Attempting to use this to change the value of the variable will not work. If you want to change the value of the variable either use a commone event of the function $gameVariable.setValue(); instead. Any attempt to change the value using this will cause an invalid left hand assignment error that can crash the game.

Status

Battler status can be accessed using many different functions. Much the same way as you
refer to parameters, a represents the user and b represents the target.

battler.isStateAffected(ID) true if the battler is in the given state
battler.isBuffAffected(param) true if the battler has the given buff
battler.isMaxBuffAffected(param) true if the battler has the maximum value of the given buff
battler.isDebuffAffected(param) true if the battler has the given debuff
battler.isMaxDebuffAffected(param) true if the battler has the maximum value of the given debuff
battler.canMove() true if the battler can take action
battler.isAutoBattle() true if the battler is in auto battle
battler.isGuard() true if the battler is guarding
battler.isSubstitute() true if the battler is substituting
battler.isPreserveTp() true if the battler is preserving TP
battler.elementRate(ID) damage multiplier for specified element
battler.stateRate(ID) chance multiplier for specified state
battler.isStateRestrict(ID) true if the battler is restricted from being affected by this state
battler.isStateAddable(ID) true if the battler is allowed to have this state added
battler.isAlive() true if the battler is alive

Where ID is used you will need a number corresponding to where the state or element is
defined in the database. Param is a number 0-7 corresponding to the 8 primary paramaters.
Here's the correspondance:

0: Max HP
1: Max MP
2: Attack
3: Defense
4: Magic Attack
5: Magic Defense
6: Agility
7: Luck

Other Game Data

Here's some other miscellaneous game data you may want to access to potentially alter the
damage calculation of your skills.

battler.name() the battler's name
battler.currentExp() battler's experience
battler.steps() steps taken
$gameParty.gold() current gold
$gameParty.hasItem(item, includeEquip) true if the party has the given item
$gameParty.hasWeapon(item, includeEquip) true if the party has the given weapon
$gameParty.hasArmor(item, includeEquip) true if the party has the given armor
battler.isClass(ID) true if the battler is of the given class
battler.isLearnedSkill(ID) true if the battler learned the given skill

includeEquip is a boolean designating whether or not you wish to include equiped items in the evluation.

Note: Where either the user or targe can be used in place of $gameParty, however using $gameParty or $gameTroop will be far more useful for the functions listed.
Utilizing Game Functions
Basic game functions can be called with the formula box as well to cause some interesting effects as well. Some effects can be simulated with common events but there may be situations where you don't want to use common events for one reason or another.

battler.gainHp(value); restores specified amount of HP to the target
battler.gainMp(value); restores specified amount of MP to the target
battler.gainTp(value); restores specified amount of TP to the target

Note 1: these will restore the exact specified amount without variance. And without consideration for Ex Paramaters such as Recovery Effect, Physical/Magical Damage rate, etc. Such paramaters should factored in for best results.

Note 2: negative value amounts can be used to apply damage rather than recover it.


Ex: Mind Boggle

Let's set up a skill which will deal HP damage but recover the user's MP. I strongly recommend you make use of Yanfly's Damage Core[yanfly.moe] for this as it will take multiple lines.

The tricky part of this is that RPG Maker gives no intuitive way to deal HP damage but recover MP. So we'll need to put a gainMp(); statement in out formula to accomplish this. However, what if we want some variance? If we look in the source code we can find the formula for variance!

var amp = Math.floor(Math.max(Math.abs(damage) * variance / 100, 0)); var v = Math.randomInt(amp + 1) + Math.randomInt(amp + 1) - amp;

I know it looks like a mess but if we take it apart we can make a little more sense of it.

Math.abs(damage) * variance / 100

Variance is given as a whole number but really it is a fraction. By divinding by 100 we properly convert it into a fraction. So 20% becomes 0.2. We multiply this by the absolute value of the damage. This gives us a value equal to some freaction of the damage we can use to fluctuate the value a bit. For the sake of demonstration damage is 100 and variance is 0.2, the result would be 20

Math.max(Math.abs(damage) * variance / 100, 0)

This is a fairly simple statement, here we just make sure the result of the variance multiplied by the damage is at least 0. Since the result so far is 20, which is greater than 0, we simply pass the value of 20 on to the next function.

Math.floor(Math.max(Math.abs(damage) * variance / 100, 0));

This rounds the value down. That way we don't end up with fractions in our final damage amount. 20 is not a fraction so here we finally set the value of amp to 20.

var v = Math.randomInt(amp + 1) + Math.randomInt(amp + 1) - amp;

This creates two random numbers from 0 to amp + 1, adds them together and then subtracts amp.
This will create two numbers 0 to 21 and then subtact 20. This value will be equal to v. v will be some value between 22 and -20.

The result we have here, v will be used to affects the value of MP we recover.

a.gainMp((damage*a.rec)+v);

Here we take the value of the damage we input into the variance formula, multiply it by the user's recovery effect and apply the variance amount. For demonstration damage is 100 again, the user's recovery effect is 100%. The MP recovered will be between 122 and 80.

value = 4*a.atk - 2*b.def;

Finally we set the damage value equal to that of a normal attack. And we're done. The final code should look something like this:

<Damage Formula> var amp = Math.floor(Math.max(Math.abs(100*a.rec) * 0.2, 0)); var v = Math.randomInt(amp + 1) + Math.randomInt(amp + 1) - amp; a.gainMp((100*a.rec)+v); value = 4*a.atk - 2*b.def; </Damage Formula>

Note: use these notetags and put it in the note box ONLY if you have installed Yanfly's aforementioned plugin. Otherwise compress the code to one line and put that in the formula box.

var amp = Math.floor(Math.max(Math.abs(100*a.rec) * 0.2, 0)); var v = Math.randomInt(amp + 1) + Math.randomInt(amp + 1) - amp; a.gainMp((100*a.rec)+v); value = 4*a.atk - 2*b.def;

And there you go, ready to boggle minds and take some MP while dealing HP damage!

battler.addState(ID); Applies specified state to the battler.
battler.removeState(ID); Removes specified state from the battler.
battler.addBuff(param); Applies specified buff to the battler.
battler.removeBuff(param); Removes specified state to the battler.
battler.addDebuff(param); Applies specified debuff to the battler.
battler.removeDebuff(param); Removes specified state to the battler.
$gameParty.gainGold(value); Causes the party to gain the specified amount of gold.
$gameParty.loseGold(value); Causes the party to lose the specified amount of gold.
$gameVariables.setValue(ID, value); Change the value of the selected variable.
Game Data In Action
COMING SOOOOOOOOON!
Conclusion
Well thanks for reading all that! Hope it was helpful to anyone looking to get a bit more
out of their skills. Please reply with any questions, comments, or additions. I'll try to
respond to all feedback as soon as I can. Thaaaaaaaanks.
112 Comments
Aethiriat Games Aug 7, 2021 @ 6:19am 
Hey there! I can see that this will help out a lot of people as RPG Maker's mechanics can be confusing to some. Great job on this guide!
GeraTo Jul 21, 2020 @ 6:59am 
Thank you! You are right, this is easier than I actually thought! Will try this out when I'm on RPG maker again and will say how it turned out. Thank you again and have a great day!
Hraesvelg  [author] Jul 20, 2020 @ 4:36pm 
Sorry for the long winded response. I wanted to be as clear as possible on why this formula works out mathematically and the easiest way to do so is with a concrete example.
Hraesvelg  [author] Jul 20, 2020 @ 4:36pm 
Getting a random number between two values is easier than you might think. A well established formula for how this works in JavaScript is Math.floor(Math.random() * (max - min + 1) + min). So to get a random value between 5 and 50 you use Math.floor((Math.random() * 46) + 5)

The function Math.random() generates a value between 0 and (very, very close to) 1. The value you get from this will be a decimal so Math.floor() is used to round down. The +1 is added as the random value will never be exactly 1. And when you multiple just your max value by 0.9999... and round down it will always end up 1 below that value. The minimum value is subtracted from the multiplication as it will later be added back to the final value.

For our example:
(0.9999 * 46) + 5
45.9954 + 5
50.9954 which is then rounded down to 50.

(0 * 46) + 5
0 + 5
GeraTo Jul 17, 2020 @ 10:59am 
Thank you a lot for this guide! This is very concise and very helpful overall! I have a question however, is there a command i can input into the formula box that would generate a random number between the two stated numbers? The concept is simple but it is probably more complex to do than I think... thank you for any help in advance!
Link117 Mar 26, 2020 @ 4:32pm 
wow this was needed for me as i made a spell that did 0 damage but kills the target in one hit. and on a side note i would like to see more stuff on java as am looking for ways to add more stuff to creations like adding a jump botton
[BLANK] Jan 15, 2020 @ 4:58pm 
Ah i think i get it now, Ty!
Hraesvelg  [author] Jan 14, 2020 @ 3:44pm 
It is a bit unintuitive to think of at first. Math.max() takes the higher of the two values it is given. What this means is you put in your damage formula as one value and the minimum constant as the second value. This way if your formula results in a number lower than the minimum constant you use the minimum value instead since it is bigger. For similar reasons you use Math.min() when establishing maximum damage values as well.
[BLANK] Jan 5, 2020 @ 10:53pm 
"In order to establish a "minimum" value, you will use the Math."max"() function" I read this and the vice versa one but.. is Java just dumb or am i? Because i would assume Math.max to mean the MAXimum value and Math.min to be the MINimum value.. Just want to make sure so i dont go screwing everything up, ty! :ralphsmile:
XLR8_F8 Jan 1, 2020 @ 2:09am 
Does anyone else have glitches where random things stop working for no reason in this game?