10 Replies - 1909 Views - Last Post: 23 September 2008 - 08:33 PM Rate Topic: -----

#1 girasquid  Icon User is offline

  • Barbarbar
  • member icon

Reputation: 108
  • View blog
  • Posts: 1,825
  • Joined: 03-October 06

Designing a Flexible items system (PBBG)

Post icon  Posted 22 September 2008 - 11:36 AM

Hello, all.

I am currently working on a PBBG, which is going to have items that perform various actions on the player. I am trying to design my items system in such a way that it will be easy to add more items in the future, while allowing them to have their own code to perform their actions.

Currently, I have planned on having a column within my items table, called items.on_use - inside this column, there would be a function name - and when the item was used, the value within that column would be used in the context of an eval() statement, to run whatever code was in place for that item.

I have been cautioned many, many times about the danger of using eval() statements - which is why I am asking for help. Is there a better way to do this, that will still allow me the same amount of flexibility? If not, is there a way to 'safely' eval my code(perhaps by forcing it into a specific namespace?)?

Thanks,
girasquid

Is This A Good Question/Topic? 0
  • +

Replies To: Designing a Flexible items system (PBBG)

#2 CTphpnwb  Icon User is offline

  • D.I.C Lover
  • member icon

Reputation: 3034
  • Posts: 10,598
  • Joined: 08-August 08

Re: Designing a Flexible items system (PBBG)

Posted 22 September 2008 - 12:48 PM

I think it would be better to use a token in the column, and then test that token with an 'if' or 'switch' statement in your code.
Was This Post Helpful? 0
  • +
  • -

#3 AdaHacker  Icon User is offline

  • Resident Curmudgeon

Reputation: 452
  • View blog
  • Posts: 811
  • Joined: 17-June 08

Re: Designing a Flexible items system (PBBG)

Posted 22 September 2008 - 01:08 PM

View Postgirasquid, on 22 Sep, 2008 - 01:36 PM, said:

inside this column, there would be a function name - and when the item was used, the value within that column would be used in the context of an eval() statement, to run whatever code was in place for that item.

I'm a little unclear on what you mean here. What, exactly, are you putting in this column? Is it just the name of a function, e.g. "useMyItem"? Or are you putting the actual body of the function in the database, e.g. "function useMagicItem(){...}"? If it's just the name, you don't need to use eval() at all - you can just call the function name from a variable, e.g. $func_name();

There are any number of ways to do this without putting code in the database. Ultimately, the best method depends on the specific functionality you're looking for. Maybe you could go into a little more detail on exactly what you're looking for.

Off the top of my head, without knowing anything about your application, my first instinct would be to go the "convention" route. Presumably your "items" table holds all the data for each item. So to add behavior to that, I'd simply create a class for each item, either tying the class name to the item name or storing the class name in the database. For each type of action that can be performed on an item, I'd simply create a method with the corresponding name that takes whatever parameters might be relevant. Since the code that invokes an action knows what item it's using and what the action is, all it needs to instantiate that class, feed it the item data, and call the appropriate method.

Actually, it would probably be easier to simply have an ItemFactory that fetches the items from the database and returns the objects of the appropriate class directly. That way your item-using code could simply call, e.g. a use() method on the item object in question.

Needless to say I'm making a lot of assumptions about your code here. My point is simply that, unless you need to put the bodies of your functions in the database (which you probably don't), there's no shortage of solutions that don't involve use of eval().
Was This Post Helpful? 0
  • +
  • -

#4 girasquid  Icon User is offline

  • Barbarbar
  • member icon

Reputation: 108
  • View blog
  • Posts: 1,825
  • Joined: 03-October 06

Re: Designing a Flexible items system (PBBG)

Posted 22 September 2008 - 01:39 PM

Sorry for not explaining a little bit better - it would be only the function name stored into the database. Then, when a user used 'the wand of teleport', TeleportUser() would get called and teleport the user somewhere. When a user went to use the 'orb of remembrance', UnTeleportUser() would get called, and send the user back.
Was This Post Helpful? 0
  • +
  • -

#5 grimpirate  Icon User is offline

  • Pirate King
  • member icon

Reputation: 149
  • View blog
  • Posts: 714
  • Joined: 03-August 06

Re: Designing a Flexible items system (PBBG)

Posted 22 September 2008 - 08:47 PM

Why not create items as classes/objects and have whatever it is they do as a method within it. Then when it's called since the object is already instantiated within the character's "item bag" just pass the character (or the character's pertinent stat i.e. health, xp, location, whatever) to the method as a parameter on which the method is to be performed.
Was This Post Helpful? 0
  • +
  • -

#6 girasquid  Icon User is offline

  • Barbarbar
  • member icon

Reputation: 108
  • View blog
  • Posts: 1,825
  • Joined: 03-October 06

Re: Designing a Flexible items system (PBBG)

Posted 23 September 2008 - 08:06 AM

Unfortunately, the code that I have inherited for this project is mostly procedural - and I don't really have the time to re-write it all to be OO. Can I safely intermingle the two?
Was This Post Helpful? 0
  • +
  • -

#7 CTphpnwb  Icon User is offline

  • D.I.C Lover
  • member icon

Reputation: 3034
  • Posts: 10,598
  • Joined: 08-August 08

Re: Designing a Flexible items system (PBBG)

Posted 23 September 2008 - 08:42 AM

How about a function?
function teleport($teluntel,$user)
	{
	if ($teluntel=="teleport")
		{
			// Code to teleport the user
		}
	if ($teluntel=="unteleport")
		{
			// Code to unteleport the user
		}	
	}

$x="teleport";
teleport($x,$someuser);
$y="unteleport";
teleport($y,$someotheruser);


Edit: fixed 'if' statement. Need ==, not =

This post has been edited by CTphpnwb: 23 September 2008 - 08:48 AM

Was This Post Helpful? 0
  • +
  • -

#8 girasquid  Icon User is offline

  • Barbarbar
  • member icon

Reputation: 108
  • View blog
  • Posts: 1,825
  • Joined: 03-October 06

Re: Designing a Flexible items system (PBBG)

Posted 23 September 2008 - 09:18 AM

CTphpnwb, that's what the original idea was - we would use a function to handle what happens when our items get used, and store the names of the functions to call within the database.
Was This Post Helpful? 0
  • +
  • -

#9 CTphpnwb  Icon User is offline

  • D.I.C Lover
  • member icon

Reputation: 3034
  • Posts: 10,598
  • Joined: 08-August 08

Re: Designing a Flexible items system (PBBG)

Posted 23 September 2008 - 09:55 AM

Right, but I'm suggesting that you don't store the name of the function in the database. Instead store a token ($teluntel), the value of which tells your function what to do for the user.
Was This Post Helpful? 0
  • +
  • -

#10 Ambercroft  Icon User is offline

  • D.I.C Head
  • member icon

Reputation: 5
  • View blog
  • Posts: 129
  • Joined: 05-January 07

Re: Designing a Flexible items system (PBBG)

Posted 23 September 2008 - 07:07 PM

If the prgm is not being added to dynamically, I would work with the tokens. If the methods were being added while the program is running, I would put the function names in the database. If you will be adding and remove code rapidly, then go with functions in the data base. I've seen this work in C very well. Not sure the exact way but seems feasible.

B)
Was This Post Helpful? 0
  • +
  • -

#11 girasquid  Icon User is offline

  • Barbarbar
  • member icon

Reputation: 108
  • View blog
  • Posts: 1,825
  • Joined: 03-October 06

Re: Designing a Flexible items system (PBBG)

Posted 23 September 2008 - 08:33 PM

I don't think things will be getting added quite that dynamically - chances are, the fastest you're looking at for adding an item and having it run it's own code is 5 minutes(2 seconds to insert the item into the database, and 5 minutes to write the code behind it).
Was This Post Helpful? 0
  • +
  • -

Page 1 of 1