• Advertisement
Sign in to follow this  

Pokemon game structure. Help with class design

This topic is 1251 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

I'm trying to recreate the Pokemon battle engine using C#.NET. And this is how I've planned things out so far-


All species of Pokemon (Nidorino, Gengar etc) are instances of base Pokemon class. The base class is the blueprint containing variables like the index number, sprite filename, height, weight, base stats etc.


Class Species inherits Class Pokemon


Species that inherit this class fills up these variables and become the base species definition. (All Gengars have 130 Sp.Attack and Nidorinos have 55 Sp.Attack)


Gengar.SpecialAttack = 130


Separately, a current nickname, experience, level, IV set, EV set are stored against all wild/owned Species to give them individuality (my Pikachu is not your Pikachu).


Trainer.Mon1 = [ <Species>, <Nickname>, <XP>, <Level>, <IVArray>, <EVrray>, <Moveset> ]


The way the original Pokemon games work is, instead of storing current stats of every individual Pokemon, the games recalculate them before every battle from it's base stats, IV/EVs and its level. This is a smart design and I plan to implement that as well.


But I have several queries on the class design. Like-


How do I handle Type / Moves / Abilties?


A Pokemon has things like types, an array of moves and abilities. How do I define these Types / Abilities / Moves?


Do I use base class for Types? Do I define them as enumerations? Do I create an array / dictionary? Which would be better and why?


Also a type has paper/scissors/stone relation with other types. Where should I have the game check/calculate for this? Hardcoded during battle? Or a lookup table? If a lookup table, should it somehow be a part of the Type class? (If it is a class at all!)


When to event check for abilities?


Abilities are a tricky thing. They are passives that are always checking for certain events before they trigger. Simplest way to manage this is to have a switch case checking the right conditions in a context.

For example, when whether changes (context), Check (switch case) if it's raining and then check if Pokemon has ability Hydration. Or if it has Rain Dish. Or if it has Swift Swim. Each ability has different effects and should be triggered accordingly.


This method is simple but actually makes things more complicated, with so many abilities. Which leaves room for bugs.


How to Handle multiple Formes?


Taking Deoxys for example, a Pokemon with THREE other formes: Attack, Defense, Speed. How should the game be designed to handle this?


I plan to treat separate formes as different Species designated by a secret ID (other than the National Dex ID). For example: if Deoxys Normal 86, Deoxys A is 87, Deoxys D is 88 and Deoxys S is 89. When a forme change is required, the Species in Trainer's Mon1 array is changed to the appropriate form. This also allows the individual formes to have their own sprites, type data, moveset and base stats.


Or should I scrap that and add a separate Forme variable to the base Pokemon class, just in case it needs to have a different Forme?



Do comment on this structure design and give me any tips or suggestions on how I can improve this model. Give me your opinions and tell me how you would have done it. I'm interested.

Share this post

Link to post
Share on other sites

As phil_t is saying, inheritance is not needed here. You only need one 'Pokemon' class, because each pokemon has the same variables. You just set the variables differently for each pokemon.


This is just to illustrate what I mean, and is not actual code:

class Pokemon

     PokeID id;
     ImageID imageID; //Used to look up the image used to draw the pokemon.
     unsigned level;
     unsigned experience;
     unsigned maxHealth;
     unsigned currentHealth;

     unsigned strength, endurance, etc...;
     float fireResistance; //Resistances (>1.0f) and weaknesses (< 1.0f)
     float waterResistance; //Resistances (>1.0f) and weaknesses (< 1.0f)
     float plantResistance; //Resistances (>1.0f) and weaknesses (< 1.0f)
     std::vector<Abiltiies> abilities;

AreaID currentAreaID;

std::vector<PokeID> wildPokemonInArea = GetPokemonInArea(currentAreaID);

PokeID wildPokemonID = GetRandomFrom(wildPokemonInArea);
Pokemon wildPokemon = GenerateWildPokemonStats(wildPokemonID, currentAreaID)

Pokemon yourGengar;
yourGengar.imageID = GetOnePossiblePokemonAppearance(PokeID::Gengar);
yourGengar.strength += 3;

Every pokemon has the same variables - they are just set to different values. Inheritance is not needed here.


Also, myArcanine.IsCoolerThan(yourGengar)tongue.png

Edited by Servant of the Lord

Share this post

Link to post
Share on other sites
Sign in to follow this  

  • Advertisement