Howdy, Stranger!

It looks like you're new here. If you want to get involved, click one of these buttons!

Inventory Code for Sugarcube 1.x (Twine 2)

I made this inventory code that lets you pick up and drop items from a room, as well as being able to look at them and use it (currently only one option). It's not perfect (and it will probably slow a large game down significantly, if you have a lot of objects) but it does work.
For this to work, you'll need to paste the code into a passage titled "storyInit", and give it the tag "widget". You'll also need to add two passages. One of them will be called "desc" and contain the following:

<<print $opta>>

<<return "Back">>

The other will be called "action" and contain just one line:

<<print $opta>>

Finally, you'll need to add these two lines to any passage that you want to be considered as a room (objects and inventory will be displayed:

<<inv>>
<<roominv>>

(You can switch those around if you want.)

You'll probably see a passage appear called "' + $passageString + '": it's not important and won't cause a problem. Delete it if you don't mind seeing the broken link error.
<<set $invCur to 0>> /% Don't change this unless you have items in your inventory to begin with. %/
<<set $invMax to 7>> /% Maximum amount of items you can hold at one time. %/

/% All of the following arrays MUST be the same length, even if some of the unnecessary pieces are just empty quotes. %/
<<set $items to ["watch"]>> /% To add an item, you need to add a comma and the name of the item in quotes here. %/
<<set $locs to ["First Room"]>> /% Then add which passage it is located in exactly. The string to add an item to the inventory is "inv", an abbreviation to keep the system simple. If you have items in your inventory to begin with, count them and then add that number to the $invCur value. Make sure you keep the number of items in your inventory to a maximum of the value you've set for $invMax. %/
<<set $descs to ["A plain digital watch."]>> /% This is the description. It can be anything. %/
<<set $actions to ["It's 9:04 AM."]>> /% This can be a quoted string or a set of commands in single quotes. Escape any other quotes with the '\' character. For example: '<<goto \"Basement\">>' or '<<set \$x to 3>><<print \$x>>' %/
<<set $adesc to ["Check time"]>> /% A description of the action. Actions can only be performed if you are holding the object. %/

<<widget "inv">>
You are carrying:

<<nobr>>
<<for $i to 0; $i < $items.length; $i++>>
<<set $ims to $items[$i]>>
<<set $baseString to "(D): Drop the " + $items[$i] + "">>
<<set $baseString2 to "(L): Look at the " + $items[$i] + "">>
<<set $baseString3 to "(A): " + $adesc[$i]>>
<<set $passageString to passage()>>
<<if $locs[$i] is "inv">>
    <<print $items[$i]>><br><<print '<<click [[' + $baseString + '|' + $passageString + ']]>><<set $locs[' + $i + '] to $passageString>><<set $invCur-->><</click>>'>><br>
    <<print '<<click $baseString2>><<description $descs[' + $i + ']>><</click>>'>><br>
    <<if $adesc[$i] is "none">><<else>>
    <<print '<<click $baseString3>><<action $actions[' + $i + ']>><</click>>'>><br><</if>>
<</if>>
<</for>>
<<if $invCur is $invMax>><<print "You can't carry any more items.">><<else>>
<<set $m to $invMax - $invCur>><<print "You can carry $m more items.">><</if>>
<</nobr>>
<</widget>>

<<widget "roominv">>
You can see:

<<nobr>>
<<for $i to 0; $i < $items.length; $i++>>
<<set $ims to $items[$i]>>
<<set $baseString to "(T): Take the " + $items[$i]>>
<<set $baseString2 to "(L): Look at the " + $items[$i]>>
<<set $passageString to passage()>>
<<if $locs[$i] is passage()>>
    <<print $items[$i]>>
    <br>
    <<print '<<click [[' + $baseString + '|' + $passageString + ']]>><<if $invCur < $invMax>><<set $locs[' + $i + '] to "inv">><<set $invCur++>><<else>><<goto $passageString>><</if>><</click>>'>>
    <br>
    <<print '<<click $baseString2>><<description $descs[' + $i + ']>><</click>>'>><br>
<</if>>
<</for>>
<</nobr>>
<</widget>>

<<widget "description">>
<<set $opta to $args[0]>>
<<goto "desc">>
<</widget>>

<<widget "action">>
<<set $opta to $args[0]>>
<<goto "action">>
<</widget>>

- This code is not finished and I want to improve it eventually with items that can't be picked up, for example, or multiple actions for a single item, or actions that can work when the item is not being held. I would make containers which can hold other objects, but that would probably slow the code down significantly and I don't want to have to worry about that.

- If you want to use this, just give me credit, or at least don't imply you wrote this code.

- I don't think this could be replicated in Harlowe without adding macros through JavaScript (there's no for loop or widget macro in Harlowe, as far as I know. But if you could make two macros for that, you could probably recreate this.)

- It should work in Sugarcube 2.x as far as I know.

- To set this up, you just need to follow the instructions in the first comment.

- To test the example item I added, follow the setup instructions and add a passage called "First Room" with the <<inv>> and <<roominv>> widgets at the end of it. (Don't forget to add the "action" and "desc" passages too.)

- The (T), (D), (L), and (A) tags at the beginning of each option is my own format for games of this type: each option is preceded by a one letter tag describing what kind of option it is. An exit to another room would be (X), talking to a character would be (C). You can remove this if you want.

Comments

  • I added something to prevent certain items from being picked up.

    Just before the <<widget "inv>> line, add this:
    <<set $cbh to []>> 
    
    $cbh stands for "Can't Be Held."
    (Add the names of any objects that can't be picked up here. This array doesn't need to be the same size as the others.)

    And then change this:
    <<widget "roominv">>
    You can see:
    
    <<nobr>>
    <<for $i to 0; $i < $items.length; $i++>>
    <<set $ims to $items[$i]>>
    <<set $baseString to "(T): Take the " + $items[$i]>>
    <<set $baseString2 to "(L): Look at the " + $items[$i]>>
    <<set $passageString to passage()>>
    <<if $locs[$i] is passage()>>
        <<print $items[$i]>>
        <br>
        <<print '<<click [[' + $baseString + '|' + $passageString + ']]>><<if $invCur < $invMax>><<set $locs[' + $i + '] to "inv">><<set $invCur++>><<else>><<goto $passageString>><</if>><</click>>'>>
        <br>
        <<print '<<click $baseString2>><<description $descs[' + $i + ']>><</click>>'>><br>
    <</if>>
    <</for>>
    <</nobr>>
    <</widget>>
    

    to this:
    <<widget "roominv">>
    You can see:
    
    <<nobr>>
    <<for $i to 0; $i < $items.length; $i++>>
    <<set $ims to $items[$i]>>
    <<set $baseString to "(T): Take the " + $items[$i]>>
    <<set $baseString2 to "(L): Look at the " + $items[$i]>>
    <<set $passageString to passage()>>
    <<if $locs[$i] is passage()>>
        <<print $items[$i]>>
        <br>
        <<if not $cbh.contains($items[$i])>>
        <<print '<<click [[' + $baseString + '|' + $passageString + ']]>><<if $invCur < $invMax>><<set $locs[' + $i + '] to "inv">><<set $invCur++>><<else>><<goto $passageString>><</if>><</click>>'>>
        <</if>>
        <br>
        <<print '<<click $baseString2>><<description $descs[' + $i + ']>><</click>>'>><br>
    <</if>>
    <</for>>
    <</nobr>>
    <</widget>>
    

    That will prevent those items from being picked up: you can still look at them, though.
  • Thank the Lord. You really saved my hide with this. I can't thank you enough.
  • but now it shows that it doesn't understand what you are telling it. what do you put in the JavaScript box?
Sign In or Register to comment.