Jump to content
You are about to reply to a thread that has been inactive for 3033 days.

Please take a moment to consider if this thread is worth bumping.

Recommended Posts

Posted

I have 2 objects - one of them generates a channel using:

 

MyChannel = 0x80000000 | (integer)("0x"+(string)llGetOwner);

 

let's call that object "the key"

and the second object, "the listener" generates the channel with:

 

MyChannel = 0x80000000 | (integer)("0x"+(string)llGetObjectDesc);

 

where llGetObjectDesc contains the UUID of the person holding "the key".

2 people. 1 of them holds the key, the other the listener

 

For example:

I, Morri(c043ccc0-8416-417d-aa69-0155d67ff857), have "the key", and it generates the channel using my own UUID.

Second person, has "the listener" and it generates the channel using MY UUID, which is in the object's description.

In result, we both are using the same channel and can communicate between these two objects.

 

The issue:

The problem I have with that is if there was 1 person holding the key,
and 5 people had the listener object and all of them had the same UUID of the person holding the key in their object description
= the key commands would affect all 5 listeners at the same time.

How do I link 1 key to only 1 listener?

 

 

Code:

The lintener:

integer MyChannel;
key MyOwner;

default
{
    state_entry()
    {
        MyOwner = llList2String(llGetLinkPrimitiveParams(4, [ PRIM_DESC ]), 0);
        MyChannel = 0x80000000 | (integer)("0x"+(string)MyOwner);
        llListen (MyChannel,"","","");
    }

    listen(integer channel, string name, key id, string msg)
    {
        if(msg == "show") 
{ llSetLinkAlpha(LINK_SET, 1.0, ALL_SIDES); } } }

 

The key:

integer MyChannel;
key MyOwner;
integer gListener;

 
default
{
        state_entry()
    {
        MyOwner = llGetOwner();
        MyChannel = 0x80000000 | (integer)("0x"+(string)MyOwner);
    }

    changed(integer change)
    {
        if (change & CHANGED_OWNER){
            llResetScript();
        }
    }
    
 touch_start(integer total_number)
    {
        llListenRemove(gListener);
        key user = llGetOwner();
        gListener = llListen(-99, "", user, "");
        llDialog(user, "\nWhat do you want to do?", ["Show", "Hide"] , -99);
        llSetTimerEvent(60.0);
    }
    listen(integer chan, string name, key id, string msg)
    {
        if(llToLower(msg) == "hide")
          {
              llSay(MyChannel, "hide");
            }
        else if(llToLower(msg) == "show")
          {
              llSay(MyChannel, "show");
            }
            
        llSetTimerEvent(0.1);        
    }
    timer()
    {
        llListenRemove(gListener);
        llSetTimerEvent(0.0);
    }
}

 

Posted

You could try all sorts of solutions, some of which may be more practical than others, depending on your setup.  Your listen event, for example, can tell you more than just the channel number and the message.  Check the name or key variables to see who sent the message. 

If that's not practical, you could assign each user a unique identifier and then modify the listen event in their script so that it sends

    listen(integer chan, string name, key id, string msg)    {        llSay(MyChannel, gsMyIdentifier+ "~"+msg);            llSetTimerEvent(0.1);            }

(Note that you don't need the llToLower, because you know exactly what messages to expect from your own dialog.)  Then you change the listen event in your other script to be

    listen(integer channel, string name, key id, string msg)    {        list temp = llParseString2List(msg,["~"],[]);        string sIdentifier = llList2String(temp,0);        integer idx = llListFindList(glAllSenders,[sIdentifier]);        //Then, if you only want to obey a message from sender #1 ...        if((msg == "show") && idx == 0))        {            llSetLinkAlpha(LINK_SET, 1.0, ALL_SIDES);        }    }

As long as you have a list of the identiifiers your senders will use (glAllSenders), you can always check that list as I have in order to pay attention to each of them exclusively. 

And I'm sure you can think up other methods too ....

Posted

Thank you very much for your reply, Rolig Loon. I've been seeing you in a lot of LSL threads last 2 days, you've been a great help already!

As for other methods, I can think of simple ones, but they are prone to fail, or make buyers disatisfied with the solution.

I've been playing around in LSL for last 2 days after few years break, and I'm learning as I go. Unfortunately I must admit that I don't get your solution fully. I'm not sure how to assign each user a unique identifier.

Would you mind explaining your solution a bit more noob-friendly?

 

Posted

Hi Kropah,

I'm not sure I understand exactly what you're trying to do, but it sounds like you want to sell two things that, regardless who has them, can establish a connection to each other, and nothing else. If there will be three or more of these things on a sim at the same time, and they come from you in an unitialized state, there will need to be a user moderated pairing mechanism of some sort.

I'd do that by creating a finite time "pairing window" during which the listener script will perhaps listen on a fixed private channel for a message from a key. The owner of the listener must do something (touch?) to place the script in the pairing mode and then notifies the owner of the key in some way (IM?) to get their key into pairing mode. The owner of the key then does something to make the key script send a message containing the link ID on that private channel, which can be another channel number (generated from UUID as you did) or a code (generated a similar way) that must be in every message the listener is to hear. If the listener script doesn't receive a key within the pairing window, it waits for another pairing command from the owner.

Once pairing is complete, the listening script will hear only the key it was paired with. To re-pair, the owner of the listening thing repeats the pairing procedure.

Posted

That all depends on how you hand out your sending devices.  You could do it all manually, I suppose ("Bob, your code is Bubba"), but I would probably do it with a rezzer, assigning a numerical identifier:

 

touch_start(integer num){    ++gCount;   // Keep track of how many devices you have rezzed already...    // ... then save the current value of gCount (your identifier) and the person's UUID ....    glAllSenders += [gCount,llDetectedKey(0)];    // ... and rez the device, sending the value of gCount as the start parameter.    llRezAtRoot("My Sending Device", llGetPos() + <0.0,0.0,1.0>,ZERO_VECTOR,ZERO_ROTATION,gCount);}

That's slightly different from what I wrote earlier, but you have asked a slightly different question too.  :smileywink:  In any case, script your newly-rezzed device to save that value of gCount in its on_rez event and store it somewhere for use as gsMyIdentifier. I didn't really need to save the toucher's UUID, but I did it as a reflex action.  It could be very handy later if, for example, the same person clicked your rezzer a second time.  Since the person's UUID is saved in the strided list glAllSenders, you can easily identify him as a returnee and send the old value of the numerical identifier as the start value instead of assigning a new one.

 ETA:  I see that Maddy has suggested yet another possible way to solve your problem.  Fertile minds can keep this up all day.  The bottom line is that there is no unique or "best" way to do what you're asking.  Whatever you decide should be something that makes sense in the context of your own design and is least confusing for you and your users.

You are about to reply to a thread that has been inactive for 3033 days.

Please take a moment to consider if this thread is worth bumping.

Please sign in to comment

You will be able to leave a comment after signing in



Sign In Now
×
×
  • Create New...