How to only use one item with inventory?

Whether you're a newbie or an experienced programmer, any questions, help, or just talk of any language will be welcomed here.

Moderator: Coders of Rage

Post Reply
PaperDuckyFTW
Chaos Rift Cool Newbie
Chaos Rift Cool Newbie
Posts: 76
Joined: Sat Apr 03, 2010 5:08 am
Programming Language of Choice: C++

How to only use one item with inventory?

Post by PaperDuckyFTW »

Hi. (ill try to keep it short and to the point)

Well, ima back to ask another noob question which is probably caused by my lazy efforts not completing my study of the language.
For no implimental reasons other then to just...make one, I've decided to make an inventory system. I've also made a very basic item class which when an item is left clicked, it's placed in the first available inventory slot. When it is in an inventory slot and right clicked, it's warped to the player's position, or dropped under the player.

Long story short, when I add the 2 testing items to the inventory, everything is fine. When I 'drop' the two items it works fine. But if I re-add the two items, I need to add them in the same order as I dropped them or else both items are added to the inventory.

As the title says, I think what is happeneing is that it is using both of the item's SDL_Rect.
My internet has officially crapped itself so I am at the library, and dont have any available source code. If you have the time, I would be eternally greatful if you could post how you have/would make an item system that uses one item? Sorry this isnt much of a help but I hope you understand my conundrum, and I'll post the bothering source code as soon as I can.
User avatar
dandymcgee
ES Beta Backer
ES Beta Backer
Posts: 4709
Joined: Tue Apr 29, 2008 3:24 pm
Current Project: https://github.com/dbechrd/RicoTech
Favorite Gaming Platforms: NES, Sega Genesis, PS2, PC
Programming Language of Choice: C
Location: San Francisco
Contact:

Re: How to only use one item with inventory?

Post by dandymcgee »

It depends on the type of inventory system. There are at least a few different systems I can think and I've listed them below from simple to complex.

A list of items.
A grid system that allows one item per space.
A grid system where different items take up different amounts of space.

The first I would represent with a linked list, or a vector. The second with a static array. The third would require some thought, as it's a rather advanced inventory system. I'll assume for now this is not what you are trying to make, correct me if I am wrong.
Falco Girgis wrote:It is imperative that I can broadcast my narcissistic commit strings to the Twitter! Tweet Tweet, bitches! :twisted:
PaperDuckyFTW
Chaos Rift Cool Newbie
Chaos Rift Cool Newbie
Posts: 76
Joined: Sat Apr 03, 2010 5:08 am
Programming Language of Choice: C++

Re: How to only use one item with inventory?

Post by PaperDuckyFTW »

Thanks, I'll play with vectors to see if I can find a solution. I'm able to post some code but beware to anyone who tries to read it: It looks like crap.

Code: Select all

Inventory::Inventory()
{
	is_open = true;
	sInv = SDL_LoadBMP( "invSprite.bmp" );
}
Thats basically all for the Inventory, and it is later initialised in an array: Inventory slots[8]. THis gives me 8 available slots

Code: Select all

void Item::onClick( Player pl, Inventory inv[], Item &item )
{
	//When user has clicked on the item
	//process events
	int x = 0, y = 0;

	if( event.type == SDL_MOUSEBUTTONUP )
	{
		//If we right click the item and the item is in a slot
		if( event.button.button == SDL_BUTTON_RIGHT && item.in_slot == true ) 
		{
			x = event.motion.x;
			y = event.motion.y;
			
			//If the right click is made inside the item's rect
			if( (x>rcItem.x) && (x < rcItem.x + rcItem.w) && (y>rcItem.y) && (y<rcItem.y + rcItem.h ) )
			{
				//drop the item
				item.rcItem.x = pl.getX();
				item.rcItem.y = pl.getY();
				item.in_slot = false;

				for( int i=0; i<8;i++ )
				{
					inv[i].is_open = true;
				}
			}
		}

		//If we make a left click
		else if( event.button.button == SDL_BUTTON_LEFT && item.in_slot == false  )
		{
			x = event.motion.x;
			y = event.motion.y;
			{	

				//And it is clicked inside the item
		if( (x>rcItem.x) && (x < rcItem.x + rcItem.w) && (y>rcItem.y) && (y<rcItem.y + rcItem.h ) )
		{
			//do logic
				//If the 1st inventory slot is open
				if( inv[0].is_open )
				{
					//Change it's position, make the 1st slot unavailable and set
					//The item in a slot
					item.rcItem.x = inv[0].GetX();
					item.rcItem.y = inv[0].GetY();
					inv[0].is_open = false;
					item.in_slot = true;
				}
				//Do for every other inventory slot
				else if( inv[1].is_open )
				{
					item.rcItem.x = inv[1].GetX();
					item.rcItem.y = inv[1].GetY();
					inv[1].is_open = false;
					item.in_slot = true;
				}
			}
		}
	}
}
Then, I have each of the hard coded items using the above function:
pot1.onClick(player, slots, pot1);
pot2.onClick(player, slots, pot2);
pot3.onClick(player, slots, pot3);

It's not very intellegently planned out, but for the time being until i 'perfect' it, it works just fine. Like I said, with this method i need to re-add the dropped items in the ordewr I dropped them so they
wearymemory
Chaos Rift Junior
Chaos Rift Junior
Posts: 209
Joined: Thu Feb 12, 2009 8:46 pm

Re: How to only use one item with inventory?

Post by wearymemory »

Are you saying that, if your character is standing in one location and drops two items from your character's inventory, then those two items will appear under your character, overlapping that same location? Are you also claiming that, you have experienced two dilemmas; one where clicking at a spot on a map that contains overlapping items will pick up both items from the same location, but you've fixed that issue, and now clicking at a spot on a map that contains overlapping items will pick up each item in the order that it was dropped.

If not, please correct me. If so, then here's what I suspect:
You are keeping dropped items ordered into an array that is traversed from beginning to end, while each element is checked to see if the user's click is contained within an item's rectangle. The first issue may have been caused by not stopping this process after an item was found at the location, where it would then continue finding all other items in the location, and add them to the inventory as well. However, you've apparently fixed this issue. For your current problem, I would expect that, as you drop the item from the first inventory slot, it would appear in the next available slot in the array for dropped items, this available slot number would be incremented to allow another item to be added, and this is where the item from the second inventory slot comes in. I assume that you're iterating through this dropped item array from the beginning to the end, therefore, it would naturally select the first dropped item at the location of the user's click, hence your issue.

If this is the case, then here are my proposed solutions:
  • If you would like the first item you pick up to be the last item you dropped, then consider reversing the order in which you loop through your array, or
  • do not allow the user to drop more than one item in the same location, but
  • if you would still like the user to be able to drop multiple items FROM the same spot, then randomly select one of the surrounding cells to place the item in, until there are no more surround cells. An example of this behavior is in games such as TQ Digital's Conquer Online; however,
  • if you would like to allow the user to be able to drop multiple items IN the same spot, then provide the user with a list of items that are located in the spot that they've selected within a neatly organized interface—much like an inventory. This behavior is replicated in games such as Blizzard's World of Warcraft.
If I've completely missed your point, then forgive me. Perhaps you could explain it a little more.
PaperDuckyFTW
Chaos Rift Cool Newbie
Chaos Rift Cool Newbie
Posts: 76
Joined: Sat Apr 03, 2010 5:08 am
Programming Language of Choice: C++

Re: How to only use one item with inventory?

Post by PaperDuckyFTW »

Thanks for everyone's help, I'm sorry about this, I realised how can anyone ask for help if I cant even describe or explain the issue? So I made a video which I hope you can understand. Windows movie maker was screwing up when I was trying to edit the film so I couldnt add any captions so I really hope it makes sense to anyone who views it. Basicallly when you see the items move to wherer the player is, I'm right clicking it, when it is sent to the inventory, I am left clicking.

http://www.youtube.com/watch?v=njcA-OtF0As

If anyone can understand whats going on and knows of a way to help me, even if it doesnt work i'd be greatful
Spanks 4 ur tiem
gm3dgames
Chaos Rift Newbie
Chaos Rift Newbie
Posts: 5
Joined: Thu Nov 11, 2010 11:33 pm
Current Project: GM3D 2D Game Engine
Favorite Gaming Platforms: PC, Dreamcast, Xbox360
Programming Language of Choice: C++

Re: How to only use one item with inventory?

Post by gm3dgames »

wait, so your problem is that when you have muliple items and you click the last one, all of them get put into or out of the inventory?
no offense but your code is confusing me a bit, it seems as if its only accept 1 item as its value then looping and opening them all. Im not sure :S

Im really wondering about the onClick function in the first place. i would check the mouse click outside the item code and compare the coordinates of the mouse vs. the item through a for loop. I would need more details of how your game calls the onClick of the item and how you store the items to help. I have some theory, but i cant be too sure.
PaperDuckyFTW
Chaos Rift Cool Newbie
Chaos Rift Cool Newbie
Posts: 76
Joined: Sat Apr 03, 2010 5:08 am
Programming Language of Choice: C++

Re: How to only use one item with inventory?

Post by PaperDuckyFTW »

Haha i would take offense if it was understandable. I know its a pile of crap.
The logic behind the onClick function is this
onClick( player we drop the item under, inventory we add it to, item we are clicking on)
So in this case, it is:
Item item1(x, y); item1.onClick( player, slots, item1 );
Yeah, the problem seems to be that when I click the item to change it's position, it changes the position of all of the items that share the same SDL_Rect
I still have a few ideas to try out but its bothering me quite some
User avatar
dandymcgee
ES Beta Backer
ES Beta Backer
Posts: 4709
Joined: Tue Apr 29, 2008 3:24 pm
Current Project: https://github.com/dbechrd/RicoTech
Favorite Gaming Platforms: NES, Sega Genesis, PS2, PC
Programming Language of Choice: C
Location: San Francisco
Contact:

Re: How to only use one item with inventory?

Post by dandymcgee »

PaperDuckyFTW wrote:Haha i would take offense if it was understandable. I know its a pile of crap.
The logic behind the onClick function is this
onClick( player we drop the item under, inventory we add it to, item we are clicking on)
So in this case, it is:
Item item1(x, y); item1.onClick( player, slots, item1 );
Yeah, the problem seems to be that when I click the item to change it's position, it changes the position of all of the items that share the same SDL_Rect
I still have a few ideas to try out but its bothering me quite some
So give them all separate rects.
Falco Girgis wrote:It is imperative that I can broadcast my narcissistic commit strings to the Twitter! Tweet Tweet, bitches! :twisted:
PaperDuckyFTW
Chaos Rift Cool Newbie
Chaos Rift Cool Newbie
Posts: 76
Joined: Sat Apr 03, 2010 5:08 am
Programming Language of Choice: C++

Re: How to only use one item with inventory?

Post by PaperDuckyFTW »

But doing that would become inefficient, especially if I had over 100 items.
User avatar
dandymcgee
ES Beta Backer
ES Beta Backer
Posts: 4709
Joined: Tue Apr 29, 2008 3:24 pm
Current Project: https://github.com/dbechrd/RicoTech
Favorite Gaming Platforms: NES, Sega Genesis, PS2, PC
Programming Language of Choice: C
Location: San Francisco
Contact:

Re: How to only use one item with inventory?

Post by dandymcgee »

PaperDuckyFTW wrote:But doing that would become inefficient, especially if I had over 100 items.
Dude. Giving every item it's own position is not inefficient. It is perfectly logical and the right way to do it.
How could you possibly represent the position of multiple dynamic objects with a single set of x,y coordinates? :shock:
Falco Girgis wrote:It is imperative that I can broadcast my narcissistic commit strings to the Twitter! Tweet Tweet, bitches! :twisted:
PaperDuckyFTW
Chaos Rift Cool Newbie
Chaos Rift Cool Newbie
Posts: 76
Joined: Sat Apr 03, 2010 5:08 am
Programming Language of Choice: C++

Re: How to only use one item with inventory?

Post by PaperDuckyFTW »

In a platformer thing i was making, I used a vector to store enemies read from a map the same way a map is read from a file. It worked perfectly and when the player collided with the enemy, it worked fine.

What i meant by inefficient was because I understood your suggection as this:
SDL_Rect Item1 = {x,y,w,h};
SDL_Rect Item2 = {x,y,w,h};
SDL_Rect Item3 = {x,y,w,h};

I didn't think that wouls have been efficient but I wouldnt doubt if i misunderstood you
User avatar
dandymcgee
ES Beta Backer
ES Beta Backer
Posts: 4709
Joined: Tue Apr 29, 2008 3:24 pm
Current Project: https://github.com/dbechrd/RicoTech
Favorite Gaming Platforms: NES, Sega Genesis, PS2, PC
Programming Language of Choice: C
Location: San Francisco
Contact:

Re: How to only use one item with inventory?

Post by dandymcgee »

PaperDuckyFTW wrote:In a platformer thing i was making, I used a vector to store enemies read from a map the same way a map is read from a file. It worked perfectly and when the player collided with the enemy, it worked fine.

What i meant by inefficient was because I understood your suggection as this:
SDL_Rect Item1 = {x,y,w,h};
SDL_Rect Item2 = {x,y,w,h};
SDL_Rect Item3 = {x,y,w,h};

I didn't think that wouls have been efficient but I wouldnt doubt if i misunderstood you
What information did you store in the vector? If anything using a vector is surely less efficient than an SDL_Rect, but depending on the circumstances the dynamic properties of the vector may be necessary. I agree that we certainly wouldn't want every entity hard-coded into the source as an SDL_Rect for anything other than a very simple game.

Maybe this would help you out when deciding which type of storage container is most useful for your situation:
Image
Falco Girgis wrote:It is imperative that I can broadcast my narcissistic commit strings to the Twitter! Tweet Tweet, bitches! :twisted:
pritam
Chaos Rift Demigod
Chaos Rift Demigod
Posts: 991
Joined: Thu Nov 13, 2008 3:16 pm
Current Project: Elysian Shadows
Favorite Gaming Platforms: Amiga, PSOne, NDS
Programming Language of Choice: C++
Location: Sweden

Re: How to only use one item with inventory?

Post by pritam »

Awesome diagram :)
User avatar
ismetteren
Chaos Rift Junior
Chaos Rift Junior
Posts: 276
Joined: Mon Jul 21, 2008 4:13 pm

Re: How to only use one item with inventory?

Post by ismetteren »

pritam wrote:Awesome diagram :)
I agree :)
Image ImageImage Image
PaperDuckyFTW
Chaos Rift Cool Newbie
Chaos Rift Cool Newbie
Posts: 76
Joined: Sat Apr 03, 2010 5:08 am
Programming Language of Choice: C++

Re: How to only use one item with inventory?

Post by PaperDuckyFTW »

D-D-Diagram :shock: *points*

After some investivagating, I think have found the solution to the problem. I havn't found the fix to which the solution is but I know how to fix it.
For example, when I right click anywhere BEFORE I've added an item to the inventory, it doesn't do anything like it's suppost to. But after the item has been added to the inventory, even if it isn't in the inventory, when I right click anywhere the item is warped to me.

In short I need to either add a boolean or two, or find a way to reset the booleans I already have in place. If I am right, then I'll close this post thingy.
Post Reply