• Advertisement
Sign in to follow this  

storing spells and effects

This topic is 3458 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

Hi, In C++, what are my solutions to store 200+ spells and effects? (each spell is to be triggered by clicking on a button) Ideally I'd like to have 2 structures:
struct spell {
	int id;
	string name;
	int cost;
	int effect[5]; //effect IDs, max 5 effects for each spell
}

struct effect {
	int id;
	int remLife; //optional damage to target
	int addLife; //optional heal target if heal spell
	int poison; //points to lose each turn if poisoned
	//...and additional effects...
}
To store the effects I'd like to avoid XML and use "arrays" harcoded in a header file. How should I go to store data of different types?

Share this post


Link to post
Share on other sites
Advertisement
I would suggest using XML anyway, because it's a much easier format to work with than C++ source code, but you can still transform XML into a bit of C++ source that initializes the appropriate data.

For instance, consider the following XML file:

<spell id="SPELL_FIREBALL" 
name="fireball"
cost="10">
<effect-fire damage="20" />
<effect-blast radius="10" damage="5" />
</spell>

<spell id="SPELL_POISON_LANCE"
name="poison lance"
cost="5">
<effect-poison damage="3" duration="10" />
</spell>


You can easily and automatically turn this XML file into a C++ header file:

class Spells
{
public:
enum SpellID =
{
// BEGIN GENERATED CODE
SPELL_FIREBALL,
SPELL_POISON_LANCE,
// END GENERATED CODE
NUM_SPELLS
};

private:
Spell spells[NUM_SPELLS];

public:

const Spell &operator[](SpellID id)
{
assert (id >= 0 && id < NUM_SPELLS);
return spells[id];
}

Spells()
{
// BEGIN GENERATED CODE
{
Spell s("fireball", 10);
s.effects.push_back(new FireEffect(20));
s.effects.push_back(new BlastEffect(10, 5));
spells[SPELL_FIREBALL] = s;
}

{
Spell s("poison lance", 5);
s.effects.push_back(new PoisonEffect(3, 10));
spells[SPELL_POISON_LANCE] = s;
}
// END GENERATED CODE
}
};


An example of XSLT code to do the transform would be:

<xsl:template match="/">
class Spells
{
public:
enum SpellID =
{
// BEGIN GENERATED CODE
<xsl:for-each select="spell">
<xsl:value-of select="@id"/>,
</xsl:for-each>
// END GENERATED CODE
NUM_SPELLS
};

private:
Spell spells[NUM_SPELLS];

public:

const Spell &operator[](SpellID id)
{
assert (id >= 0 && id < NUM_SPELLS);
return spells[id];
}

Spells()
{
// BEGIN GENERATED CODE
<xsl:for-each select="spell">
{
Spell s("<xsl:value-of select="@name"/>", <xsl:value-of select="@cost"/>);
<xsl:apply-templates />

s.effects.push_back(new BlastEffect(10, 5));
spells[<xsl:value-of select="@id"/>] = s;
}
</xsl:for-each>
// END GENERATED CODE
}
};
<xsl:template>

<xsl:template match="spell/effect-fire">
s.effects.push_back(new FireEffect(
<xsl:value-of select="@damage"/>
));
</xsl:template>

<xsl:template match="spell/effect-blast">
s.effects.push_back(new BlastEffect(
<xsl:value-of select="@damage"/>,
<xsl:value-of select="@radius"/>
));
</xsl:template>

<xsl:template match="spell/effect-poison">
s.effects.push_back(new PoisonEffect(
<xsl:value-of select="@damage"/>,
<xsl:value-of select="@duration"/>
));
</xsl:template>

Share this post


Link to post
Share on other sites
That's very helpful code, thanks

Though, it's not very convenient if I want to add a new spell or just modify one, I have to change the XML, do the transform again, replace the source and recompile. Moreover the header file is going to be huge and hard to read.

I think it's a very good solution for a small database, but I was looking for something a little more low-level, like a binary file or something.

I'm sure I can reuse your code somehow though, cheers for that.

~

Share this post


Link to post
Share on other sites
You could store the information in an array of structures and read it from a data file. You would need to write an editor to create/edit the data file, but this is the best way to go about it in my opinion. It works great for me anyways :).

Share this post


Link to post
Share on other sites
Quote:
Original post by sefo
To store the effects I'd like to avoid XML and use "arrays" harcoded in a header file.
Hard coding *anything* is going to come back and bite you in the arse at some point in the future. While I view XML as bloated and overrated, *anything* is preferable to hardcoding. Maybe look into JSON (a lightweight XML alternative), or roll your own binary format.

Share this post


Link to post
Share on other sites
Thanks for all the feedbacks.
I think I'll just go with an array of structures generated from a file as VBStrider suggested.

I also like ToohrVyk's code and will surely find a place for it.

~

Share this post


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

  • Advertisement