void CClientWeaponMgr::ToggleHolster( bool bPlayDeselect ) { bPlayDeselect = bPlayDeselect && WeaponsEnabled(); // [kml] 3/26/02 Sanity check because we entered a world // without a current weapon if( m_pCurrentWeapon ) { // when bPlayDeselect == FALSE, ToggleHolster will force // the weapon to change without the deselect animation if ( g_pWeaponDB->GetUnarmedRecord( ) == m_pCurrentWeapon->GetWeaponRecord() ) { // the current weapon is the default, get out the holstered weapon ChangeWeapon( m_hHolsterWeapon, NULL, -1, sk_bPlaySelect, bPlayDeselect ); m_hHolsterWeapon = NULL; } else { // put the current weapon away and switch to the default m_hHolsterWeapon = m_pCurrentWeapon->GetWeaponRecord(); // Can only do this if a holster weapon was specified in weapons.txt. if( g_pWeaponDB->GetUnarmedRecord( )) { ChangeWeapon( g_pWeaponDB->GetUnarmedRecord( ), NULL, -1, sk_bPlaySelect, bPlayDeselect ); } } } }
//----------------------------------------------------------------------------- // Called when something collides with the object. //----------------------------------------------------------------------------- void PlayerObject::CollisionOccurred( SceneObject *object, unsigned long collisionStamp ) { // Ignore collisions if the player is dying (or dead) if( m_dying == true ) return; // Allow the base scene object to register the collision. SceneObject::CollisionOccurred( object, collisionStamp ); // Check if the player has hit a spawner object. if( object->GetType() != TYPE_SPAWNER_OBJECT ) return; // Get a pointer to the spawner object. SpawnerObject *spawner = (SpawnerObject*)object; // Check if the player has picked up a weapon. if( *spawner->GetObjectScript()->GetNumberData( "type" ) == WEAPON_SPAWN_OBJECT ) { // Get the list position of the weapon. char listPosition = (char)*spawner->GetObjectScript()->GetNumberData( "list_position" ); // Ensure the player doesn't already have a weapon in this slot. if( m_weapons[listPosition] == NULL ) { // Load the new weapon in. m_weapons[listPosition] = new Weapon( spawner->GetObjectScript(), m_viewWeaponOffset ); // Check if this is the local player. if( m_dpnid == g_engine->GetNetwork()->GetLocalID() ) { // Set the weapon to use the first person mesh. m_weapons[listPosition]->UseViewWeapon( true ); // Change to this weapon. ChangeWeapon( 0, listPosition ); } else { // Set the weapon to use the first person mesh. m_weapons[listPosition]->UseViewWeapon( false ); } } else if( m_weapons[listPosition]->GetValid() == false ) { // Validate the weapon. m_weapons[listPosition]->SetValid( true ); // Change to this weapon. ChangeWeapon( 0, listPosition ); } } }
void CClientWeaponMgr::ChangeToNextRealWeapon() { // If we're supposed to hide the weapon when it is empty // (i.e., it doesn't make sense to see it) then we don't // want to play the deselect animation... if (!m_pCurrentWeapon) return; HWEAPON hCurWeapon = m_pCurrentWeapon->GetWeaponRecord(); if( !hCurWeapon ) return; HWEAPONDATA hWpnData = g_pWeaponDB->GetWeaponData(hCurWeapon, !USE_AI_DATA); bool bCanDeselect = !g_pWeaponDB->GetBool( hWpnData, WDB_WEAPON_bHideWhenEmpty ); // Find the next available weapon on the weapon selection list... CUserProfile *pProfile = g_pProfileMgr->GetCurrentProfile(); int32 nNumPriorities = ( int32 )pProfile->m_vecWeapons.size(); for( int32 nWeapon = ( nNumPriorities - 1 ); nWeapon >= 0; --nWeapon ) { HWEAPON hWeapon = pProfile->m_vecWeapons[nWeapon]; if( hWeapon ) { uint8 nWeaponIndex = g_pWeaponDB->GetPlayerWeaponIndex( hWeapon ); if( CWM_NO_WEAPON != nWeaponIndex ) { HWEAPONDATA hWpnData = g_pWeaponDB->GetWeaponData(hWeapon, !USE_AI_DATA); HWEAPON hDualWeapon = g_pWeaponDB->GetRecordLink( hWpnData, WDB_WEAPON_rDualWeapon ); if( hDualWeapon && ( g_pPlayerStats->HaveWeapon( hDualWeapon ) ) && // have the weapon ( m_apClientWeapon[ nWeaponIndex ]->HasAmmo() ) ) // weapon has ammo { ChangeWeapon( hDualWeapon, NULL, -1, sk_bPlaySelect, bCanDeselect); return; } else if ( ( g_pPlayerStats->HaveWeapon( hWeapon ) ) && // have the weapon ( m_apClientWeapon[ nWeaponIndex ]->HasAmmo() ) ) // weapon has ammo { ChangeWeapon( hWeapon, NULL, -1, sk_bPlaySelect, bCanDeselect); return; } } } } //couldn't find any regular weapons... go to melee ChangeWeapon( g_pWeaponDB->GetUnarmedRecord( ), NULL, -1, sk_bPlaySelect, bCanDeselect); }
/* * Called by ClientBeginServerFrame and ClientThink */ void Think_Weapon(edict_t *ent) { if (!ent) { return; } /* if just died, put the weapon away */ if (ent->health < 1) { ent->client->newweapon = NULL; ChangeWeapon(ent); } /* call active weapon think routine */ if (ent->client->pers.weapon && ent->client->pers.weapon->weaponthink) { is_quad = (ent->client->quad_framenum > level.framenum); is_quadfire = (ent->client->quadfire_framenum > level.framenum); if (ent->client->silencer_shots) { is_silenced = MZ_SILENCED; } else { is_silenced = 0; } ent->client->pers.weapon->weaponthink(ent); } }
/* ================= Think_Weapon Called by ClientBeginServerFrame and ClientThink ================= */ void Think_Weapon (edict_t *ent) { // Make sure ent exists! if (!G_EntExists(ent)) return; // if just died, put the weapon away if (ent->health < 1) { ent->client->newweapon = NULL; ChangeWeapon (ent); } // call active weapon think routine if (ent->client->pers.weapon && ent->client->pers.weapon->weaponthink) { is_quad = (ent->client->quad_framenum > level.framenum); //RAV is_strength = rune_has_rune(ent, RUNE_STRENGTH); // if (ent->client->silencer_shots) is_silenced = MZ_SILENCED; else is_silenced = 0; ent->client->pers.weapon->weaponthink (ent); } }
bool CClientWeaponMgr::OnCommandOn( int nCmd ) { if (COMMAND_ID_HOLSTER == nCmd) { ToggleHolster(true); return true; } if( (COMMAND_ID_WEAPON_BASE <= nCmd) && (nCmd <= COMMAND_ID_WEAPON_MAX) ) { uint8 nIndex = nCmd - COMMAND_ID_WEAPON_BASE; HWEAPON hWeapon = g_pPlayerStats->GetWeaponInSlot(nIndex); return ChangeWeapon( hWeapon ); } if( (COMMAND_ID_GRENADE_BASE <= nCmd) && (nCmd <= COMMAND_ID_GRENADE_MAX) ) { uint8 nIndex = nCmd - COMMAND_ID_GRENADE_BASE; //get grenade for this slot HWEAPON hGrenade = g_pWeaponDB->GetPlayerGrenade(nIndex); if (hGrenade) { g_pPlayerStats->UpdatePlayerGrenade( hGrenade, true ); } } return false; }
void G_NPCMunroMatchPlayerWeapon( gentity_t *ent ) { //special uber hack for cinematic Munro's to match player's weapon if ( !in_camera ) { if ( ent && ent->client && ent->NPC && (ent->NPC->aiFlags&NPCAI_MATCHPLAYERWEAPON) ) {//we're a Munro NPC int newWeap; if ( g_entities[0].client->ps.weapon == WP_PHASER || g_entities[0].client->ps.weapon > WP_DREADNOUGHT )//WP_VOYAGER_HYPO { newWeap = WP_COMPRESSION_RIFLE; } else { newWeap = g_entities[0].client->ps.weapon; } if ( newWeap != WP_NONE && ent->client->ps.weapon != newWeap ) { ent->client->ps.stats[STAT_WEAPONS] = ( 1 << newWeap ); ent->client->ps.ammo[weaponData[newWeap].ammoIndex] = 999; ChangeWeapon( ent, newWeap ); ent->client->ps.weapon = newWeap; ent->client->ps.weaponstate = WEAPON_READY; } } } }
void Unit::PickupWeapon( Weapon* Instance ) { // Pick up the weapon and change // to it gSecondaryWeapon = Instance; ChangeWeapon(); }
void Bot::LookAround() { CheckIsInThinkFrame(__FUNCTION__); TestClosePlace(); RegisterVisibleEnemies(); if (!botBrain.combatTask.Empty()) ChangeWeapon(botBrain.combatTask); }
void CClientWeaponMgr::HandleMsgWeaponChange (ILTMessage_Read *pMsg) { if( !pMsg ) return; HWEAPON hWeapon = pMsg->ReadDatabaseRecord( g_pLTDatabase, g_pWeaponDB->GetWeaponsCategory() ); bool bForce = pMsg->Readbool(); bool bPlaySelect = pMsg->Readbool(); bool bPlayDeselect = pMsg->Readbool(); HAMMO hAmmo = pMsg->ReadDatabaseRecord( g_pLTDatabase, g_pWeaponDB->GetAmmoCategory() ); // const char* pszName = g_pLTDatabase->GetRecordName(hWeapon); if( !hWeapon ) return; bool bChange = bForce; if (!bForce) { if (IsMultiplayerGameClient()) bChange = GetConsoleBool( "MPAutoWeaponSwitch",true ); else bChange = GetConsoleBool( "SPAutoWeaponSwitch",true ); } // See what ammo the weapon should start with... HWEAPONDATA hWpnData = g_pWeaponDB->GetWeaponData(hWeapon, !USE_AI_DATA); if (g_pWeaponDB->GetBool(hWpnData,WDB_WEAPON_bIsGrenade)) return; HAMMO hDefaultAmmo = g_pWeaponDB->GetRecordLink( hWpnData, WDB_WEAPON_rAmmoName ); if( hAmmo ) { hDefaultAmmo = hAmmo; } if( bChange ) { // Force a change to the appropriate weapon... if( g_pPlayerStats ) { //if we're forcing a weapon change, do not honor any old weapon requests if (!bPlaySelect) { m_hRequestedWeapon = NULL; m_hRequestedAmmo = NULL; } ChangeWeapon(hWeapon, hDefaultAmmo, g_pPlayerStats->GetAmmoCount( hDefaultAmmo ), bPlaySelect, bPlayDeselect); } } }
bool CClientWeaponMgr::SetDefaultWeapon( HWEAPON hWeapon ) { if( !g_pWeaponDB->IsPlayerWeapon( hWeapon )) return false; m_hDefaultWeapon = hWeapon; if (NULL == GetCurrentClientWeapon()) ChangeWeapon(m_hDefaultWeapon); return true; }
void FPSPlayerComponent::_OnKeyDown(const OIS::KeyEvent& event) { switch(event.key) { case OIS::KC_1: ChangeWeapon(0); break; case OIS::KC_2: ChangeWeapon(1); break; case OIS::KC_3: ChangeWeapon(2); break; case OIS::KC_4: ChangeWeapon(3); break; case OIS::KC_5: ChangeWeapon(4); break; case OIS::KC_6: ChangeWeapon(5); break; case OIS::KC_7: ChangeWeapon(6); break; case OIS::KC_8: ChangeWeapon(7); break; case OIS::KC_9: ChangeWeapon(8); break; case OIS::KC_G: if(mWeaponInUse != nullptr) RemoveWeapon(mWeaponInUse->GetType()); break; case OIS::KC_R: if(mWeaponInUse != nullptr) mWeaponInUse->Reload(); break; case OIS::KC_E: mGrabber->Check(); break; default: return; } }
void CClientWeaponMgr::LastWeapon() { if (!WeaponsEnabled()) return; uint8 nWeaponIndex = g_pWeaponDB->GetPlayerWeaponIndex( m_hLastWeapon ); if( CWM_NO_WEAPON != nWeaponIndex ) { if ( ( g_pPlayerStats->HaveWeapon( m_hLastWeapon ) ) && // have the weapon ( m_apClientWeapon[ nWeaponIndex ]->HasAmmo() ) ) // weapon has ammo { ChangeWeapon( m_hLastWeapon, NULL, -1 ); } } }
WeaponState CClientWeaponMgr::Update( LTRotation const &rRot, LTVector const &vPos ) { if ( ( CWM_NO_WEAPON == m_nCurClientWeaponIndex ) && ( m_pCurrentWeapon ) ) { // the weapon is out of sync with itself, check calling order ASSERT( 0 ); } // update the current weapon WeaponState eWeaponState = W_IDLE; if ( m_pCurrentWeapon ) { // Set the weapon that the player is using so the PlayerBody plays the correct animations... CPlayerBodyMgr::Instance( ).SetAnimProp( kAPG_Weapon, m_pCurrentWeapon->GetAnimationProperty() ); m_pCurrentWeapon->SetCameraInfo( rRot, vPos ); eWeaponState = m_pCurrentWeapon->Update( ); } // Check to see if we should auto-switch to a new weapon... if ( W_AUTO_SWITCH == eWeaponState ) { AutoSelectWeapon(); } // if we received a request to change the weapon during // the update, do it now if( (CWM_NO_WEAPON == m_nCurClientWeaponIndex) || CPlayerBodyMgr::Instance( ).IsPlayingSpecial( )) { // no current weapon, see if we are trying to change // to another weapon if( m_hRequestedWeapon ) { // select the requested weapon ChangeWeapon( m_hRequestedWeapon, m_hRequestedAmmo, -1, sk_bPlaySelect, !sk_bPlayDeselect ); m_hRequestedWeapon = NULL; m_hRequestedAmmo = NULL; } } // update the state of specialty weapons (forensics) UpdateCustomWeapon(); return eWeaponState; }
/* ================= Think_Weapon Called by ClientBeginServerFrame and ClientThink ================= */ void Think_Weapon(edict_t * ent) { // if just died, put the weapon away if (ent->health < 1) { ent->client->newweapon = NULL; ChangeWeapon(ent); } // call active weapon think routine if (ent->client->pers.weapon && ent->client->pers.weapon->weaponthink) { is_quad = (ent->client->quad_framenum > level.framenum); if (ent->client->silencer_shots) is_silenced = MZ_SILENCED; else is_silenced = 0; ent->client->pers.weapon->weaponthink(ent); } }
/* * Called by ClientBeginServerFrame and ClientThink */ void Think_Weapon(edict_t *ent) { if (!ent) { return; } /* if just died, put the weapon away */ if (ent->health < 1) { ent->client->newweapon = NULL; ChangeWeapon(ent); } /* call active weapon think routine */ if (ent->client->pers.weapon && ent->client->pers.weapon->weaponthink) { ent->client->pers.weapon->weaponthink(ent); } }
void CClientWeaponMgr::AutoSelectWeapon() { // [KLS 4/25/02] First see if we can just change ammo types... if (m_pCurrentWeapon) { // Get the best new ammo type HAMMO hNewAmmo = m_pCurrentWeapon->GetBestAvailableAmmo( ); if( hNewAmmo ) { m_pCurrentWeapon->ChangeAmmoWithReload( hNewAmmo ); return; } // Okay, need to change, find the next weapon ChangeToNextRealWeapon(); } else { // No current weapon so find the best... HWEAPON hBestWeapon = NULL; uint8 nNumPlayerWeapons = g_pWeaponDB->GetNumPlayerWeapons( ); for( uint8 nPlayerWeaponIndex = 0; nPlayerWeaponIndex < nNumPlayerWeapons; ++nPlayerWeaponIndex ) { HWEAPON hCurWeapon = g_pWeaponDB->GetPlayerWeapon( nPlayerWeaponIndex ); HWEAPONDATA hWpnData = g_pWeaponDB->GetWeaponData(hCurWeapon, !USE_AI_DATA); HWEAPON hDualWeapon = g_pWeaponDB->GetRecordLink( hWpnData, WDB_WEAPON_rDualWeapon ); if( hDualWeapon && g_pPlayerStats->HaveWeapon( hDualWeapon ) && g_pWeaponDB->IsBetterWeapon( hDualWeapon, hBestWeapon )) { hBestWeapon = hDualWeapon; } else if( g_pPlayerStats->HaveWeapon( hCurWeapon ) && g_pWeaponDB->IsBetterWeapon( hCurWeapon, hBestWeapon )) hBestWeapon = hCurWeapon; } if( hBestWeapon ) ChangeWeapon( hBestWeapon ); } }
void CClientWeaponMgr::OnPlayerAlive() { EnableWeapons(); if( m_hRequestedWeapon ) { // select the requested weapon immediately ChangeWeapon( m_hRequestedWeapon, m_hRequestedAmmo, -1, !sk_bPlaySelect, !sk_bPlayDeselect ); m_hRequestedWeapon = NULL; m_hRequestedAmmo = NULL; } if( m_pCurrentWeapon ) m_pCurrentWeapon->ClearFiring(); }
//ZOID void Weapon_Generic (edict_t *ent, int FRAME_ACTIVATE_LAST, int FRAME_FIRE_LAST, int FRAME_IDLE_LAST, int FRAME_DEACTIVATE_LAST, int *pause_frames, int *fire_frames, void (*fire)(edict_t *ent)) { int oldstate; // Make sure ent exists! if (!G_EntExists(ent)) return; if( ent->client->pers.pl_state < 1 || ent->client->resp.spectator ||(ctf->value && ent->client->resp.ctf_team < 1)) return; if (ent->client->newweapon) { ChangeWeapon(ent); return; } oldstate = ent->client->weaponstate; Weapon_Generic2 (ent, FRAME_ACTIVATE_LAST, FRAME_FIRE_LAST, FRAME_IDLE_LAST, FRAME_DEACTIVATE_LAST, pause_frames, fire_frames, fire); // run the weapon frame again if hasted if (stricmp(ent->client->pers.weapon->pickup_name, "Grapple") == 0 && ent->client->weaponstate == WEAPON_FIRING) return; if ((CTFApplyHaste(ent) || (Q_stricmp(ent->client->pers.weapon->pickup_name, "Grapple") == 0 && ent->client->weaponstate != WEAPON_FIRING)) && oldstate == ent->client->weaponstate) { Weapon_Generic2 (ent, FRAME_ACTIVATE_LAST, FRAME_FIRE_LAST, FRAME_IDLE_LAST, FRAME_DEACTIVATE_LAST, pause_frames, fire_frames, fire); } if (rune_has_rune(ent, RUNE_HASTE)) { Weapon_Generic2 (ent, FRAME_ACTIVATE_LAST, FRAME_FIRE_LAST, FRAME_IDLE_LAST, FRAME_DEACTIVATE_LAST, pause_frames, fire_frames, fire); } }
/* ================= Think_Weapon Called by ClientBeginServerFrame and ClientThink ================= */ void Think_Weapon (edict_t *ent) { // if just died, put the weapon away if (ent->health < 1) { ent->client->newweapon = NULL; ChangeWeapon (ent); } // don't run weapons at all during timeout, preserve reload frame etc if (tdm_match_status == MM_TIMEOUT) return; //r1: don't allow any attack during countdown if (tdm_match_status == MM_COUNTDOWN) { ent->client->buttons &= ~BUTTON_ATTACK; ent->client->latched_buttons &= ~BUTTON_ATTACK; } // variable FPS support if (ent->client->next_weapon_think > level.framenum) return; ent->client->next_weapon_think = level.framenum + (SECS_TO_FRAMES(0.1f)); // call active weapon think routine if (ent->client->weapon && ent->client->weapon->weaponthink) { if (ent->client->quad_framenum > level.framenum) is_quad = ent; else is_quad = NULL; if (ent->client->silencer_shots) is_silenced = MZ_SILENCED; else is_silenced = 0; ent->client->weapon->weaponthink (ent); } }
void Weapon_Grenade (edict_t *ent) { if ((ent->client->newweapon) && (ent->client->weaponstate == WEAPON_READY)) { ChangeWeapon (ent); return; } if (ent->client->weaponstate == WEAPON_ACTIVATING) { ent->client->weaponstate = WEAPON_READY; ent->client->ps.gunframe = 16; return; } if (ent->client->weaponstate == WEAPON_READY) { if ( ((ent->client->latched_buttons|ent->client->buttons) & BUTTON_ATTACK) ) { ent->client->latched_buttons &= ~BUTTON_ATTACK; if (ent->client->pers.inventory[ent->client->ammo_index]) { ent->client->ps.gunframe = 1; ent->client->weaponstate = WEAPON_FIRING; ent->client->grenade_time = 0; } else { if (level.time >= ent->pain_debounce_time) { gi.sound(ent, CHAN_VOICE, gi.soundindex("weapons/noammo.wav"), 1, ATTN_NORM, 0); ent->pain_debounce_time = level.time + 1; } NoAmmoWeaponChange (ent); } return; } if ((ent->client->ps.gunframe == 29) || (ent->client->ps.gunframe == 34) || (ent->client->ps.gunframe == 39) || (ent->client->ps.gunframe == 48)) { if (rand()&15) return; } if (++ent->client->ps.gunframe > 48) ent->client->ps.gunframe = 16; return; } if (ent->client->weaponstate == WEAPON_FIRING) { if (ent->client->ps.gunframe == 5) gi.sound(ent, CHAN_WEAPON, gi.soundindex("weapons/hgrena1b.wav"), 1, ATTN_NORM, 0); if (ent->client->ps.gunframe == 11) { if (!ent->client->grenade_time) { ent->client->grenade_time = level.time + GRENADE_TIMER + 0.2; ent->client->weapon_sound = gi.soundindex("weapons/hgrenc1b.wav"); } // they waited too long, detonate it in their hand if (!ent->client->grenade_blew_up && level.time >= ent->client->grenade_time) { ent->client->weapon_sound = 0; weapon_grenade_fire (ent, true); ent->client->grenade_blew_up = true; } if (ent->client->buttons & BUTTON_ATTACK) return; if (ent->client->grenade_blew_up) { if (level.time >= ent->client->grenade_time) { ent->client->ps.gunframe = 15; ent->client->grenade_blew_up = false; } else { return; } } } if (ent->client->ps.gunframe == 12) { ent->client->weapon_sound = 0; weapon_grenade_fire (ent, false); } if ((ent->client->ps.gunframe == 15) && (level.time < ent->client->grenade_time)) return; ent->client->ps.gunframe++; if (ent->client->ps.gunframe == 16) { ent->client->grenade_time = 0; ent->client->weaponstate = WEAPON_READY; } } }
static void Weapon_Generic2 (edict_t *ent, int FRAME_ACTIVATE_LAST, int FRAME_FIRE_LAST, int FRAME_IDLE_LAST, int FRAME_DEACTIVATE_LAST, int *pause_frames, int *fire_frames, void (*fire)(edict_t *ent)) { int n; if(ent->deadflag || ent->s.modelindex != 255) // VWep animations screw up corpses { return; } if (ent->client->weaponstate == WEAPON_DROPPING) { if (ent->client->ps.gunframe == FRAME_DEACTIVATE_LAST) { ChangeWeapon (ent); return; } else if ((FRAME_DEACTIVATE_LAST - ent->client->ps.gunframe) == 4) { ent->client->anim_priority = ANIM_REVERSE; if(ent->client->ps.pmove.pm_flags & PMF_DUCKED) { ent->s.frame = FRAME_crpain4+1; ent->client->anim_end = FRAME_crpain1; } else { ent->s.frame = FRAME_pain304+1; ent->client->anim_end = FRAME_pain301; } } ent->client->ps.gunframe++; return; } if (ent->client->weaponstate == WEAPON_ACTIVATING) { if (ent->client->ps.gunframe == FRAME_ACTIVATE_LAST || instantweap->value) { ent->client->weaponstate = WEAPON_READY; ent->client->ps.gunframe = FRAME_IDLE_FIRST; return; } ent->client->ps.gunframe++; return; } if ((ent->client->newweapon) && (ent->client->weaponstate != WEAPON_FIRING)) { ent->client->weaponstate = WEAPON_DROPPING; if (instantweap->value) { ChangeWeapon(ent); return; } else ent->client->ps.gunframe = FRAME_DEACTIVATE_FIRST; if ((FRAME_DEACTIVATE_LAST - FRAME_DEACTIVATE_FIRST) < 4) { ent->client->anim_priority = ANIM_REVERSE; if(ent->client->ps.pmove.pm_flags & PMF_DUCKED) { ent->s.frame = FRAME_crpain4+1; ent->client->anim_end = FRAME_crpain1; } else { ent->s.frame = FRAME_pain304+1; ent->client->anim_end = FRAME_pain301; } } return; } if (ent->client->weaponstate == WEAPON_READY) { if ( ((ent->client->latched_buttons|ent->client->buttons) & BUTTON_ATTACK) ) { ent->client->latched_buttons &= ~BUTTON_ATTACK; if ((!ent->client->ammo_index) || ( ent->client->pers.inventory[ent->client->ammo_index] >= ent->client->pers.weapon->quantity)) { ent->client->ps.gunframe = FRAME_FIRE_FIRST; ent->client->weaponstate = WEAPON_FIRING; // start the animation ent->client->anim_priority = ANIM_ATTACK; if (ent->client->ps.pmove.pm_flags & PMF_DUCKED) { ent->s.frame = FRAME_crattak1-1; ent->client->anim_end = FRAME_crattak9; } else { ent->s.frame = FRAME_attack1-1; ent->client->anim_end = FRAME_attack8; } } else { if (level.time >= ent->pain_debounce_time) { gi.sound(ent, CHAN_VOICE, gi.soundindex("weapons/noammo.wav"), 1, ATTN_NORM, 0); ent->pain_debounce_time = level.time + 1; } NoAmmoWeaponChange (ent); } } else { if (ent->client->ps.gunframe == FRAME_IDLE_LAST) { ent->client->ps.gunframe = FRAME_IDLE_FIRST; return; } if (pause_frames) { for (n = 0; pause_frames[n]; n++) { if (ent->client->ps.gunframe == pause_frames[n]) { if (rand()&15) return; } } } ent->client->ps.gunframe++; return; } } if (ent->client->weaponstate == WEAPON_FIRING) { for (n = 0; fire_frames[n]; n++) { if (ent->client->ps.gunframe == fire_frames[n]) { //ZOID if (!CTFApplyStrengthSound(ent)) //ZOID if (ent->client->quad_framenum > level.framenum) gi.sound(ent, CHAN_ITEM, gi.soundindex("items/damage3.wav"), 1, ATTN_NORM, 0); //ZOID CTFApplyHasteSound(ent); //ZOID fire (ent); break; } } if (!fire_frames[n]) ent->client->ps.gunframe++; if (ent->client->ps.gunframe == FRAME_IDLE_FIRST+1) ent->client->weaponstate = WEAPON_READY; } }
/////////////////////////////////////////////////////////////////////// // Modified version of id's code /////////////////////////////////////////////////////////////////////// void ACESP_PutClientInServer(edict_t *bot, qboolean respawn, int team) { vec3_t mins = {-16, -16, -24}; vec3_t maxs = {16, 16, 32}; int index; vec3_t spawn_origin, spawn_angles; gclient_t *client; client_persistant_t saved; client_respawn_t resp; char *s; int spawn_style; int spawn_health; // find a spawn point // do it before setting health back up, so farthest // ranging doesn't count this client SelectSpawnPoint (bot, spawn_origin, spawn_angles, &spawn_style, &spawn_health); index = bot-g_edicts-1; client = bot->client; // deathmatch wipes most client data every spawn if (deathmatch->value) { char userinfo[MAX_INFO_STRING]; resp = bot->client->resp; memcpy (userinfo, client->pers.userinfo, sizeof(userinfo)); InitClientPersistant (client, spawn_style); ClientUserinfoChanged (bot, userinfo); } else memset(&resp, 0, sizeof(resp)); // clear everything but the persistant data saved = client->pers; memset(client, 0, sizeof(*client)); client->pers = saved; client->resp = resp; // copy some data from the client to the entity FetchClientEntData (bot); // clear entity values bot->groundentity = NULL; bot->client = &game.clients[index]; bot->takedamage = DAMAGE_AIM; bot->movetype = MOVETYPE_WALK; bot->viewheight = 24; bot->classname = "bot"; bot->mass = 200; bot->solid = SOLID_BBOX; bot->deadflag = DEAD_NO; bot->air_finished = level.time + 12; bot->clipmask = MASK_PLAYERSOLID; bot->model = "players/male/tris.md2"; bot->pain = player_pain; bot->die = player_die; bot->waterlevel = 0; bot->watertype = 0; bot->flags &= ~FL_NO_KNOCKBACK; bot->svflags &= ~SVF_DEADMONSTER; bot->is_jumping = false; if (ctf->value) { client->resp.ctf_team = team; client->resp.ctf_state = CTF_STATE_START; s = Info_ValueForKey(client->pers.userinfo, "skin"); CTFAssignSkin(bot, s); } VectorCopy(mins, bot->mins); VectorCopy(maxs, bot->maxs); VectorClear(bot->velocity); // clear playerstate values memset(&bot->client->ps, 0, sizeof(client->ps)); client->ps.pmove.origin[0] = spawn_origin[0]*8; client->ps.pmove.origin[1] = spawn_origin[1]*8; client->ps.pmove.origin[2] = spawn_origin[2]*8; //ZOID client->ps.pmove.pm_flags &= ~PMF_NO_PREDICTION; //ZOID if (deathmatch->value && ((int)dmflags->value & DF_FIXED_FOV)) { client->ps.fov = 90; } else { client->ps.fov = atoi(Info_ValueForKey(client->pers.userinfo, "fov")); if (client->ps.fov < 1) client->ps.fov = 90; else if (client->ps.fov > 160) client->ps.fov = 160; } // Knightmare- fix for null model? if (client->pers.weapon && client->pers.weapon->view_model) client->ps.gunindex = gi.modelindex(client->pers.weapon->view_model); // clear entity state values bot->s.effects = 0; bot->s.skinnum = bot - g_edicts - 1; bot->s.modelindex = MAX_MODELS-1; // will use the skin specified model bot->s.modelindex2 = MAX_MODELS-1; // custom gun model bot->s.frame = 0; VectorCopy(spawn_origin, bot->s.origin); bot->s.origin[2] += 1; // make sure off ground // set the delta angle for (int i = 0; i < 3; i++) client->ps.pmove.delta_angles[i] = ANGLE2SHORT(spawn_angles[i] - client->resp.cmd_angles[i]); bot->s.angles[PITCH] = 0; bot->s.angles[YAW] = spawn_angles[YAW]; bot->s.angles[ROLL] = 0; VectorCopy(bot->s.angles, client->ps.viewangles); VectorCopy(bot->s.angles, client->v_angle); // force the current weapon up client->newweapon = client->pers.weapon; ChangeWeapon (bot); bot->enemy = NULL; bot->movetarget = NULL; bot->state = STATE_MOVE; // Set the current node bot->current_node = ACEND_FindClosestReachableNode(bot,NODE_DENSITY, NODE_ALL); bot->goal_node = bot->current_node; bot->next_node = bot->current_node; bot->next_move_time = level.time; bot->suicide_timeout = level.time + 15.0; // If we are not respawning hold off for up to three seconds before releasing into game if (!respawn) { bot->think = ACESP_HoldSpawn; //bot->nextthink = level.time + 0.1; //mxd bot->nextthink = level.time + random()*3.0f; // up to three seconds } else { if (!KillBox(bot)) { // could't spawn in? } gi.linkentity(bot); bot->think = ACEAI_Think; bot->nextthink = level.time + FRAMETIME; // send effect gi.WriteByte(svc_muzzleflash); gi.WriteShort(bot-g_edicts); gi.WriteByte(MZ_LOGIN); gi.multicast(bot->s.origin, MULTICAST_PVS); } }
/* =========== PutClientInServer Called when a player connects to a server or respawns in a deathmatch. ============ */ void PutClientInServer (edict_t *ent) { vec3_t mins = {-16, -16, -24}; vec3_t maxs = {16, 16, 32}; int index; vec3_t spawn_origin, spawn_angles; gclient_t *client; int i; client_persistant_t saved; client_respawn_t resp; // find a spawn point // do it before setting health back up, so farthest // ranging doesn't count this client SelectSpawnPoint (ent, spawn_origin, spawn_angles); index = ent-g_edicts-1; client = ent->client; // deathmatch wipes most client data every spawn if (deathmatch->value) { char userinfo[MAX_INFO_STRING]; resp = client->resp; memcpy (userinfo, client->pers.userinfo, sizeof(userinfo)); InitClientPersistant (client); ClientUserinfoChanged (ent, userinfo); } else if (coop->value) { int n; char userinfo[MAX_INFO_STRING]; resp = client->resp; memcpy (userinfo, client->pers.userinfo, sizeof(userinfo)); // this is kind of ugly, but it's how we want to handle keys in coop for (n = 0; n < MAX_ITEMS; n++) { if (itemlist[n].flags & IT_KEY) resp.coop_respawn.inventory[n] = client->pers.inventory[n]; } client->pers = resp.coop_respawn; ClientUserinfoChanged (ent, userinfo); if (resp.score > client->pers.score) client->pers.score = resp.score; } else { memset (&resp, 0, sizeof(resp)); } // clear everything but the persistant data saved = client->pers; memset (client, 0, sizeof(*client)); client->pers = saved; if (client->pers.health <= 0) InitClientPersistant(client); else if (Q_stricmp(level.mapname, "zboss") == 0) { char userinfo[MAX_INFO_STRING]; int health = client->pers.health; memcpy (userinfo, client->pers.userinfo, sizeof(userinfo)); InitClientPersistant(client); ClientUserinfoChanged (ent, userinfo); client->pers.health = health; } client->resp = resp; // copy some data from the client to the entity FetchClientEntData (ent); // clear entity values ent->groundentity = NULL; ent->client = &game.clients[index]; ent->takedamage = DAMAGE_AIM; ent->movetype = MOVETYPE_WALK; ent->viewheight = 22; ent->inuse = true; ent->classname = "player"; ent->mass = 200; ent->solid = SOLID_BBOX; ent->deadflag = DEAD_NO; ent->air_finished = level.time + 12; ent->clipmask = MASK_PLAYERSOLID; ent->model = "players/male/tris.md2"; ent->pain = player_pain; ent->die = player_die; ent->waterlevel = 0; ent->watertype = 0; ent->flags &= ~FL_NO_KNOCKBACK; ent->svflags &= ~SVF_DEADMONSTER; #ifdef WITH_ACEBOT // ACEBOT_ADD ent->is_bot = false; ent->last_node = -1; ent->is_jumping = false; // ACEBOT_END #endif VectorCopy (mins, ent->mins); VectorCopy (maxs, ent->maxs); VectorClear (ent->velocity); // clear playerstate values memset (&ent->client->ps, 0, sizeof(client->ps)); client->ps.pmove.origin[0] = spawn_origin[0]*8; client->ps.pmove.origin[1] = spawn_origin[1]*8; client->ps.pmove.origin[2] = spawn_origin[2]*8; if (deathmatch->value && ((int)dmflags->value & DF_FIXED_FOV)) { client->ps.fov = 90; } else { client->ps.fov = atoi(Info_ValueForKey(client->pers.userinfo, "fov")); if (client->ps.fov < 1) client->ps.fov = 90; else if (client->ps.fov > 160) client->ps.fov = 160; } client->ps.gunindex = gi.modelindex(client->pers.weapon->view_model); // clear entity state values ent->s.effects = 0; ent->s.skinnum = ent - g_edicts - 1; ent->s.modelindex = 255; // will use the skin specified model ent->s.modelindex2 = 255; // custom gun model ent->s.frame = 0; #ifdef WITH_ACEBOT //botchat> ent->last_insult = level.time; ent->last_taunt = level.time; ent->last_chat = level.time; //<botchat #endif VectorCopy (spawn_origin, ent->s.origin); ent->s.origin[2] += 1; // make sure off ground VectorCopy (ent->s.origin, ent->s.old_origin); // set the delta angle for (i=0 ; i<3 ; i++) client->ps.pmove.delta_angles[i] = ANGLE2SHORT(spawn_angles[i] - client->resp.cmd_angles[i]); ent->s.angles[PITCH] = 0; ent->s.angles[YAW] = spawn_angles[YAW]; ent->s.angles[ROLL] = 0; VectorCopy (ent->s.angles, client->ps.viewangles); VectorCopy (ent->s.angles, client->v_angle); if (!KillBox (ent)) { // could't spawn in? } gi.linkentity (ent); // force the current weapon up client->newweapon = client->pers.weapon; ChangeWeapon (ent); }
void Weapon_Grenade (edict_t *ent) { if ((ent->client->newweapon) && (ent->client->weaponstate == WEAPON_READY)) { ChangeWeapon (ent); return; } if (ent->client->weaponstate == WEAPON_ACTIVATING) { ent->client->weaponstate = WEAPON_READY; ent->client->ps.gunframe = 16; return; } if (ent->client->weaponstate == WEAPON_READY) { if ( ((ent->client->latched_buttons|ent->client->buttons) & BUTTON_ATTACK) ) { ent->client->latched_buttons &= ~BUTTON_ATTACK; if (ent->client->inventory[ent->client->ammo_index]) { ent->client->ps.gunframe = 1; ent->client->weaponstate = WEAPON_FIRING; ent->client->grenade_framenum = 0; } else { if (level.framenum >= ent->pain_debounce_framenum) { gi.sound(ent, CHAN_VOICE, gi.soundindex("weapons/noammo.wav"), 1, ATTN_NORM, 0); ent->pain_debounce_framenum = level.framenum + SECS_TO_FRAMES(1); } NoAmmoWeaponChange (ent); } return; } if ((ent->client->ps.gunframe == 29) || (ent->client->ps.gunframe == 34) || (ent->client->ps.gunframe == 39) || (ent->client->ps.gunframe == 48)) { if (genrand_int32()&15) return; } if (++ent->client->ps.gunframe > 48) ent->client->ps.gunframe = 16; return; } if (ent->client->weaponstate == WEAPON_FIRING) { if (ent->client->ps.gunframe == 5) gi.sound(ent, CHAN_WEAPON, gi.soundindex("weapons/hgrena1b.wav"), 1, ATTN_NORM, 0); if (ent->client->ps.gunframe == 11) { if (!ent->client->grenade_framenum) { ent->client->grenade_framenum = level.framenum + SECS_TO_FRAMES(GRENADE_TIMER + 0.2f); ent->client->weapon_sound = gi.soundindex("weapons/hgrenc1b.wav"); } // they waited too long, detonate it in their hand if (ent->client->grenade_state != GRENADE_BLEW_UP && level.framenum >= ent->client->grenade_framenum) { ent->client->weapon_sound = 0; weapon_grenade_fire (ent, true); ent->client->grenade_state = GRENADE_BLEW_UP; } if (ent->client->buttons & BUTTON_ATTACK) return; if (ent->client->grenade_state == GRENADE_BLEW_UP) { if (level.framenum >= ent->client->grenade_framenum) { ent->client->ps.gunframe = 15; ent->client->grenade_state = GRENADE_NONE; } else { return; } } } if (ent->client->ps.gunframe == 12) { ent->client->weapon_sound = 0; weapon_grenade_fire (ent, false); ent->client->grenade_state = GRENADE_THROWN; } if ((ent->client->ps.gunframe == 15) && (level.framenum < ent->client->grenade_framenum)) return; ent->client->ps.gunframe++; if (ent->client->ps.gunframe == 16) { ent->client->grenade_framenum = 0; ent->client->grenade_state = GRENADE_NONE; ent->client->weaponstate = WEAPON_READY; } } }
void ExitEmplacedWeapon( gentity_t *ent ) { // requesting to unlock from the weapon // We'll leave the gun pointed in the direction it was last facing, though we'll cut out the pitch if ( ent->client ) { // if we are the player we will have put down a brush that blocks NPCs so that we have a clear spot to get back out. //gentity_t *place = G_Find( NULL, FOFS(classname), "emp_placeholder" ); if ( ent->health > 0 ) {//he's still alive, and we have a placeholder, so put him back if ( ent->owner->nextTrain ) { // reset the players position VectorCopy( ent->owner->nextTrain->currentOrigin, ent->client->ps.origin ); //reset ent's size to normal VectorCopy( ent->owner->nextTrain->mins, ent->mins ); VectorCopy( ent->owner->nextTrain->maxs, ent->maxs ); //free the placeholder G_FreeEntity( ent->owner->nextTrain ); //re-link the ent gi.linkentity( ent ); } else if ( ent->owner->e_UseFunc == useF_eweb_use )//yeah, crappy way to check this, but... { // so give 'em a push away from us vec3_t backDir, start, end; trace_t trace; gentity_t *eweb = ent->owner; float curRadius = 0.0f; float minRadius, maxRadius; qboolean safeExit = qfalse; VectorSubtract( ent->currentOrigin, eweb->currentOrigin, backDir ); backDir[2] = 0; minRadius = VectorNormalize( backDir )-8.0f; maxRadius = (ent->maxs[0]+ent->maxs[1])*0.5f; maxRadius += (eweb->maxs[0]+eweb->maxs[1])*0.5f; maxRadius *= 1.5f; if ( minRadius >= maxRadius - 1.0f ) { maxRadius = minRadius + 8.0f; } ent->owner = NULL;//so his trace hits me for ( curRadius = minRadius; curRadius <= maxRadius; curRadius += 4.0f ) { VectorMA( ent->currentOrigin, curRadius, backDir, start ); //make sure they're not in the ground VectorCopy( start, end ); start[2] += 18; end[2] -= 18; gi.trace(&trace, start, ent->mins, ent->maxs, end, ent->s.number, ent->clipmask, (EG2_Collision)0, 0); if ( !trace.allsolid && !trace.startsolid ) { G_SetOrigin( ent, trace.endpos ); gi.linkentity( ent ); safeExit = qtrue; break; } } //Hmm... otherwise, don't allow them to get off? ent->owner = eweb; if ( !safeExit ) {//don't try again for a second ent->owner->delay = level.time + 500; return; } } } else if ( ent->health <= 0 ) { // dead, so give 'em a push out of the chair vec3_t dir; AngleVectors( ent->owner->s.angles, NULL, dir, NULL ); if ( rand() & 1 ) { VectorScale( dir, -1, dir ); } VectorMA( ent->client->ps.velocity, 75, dir, ent->client->ps.velocity ); } //don't let them move towards me for a couple frames so they don't step back into me while I'm becoming solid to them if ( ent->s.number < MAX_CLIENTS ) { if ( ent->client->ps.pm_time < 100 ) { ent->client->ps.pm_time = 100; } ent->client->ps.pm_flags |= (PMF_TIME_NOFRICTION|PMF_TIME_KNOCKBACK); } if ( !ent->owner->bounceCount ) {//not an EWeb - the overridden bone angles will remember the angle we left it at VectorCopy( ent->client->ps.viewangles, ent->owner->s.angles ); ent->owner->s.angles[PITCH] = 0; G_SetAngles( ent->owner, ent->owner->s.angles ); VectorCopy( ent->owner->s.angles, ent->owner->pos1 ); } } // Remove the emplaced gun from our inventory ent->client->ps.stats[STAT_WEAPONS] &= ~( 1 << WP_EMPLACED_GUN ); extern void ChangeWeapon( gentity_t *ent, int newWeapon ); extern void CG_ChangeWeapon( int num ); if ( ent->health <= 0 ) {//when die, don't set weapon back on when ejected from emplaced/eweb //empty hands ent->client->ps.weapon = WP_NONE; if ( ent->NPC ) { ChangeWeapon( ent, ent->client->ps.weapon ); // should be OK actually. } else { CG_ChangeWeapon( ent->client->ps.weapon ); } if ( ent->s.number < MAX_CLIENTS ) { gi.cvar_set( "cg_thirdperson", "1" ); } } else { // when we lock or unlock from the the gun, we get our old weapon back ent->client->ps.weapon = ent->owner->s.weapon; if ( ent->NPC ) {//BTW, if a saber-using NPC ever gets off of an emplaced gun/eweb, this will not work, look at NPC_ChangeWeapon for the proper way ChangeWeapon( ent, ent->client->ps.weapon ); } else { G_RemoveWeaponModels( ent ); CG_ChangeWeapon( ent->client->ps.weapon ); if ( ent->client->ps.weapon == WP_SABER ) { WP_SaberAddG2SaberModels( ent ); } else { G_CreateG2AttachedWeaponModel( ent, weaponData[ent->client->ps.weapon].weaponMdl, ent->handRBolt, 0 ); } if ( ent->s.number < MAX_CLIENTS ) { if ( ent->client->ps.weapon == WP_SABER ) { gi.cvar_set( "cg_thirdperson", "1" ); } else if ( ent->client->ps.weapon != WP_SABER && cg_gunAutoFirst.integer ) { gi.cvar_set( "cg_thirdperson", "0" ); } } } if ( ent->client->ps.weapon == WP_SABER ) { if ( ent->owner->alt_fire ) { ent->client->ps.SaberActivate(); } else { ent->client->ps.SaberDeactivate(); } } } //set the emplaced gun/eweb's weapon back to the emplaced gun ent->owner->s.weapon = WP_EMPLACED_GUN; // gi.G2API_DetachG2Model( &ent->ghoul2[ent->playerModel] ); ent->s.eFlags &= ~EF_LOCKED_TO_WEAPON; ent->client->ps.eFlags &= ~EF_LOCKED_TO_WEAPON; ent->owner->noDamageTeam = TEAM_FREE; ent->owner->svFlags &= ~SVF_NONNPC_ENEMY; ent->owner->delay = level.time; ent->owner->activator = NULL; if ( !ent->NPC ) { // by keeping the owner, a dead npc can be pushed out of the chair without colliding with it ent->owner = NULL; } }
//---------------------------------------------------------- void emplaced_gun_use( gentity_t *self, gentity_t *other, gentity_t *activator ) { vec3_t fwd1, fwd2; if ( self->health <= 0 ) { // can't use a dead gun. return; } if ( self->svFlags & SVF_INACTIVE ) { return; // can't use inactive gun } if ( !activator->client ) { return; // only a client can use it. } if ( self->activator ) { // someone is already in the gun. return; } if ( other && other->client && G_IsRidingVehicle( other ) ) {//can't use eweb when on a vehicle return; } if ( activator && activator->client && G_IsRidingVehicle( activator ) ) {//can't use eweb when on a vehicle return; } // We'll just let the designers duke this one out....I mean, as to whether they even want to limit such a thing. if ( self->spawnflags & EMPLACED_FACING ) { // Let's get some direction vectors for the users AngleVectors( activator->client->ps.viewangles, fwd1, NULL, NULL ); // Get the guns direction vector AngleVectors( self->pos1, fwd2, NULL, NULL ); float dot = DotProduct( fwd1, fwd2 ); // Must be reasonably facing the way the gun points ( 90 degrees or so ), otherwise we don't allow to use it. if ( dot < 0.0f ) { return; } } // don't allow using it again for half a second if ( self->delay + 500 < level.time ) { int oldWeapon = activator->s.weapon; if ( oldWeapon == WP_SABER ) { self->alt_fire = activator->client->ps.SaberActive(); } // swap the users weapon with the emplaced gun and add the ammo the gun has to the player activator->client->ps.weapon = self->s.weapon; Add_Ammo( activator, WP_EMPLACED_GUN, self->count ); activator->client->ps.stats[STAT_WEAPONS] |= ( 1 << WP_EMPLACED_GUN ); // Allow us to point from one to the other activator->owner = self; // kind of dumb, but when we are locked to the weapon, we are owned by it. self->activator = activator; G_RemoveWeaponModels( activator ); extern void ChangeWeapon( gentity_t *ent, int newWeapon ); if ( activator->NPC ) { ChangeWeapon( activator, WP_EMPLACED_GUN ); } else if ( activator->s.number == 0 ) { // we don't want for it to draw the weapon select stuff cg.weaponSelect = WP_EMPLACED_GUN; CG_CenterPrint( "@SP_INGAME_EXIT_VIEW", SCREEN_HEIGHT * 0.95 ); } // Since we move the activator inside of the gun, we reserve a solid spot where they were standing in order to be able to get back out without being in solid if ( self->nextTrain ) {//you never know G_FreeEntity( self->nextTrain ); } self->nextTrain = G_Spawn(); //self->nextTrain->classname = "emp_placeholder"; self->nextTrain->contents = CONTENTS_MONSTERCLIP|CONTENTS_PLAYERCLIP;//hmm... playerclip too now that we're doing it for NPCs? G_SetOrigin( self->nextTrain, activator->client->ps.origin ); VectorCopy( activator->mins, self->nextTrain->mins ); VectorCopy( activator->maxs, self->nextTrain->maxs ); gi.linkentity( self->nextTrain ); //need to inflate the activator's mins/maxs since the gunsit anim puts them outside of their bbox VectorSet( activator->mins, -24, -24, -24 ); VectorSet( activator->maxs, 24, 24, 40 ); // Move the activator into the center of the gun. For NPC's the only way the can get out of the gun is to die. VectorCopy( self->s.origin, activator->client->ps.origin ); activator->client->ps.origin[2] += 30; // move them up so they aren't standing in the floor gi.linkentity( activator ); // the gun will track which weapon we used to have self->s.weapon = oldWeapon; // Lock the player activator->client->ps.eFlags |= EF_LOCKED_TO_WEAPON; activator->owner = self; // kind of dumb, but when we are locked to the weapon, we are owned by it. self->activator = activator; self->delay = level.time; // can't disconnect from the thing for half a second // Let the gun be considered an enemy //Ugh, so much AI code seems to assume enemies are clients, maybe this shouldn't be on, but it's too late in the game to change it now without knowing what side-effects this will have self->svFlags |= SVF_NONNPC_ENEMY; self->noDamageTeam = activator->client->playerTeam; // FIXME: don't do this, we'll try and actually put the player in this beast // move the player to the center of the gun // activator->contents = 0; // VectorCopy( self->currentOrigin, activator->client->ps.origin ); SetClientViewAngle( activator, self->pos1 ); //FIXME: should really wait a bit after spawn and get this just once? self->waypoint = NAV::GetNearestNode(self); #ifdef _DEBUG if ( self->waypoint == -1 ) { gi.Printf( S_COLOR_RED"ERROR: no waypoint for emplaced_gun %s at %s\n", self->targetname, vtos(self->currentOrigin) ); } #endif G_Sound( self, G_SoundIndex( "sound/weapons/emplaced/emplaced_mount.mp3" )); if ( !(self->spawnflags&EMPLACED_PLAYERUSE) || activator->s.number == 0 ) {//player-only usescript or any usescript // Run use script G_ActivateBehavior( self, BSET_USE ); } } }
void eweb_use( gentity_t *self, gentity_t *other, gentity_t *activator ) { if ( !eweb_can_be_used( self, other, activator ) ) { return; } int oldWeapon = activator->s.weapon; if ( oldWeapon == WP_SABER ) { self->alt_fire = activator->client->ps.SaberActive(); } // swap the users weapon with the emplaced gun and add the ammo the gun has to the player activator->client->ps.weapon = self->s.weapon; Add_Ammo( activator, WP_EMPLACED_GUN, self->count ); activator->client->ps.stats[STAT_WEAPONS] |= ( 1 << WP_EMPLACED_GUN ); // Allow us to point from one to the other activator->owner = self; // kind of dumb, but when we are locked to the weapon, we are owned by it. self->activator = activator; G_RemoveWeaponModels( activator ); extern void ChangeWeapon( gentity_t *ent, int newWeapon ); if ( activator->NPC ) { ChangeWeapon( activator, WP_EMPLACED_GUN ); } else if ( activator->s.number == 0 ) { // we don't want for it to draw the weapon select stuff cg.weaponSelect = WP_EMPLACED_GUN; CG_CenterPrint( "@SP_INGAME_EXIT_VIEW", SCREEN_HEIGHT * 0.95 ); } VectorCopy( activator->currentOrigin, self->pos4 );//keep this around so we know when to make them play the strafe anim // the gun will track which weapon we used to have self->s.weapon = oldWeapon; // Lock the player activator->client->ps.eFlags |= EF_LOCKED_TO_WEAPON; activator->owner = self; // kind of dumb, but when we are locked to the weapon, we are owned by it. self->activator = activator; self->delay = level.time; // can't disconnect from the thing for half a second // Let the gun be considered an enemy //Ugh, so much AI code seems to assume enemies are clients, maybe this shouldn't be on, but it's too late in the game to change it now without knowing what side-effects this will have self->svFlags |= SVF_NONNPC_ENEMY; self->noDamageTeam = activator->client->playerTeam; //FIXME: should really wait a bit after spawn and get this just once? self->waypoint = NAV::GetNearestNode(self); #ifdef _DEBUG if ( self->waypoint == -1 ) { gi.Printf( S_COLOR_RED"ERROR: no waypoint for emplaced_gun %s at %s\n", self->targetname, vtos(self->currentOrigin) ); } #endif G_Sound( self, G_SoundIndex( "sound/weapons/eweb/eweb_mount.mp3" )); if ( !(self->spawnflags&EMPLACED_PLAYERUSE) || activator->s.number == 0 ) {//player-only usescript or any usescript // Run use script G_ActivateBehavior( self, BSET_USE ); } }
void Weapon_Generic (edict_t *ent, int FRAME_ACTIVATE_LAST, int FRAME_FIRE_LAST, int FRAME_IDLE_LAST, int FRAME_DEACTIVATE_LAST, int *pause_frames, int *fire_frames, void (*fire)(edict_t *ent)) { int n; if (ent->client->weaponstate == WEAPON_DROPPING) { if (ent->client->ps.gunframe == FRAME_DEACTIVATE_LAST) { ChangeWeapon (ent); return; } ent->client->ps.gunframe++; return; } if (ent->client->weaponstate == WEAPON_ACTIVATING) { if (ent->client->ps.gunframe == FRAME_ACTIVATE_LAST) { ent->client->weaponstate = WEAPON_READY; ent->client->ps.gunframe = FRAME_IDLE_FIRST; return; } ent->client->ps.gunframe++; return; } if ((ent->client->newweapon) && (ent->client->weaponstate != WEAPON_FIRING)) { ent->client->weaponstate = WEAPON_DROPPING; ent->client->ps.gunframe = FRAME_DEACTIVATE_FIRST; return; } if (ent->client->weaponstate == WEAPON_READY) { if ( ((ent->client->latched_buttons|ent->client->buttons) & BUTTON_ATTACK) ) { ent->client->latched_buttons &= ~BUTTON_ATTACK; if ((!ent->client->ammo_index) || ( ent->client->pers.inventory[ent->client->ammo_index] >= ent->client->pers.weapon->quantity)) { ent->client->ps.gunframe = FRAME_FIRE_FIRST; ent->client->weaponstate = WEAPON_FIRING; // start the animation ent->client->anim_priority = ANIM_ATTACK; if (ent->client->ps.pmove.pm_flags & PMF_DUCKED) { ent->s.frame = FRAME_crattak1-1; ent->client->anim_end = FRAME_crattak9; } else { ent->s.frame = FRAME_attack1-1; ent->client->anim_end = FRAME_attack8; } } else { if (level.time >= ent->pain_debounce_time) { gi.sound(ent, CHAN_VOICE, gi.soundindex("weapons/noammo.wav"), 1, ATTN_NORM, 0); ent->pain_debounce_time = level.time + 1; } NoAmmoWeaponChange (ent); } } else { if (ent->client->ps.gunframe == FRAME_IDLE_LAST) { ent->client->ps.gunframe = FRAME_IDLE_FIRST; return; } if (pause_frames) { for (n = 0; pause_frames[n]; n++) { if (ent->client->ps.gunframe == pause_frames[n]) { if (rand()&15) return; } } } ent->client->ps.gunframe++; return; } } if (ent->client->weaponstate == WEAPON_FIRING) { for (n = 0; fire_frames[n]; n++) { if (ent->client->ps.gunframe == fire_frames[n]) { fire (ent); break; } } if (!fire_frames[n]) ent->client->ps.gunframe++; if (ent->client->ps.gunframe == FRAME_IDLE_FIRST+1) ent->client->weaponstate = WEAPON_READY; } }
void Weapon_Generic (edict_t *ent, int FRAME_ACTIVATE_LAST, int FRAME_FIRE_LAST, int FRAME_IDLE_LAST, int FRAME_DEACTIVATE_LAST, int *pause_frames, int *fire_frames, void (*fire)(edict_t *ent)) { int n; if(ent->deadflag || ent->s.modelindex != 255) // VWep animations screw up corpses { return; } if (ent->client->weaponstate == WEAPON_DROPPING) { if (ent->client->ps.gunframe == FRAME_DEACTIVATE_LAST) { if (ent->client->pers.itemchangetime < level.time) { ChangeWeapon (ent); } return; } else if ((FRAME_DEACTIVATE_LAST - ent->client->ps.gunframe) == 4) { ent->client->anim_priority = ANIM_REVERSE; if(ent->client->ps.pmove.pm_flags & PMF_DUCKED) { ent->s.frame = FRAME_crpain4+1; ent->client->anim_end = FRAME_crpain1; } else { ent->s.frame = FRAME_pain304+1; ent->client->anim_end = FRAME_pain301; } } ent->client->ps.gunframe++; return; } if (ent->client->weaponstate == WEAPON_ACTIVATING) { if (ent->client->ps.gunframe == FRAME_ACTIVATE_LAST) { ent->client->weaponstate = WEAPON_READY; ent->client->ps.gunframe = FRAME_IDLE_FIRST; return; } ent->client->ps.gunframe++; return; } if ((ent->client->newweapon) && (ent->client->weaponstate != WEAPON_FIRING)) { if (ent->client->pers.itemchanging == 0) { ent->client->weaponstate = WEAPON_DROPPING; ent->client->ps.gunframe = FRAME_DEACTIVATE_FIRST; if ((FRAME_DEACTIVATE_LAST - FRAME_DEACTIVATE_FIRST) < 4) { ent->client->anim_priority = ANIM_REVERSE; if(ent->client->ps.pmove.pm_flags & PMF_DUCKED) { ent->s.frame = FRAME_crpain4+1; ent->client->anim_end = FRAME_crpain1; } else { ent->s.frame = FRAME_pain304+1; ent->client->anim_end = FRAME_pain301; } } } return; } if (ent->client->weaponstate == WEAPON_READY) { if ( ((ent->client->latched_buttons|ent->client->buttons) & BUTTON_ATTACK)/* && (ent->client->spelltime < level.time)*/) { iteminfo_t *iteminfo; ent->client->latched_buttons &= ~BUTTON_ATTACK; if (ent->client->pers.skills.wornItem[0] == -1) { gi.cprintf(ent, PRINT_HIGH, "No weapon in hand\n"); return; } iteminfo = getWornItemInfo(ent, 0); if ((iteminfo->name[0] == '\0') || (iteminfo->item == NULL) || (iteminfo->item != ent->client->pers.weapon)) { gi.cprintf(ent, PRINT_HIGH, "Weapon mismatch, please report this to Chamooze and try to remember events around the last time you switched weapons.\nWorn weapon: %s, Actual weapon: %s\nTry equipping another weapon before continuing to play.\n", iteminfo->name, ent->client->pers.weapon->classname); return; } if ((!ent->client->ammo_index) || ( ent->client->pers.inventory[ent->client->ammo_index] >= ent->client->pers.weapon->quantity)) { ent->client->ps.gunframe = FRAME_FIRE_FIRST; ent->client->weaponstate = WEAPON_FIRING; // start the animation ent->client->anim_priority = ANIM_ATTACK; if (ent->client->ps.pmove.pm_flags & PMF_DUCKED) { ent->s.frame = FRAME_crattak1-1; ent->client->anim_end = FRAME_crattak9; } else { ent->s.frame = FRAME_attack1-1; ent->client->anim_end = FRAME_attack8; } } else { if (level.time >= ent->pain_debounce_time) { gi.sound(ent, CHAN_VOICE, gi.soundindex("weapons/noammo.wav"), 1, ATTN_NORM, 0); ent->pain_debounce_time = level.time + 1; } NoAmmoWeaponChange (ent); } } else { if (ent->client->ps.gunframe == FRAME_IDLE_LAST) { ent->client->ps.gunframe = FRAME_IDLE_FIRST; return; } if (pause_frames) { for (n = 0; pause_frames[n]; n++) { if (ent->client->ps.gunframe == pause_frames[n]) { if (rand()&15) return; } } } ent->client->ps.gunframe++; return; } } if (ent->client->weaponstate == WEAPON_FIRING) { for (n = 0; fire_frames[n]; n++) { if (ent->client->ps.gunframe == fire_frames[n]) { if (ent->client->quad_framenum > level.framenum) gi.sound(ent, CHAN_ITEM, gi.soundindex("items/damage3.wav"), 1, ATTN_NORM, 0); fire (ent); break; } } if (!fire_frames[n]) ent->client->ps.gunframe++; if (ent->client->ps.gunframe == FRAME_IDLE_FIRST+1) ent->client->weaponstate = WEAPON_READY; } }