Getting my Head Around Wearables...and vice versa.

Apologies, I have a series of questions but will present them one at time...

Quest 5.7.2 introduced an extensive built-in 'wearables' feature. At the time of its release I looked briefly at it but couldn't immediately understand how to use it. It seemed more complex than I needed so I just defined my own "wear/put on" and "remove/take off" commands to override what was built in. Some action was needed as the 'wear' verb I had been using seemed to have disappeared from my code (though not 'remove'?).

My first question is: does the 'wearables' feature of Quest 5.7.2 affect all games using the 'wear' verb' or did I have special circumstances?


Yes, it will affect all games. Quest checks verbs to make sure they do not clash with anything.

I would suggest having another look at the built-in system. All you have to do is set "Wearable" on the Features tab, and select "Can be worn" on the Wearables tab. The rest is optional.

If you are sure you want to make your own system, you can disable the built in commands. At the bottom left, go Filter - Show library elements, and select the WEAR command. Click copy to put a copy in your game. Then type some long, random text for the command pattern. Do the same for REMOVE. You should now be able to add your own verbs.


Yes, it will affect all games.

Okay, just to clarify. I'm assuming the change doesn't affect published games (.quest) but does affect anyone working on a game file(.aslx)?
...and means that all 'wear' verbs, plus any associated scripting are removed from those games?

I would suggest having another look at the built-in system.

Yes, that is exactly what I'm doing, which has generated these questions...and almost certainly more to follow!


Already published games will not be affected, no.


Already published games will not be affected, no.

As games under development (or being updated) are affected, would it be possible to warn the developer?
Does the change currently generate the rather worrying message "Your game has been modified outside Quest", offering a 'reload' button?

I've created a small game to try out the wearable facility:

  1. I like the automatic indication of (worn) against an item
  2. I like the function that lists what I'm wearing for possible use in 'x me', for example.
  3. I like the fact 'wear all' has been implemented to put several items on at one time, and ditto for 'remove all'
  4. Not sure why I need to indicate twice that an item is wearable (pick feature and then select in a pull-down list?)
  5. In my own game, I allowed an item to be picked up and put on in one action and similarly dropped while being worn. Can I achieve that effect with the built-in wearable facility?

Shouldn’t this post be titled “Getting Wearables Around My Head”?

🙄


K.V.

Not sure why I need to indicate twice that an item is wearable (pick feature and then select in a pull-down list)

This is just the way the code works. You enable the feature that allows you to set the wearable type. When enabling similar features (such as a container), the drop down has numerous types to choose from.


In my own game, I allowed an item to be picked up and put on in one action and similarly dropped while being worn. Can I achieve that effect with the built-in wearable facility?

In your take script, add WearGarment(this).


Shouldn’t this post be titled “Getting Wearables Around My Head”?

Have you ever heard this saying? --> "Nobody likes a smart aleck!"

It's not true. I enjoy smart alecks!


K.V.

Pop Quiz

Why does my old 5.6.3 game with a wear verb work in the editor in ANY version of Quest? (As an .aslx file, not as a published game.)

<!--Saved by Quest 5.6.6582.36962-->
<asl version="550">
  <include ref="English.aslx" />
  <include ref="Core.aslx" />
  <game name="Wear 5.6.3">
    <gameid>e68e0515-68e0-46f0-89c0-8703f7e03854</gameid>
    <version>1.0</version>
    <firstpublished>2017</firstpublished>
  </game>
  <object name="room">
    <inherit name="editor_room" />
    <object name="player">
      <inherit name="editor_object" />
      <inherit name="editor_player" />
    </object>
    <object name="hat">
      <inherit name="editor_object" />
      <take />
      <look>{if hat.worn:You can't see it very well, seeming how its currently resting on top of your head.}{if not hat.worn:It's a Derby.}</look>
      <don type="script">
        if (TypeOf(this.alias) = "null") {
          this.alias = this.name
        }
        if (not GetBoolean(this,"worn")) {
          msg ("You put "+Replace(GetDisplayName(this),"a ","the ")+" on.")
          this.alias = this.alias + " (worn)"
          this.worn = true
          if (not this.parent = game.pov) {
            AddToInventory (this)
          }
        }
        else {
          msg ("You are already wearing it.")
        }
      </don>
      <remove type="script">
        if (TypeOf(this.alias) = "null") {
          this.alias = this.name
        }
        if (GetBoolean(this,"worn")) {
          this.worn = false
          this.alias = Replace(this.alias," (worn)","")
          msg ("You remove "+Replace(GetDisplayName(this),"a ","the ")+".")
          JS.eval ("$('span').last().prev().prev().html($('span').last().prev().prev().html().replace(/ \\(worn\\)/,''));")
        }
        else {
          msg ("You aren't wearing "+GetDisplayName(this)+".")
        }
      </remove>
      <ondrop type="script">
        if (GetBoolean(this,"worn")) {
          this.worn = false
          this.alias = Replace(this.alias," (worn)","")
          JS.eval ("$('span').last().prev().prev().html($('span').last().prev().prev().html().replace(/ \\(worn\\)/,''));")
        }
      </ondrop>
    </object>
  </object>
  <verb>
    <property>don</property>
    <pattern>wear;don;put on;sport;put #object# on</pattern>
    <defaultexpression>"You can't wear " + object.article + "."</defaultexpression>
  </verb>
  <verb>
    <property>remove</property>
    <pattern>remove;take off;take #object# off</pattern>
    <defaultexpression>"You can't remove " + object.article + "."</defaultexpression>
  </verb>
</asl>

NOTE: I already know why it works. This is a only a pop quiz.


This is just the way the code works. You enable the feature that allows you to set the wearable type.

Could the default be 'wearable' rather than 'not wearable'? I realise it is mirroring the container code but that also looks odd!

In your take script, add WearGarment(this).

Not quite, I meant the player could say 'wear garment' and it be taken up and worn. You are suggesting 'take' means an automatic wear which may not be the desired outcome. Also, what about dropping things that are worn?


K.V.

Could the default be 'wearable' rather than 'not wearable'?

That would mean making wearable a default type on every default object. If that was the case, we'd have to go in and remove wearable from everything that couldn't be worn.

This is what's happening:

  1. The object is not wearable by default
  2. The 'Wearable: object can be put on and taken off' feature is enabled.

At this point, it would seem that the object is now wearable, but what this is REALLY doing is telling the Quest editor to display the Wearable options tab. That's all that does.

  1. The drop-down in the new 'Wearable' tab is set to 'Can be worn', and the 'wearable' type is added to the object, hence making it wearable.

  2. To change the object so it is no longer wearable, that drop-down under the 'Wearable' tab must be set to 'Cannot be worn'. This is what will remove the type from the object.


You could bypass that 'Features' tab altogether and simply add the inherited type "wearable" to your object. Everything would work.

When you check that first box, that ONLY tells the editor to display the 'Wearable' options tab. You can check that box, switch to the wearable tab, set the drop-down to 'Can be worn', flip back to the features tab, uncheck "Wearable: object can be put on and taken off", and the object would still be wearable. The only change would be that the editor no longer displayed the 'Wearable' tab.


I meant the player could say 'wear garment' and it be taken up and worn.

Oh! (Duh!) Sorry about that.

First, show all of your library elements:

screenshot


Then, remove 'inventory' from the scope:

image


Then put this in place of the script:

if (multiple and ListCount(object) = 0) {
  msg ("You've nothing to wear.")
}
else {
  foreach (obj, object) {
    if (not obj.parent = game.pov) {
      if (ListCount(object) >1) {
        OutputTextNoBr (GetDisplayAlias(obj)+": ")
      }
      do (obj, "take")
    }
    if (obj.parent = game.pov) {
      if (ListCount(object) >1) {
        OutputTextNoBr (GetDisplayAlias(obj)+": ")
      }
      f = _DoWear(obj)
      UpdateArmour
    }
  }
}

Finally, to make WEAR ALL work, we need to go to the WEAR commands attributes tab:

image


Paste this in place of what's there:

game.pov.currentcommandpendingobjectscope = ListExclude(ScopeReachable(),game.pov)

After you're done, it should look like this in full code view:

  <command name="wear">
    <pattern>put #object# on; wear #object#; put on #object#; don #object#; wear #object#</pattern>
    <scope type="string"></scope>
    <multipleobjects type="script">
      game.pov.currentcommandpendingobjectscope = ListExclude(ScopeReachable(),game.pov)
    </multipleobjects>
    <script><![CDATA[
      if (multiple and ListCount(object) = 0) {
        msg ("You've nothing to wear.")
      }
      else {
        foreach (obj, object) {
          if (not obj.parent = game.pov) {
            if (ListCount(object) >1) {
              OutputTextNoBr (GetDisplayAlias(obj)+": ")
            }
            do (obj, "take")
          }
          if (obj.parent = game.pov) {
            if (ListCount(object) >1) {
              OutputTextNoBr (GetDisplayAlias(obj)+": ")
            }
            f = _DoWear(obj)
            UpdateArmour
          }
        }
      }
    ]]></script>
  </command>

And it will try to take an object first. If the object can't be taken, it will stop the wear script.

image


With another wearable object which can't be picked up in the same location:

image


Shouldn’t this post be titled “Getting Wearables Around My Head”?

Thanks XanMag, your contribution has been acknowledged in the revised title of the post :)

KV, thanks for all your work above. It's helping my understanding though tending to make me wonder if, in general, I should mod the wearable facility or block it and start from scratch. It would probably depend on the requirements in any particular game.

It does seem an issue that the 'wear' verb is automatically removed from existing games, effectively breaking them. It also seems inconsistent to leave the 'remove' operation behind, especially as it may then be broken as well.

No one has mentioned the dreaded "... [your game] has been modified outside Quest message" so far. Would it be possible to add an 'explain' button alongside 'reload' which could then warn and give advice? ...perhaps this point should be discussed in a separate thread?


K.V.

block it and start from scratch

Good luck! I tried that before I came up with my workaround.

You can just alter your verb's property to make it work in the newer versions of Quest. This game file proves that. Just change your main wear verb's property to don. Then change the wear verb on your object to don in full code view.


It does seem an issue that the 'wear' verb is automatically removed from existing games, effectively breaking them. It also seems inconsistent to leave the 'remove' operation behind, especially as it may then be broken as well.

I don't think it removes it, but it definitely messes stuff up.

My advice is to finish any works in progress before updating your creation software, whether it's Quest or something else.


No one has mentioned the dreaded "... [your game] has been modified outside Quest message" so far. Would it be possible to add an 'explain' button alongside 'reload' which could then warn and give advice? ...perhaps this point should be discussed in a separate thread?

This only happens when you modify a loaded game (or library) outside of the instance of Quest in which it is loaded.

Meaning you have more than one Quest window open, or you have the file open in an editor while it is loaded in Quest.


Good luck! I tried that before I came up with my workaround.

I created two new commands "wear/put on #object#" and "remove/take off #object#" and was able to work from there. Coincidentally, I had previously implemented wear and remove using a 'worn' attribute in the objects concerned.

This only happens when you modify a loaded game (or library) outside of the instance of Quest in which it is loaded.

That's good to know. I assume it means the removal of 'wear' is completely silent? ...which doesn't feel very friendly!


K.V.

I don't think we're saying what each of us thinks the other is saying.

  • I thought you were trying to keep your old verbs. You can change the property of your wear verb to don, then change the same thing in code view for the verb on your wearable objects. You just have to make sure the verb's pattern matches the pattern of wear in CoreWearables. (Also make sure the patterns for remove match.)

  • When you said "block it and start from scratch", I thought you meant removing the CoreWearables library so you could keep your old verbs without having to alter or rewrite any code.

  • If you have a wear verb (or command; same thing) in your game, it should override the wear command in CoreWearables.aslx, just like the new commands you just created do. You just have to have the same patterns as the commands in CoreWearables. If your wear's pattern is just wear #object#;put on #object#, when you enter PUT HAT ON, the wear from CoreWearables will take over because PUT #OBJECT# ON matches its pattern and not the pattern of your custom wear.

  • The "Your game has been modified outside of Quest" message should only display when you modify a loaded game (or library) outside of the instance of Quest in which it is loaded. Meaning you have more than one Quest window open, or you have the file open in an editor while it is loaded in Quest.

  • Quest shouldn't be removing your wear verb, silently or otherwise. Your patterns probably just don't match.


Thanks for sticking with this KV! It's hard to explain issues as I don't want to bore anyone by writing too much and what I say is based on my limited experience as a developer.

Quest shouldn't be removing your wear verb, silently or otherwise. Your patterns probably just don't match.

We now seem to be down to the central issue. This all started after the last Quest release when I played my games through to see if anything had changed. What I found was that I could no longer see the 'wear' verb I had attached to four objects and wasn't allowed to put it back in. This led me to look at the wearables feature, decided it was too complicated for me and implemented a workaround with 'wear' and 'remove' commands.

While you are thinking about that, I plan to go back and use the wearables feature as far as I can and report the result. This will be on Monday as I'm away all weekend.


K.V.

This all started after the last Quest release when I played my games through to see if anything had changed. What I found was that I could no longer see the 'wear' verb I had attached to four objects and wasn't allowed to put it back in.

I'd very much like access to this file, before anything was changed to work with the new version of Quest. I believe the evidence needed to solve this mystery can be found within that code.


I'd very much like access to this file, before anything was changed to work with the new version of Quest.

Version 2.3 from September 2017 has been emailed to you.


I'm afraid this is still an open issue. I have just helped Bitter Karella fix up Carnival of Regrets (see game comments). After a minor change unrelated to wearables and uploading a new version on 16 April, the game was broken by the 'wear' verb being suppressed without warning. In making the fix, I initially tried to just set the items affected to 'wearable' but that didn't bring back the previous 'wear' script. It did seem to require reasonable technical knowledge to find the old code for wear and then adjust the game to make it work again. Is there something simple that I missed? Are there guidelines for the adjustment? Can game developers be warned about this issue at the time of making changes and guided through the adjustments needed?


K.V.

wear is a command in the most recent versions of Quest, so it does not check for a wear attribute on an object.

In theory (as all games are coded differently), you could have simply changed the pattern for the wear command to something like "fjsadofhiuonfbndfbnfdkjghk". This way, the wear verb would take precedence and actually check for attributes on objects.


The same thing goes for remove. Changing the remove command's pattern to "gkghlkghlsakgjlkghslghl" would be necessary, as well.


This is all theory (which I should have thought of the first time I saw this thread). I'm about to go test it out.


'enter' now also seems to be reserved. I'm not sure when that happened or why it was necessary but my use of enter in a game was unaffected. I cannot have new uses of 'enter' but nothing is broken. It would have been better if 'wear' had been implemented in a similar way.

I am, of course, talking at a user level!


K.V.

Step 1

Change the patterns for wear and remove by adding these two lines to the start script:

wear.pattern = "upupdowndownleftrightleftrightba"
remove.pattern = "upupdowndownleftrightleftrightab"

Step 2

Add these verbs in full code view:

  <verb name="wear_verb">
    <pattern>wear</pattern>
    <defaultexpression>"You can't wear " + object.article + "."</defaultexpression>
    <property>wear</property>
  </verb>
  <verb name="remove_verb">
    <pattern>remove</pattern>
    <defaultexpression>"You can't remove " + object.article + "."</defaultexpression>
    <property>remove</property>
  </verb>

Step 3

Test to make sure everything works!


K.V.

'enter' now also seems to be reserved. I'm not sure when that happened or why it was necessary but my use of enter in a game was unaffected. I cannot have new uses of 'enter' but nothing is broken. It would have been better if 'wear' had been implemented in a similar way.

I have run into this as well. enter is a room attribute. Quest is setup to throw an error if you try to create a verb named "enter". Most people make a command to handle EVERY situation, but I prefer this method:

Step 1 (of 1)

Go into full code view (or edit your .aslx file in a text editor), and change the first line of your enter verb from <verb> to <verb name="enter_verb">. (NOTE: You can add an "enter" verb to any game by doing this.)

If the pattern is simply "enter", it should look like this:

  <verb name="enter_verb">
    <property>enter</property>
    <pattern>enter</pattern>
    <defaultexpression>"You can't enter " + object.article + "."</defaultexpression>
  </verb>

If you don't like to fool around in code view, you can add (or edit) a verb in the GUI:


I've just tried this with the version of Carnival of Regrets that was failing. Unfortunately using 'wear' produces:

Error running script: Error compiling expression 'TypeOf(object, this.property)': FunctionCallElement: Could find not function 'TypeOf(Element, Object)'


K.V.

I've just tried this

Tried what code, specifically?

It doesn't sound like you changed the pattern for the wear command.


If you email me the file, I'll forego my star for the day if I can't get it to work using this method.


K.V.

I just decompiled Carnival of Regrets.

new_wear and new_remove seem to work perfectly, (EDIT) but I'd still like to play with the old code to see if my new fix works.


(this probably doesn't make any difference... as I think if I understand, you're just doing this to prevent it from being used)

not sure if Davy saw/recognized this typo mistake and fixed it or not:

'...tba' vs '...tab'

wear.pattern = "upupdowndownleftrightleftrightba"

which should be (I presume, lol):

wear.pattern = "upupdowndownleftrightleftrightab"

K.V.

The Konami Code:

wear.pattern = "upupdowndownleftrightleftrightba"

The Konami Code for Teenage Mutant Ninja Turtles III:

remove.pattern = "upupdowndownleftrightleftrightab"

I just picked something no one would ever enter, like you say, HK.


Tried what code, specifically?
It doesn't sound like you changed the pattern for the wear command.

I followed your three steps and found the error when testing. I'll try it again tomorrow, making sure I work on the original game and put everything in precisely.


K.V.

If it ain't broke, I wouldn't mess with it (unless you just really, really wanted to).

...and it seemed to be working for me before making any changes.

I simply enjoy finding my errors. That's why I remained curious and wished for the original code.

(I'm not trying to dissuade you from trying it out. I just don't want to cause you to waste your time with my code when yours already works.)


Also, if you're still working on that Carnival of Regrets game, this shows you how to hide the map during the prologue (since nothing is displayed in the grid until afterwards, anyway):

http://docs.textadventures.co.uk/quest/showing_a_map.html#turning-the-grid-on-and-off


Sorry KV, I've confused you! What you are looking at is the version of Carnival of Regrets that I've already 'fixed'. This is the game that encouraged me to try and find a way to make all Quest facilities optional. Try typing COMPLAIN to see what I mean. The next version will include the full dynamic flexibility we have discussed in separate threads over the last week or so.

My goal is not to fix a specific game but to find a simple general strategy that someone might follow if they encounter the problem with 'wear' disappearing. I guess one possibility is to download and use an earlier version of Quest...perhaps the one used to create the game? This, however, doesn't feel like something to be encouraged!

So, the general question in this thread is: "My previously working game is now broken because of the wearables feature in the latest version of Quest, what can I do to fix it?" Is there a simple reversal to bring back the old 'wear' code? Better still, is there a simple way to switch to use the new wearables feature without losing the 'wear' code that was there before? ...and can this be described in a suitable form for developers with little technical knowledge?


'enter' now also seems to be reserved.

Using "enter" as a verb has always caused problems, because rooms have "enter" scripts, and rooms and items are both just objects. In Quest 5.7.x, it was added to the list of reserved verbs to prevent that.

My goal is not to fix a specific game but to find a simple general strategy that someone might follow if they encounter the problem with 'wear' disappearing.

Using commands on the desktop

At the bottom left, do Filter - Show library elements. Find the "wear" and "remove" commands, and copy them to your game. Change them to do whatever you want.

Using verbs on the desktop

At the bottom left, do Filter - Show library elements. Find the "wear" and "remove" commands, and copy them to your game. Change the pattern to some long, random text. Then go to the garment, and add a wear verb (when I did this, I got an error, but the verb object was created, and giving it a name, "wearverb", fixed the problem).

Using commands on the web version

Create new commands. For wear, use this pattern:

put #object# on; wear #object#; put on #object#; don #object#; wear #object#

For remove, use this:

take #object# off; remove #object#; take off #object#; doff #object#


K.V.

Sorry KV, I've confused you! What you are looking at is the version of Carnival of Regrets that I've already 'fixed'.

No, I'm with you. I played the most recent version of that game and mentioned that your changes seem to have fixed wear and remove. Then, I said I'd like to see that file before you made any changes, just to make sure my fix works.


My goal is not to fix a specific game but to find a simple general strategy that someone might follow if they encounter the problem with 'wear' disappearing.

Yes, I understand that.

I theorized a simple, general strategy. Then, I tested it on six older games, one game at a time (since testing it on all of the games at once wasn't really plausible, and merely theorizing only gets you so far). It worked every time.

You add 2 lines to the start script, then you add two verbs.

If someone can come up with a method easier than this, I am quite eager to see the code.

...and if this ever fails (before modifying anything else), I'd like to see that too, so I can learn from my mistakes.


THE FOLLOWING STEPS WORK ONLINE OR IN THE DESKTOP EDITOR


PART ONE - A FIX FOR OLD GAMES WITH "WEAR" AND "REMOVE" VERBS

Step 1

Change the patterns for wear and remove by adding these two lines to the start script:

IN CODE VIEW:

wear.pattern = "upupdowndownleftrightleftrightba"
remove.pattern = "upupdowndownleftrightleftrightab"

IN GUI VIEW:

image


Step 2

Add these verbs:

IN FULL CODE VIEW:

  <verb name="wear_verb">
    <pattern>wear</pattern>
    <defaultexpression>"You can't wear " + object.article + "."</defaultexpression>
    <property>wear</property>
  </verb>

IN GUI:

image


IN FULL CODE VIEW:

  <verb name="remove_verb">
    <pattern>remove</pattern>
    <defaultexpression>"You can't remove " + object.article + "."</defaultexpression>
    <property>remove</property>
  </verb>

IN GUI:

image


Step 3

Test to make sure everything works!


To reiterate, I'm not trying to say that my way is the only way, or that my way is the best way, or that my way never fails.

I'd just like to see it fail if it doesn't always work, because I've tested it out six times in the past 12 hours, with 100% success rate.

If this DOES work at least 95% of the time (which I believe it will, unless someone needs to add on to the verbs' patterns), it can easily be made into a library for desktop users.

OldWearFixLib.aslx

<?xml version="1.0"?>
<library>
  <command name="wear">
    <pattern>upupdowndownleftrightleftrightba</pattern>
    <script>
      msg("Nothing happens.")
    </script>
  </command>

  <command name="remove">
    <pattern>upupdowndownleftrightleftrightab</pattern>
    <script>
      msg("Nothing happens.")
    </script>
  </command>

  <!-- 
      NOTE:  You may need to add more patterns to these verbs, depending on your game.

      I did not add anything extra to these patterns because there's no telling what patterns may exist, 
      and the wrong pattern(s) could create bugs (i.e., if you have separate WEAR and DON verbs set up).
     -->

  <verb name="wear_verb">
    <pattern>wear</pattern>
    <defaultexpression>"You can't wear " + object.article + "."</defaultexpression>
    <property>wear</property>
  </verb>

  <verb name="remove_verb">
    <pattern>remove</pattern>
    <defaultexpression>"You can't remove " + object.article + "."</defaultexpression>
    <property>remove</property>
  </verb>

</library>

PART TWO - AN ENTER VERB

Step 1 (of 1)

Go into full code view (or edit your .aslx file in a text editor), and change the first line of your enter verb from <verb> to <verb name="enter_verb">. (NOTE: You can add an "enter" verb to any game by doing this.)

If the pattern is simply "enter", it should look like this:

  <verb name="enter_verb">
    <property>enter</property>
    <pattern>enter</pattern>
    <defaultexpression>"You can't enter " + object.article + "."</defaultexpression>
  </verb>

If you don't like to fool around in code view, you can add (or edit) a verb in the GUI:


I have actually tested the code I have posted, and I have done so numerous times -- on my games as well as games made by other authors (including your game, DavyB).

If I see someone post, "I have tried these methods, and they do not work because ___ ," I'll continue to try to help. Otherwise, I'll assume I'm just bothering everyone, no one has even tested it out with my code, and that no one is interested in my input (for whatever reason; even if it is basically the same thing that Pixie suggested -- only a little more simplified, since I change the new commands' patterns in the start script, which can also be done online or in the desktop).

I am not offended, nor do I wish to offend, by the way. I'm just thinking that the best way to help when my input isn't helping is to nix my input. (This is for the greater good, you understand.)

So, I apologize if I have upset anyone, or confused anyone, or in any way exacerbated things.

...and I'm also sorry about this wall of text, but only if it isn't helping anyone.

Cheers!


K.V.

PS

If the pattern of the existing "wear" verb is something other than wear, that pattern will need to be applied to the new "wear_verb".

The same goes for the existing "remove" verb.

(This is the 5% of the time my fix needs a little tweaking.)


Have a nice day!


Thanks KV and Pixie. I'll try this out and get back you. One query, however, for Pixie:

At the bottom left, do Filter - Show library elements. Find the "wear" and "remove" commands, and copy them to your game.

Do you mean "wear" and "remove" under "Templates"?


@ KV:

haha... never recognized that to be inputs for a game code, haha... (for some reason, I was taking the 't' off of 'right' and thinking it went with the 'ab', as 'tab'... lol --- maybe becoming dyzlexic as I'm getting older... hmm... argh... lol)

(some gamer, is "gamer HK"... sighs, lol)

HK liked TMNT 1+2 (NES), hard/fun games...

did konami do the old contra games too? (I'm sure konami has done tons of the old games... one of the big brands/companies way back then/when... lol)

https://en.wikipedia.org/wiki/Konami (ya... lots of games... lol)

wow... didn't know konami did MGS (metal gear solid, PS1)... that was a good game...


K.V.

I was taking the 't' off of 'right' and thinking it went with the 'ab', as 'tab'... lol

Hehehe.

I deduced that! In your defense, it does say "tab"...


did konami do the old contra games too?

Yes, sir!

If you input the pattern of wear while the Contra menu is on the screen, you get 30 lives!


Do you mean "wear" and "remove" under "Templates"?

No, the commands. The commands are at the top of the list.


Okay, taking into account everything that has been said so far, and what I've learned from experiments, here is DavyB's proposed 10-point plan for how to get from a broken game that had been using the 'wear' verb to one working with the new wearables feature, which is, I guess, the better way to go:
1. Your 'wear' and 'remove' code appears to have disappeared. Don't worry, it is still there but less obvious.
2. To repair your game to use the new 'wearables' feature, first delete any wear-related verbs (‘'wear', 'remove', put on, take off…) from the verb list at the top of the panel on the left hand side.
3. Next, click on 'game' at the top of that panel, select 'features' and tick the box for "Show advanced options for wearables"
4. Then go to the (first) item that was previously using 'wear' (or any other verb that has disappeared). Click on 'attributes' for that item. You will see an entry for 'wear' (or other missing verbs). Click on it to bring up the old script for 'wear'. Take a copy. (It can also be deleted but wait until testing is complete!)
5. For that item, tick the 'wearables' box under the 'features' tab; and then under the 'wearable' tab that appears, select "can be worn".
6. Now complete the wearable details for the item, pasting in the script you have just copied.
7. The 'wearables' feature uses a Boolean flag 'worn', which is set to 'true' after the 'wear' (or equivalent) verb has been used successfully (and 'false' after 'remove' or equivalent). Your game should be adjusted to use 'worn' anywhere you test for that item being on or off.
8. Repeat for all items that had wear-related verbs in your game.
9. Test your game from start to finish to make sure everything works as intended, with no side effects. Tune as necessary, possibly using other wearable operations.
10. Upload the resulting game.

This seems to work with tests performed so far. The only issue I’ve had is with dropping worn items. If there is an associated script the operation is blocked with the vague error message: “You can’t drop it/them” and there doesn’t seem to be any way of controlling this message. If there is no script, the item appears to be dropped, which is a bug. Controlling the message for attempted ‘wear’ operations on items not held would also be useful…perhaps in the advance wearables interface?
My experimentation continues…


Adding this to the start script should be all that is required if you want to keep your existing scripts, otherwise follow Pixie's suggestion:


ETA: added multiobject pre; fixed "wear" and "remove" to handle multiple; removed pattern changes as existing "don", "put on", etc. still work regardless; added check for empty object list

wear.script => {
  if (multiple and ListCount(object) = 0) {
    msg ("You've nothing to wear.")
  }
  else {
    foreach (o, object) {
      if (ListCount(object) > 1) {
        s = CapFirst(GetDisplayName(o)) + ": "
        OutputTextNoBr (s)
      }
      if (HasAttribute(o, "wear")) {
        if (HasScript(o, "wear")) {
          do (o, "wear")
        }
        if (HasString(o, "wear")) {
          msg (o.wear)
        }
      }
      else {
        msg (s"You can't wear "+o.article+".")
      }
    }
  }
}
remove.script => {
  if (multiple and ListCount(object) = 0) {
    msg ("You've nothing to remove.")
  }
  else if (TypeOf(object) = "objectlist") {
    foreach (o, object) {
      if (ListCount(object) > 1) {
        s = CapFirst(GetDisplayName(o)) + ": "
        OutputTextNoBr (s)
      }
      if (HasAttribute(o, "remove")) {
        if (HasScript(o, "remove")) {
          do (o, "remove")
        }
        if (HasString(o, "remove")) {
          msg (o.remove)
        }
      }
      else {
        msg ("You can't remove "+o.article+".")
      }
    }
  }
  else {
    if (HasAttribute(object, "remove")) {
      if (HasScript(object, "remove")) {
        do (object, "remove")
      }
      if (HasString(object, "remove")) {
        msg (object.remove)
      }
    }
    else {
      msg ("You can't remove "+o.article+".")
    }
  }
}
foreach (o, AllObjects()) {
  if (HasAttribute(o, "wear")) {
    o.displayverbs = ListExclude(o.displayverbs, "")
    if (not ListContains(o.displayverbs, "Wear")) {
      list add (o.displayverbs, "Wear")
    }
    o.inventoryverbs = ListExclude(o.inventoryverbs, "")
    if (not ListContains(o.inventoryverbs, "Wear")) {
      list add (o.inventoryverbs, "Wear")
    }
  }
}

To edit the wear script on the objects in the GUI, use the 'Attributes' tab (because "wear" will not be displayed in the 'Verbs' tab).


Sorry KV, I've confused you! What you are looking at is the version of Carnival of Regrets that I've already 'fixed'.

No, I'm with you. I played the most recent version of that game and mentioned that your changes seem to have fixed wear and remove. Then, I said I'd like to see that file before you made any changes, just to make sure my fix works.

My goal is not to fix a specific game but to find a simple general strategy that someone might follow if they encounter the problem with 'wear' disappearing.

Yes, I understand that.

I theorized a simple, general strategy. Then, I tested it on six older games, one game at a time (since testing it on all of the games at once wasn't really plausible, and merely theorizing only gets you so far). It worked every time.

You add 2 lines to the start script, then you add two verbs.

If someone can come up with a method easier than this, I am quite eager to see the code.

...and if this ever fails (before modifying anything else), I'd like to see that too, so I can learn from my mistakes.

THE FOLLOWING STEPS WORK ONLINE OR IN THE DESKTOP EDITOR
PART ONE - A FIX FOR OLD GAMES WITH "WEAR" AND "REMOVE" VERBS
Step 1
Change the patterns for wear and remove by adding these two lines to the start script:

IN CODE VIEW:

wear.pattern = "upupdowndownleftrightleftrightba"
remove.pattern = "upupdowndownleftrightleftrightab"
IN GUI VIEW:

Details
Step 2
Add these verbs:

IN FULL CODE VIEW:

  <verb name="wear_verb">
    <pattern>wear</pattern>
    <defaultexpression>"You can't wear " + object.article + "."</defaultexpression>
    <property>wear</property>
  </verb>
IN GUI:

Details
IN FULL CODE VIEW:

  <verb name="remove_verb">
    <pattern>remove</pattern>
    <defaultexpression>"You can't remove " + object.article + "."</defaultexpression>
    <property>remove</property>
  </verb>
IN GUI:

Details
Step 3
Test to make sure everything works!

To reiterate, I'm not trying to say that my way is the only way, or that my way is the best way, or that my way never fails.

I'd just like to see it fail if it doesn't always work, because I've tested it out six times in the past 12 hours, with 100% success rate.

If this DOES work at least 95% of the time (which I believe it will, unless someone needs to add on to the verbs' patterns), it can easily be made into a library for desktop users.

OldWearFixLib.aslx

<?xml version="1.0"?>
<library>
  <command name="wear">
    <pattern>upupdowndownleftrightleftrightba</pattern>
    <script>
      msg("Nothing happens.")
    </script>
  </command>

  <command name="remove">
    <pattern>upupdowndownleftrightleftrightab</pattern>
    <script>
      msg("Nothing happens.")
    </script>
  </command>

  <!-- 
      NOTE:  You may need to add more patterns to these verbs, depending on your game.

      I did not add anything extra to these patterns because there's no telling what patterns may exist, 
      and the wrong pattern(s) could create bugs (i.e., if you have separate WEAR and DON verbs set up).
     -->

  <verb name="wear_verb">
    <pattern>wear</pattern>
    <defaultexpression>"You can't wear " + object.article + "."</defaultexpression>
    <property>wear</property>
  </verb>

  <verb name="remove_verb">
    <pattern>remove</pattern>
    <defaultexpression>"You can't remove " + object.article + "."</defaultexpression>
    <property>remove</property>
  </verb>

</library>
PART TWO - AN ENTER VERB
Step 1 (of 1)
Go into full code view (or edit your .aslx file in a text editor), and change the first line of your enter verb from <verb> to <verb name="enter_verb">. (NOTE: You can add an "enter" verb to any game by doing this.)

If the pattern is simply "enter", it should look like this:

  <verb name="enter_verb">
    <property>enter</property>
    <pattern>enter</pattern>
    <defaultexpression>"You can't enter " + object.article + "."</defaultexpression>
  </verb>
If you don't like to fool around in code view, you can add (or edit) a verb in the GUI:

Details
I have actually tested the code I have posted, and I have done so numerous times -- on my games as well as games made by other authors (including your game, DavyB).

If I see someone post, "I have tried these methods, and they do not work because ___ ," I'll continue to try to help. Otherwise, I'll assume I'm just bothering everyone, no one has even tested it out with my code, and that no one is interested in my input (for whatever reason; even if it is basically the same thing that Pixie suggested -- only a little more simplified, since I change the new commands' patterns in the start script, which can also be done online or in the desktop).

I am not offended, nor do I wish to offend, by the way. I'm just thinking that the best way to help when my input isn't helping is to nix my input. (This is for the greater good, you understand.)

So, I apologize if I have upset anyone, or confused anyone, or in any way exacerbated things.

...and I'm also sorry about this wall of text, but only if it isn't helping anyone.

Cheers!

Hey, KV! Maybe you could put all this in the libraries and sample codes section of the forum? I'm sure it would help a lot of people!


Hey, KV! Maybe you could put all this in the libraries and sample codes section of the forum? I'm sure it would help a lot of people!

...wouldn't it be nice to have a 'wear_convert' among the 'wearables' operations, which took an existing game using 'wear' etc and converted it to use the new format!


Upgrading Wearables

Add these two functions to your game in full code view, then add UpgradeWearables to your start script:

ETA: Added remove.pattern; Resolved issues with existing verbs

  <function name="UpgradeWearables"><![CDATA[
    remove.pattern = "^take (?<object>.+) off$|^remove (?<object>.+)$|^doff (?<object>.+)$|^take off (?<object>.+)$"
    foreach (c, ScopeCommands()){
      foreach (att, Split("don;puton;takeoff;doff", ";")){
        if (c.property = att){
          c.parent = game
        }
      }
    }
    remove.multipleobjects => {
      game.pov.currentcommandpendingobjectscope = ScopeInventory()
    }
    remove.script => {
      if (multiple and ListCount(object) = 0) {
        msg ("[NothingToRemove]")
      }
      else {
        foreach (obj, object) {
          f = _DoRemove(obj)
        }
      }
      UpdateArmour
    }
    remove.scope = "inventory"
    foreach (o, AllObjects()) {
      if (HasAttribute(o, "wear")) {
        o.wear = null
        o.don = null
        o.puton = null
        o.remove = null
        o.takeoff = null
        o.doff = null
        o.wearable = true
        o.usestandardverblist = true
        o.worn = false
        o.armour = 0
        o.multistate_status = 0
        o.invverbs = ""
        o.wornverbs = ""
        o.take => {
          msg (DynamicTemplate("TakeSuccessful", this))
          this.parent = game.pov
          SetVerbs
        }
        o.removeable = true
        o.wear_layer = 2
        o.inventoryverbs = ListCombine (o.inventoryverbs, Split("Wear;Remove", ";"))
        o.wear_slots = NewStringList()
        o.colourmylistalias => {
          if (HasString(this, "alias")) {
            s = CapFirst(this.alias)
          }
          else {
            s = CapFirst(this.name)
          }
          if (HasString(this, "listalias")) {
            s = this.listalias
          }
          this.listalias = "<span style=\"color:blue\">" + s + "</span>"
          if (HasAttribute(this,"remove")) {
            this.remove = null
          }
        }
      }
    }
  ]]></function>
  <function name="SetVerbs">
    foreach (o, GetAllChildObjects(game.pov)) {
      if (DoesInherit(o, "wearable") or HasAttribute(o, "wearable")) {
        if (HasAttribute(o, "wear_slots") and HasInt(o, "wear_layer")) {
          _SetVerbsForGarment (o)
        }
        if (not HasString(o, "alias")) {
          o.alias = o.name
        }
        if (not HasString(o, "listalias")) {
          o.listalias = o.alias
        }
      }
    }
  </function>

@Richard Headkid, out this morning but looking forward to trying this later!


Then type some long, random text for the command pattern.

Could also use one of the regular expressions ^(?!x)x, (*FAIL), ^(?<=x), ^\b$, or ^(?!) which don't match any possible string. (Not sure if Visual Studio supports (*FAIL); you should be able to see how the others work, but if not I'd love to explain them).
Actually, you could probably use the pattern "^" (that's a string starting with a space) because the parser removes any spaces from the start of a command before checking it against the pattern.


@Richard Headkid, sorry for the delay...working on too many issues at the same time!

I tied plugging your code into a game with wearable items that was affected by the recent change. It's showing an error when I attempt to wear an item. Was your code supposed to reconnect with all previous wear and remove scripts in the game and run as it would have done before the last update? ...and also convert to the new structure? I realise that the second part cannot be completed fully because of the need to handle 'worn' in the scripts. It would be useful if the conversion displayed the items involved?


K.V.

Did you add UpgradeWearables to the start script?


Yup, and just checked to make sure. I'll try to put in some sort of trace and run it again.


K.V.

I added this line to the main function, so check the log to see what all was modified:

Log ("Modifying wear settings for " + o.name + ".")

Here's the revised function (with the function on which it depends included):

  <function name="UpgradeWearables"><![CDATA[
    remove.pattern = "^take (?<object>.+) off$|^remove (?<object>.+)$|^doff (?<object>.+)$|^take off (?<object>.+)$"
    foreach (c, ScopeCommands()) {
      foreach (att, Split("don;puton;takeoff;doff", ";")) {
        if (c.property = att) {
          c.parent = game
        }
      }
    }
    remove.multipleobjects => {
      game.pov.currentcommandpendingobjectscope = ScopeInventory()
    }
    remove.script => {
      if (multiple and ListCount(object) = 0) {
        msg ("You've nothing to take off.")
      }
      else {
        foreach (obj, object) {
          f = _DoRemove(obj)
        }
      }
      UpdateArmour
    }
    remove.scope = "inventory"
    foreach (o, AllObjects()) {
      if (HasAttribute(o, "wear")) {
        Log ("Modifying wear settings for " + o.name + ".")
        o.wear = null
        o.don = null
        o.puton = null
        o.remove = null
        o.takeoff = null
        o.doff = null
        o.wearable = true
        o.usestandardverblist = true
        o.worn = false
        o.armour = 0
        o.multistate_status = 0
        o.invverbs = ""
        o.wornverbs = ""
        o.take => {
          msg (DynamicTemplate("TakeSuccessful", this))
          this.parent = game.pov
          SetVerbs
        }
        o.removeable = true
        o.wear_layer = 2
        o.inventoryverbs = ListCombine (o.inventoryverbs, Split("Wear;Remove", ";"))
        o.wear_slots = NewStringList()
        o.colourmylistalias => {
          if (HasString(this, "alias")) {
            s = CapFirst(this.alias)
          }
          else {
            s = CapFirst(this.name)
          }
          if (HasString(this, "listalias")) {
            s = this.listalias
          }
          this.listalias = "<span style=\"color:blue\">" + s + "</span>"
          if (HasAttribute(this,"remove")) {
            this.remove = null
          }
        }
      }
    }
  ]]></function>
  <function name="SetVerbs">
    foreach (o, GetAllChildObjects(game.pov)) {
      if (DoesInherit(o, "wearable") or HasAttribute(o, "wearable")) {
        if (HasAttribute(o, "wear_slots") and HasInt(o, "wear_layer")) {
          _SetVerbsForGarment (o)
        }
        if (not HasString(o, "alias")) {
          o.alias = o.name
        }
        if (not HasString(o, "listalias")) {
          o.listalias = o.alias
        }
      }
    }
  </function>

Create a GET WEARABLE command, and put this for the script to test this:

wearable = PickOneObject(FilterByAttribute(AllObjects(),"removeable",true))
cloned_wearable = CloneObjectAndMove(wearable, game.pov)
msg("You are now carrying " + GetDisplayName(cloned_wearable) + ".")
cloned_wearable.scenery = false // Just to make sure
cloned_wearable.visible = true // Just to make sure

I am testing this in the game you sent me, DavyB.

I added these functions, the line in the start script, and the command to test it (which is KVTEST).

I will email it to you.


K.V.

This is what we've currently got (mostly coded by DavyB, which is why it looks good when it prints out).

Anyone see room for improvements?

msg ("</br><center>+ + + + +</center></br>")
msg ("<b>Wearables Conflict Report</b>")
msg ("Your game has been analysed to identify uses of the <i>worn</i> attribute and verbs that may have to be modified as a result of the introduction of the 'wearables' feature in Quest 5.7.2.</br>")
msg ("The full range of verbs for 'wear' where there may be conflict is:</br>...[wear]</br>")
msg ("The full range of verbs for 'remove' where there may be conflict is:</br>...[remove]</br>")
wearables = NewList()
foreach (o, AllObjects()) {
  if (HasAttribute(o, "wear") or HasAttribute(o, "remove") or HasAttribute(o, "puton") or HasAttribute(o, "takeoff") or HasAttribute(o, "don") or HasAttribute(o, "doff")) {
    if (not DoesInherit(o,"wearable")) {
      list add (wearables, o)
    }
  }
}
if (ListCount(wearables) = 0) {
  msg ("No use of wear-related items was found.")
}
else {
  msg ("The following use of wear-related verbs on objects was found:")
  foreach (o, wearables) {
    str = "</br><b>" + o.name + "</b>"
    if (HasAttribute(o, "alias")) {
      str = str + " (alias: " + o.alias + ")"
    }
    msg (str)
    if (HasAttribute(o, "worn")) {
      msg ("Object " + o.name + " has a <i>worn</i> attribute.")
    }
    str = ""
    if (HasAttribute(o, "wear")) {
      str = str + " (wear)"
    }
    if (HasAttribute(o, "puton")) {
      str = str + " (put on)"
    }
    if (HasAttribute(o, "don")) {
      str = str + " (take off)"
    }
    if (HasAttribute(o, "remove")) {
      str = str + " (remove)"
    }
    if (HasAttribute(o, "takeoff")) {
      str = str + " (take off)"
    }
    if (HasAttribute(o, "doff")) {
      str = str + " (take off)"
    }
    msg ("Verbs used are: " + str + ".")
  }
  msg ("</br><center>+ + + + +</center></br>")
} 

I've modified several games to use the new wearables feature, rather than overriding it with my own commands as before. This has been fine so far but on working on Woo Goes Further, I've run into two problems...or rather one problem and a query!

The problem is that if text is specified for the attempted remove of a worn item that can't be removed, it doesn't appear to be used (I've tried this with the latest Beta)?

The query is in relation to preventing a wearable item being removed. If say, the player is wearing a gas mask and can't take if off in some parts of the game, how should that be handled? What I've done as a workaround is to move the player to the nearest safe location. I know I can take off the gas mask and add code to put it back on again but I'd prefer the player to be stopped.

Thanks!


K.V.

Hello, DavyB!

This works for me in a test game:

EDIT: This did not work. I am crazy.

BAD CODE
<!--Saved by Quest 5.8.6737.23645-->
<asl version="580">
  <include ref="English.aslx" />
  <include ref="Core.aslx" />
  <game name="The Wedding Band">
    <gameid>567d1b62-d7ca-4884-a707-b17cb9079082</gameid>
    <version>1.0</version>
    <firstpublished>2018</firstpublished>
  </game>
  <object name="room">
    <inherit name="editor_room" />
    <isroom />
    <object name="player">
      <inherit name="editor_object" />
      <inherit name="editor_player" />
      <object name="wedding band">
        <inherit name="editor_object" />
        <inherit name="wearable" />
        <feature_wearable />
        <removeable type="boolean">false</removeable>
        <removemsg>You can't take that off!</removemsg>
        <feature_startscript />
        <attr name="_initialise_" type="script">
          WearGarment (this)
        </attr>
      </object>
    </object>
  </object>
</asl>

You are in a room.

> i
You are carrying a wedding band (worn).

> remove band
You cannot remove it!


K.V.

Oh, wait...

That didn't work. I saw that the response ended with "!", and I assumed it was my custom response.

Hrmm...


K.V.

Ah...

We have to set removeable to false and add an attribute named notremoveablemessage with our message as the string.

<!--Saved by Quest 5.8.6737.23645-->
<asl version="580">
  <include ref="English.aslx" />
  <include ref="Core.aslx" />
  <game name="The Wedding Band">
    <gameid>567d1b62-d7ca-4884-a707-b17cb9079082</gameid>
    <version>1.0</version>
    <firstpublished>2018</firstpublished>
  </game>
  <object name="room">
    <inherit name="editor_room" />
    <isroom />
    <object name="player">
      <inherit name="editor_object" />
      <inherit name="editor_player" />
      <object name="wedding band">
        <inherit name="editor_object" />
        <inherit name="wearable" />
        <feature_wearable />
        <removeable type="boolean">false</removeable>
        <feature_startscript />
        <attr name="_initialise_" type="script">
          WearGarment (this)
        </attr>
        <notremoveablemessage>You can't take that off!</notremoveablemessage>
      </object>
    </object>
  </object>
</asl>

You are in a room.

> i
You are carrying a wedding band (worn).

> remove band
You can't take that off!


@KV, that was a short holiday!
Thanks for the fix. I'll assume the Pixie will look at this in terms of the higher level user interface.


This topic is now closed. Topics are closed after 60 days of inactivity.

Support

Forums