Welcome to the Second Life Forums Archive

These forums are CLOSED. Please visit the new forums HERE

Event handling question.

Klaire Larnia
Learner, be gentle....
Join date: 2 Jun 2008
Posts: 41
05-25-2009 12:24
Okay I am confused again... no real suprise these days sadly.

I have a script which sets up a menu configured via a notecard. This inital setup is done in the default state. It then swaps to a new state called "mainmenu" to run the acutal menu itself.

Now, and this is where I am confused..

After the notecards are read and the data sorted I have this:
CODE

touch_start(integer total_number)
{
state mainmenu;
}

state mainmenu
{
state_entry()
{
llListen(Channel, "", NULL_KEY, ""); // listen for dialog answers (from multiple users)
}

touch_start(integer total_number)
{
llDialog(llDetectedKey(0), "What do you want to do?", MenuMain1, Channel); // present dialog on click
}


Okay I hope that makes sense so far.. The problem here is it takes two clicks and not one to make the menu appear as there are two touch events.

If I remove either of the touch events tho, the menu will NOT appear. If I remove the first one, I get no menu at all. If I remove the second one I acutally get scripting errors when it runs.

I have only just today worked out how to use States, and event handling is a little confusing as I am not totaly sure of all the operators - ao I wonder if I have missed something in the setup of the second state that is causing the error to occur.

Soo, what I am (hopefully) leading to is, how do I alter the above to work so only one click is needed.

Apollogies for the long winded and waffly question. but I hope it all make sense.

Klaire
Lynnore Vaher
Registered User
Join date: 19 Jul 2008
Posts: 16
05-25-2009 12:33
Try this, removed the touch event and put the llDialog in the state entry so once you touch and your script enters the mainmenu state, it opens the listen and calls the dialog right after.

Edit: Forgot about the key, so once the person click it enters the state, but you have to remember who touches it so you save the key in a variable, "toucher" in this case.

CODE


//This way on the top
key toucher;

// rest of your script

//Now the part you posted
touch_start(integer total_number)
{
toucher = llDetectedKey(0);
state mainmenu;

}

state mainmenu
{
state_entry()
{
llListen(Channel, "", NULL_KEY, ""); // listen for dialog answers (from multiple users)
llDialog(toucher, "What do you want to do?", MenuMain1, Channel); // present dialog on click
toucher = NULL_KEY;
}
}


A better way would be though, after your notecard is read you let it go to the state and just have the touch event there with a llDetectedKey(0). So once your dataserver is over, you put in "state mainmenu", and keep that state as you posted it.
Klaire Larnia
Learner, be gentle....
Join date: 2 Jun 2008
Posts: 41
05-25-2009 12:48
From: Lynnore Vaher
Try this, removed the touch event and put the llDialog in the state entry so once you touch and your script enters the mainmenu state, it opens the listen and calls the dialog right after.

CODE


//This way on the top
key toucher;

// rest of your script

//Now the part you posted
touch_start(integer total_number)
{
toucher = llDetectedKey(0);
state mainmenu;

}

state mainmenu
{
state_entry()
{
llListen(Channel, "", NULL_KEY, ""); // listen for dialog answers (from multiple users)
llDialog(toucher, "What do you want to do?", MenuMain1, Channel); // present dialog on click
toucher = NULL_KEY;
}
}



Thank you. That works perfectly

To make sure I understand, you are getting the key for whoever touches the prim, using that to direct the menu at them and then clearing it afterwards.

You just call the check before the dialog box and store the info for use, rather than check as you try to bring the menu up, so the value is known proir and cannot be interperted wrong.

Is that right?

Klaire
Rolig Loon
Not as dumb as I look
Join date: 22 Mar 2007
Posts: 2,482
05-25-2009 12:57
From: Lynnore Vaher

A better way would be though, after your notecard is read you let it go to the state and just have the touch event there with a llDetectedKey(0). So once your dataserver is over, you put in "state mainmenu", and keep that state as you posted it.


Yup.... That's how I would do it. The reading of notecards is all part of the setup that happens before somebody wanders by and decides to click on your object, so keep it and all other setup stuff in state default. As Lynnore says, let the EOF in the dataserver event that reads notecards be the trigger that moves to state mainmenu. Then put the llDialog statement in a touch_start event in that new state. Finally, use a listen event to respond when people play with the Dialog buttons. I would also put a change event in state mainmenu so that the script resets if you decide to drop a new notecard in while the script is running.
_____________________
It's hard to tell gender from names around here but if you care, Rolig = she. And I exist only in SL, so don't ask.... ;)

Look for my work in XStreetSL at
Lynnore Vaher
Registered User
Join date: 19 Jul 2008
Posts: 16
05-25-2009 12:59
From: someone
Thank you. That works perfectly

To make sure I understand, you are getting the key for whoever touches the prim, using that to direct the menu at them and then clearing it afterwards.

You just call the check before the dialog box and store the info for use, rather than check as you try to bring the menu up, so the value is known proir and cannot be interperted wrong.

Is that right?

Klaire


Once you change states, your llDetectedKey(0) from previous state wont work anymore, neither will local variables work so you have to store the key in a global variable to use after you change states. But again, the best way would be te switch states after reading notes and use the touch event from the mainmenu. Then there's no need to save unneccesary variables.

Anyway glad i could help! Have fun scripting ^^
Rolig Loon
Not as dumb as I look
Join date: 22 Mar 2007
Posts: 2,482
05-25-2009 13:03
From: Lynnore Vaher
Once you change states, your llDetectedKey(0) from previous state wont work anymore, neither will local variables work so you have to store the key in a global variable to use after you change states.

Glad i could help! ^^


... unless you wait until state mainmenu to use a touch_start event. Keeping setup business and runtime business in separate states is a bit cleaner anyway, and it saves you having to pass llDetectedKey(0) in a global variable. ;)
_____________________
It's hard to tell gender from names around here but if you care, Rolig = she. And I exist only in SL, so don't ask.... ;)

Look for my work in XStreetSL at
Lynnore Vaher
Registered User
Join date: 19 Jul 2008
Posts: 16
05-25-2009 13:09
From: Rolig Loon
... unless you wait until state mainmenu to use a touch_start event. Keeping setup business and runtime business in separate states is a bit cleaner anyway, and it saves you having to pass llDetectedKey(0) in a global variable. ;)



Yup, editted right after i posted. Don't want to encourage that way of scripting ( the saving key in global variable one) so once again i mentioned doing it the right way :P
Klaire Larnia
Learner, be gentle....
Join date: 2 Jun 2008
Posts: 41
05-25-2009 13:13
From: Rolig Loon
I would also put a change event in state mainmenu so that the script resets if you decide to drop a new notecard in while the script is running.


I understand the priciple of this. Would this be soemthing like:

CODE

changed(integer change)
{
if (change & CHANGED_INVENTORY)
llSay (0,"Notecard has been changed. Resetting...");
llResetScript()
}


is that right?
_____________________
Klaire
xXx =^.^= xXx
Rolig Loon
Not as dumb as I look
Join date: 22 Mar 2007
Posts: 2,482
05-25-2009 13:22
From: Klaire Larnia
I understand the priciple of this. Would this be soemthing like:

CODE

changed(integer change)
{
if (change & CHANGED_INVENTORY)
llSay (0,"Notecard has been changed. Resetting...");
llResetScript()
}


is that right?


Yes. The only thing I would do differently is to use either llOwnerSay or an IM for the little message. Nobody else needs to hear your reset conversation. Also, if you were to decide to let someone else drop a notecard in, an IM would let you get the news remotely.
_____________________
It's hard to tell gender from names around here but if you care, Rolig = she. And I exist only in SL, so don't ask.... ;)

Look for my work in XStreetSL at
Rolig Loon
Not as dumb as I look
Join date: 22 Mar 2007
Posts: 2,482
05-25-2009 13:30
BTW, not that the question has come up, but if you have setup things happening in an on_rez event in state default, be sure that you also have an on_rez event in state mainmenu. If you don't, then there's a good possibility that you will take the object into inventory while it is in state mainmenu and it will never see the on_rez event in state default when you re-rez it. The on_rez event in state mainmenu can be as simple as

CODE

on_rez(integer start_param)
{
llResetScript();
}
_____________________
It's hard to tell gender from names around here but if you care, Rolig = she. And I exist only in SL, so don't ask.... ;)

Look for my work in XStreetSL at
Klaire Larnia
Learner, be gentle....
Join date: 2 Jun 2008
Posts: 41
05-25-2009 13:39
From: Rolig Loon
BTW, not that the question has come up, but if you have setup things happening in an on_rez event in state default, be sure that you also have an on_rez event in state mainmenu. If you don't, then there's a good possibility that you will take the object into inventory while it is in state mainmenu and it will never see the on_rez event in state default when you re-rez it. The on_rez event in state mainmenu can be as simple as


Acutally I have no on_rez event at all... I did not think it necessary as the script will be in a non-copy object so will only active the time it is initally rezzed.

I thought you only need that for items which you need to do something the instant they are rezzed, like a prim spining script etc.
_____________________
Klaire
xXx =^.^= xXx
Rolig Loon
Not as dumb as I look
Join date: 22 Mar 2007
Posts: 2,482
05-25-2009 14:00
From: Klaire Larnia
Acutally I have no on_rez event at all... I did not think it necessary as the script will be in a non-copy object so will only active the time it is initally rezzed.

I thought you only need that for items which you need to do something the instant they are rezzed, like a prim spining script etc.


Quite right. You don't need an on_rez event. It just occurred to me to mention it because that's a common thing for people to forget when they have scripts with multiple states. On_rez events are handy when you want to be sure that the script doesn't just pick up where it left off when the object was taken to inventory. You can force the script to re-initialize or perhaps to do something (changing color or position, for example) when it's rezzed that it wouldn't do if you llResetScript() while it's already rezzed.
_____________________
It's hard to tell gender from names around here but if you care, Rolig = she. And I exist only in SL, so don't ask.... ;)

Look for my work in XStreetSL at