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

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

Recommended Posts

Posted

So, im playing around with a new idea i had. I want to detect avatars that are within 2 Meters infront of me without using a Sensor. So far i have used llGetAgentList to do this and have set a condition so it only returns people within 2 Meters of me BUT it returns everyone within 2 Meteres within 360 degrees of me. So if someone is stood behind me it will stick pick them up. So what i want to do is have my script only detect other avatars that are standing infront of me, inside a 45 degree angle. So a similar shape to this \ / . And are no further away than 2 meters. My code is as follows :

list avatars=[];
integer i;

av(){
    avatars=llGetAgentList(AGENT_LIST_REGION,[]);
    i=-1;
    while(++i<llGetListLength(avatars)){
        vector pos=(vector)llList2String(llGetObjectDetails((key)llList2String(avatars,i),[OBJECT_POS]),0);
        vector pos2=llGetPos()+<0,0,0>*llGetRot();
        vector pos3=pos2-pos;
        
        
        if(llVecDist(pos,llGetPos())<2){
            if((key)llList2String(avatars,i)!=llGetOwner()){
           
                //This section is the section that needs to only detect avatars in front of me within the 2 meter / 45 degree range
                llOwnerSay(llKey2Name((key)llList2String(avatars,i))+" is within range");
                llOwnerSay("Pos3 is : "+(string)pos3);
            }
        }
    }
}
default{
    touch_start(integer x){
        av();
    }
}

As you can see i have made some attempts already with the pos, pos2, pos3 and have tried a variety of other ideas but i just can not seem to crack this. 

 

Would someone kindly be of help to me?

Posted

Hello,

Why to not use llSensor for this?

Please check this function here:

 Function: llSensor( string name, key id, integer type, float radius, float arc );28 	Function ID0.0 	Forced Delay10.0 	EnergyPerforms a single scan for name and id with type within radius meters and arc radians of forward vector• string 	name 	– 	object or avatar name! 	• key 	id 	– 	group, avatar or object UUID that is in the same region 	• integer 	type 	– 	mask (AGENT, AGENT_BY_LEGACY_NAME, AGENT_BY_USERNAME, ACTIVE, PASSIVE, and/or SCRIPTED) 	• float 	radius 	– 	distance from center [0.0, 96.0m] 	• float 	arc 	– 	the max angle between the local x-axis of the prim and detectable objects, range 0.0 to PI

http://wiki.secondlife.com/wiki/LlSensor

 

Because when you don't use a timer and when the avatars are in range of 96m: you can use this function, it does the job already and you don't need to create a new one...

 

 

Posted

The vector dot product is your friend

  1. Get your position and rotation ( provided your script is in the root of an attachment)
    vector mypos = llGetPos;
    rotation myrot = llGetRot();
  2. Get position of the avatar you test
    It looks like you already have the variable pos
  3. One vector is
    vector avdir = llVecNorm( pos - mypos);
  4. The other vector is
    vector lookdir = llRot2Fwd( myRot);
  5. The vector dot product is
    float dp = avdir * lookdir; // (note that the two vectors avdir and lookdir are unit vectors)

dp lays in the range -1 <= dp <= 1

When dp == 1 you are looking exactly at the avatar and when dp == -1 you look the opposite direction

The angle between avdir and lookdir is
float angle = llAcos( dp);

Use this angle to select avatar

:smileysurprised::):smileyvery-happy:

Posted

@Luxen I am already more than aware of Sensors and how they operate. I have used them regularly in the past. However, i am exploring alternative ways to do this. 

 

@Dora That is a very interesting way to do it. I have been sat here thinking "So i must have to get my position and then my rotation and then somehow extend my field of check X meters infront of the positon of my avatar....but how do i do this exactly". Thank you for the response :)

Posted


D4rkHax wrote:

@Luxen I am already more than aware of Sensors and how they operate. I have used them regularly in the past. However, i am exploring alternative ways to do this.

lol, ok sorry for the mistake then.

Posted

It couldn't be more simple
first note that Acos( 1) == 0° and Acos(-1) == 180°
Acos always is a positive angle in [0,180]°

If you only want to accept avatars within ±5° you could write this code in LSL (LSL uses radians)

if ( RAD_TO_DEG * llAcos( dp) < 5.0 ){ // accept avatar}

dp is the dot product from a previous post

the very same in condensed form:

if ( dp > 0.9962 ){ // accept avatar}

0.9962 equals cos(5°)

:smileysurprised::):smileyvery-happy:

Posted

And just a thing if i can:

vector pos=(vector)llList2String(llGetObjectDetails((key)llList2String(avatars,i),[OBJECT_POS]),0);->(key)llList2String(avatars,i) : it's a key and you take this key with llList2String 
and so llList2String cast this key to a string and after this you cast this string to a key
...After that you cast all of this into a string to cast it after to a vector....

 I say that because it's more complicate after to find an error in a script if we don't simplify our scripts.

Posted

It is just force of habit Lux, i read a long time ago on one the wiki somewhere that whilst we do have llList2Key and llList2Vector. Due to all the data in a list being stored by default as a string it was reccomended to always cast the information back from a string into your chosen data type. So i started using the likes of (vector)llList2String and its just become something that has stuck with me 

Posted

Well, i never saw that. I think that is recommended is to always use the good type: so if the list store a key: to use llList2Key and if it's a string to use llList2String...

But sometimes, i use the cast of these functions and don't care about the type, example: if i want a string and that is a key: so i use, in some cases (not always), llList2String. I never had bugs with that but i think that is not recommended by the wiki.

But i know a thing: more your code is simple and logical: more your code is correct and optimized...

Posted

I agree it will be shorter to

vector pos = llList2Vector( llGetObjectDetails( llList2Key(avatars,i),[OBJECT_POS]),0);

 In this case we know for certain the list element is of type vector so there is no reason to take the detour with getting a string and then cast it. It even saves accuracy not to have a string in between

Also we can get the key directly from the llGetObjectDetails list, no need to get it as a string and then cast to key

:smileysurprised::):smileyvery-happy:

Posted

[Trying to detect avatars 2m in front of me without using a Sensor]

If you need to be extremely precise you can always cast a few rays.

Alternatively if you want to be extremely simply you can just compare the distance of each avatars positon to a point exactly 2 meters directly in front of you.

 

OffsetTestPosition = mypos+<2,0,0>*myrot;

llVecDist(OffsetTestPos,RandomAvatarPos)  will tell you how close they are to the designated point.

You are about to reply to a thread that has been inactive for 3104 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...