/* Boomerang gun 3.0, by Foly http://www.jazz2online.com/snippets/62/boomerang-gun/ */ /***Constants***/ const float cMaxSpeed = 10; //The maximum speed the boomerang can have const float cAcceleration = 0.2; //The acceleration of the boomerang const float cReturnAccMult = 1; //When the boomerang is returning, this is a multiplier for the acceleration (so a value of 2 let's the boomerang return with 2x acceleration) const float cVerSpdMult = 0.7; //When the boomerang is shot vertical and not returning, this is a multiplier for the acceleration (a higher value lets the boomerang go faster and higher upward) const float cReturnSpeed = 0.4; //At what speed the boomerang returns back to the player (WARNING! This constant should always be higher than cAcceleration) const float cReturnRadius = 32; //Radius in pixels at which the player takes the boomerang back /***Variables***/ array returning(32, false); array boomerangfired(32, false); array speed(32, cMaxSpeed); /***Math functions***/ //Calculates the distance between two points float distance(float x1, float y1, float x2, float y2) { return sqrt((x2 - x1)*(x2 - x1) + (y2 - y1)*(y2 - y1)); } //The square root function float sqrt(float x) { float y = 1.0; for (int i = 0; i < 20; i++) y = (y + x/y)/2; return y; } //Determines the absolute value float abs(float x) { if (x < 0) x = -x; return x; } /***Other functions***/ void BoomerangGun(int boomerangID) { int playerID = jjObjects[boomerangID].creator - 32768; if ((abs(jjObjects[boomerangID].xSpeed) < cReturnSpeed && jjObjects[boomerangID].direction != 0) || (abs(jjObjects[boomerangID].ySpeed) < cReturnSpeed && jjObjects[boomerangID].direction == 0) && !returning[playerID]) returning[playerID] = true; if (jjObjects[boomerangID].counter == 1) { if (playerID == p.playerID) p.noFire = true; jjObjects[boomerangID].determineCurAnim(ANIM::TUFBOSS, 3); jjObjects[boomerangID].counterEnd = 254; } if (returning[playerID]) { if (distance(jjPlayers[playerID].xPos, jjPlayers[playerID].yPos, jjObjects[boomerangID].xPos, jjObjects[boomerangID].yPos) < cReturnRadius) jjKillObject(boomerangID); if (speed[playerID] < cMaxSpeed) speed[playerID] = speed[playerID] + cAcceleration*cReturnAccMult; jjObjects[boomerangID].ySpeed = speed[playerID]*(jjPlayers[playerID].yPos - jjObjects[boomerangID].yPos)/distance(jjPlayers[playerID].xPos, jjPlayers[playerID].yPos, jjObjects[boomerangID].xPos, jjObjects[boomerangID].yPos); jjObjects[boomerangID].xSpeed = speed[playerID]*(jjPlayers[playerID].xPos - jjObjects[boomerangID].xPos)/distance(jjPlayers[playerID].xPos, jjPlayers[playerID].yPos, jjObjects[boomerangID].xPos, jjObjects[boomerangID].yPos); } else { if (speed[playerID] > 0) speed[playerID] = speed[playerID] - cAcceleration; if (jjObjects[boomerangID].direction == 0) jjObjects[boomerangID].ySpeed = -speed[playerID]*cVerSpdMult; else jjObjects[boomerangID].xSpeed = speed[playerID]*jjObjects[boomerangID].direction; } if (jjObjects[boomerangID].counter > 200) jjObjects[boomerangID].counter = 30; } /***Gameplay functions***/ void onMain() { for (int i = 0; i < jjObjectCount; i++) if (jjObjects[i].isActive && jjObjects[i].creatorType == CREATOR::PLAYER) { //Maintain boomerang gun if (jjObjects[i].eventID == OBJECT::BLASTERBULLETPU) { BoomerangGun(i); jjObjects[i].animSpeed = 3; boomerangfired[jjObjects[i].creator - 32768] = true; continue; } } for (int i = 0; i < 32; i++) if (!boomerangfired[i]) { speed[i] = cMaxSpeed; returning[i] = false; if (i == p.playerID) p.noFire = false; } else boomerangfired[i] = false; }