0 registered members (),
792
guests, and 2
spiders. |
Key:
Admin,
Global Mod,
Mod
|
|
|
Re: Access variable from other program?
[Re: WretchedSid]
#434871
12/28/13 20:25
12/28/13 20:25
|
Joined: Jun 2010
Posts: 590 California
Ruben
OP
User
|
OP
User
Joined: Jun 2010
Posts: 590
California
|
As far as the current translation unit is concerned: Yes. The include is replaced with the contents of the other script by the pre-processor.
By the way at whoever suggested global variables: Shame on you! Polluting the global namespace with variables is evil! Okay. Let say I create a function named active_weapon_slot() in OrcStronghold.c , as shown below:
function active_weapon_slot()
{
if(str_cmp(active_weapon_slot.floating_icon, "steel_sword.pcx"))
{
active_sword = ent_create ("sword.mdl", my.x, attach_weapon);
}
else
{
ent_remove(active_sword);
}
}
Now lets say I use the inv_create_item() function (taken from inventory.c) in the main function of OrcStronghold.c , as shown below:
// Inside OrcStronghold.c
function main()
{
...
item_shield = inv_create_item(1,0,"shield.pcx","shield.pcx");
item_apple = inv_create_item(1,0,"apple.pcx","apple.pcx");
item_sword = inv_create_item(0,1,"steel_sword.pcx","steel_sword.pcx");
item_mace = inv_create_item(0,1,"mace.pcx","mace.pcx");
item_gold = inv_create_item(1,0,"gold_coins.pcx","gold_coins.pcx");
In this last piece of code, I just created five items (.pcx images of equipment items) to be used to populate the slots of the inventory bag. I can drag these images among the different slots of the inventory bag, if I chose to. However, I still have not created the slots themselves for the inventory bag, in order to put items into. I now perform that action here within the same OrcStrongholdMain.c main function:
...
// ACTIVE ITEM SLOT
active_weapon_slot = inv_add_slot_to_bag(bag, 0, 1,
"leather_texture.pcx", 9, 60); // 3RD VALUE "1" (which
// belongs to group_id variable), ONLY EQUIPMENT
// ITEMS WITH group_id value = 1 CAN BE INSERTED
// INTO THIS SLOT. ONLY WEAPON ITEMS ARE ASSIGNED
// group_id = 1 . ALL NON-WEAPON ITEMS ARE ASSIGNED
// group_id = 0 , SO ONLY WEAPON ITEMS CAN BE
// INSERTED INTO THIS SLOT. I SET
// active_weapon_slot EQUAL TO THIS SLOT.
// "active_weapon_slot()" is a function in
// OrcStronghold.c , outside the main function.
// EACH ROW OF INVENTORY BAG IS SPACED OUT BY 64 HEIGHT
// FIRST ROW OF INVENTORY BAG
inv_add_slot_to_bag(bag,1,0,"leather_texture.pcx",9,150);
inv_add_slot_to_bag(bag,2,0,"leather_texture.pcx",70,150);
inv_add_slot_to_bag(bag,3,0,"leather_texture.pcx",130,150);
inv_add_slot_to_bag(bag,4,0,"leather_texture.pcx",190,150);
// NOTICE THAT THE THIRD VALUE OF THESE SLOTS
// ARE ASSIGNED THE VALUE 0 (zero). THE REASON FOR
// THIS IS BECAUSE THESE ITEMS ARE NOT WEAPONS,
// THEREFORE, I ASSIGN THEIR group_id VARIABLE TO 0.
...
So in the last code above, I created an inventory bag with five slots. The top slot is reserved as the "active weapon" slot. This slot checks to see what the group_id is of an equipment item (.pcx image). If the group_id of the image is 1, that image can be placed in that slot. If the group_id of the equipment item is not 1 (like zero), then the equipment item cannot be placed in this slot. I also created four other slots underneath the "active weapon" slot. These four slots can accept any items, weapon or non-weapon. That is because their group_id value (3rd value) is equal to 0. Now, I also created the function active_weapon_slot() in OrcStronghold.c , before the main function. This function is supposed to represent the "active weapon" slot in the inventory bag. Whatever .pcx image of a weapon is placed in this "active weapon" slot inside the inventory bag, that is the weapon that the player should be armed with, in the player's hand, ready to use. This is the code of function active_weapon_slot() that is trying to accomplish this:
// Inside OrcStronghold.c
function active_weapon_slot()
{
if(str_cmp(active_weapon_slot.floating_icon, "steel_sword.pcx"))
{
active_sword = ent_create ("sword.mdl", my.x, attach_weapon);
}
else
{
ent_remove(active_sword);
}
}
The function above is comparing the floating_icon variable's string, to the string "steel_sword.pcx". The variable floating_icon comes from inventory.c , and is used in the function inv_create_item , that we used earlier to create equipment item .pcx images, to be used to populate slots in the inventory bag. The function inv_create_item() is shown here:
// Inside inventory.c
...
function inv_create_item(item_id, group_id, STRING* floating_icon, STRING* inventory_icon)
{
// Create item and assign images
Item* item = new(Item);
item->floating_icon = floating_icon;
item->inventory_icon = inventory_icon;
item->id = item_id;
item->group_id = group_id;
// Add item to global array for cleanup purposes
inv_items_array[inv_item_count] = item;
inv_item_count++;
return item;
}
As you see in the code above, floating_icon is the third variable taken as an argument in the inv_create_item function. However, if you notice in the code before last, I am trying to access the string value of that floating_icon variable (that is used as an argument in inv_create_item() inside inventory.c script) from the OrcStronghold.c script , in order to compare it with the string value "steel_sword.pcx". "steel_sword.pcx" is the file name of the sword image that is used to populate the inventory bag slots. If floating_icon string value of the active weapon slot equals "steel_sword.pcx", I want to attach a .mdl sword model to the player's hand, which is shown in the code above last. When I compile this, this is my error: Compiling ORCSTRONGHOLD.C - [Esc] to abort...... Error in 'line 180: 'floating_icon' : is not a member of 'BOOL' < if(str_cmp(active_weapon_slot.floating_icon, "steel_sword.pcx")) .. 0.108 sec Error compiling ORCSTRONGHOLD.C Error E355: Startup failure - any key to abort Even though I #include inventory.c at the beginning of OrcStronghold.c , either I am using the function active_weapon_slot incorrectly, or I am not able to access the floating_icon value in the active weapon slot for some reason. Do you know what I am doing wrong?
Last edited by Ruben; 12/28/13 20:34.
|
|
|
Re: Access variable from other program?
[Re: Ruben]
#434872
12/28/13 20:36
12/28/13 20:36
|
Joined: Jun 2010
Posts: 590 California
Ruben
OP
User
|
OP
User
Joined: Jun 2010
Posts: 590
California
|
Speaking in layman's terms, when a picture of a sword is inside the "active weapon" slot of the inventory bag, I want my player to be armed with a sword. If a picture of a mace is inside the "active weapon slot" of the inventory bag, I want my player to be armed with a mace; etc.
That is what this code is trying to accomplish.
Should I post this in a different thread that is beyond the "Starting with Gamestudio" thread?
Last edited by Ruben; 12/28/13 20:37.
|
|
|
Re: Access variable from other program?
[Re: Ruben]
#434877
12/29/13 01:27
12/29/13 01:27
|
Joined: Jun 2010
Posts: 590 California
Ruben
OP
User
|
OP
User
Joined: Jun 2010
Posts: 590
California
|
I will attempt to explain this in simpler terms again. It seems very hard for me to communicate this problem to people. If people on this thread cannot understand my problem after trying to explain it here, I will have no choice but to take this to a different thread beyond "Starting with Gamestudio". So here it goes:
Script: OrcStronghold.c
Functions: main()
active_weapon_slot()
Actions: #include "inventory.c" in beginning of script.
In Main(): Uses inv_create_item() function
(stored in inventory.c) to process .pcx images
of equipment items, like sword, mace, gold,
apple, etc., so that their .pcx images can be
used in the inventory bag GUI as equipment
item images that can be placed in slots,
representing equipment items in the player's
inventory.
In Main(): Uses inv_add_slot_to_bag() function
(stored in inventory.c) to add slots in the
inventory bag. The programmer can create as
many slots as she/he wants for the inventory
bag. The function name "active_weapon_slot"
is set equal to the inv_add_slot_to_bag
instance that is supposed to represent the
slot used for arming the player with a weapon.
In active_weapon_slot(): Tries to compare the
variable string stored in floating_icon
variable (which is an argument in
inv_create_item() function, stored in
inventory.c) against the string
"steel_sword.pcx". The file name
"steel_sword.pcx" is an argument passed to the
inv_create_item() function from
OrcStronghold.c main() function, to allow an
image of a sword representing a sword in
inventory, that can be used among the slots in
the inventory bag.
Script: inventory.c
Functions: inv_add_slot_to_bag(Bag* bag, int slot_id, int
group_id, STRING* default_image, int
rel_x_pos, int rel_y_pos)
inv_create_item(item_id, group_id, STRING*
floating_icon, STRING* inventory_icon)
Actions: inv_add_slot_to_bag() function creates a slot for
a custom made inventory bag for the player.
inv_create_item() function allow a .pcx image to
be used in the inventory bag, representing an
equipment item.
Code:
// OrcStronghold.c
#include "inventory.c"
...
function active_weapon_slot()
{
if(str_cmp(active_weapon_slot.floating_icon, "steel_sword.pcx"))
{
active_sword = ent_create ("sword.mdl", my.x, attach_weapon);
}
else
{
ent_remove(active_sword);
}
}
...
function main()
{
...
item_shield = inv_create_item(1,0,"shield.pcx","shield.pcx");
item_apple = inv_create_item(1,0,"apple.pcx","apple.pcx");
item_sword = inv_create_item(0,1,"steel_sword.pcx","steel_sword.pcx");
item_mace = inv_create_item(0,1,"mace.pcx","mace.pcx");
item_gold = inv_create_item(1,0,"gold_coins.pcx","gold_coins.pcx");
...
// START OF INVENTORY BAG
// ACTIVE ITEM SLOT
active_weapon_slot = inv_add_slot_to_bag(bag, 0, 1, "leather_texture.pcx",
9, 60);
inv_add_slot_to_bag(bag,1,0,"leather_texture.pcx",9,150);
inv_add_slot_to_bag(bag,2,0,"leather_texture.pcx",70,150);
inv_add_slot_to_bag(bag,3,0,"leather_texture.pcx",130,150);
inv_add_slot_to_bag(bag,4,0,"leather_texture.pcx",190,150);
...
}
// inventory.c
...
function inv_create_item(item_id, group_id, STRING* floating_icon, STRING* inventory_icon)
{
// Create item and assign images
Item* item = new(Item);
item->floating_icon = floating_icon;
item->inventory_icon = inventory_icon;
item->id = item_id;
item->group_id = group_id;
// Add item to global array for cleanup purposes
inv_items_array[inv_item_count] = item;
inv_item_count++;
return item;
}
...
function inv_add_slot_to_bag(Bag* bag, int slot_id, int group_id, STRING* default_image, int rel_x_pos, int rel_y_pos)
{
Slot* new_slot;
new_slot = new(Slot);
// Set the position for the new slot
new_slot->rel_x_pos = rel_x_pos;
new_slot->rel_y_pos = rel_y_pos;
new_slot->background_image = default_image;
new_slot->item = NULL;
new_slot->id = slot_id;
new_slot->group_id = group_id;
new_slot->bag_id = bag->id;
bag->slots[bag->_slot_count] = new_slot;
bag->_slot_count += 1;
}
...
How can I get OrcStronghold.c to access the floating_icon value (stored in inv_create_item() function, which is stored in inventory.c script) for the "active weapon" slot, using the active_weapon_slot() function in OrcStronghold.c ? I think this is about the simplest way that I can try to explain this.
Last edited by Ruben; 12/29/13 01:39.
|
|
|
Re: Access variable from other program?
[Re: Ruben]
#434878
12/29/13 02:20
12/29/13 02:20
|
Joined: Nov 2006
Posts: 497 Ohio
xbox
Senior Member
|
Senior Member
Joined: Nov 2006
Posts: 497
Ohio
|
From what I am understanding, by the looks of part of your code such as
Slot* new_slot;
new_slot = new(Slot);
you are trying to use structs. You cannot (as far as I am aware) store variables in functions. Functions are just routines or methods that allow you to modify data, call other routines, etc. You can do as the others were saying and save these variables to global variables so that you can always access them, However the downside to that is if you decide to make more inventory slots, you must go add more global variables to match the new slots. Back to using stucts. Structs are the best way to go in this situation because for every new "slot" you want to add, create a new "instance" of a slot struct and now you can easily access those variables per instance. example
typedef struct{
var rel_x_pos, rel_y_pos;
STRING* background_image;
var item;
var id;
var group_id;
var bag_id;
} Slot;
If you have already done that, sorry for typing code. Once that is done, if you have stored the instances in an array example.
Slot* inv_slots[100];
inv_slots[0] = new Slot;
you could easily access the variables like this
inv_slots[21].item = 2; // or what ever you want to do with it.
//or change the background picture like this.
inv_slots[53].background_image = "newBackground.pcx";
I hope this helps. If not I sincerely apologize. Best wishes!
|
|
|
Re: Access variable from other program?
[Re: xbox]
#435012
01/01/14 20:18
01/01/14 20:18
|
Joined: Jun 2010
Posts: 590 California
Ruben
OP
User
|
OP
User
Joined: Jun 2010
Posts: 590
California
|
Thank you xbox. I think you are on the right track. I am trying to use structs now in my situation. However, for some reason I am still not able to attach a sword to my player's hand when I drag a sword image toward the active weapon slot in the player's inventory bag. So far, this is what I have done in my code: OrcStronghold.c
// OrcStronghold.c
#include "Player.c"
...
Item* inv_slots[13];
inv_slots = new(Item);
...
function main()
{
...
// Creating equipment items to be used in inventory bag (.pcx images to click
// and drag among slots in inventory bag)
item_shield = inv_create_item(1,0,"shield.pcx","shield.pcx");
item_apple = inv_create_item(1,0,"apple.pcx","apple.pcx");
item_sword = inv_create_item(0,1,"steel_sword.pcx","steel_sword.pcx");
item_mace = inv_create_item(0,1,"mace.pcx","mace.pcx");
item_gold = inv_create_item(1,0,"gold_coins.pcx","gold_coins.pcx");
bag = inv_create_bag(1,"leather_seam.pcx"); // <---- added this line
// START OF INVENTORY BAG
// ACTIVE ITEM SLOT
inv_slots[0] = inv_add_slot_to_bag(bag,0,1,"leather_texture.pcx",9,60);
// Active Weapon slot
// EACH ROW OF INVENTORY BAG IS SPACED OUT BY 64 HEIGHT
// FIRST ROW OF INVENTORY BAG
inv_slots[1] = inv_add_slot_to_bag(bag,1,0,"leather_texture.pcx",9,150);
inv_slots[2] = inv_add_slot_to_bag(bag,2,0,"leather_texture.pcx",70,150);
inv_slots[3] = inv_add_slot_to_bag(bag,3,0,"leather_texture.pcx",130,150);
inv_slots[4] = inv_add_slot_to_bag(bag,4,0,"leather_texture.pcx",190,150);
// SECOND ROW OF INVENTORY BAG
inv_slots[5] = inv_add_slot_to_bag(bag,5,0,"leather_texture.pcx",9,214);
inv_slots[6] = inv_add_slot_to_bag(bag,6,0,"leather_texture.pcx",70,214);
inv_slots[7] = inv_add_slot_to_bag(bag,7,0,"leather_texture.pcx",130,214);
inv_slots[8] = inv_add_slot_to_bag(bag,8,0,"leather_texture.pcx",190,214);
// THIRD ROW OF INVENTORY BAG
inv_slots[9] = inv_add_slot_to_bag(bag,9,0,"leather_texture.pcx",9,278);
inv_slots[10] = inv_add_slot_to_bag(bag,10,0,"leather_texture.pcx",70,278);
inv_slots[11] = inv_add_slot_to_bag(bag,11,0,"leather_texture.pcx",130,278);
inv_slots[12] = inv_add_slot_to_bag(bag,12,0,"leather_texture.pcx",190,278);
if(str_cmp(inv_slots[0].floating_icon, "steel_sword.pcx"))
{
active_sword = ent_create ("sword.mdl", my.x, attach_weapon);
}
else
{
ent_remove(active_sword);
}
...
}
// Player.c
#include "inventory.c"
...
// Attaches a weapon to player's hand
action attach_weapon()
{
set(my,PASSABLE);
proc_mode = PROC_LATE;
while (you != NULL)
{
vec_for_vertex(temp.x,you,997); //hand palm base: Vector # 987
vec_for_vertex(temp2.x,you,968); //hand palm tip: Vector # 982
vec_set(my.x,temp.x);
vec_diff(temp.x,temp2.x,temp.x);
vec_to_angle(my.pan,temp.x); // ERROR "'pan' is not a member of 'VECTOR'
vec_set(my.pan,my.pan);
wait(1);
}
}
...
// inventory.c
...
typedef struct
{
int id;
int group_id;
STRING* floating_icon;
STRING* inventory_icon;
} Item;
// === Slot ===
typedef struct
{
PANEL* slot_panel;
int id;
int group_id;
int rel_x_pos;
int rel_y_pos;
int width;
int height;
STRING* background_image;
Item *item;
int bag_id;
} Slot;
// === Bag ===
typedef struct
{
int id;
int is_open;
int drag_region_top_left_x;
int drag_region_top_left_y;
int drag_region_bottom_right_x;
int drag_region_bottom_right_y;
int close_region_top_left_x;
int close_region_top_left_y;
int close_region_bottom_right_x;
int close_region_bottom_right_y;
PANEL* bag_panel;
Slot* slots[16];
int _slot_count;
STRING* image_name;
} Bag;
...
function inv_create_item(item_id, group_id, STRING* floating_icon, STRING* inventory_icon)
{
// Create item and assign images
Item* item = new(Item);
item->floating_icon = floating_icon;
item->inventory_icon = inventory_icon;
item->id = item_id;
item->group_id = group_id;
// Add item to global array for cleanup purposes
inv_items_array[inv_item_count] = item;
inv_item_count++;
return item;
}
...
function inv_create_bag(int bag_id, STRING* image_name)
{
Bag* bag;
bag = new(Bag);
bag->image_name = image_name;
bag->id = bag_id;
// Initialize slot_count to 0
bag->_slot_count = 0;
bag->is_open = 0;
// Add bag to global array for cleanup purposes
inv_bags_array[inv_bag_count] = bag;
inv_bag_count++;
return bag;
}
...
function inv_add_slot_to_bag(Bag* bag, int slot_id, int group_id, STRING* default_image, int rel_x_pos, int rel_y_pos)
{
Slot* new_slot;
new_slot = new(Slot);
// Set the position for the new slot
new_slot->rel_x_pos = rel_x_pos;
new_slot->rel_y_pos = rel_y_pos;
new_slot->background_image = default_image;
new_slot->item = NULL;
new_slot->id = slot_id;
new_slot->group_id = group_id;
new_slot->bag_id = bag->id;
bag->slots[bag->_slot_count] = new_slot;
bag->_slot_count += 1;
}
...
When I compile OrcStronghold.c , it does not produce any syntax errors, but when I access my inventory bag and drag a sword image ("steel_sword.pcx") over to the active weapon slot, and get out of the inventory bag, my player is not being armed with the sword. Does anyone know what I may be doing wrong in trying to make this happen?
Last edited by Ruben; 01/01/14 20:34.
|
|
|
Re: Access variable from other program?
[Re: Ruben]
#435014
01/01/14 21:07
01/01/14 21:07
|
Joined: Nov 2006
Posts: 497 Ohio
xbox
Senior Member
|
Senior Member
Joined: Nov 2006
Posts: 497
Ohio
|
where is the code showing what happens when you drag the sword to the active slot? From the above code, I see that you have the active weapon slot set with what I assume to be just an empty square to represent an inventory space. I think what you need to do via code is set
inv_slots[0] = item_sword;
For some reason though, I feel like the visual inventory will get messed up by overwriting the inventory to the sword, although the sword should be created.
|
|
|
Re: Access variable from other program?
[Re: xbox]
#435018
01/01/14 21:26
01/01/14 21:26
|
Joined: Jun 2010
Posts: 590 California
Ruben
OP
User
|
OP
User
Joined: Jun 2010
Posts: 590
California
|
There seems to be a lot going on with the code that drags the sword to the active slot, which I don't even fully understand. Here is the entire open source inventory.c script that I am using:
//
// Inventory.c - programmed by Bret Truchan. You are welcome to use this inventory
// system in the creation of commercial or free games. You may not use it for any
// other purpose.
//
/*
DOCUMENTATION
Table of Contents
I. Introduction
II. Essentials: inv_init() and inv_cleanup()
III. Creating items for your inventory
IV. Making your first bag
V. Opening and Closing bags
VI. Setting bag close and drag regions
VII. Adding items to bags
VIII. Item Groups
IX. Callbacks
X. Other helpful functions
I. Introduction
---------------
Hello fellow programmer! I hope that you can find the following inventory
system useful. My main goal when making this inventory system was to decouple
the inventory system from the rest of the game code. I also wanted to make it
as easy as possible to create and manage your inventory system.
This inventory has the following features:
1. Easy to use
2. Supports multiple bags
3. Handles the layering of bags for you
4. Supports callbacks for inventory events
5. Supports item "groups". (For example, gerbils can only be put in gerbil
slots.)
I modeled the inventory system after World of Warcraft. One limitation to this
system is that slots in bags really need to be the same size. I know how to
fix this so, for example, your sword would show up huge in the sword slot but
small in a backpack slot, but I'll have to save that for a later release.
II. Essentials: inv_init() and inv_cleanup()
--------------------------------------------
Let's dive right in. Creating your inventory is done in your lite-c code.
You should not need to modify inventory.c. Before anything else, include
inventory.c in your code, like so:
#include <acknex.h>
#include <default.c>
#include "inventory.c" // <---- ADDED THIS
void main()
{
inv_init(); // <---- ADDED THIS
wait(1); // <---- ADDED THIS
// etc..
Add the inv_init(); function call to your main loop as shown above. Because
inventory.c uses some low level C structures, you need to call inv_cleanup()
just before your game closes.
III. Creating items for your inventory
--------------------------------------
Let's skip ahead and create some images that will be needed for your
inventory. If you have the demo for this inventory code, you can use my demo
images.
pack.pcx - The is the background image of your inventory pack.
slot_bg.pcx - The background image of an empty slot.
item1.pcx - An icon of an item, such as a sword. This should be the same
size as slot_bg.pcx.
Ok, back to items....
Items are strange. You might think of an item like a "sword" or "gun".
However, this inventory system is NOT trying to control how you manage items
for your game. Although you might have a "sword" item in your inventory, the
structure that's passed around in the inventory code should NOT have
attributes such as "damage" or "weight".
Let's move ahead with an example of adding your first item - A pile of sand.
Maybe this pile of sand will go into your nephew's Christmas Stocking
because he ate all your friggin' cookies?!
#include <acknex.h>
#include <default.c>
#include "inventory.c"
Item* item_sand;
void main()
{
inv_init();
wait(1);
item_sand = inv_create_item(1,0,"item1.pcx","item1.pcx");
See that inv_create_item(...) statement? inv_create_item() creates an abstract
item in your inventory system. Let's break it down:
item_pointer = inv_create_item(item_id,group_id,floating_icon,inventory_icon);
Arguments:
item_id - You make this up. It can be anything that you want. It doesn't affect the inventory engine.
group_id - Later on, slots will also have a group id. Items can only be put into slots with the right group id.
floating_icon - The image used for the item while it's being dragged around the inventory system.
inventory_icon - The image for displaying the item when the item is in a slot.
To reiterate, we introduced a new item into our inventory system. We gave it an item id of 1, which really doesn't mean anything. We gave it a group_id = 0, which means that the item can be placed into any slot having group_id=0. We choose the same image "item1.pcx" for the icon used to "float" the item around in the inventory as well as the icon that represents the item in a slot. That's good enough for now. We'll keep moving forward..
IV. Making your first bag
-------------------------
There are a few terms that I loosly introduced above. Your inventory may have multiple "bags". Bags have multiple "slots", and slots may contain items. Let's make our first bag. Luckily, it's pretty easy:
#include <acknex.h>
#include <default.c>
#include "inventory.c"
Item* item_sand;
Bag* bag; // <---- added this line
void main()
{
inv_init();
wait(1);
item_sand = inv_create_item(1,0,"item1.pcx","item1.pcx");
bag = inv_create_bag(1,"pack.pcx"); // <---- added this line
Easy! When you do this, the bag does not appear on the screen. We'll handle that later. For now, let's look closely at the
inv_create_bag() function:
bag = inv_create_bag(bag_id,bag_image);
Arguments
bag_id - You make this up. It's not used within the inventory system, but it can be useful when handling callbacks. We'll
discuss callbacks later on.
bag_image - This should be an image of your open inventory bag.
Creating a bag is only half the battle. Generally, you use the inv_add_slot_to_bag() function to add
a slot to your bag. Here's the generic version:
function inv_add_slot_to_bag(Bag* bag, int slot_id, int group_id, STRING* default_image, int rel_x_pos, int rel_y_pos)
Arguments:
bag - The bag that you created above.
slot_id - Any value that you like. It's only used for callbacks, which I'll cover later.
group_id - Only items having this value may be added to the slot.
default_image - An image showing an empty slot.
rel_x_pos - x position relative to the top left of the bag's image
rel_y_pos - y position relative to the top left of the bag's image
Here's a real world example of creating 4 slots to your bag:
inv_add_slot_to_bag(bag,1,0,"slot_bg.pcx",9,38);
inv_add_slot_to_bag(bag,2,0,"slot_bg.pcx",44,38);
inv_add_slot_to_bag(bag,3,0,"slot_bg.pcx",78,38);
inv_add_slot_to_bag(bag,4,0,"slot_bg.pcx",112,38);
V. Opening and Closing bags
---------------------------
Opening bags is easy:
inv_open_bag(Bag* bag, int panel_x_position, int panel_y_position);
That's it! Here's use a real world example:
inv_open_bag(bag, 100,100);
Closing your bag is even easier:
inv_close_bag(bag);
We haven't added items to bags yet, but you'll see that it's very easy. When you open and close bags, the bags remember what items they contained. You don't need to re-add the items.
VI. Setting bag close and drag regions
--------------------------------------
This inventory system allows you to drag bags around the screen and close them. It's optional. All you need to do is tell the inventory system where the drag region and close region are on the bag image. Here's an example:
inv_set_bag_drag_region(bag,5,3,128,18);
inv_set_bag_close_region(bag,129,0,148,19);
The arguments are:
function inv_set_bag_drag_region(Bag* bag, int top_left_x, int top_left_y, int bottom_right_x, int bottom_right_y)
function inv_set_bag_close_region(Bag* bag, int top_left_x, int top_left_y, int bottom_right_x, int bottom_right_y)
Quick note: For multiple bags, the inventory code automatically handles which bag should be "on top" if they overlap.
VII. Adding items to bags
-------------------------
Believe it or not, you're almost done. Adding items to the inventory system can be done in two ways. First, you can add an item directly to a bag. Alternatively, you can create an item and immediately have it "float" (which means that the icon is visible and is being dragged by the mouse).
Adding an item directly to a bag:
function inv_insert_item_into_bag(Bag* bag, Item* item)
For example:
inv_insert_item_into_bag(bag,item_sand);
(This function will return 1 if there was room in the bag for the item, otherwise 0.)
... OR "Floating" a new item:
function inv_float_item(Item* item)
For example:
function inv_float_item(item_sand);
That's it!
VIII. Item Groups
-----------------
Item groups are super easy. Group_id 0 is special. If you assign group_id = 0 to a slot, that slot can hold ANY
item. Let's pretend that you want to make a weapon slot that can ONLY hold weapons. When you create the sword item,
use the group_id = 4; Then, when you create the sword slot, set its group_id = 4 too. Done!
IX. Callbacks
-------------
If you need to know when certain events happen in the inventory system, you'll want to use the callbacks. I'll explain with an example. Let's say that you want to know whenever a bag is opened. First, you need to define a function in your lite-c that will be called when a bag is open. An open-bag callback function looks like:
a) open_bag_callback
// put something like this in your lite-c
function bag_was_opened(int bag_id)
{
// do something
}
Then, register this function with the inventory system by calling set_on_open_bag_callback() like so:
set_on_open_bag_callback("bag_was_opened");
Whenever a bag is opened, your function bag_was_opened() will be called. The bag_id of the opened bag will be passed into your function automatically. Remember when we first created a bag and I said that the bag_id was useless? I lied. Here's where it comes into play. You can tell which bag was opened by looking at the bag_id that's passed in to your callback function.
b) on_click_callback
This is most complicated callback. It's triggered whenever someone clicks on a slot. To use it, add something like this to your lite-c:
function slot_was_clicked(int action, int bag_id, int slot_id, int placed_item_id, int removed_item_id)
{
if (action == INV_ITEM_PLACED)
{
// item was placed in bag
// bag_id is the id of the bag where the item was placed
// slot_id is the id of the slot where the item was placed
// placed_item_id is the item id that was placed into the slot
// removed_item_id is 0 and should be ignored
}
if (action == INV_ITEM_REMOVED)
{
// item was removed from bag
// bag_id is the id of the bag where the item was placed
// slot_id is the id of the slot where the item was placed
// placed_item_id is 0 and should be ignored
// removed_item_id is the item id that was removed from the slot
}
if (action == INV_ITEM_SWAPED)
{
// item was put in to a slot that already contained an item, so they were swapped
// bag_id is the id of the bag where the item was placed
// slot_id is the id of the slot where the item was placed
// placed_item_id is the item id that was placed into the slot
// removed_item_id is the item id that was removed from the slot
}
}
And register your callback like:
set_on_click_callback("slot_was_clicked");
c) on_bag_close_callback
This is just like on_bag_open_callback. Here's an example:
function bag_was_closed(int bag_id)
{
// do something
}
Then, register this function with the inventory system by calling set_on_close_bag_callback() like so:
set_on_close_bag_callback("bag_was_closed");
X. Other helpful functions
--------------------------
PANEL* inv_get_bag_panel_ptr(Bag* bag); // given a bag, return its panel pointer
inv_is_bag_open(Bag* bag); // returns 1 if the bag is open, otherwise 0
inv_get_open_bag_count(); // returns the number of open bags
inv_is_floating(); // returns 1 if the player is floating an inventory item
inv_is_item_in_bag(Bag* bag, Item* item); // returns 1 if the item is in the bag
*/
// ============================ BEGIN CODE =================================
#define new(type) malloc(sizeof(type##))
#define delete(object) free(object)
#define bag_layer 1
#define slot_layer 2
#define floating_item_layer 94
#define INV_ITEM_PLACED 1
#define INV_ITEM_SWAPPED 2
#define INV_ITEM_REMOVED 3
/*
struct Item
The item structure holds a single item's information. Items are intended to
track inventory icons only. They're not really meant to manage an entire
game's items. For example, you would NOT use the item struct to hold values
such as damage or defense rating for a sword. The id in the item struct is
intended to help associate these inventory based items with whatever item
management is used in the game. The id is set by the game developer to
any arbitrary value. The id is used in callback functions.
*/
typedef struct
{
int id;
int group_id;
STRING* floating_icon;
STRING* inventory_icon;
} Item;
// === Slot ===
typedef struct
{
PANEL* slot_panel;
int id;
int group_id;
int rel_x_pos;
int rel_y_pos;
int width;
int height;
STRING* background_image;
Item *item;
int bag_id;
} Slot;
// === Bag ===
typedef struct
{
int id;
int is_open;
int drag_region_top_left_x;
int drag_region_top_left_y;
int drag_region_bottom_right_x;
int drag_region_bottom_right_y;
int close_region_top_left_x;
int close_region_top_left_y;
int close_region_bottom_right_x;
int close_region_bottom_right_y;
PANEL* bag_panel;
Slot* slots[16];
int _slot_count;
STRING* image_name;
} Bag;
// === Floating Item ===
typedef struct
{
Item* item;
PANEL* floating_item_panel;
} FloatingItem;
// Ugly linked list for keeping track of panels and associated slots
typedef struct SlotPanelAssoc
{
PANEL* slot_panel;
Slot* slot;
struct SlotPanelAssoc* next;
struct SlotPanelAssoc* prev;
} SlotPanelAssoc;
// Another ugly linked list for keeping track of z-order of open bags
typedef struct BagLayer
{
Bag* bag;
struct BagLayer* next;
struct BagLayer* prev;
} BagLayer;
// Global variables
SlotPanelAssoc* slot_panel_assoc;
BagLayer* bag_layer_node;
FloatingItem* global_floating_item_ptr;
int inv_floating_flag;
int inv_open_bag_count; // The number of open bags
int inv_item_count; // index used for the inv_items_array
int inv_bag_count; // index used for the inv_bags_array
Item* inv_items_array[5000]; // Global array to hold item pointers. Used by cleanup script only.
Bag* inv_bags_array[100]; // Again, store all created bags in this array so we can properly deallocate them later.
// =============== FUNCTIONS =============================================================
// function prototypes
function inv_close_bag(Bag*);
function _inv_do_float(FloatingItem*);
function _inv_drag_bag(Bag*, int drag_offset_x, int drag_offset_y);
function addBagLayer(Bag*);
function removeBagLayer(Bag*);
function reorderBagLayers();
function addSlotPanelAssoc(Slot* slot, PANEL* slot_panel);
function removeSlotPanelAssoc(Slot* slot);
function getSlotPtrForPanelPtr(PANEL* panel_ptr);
function getBagPtrForPanelPtr(PANEL* panel_ptr);
// Callback function prototypes
void on_click_callback_function_ptr(int inv_action, int bag_id, int slot_id, int placed_item_id, int removed_item_id);
void on_float_end_callback_function_ptr();
void on_close_bag_callback_function_ptr(int bag_id);
void on_open_bag_callback_function_ptr(int bag_id);
// --------------- Inventory Function -----------------------------------
function inv_init()
{
// Create a instance of the floating item struct and set the global_floating_item_ptr to it
FloatingItem* floating_item = new(FloatingItem);
floating_item->item = NULL;
inv_floating_flag = 0; // set global floating flag
global_floating_item_ptr = floating_item;
}
function bagOnClick(PANEL* panel_ptr)
{
Bag* bag;
bag = getBagPtrForPanelPtr(panel_ptr);
// Check to see if the player is dragging the panel
if (bag->drag_region_top_left_x != bag->drag_region_bottom_right_x)
{
if ((mouse_pos.x > (bag->bag_panel->pos_x + bag->drag_region_top_left_x))
&& (mouse_pos.x < (bag->bag_panel->pos_x + bag->drag_region_top_left_x + (bag->drag_region_bottom_right_x - bag->drag_region_top_left_x)))
&& (mouse_pos.y > (bag->bag_panel->pos_y + bag->drag_region_top_left_y))
&& (mouse_pos.y < (bag->bag_panel->pos_y + bag->drag_region_top_left_y + (bag->drag_region_bottom_right_y - bag->drag_region_top_left_y))))
{
_inv_drag_bag(bag,mouse_pos.x - bag->bag_panel->pos_x, mouse_pos.y - bag->bag_panel->pos_y);
}
}
if (bag->close_region_top_left_x != bag->close_region_bottom_right_x)
{
if ((mouse_pos.x > (bag->bag_panel->pos_x + bag->close_region_top_left_x))
&& (mouse_pos.x < (bag->bag_panel->pos_x + bag->close_region_top_left_x + (bag->close_region_bottom_right_x - bag->close_region_top_left_x)))
&& (mouse_pos.y > (bag->bag_panel->pos_y + bag->close_region_top_left_y))
&& (mouse_pos.y < (bag->bag_panel->pos_y + bag->close_region_top_left_y + (bag->close_region_bottom_right_y - bag->close_region_top_left_y))))
{
inv_close_bag(bag);
return(0);
}
}
// Bring bag to the front
removeBagLayer(bag);
addBagLayer(bag);
reorderBagLayers();
}
function _inv_drag_bag(Bag* bag, int drag_offset_x, int drag_offset_y)
{
int i;
while(mouse_left)
{
vec_set(mouse_pos,mouse_cursor);
// Move bag
bag->bag_panel->pos_x = mouse_pos.x - drag_offset_x;
bag->bag_panel->pos_y = mouse_pos.y - drag_offset_y;
// Move all slots
for (i=0; i < bag->_slot_count; i++)
{
bag->slots[i]->slot_panel->pos_x = bag->slots[i]->rel_x_pos + bag->bag_panel->pos_x;
bag->slots[i]->slot_panel->pos_y = bag->slots[i]->rel_y_pos + bag->bag_panel->pos_y;
}
wait(1);
}
}
function slotOnClick(PANEL* clicked_panel)
{
Slot* clicked_slot = getSlotPtrForPanelPtr(clicked_panel);
if (clicked_slot == NULL) { diag("\n*** Error: panel not found\n"); }
// player clicked on item in inventory while not floating an item
diag("test1");
if (global_floating_item_ptr->item == NULL)
{
diag("test2");
if (clicked_slot->item != NULL) // Player is grabbing an item out of the inventory
{
diag("\ngrab started\n");
// optionally callback with action, bag_id, slot_id, item_id
if (on_click_callback_function_ptr) on_click_callback_function_ptr(INV_ITEM_REMOVED,clicked_slot->bag_id,clicked_slot->id,0,clicked_slot->item->id);
// Create the floating panel
global_floating_item_ptr->floating_item_panel = pan_create("",floating_item_layer);
// Set the item and panel image of the floating item structure. This effectively "floats"
// the item that was stored in the inventory slot.
global_floating_item_ptr->item = clicked_slot->item;
global_floating_item_ptr->floating_item_panel->bmap = bmap_create(clicked_slot->item->floating_icon);
global_floating_item_ptr->floating_item_panel->flags |= VISIBLE;
// Set the item pointer of the clicked on slot to NULL
clicked_slot->item = NULL;
// Restore inventory slot image to be the default background image
clicked_slot->slot_panel->bmap = bmap_create(clicked_slot->background_image);
inv_floating_flag = 1;
_inv_do_float(global_floating_item_ptr);
}
}
else
{
diag("test3");
if ((clicked_slot->group_id == 0) || (clicked_slot->group_id == global_floating_item_ptr->item->group_id)) // Test to make sure that item can be placed in the slot
{
if (clicked_slot->item == NULL) // player is putting an item into an empty inventory slot
{
// optionally callback with action, bag_id, slot_id, item_id
if (on_click_callback_function_ptr) on_click_callback_function_ptr(INV_ITEM_PLACED,clicked_slot->bag_id,clicked_slot->id,global_floating_item_ptr->item->id,0);
// Place item in slot
clicked_slot->item = global_floating_item_ptr->item;
clicked_panel->bmap = bmap_create(global_floating_item_ptr->item->inventory_icon);
global_floating_item_ptr->item = NULL;
// End float
pan_remove(global_floating_item_ptr->floating_item_panel);
inv_floating_flag = 0;
}
else // player is swapping the floating item for the one in the inventory
{
// optionally callback with action, bag_id, slot_id, item_id
if (on_click_callback_function_ptr) on_click_callback_function_ptr(INV_ITEM_SWAPPED,clicked_slot->bag_id,clicked_slot->id,global_floating_item_ptr->item->id,clicked_slot->item->id);
// Backup the information of the clicked on slot
Item* clicked_slot_item_pointer = clicked_slot->item;
STRING* clicked_slot_inventory_icon = str_create(clicked_slot->item->inventory_icon);
// Set the slot to the floating item
clicked_slot->item = global_floating_item_ptr->item;
clicked_panel->bmap = bmap_create(global_floating_item_ptr->item->inventory_icon);
// Set the floating item to the slot
global_floating_item_ptr->item = clicked_slot_item_pointer;
global_floating_item_ptr->floating_item_panel->bmap = bmap_create(clicked_slot_inventory_icon);
}
}
}
}
function inv_create_item(item_id, group_id, STRING* floating_icon, STRING* inventory_icon)
{
// Create item and assign images
Item* item = new(Item);
item->floating_icon = floating_icon;
item->inventory_icon = inventory_icon;
item->id = item_id;
item->group_id = group_id;
// Add item to global array for cleanup purposes
inv_items_array[inv_item_count] = item;
inv_item_count++;
return item;
}
function _inv_do_float(FloatingItem* floating_item)
{
proc_mode = PROC_LATE;
mouse_mode = 4;
mouse_pointer = 1;
while(inv_floating_flag == 1)
{
floating_item->floating_item_panel.pos_x = mouse_pos.x + 10;
floating_item->floating_item_panel.pos_y = mouse_pos.y + 10;
wait(1);
}
// optionally do a callback when floating ends
if (on_float_end_callback_function_ptr) on_float_end_callback_function_ptr();
}
function inv_float_item(Item* item)
{
global_floating_item_ptr->item = item;
global_floating_item_ptr->floating_item_panel = pan_create("",floating_item_layer);
global_floating_item_ptr->floating_item_panel->bmap = bmap_create(item->floating_icon);
global_floating_item_ptr->floating_item_panel->flags |= VISIBLE;
inv_floating_flag = 1; // set global floating flag
_inv_do_float(global_floating_item_ptr);
return global_floating_item_ptr;
}
function inv_create_bag(int bag_id, STRING* image_name)
{
Bag* bag;
bag = new(Bag);
bag->image_name = image_name;
bag->id = bag_id;
// Initialize slot_count to 0
bag->_slot_count = 0;
bag->is_open = 0;
// Add bag to global array for cleanup purposes
inv_bags_array[inv_bag_count] = bag;
inv_bag_count++;
return bag;
}
function inv_set_bag_drag_region(Bag* bag, int top_left_x, int top_left_y, int bottom_right_x, int bottom_right_y)
{
bag->drag_region_top_left_x = top_left_x;
bag->drag_region_top_left_y = top_left_y;
bag->drag_region_bottom_right_x = bottom_right_x;
bag->drag_region_bottom_right_y = bottom_right_y;
}
function inv_set_bag_close_region(Bag* bag, int top_left_x, int top_left_y, int bottom_right_x, int bottom_right_y)
{
bag->close_region_top_left_x = top_left_x;
bag->close_region_top_left_y = top_left_y;
bag->close_region_bottom_right_x = bottom_right_x;
bag->close_region_bottom_right_y = bottom_right_y;
}
function inv_open_bag(Bag* bag, int panel_x_position, int panel_y_position)
{
bag->bag_panel = pan_create("",bag_layer_node);
bag->bag_panel->bmap = bmap_create(bag->image_name);
bag->bag_panel->event = bagOnClick;
bag->is_open = 1;
int i;
// Add slots
for (i=0; i < bag->_slot_count; i++)
{
bag->slots[i]->slot_panel = pan_create("",slot_layer);
if (bag->slots[i]->item == NULL)
{
bag->slots[i]->slot_panel->bmap = bmap_create(bag->slots[i]->background_image);
}
else
{
bag->slots[i]->slot_panel->bmap = bmap_create(bag->slots[i]->item->inventory_icon);
}
bag->slots[i]->slot_panel->event = slotOnClick;
bag->slots[i]->slot_panel->pos_x = bag->slots[i]->rel_x_pos + panel_x_position;
bag->slots[i]->slot_panel->pos_y = bag->slots[i]->rel_y_pos + panel_y_position;
// Make the new slot panel visible
bag->slots[i]->slot_panel->flags |= VISIBLE;
// Add this panel and slot to the linked list
addSlotPanelAssoc(bag->slots[i],bag->slots[i]->slot_panel);
}
bag->bag_panel->pos_x = panel_x_position;
bag->bag_panel->pos_y = panel_y_position;
bag->bag_panel->flags |= VISIBLE;
if (on_open_bag_callback_function_ptr) on_open_bag_callback_function_ptr(bag->id);
inv_open_bag_count++;
// Add the pointer to this bag to the front of a linked list of bag pointers. This
// linked list is maintained to allow reordering of bags based on layer.
addBagLayer(bag);
reorderBagLayers();
}
function inv_close_bag(Bag* bag)
{
if (bag == NULL)
{
diag("\nWARNING: inv_close_bag called with argument NULL\n");
return 0;
}
bag->is_open = 0;
int i;
for (i=0; i < bag->_slot_count; i++)
{
// Remove each slot panel
pan_remove(bag->slots[i]->slot_panel);
// Remove the slot from the associative array
removeSlotPanelAssoc(bag->slots[i]);
}
// remove bag panel
pan_remove(bag->bag_panel);
if (on_close_bag_callback_function_ptr) on_close_bag_callback_function_ptr(bag->id);
inv_open_bag_count--;
// Remove the pointer to this bag from a linked list of bag pointers. This
// linked list is maintained to allow reordering of bags based on layer.
removeBagLayer(bag);
}
//***********************************************************************************************************************************************************************
function inv_add_slot_to_bag(Bag* bag, int slot_id, int group_id, STRING* default_image, int rel_x_pos, int rel_y_pos)
{
Slot* new_slot;
new_slot = new(Slot);
// Set the position for the new slot
new_slot->rel_x_pos = rel_x_pos;
new_slot->rel_y_pos = rel_y_pos;
new_slot->background_image = default_image;
new_slot->item = NULL;
new_slot->id = slot_id;
new_slot->group_id = group_id;
new_slot->bag_id = bag->id;
bag->slots[bag->_slot_count] = new_slot;
bag->_slot_count += 1;
}
function inv_insert_item_into_bag(Bag* bag, Item* item) // COULD THIS SOLVE THE PROBLEM?????????????????????????????????????????????????????????????????????
{
int i;
for(i=0;i < bag->_slot_count; i++)
{
if (bag->slots[i] != NULL)
{
if (bag->slots[i]->item == NULL)
{
if ((bag->slots[i]->group_id == item->group_id) || (bag->slots[i]->group_id == 0))
{
bag->slots[i]->item = item;
bag->slots[i]->slot_panel->bmap = bmap_create(item->inventory_icon);
return 1;
}
/*
else // ADDED BY RUBEN
if(bag->slots[i]->group_id == 1)
{
bag->slots[i]->item = item;
bag->slots[i]->slot_panel->bmap = bmap_create(item->inventory_icon);
return 1;
}
// END OF ADDED BY RUBEN
*/
}
}
}
return 0;
}
function inv_cleanup()
{
diag("\nStarting inventory cleanup\n");
int i;
int j;
// Clean up items
Item* item;
for(i=0;i<inv_item_count;i++)
{
diag("\n * cleaning up inventory item");
item = inv_items_array[i];
if (item != NULL)
{
free(item->floating_icon);
free(item->inventory_icon);
free(item);
diag(" - success");
}
}
// Clean up bags
Bag* bag;
for (i=0; i<inv_bag_count; i++)
{
diag("\n * cleaning up bag");
bag = inv_bags_array[i];
if (bag != NULL)
{
// Clean up slots in bag
for (j=0; j < bag->_slot_count; j++)
{
diag("\n - cleaning up slot");
free(bag->slots[j]->background_image);
free(bag->slots[j]);
}
free(bag->image_name);
free(bag);
}
}
free(global_floating_item_ptr);
diag("\nCompleted inventory cleanup\n");
}
// ------------- Helpful functions --------------
function inv_get_bag_panel_ptr(Bag* bag)
{
return bag->bag_panel;
}
function inv_is_bag_open(Bag* bag)
{
if (bag == NULL) return 0;
return bag->is_open;
}
function inv_get_open_bag_count()
{
return inv_open_bag_count;
}
function inv_is_floating()
{
return inv_floating_flag;
}
function inv_is_item_in_bag(Bag* bag, Item* item)
{
int i;
for(i=0;i < bag->_slot_count; i++)
{
if (bag->slots[i]->item == item)
{
return 1;
}
}
return 0;
}
// ------------- Create Callback Functions ---------
function set_on_click_callback(STRING* function_name) { on_click_callback_function_ptr = engine_getscript(function_name); }
function set_on_float_end_callback(STRING* function_name) { on_float_end_callback_function_ptr = engine_getscript(function_name); }
function set_on_close_bag_callback(STRING* function_name) { on_close_bag_callback_function_ptr = engine_getscript(function_name); }
function set_on_open_bag_callback(STRING* function_name) { on_open_bag_callback_function_ptr = engine_getscript(function_name); }
// --------------- linked-list functions --------------------------------
// ** list functions for managing bag z order
function addBagLayer(Bag* bag)
{
if(bag_layer_node == NULL)
{
bag_layer_node = new(BagLayer);
bag_layer_node->bag = bag;
bag_layer_node->next = NULL;
bag_layer_node->prev = NULL;
}
else
{
// Create a new BagLayer struct and put it at the beginning of the list
BagLayer* new_bag_layer_node = new(BagLayer);
new_bag_layer_node->bag = bag;
bag_layer_node->prev = new_bag_layer_node;
new_bag_layer_node->next = bag_layer_node;
new_bag_layer_node->prev = NULL;
bag_layer_node = new_bag_layer_node;
}
}
function removeBagLayer(Bag* bag)
{
int first_node = 1;
BagLayer* iterator = bag_layer_node;
while(iterator != NULL)
{
if (iterator->bag == bag)
{
// Tie together next and previous nodes
if (iterator->prev != NULL) iterator->prev->next = iterator->next;
if (iterator->next != NULL) iterator->next->prev = iterator->prev;
if (first_node) bag_layer_node = iterator->next;
// Free up removed slotPanelAssoc struct
delete(iterator);
return 1;
}
iterator = iterator->next;
first_node = 0;
}
}
function reorderBagLayers()
{
int new_bag_layer = 90;
int sanity_check = 0;
int i;
BagLayer* iterator = bag_layer_node;
Bag* bag;
while(iterator != NULL)
{
// Chage bag layer
bag = iterator->bag;
layer_sort(bag->bag_panel,new_bag_layer);
// Change bag's slot layers
for (i=0; i < bag->_slot_count; i++)
{
layer_sort(bag->slots[i]->slot_panel,new_bag_layer + 1);
}
new_bag_layer -= 3;
iterator = iterator->next;
sanity_check++;
if (sanity_check > 100)
{
diag("ERROR: reorderBagLayers has run amok!");
break;
}
}
}
// ** list functions for storing associations between panels and slots
function addSlotPanelAssoc(Slot* slot, PANEL* slot_panel)
{
if(slot_panel_assoc == NULL)
{
slot_panel_assoc = new(SlotPanelAssoc);
slot_panel_assoc->slot_panel = slot_panel;
slot_panel_assoc->slot = slot;
slot_panel_assoc->next = NULL;
slot_panel_assoc->prev = NULL;
}
else
{
// Create a new slot_panel_assoc struct and put it at the beginning of the list
SlotPanelAssoc* new_slot_panel_assoc = new(SlotPanelAssoc);
new_slot_panel_assoc->slot_panel = slot_panel;
new_slot_panel_assoc->slot = slot;
slot_panel_assoc->prev = new_slot_panel_assoc;
new_slot_panel_assoc->next = slot_panel_assoc;
new_slot_panel_assoc->prev = NULL;
slot_panel_assoc = new_slot_panel_assoc;
}
}
function removeSlotPanelAssoc(Slot* slot)
{
int first_node = 1;
SlotPanelAssoc* iterator = slot_panel_assoc;
while(iterator != NULL)
{
if (iterator->slot == slot)
{
// Tie together next and previous nodes
if (iterator->prev != NULL) iterator->prev->next = iterator->next;
if (iterator->next != NULL) iterator->next->prev = iterator->prev;
if (first_node) slot_panel_assoc = iterator->next;
// Free up removed slotPanelAssoc struct
delete(iterator);
return 1;
}
iterator = iterator->next;
first_node = 0;
}
}
function getSlotPtrForPanelPtr(PANEL* panel_ptr)
{
SlotPanelAssoc* iterator = slot_panel_assoc;
if (iterator == NULL)
{
diag("\nWARNING: getStructForPanelPtr returned NULL.");
}
while(iterator != NULL)
{
if (iterator.slot_panel == panel_ptr)
{
return(iterator.slot);
}
iterator = iterator->next;
}
return NULL;
}
/*
getBagPtrForPanelPtr(PANEL* panel_ptr)
Given a panel pointer, return a pointer to the bag having that panel.
In this case, we're lucky because the bags are all stored in the
global inv_bags_array. Why not store the slots in a similar array? --
Because they're constantly created and destroyed.
*/
function getBagPtrForPanelPtr(PANEL* panel_ptr)
{
int i;
Bag* bag;
for (i=0;i<inv_bag_count;i++)
{
bag = inv_bags_array[i];
if (bag->bag_panel == panel_ptr)
{
return bag;
}
}
return NULL;
}
I don't know if you can find it in there. I will look myself and see if I myself can find it.
Last edited by Ruben; 01/01/14 21:28.
|
|
|
Re: Access variable from other program?
[Re: Ruben]
#435025
01/01/14 21:42
01/01/14 21:42
|
Joined: Nov 2006
Posts: 497 Ohio
xbox
Senior Member
|
Senior Member
Joined: Nov 2006
Posts: 497
Ohio
|
I believe the part you're looking for is at the end of the function slotOnClick.
This seems to be were the item being dragged is being set to the slot in the inventory. So you need to check if the sword is placed in a specific slot.
I need to leave for work right now so I'll help more tomorrow.
EDIT: In your if statement where you are doing the strcmp instead of doing inv_slots[0].floating_icon try inv_slots[0]->floating_icon
Last edited by xbox; 01/02/14 05:17.
|
|
|
Re: Access variable from other program?
[Re: xbox]
#435028
01/02/14 06:28
01/02/14 06:28
|
Joined: Jun 2010
Posts: 590 California
Ruben
OP
User
|
OP
User
Joined: Jun 2010
Posts: 590
California
|
Well, I put this in the beginning of OrcStronghold.c :
Item* inv_slots[13];
inv_slots = new(Item);
ENTITY* active_sword;
I also changed the string comparison if statement in my main function (inside OrcStronghold.c) to:
if(str_cmp(inv_slots[0]->floating_icon, "steel_sword.pcx"))
{
active_sword = ent_create ("sword.mdl", my.x, attach_weapon);
}
else
{
ent_remove(active_sword);
}
...and I am still getting the same results. I am able to place a .pcx image of a sword in the active weapon slot of my inventory bag, but it is not arming my player with a sword attached to its hand as a result.
|
|
|
Re: Access variable from other program?
[Re: Ruben]
#435030
01/02/14 07:36
01/02/14 07:36
|
Joined: Jun 2007
Posts: 1,337 Hiporope and its pain
txesmi
Serious User
|
Serious User
Joined: Jun 2007
Posts: 1,337
Hiporope and its pain
|
Hi, I guess you have to use the module callbacks that are built for these cases. If you define and register the slot callback function it should be called when you click/drop on a slot.
// bags
#define MAIN_BAG_ID 1
#define TRADER01_BAG_ID 2
// slots
#define WEAPON_SLOT_ID 1
// groups
#define WEAPON_GROUP 1
// items
#define SWORD01_ID 101
#define SWORD02_ID 102
#define HAMMER01_ID 201
#define HAMMER02_ID 202
function fncMyCallback ( int action, int bag_id, int slot_id, int placed_item_id, int removed_item_id )
{
if ( bag_id == MAIN_BAG_ID )
{
if ( slot_id == WEAPON_SLOT_ID )
{
if ( removed_item_id != 0 )
{
// Remove the old weapon model
}
if ( ( placed_item >= SWORD01_ID ) && ( placed_item < HAMMER01_ID ) )
{
// Create the new sword model
}
}
}
}
function main ()
{
Bag *bag = inv_create_bag ( MAIN_BAG_ID, "leather_seam.pcx" );
Slot *slot = inv_add_slot_to_bag ( bag, WEAPON_SLOT_ID, WEAPON_GROUP, "leather_texture.pcx", 9, 60 ); // Active Weapon slot
Item *item_sword01 = inv_create_item ( SWORD01_ID, WEAPON_GROUP, "steel_sword.pcx", "steel_sword.pcx" );
set_on_click_callback ( "fncMyCallback" );
}
|
|
|
Moderated by mk_1, Perro, rayp, Realspawn, Rei_Ayanami, rvL_eXile, Spirit, Superku, Tobias, TSG_Torsten, VeT
|