Use a game item

Started by
7 comments, last by Motorherp 13 years, 3 months ago
Hi all,

I am making a game with game items. For example, weapons, armors, potions, etc. However, I can't make up my mind how to apply the function of the item to the player when equipped or consumed.

I have a base class called Item, and each item is a child to this base class. There are only five items in the game, but I do plan to expand in the future. My ideas are:

1. Pass player information as a pointer to the item class, and each item class could modify the information based on the item functionality.

2. Have one huge switch statement, so when player chooses an item to use, we enter this switch statement and determine which item has been chosen and apply what the item does.

The first solution contains the actually function of the item in each child item class, and the second solution controls it in a huge switch statement. I am not sure what is the right way to do, or both are wrong.

If anyone knows a better way or more standard way to do this, I would appreciate a lot!

Thank you,

eAGLO.
Advertisement
The first one is probably the most standard, and the most convenient...

someItem->use(somePlayer);
delete item;

Done!
I would just pass the item onto the player instead. It makes more functional sense, at least to me.

class Item {

int hp;
int attack;
int def;
bool consumable;

// etc.
}

A potion would only have positive HP to boost the player's health, a sword is just for boosting attack, and so on.
It might come in handy to have several item slots to fit a particular item type. The player would use a temporary item like this:

Player.useItem(MyPotion);
// If item is consumable (do your own check here)
Player.throwAway(MyPotion);

For an item you keep for an indefinite time:

Player.useItem(MySword);
Player.unequip(MySword);

Unequip will remove the properties (subtract from the base stats) the item gives to the player, while throwAway simply frees up an item slot but keeps the properties given to the player.
Electronic Meteor - My experiences with XNA and game development
If you wish to create a really flexible and extensible system you could tackle this by having entities and properties as different classes. Entities would be objects in your game such as the player, monsters, potions, weapons etc, and properties are things which describe the state of an entity such as its physical strength value, its endurance value, whether the entity is resistant to fire, whether the entity is consumable or equipable, etc. The entity base class would contain an enum describing its entity type so other entities and properties know what it is, and a list or vector of properties which apply to that entity. Similarly the property base class would contain an enum describing its property type, and the derived property class could contain any additional data needed for that property. Entities can then interact with each other appropriately by adding properties to each other, scanning for the existance of propeties to see if they can undergoe appropriate interactions with each other, and altering the values of existing properties to effect each other.

Some basic rough psuedo code as an example of how you could begin to build and use such a system to give you an idea:


// base classes
class Property
{
Entity* m_pOwner;
PropertyType m_myType;
void Update();
};

class Entity
{
EntityType m_myType;
vector<Property*> m_myProperties;

void ApplyToEntity(Entity* pEntity);
void UpdateProperties();
};


// some derived classes
class HealthProperty : public Property
{
float m_value;

HealthProperty(float value)
{
m_myType = PropertyType_Health;
m_value = value;
}
};

class FlamableProperty : public Property
{
FlamableProperty (float value)
{
m_myType = PropertyType_Flamable;
}
};

class OnFireProperty : public Property
{
float m_dpu; // damager per update
OnFireProperty (float dpu)
{
m_dpu = dpu;
m_myType = PropertyType_Flamable;
}

Update()
{
if(m_pOwner->HasProperty(PropertyType_Health))
{
m_pOwner->GetProperty(PropertyType_Health)->m_value -= m_dpu;
}
}
};

class Monster : public Entity
{
Monster()
{
m_myType = EntityType_Monster;
m_myProperties.push_back(new HealthProperty(100));
m_myProperties.push_back(new FlamableProperty());
}
};

class FireBomb: public Entity
{
FireBomb()
{
m_myType = EntityType_FireBomb;
}

void ApplyToEntity(Entity* pEntity)
{
// apply damage from the initial explosion
if(pEntity->HasProperty(PropertyType_Health))
{
pEntity->GetProperty(PropertyType_Health)->m_value -= 10;
}

// set entity on fire if it is flamable
if(pEntity->HasProperty(PropertyType_Flamable))
{
pEntity->AddProperty(new OnFireProperty(2));
}
}
};


Its not a perfect example but hopefully you get the idea and can see the scope and flexibility that a system like that can give you. Might be worth considering if you intend on making a large roguelike game or something like that.
[size="1"] [size="4"]:: SHMUP-DEV ::
What you could do is have a delta list associated with each stat. These lists would contain all the bonuses and penalties currently applied to that stat. Equipping an item would a bonus to that list, while drinking a potion would add a temporary bonus to the list. The advantage of this is it easily ties in with your ui if you want to show the player the breakdown of a stats current derived value. And if you want add negative affects from attacks or traps later on you already have a frame work in place to do that.

Thanks guys,

I see a few different solutions here, but I think I can make up my mind for which design I am going to apply to my game. JustChrist, Motorherp and TecnoGoth, thanks for providing a new perspective I haven't thought about before, I have learned a lot!

eAGLO.

If you wish to create a really flexible and extensible system you could tackle this by having entities and properties as different classes. Entities would be objects in your game such as the player, monsters, potions, weapons etc, and properties are things which describe the state of an entity such as its physical strength value, its endurance value, whether the entity is resistant to fire, whether the entity is consumable or equipable, etc. The entity base class would contain an enum describing its entity type so other entities and properties know what it is, and a list or vector of properties which apply to that entity. Similarly the property base class would contain an enum describing its property type, and the derived property class could contain any additional data needed for that property. Entities can then interact with each other appropriately by adding properties to each other, scanning for the existance of propeties to see if they can undergoe appropriate interactions with each other, and altering the values of existing properties to effect each other.

Some basic rough psuedo code as an example of how you could begin to build and use such a system to give you an idea:


// base classes
class Property
{
Entity* m_pOwner;
PropertyType m_myType;
void Update();
};

class Entity
{
EntityType m_myType;
vector<Property*> m_myProperties;

void ApplyToEntity(Entity* pEntity);
void UpdateProperties();
};


// some derived classes
class HealthProperty : public Property
{
float m_value;

HealthProperty(float value)
{
m_myType = PropertyType_Health;
m_value = value;
}
};

class FlamableProperty : public Property
{
FlamableProperty (float value)
{
m_myType = PropertyType_Flamable;
}
};

class OnFireProperty : public Property
{
float m_dpu; // damager per update
OnFireProperty (float dpu)
{
m_dpu = dpu;
m_myType = PropertyType_Flamable;
}

Update()
{
if(m_pOwner->HasProperty(PropertyType_Health))
{
m_pOwner->GetProperty(PropertyType_Health)->m_value -= m_dpu;
}
}
};

class Monster : public Entity
{
Monster()
{
m_myType = EntityType_Monster;
m_myProperties.push_back(new HealthProperty(100));
m_myProperties.push_back(new FlamableProperty());
}
};

class FireBomb: public Entity
{
FireBomb()
{
m_myType = EntityType_FireBomb;
}

void ApplyToEntity(Entity* pEntity)
{
// apply damage from the initial explosion
if(pEntity->HasProperty(PropertyType_Health))
{
pEntity->GetProperty(PropertyType_Health)->m_value -= 10;
}

// set entity on fire if it is flamable
if(pEntity->HasProperty(PropertyType_Flamable))
{
pEntity->AddProperty(new OnFireProperty(2));
}
}
};


Its not a perfect example but hopefully you get the idea and can see the scope and flexibility that a system like that can give you. Might be worth considering if you intend on making a large roguelike game or something like that.



This is quite interesting. I've never thought of managing a player/monster's stats like separated classes, but I've been thinking if I can just pass the player's properties to the item class. This shows me a more established example. Thanks!


What you could do is have a delta list associated with each stat. These lists would contain all the bonuses and penalties currently applied to that stat. Equipping an item would a bonus to that list, while drinking a potion would add a temporary bonus to the list. The advantage of this is it easily ties in with your ui if you want to show the player the breakdown of a stats current derived value. And if you want add negative affects from attacks or traps later on you already have a frame work in place to do that.




It does make a lot of sense to me to have a list of bonuses/penalties for stats that I need to track down, but I am more curious about the design of the items when used. How would you pass your parameters? Would you pass items to the player class and determine it's function in player class? or pass the player object as a pointer to item class and let each item to decide what to do to the player.

Thanks.

This is quite interesting. I've never thought of managing a player/monster's stats like separated classes, but I've been thinking if I can just pass the player's properties to the item class. This shows me a more established example. Thanks!


Passing a pointer to a structure of predefined hardcoded entity statistics to your item to modify can work. Either that or passing your item to your entity to handle. These simpler methods have their limitations however in that your properties are hardcoded and each entity must contain the full set even if many of those properties dont apply to that particular entity. Either that or you end up in a situation where your entities have to be aware of every possible item that could exist or vice versa so that they can interact correctly. That's not a big deal if you only plan on having a small number of different item types or entity properties and you know in advance what they all are. If you start adding in lots and lots of different effects though then a hardcoded system like that can become pretty cumbersome and difficult to manage. That's where a system like I describe starts to shine. It's more complicated to setup but the extra effort will pay dividends if you start to make lots and lots of additions to your game. Another feature of such a system is that properties and entities aren't hard linked to each other and can be freely mixed and matched which if well designed can lead to lots of unexpected interesting emergent interactions and mechanics. Of course that could be considered an advantage or disadvantage depending on the type of game you're making.
[size="1"] [size="4"]:: SHMUP-DEV ::

This topic is closed to new replies.

Advertisement