The only flaw I can't iron out is that there seems to be a slight delay on keystrokes for some reason now that I have the state changes working properly.
You can seemlessly go from car to plane and back again with no problem, and all controls work, but from the time you press the key or click the mouse, to the time the vehicle responds - is around.3 to .5 seconds or so.
I don't get it. So without further ado... here it is.
CODE
integer FwdPwr = 20;
float SteerPwr = 4;
integer nos = FALSE;
integer gear = 1;
integer sit = FALSE;
integer brake = TRUE;
float X_THRUST = 20;
float Z_THRUST = 15;
float xMotor;
float zMotor;
key agent;
key pilot;
vector SIT_POS = <0.25, 0.0, 0.65>;
vector CAM_OFFSET = <-10.0, 0.0, 2.0>;
vector CAM_ANG = <0.0, 0.0, 2.0>;
default
{
state_entry()
{
llSetSitText("Ride");
llSitTarget(<0.1, -0.01, -0.15>, ZERO_ROTATION);
llSetCameraEyeOffset(<-5.0, 0.0, 2.0>);
llSetCameraAtOffset(<3.0, 0.0, 2.0>);
state bike;
}
}
state bike
{
state_entry()
{
llSetVehicleFlags(-1);
llSetVehicleType(VEHICLE_TYPE_CAR);
llSetVehicleFlags(VEHICLE_FLAG_LIMIT_ROLL_ONLY);
llSetVehicleFloatParam(VEHICLE_ANGULAR_DEFLECTION_EFFICIENCY, 0.2);
llSetVehicleFloatParam(VEHICLE_LINEAR_DEFLECTION_EFFICIENCY, 0.80);
llSetVehicleFloatParam(VEHICLE_ANGULAR_DEFLECTION_TIMESCALE, 0.10);
llSetVehicleFloatParam(VEHICLE_LINEAR_DEFLECTION_TIMESCALE, 0.10);
llSetVehicleFloatParam(VEHICLE_LINEAR_MOTOR_TIMESCALE, 1.0);
llSetVehicleFloatParam(VEHICLE_LINEAR_MOTOR_DECAY_TIMESCALE, 0.2);
llSetVehicleFloatParam(VEHICLE_ANGULAR_MOTOR_TIMESCALE, 0.1);
llSetVehicleFloatParam(VEHICLE_ANGULAR_MOTOR_DECAY_TIMESCALE, 0.5);
llSetVehicleVectorParam(VEHICLE_LINEAR_FRICTION_TIMESCALE, <1000.0, 2.0, 1000.0>);
llSetVehicleVectorParam(VEHICLE_ANGULAR_FRICTION_TIMESCALE, <10.0, 10.0, 1000.0>);
llSetVehicleFloatParam(VEHICLE_VERTICAL_ATTRACTION_EFFICIENCY, 0.50);
llSetVehicleFloatParam(VEHICLE_VERTICAL_ATTRACTION_TIMESCALE, 0.50);
llSetVehicleFloatParam(VEHICLE_BANKING_EFFICIENCY, 0.99);
llSetVehicleFloatParam(VEHICLE_BANKING_TIMESCALE, 0.01);
}
changed(integer change)
{
if (change & CHANGED_LINK){
key agent = llAvatarOnSitTarget();
if (agent){
if (agent != llGetOwner()){
llSay(0, "You aren't the owner");
llUnSit(agent);
llPushObject(agent, <0,0,100>, ZERO_VECTOR, FALSE);
}
else{
llSetStatus(STATUS_PHYSICS, TRUE);
llCollisionSound("",0.0);
llRequestPermissions(agent, PERMISSION_TRIGGER_ANIMATION | PERMISSION_TAKE_CONTROLS);
}
}
else{
llSetStatus(STATUS_PHYSICS, FALSE);
llReleaseControls();
llStopAnimation("sit");
}
}
}
run_time_permissions(integer perm)
{
if (perm){
llStartAnimation("cruisin");
llTakeControls(CONTROL_FWD | CONTROL_DOWN | CONTROL_UP
| CONTROL_BACK | CONTROL_RIGHT | CONTROL_LEFT
| CONTROL_ROT_RIGHT | CONTROL_ROT_LEFT | CONTROL_LBUTTON, TRUE, FALSE);
}
}
control(key id, integer level, integer edge)
{
vector angular_motor;
if(level & CONTROL_FWD){
llSetVehicleVectorParam(VEHICLE_LINEAR_MOTOR_DIRECTION, <FwdPwr,0,0>);
}
if(level & CONTROL_BACK){
llSetVehicleVectorParam(VEHICLE_LINEAR_MOTOR_DIRECTION, <-10,0,0>);
}
if(level & (CONTROL_ROT_RIGHT)){
angular_motor.x += SteerPwr;
angular_motor.z -= SteerPwr;
}
if(level & (CONTROL_ROT_LEFT)){
angular_motor.x -= SteerPwr;
angular_motor.z += SteerPwr;
}
if(level & (CONTROL_UP)){
angular_motor.y -= 50;
}
if(level & (CONTROL_DOWN)){
angular_motor.y += 50;
}
if(level & (CONTROL_RIGHT)){
if (gear == 1){
FwdPwr = 100;
SteerPwr = 80;
llSleep(.15);
llOwnerSay("Second");
gear = 2;
}
else if (gear == 2){
FwdPwr = 500;
SteerPwr = 100;
llSay(24,"gon");
llSleep(.15);
gear = 3;
}}
if(level & (CONTROL_LEFT)){
if (gear == 3){
FwdPwr = 100;
SteerPwr = 80;
llSay(24,"goff");
// Took these out just in case. Used to inhibit double commands -- llSleep(.15);
llOwnerSay("Second");
gear = 2;
}
else if (gear == 2){
FwdPwr = 20;
SteerPwr = 4;
llOwnerSay("First");
//llSleep(.15);
gear = 1;
}}
if(level & (CONTROL_LBUTTON)){
llSay(666,"gon");
llOwnerSay("Fly");
state plane;
}
llSetVehicleVectorParam(VEHICLE_ANGULAR_MOTOR_DIRECTION, angular_motor);
}
}
state plane
{
state_entry()
{
llCollisionSound("",0.0);
llSetVehicleType(VEHICLE_TYPE_AIRPLANE);
llSetVehicleVectorParam( VEHICLE_LINEAR_FRICTION_TIMESCALE, <200, 20, 20> );
llSetVehicleFloatParam( VEHICLE_ANGULAR_FRICTION_TIMESCALE, 2 );
llSetVehicleVectorParam( VEHICLE_LINEAR_MOTOR_DIRECTION, <0, 0, 0> );
llSetVehicleFloatParam( VEHICLE_LINEAR_MOTOR_TIMESCALE, 2 );
llSetVehicleFloatParam( VEHICLE_LINEAR_MOTOR_DECAY_TIMESCALE, 120 );
llSetVehicleVectorParam( VEHICLE_ANGULAR_MOTOR_DIRECTION, <0, 0, 0> );
llSetVehicleFloatParam( VEHICLE_ANGULAR_MOTOR_TIMESCALE, 0 );
llSetVehicleFloatParam( VEHICLE_ANGULAR_MOTOR_DECAY_TIMESCALE, .4);
llSetVehicleFloatParam( VEHICLE_HOVER_HEIGHT, 2 );
llSetVehicleFloatParam( VEHICLE_HOVER_EFFICIENCY, 0 );
llSetVehicleFloatParam( VEHICLE_HOVER_TIMESCALE, 10000 );
llSetVehicleFloatParam( VEHICLE_BUOYANCY, 0.977 );
llSetVehicleFloatParam( VEHICLE_LINEAR_DEFLECTION_EFFICIENCY, 0 );
llSetVehicleFloatParam( VEHICLE_LINEAR_DEFLECTION_TIMESCALE, 5 );
llSetVehicleFloatParam( VEHICLE_ANGULAR_DEFLECTION_EFFICIENCY, 0);
llSetVehicleFloatParam( VEHICLE_ANGULAR_DEFLECTION_TIMESCALE, 5);
llSetVehicleFloatParam( VEHICLE_VERTICAL_ATTRACTION_EFFICIENCY, 1 );
llSetVehicleFloatParam( VEHICLE_VERTICAL_ATTRACTION_TIMESCALE, 1 );
llSetVehicleFloatParam( VEHICLE_BANKING_EFFICIENCY, 1);
llSetVehicleFloatParam( VEHICLE_BANKING_MIX, .5);
llSetVehicleFloatParam( VEHICLE_BANKING_TIMESCALE, 0.01);
llSetVehicleRotationParam( VEHICLE_REFERENCE_FRAME, <0,0,0,1>);
llRemoveVehicleFlags( VEHICLE_FLAG_NO_DEFLECTION_UP
| VEHICLE_FLAG_HOVER_WATER_ONLY
| VEHICLE_FLAG_LIMIT_ROLL_ONLY
| VEHICLE_FLAG_HOVER_TERRAIN_ONLY
| VEHICLE_FLAG_HOVER_GLOBAL_HEIGHT
| VEHICLE_FLAG_HOVER_UP_ONLY
| VEHICLE_FLAG_LIMIT_MOTOR_UP );
}
control(key id, integer level, integer edge)
{
vector angular_motor;
integer motor_changed;
if ((level & CONTROL_FWD) || (level & CONTROL_BACK)){
if (edge & CONTROL_FWD) xMotor = X_THRUST;
if (edge & CONTROL_BACK) xMotor = -X_THRUST;
}
else{
xMotor = 0;
}
if ((level & CONTROL_UP) || (level & CONTROL_DOWN)){
if (level & CONTROL_UP){
zMotor = Z_THRUST;
}
if (level & CONTROL_DOWN){
zMotor = -Z_THRUST;
}
}
else{
zMotor = 0;
}
llSetVehicleVectorParam(VEHICLE_LINEAR_MOTOR_DIRECTION, <xMotor,0,zMotor>);
if (level & CONTROL_RIGHT){
angular_motor.x = TWO_PI;
angular_motor.y /= 8;
}
if (level & CONTROL_LEFT){
angular_motor.x = -TWO_PI;
angular_motor.y /= 8;
}
if (level & CONTROL_ROT_RIGHT){
angular_motor.x = TWO_PI;
angular_motor.y /= 8;
}
if (level & CONTROL_ROT_LEFT){
angular_motor.x = -TWO_PI;
angular_motor.y /= 8;
}
if(level & (CONTROL_LBUTTON)){
llSay(666,"goff");
llOwnerSay("Drive");
state bike;
}
llSetVehicleVectorParam(VEHICLE_ANGULAR_MOTOR_DIRECTION, angular_motor);
}}
Hopefully it's simple and I'm just to tired to notice, and it's not just too bulky and poorly written
I'm sure it's a combo of both, hopefully not entirely the latter, but feel free to beat me with a virtual coding bat if I've really made a mess of it.Thanks again,
- Hap