Jump to content

Help with collision script to ignore avatars but respond to anything else


Ravenmists
 Share

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

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

Recommended Posts

Hi, im trying to figure out how to correctly use the llDetectedType function so that in a collision event it will ignore avatars but will respond to any other object it collides with. I have tried everything from the sensible to the not so sensible like if(llDetectedType(0)!=AGENT_BY_LEGACY_NAME) or if(llDetectedType(0)!=AGENT_BY_LEGACY_NAME|ACTIVE) or if(llDetectedType(0)!=AGENT_BY_LEGACY_NAME&ACTIVE) of if(!llDetectedType(AGENT_BY_LEGACY_NAME&ACTIVE) etc etc etc.

 

Can anyone provide me with a working example that ignores avatars but responds to anything else on collision?

 

ty ^_^_^_^_^_^_^

Link to comment
Share on other sites

I see a couple potential problems here.

First, there are three collision events. collision_start(), collision_end(), and collision(). They do what they sound like -- collision_start() is triggered when a collision begins, while the item is colliding (eg, pushing against the prim) the collision() event will fire something like every 0.05 seconds (or 0.1-ish probably), and when the colliding object finally goes away collision_end() will fire. You simply mentioned "collision event", so if you're not certain you're using the right one (or combination thereof), you can outline what it is you're making and we can help with that.

Second, you're using a (very useful) shortcut, but which can be dangerous in this case. llDetectedType(0), using a zero, assumes that only one item is colliding. If more than one is colliding, you will only be checking against the first item in the list of colliding items. If you're doing something like a touch_start() event in a HUD, you can almost guarantee only one person will ever be touching it, and can save some effort by using this shortcut. However, in this case you probably don't want to do that.

To find the problem, I recommend outputting some debug information. You can use the following script to see what's actually going on, rather than shooting into the darkness and hoping you hit something. Then use the information to make whatever it is you're trying to make.

// Debug style output for collision events.string returnType(integer i) {    string s;    if (i & AGENT_BY_LEGACY_NAME) {        s += "AGENT ";    }    if (i & ACTIVE) {        s += "ACTIVE ";    }    if (i & PASSIVE) {        s += "PASSIVE ";    }    if (i & SCRIPTED) {        s += "SCRIPTED ";    }    return s;}// Modified LSL library functionstring int2hex(integer iInt, integer iLen) {    string s;    do {        s = llGetSubString("0123456789ABCDEF", iInt & 0x0000000F, iInt & 0x0000000F) + s;        iInt = iInt >> 4;    } while (iLen = ~-iLen);    return s;}default {    collision_start(integer x) {        llOwnerSay((string)llGetTime()+": collision_start("+(string)x+") triggered.");        while (x--) {            integer iType = llDetectedType(x);            string sName = llDetectedName(x);            string s = returnType(iType);            llOwnerSay((string)x+" ("+sName+") is type "+s+" (0x"+int2hex(iType,4)+")");        }    }    collision(integer x) {        llOwnerSay((string)llGetTime()+": collision("+(string)x+") triggered.");        while (x--) {            integer iType = llDetectedType(x);            string sName = llDetectedName(x);            string s = returnType(iType);            llOwnerSay((string)x+" ("+sName+") is type "+s+" (0x"+int2hex(iType,4)+")");        }    }    collision_end(integer x) {        llOwnerSay((string)llGetTime()+": collision_end("+(string)x+") triggered.");        while (x--) {            integer iType = llDetectedType(x);            string sName = llDetectedName(x);            string s = returnType(iType);            llOwnerSay((string)x+" ("+sName+") is type "+s+" (0x"+int2hex(iType,4)+")");        }    }}

Third, and this is probably the actual solution now that I think about it, you're mixing comparison and bitwise operations, but not in the right way.

llDetectedType(0) != (AGENT_BY_LEGACY NAME | ACTIVE) should have worked (for any agent not sitting on something, I think). I'm not sure if the bitwise and (pipe, |) is evaluated before or after the "not equal to" (!=) operator. So when in doubt, add parenthesis. Also add them for readability when it's confusing.

The following would match any avatar collision:

llDetecectedType(0) & AGENT_BY_LEGACY_NAME

Which means this would match any non-avatar collision:

!(llDetecectedType(0) & AGENT_BY_LEGACY_NAME)

For more information on how bitwise operators work, check out the entries near the bottom of the table here: http://wiki.secondlife.com/wiki/LSL_Operators and then check out the last section of the page. Understanding how to build your conditions and how to use flags or masks is important.

Link to comment
Share on other sites

How about this (off the top of my head and untested)?

 

	collision_start(integer total_number)	{		integer i;		do {			if(llDetectedType(i)&AGENT_BY_LEGACY_NAME){				//don't do anything			}			else{				llOwnerSay(llDetectedName(i)+", which is not an agent, collided with me");			}		}		while (++i<total_number);	}

 

  • Like 1
Link to comment
Share on other sites

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

×
×
  • Create New...