How to ask: If attribute 'take' = True

psymann
01 Apr 2013, 11:15
Hello all,

So I want to print one of three messages when I do a particular action (an action that is not 'take') to an object:

1) [If the object has a "take" attribute of "false" - ie it can't be taken]
- Print "Leave it where it is."

2) [If the object has a "take" attribute of "true" - ie it can be taken]
- Print "Try picking it up."

3) [If the object has a "take" attribute of some sort of scripty thing - ie it's not easy to work out if it can be taken or not]
- Print "Take it or leave it."

When I try to put in
If [object attribute equals] object [myobject] Attribute [take] = false
- Print "Leave it where it is."
Else if [object attribute equals] object [myobject] Attribute [take] = true
- Print "Try picking it up."
Else
- Print "Take it or leave it."


if (myobject.take = false) {
msg ("Leave it where it is.")
}
else if (myobject.take = true) {
msg ("Try picking it up.")
}
else {
msg ("Take it or leave it.")
}


Then I get the in-game error message "Operation 'Equal' is not defined for types 'LazyLoadScript' and 'Boolean'".

That seems a bit odd - why can't I test whether Take is equal to True or not? Or am I just doing it the wrong way? :?

psymann

jaynabonne
01 Apr 2013, 13:43
You're running into the case where "take" is a script. You can't compare that to true, as they are different types. I'd do something like:

if (HasBoolean(myobject, "take")) {
if (myobject.take) {
msg ("Try picking it up.")
}
else {
msg ("Leave it where it is.")
}
} else {
msg ("Take it or leave it.")
}

You only treat "take" as a boolean if it, in fact, is a boolean. You can also use "HasScript" to see if the attribute is a script.

A stylistic thing: there isn't really any need to compare a boolean value to true or false, as "if (somebool = true)" is equivalent to "if (somebool)". (Does Quest insert that into scripts? I see that a lot. Just use "object has flag", which maps to GetBoolean) Also, you don't need to check for both true and false, as if it's not one, it's the other.

psymann
01 Apr 2013, 16:05
Thanks, jay, that makes sense :-)

And I've just tested it out in my code and works perfectly, thanks!

Another bit of code overcome, so another bit of story/puzzle can be written :-D

And to think all that was just so I can give an appropriate "you can't do that" message for a different verb ;-)

HegemonKhan
01 Apr 2013, 21:42
just a bit of additional comments to add to jaynabonne's comments:

"take" is a core (pre-set) verb, and it's type is "SCRIPT". This is because, most of the core stuff in very complicated for it to work (so simply for us users, lol), so lots of the core stuff is of the SCRIPT type as it requires all that complex coding which goes on hidden from us users as we use such core stuff, such as the "take" verb.

I'd have to check, if the core has a boolean type of~for "take", such as maybe "takeable", (usually -able or -ed or -ing are used for boolean's names*, but these suffixes aren't the only words used for booleans, as for example, "dead", is a common boolean that is used for npcs or monsters when making an rpg like game, but it doesn't use any suffixes. "Human" could be another boolean, if you're working with races, again common with rpg like games ~ HK loves rpgs lol, though booleans aren't the only ways of "flag referencing" something, as there is also the inherited object types, and a creative way is to use integers too: if whatever = 0, then do this_0; if whatever = 1, then do this_1; etc etc etc. Booleans are a quick and useful way however to do most things that people want to do, with "flag referencing" and most coding. In my limited experience, use of "boolean type attributes" and "integer type attributes" and "set a variable or attribute scripts" and "IF scripts", are the four main codings for doing almost anything that you need done. They're very powerful, you can do A LOT of stuff with just these four code things).

*see below:
If (object.flying = true), then...
if (object.equipped = true), then...
if (object.equipable = true), then...

so, if you want to set something to be "= to true or false", then it has to be a boolean type (or maybe you could use a string type too)**

an error that has been popping up a lot on this forum by posters is the:

~ "Error: "string" and "int32"

this means that you've got:

string type = integer type (and thus since a string is not an integer, and vice-versa, you get the error)

a way to match them up:

string type = ToString (integer type)

"ToString" converts an integer type into a string type

attribute types:

string = string : no error
integer = integer : no error
boolean = boolean : no error
boolean = true/false only string : no error
etc etc etc

string = integer : ERROR
script = boolean : ERROR
etc etc etc

jaynabonne
01 Apr 2013, 21:51
Keep in mind two things:

1) true and false are built-in, atomic values, like null or numbers (e.g. 0, 2.5, -3.14159, etc). If you had a string value, you would have to use "true" and "false" (with quotes) to make them strings.

2) Assigning an attribute sets its type. (I really hate in these discussions that Quest overloads '=' based on context - sometimes it's assignment, and sometimes it's an equality operator, so it can be confusing here on the forum to always be sure.) So if you have an attribute defined in your object:


<object name="myobject">
<take type="script">
...
</take>
</object>


and then do the assignment:

myobject.take = true


then the "take" attribute of "myobject" will now be of type boolean.

I had an interesting case once where I was concatenating a bunch of values onto a string, and I made the mistake of trying to append a string list to it, and suddenly my string variable had turned, itself, into a string list... :)

psymann
01 Apr 2013, 21:58
Sounds as if I'll have to be at least as careful when checking type mismatches on here as I do at work with excel ;) Thanks for the tips.

HegemonKhan
01 Apr 2013, 22:05
could this be remedied, by braking apart the operations, such as doing this (if alex wanted to change with with quest and~or if it was easy or even possible to do so and~or if it doesn't cause other problems as well):

"==" <-> "equality operator"

"=" <-> "an assignment"

that way, you wouldn't have a single symbol~character ("=") doing both operations.

jaynabonne
01 Apr 2013, 22:37
That's the way it's done in some other language (e.g. C, C++, Java, Javascript). Some languages do it the other way; for example, Pascal uses '=' for equaily and ':=' for assignment.

I'm sure Alex could change it if he wanted to. I do understand to some extent why it is the way it is - people are more used to '=' than something exotic like '==', so if he's targetting a less coding-savvy audience, keeping it with a more intuitive symbol makes sense. And generally it works fine, as '=' morphs within context to do the right thing.

It's just when we try to talk about it that it can get confusing. :)