Users browsing this thread: 1 Guest(s)
C++ Object parameter question

#1
Posts: 11
Threads: 4
Thanks Received: 0
Thanks Given: 0
Joined: Oct 2012
Reputation: 0
Status
None
To keep a long story short, I'm trying to code a small RPG-type game in C++ right now, and I'm creating several arrays of objects that store all of the items, abilities, etc. in them and passes all of their parameters, and I'm doing it in a way similar to FF6. Anyone who has experience hacking FF6 or uses FF6usme can tell that the spells and items and the such are all contained within an array of objects, and all of the editable fields and checkboxes are all properties of the classes that they're made from. For example, the 'Fire' checkbox for spells should just be a boolean property that when checked, will tell the game that it is a fire-elemental ability, and then to apply any damage modifications if the target is weak/immune/absorbs the element. That much is obvious.

I'm doing pretty much the same thing with my game, but I wanted to know if there is a more efficient way of coding each individual spell rather than having to pass a load of parameters for each individual spell. An example of this is having a bunch of boolean parameters that determine whether or not the spell can apply a status or apply an element, but each element and status has ITS OWN parameter, which means that I have a metric crapton of boolean parameters in addition to the already obvious ones like spell name, spell power, spell MP cost, etc.

What I'm asking here does anyone know of any other, more efficient ways of going about this in an object-oriented manner? Would it be smarter to just have one boolean parameter for isElemental and canInflictStatus and then tell each individual spell what element/status it is in, say, a string or an int array and then just have another parameter set it to a value that the code will recognize.

For example, here is me creating a spell object and adding it to my spell array:


Spells[1] = Spell("Blast Strike", 16, 15, 0, false, false, false, false, false, false, false,
false, true, true, false, false, false, false, false, false, false, false,
false, false, false, false, false, false, false, false, false, false);

I'm not going to get into what all of the parameters do, but some should be obvious, like the booleans are all elements, is physical, does it ignore defense, does it have a perfect hit rate, can it inflict poison, etc. The point is, I feel like there's simply too many parameters being passed and it makes it look very sloppy. I'm trying to think of a logical method that I can use that would make this simpler. If anyone knows of a more efficient way to code elements and status effects, let me know. I'm going to stick with the method I'm using for now, but if there's a better method I can use in the future for the sake of learning and the such, then I'm most certainly going to do it.

Thanks for any help
  Find
 

#2
Posts: 826
Threads: 11
Thanks Received: 22
Thanks Given: 13
Joined: Nov 2011
Reputation: 16
Status
Double
I think that the alternative tactic you described (with an array of elements/statuses that the spell has) would be faster. I think you would probably only have one or zero elements/statuses to compare on most weapons/spells, except for weird things like Bad Breath, so I would guess that would require less comparisons. I'm not exactly an expert in C++, but that's my reasoning anyways. I can't think of anything else offhand.


Confused Moogles FTW
 

#3
Posts: 3,970
Threads: 279
Thanks Received: 236
Thanks Given: 58
Joined: Oct 2011
Reputation: 65
Status
Tissue-aware
If you are comfortable with bits and bytes you could have 8 attributes or less on a 2 digit number (hex value). This is how attributes are stored in FF3us. Maybe some will find it overkill with modern programming but if you want to save parameters it's a good solution.

So a byte have 8 bits and it's a 8 digit binary number. C++ or most programming languagues will accept bit 0 to bit 7 as 0x00, 0x01, 0x02, 0x04, 0x08, 0x10, 0x20, 0x40 and 0x80. Notice that it double everytime (it's binary duh!). Any combination of 1 to all 8 bits will give you a number between 0x00 and 0xFF in hexadecimal base (0xFF = 256). Now each bit will represent an attribute.

Code:
public class Monster
{
    bool attribute1
    bool attribute2
    bool attribute3
    bool attribute4
    bool attribute5
    bool attribute6
    bool attribute7
    bool attribute8

    public Monster(byte attributes)
    {
           if((attributes & 0x01) != 0){ attribute1 == true} // if bit 0 is set, attribute1 is true
           if((attributes & 0x02) != 0){ attribute2 == true} // if bit 1 is set, attribute2 is true
           if((attributes & 0x04) != 0){ attribute3 == true} // if bit 2 is set, attribute3 is true
           if((attributes & 0x08) != 0){ attribute4 == true} // if bit 3 is set, attribute4 is true
           if((attributes & 0x10) != 0){ attribute5 == true} // if bit 4 is set, attribute5 is true
           if((attributes & 0x20) != 0){ attribute6 == true} // if bit 5 is set, attribute6 is true
           if((attributes & 0x40) != 0){ attribute7 == true} // if bit 6 is set, attribute7 is true
           if((attributes & 0x80) != 0){ attribute8 == true} // if bit 7 is set, attribute8 is true
    }
}

Now you can just create a monster like that:

Monster m1(0x5F) or
Monster m1 = new Monster(0x5F)

meaning attributes 1, 2, 3, 4, 5 and 7 will be true for that monster.

It might be hard to figure out for someone who doesn't know hex but you can save parameters that way. I can't think of any other solution.



Edit: Lockirby2's solution is also good:

Code:
int[] attributes = new int[8]
attributes = {0, 1, 1, 0, 0, 1, 0, 1}

Now you could just do: Monster m1(attributes), and you will check if each attribute of the array is true(1) or false(0).

Man I'm so rusty in C++, I think I'm mixing C++ and C# syntax lol
  Find
 

#4
Posts: 11
Threads: 4
Thanks Received: 0
Thanks Given: 0
Joined: Oct 2012
Reputation: 0
Status
None
Thanks for the tips, everyone. Sorry for not replying sooner... I posted this in other places, as well, and was basically just going around gathering different tips and methods and trying to decide what I'm going to do. At the end of the day, it ends up being quite a bit of coding regardless of whether I stick with my method or go with other ones that I've been seeing, since there's a lot of checking to do here and there.

Regardless, I always like seeing different logical algorithms to solve the same problem, since it basically expands on my knowledge of how to manipulate code. Thanks again Smile
  Find
 

#5
Posts: 159
Threads: 7
Thanks Received: 1
Thanks Given: 4
Joined: Jul 2012
Reputation: 3
Status
None
Just try to sub-categorize your effect so you wont have to repeat yourself. Heres how i proceed in my own game.
I have Effect object. A Characters (PC object) have an array of Effect ( Effect currently applied to the characters) and abilities have a single Effect ( the effect the abilities applies when used).
Before creating your abilities, you create your array of your basic effects with unique ID. Thereafter, when you create your abilities, you just have to pass on the ID of the effect. For example, Bio and Poison will probably use exactly the same "effect". Not just the same attack power and mp usage.

Also, if you a parameter that can have more than 2 value, dont use a boolean. For example, for my elements, i just use an int, 0 = No element/Physical and 1 to 7 for the other element.

Note that i also use a method very similar to what Madsiur suggested when you are "forced" to use a long list of boolean, however i do it in decimal.
Let's say each effects have a unique value,
Poison = 1,
Blind =2,
Confused = 4
Silence = 8
Paralyze = 16

When the character receive a status ailment, you add its value to an Int of the charcaters.
When you wanna know what status ailment the character have, you pass each and every status ailment value and check if its higher or equal to the character effect.
For example, if a character has a Effect value of 21.
If (char.effect >= 16)
{
//Char is paralyzed
char.effect = char.effect - 16
}
//(Char.effect now equal to 5)

If (char.effect >= 8)
{
//Char isnt silenced
char.effect = char.effect - 8
}

If (char.effect >= 4)
{
//Char is confused
char.effect = char.effect - 4
}
//(Char.effect now equal to 1)

//etc



[Image: rrj.gif]
  Find
 



Forum Jump:

Users browsing this thread: 1 Guest(s)


Theme by Madsiur2017Custom Graphics by JamesWhite