string BTN_UP = "▲";
string BTN_ZUP1 = "z +1.0";
string BTN_ZUP01 = "z +0.1";
string BTN_ZDN1 = "z -1.0";
string BTN_ZDN01 = "z -0.1";
list STATES = ["[[ON]]","[OFF]"];
list BRUSHSIZES = ["2x2","4x4","8x8"];
integer brushSize = 0;
list BRUSHTOOLS = ["Level","Raise","Lower","Smooth","Noise","Revert"];
integer brushTool = 0;
list STEPSIZES = ["1","2","4","8","16","32","64"];
integer stepSize = 0;
integer active;
integer moving;
vector scale;
integer menu_handler;
integer menu_channel;
string Float2String(float f) { return llGetSubString((string)f,0,-6); }
string Vector2String(vector v) { return Float2String(v.x)+","+Float2String(v.y)+","+Float2String(v.z); }
Menu(key user,string title,list buttons)
{
menu_channel = (integer)(llFrand(99999.0) * -1);
menu_handler = llListen(menu_channel,"","","");
title += "\nBrush Tool: "+llList2String(BRUSHTOOLS,brushTool);
title += "\nBrush Size: "+llList2String(BRUSHSIZES,brushSize);
title += "\nStep Size: "+llList2String(STEPSIZES,stepSize);
llDialog(user,title,buttons,menu_channel);
}
MainMenu(key user)
{
Menu(user,"MainMenu",["Brush Size","Brush Tool","Step Size",BTN_ZUP01,llList2String(STATES,active),BTN_ZDN01,BTN_ZUP1,"Reset",BTN_ZDN1]);
}
FixPosition()
{
vector pos = llGetPos();
pos.x = llRound(pos.x);
if(pos.x > 255) pos.x = 255; else if(pos.x < 0) pos.x = 0;
pos.y = llRound(pos.y);
if(pos.y > 255) pos.y = 255; else if(pos.y < 0) pos.y = 0;
pos.z = llCeil(pos.z*10);
pos.z /= 10;
llSetPos(pos);
}
default
{
state_entry()
{
scale = <2,2,0.1>;
llSetText("",<0,1,1>,1);
llSetKeyframedMotion([],[KFM_COMMAND, KFM_CMD_STOP]);
llSetTimerEvent(0.0);
llSitTarget(<-0.2, -0.2, 0.7>, ZERO_ROTATION);
llSetCameraEyeOffset(<-10.0, 0.0, 2.0>);
llSetCameraAtOffset(<6.0, 0.0, 2.0>);
vector pos = llGetPos();
pos.z = llGround(<0,0,scale.z/2>);
llSetLinkPrimitiveParamsFast(0,[PRIM_POSITION,pos,
PRIM_ROTATION,ZERO_ROTATION,
PRIM_SIZE,scale,
PRIM_PHYSICS_SHAPE_TYPE, PRIM_PHYSICS_SHAPE_CONVEX,
PRIM_PHANTOM,TRUE]);
FixPosition();
moving = FALSE;
active = FALSE;
llMessageLinked(LINK_THIS,0,"stop","");
}
changed(integer change)
{
if (change & CHANGED_LINK)
{
llSetKeyframedMotion([],[]);
key agent = llAvatarOnSitTarget();
if (agent)
{
llSetKeyframedMotion([],[KFM_COMMAND, KFM_CMD_STOP]);
llSetKeyframedMotion([],[]);
if (agent == llGetOwner())
{
llRequestPermissions(agent,PERMISSION_TAKE_CONTROLS|PERMISSION_TRIGGER_ANIMATION);
}
}
else
{
llSetKeyframedMotion([],[KFM_COMMAND, KFM_CMD_STOP]);
llReleaseControls();
if(llGetPermissions() & PERMISSION_TRIGGER_ANIMATION) llStopAnimation(animation);
llResetScript();
}
}
}
run_time_permissions(integer perm)
{
if(perm & PERMISSION_TRIGGER_ANIMATION)
{
llStopAnimation("sit");
llStartAnimation(llGetInventoryName(INVENTORY_ANIMATION,0));
}
if(perm & PERMISSION_TAKE_CONTROLS)
{
llTakeControls((CONTROL_FWD|CONTROL_BACK|CONTROL_ROT_RIGHT|CONTROL_ROT_LEFT), TRUE, FALSE);
}
}
touch_start(integer num_detected)
{
key toucher = llDetectedKey(0);
if(toucher != llGetOwner()) return;
if(moving) return;
MainMenu(toucher);
}
control(key id, integer level, integer edge)
{
if(level & (CONTROL_FWD|CONTROL_BACK|CONTROL_ROT_RIGHT|CONTROL_ROT_LEFT))
{
if(moving) return;
vector pos = llGetPos();
float step = (float)llList2String(STEPSIZES,stepSize);
float speed = step;
if(active) speed = step; else speed = step/4;
if (level & edge & CONTROL_FWD) { llSetKeyframedMotion([<step,0,0>,speed],[KFM_DATA, KFM_TRANSLATION]); }
else if(level & edge & CONTROL_BACK) { llSetKeyframedMotion([<-step,0,0>,speed],[KFM_DATA, KFM_TRANSLATION]); }
else if(level & edge & CONTROL_ROT_RIGHT) { llSetKeyframedMotion([<0,-step,0>,speed],[KFM_DATA, KFM_TRANSLATION]); }
else if(level & edge & CONTROL_ROT_LEFT) { llSetKeyframedMotion([<0,step,0>,speed],[KFM_DATA, KFM_TRANSLATION]); }
moving = TRUE;
}
}
moving_end()
{
llSetKeyframedMotion([],[KFM_COMMAND, KFM_CMD_STOP]);
moving = FALSE;
FixPosition();
}
listen( integer channel, string name, key id, string message )
{
llListenRemove(menu_handler);
if(message == BTN_UP)
{
MainMenu(id);
}
else if(message == "reset")
{
llResetOtherScript("TF_brush");
llResetScript();
}
else if(message == BTN_ZUP01)
{
vector pos = llGetPos();
if(pos.z > 399.9) return;
pos.z += 0.1;
llSetPos(pos);
FixPosition();
MainMenu(id);
}
else if(message == BTN_ZUP1)
{
vector pos = llGetPos();
if(pos.z > 399) return;
pos.z += 1;
llSetPos(pos);
FixPosition();
MainMenu(id);
}
else if(message == BTN_ZDN01)
{
vector pos = llGetPos();
if(pos.z < 0.1) return;
pos.z -= 0.1;
llSetPos(pos);
FixPosition();
MainMenu(id);
}
else if(message == BTN_ZDN1)
{
vector pos = llGetPos();
if(pos.z < 1.0) return;
pos.z -= 1;
llSetPos(pos);
FixPosition();
MainMenu(id);
}
else if(message == "Brush Size")
{
Menu(id,"BrushSize",BRUSHSIZES+[BTN_UP]);
}
else if(~llListFindList(BRUSHSIZES,[message]))
{
brushSize = llListFindList(BRUSHSIZES,[message]);
if (brushSize == 0) llSetLinkPrimitiveParamsFast(LINK_ROOT,[PRIM_SIZE,<2,2,scale.z>]);
else if (brushSize == 1) llSetLinkPrimitiveParamsFast(LINK_ROOT,[PRIM_SIZE,<4,4,scale.z>]);
else if (brushSize == 2) llSetLinkPrimitiveParamsFast(LINK_ROOT,[PRIM_SIZE,<8,8,scale.z>]);
llMessageLinked(LINK_THIS,brushSize,"brushsize","");
Menu(id,"BrushSize",BRUSHSIZES+[BTN_UP]);
}
else if(message == "Brush Tool")
{
Menu(id,"Brush Tool",BRUSHTOOLS+[BTN_UP]);
}
else if(~llListFindList(BRUSHTOOLS,[message]))
{
brushTool = llListFindList(BRUSHTOOLS,[message]);
llMessageLinked(LINK_THIS,brushTool,"brushtool","");
Menu(id,"Brush Tool",BRUSHTOOLS+[BTN_UP]);
}
else if(message == "Step Size")
{
Menu(id,"Step Size",STEPSIZES+[BTN_UP]);
}
else if(~llListFindList(STEPSIZES,[message]))
{
stepSize = llListFindList(STEPSIZES,[message]);
Menu(id,"Step Size",STEPSIZES+[BTN_UP]);
}
else if(~llListFindList(STATES,[message]))
{
active = llListFindList(STATES,[message]);
active = !active;
if(active) llMessageLinked(LINK_THIS,0,"start",""); else llMessageLinked(LINK_THIS,0,"stop","");
}
}
}