Tables using two values as coordinates for Pokémon style type effectiveness chart


Hi folks!

I'm working on a monster tamer and I'm trying to figure out how to best handle type effectiveness in Lua. Originally, I was going to use a class method to test this, where you can say something like Fire:getEffectiveness(Water). But that seemed a bit unwieldy, since the actual function to test this would be further obscured by the class method, and I would much rather have just a basic function that could take the move type and defender's type as an argument.

What I arrived at as a more extensible way to handle it would be to have a table that a function can use take two values (move type, defender's type) as x and y coordinates to return the damage modifier that applies to the attacking type from a table like you would for a spreadsheet. Then that coordinate would have the applicable modifier and return that for use in the damage calculator.

I can't seem to wrap my head around how to execute this in Lua.

If anyone has any helpful suggestions or resources for this, I'd love to see it. I couldn't find the answer in the SDK docs and my Google-fu is leaving me wanting.

You'll need to search 'Lua two dimensional array' I believe. What you are describing won't be part of the SDK because tables and arrays are a core part of the Lua language instead.

From Luas own documentation: Programming in Lua : 11.2

However that's a pretty bare bone description of the basic language. Googling might find you a more complete how to.

For the SDK I would suggest looking up the JSON functions, because then you could make your game tables data driven and easier to change as you experiment with defense/move values.

1 Like

Thanks, that's a good idea. I was considering building my monsters using the JSON functions because there's a lot of data to consider with them and it'd be nice to generate monsters from a single class that takes a JSON as an argument.

Hi! Apologies if I’m misunderstanding what you’re looking for, but here’s an example that takes two types and returns a damage modifier value:

local damageModifierTable = {
    fire  = {fire = 1.0, water = 0.3, earth = 1.0, sky = 1.6},
    water = {fire = 1.9, water = 1.0, earth = 0.8, sky = 1.2},
    earth = {fire = 1.1, water = 1.2, earth = 1.0, sky = 0.0},
    sky   = {fire = 0.8, water = 0.9, earth = 1.5, sky = 1.0}

function getDamageModifier(attackerType, defenderType)
    return damageModifierTable[attackerType][defenderType]

attackerType is on the table y axis and defenderType on the x axis.

1 Like

That’s exactly what I was looking for actually! This is way less complex than what I had been trying to make happen!

I think I was just getting confused with how to properly write that.

To save writing lines for each of the 13 types I have, would I be able to have an if statement return a value of 1 if it evaluates to nil?

1 Like

Great! To avoid having to include combinations that don't require a modifier, you could replace the function with something like:

function getDamageModifier(attackerType, defenderType)
    if damageModifierTable[attackerType] and damageModifierTable[attackerType][defenderType] then
        return damageModifierTable[attackerType][defenderType]
        return 1

This will return 1 if the combination of types doesn't exist.

1 Like

Brilliant! Thanks so much!

1 Like