I am trying to give the player one item out of a number of potential items. I don’t know in advance which item the player is going to get - it depends on how they define their stats during the game.
Right now I have the following:
A weapon is a kind of thing. The plural of weapon is weapons. A weapon is always wearable. Range is a kind of value. Ranges are melee, ranged. Flavor is a kind of value. The flavors are edge, blunt, chop, pierce. AmmoType is a kind of value. The AmmoTypes are none, bolt, arrow, dart, bullet. Some weapons are defined by the Table of WeaponTypes.
And a brief snippet of my WeaponType table:
Table of WeaponTypes
Weapon Descripion Range Required Strength Required Agility Min Damage Max Damage Flavor AmmoType
dagger "A wickedly sharp dagger." melee 1 5 1 6 edge none
club "A sturdy length of wood." melee 5 1 1 6 blunt none
staff "A gnarled staff." melee 5 5 2 10 blunt none
The problem with this is that it makes every single weapon in the table. It’s only around 11 items in that table, but I’ve got some other tables with armor and shields and whatnot, not to mention all kinds of random loot that’s going to be scattered about, and I’d rather keep the number of unused items down to a minimum.
Is there a way I can simply create one item and pick which row defines it?
One possibility would be to write your own code that changes an existing weapon by “manually” copying in the values from a row in the table. (including the printed name and the name by which it’s understood). You could then either create a pool of weapon objects and/or use Jesse McGrew’s Dynamic Objects extension to clone a dummy weapon (treasure/monster/…) item on the fly.
Range is a kind of value. The ranges are melee, ranged. Flavor is a kind of value. The flavors are edge, blunt, chop, pierce. Ammotype is a kind of value. The ammotypes are none, bolt, arrow, dart, bullet.
A weapon is a kind of thing. A weapon has an indexed text called the weapon name. The weapon name of a weapon is “weapon”. A weapon has a range called the weapon range. A weapon has a number called the required strength. A weapon has a number called the required agility. A weapon has a number called the minimum damage. A weapon has a number called the maximum damage. A weapon has a flavor called the weapon flavor. A weapon has an ammotype called the weapon ammotype. The printed name of a weapon is “[weapon name]”. Understand the weapon name property as describing a weapon.
To set the/-- (chosen weapon - a weapon):
choose a random row in the table of weapontypes;
now the weapon name of the chosen weapon is the weapon entry;
now the description of the chosen weapon is the description entry;
now the weapon range of the chosen weapon is the range entry;
now the required strength of the chosen weapon is the strength entry;
now the required agility of the chosen weapon is the agility entry;
now the minimum damage of the chosen weapon is the min entry;
now the maximum damage of the chosen weapon is the max entry;
now the weapon flavor of the chosen weapon is the flavor entry;
now the weapon ammotype of the chosen weapon is the ammotype entry;
blank out the whole row. [You only need this line if you only want one of each weapon.]
Table of WeaponTypes
Weapon Description Range Strength Agility Min Max Flavor Ammotype
“dagger” “A wickedly sharp dagger.” melee 1 5 1 6 edge none
“club” “A sturdy length of wood.” melee 5 1 1 6 blunt none
“staff” “A gnarled staff.” melee 5 5 2 10 blunt none
Check taking a not handled weapon: set the noun. [The not handled bit prevents it changing once set.]
The Testing Room is A Room. Three weapons are in the testing room. The weapon is always wearable.
Test me with “take weapon / i / take weapon / i / take weapon / i”.[/code]
This will assign a random weapon from the table to a blank weapon when it is taken for the first time.
Climbingstars’s solution is pretty nice, but a word of warning: it may make it hard to assign synonyms. For instance, if you call one of your weapons a “bustard sword,” then the player will have to enter “bustard sword,” just like that, to refer to it. Referring to “bustard” and to “sword” will get “You can’t see any such thing.”
There may be a workaround for this, but it’s beyond my power right now. (Hey, it’s broken egg compilation error icon day!)
The reason I want to cut back on the number of objects I’m using is I’ve already got something like 81 before I’ve even built more than five rooms. It just feels horribly wasteful. I haven’t even added random bits of treasure to be found or the gear that various other monsters will be wearing…
Am I going to spend more memory trying to work around this than I’d save by not creating a bunch of extra items in the first place?
Now I’m going to go figure out how to pull individual words out of indexed text and put them into an ‘understand x as “indexed” or “text”’ type thing.
If you’re compiling to z-code, then you lose more memory by using any indexed text at all than you would be likely to use by including all of your weapons. That’s because Inform only compiles the indexed text code into your game if you use indexed text, and the code it includes costs about 100KB. That’s a real concern if you’re compiling to z-code.
But 100KB is not even a drop in the bucket if you’re creating a Glulx game. Glulx’s memory limits are so high that there’s no need to trade programming hurdles for a few KB of memory. If you’re compiling to Glulx rather than z-code, then I wouldn’t even give a second thought to the memory issues created by using a few more objects. Just do it the easy way and you’ll be fine.