Archived

This topic is now archived and is closed to further replies.

Classes and Inventory?

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

Alright, new question. Before, I was doing inventory like so: int inventory[3][50][16]; The first dimension would differentiate between Weapons, Armor, and Objects (potions, etc.) The second dimension would be each item. In this case, I would have up to 50 items for each type... The third dimension were the stats for each item, of which I had 16 (minimum strength, different flags...) Then this would work great, because I could just set a person''s inventory to the value of the item. (I had 11 slots for the inventory, #0 was for a weapon, #1 and #2 were for armor pieces, and #3-#11 were for regular objects). Well, as you can imagine, it works, but it''s an absolute pain. If, say, I had classes written for each (weapon class, armor class, and maybe item class... or have weapon and armor class that are sub-classes of item). So, my only question, is how I would assign these objects (weapon sword_of_death) to an inventory slot, or have them equiped? Maybe have more specific equiping rather than setting the items to certain inventory slots? Having an array of weapons? Any ideas would be appreciated, thanks. - Goblin

Share this post


Link to post
Share on other sites
I would create an abstract base class called CItem.
This would contain common attributes of weapons and armour, and objects (such as a wear and tear, how much damage can be applied to it before destruction, who can use it etc).
Then i would create derived classes for each of your SubTypes holding their specific attributes (and possibly pointers to some global value structures).

Then i would hold all these in an array and build some virtual interfaces to manipulate them. eg a Damage function which is virtually defined for each class (CWeapon, CArmour etc), or a Wear() function, Drink() function etc. When the item does not allow it to be worn or drunk, return false and display your message. This way you are shifting all the processing to your items in a true OOP way (You tell the item to process the instruction and tell you any result, as opposed to querying what type of item it is and can i use it for that - a subtle but important difference!)

Share this post


Link to post
Share on other sites
Well, some quick code would be usefull if you (or anybody) could supply it...

In addition, how would I know whether or not the player has the item or not?

Perhaps a flag inherited by all classes of whether it is worn or equiped or whatnot?

Just wondering :]

- Goblin
"In order to understand the full depth of mankind, you must first seperate the word into its component parts: 'mank' and 'ind'."

Share this post


Link to post
Share on other sites
Argh... I really hate saying it, but:

Anybody, anybody at all?

Would I have each object have a bit that would say whether the player has it or not?

Would I have an array for inventory that I could set them somehow to the objects? If so, how?

Any ideas?

- Goblin
"In order to understand the full depth of mankind, you must first seperate the word into its component parts: 'mank' and 'ind'."

Share this post


Link to post
Share on other sites
quote:
Original post by Goblin

Would I have each object have a bit that would say whether the player has it or not?

Would I have an array for inventory that I could set them somehow to the objects? If so, how?




No you dont need a "has it" bit.

You just have to set all the pointers in your inventory array to NULL initially:

    

#define INV_SIZE 50


CItem* inventory[INV_SIZE];


for(int i=0; i<INV_SIZE; i++){
inventory<i> = NULL;
}



I'm sure theres an easier way of doing this but none springs to mind at the moment.

Then when you add an item to the inventory you just make a free space in the array point to the coresponding CItem Object:



inventory[0] = &potionOfHealingObject;



To remove it just set that space to NULL again. (Be sure to delete all your objects properly before you quit.)

Hope that helps.
ro



Edited by - rowbot on July 16, 2000 7:52:55 PM

Share this post


Link to post
Share on other sites
I thought that all pointers by default are initialized to NULL? And if I wanted all slots to have the item ''empty'' by default, I would:

    
CItem empty;
for(loop=0;loop<INV_SIZE;loop++)
{
inventory[loop]=∅
}
[/source]

I guess that sort of makes sense... and because inventory[] would be an array of pointers, I would have to set them equal to the <i>memory address </i> of the object?

Also, would I want to create the item ''empty'' (or any item, for that matter) normally, or in the free store:

[source]
new CItem empty;
//game code... la, la, la...
delete empty;


Right? Or not? What would be the difference, anyway?


- Goblin
"In order to understand the full depth of mankind, you must first seperate the word into its component parts: 'mank' and 'ind'."

Share this post


Link to post
Share on other sites
You cant guarentee an array of pointers will be set to null initially - you will get nasty errors happening otherwise.

Here is a basic header structure for you:

    
class CItem
{
protected:
// Generic attributes

unsigned short m_integrity; // how healthy is the object

unsigned int m_composition; // whats it made from?

// etc..


public:
CItem();
~CItem();

virtual void Destroyed( void);
virtual void Damage( unsigned int appliedDamage);
virtual int Wield( CEntity *owner, int hand) { return 0; } // default - cannot be wielded

};

class CWeapon : public CItem
{
protected:
unsigned int m_damage;

public:
void Damage( unsigned int appliedDamage)
{ m_integrity -= m_damage/ 2;
if ( m_integrity < 0)
Destroyed();
}
void Wield( COwner *owner, int hand) { return Owner->AddToHand( hand); }
};



Anyhow you get the idea.
Store your items in an array or linked-list within your class CEntity (which can be subderived into species for example).

Share this post


Link to post
Share on other sites
hmmmm just saw your last post Goblin.

You really want something like rowbot was suggesting.

        
#define INV_SIZE 50

class CEntity
{
CItem ** m_inventory;
// etc...


CEntity();
~CEntity();
// etc..

}

CEntity::CEntity()
{
m_inventory = new CItem *[INV_SIZE];
memset( m_inventory, 0, sizeof( CItem *) * INV_SIZE);
}

CEntity::~CEntity()
{
// Delete each item in the inventory

for( int i = 0; i < INV_SIZE; i++)
{
if ( m_inventory<i>)
delete m_inventory[i];
}

// Delete the inventory

delete [] inventory;
}


Make sense?

Edited by - shamen on July 17, 2000 5:47:03 PM

Share this post


Link to post
Share on other sites
Yeah, thanks tons for the help, though I''m still confused about a few things (I know, I know, I don''t know enough about classes, etc.)...

Just wondering what a ** declaration means? Double pointer? Pointer array?

And also what an item in means? I''ve never really seen it before, so it strikes me as odd...

Thanks!

- Goblin
"In order to understand the full depth of mankind, you must first seperate the word into its component parts: 'mank' and 'ind'."

Share this post


Link to post
Share on other sites
quote:
Original post by Goblin

Just wondering what a ** declaration means? Double pointer? Pointer array?




When u use ** in declaration for a variable. That's mean that variable is a pointer on a pointer. You can use this like you want. (ie: an array of pointer, a 2-dimension array or simply a pointer on a pointer)

        
CItem **items;

// This will create a array of 100 pointers on some instance of CItem class

items = new *CItem [100];

// This will create a 2 dimension array

items = new CItem[10][10];



Happy Coding

LowRad



Edited by - Lowrad on July 18, 2000 10:09:19 AM

Share this post


Link to post
Share on other sites
CItem is just the name of a class i made up (simply defined in one of the posts above). It was my idea for an abstract base class (a class that is useless on its own, but is defined as a template for inheritance). All your other object classes would inherit from this (gives you a common base for all your different types of items).

The definition:
        
CItem **m_inventory;

[/source]

basically declares a variable m_inventory to be a pointer to a pointer. You can use that to declare an array of pointers to instances of CItem.
You could have equally done this (example 1):

[source]
CItem *m_inventory[50];

[/source]

which declares an array of pointers to instances of class CItem.
This locks you into having an array of 50 items (for example). Where as the original example (example 2) eg:

[source]
int m_maxItems = 30;
CItem **m_inventory;
m_inventory = new CItem*[m_maxItems];



allows you to dynamically allocate as many items you wish for a single entity. Ie if some Entities cannot carry any objects, there's no need to allocate memory for it (a saving) whereas with example 1, you will always have allocated 50 pointers for every Entity whether you need less or more.

I dont mean this nastily, but i think you should have a read of some books on object orientated programming and C++. They can explain more than i can write here.


Edited by - shamen on July 18, 2000 10:20:59 AM

Share this post


Link to post
Share on other sites
D''oh! Sorry to seem so stupid, but when I said:
quote:

And also what an item in means? I''ve never really seen it before, so it strikes me as odd...


... I had just made a stupid grammer mistake. I wasn''t asking about the CItem class, but I meant to be asking about stuff inside those kind of tag-brackets... never seen it before.

Hehe, sorry about the confusion.

- Goblin
"A woodchuck would chuck as much wood as a woodchuck could if a woodchuck could chuck wood. Deal."

Share this post


Link to post
Share on other sites