int AllowedToFireFlare (void) { if ((xNextFlareFireTime > gameData.time.xGame) && (xNextFlareFireTime < gameData.time.xGame + FLARE_BIG_DELAY)) // In case time is bogus, never wait > 1 second. return 0; if (LOCALPLAYER.energy >= WI_energy_usage (FLARE_ID)) xNextFlareFireTime = gameData.time.xGame + (fix) (gameStates.gameplay.slowmo [0].fSpeed * F1_0 / 4); else xNextFlareFireTime = gameData.time.xGame + (fix) (gameStates.gameplay.slowmo [0].fSpeed * FLARE_BIG_DELAY); return 1; }
void CreateFlare (CObject *objP) { fix xEnergyUsage = WI_energy_usage (FLARE_ID); if (gameStates.app.nDifficultyLevel < 2) xEnergyUsage = FixMul (xEnergyUsage, I2X (gameStates.app.nDifficultyLevel+2)/4); LOCALPLAYER.energy -= xEnergyUsage; if (LOCALPLAYER.energy <= 0) { LOCALPLAYER.energy = 0; } LaserPlayerFire (objP, FLARE_ID, 6, 1, 0, -1); if (IsMultiGame) { gameData.multigame.laser.bFired = 1; gameData.multigame.laser.nGun = FLARE_ADJUST; gameData.multigame.laser.nFlags = 0; gameData.multigame.laser.nLevel = 0; } }
int DrawPolygonObject (CObject *objP, int bDepthSort, int bForce) { fix xLight; int imSave = 0; fix xEngineGlow [2]; //element 0 is for engine glow, 1 for headlight int bBlendPolys = 0; int bBrightPolys = 0; int bGatling = 0; int bCloaked = ObjectIsCloaked (objP); int bEnergyWeapon; int i, id, bOk = 0; if (objP->info.nType == 255) return 0; id = (int) objP->info.nId; if ((id < 0) || (id == 255)) bEnergyWeapon = id = 0; else { #if 0 bGatling = ((objP->info.nType == OBJ_WEAPON) && ((id == VULCAN_ID) || (id == GAUSS_ID))); #endif bEnergyWeapon = (objP->info.nType == OBJ_WEAPON) && gameData.objs.bIsWeapon [id] && !gameData.objs.bIsMissile [id]; } #if SHADOWS if (!bForce && FAST_SHADOWS && !gameOpts->render.shadows.bSoft && (gameStates.render.nShadowPass == 3)) return 1; #endif if (gameStates.render.bBuildModels) xLight = I2X (1); else { xLight = CalcObjectLight (objP, xEngineGlow); if ((bCloaked || bEnergyWeapon) && bDepthSort && (gameStates.render.nShadowPass != 2)) { transparencyRenderer.AddObject (objP); return 1; } if (DrawHiresObject (objP, xLight, xEngineGlow)) return 1; gameStates.render.bBrightObject = bEnergyWeapon; gameOpts->render.bDepthSort = -gameOpts->render.bDepthSort; imSave = gameStates.render.nInterpolationMethod; if (bLinearTMapPolyObjs) gameStates.render.nInterpolationMethod = 1; } if (objP->rType.polyObjInfo.nTexOverride != -1) { #if DBG CPolyModel* pm = gameData.models.polyModels [0] + objP->rType.polyObjInfo.nModel; #endif tBitmapIndex bm = gameData.pig.tex.bmIndex [0][objP->rType.polyObjInfo.nTexOverride], bmiP [MAX_MODEL_TEXTURES]; #if DBG Assert (pm->TextureCount () <= 12); #endif for (i = 0; i < MAX_MODEL_TEXTURES; i++) //fill whole array, in case simple model needs more bmiP [i] = bm; bOk = DrawPolyModel (objP, &objP->info.position.vPos, &objP->info.position.mOrient, reinterpret_cast<CAngleVector*> ( &objP->rType.polyObjInfo.animAngles), objP->rType.polyObjInfo.nModel, objP->rType.polyObjInfo.nSubObjFlags, xLight, xEngineGlow, bmiP, NULL); } else { if (bCloaked) { if (objP->info.nType == OBJ_PLAYER) bOk = DrawCloakedObject (objP, xLight, xEngineGlow, gameData.multiplayer.players [id].cloakTime, gameData.multiplayer.players [id].cloakTime + CLOAK_TIME_MAX); else if (objP->info.nType == OBJ_ROBOT) { if (!ROBOTINFO (id).bossFlag) bOk = DrawCloakedObject (objP, xLight, xEngineGlow, gameData.time.xGame - I2X (10), gameData.time.xGame + I2X (10)); else if (0 <= (i = gameData.bosses.Find (objP->Index ()))) bOk = DrawCloakedObject (objP, xLight, xEngineGlow, gameData.bosses [i].m_nCloakStartTime, gameData.bosses [i].m_nCloakEndTime); } } else { tBitmapIndex *bmiAltTex = (objP->rType.polyObjInfo.nAltTextures > 0) ? mpTextureIndex [objP->rType.polyObjInfo.nAltTextures - 1] : NULL; // Snipers get bright when they fire. if (!gameStates.render.bBuildModels) { if ((objP->info.nType == OBJ_ROBOT) && (gameData.ai.localInfo [objP->Index ()].nextPrimaryFire < I2X (1) / 8) && (objP->cType.aiInfo.behavior == AIB_SNIPE)) xLight = 2 * xLight + I2X (1); bBlendPolys = bEnergyWeapon && (gameData.weapons.info [id].nInnerModel > -1); bBrightPolys = bGatling || (bBlendPolys && WI_energy_usage (id)); if (bEnergyWeapon) { if (gameOpts->legacy.bRender) gameStates.render.grAlpha = GrAlpha (FADE_LEVELS - 2); else ogl.BlendFunc (GL_ONE, GL_ONE); } if (bBlendPolys) { #if 0 fix xDistToEye = CFixVector::Dist(gameData.objs.viewerP->info.position.vPos, objP->info.position.vPos); if (xDistToEye < gameData.models.nSimpleModelThresholdScale * I2X (2)) #endif bOk = DrawPolyModel (objP, &objP->info.position.vPos, &objP->info.position.mOrient, objP->rType.polyObjInfo.animAngles, gameData.weapons.info [id].nInnerModel, objP->rType.polyObjInfo.nSubObjFlags, bBrightPolys ? I2X (1) : xLight, xEngineGlow, bmiAltTex, NULL); } if (bEnergyWeapon) gameStates.render.grAlpha = GrAlpha (4 * FADE_LEVELS / 5); else if (!bBlendPolys) gameStates.render.grAlpha = 1.0f; } bOk = DrawPolyModel (objP, &objP->info.position.vPos, &objP->info.position.mOrient, objP->rType.polyObjInfo.animAngles, objP->rType.polyObjInfo.nModel, objP->rType.polyObjInfo.nSubObjFlags, (bGatling || bBrightPolys) ? I2X (1) : xLight, xEngineGlow, bmiAltTex, (bGatling || bEnergyWeapon) ? gameData.weapons.color + id : NULL); if (!gameStates.render.bBuildModels) { if (!gameOpts->legacy.bRender) ogl.BlendFunc (GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); gameStates.render.grAlpha = 1.0f; } } } if (!gameStates.render.bBuildModels) { gameStates.render.nInterpolationMethod = imSave; gameStates.render.bBrightObject = 0; gameOpts->render.bDepthSort = -gameOpts->render.bDepthSort; } return bOk; }
// ------------------------------------------------------------------------------------ // Return: // Bits set: // HAS_WEAPON_FLAG // HAS_ENERGY_FLAG // HAS_AMMO_FLAG // See weapon[HA] for bit values int PlayerHasWeapon (int nWeapon, int bSecondary, int nPlayer, int bAll) { int returnValue = 0; int nWeaponIndex; tPlayer *playerP = gameData.multiplayer.players + ((nPlayer < 0) ? gameData.multiplayer.nLocalPlayer : nPlayer); // Hack! If energy goes negative, you can't fire a weapon that doesn't require energy. // But energy should not go negative (but it does), so find out why it does! if (gameStates.app.bD1Mission && (nWeapon >= SUPER_WEAPON)) return 0; if (playerP->energy < 0) playerP->energy = 0; if (!bSecondary) { nWeaponIndex = primaryWeaponToWeaponInfo [nWeapon]; if (nWeapon == SUPER_LASER_INDEX) { if ((playerP->primaryWeaponFlags & (1 << LASER_INDEX)) && (bAll || (playerP->laserLevel > MAX_LASER_LEVEL))) returnValue |= HAS_WEAPON_FLAG; } else if (nWeapon == LASER_INDEX) { if ((playerP->primaryWeaponFlags & (1 << LASER_INDEX)) && (bAll || (playerP->laserLevel <= MAX_LASER_LEVEL))) returnValue |= HAS_WEAPON_FLAG; } else if (nWeapon == SPREADFIRE_INDEX) { if ((playerP->primaryWeaponFlags & (1 << nWeapon)) && (bAll || !(extraGameInfo [0].bSmartWeaponSwitch && (playerP->primaryWeaponFlags & (1 << HELIX_INDEX))))) returnValue |= HAS_WEAPON_FLAG; } else if (nWeapon == VULCAN_INDEX) { if ((playerP->primaryWeaponFlags & (1 << nWeapon)) && (bAll || !(extraGameInfo [0].bSmartWeaponSwitch && (playerP->primaryWeaponFlags & (1 << GAUSS_INDEX))))) returnValue |= HAS_WEAPON_FLAG; } else { if (playerP->primaryWeaponFlags & (1 << nWeapon)) returnValue |= HAS_WEAPON_FLAG; } // Special case: Gauss cannon uses vulcan ammo. if (nWeapon == GAUSS_INDEX) { if (WI_ammo_usage (nWeaponIndex) <= playerP->primaryAmmo [VULCAN_INDEX]) returnValue |= HAS_AMMO_FLAG; } else if (WI_ammo_usage (nWeaponIndex) <= playerP->primaryAmmo [nWeapon]) returnValue |= HAS_AMMO_FLAG; if (nWeapon == OMEGA_INDEX) { // Hack: Make sure tPlayer has energy to omega if (playerP->energy || gameData.omega.xCharge) returnValue |= HAS_ENERGY_FLAG; } else { /* if (nWeapon == SUPER_LASER_INDEX) { if (playerP->energy || gameData.omega.xCharge) returnValue |= HAS_ENERGY_FLAG; } */ if (WI_energy_usage (nWeaponIndex) <= playerP->energy) returnValue |= HAS_ENERGY_FLAG; } } else { nWeaponIndex = secondaryWeaponToWeaponInfo [nWeapon]; if (playerP->secondaryWeaponFlags & (1 << nWeapon)) returnValue |= HAS_WEAPON_FLAG; if (WI_ammo_usage (nWeaponIndex) <= playerP->secondaryAmmo [nWeapon]) returnValue |= HAS_AMMO_FLAG; if (WI_energy_usage(nWeaponIndex) <= playerP->energy) returnValue |= HAS_ENERGY_FLAG; } return returnValue; }
int LocalPlayerFireGun (void) { CPlayerData* playerP = gameData.multiplayer.players + gameData.multiplayer.nLocalPlayer; fix xEnergyUsed; int nAmmoUsed, nPrimaryAmmo; int nWeaponIndex; int rVal = 0; int nRoundsPerShot = 1; int bGatling = (gameData.weapons.nPrimary == GAUSS_INDEX) ? 2 : (gameData.weapons.nPrimary == VULCAN_INDEX) ? 1 : 0; fix addval; static int nSpreadfireToggle = 0; static int nHelixOrient = 0; if (gameStates.app.bPlayerIsDead) return 0; if (gameStates.app.bD2XLevel && (SEGMENTS [OBJECTS [playerP->nObject].info.nSegment].m_nType == SEGMENT_IS_NODAMAGE)) return 0; nWeaponIndex = primaryWeaponToWeaponInfo [gameData.weapons.nPrimary]; xEnergyUsed = WI_energy_usage (nWeaponIndex); if (gameData.weapons.nPrimary == OMEGA_INDEX) xEnergyUsed = 0; // Omega consumes energy when recharging, not when firing. if (gameStates.app.nDifficultyLevel < 2) xEnergyUsed = FixMul (xEnergyUsed, I2X (gameStates.app.nDifficultyLevel + 2) / 4); // MK, 01/26/96, Helix use 2x energy in multiplayer. bitmaps.tbl parm should have been reduced for single player. if (nWeaponIndex == HELIX_INDEX) if (IsMultiGame) xEnergyUsed *= 2; nAmmoUsed = WI_ammo_usage (nWeaponIndex); addval = 2 * gameData.time.xFrame; if (addval > I2X (1)) addval = I2X (1); if (!bGatling) nPrimaryAmmo = playerP->primaryAmmo [gameData.weapons.nPrimary]; else { if ((gameOpts->sound.bHires [0] == 2) && gameOpts->sound.bGatling && gameStates.app.bHaveExtraGameInfo [IsMultiGame] && EGI_FLAG (bGatlingSpeedUp, 1, 0, 0) && (gameData.weapons.firing [0].nDuration < GATLING_DELAY)) return 0; nPrimaryAmmo = playerP->primaryAmmo [VULCAN_INDEX]; } if ((playerP->energy < xEnergyUsed) || (nPrimaryAmmo < nAmmoUsed)) AutoSelectWeapon (0, 1); // Make sure the CPlayerData can fire from this weapon. if ((gameData.laser.xLastFiredTime + 2 * gameData.time.xFrame < gameData.time.xGame) || (gameData.time.xGame < gameData.laser.xLastFiredTime)) gameData.laser.xNextFireTime = gameData.time.xGame; gameData.laser.xLastFiredTime = gameData.time.xGame; while (gameData.laser.xNextFireTime <= gameData.time.xGame) { if ((playerP->energy >= xEnergyUsed) && (nPrimaryAmmo >= nAmmoUsed)) { int nLaserLevel, flags = 0; if (gameStates.app.cheats.bLaserRapidFire == 0xBADA55) gameData.laser.xNextFireTime += I2X (1) / 25; else gameData.laser.xNextFireTime += WI_fire_wait (nWeaponIndex); nLaserLevel = LOCALPLAYER.laserLevel; if (gameData.weapons.nPrimary == SPREADFIRE_INDEX) { if (nSpreadfireToggle) flags |= LASER_SPREADFIRE_TOGGLED; nSpreadfireToggle = !nSpreadfireToggle; } if (gameData.weapons.nPrimary == HELIX_INDEX) { nHelixOrient++; flags |= ((nHelixOrient & LASER_HELIX_MASK) << LASER_HELIX_SHIFT); } if (LOCALPLAYER.flags & PLAYER_FLAGS_QUAD_LASERS) flags |= LASER_QUAD; #if 1 int fired = FireWeapon ((short) LOCALPLAYER.nObject, (ubyte) gameData.weapons.nPrimary, nLaserLevel, flags, nRoundsPerShot); if (fired) { rVal += fired; if (bGatling) { if (nAmmoUsed > playerP->primaryAmmo [VULCAN_INDEX]) nAmmoUsed = playerP->primaryAmmo [VULCAN_INDEX]; playerP->primaryAmmo [VULCAN_INDEX] -= nAmmoUsed; gameData.multiplayer.weaponStates [gameData.multiplayer.nLocalPlayer].nAmmoUsed += nAmmoUsed; if (gameData.multiplayer.weaponStates [gameData.multiplayer.nLocalPlayer].nAmmoUsed >= VULCAN_AMMO_AMOUNT) { if (gameStates.app.bHaveExtraGameInfo [IsMultiGame]) MaybeDropNetPowerup (-1, POW_VULCAN_AMMO, FORCE_DROP); gameData.multiplayer.weaponStates [gameData.multiplayer.nLocalPlayer].nAmmoUsed -= VULCAN_AMMO_AMOUNT; } MultiSendAmmo (); } else { playerP->energy -= (xEnergyUsed * fired) / gameData.weapons.info [nWeaponIndex].fireCount; if (playerP->energy < 0) playerP->energy = 0; } } #else rVal += FireWeapon ((short) LOCALPLAYER.nObject, (ubyte) gameData.weapons.nPrimary, nLaserLevel, flags, nRoundsPerShot); playerP->energy -= (xEnergyUsed * rVal) / gameData.weapons.info [nWeaponIndex].fireCount; if (playerP->energy < 0) playerP->energy = 0; if (rVal && ((gameData.weapons.nPrimary == VULCAN_INDEX) || (gameData.weapons.nPrimary == GAUSS_INDEX))) { if (nAmmoUsed > playerP->primaryAmmo [VULCAN_INDEX]) playerP->primaryAmmo [VULCAN_INDEX] = 0; else playerP->primaryAmmo [VULCAN_INDEX] -= nAmmoUsed; } #endif AutoSelectWeapon (0, 1); // Make sure the CPlayerData can fire from this weapon. } else { AutoSelectWeapon (0, 1); // Make sure the CPlayerData can fire from this weapon. StopPrimaryFire (); break; // Couldn't fire weapon, so abort. } } gameData.laser.nGlobalFiringCount = 0; return rVal; }