Team Fortress 2 Source Code as on 22/4/2020
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

1455 lines
42 KiB

  1. //========= Copyright Valve Corporation, All rights reserved. ============//
  2. //
  3. // Purpose:
  4. //
  5. //=============================================================================
  6. #include "cbase.h"
  7. #ifdef CLIENT_DLL
  8. #include "achievementmgr.h"
  9. #include "baseachievement.h"
  10. #include "tf_hud_statpanel.h"
  11. #include "c_tf_team.h"
  12. #include "c_tf_player.h"
  13. #include "c_tf_playerresource.h"
  14. #include "tf_gamerules.h"
  15. #include "achievements_tf.h"
  16. #include "c_team_objectiveresource.h"
  17. //======================================================================================================================================
  18. // FOUNDRY ACHIEVEMENT PACK
  19. //======================================================================================================================================
  20. //----------------------------------------------------------------------------------------------------------------
  21. class CAchievementTFFoundry_KillCappingEnemy : public CBaseTFAchievementSimple
  22. {
  23. public:
  24. void Init()
  25. {
  26. SetFlags( ACH_SAVE_GLOBAL );
  27. SetGoal( 1 );
  28. }
  29. // server awards this achievement, no other code within achievement necessary
  30. };
  31. DECLARE_ACHIEVEMENT( CAchievementTFFoundry_KillCappingEnemy, ACHIEVEMENT_TF_MAPS_FOUNDRY_KILL_CAPPING_ENEMY, "TF_MAPS_FOUNDRY_KILL_CAPPING_ENEMY", 5 );
  32. //----------------------------------------------------------------------------------------------------------------
  33. class CAchievementTFFoundry_PlayGameFriends : public CBaseTFAchievementSimple
  34. {
  35. void Init()
  36. {
  37. SetFlags( ACH_SAVE_GLOBAL );
  38. SetGoal( 1 );
  39. SetMapNameFilter( "cp_foundry" );
  40. }
  41. virtual void ListenForEvents()
  42. {
  43. ListenForGameEvent( "teamplay_round_win" );
  44. }
  45. void FireGameEvent_Internal( IGameEvent *event )
  46. {
  47. if ( 0 == Q_strcmp( event->GetName(), "teamplay_round_win" ) )
  48. {
  49. // are there at least 5 friends in the game? (at least 6 players total)
  50. if ( CalcPlayersOnFriendsList( 5 ) )
  51. {
  52. AwardAchievement();
  53. }
  54. }
  55. }
  56. };
  57. DECLARE_ACHIEVEMENT( CAchievementTFFoundry_PlayGameFriends, ACHIEVEMENT_TF_MAPS_FOUNDRY_PLAY_GAME_FRIENDS, "TF_MAPS_FOUNDRY_PLAY_GAME_FRIENDS", 5 );
  58. //----------------------------------------------------------------------------------------------------------------
  59. class CAchievementTFFoundry_WinMinTime : public CBaseTFAchievementSimple
  60. {
  61. void Init()
  62. {
  63. SetFlags( ACH_SAVE_GLOBAL );
  64. SetGoal( 1 );
  65. SetMapNameFilter( "cp_foundry" );
  66. }
  67. virtual void ListenForEvents()
  68. {
  69. ListenForGameEvent( "teamplay_round_win" );
  70. }
  71. void FireGameEvent_Internal( IGameEvent *event )
  72. {
  73. if ( 0 == Q_strcmp( event->GetName(), "teamplay_round_win" ) )
  74. {
  75. int iTeam = event->GetInt( "team" );
  76. if ( ( iTeam >= FIRST_GAME_TEAM ) && ( iTeam == GetLocalPlayerTeam() ) )
  77. {
  78. float flRoundTime = event->GetFloat( "round_time", 0 );
  79. if ( flRoundTime > 0 && flRoundTime < 2 * 60 )
  80. {
  81. AwardAchievement();
  82. }
  83. }
  84. }
  85. }
  86. };
  87. DECLARE_ACHIEVEMENT( CAchievementTFFoundry_WinMinTime, ACHIEVEMENT_TF_MAPS_FOUNDRY_WIN_MINTIME, "TF_MAPS_FOUNDRY_WIN_MINTIME", 5 );
  88. //----------------------------------------------------------------------------------------------------------------
  89. class CAchievementTFFoundry_WinRounds : public CBaseTFAchievementSimple
  90. {
  91. void Init()
  92. {
  93. SetFlags( ACH_SAVE_GLOBAL );
  94. SetGoal( 137 );
  95. SetStoreProgressInSteam( true );
  96. SetMapNameFilter( "cp_foundry" );
  97. }
  98. virtual void ListenForEvents()
  99. {
  100. ListenForGameEvent( "teamplay_round_win" );
  101. }
  102. void FireGameEvent_Internal( IGameEvent *event )
  103. {
  104. if ( 0 == Q_strcmp( event->GetName(), "teamplay_round_win" ) )
  105. {
  106. // Were we on the winning team?
  107. int iTeam = event->GetInt( "team" );
  108. if ( ( iTeam >= FIRST_GAME_TEAM ) && ( iTeam == GetLocalPlayerTeam() ) )
  109. {
  110. IncrementCount();
  111. }
  112. }
  113. }
  114. };
  115. DECLARE_ACHIEVEMENT( CAchievementTFFoundry_WinRounds, ACHIEVEMENT_TF_MAPS_FOUNDRY_WIN_ROUNDS, "TF_MAPS_FOUNDRY_WIN_ROUNDS", 5 );
  116. //----------------------------------------------------------------------------------------------------------------
  117. class CAchievementTFFoundry_FastFinalCap : public CBaseTFAchievementSimple
  118. {
  119. void Init()
  120. {
  121. SetFlags( ACH_SAVE_GLOBAL );
  122. SetGoal( 1 );
  123. SetMapNameFilter( "cp_foundry" );
  124. ResetCounts();
  125. }
  126. void ResetCounts()
  127. {
  128. m_bRecentCapper = false;
  129. iCapCount = 0;
  130. iCapTimes[0] = 0.0f;
  131. iCapTimes[1] = 0.0f;
  132. }
  133. virtual void ListenForEvents( void )
  134. {
  135. ListenForGameEvent( "teamplay_point_captured" );
  136. ListenForGameEvent( "teamplay_round_win" );
  137. ListenForGameEvent( "teamplay_round_start" );
  138. }
  139. void FireGameEvent_Internal( IGameEvent *event )
  140. {
  141. const char *pszEventName = event->GetName();
  142. CTFPlayer *pLocalPlayer = ToTFPlayer( C_BasePlayer::GetLocalPlayer() );
  143. if ( !pLocalPlayer )
  144. return;
  145. if ( FStrEq( pszEventName, "teamplay_point_captured" ) )
  146. {
  147. m_bRecentCapper = false;
  148. int iTeam = event->GetInt( "team" );
  149. if ( ( iTeam >= FIRST_GAME_TEAM ) && ( iTeam == pLocalPlayer->GetTeamNumber() ) )
  150. {
  151. iCapTimes[iCapCount%2] = gpGlobals->curtime;
  152. iCapCount++;
  153. const char *cappers = event->GetString( "cappers" );
  154. for ( int i = 0 ; i < Q_strlen( cappers ) ; i++ )
  155. {
  156. int iPlayerIndex = (int) cappers[i];
  157. CTFPlayer *pPlayer = ToTFPlayer( UTIL_PlayerByIndex( iPlayerIndex ) );
  158. if ( pPlayer == pLocalPlayer )
  159. {
  160. m_bRecentCapper = true;
  161. }
  162. }
  163. }
  164. }
  165. else if ( FStrEq( pszEventName, "teamplay_round_win" ) )
  166. {
  167. // If we're the winners and we were involved in capping the last point, we get this achievement.
  168. int iTeam = event->GetInt( "team" );
  169. if ( ( iTeam >= FIRST_GAME_TEAM ) && ( iTeam == pLocalPlayer->GetTeamNumber() ) && m_bRecentCapper )
  170. {
  171. if ( fabs( iCapTimes[1] - iCapTimes[0] ) <= 5.0f )
  172. {
  173. AwardAchievement();
  174. }
  175. }
  176. ResetCounts();
  177. }
  178. else if ( FStrEq( pszEventName, "teamplay_round_start" ) )
  179. {
  180. ResetCounts();
  181. }
  182. }
  183. private:
  184. bool m_bRecentCapper;
  185. int iCapCount;
  186. float iCapTimes[2];
  187. };
  188. DECLARE_ACHIEVEMENT( CAchievementTFFoundry_FastFinalCap, ACHIEVEMENT_TF_MAPS_FOUNDRY_FAST_FINAL_CAP, "TF_MAPS_FOUNDRY_FAST_FINAL_CAP", 5 );
  189. //----------------------------------------------------------------------------------------------------------------
  190. class CAchievementTFFoundry_TeleportAndCap : public CBaseTFAchievementSimple
  191. {
  192. void Init()
  193. {
  194. SetFlags( ACH_SAVE_GLOBAL );
  195. SetGoal( 1 );
  196. SetMapNameFilter( "cp_foundry" );
  197. }
  198. virtual void ListenForEvents( void )
  199. {
  200. ListenForGameEvent( "teamplay_point_captured" );
  201. }
  202. void FireGameEvent_Internal( IGameEvent *event )
  203. {
  204. const char *pszEventName = event->GetName();
  205. CTFPlayer *pLocalPlayer = ToTFPlayer( C_BasePlayer::GetLocalPlayer() );
  206. if ( !pLocalPlayer )
  207. return;
  208. if ( !pLocalPlayer->m_Shared.InCond( TF_COND_TELEPORTED ) )
  209. return;
  210. if ( FStrEq( pszEventName, "teamplay_point_captured" ) )
  211. {
  212. int iTeam = event->GetInt( "team" );
  213. if ( ( iTeam >= FIRST_GAME_TEAM ) && ( iTeam == pLocalPlayer->GetTeamNumber() ) )
  214. {
  215. const char *cappers = event->GetString( "cappers" );
  216. for ( int i = 0 ; i < Q_strlen( cappers ) ; i++ )
  217. {
  218. int iPlayerIndex = (int) cappers[i];
  219. CTFPlayer *pPlayer = ToTFPlayer( UTIL_PlayerByIndex( iPlayerIndex ) );
  220. if ( pPlayer == pLocalPlayer )
  221. {
  222. AwardAchievement();
  223. }
  224. }
  225. }
  226. }
  227. }
  228. };
  229. DECLARE_ACHIEVEMENT( CAchievementTFFoundry_TeleportAndCap, ACHIEVEMENT_TF_MAPS_FOUNDRY_TELEPORT_AND_CAP, "TF_MAPS_FOUNDRY_TELEPORT_AND_CAP", 5 );
  230. //----------------------------------------------------------------------------------------------------------------
  231. class CAchievementTFFoundry_PushIntoCauldron : public CBaseTFAchievementSimple
  232. {
  233. public:
  234. void Init()
  235. {
  236. SetFlags( ACH_SAVE_GLOBAL );
  237. SetGoal( 1 );
  238. }
  239. // server awards this achievement, no other code within achievement necessary
  240. };
  241. DECLARE_ACHIEVEMENT( CAchievementTFFoundry_PushIntoCauldron, ACHIEVEMENT_TF_MAPS_FOUNDRY_PUSH_INTO_CAULDRON, "TF_MAPS_FOUNDRY_PUSH_INTO_CAULDRON", 5 );
  242. //----------------------------------------------------------------------------------------------------------------
  243. class CAchievementTFFoundry_PushBackAndWin : public CBaseTFAchievementSimple
  244. {
  245. void Init()
  246. {
  247. SetFlags( ACH_SAVE_GLOBAL );
  248. SetGoal( 1 );
  249. SetMapNameFilter( "cp_foundry" );
  250. m_bFinalPointContested = false;
  251. }
  252. virtual void ListenForEvents()
  253. {
  254. ListenForGameEvent( "teamplay_round_win" );
  255. ListenForGameEvent( "teamplay_point_startcapture" );
  256. ListenForGameEvent( "teamplay_round_start" );
  257. ListenForGameEvent( "localplayer_changeteam" );
  258. }
  259. void FireGameEvent_Internal( IGameEvent *event )
  260. {
  261. const char *pszEventName = event->GetName();
  262. if ( FStrEq( pszEventName, "teamplay_round_win" ) )
  263. {
  264. int iTeam = event->GetInt( "team" );
  265. if ( ( iTeam >= FIRST_GAME_TEAM ) && ( iTeam == GetLocalPlayerTeam() ) )
  266. {
  267. if ( m_bFinalPointContested )
  268. {
  269. AwardAchievement();
  270. }
  271. }
  272. }
  273. else if ( FStrEq( pszEventName, "teamplay_point_startcapture" ) )
  274. {
  275. if ( ObjectiveResource() && ( ObjectiveResource()->GetBaseControlPointForTeam( GetLocalPlayerTeam() ) == event->GetInt( "cp" ) ) )
  276. {
  277. m_bFinalPointContested = true;
  278. }
  279. }
  280. else if ( FStrEq( pszEventName, "teamplay_round_start" ) || FStrEq( pszEventName, "localplayer_changeteam" ) )
  281. {
  282. m_bFinalPointContested = false;
  283. }
  284. }
  285. private:
  286. bool m_bFinalPointContested;
  287. };
  288. DECLARE_ACHIEVEMENT( CAchievementTFFoundry_PushBackAndWin, ACHIEVEMENT_TF_MAPS_FOUNDRY_PUSH_BACK_AND_WIN, "TF_MAPS_FOUNDRY_PUSH_BACK_AND_WIN", 5 );
  289. //----------------------------------------------------------------------------------------------------------------
  290. class CAchievementTFFoundry_PlayEachClass : public CBaseTFAchievementSimple
  291. {
  292. void Init()
  293. {
  294. SetFlags( ACH_SAVE_GLOBAL | ACH_LISTEN_KILL_EVENTS );
  295. SetGoal( 1 );
  296. SetMapNameFilter( "cp_foundry" );
  297. m_iClassesPlayed = 0;
  298. }
  299. virtual void ListenForEvents()
  300. {
  301. ListenForGameEvent( "teamplay_round_start" );
  302. }
  303. virtual void Event_EntityKilled( CBaseEntity *pVictim, CBaseEntity *pAttacker, CBaseEntity *pInflictor, IGameEvent *event )
  304. {
  305. CTFPlayer *pLocalPlayer = ToTFPlayer( C_BasePlayer::GetLocalPlayer() );
  306. if ( pLocalPlayer && ( pLocalPlayer == pAttacker ) && ( pVictim != pAttacker ) && ( pLocalPlayer->m_Shared.GetDesiredPlayerClassIndex() > TF_CLASS_UNDEFINED ) )
  307. {
  308. m_iClassesPlayed |= ( 1 << pLocalPlayer->m_Shared.GetDesiredPlayerClassIndex() );
  309. if ( m_iClassesPlayed == 1022 )
  310. {
  311. AwardAchievement();
  312. }
  313. }
  314. }
  315. void FireGameEvent_Internal( IGameEvent *event )
  316. {
  317. if ( FStrEq( event->GetName(), "teamplay_round_start" ) )
  318. {
  319. m_iClassesPlayed = 0;
  320. }
  321. }
  322. private:
  323. int m_iClassesPlayed;
  324. };
  325. DECLARE_ACHIEVEMENT( CAchievementTFFoundry_PlayEachClass, ACHIEVEMENT_TF_MAPS_FOUNDRY_PLAY_EACH_CLASS, "TF_MAPS_FOUNDRY_PLAY_EACH_CLASS", 5 );
  326. //----------------------------------------------------------------------------------------------------------------
  327. class CAchievementTFFoundry_KillEnemyOnRoof : public CBaseTFAchievementSimple
  328. {
  329. public:
  330. void Init()
  331. {
  332. SetFlags( ACH_SAVE_GLOBAL | ACH_LISTEN_KILL_EVENTS );
  333. SetGoal( 1 );
  334. SetMapNameFilter( "cp_foundry" );
  335. iKillCount = 0;
  336. }
  337. virtual void ListenForEvents()
  338. {
  339. ListenForGameEvent( "teamplay_round_start" );
  340. ListenForGameEvent( "player_killed_achievement_zone" );
  341. }
  342. virtual void Event_EntityKilled( CBaseEntity *pVictim, CBaseEntity *pAttacker, CBaseEntity *pInflictor, IGameEvent *event )
  343. {
  344. CTFPlayer *pLocalPlayer = ToTFPlayer( C_BasePlayer::GetLocalPlayer() );
  345. if ( pLocalPlayer && ( pLocalPlayer == pVictim ) )
  346. {
  347. iKillCount = 0;
  348. }
  349. }
  350. void FireGameEvent_Internal( IGameEvent *event )
  351. {
  352. const char *pszEventName = event->GetName();
  353. if ( FStrEq( pszEventName, "teamplay_round_start" ) )
  354. {
  355. iKillCount = 0;
  356. }
  357. else if ( FStrEq( pszEventName, "player_killed_achievement_zone" ) )
  358. {
  359. CTFPlayer *pLocalPlayer = ToTFPlayer( C_BasePlayer::GetLocalPlayer() );
  360. CTFPlayer *pAttacker = ToTFPlayer( UTIL_PlayerByIndex( event->GetInt( "attacker" ) ) );
  361. CTFPlayer *pVictim = ToTFPlayer( UTIL_PlayerByIndex( event->GetInt( "victim" ) ) );
  362. if ( pLocalPlayer && ( pLocalPlayer == pAttacker ) && pVictim && ( pVictim->GetTeamNumber() != pAttacker->GetTeamNumber() ) )
  363. {
  364. iKillCount++;
  365. if ( iKillCount >= 2 )
  366. {
  367. AwardAchievement();
  368. }
  369. }
  370. }
  371. }
  372. private:
  373. int iKillCount;
  374. };
  375. DECLARE_ACHIEVEMENT( CAchievementTFFoundry_KillEnemyOnRoof, ACHIEVEMENT_TF_MAPS_FOUNDRY_KILL_ENEMY_ON_ROOF, "TF_MAPS_FOUNDRY_KILL_ENEMY_ON_ROOF", 5 );
  376. //----------------------------------------------------------------------------------------------------------------
  377. class CAchievementTFFoundry_BackAndForthBattle : public CBaseTFAchievementSimple
  378. {
  379. void Init()
  380. {
  381. SetFlags( ACH_SAVE_GLOBAL );
  382. SetGoal( 1 );
  383. SetMapNameFilter( "cp_foundry" );
  384. m_iCapCount = 0;
  385. }
  386. virtual void ListenForEvents( void )
  387. {
  388. ListenForGameEvent( "teamplay_point_captured" );
  389. ListenForGameEvent( "teamplay_round_start" );
  390. }
  391. void FireGameEvent_Internal( IGameEvent *event )
  392. {
  393. const char *pszEventName = event->GetName();
  394. CTFPlayer *pLocalPlayer = ToTFPlayer( C_BasePlayer::GetLocalPlayer() );
  395. if ( !pLocalPlayer )
  396. return;
  397. if ( pLocalPlayer->GetTeamNumber() < FIRST_GAME_TEAM )
  398. return;
  399. if ( FStrEq( pszEventName, "teamplay_point_captured" ) )
  400. {
  401. // we don't care which team is capping or which point is capped for this achievement
  402. m_iCapCount++;
  403. if ( m_iCapCount >= 15 )
  404. {
  405. AwardAchievement();
  406. }
  407. }
  408. else if ( FStrEq( pszEventName, "teamplay_round_start" ) )
  409. {
  410. m_iCapCount = 0;
  411. }
  412. }
  413. private:
  414. int m_iCapCount;
  415. };
  416. DECLARE_ACHIEVEMENT( CAchievementTFFoundry_BackAndForthBattle, ACHIEVEMENT_TF_MAPS_FOUNDRY_BACK_AND_FORTH_BATTLE, "TF_MAPS_FOUNDRY_BACK_AND_FORTH_BATTLE", 5 );
  417. //----------------------------------------------------------------------------------------------------------------
  418. class CAchievementTFFoundry_AchieveProgress1 : public CAchievement_AchievedCount
  419. {
  420. public:
  421. DECLARE_CLASS( CAchievementTFFoundry_AchieveProgress1, CAchievement_AchievedCount );
  422. void Init()
  423. {
  424. BaseClass::Init();
  425. SetAchievementsRequired( 7, ACHIEVEMENT_TF_MAPS_FOUNDRY_START_RANGE, ACHIEVEMENT_TF_MAPS_FOUNDRY_END_RANGE );
  426. }
  427. };
  428. DECLARE_ACHIEVEMENT( CAchievementTFFoundry_AchieveProgress1, ACHIEVEMENT_TF_MAPS_FOUNDRY_ACHIEVE_PROGRESS1, "TF_MAPS_FOUNDRY_ACHIEVE_PROGRESS1", 5 );
  429. //======================================================================================================================================
  430. // DOOMSDAY ACHIEVEMENT PACK
  431. //======================================================================================================================================
  432. //----------------------------------------------------------------------------------------------------------------
  433. class CAchievementTFDoomsday_SoloCapture : public CBaseTFAchievementSimple
  434. {
  435. void Init()
  436. {
  437. SetFlags( ACH_SAVE_GLOBAL );
  438. SetGoal( 1 );
  439. SetMapNameFilter( "sd_doomsday" );
  440. m_bCarriedFromHome = false;
  441. }
  442. virtual void ListenForEvents()
  443. {
  444. ListenForGameEvent( "teamplay_flag_event" );
  445. ListenForGameEvent( "teamplay_round_start" );
  446. }
  447. void FireGameEvent_Internal( IGameEvent *event )
  448. {
  449. const char *pszEventName = event->GetName();
  450. if ( FStrEq( pszEventName, "teamplay_flag_event" ) )
  451. {
  452. int iPlayer = event->GetInt( "player" );
  453. int iType = event->GetInt( "eventtype" );
  454. bool bHome = ( event->GetInt( "home", 0 ) == 1 );
  455. switch( iType )
  456. {
  457. case TF_FLAGEVENT_PICKUP:
  458. if ( ( iPlayer == GetLocalPlayerIndex() ) && bHome )
  459. {
  460. m_bCarriedFromHome = true;
  461. }
  462. else
  463. {
  464. m_bCarriedFromHome = false;
  465. }
  466. break;
  467. case TF_FLAGEVENT_CAPTURE:
  468. if ( ( iPlayer == GetLocalPlayerIndex() ) && m_bCarriedFromHome )
  469. {
  470. IncrementCount();
  471. }
  472. break;
  473. default:
  474. m_bCarriedFromHome = false;
  475. break;
  476. }
  477. }
  478. else if ( FStrEq( pszEventName, "teamplay_round_start" ) )
  479. {
  480. m_bCarriedFromHome = false;
  481. }
  482. }
  483. private:
  484. bool m_bCarriedFromHome;
  485. };
  486. DECLARE_ACHIEVEMENT( CAchievementTFDoomsday_SoloCapture, ACHIEVEMENT_TF_MAPS_DOOMSDAY_SOLO_CAPTURE, "TF_MAPS_DOOMSDAY_SOLO_CAPTURE", 5 );
  487. //----------------------------------------------------------------------------------------------------------------
  488. class CAchievementTFDoomsday_PlayGameFriends : public CBaseTFAchievementSimple
  489. {
  490. void Init()
  491. {
  492. SetFlags( ACH_SAVE_GLOBAL );
  493. SetGoal( 1 );
  494. SetMapNameFilter( "sd_doomsday" );
  495. }
  496. virtual void ListenForEvents()
  497. {
  498. ListenForGameEvent( "teamplay_round_win" );
  499. }
  500. void FireGameEvent_Internal( IGameEvent *event )
  501. {
  502. if ( 0 == Q_strcmp( event->GetName(), "teamplay_round_win" ) )
  503. {
  504. // are there at least 5 friends in the game? (at least 6 players total)
  505. if ( CalcPlayersOnFriendsList( 5 ) )
  506. {
  507. AwardAchievement();
  508. }
  509. }
  510. }
  511. };
  512. DECLARE_ACHIEVEMENT( CAchievementTFDoomsday_PlayGameFriends, ACHIEVEMENT_TF_MAPS_DOOMSDAY_PLAY_GAME_FRIENDS, "TF_MAPS_DOOMSDAY_PLAY_GAME_FRIENDS", 5 );
  513. //----------------------------------------------------------------------------------------------------------------
  514. class CAchievementTFDoomsday_WinRounds : public CBaseTFAchievementSimple
  515. {
  516. void Init()
  517. {
  518. SetFlags( ACH_SAVE_GLOBAL );
  519. SetGoal( 138 );
  520. SetStoreProgressInSteam( true );
  521. SetMapNameFilter( "sd_doomsday" );
  522. }
  523. virtual void ListenForEvents()
  524. {
  525. ListenForGameEvent( "teamplay_round_win" );
  526. }
  527. void FireGameEvent_Internal( IGameEvent *event )
  528. {
  529. if ( 0 == Q_strcmp( event->GetName(), "teamplay_round_win" ) )
  530. {
  531. // Were we on the winning team?
  532. int iTeam = event->GetInt( "team" );
  533. if ( ( iTeam >= FIRST_GAME_TEAM ) && ( iTeam == GetLocalPlayerTeam() ) )
  534. {
  535. IncrementCount();
  536. }
  537. }
  538. }
  539. };
  540. DECLARE_ACHIEVEMENT( CAchievementTFDoomsday_WinRounds, ACHIEVEMENT_TF_MAPS_DOOMSDAY_WIN_ROUNDS, "TF_MAPS_DOOMSDAY_WIN_ROUNDS", 5 );
  541. //----------------------------------------------------------------------------------------------------------------
  542. class CAchievementTFDoomsday_PlayEachClass : public CBaseTFAchievementSimple
  543. {
  544. void Init()
  545. {
  546. SetFlags( ACH_SAVE_GLOBAL | ACH_HAS_COMPONENTS );
  547. SetGoal( ( TF_LAST_NORMAL_CLASS - 1 ) - TF_FIRST_NORMAL_CLASS + 1 ); //( TF_LAST_NORMAL_CLASS - 1 ) to exclude the new civilian class
  548. SetMapNameFilter( "sd_doomsday" );
  549. }
  550. virtual void ListenForEvents()
  551. {
  552. ListenForGameEvent( "teamplay_flag_event" );
  553. }
  554. void FireGameEvent_Internal( IGameEvent *event )
  555. {
  556. if ( FStrEq( event->GetName(), "teamplay_flag_event" ) )
  557. {
  558. int iPlayer = event->GetInt( "player" );
  559. int iType = event->GetInt( "eventtype" );
  560. switch( iType )
  561. {
  562. case TF_FLAGEVENT_CAPTURE:
  563. if ( iPlayer == GetLocalPlayerIndex() )
  564. {
  565. C_TFPlayer *pTFPlayer = C_TFPlayer::GetLocalTFPlayer();
  566. if ( pTFPlayer )
  567. {
  568. int iClass = pTFPlayer->GetPlayerClass()->GetClassIndex();
  569. if ( iClass >= TF_FIRST_NORMAL_CLASS && iClass <= ( TF_LAST_NORMAL_CLASS - 1 ) ) //( TF_LAST_NORMAL_CLASS - 1 ) to exclude the new civilian class
  570. {
  571. // yes, the achievement is satisfied for this class, set the corresponding bit
  572. int iBitNumber = ( iClass - TF_FIRST_NORMAL_CLASS );
  573. EnsureComponentBitSetAndEvaluate( iBitNumber );
  574. }
  575. }
  576. }
  577. break;
  578. default:
  579. break;
  580. }
  581. }
  582. }
  583. };
  584. DECLARE_ACHIEVEMENT( CAchievementTFDoomsday_PlayEachClass, ACHIEVEMENT_TF_MAPS_DOOMSDAY_PLAY_EACH_CLASS, "TF_MAPS_DOOMSDAY_PLAY_EACH_CLASS", 5 );
  585. //----------------------------------------------------------------------------------------------------------------
  586. class CAchievementTFDoomsday_KillEnemiesOnElevator : public CBaseTFAchievementSimple
  587. {
  588. void Init()
  589. {
  590. SetFlags( ACH_SAVE_GLOBAL );
  591. SetGoal( 1 );
  592. SetMapNameFilter( "sd_doomsday" );
  593. m_flTimeWindow = 10.0f;
  594. m_nKillsToAchieve = 3;
  595. }
  596. virtual void ListenForEvents()
  597. {
  598. ListenForGameEvent( "player_killed_achievement_zone" );
  599. }
  600. void FireGameEvent_Internal( IGameEvent *event )
  601. {
  602. if ( FStrEq( event->GetName(), "player_killed_achievement_zone" ) )
  603. {
  604. int iZoneID = event->GetInt( "zone_id" );
  605. if ( iZoneID == 1 ) // capture zone
  606. {
  607. CTFPlayer *pLocalPlayer = ToTFPlayer( C_BasePlayer::GetLocalPlayer() );
  608. CTFPlayer *pAttacker = ToTFPlayer( UTIL_PlayerByIndex( event->GetInt( "attacker" ) ) );
  609. CTFPlayer *pVictim = ToTFPlayer( UTIL_PlayerByIndex( event->GetInt( "victim" ) ) );
  610. if ( pLocalPlayer && ( pLocalPlayer == pAttacker ) && pVictim && ( pVictim->GetTeamNumber() != pAttacker->GetTeamNumber() ) )
  611. {
  612. int index = m_History.AddToHead();
  613. m_History[index] = gpGlobals->curtime;
  614. Evaluate();
  615. }
  616. }
  617. }
  618. }
  619. void Evaluate( void )
  620. {
  621. // remove any times that are older than the window
  622. float flTimeDiscard = gpGlobals->curtime - m_flTimeWindow;
  623. for ( int i = 0 ; i < m_History.Count() ; i++ )
  624. {
  625. if ( m_History[i] < flTimeDiscard )
  626. {
  627. m_History.RemoveMultiple( i, m_History.Count() - i );
  628. break;
  629. }
  630. }
  631. // have we killed enough players in the time window?
  632. if ( m_History.Count() >= m_nKillsToAchieve )
  633. {
  634. IncrementCount();
  635. }
  636. }
  637. private:
  638. CUtlVector< float > m_History;
  639. float m_flTimeWindow;
  640. int m_nKillsToAchieve;
  641. };
  642. DECLARE_ACHIEVEMENT( CAchievementTFDoomsday_KillEnemiesOnElevator, ACHIEVEMENT_TF_MAPS_DOOMSDAY_KILL_ENEMIES_ON_ELEVATOR, "TF_MAPS_DOOMSDAY_KILL_ENEMIES_ON_ELEVATOR", 5 );
  643. //----------------------------------------------------------------------------------------------------------------
  644. class CAchievementTFDoomsday_PushBackAndWin : public CBaseTFAchievementSimple
  645. {
  646. void Init()
  647. {
  648. SetFlags( ACH_SAVE_GLOBAL );
  649. SetGoal( 1 );
  650. SetMapNameFilter( "sd_doomsday" );
  651. m_bRocketOpenedByEnemyTeam = false;
  652. }
  653. virtual void ListenForEvents()
  654. {
  655. ListenForGameEvent( "teamplay_round_win" );
  656. ListenForGameEvent( "doomsday_rocket_open" );
  657. ListenForGameEvent( "teamplay_round_start" );
  658. }
  659. void FireGameEvent_Internal( IGameEvent *event )
  660. {
  661. const char *pszEventName = event->GetName();
  662. if ( FStrEq( pszEventName, "teamplay_round_win" ) )
  663. {
  664. int iTeam = event->GetInt( "team" );
  665. if ( ( iTeam >= FIRST_GAME_TEAM ) && ( iTeam == GetLocalPlayerTeam() ) )
  666. {
  667. if ( m_bRocketOpenedByEnemyTeam )
  668. {
  669. AwardAchievement();
  670. }
  671. }
  672. }
  673. else if ( FStrEq( pszEventName, "doomsday_rocket_open" ) )
  674. {
  675. int iTeam = event->GetInt( "team" );
  676. if ( ( iTeam >= FIRST_GAME_TEAM ) && ( iTeam != GetLocalPlayerTeam() ) )
  677. {
  678. m_bRocketOpenedByEnemyTeam = true;
  679. }
  680. }
  681. else if ( FStrEq( pszEventName, "teamplay_round_start" ) )
  682. {
  683. m_bRocketOpenedByEnemyTeam = false;
  684. }
  685. }
  686. private:
  687. bool m_bRocketOpenedByEnemyTeam;
  688. };
  689. DECLARE_ACHIEVEMENT( CAchievementTFDoomsday_PushBackAndWin, ACHIEVEMENT_TF_MAPS_DOOMSDAY_PUSH_BACK_AND_WIN, "TF_MAPS_DOOMSDAY_PUSH_BACK_AND_WIN", 5 );
  690. //----------------------------------------------------------------------------------------------------------------
  691. class CAchievementTFDoomsday_KillCarriers : public CBaseTFAchievementSimple
  692. {
  693. void Init()
  694. {
  695. SetFlags( ACH_SAVE_GLOBAL | ACH_LISTEN_KILL_ENEMY_EVENTS );
  696. SetGoal( 1 );
  697. SetMapNameFilter( "sd_doomsday" );
  698. m_iKillCount = 0;
  699. }
  700. virtual void ListenForEvents( void )
  701. {
  702. ListenForGameEvent( "teamplay_round_start" );
  703. }
  704. void FireGameEvent_Internal( IGameEvent *event )
  705. {
  706. CTFPlayer *pLocalPlayer = ToTFPlayer( C_BasePlayer::GetLocalPlayer() );
  707. if ( !pLocalPlayer )
  708. return;
  709. if ( pLocalPlayer->GetTeamNumber() < FIRST_GAME_TEAM )
  710. return;
  711. if ( FStrEq( event->GetName(), "teamplay_round_start" ) )
  712. {
  713. m_iKillCount = 0;
  714. }
  715. }
  716. virtual void Event_EntityKilled( CBaseEntity *pVictim, CBaseEntity *pAttacker, CBaseEntity *pInflictor, IGameEvent *event )
  717. {
  718. if ( !pVictim || !pVictim->IsPlayer() )
  719. return;
  720. if ( pAttacker == C_BasePlayer::GetLocalPlayer() && pVictim != C_BasePlayer::GetLocalPlayer() )
  721. {
  722. C_TFPlayer *pTFVictim = ToTFPlayer( pVictim );
  723. if ( pTFVictim && pTFVictim->HasTheFlag() )
  724. {
  725. m_iKillCount++;
  726. if ( m_iKillCount >= 6 )
  727. {
  728. IncrementCount();
  729. }
  730. }
  731. }
  732. }
  733. private:
  734. int m_iKillCount;
  735. };
  736. DECLARE_ACHIEVEMENT( CAchievementTFDoomsday_KillCarriers, ACHIEVEMENT_TF_MAPS_DOOMSDAY_KILL_CARRIERS, "TF_MAPS_DOOMSDAY_KILL_CARRIERS", 5 );
  737. //----------------------------------------------------------------------------------------------------------------
  738. class CAchievementTFDoomsday_RideTheElevator : public CBaseTFAchievementSimple
  739. {
  740. void Init()
  741. {
  742. SetFlags( ACH_SAVE_GLOBAL );
  743. SetGoal( 1 );
  744. }
  745. // server awards this achievement, no other code within achievement necessary
  746. };
  747. DECLARE_ACHIEVEMENT( CAchievementTFDoomsday_RideTheElevator, ACHIEVEMENT_TF_MAPS_DOOMSDAY_RIDE_THE_ELEVATOR, "TF_MAPS_DOOMSDAY_RIDE_THE_ELEVATOR", 5 );
  748. //----------------------------------------------------------------------------------------------------------------
  749. class CAchievementTFDoomsday_DenyNeutralPickup : public CBaseTFAchievementSimple
  750. {
  751. void Init()
  752. {
  753. SetFlags( ACH_SAVE_GLOBAL );
  754. SetGoal( 1 );
  755. }
  756. // server awards this achievement, no other code within achievement necessary
  757. };
  758. DECLARE_ACHIEVEMENT( CAchievementTFDoomsday_DenyNeutralPickup, ACHIEVEMENT_TF_MAPS_DOOMSDAY_DENY_NEUTRAL_PICKUP, "TF_MAPS_DOOMSDAY_DENY_NEUTRAL_PICKUP", 5 );
  759. //----------------------------------------------------------------------------------------------------------------
  760. class CAchievementTFDoomsday_PushIntoExhaust : public CBaseTFAchievementSimple
  761. {
  762. void Init()
  763. {
  764. SetFlags( ACH_SAVE_GLOBAL );
  765. SetGoal( 1 );
  766. }
  767. // server awards this achievement, no other code within achievement necessary
  768. };
  769. DECLARE_ACHIEVEMENT( CAchievementTFDoomsday_PushIntoExhaust, ACHIEVEMENT_TF_MAPS_DOOMSDAY_PUSH_INTO_EXHAUST, "TF_MAPS_DOOMSDAY_PUSH_INTO_EXHAUST", 5 );
  770. //----------------------------------------------------------------------------------------------------------------
  771. class CAchievementTFDoomsday_DefendCarrier : public CBaseTFAchievementSimple
  772. {
  773. void Init()
  774. {
  775. SetFlags( ACH_SAVE_GLOBAL );
  776. SetGoal( 1 );
  777. }
  778. // server awards this achievement, no other code within achievement necessary
  779. };
  780. DECLARE_ACHIEVEMENT( CAchievementTFDoomsday_DefendCarrier, ACHIEVEMENT_TF_MAPS_DOOMSDAY_DEFEND_CARRIER, "TF_MAPS_DOOMSDAY_DEFEND_CARRIER", 5 );
  781. //----------------------------------------------------------------------------------------------------------------
  782. class CAchievementTFDoomsday_AchieveProgress1 : public CAchievement_AchievedCount
  783. {
  784. public:
  785. DECLARE_CLASS( CAchievementTFDoomsday_AchieveProgress1, CAchievement_AchievedCount );
  786. void Init()
  787. {
  788. BaseClass::Init();
  789. SetAchievementsRequired( 7, ACHIEVEMENT_TF_MAPS_DOOMSDAY_START_RANGE, ACHIEVEMENT_TF_MAPS_DOOMSDAY_END_RANGE );
  790. }
  791. };
  792. DECLARE_ACHIEVEMENT( CAchievementTFDoomsday_AchieveProgress1, ACHIEVEMENT_TF_MAPS_DOOMSDAY_ACHIEVE_PROGRESS1, "TF_MAPS_DOOMSDAY_ACHIEVE_PROGRESS1", 5 );
  793. //----------------------------------------------------------------------------------------------------------------
  794. class CAchievementTFStandin_WinRounds : public CBaseTFAchievementSimple
  795. {
  796. void Init()
  797. {
  798. SetFlags( ACH_SAVE_GLOBAL );
  799. SetGoal( 139 );
  800. SetStoreProgressInSteam( true );
  801. SetMapNameFilter( "cp_standin_final" );
  802. }
  803. virtual void ListenForEvents()
  804. {
  805. ListenForGameEvent( "teamplay_round_win" );
  806. }
  807. void FireGameEvent_Internal( IGameEvent *event )
  808. {
  809. if ( 0 == Q_strcmp( event->GetName(), "teamplay_round_win" ) )
  810. {
  811. // Were we on the winning team?
  812. int iTeam = event->GetInt( "team" );
  813. if ( ( iTeam >= FIRST_GAME_TEAM ) && ( iTeam == GetLocalPlayerTeam() ) )
  814. {
  815. IncrementCount();
  816. }
  817. }
  818. }
  819. };
  820. DECLARE_ACHIEVEMENT( CAchievementTFStandin_WinRounds, ACHIEVEMENT_TF_MAPS_STANDIN_WIN_ROUNDS, "TF_MAPS_STANDIN_WIN_ROUNDS", 5 );
  821. //----------------------------------------------------------------------------------------------------------------
  822. class CAchievementTFProcess_WinRounds : public CBaseTFAchievementSimple
  823. {
  824. void Init()
  825. {
  826. SetFlags( ACH_SAVE_GLOBAL );
  827. SetGoal( 140 );
  828. SetStoreProgressInSteam( true );
  829. SetMapNameFilter( "cp_process_final" );
  830. }
  831. virtual void ListenForEvents()
  832. {
  833. ListenForGameEvent( "teamplay_round_win" );
  834. }
  835. void FireGameEvent_Internal( IGameEvent *event )
  836. {
  837. if ( 0 == Q_strcmp( event->GetName(), "teamplay_round_win" ) )
  838. {
  839. // Were we on the winning team?
  840. int iTeam = event->GetInt( "team" );
  841. if ( ( iTeam >= FIRST_GAME_TEAM ) && ( iTeam == GetLocalPlayerTeam() ) )
  842. {
  843. IncrementCount();
  844. }
  845. }
  846. }
  847. };
  848. DECLARE_ACHIEVEMENT( CAchievementTFProcess_WinRounds, ACHIEVEMENT_TF_MAPS_PROCESS_WIN_ROUNDS, "TF_MAPS_PROCESS_WIN_ROUNDS", 5 );
  849. //----------------------------------------------------------------------------------------------------------------
  850. class CAchievementTFSnakewater_WinRounds : public CBaseTFAchievementSimple
  851. {
  852. void Init()
  853. {
  854. SetFlags( ACH_SAVE_GLOBAL );
  855. SetGoal( 141 );
  856. SetStoreProgressInSteam( true );
  857. SetMapNameFilter( "cp_snakewater_final1" );
  858. }
  859. virtual void ListenForEvents()
  860. {
  861. ListenForGameEvent( "teamplay_round_win" );
  862. }
  863. void FireGameEvent_Internal( IGameEvent *event )
  864. {
  865. if ( 0 == Q_strcmp( event->GetName(), "teamplay_round_win" ) )
  866. {
  867. // Were we on the winning team?
  868. int iTeam = event->GetInt( "team" );
  869. if ( ( iTeam >= FIRST_GAME_TEAM ) && ( iTeam == GetLocalPlayerTeam() ) )
  870. {
  871. IncrementCount();
  872. }
  873. }
  874. }
  875. };
  876. DECLARE_ACHIEVEMENT( CAchievementTFSnakewater_WinRounds, ACHIEVEMENT_TF_MAPS_SNAKEWATER_WIN_ROUNDS, "TF_MAPS_SNAKEWATER_WIN_ROUNDS", 5 );
  877. //----------------------------------------------------------------------------------------------------------------
  878. class CAchievementTFSnakewater_PushBackAndWin : public CBaseTFAchievementSimple
  879. {
  880. void Init()
  881. {
  882. SetFlags( ACH_SAVE_GLOBAL );
  883. SetGoal( 1 );
  884. SetMapNameFilter( "cp_snakewater_final1" );
  885. m_bFinalPointContested = false;
  886. }
  887. virtual void ListenForEvents()
  888. {
  889. ListenForGameEvent( "teamplay_round_win" );
  890. ListenForGameEvent( "teamplay_point_startcapture" );
  891. ListenForGameEvent( "teamplay_round_start" );
  892. }
  893. void FireGameEvent_Internal( IGameEvent *event )
  894. {
  895. const char *pszEventName = event->GetName();
  896. if ( FStrEq( pszEventName, "teamplay_round_win" ) )
  897. {
  898. int iTeam = event->GetInt( "team" );
  899. if ( ( iTeam >= FIRST_GAME_TEAM ) && ( iTeam == GetLocalPlayerTeam() ) )
  900. {
  901. if ( m_bFinalPointContested )
  902. {
  903. AwardAchievement();
  904. }
  905. }
  906. }
  907. else if ( FStrEq( pszEventName, "teamplay_point_startcapture" ) )
  908. {
  909. if ( ObjectiveResource() && ( ObjectiveResource()->GetBaseControlPointForTeam( GetLocalPlayerTeam() ) == event->GetInt( "cp" ) ) )
  910. {
  911. m_bFinalPointContested = true;
  912. }
  913. }
  914. else if ( FStrEq( pszEventName, "teamplay_round_start" ) )
  915. {
  916. m_bFinalPointContested = false;
  917. }
  918. }
  919. private:
  920. bool m_bFinalPointContested;
  921. };
  922. DECLARE_ACHIEVEMENT( CAchievementTFSnakewater_PushBackAndWin, ACHIEVEMENT_TF_MAPS_SNAKEWATER_PUSH_BACK_AND_WIN, "TF_MAPS_SNAKEWATER_PUSH_BACK_AND_WIN", 5 );
  923. //----------------------------------------------------------------------------------------------------------------
  924. class CAchievementTFSnakewater_TeamKill : public CBaseTFAchievementSimple
  925. {
  926. void Init()
  927. {
  928. SetFlags( ACH_SAVE_GLOBAL | ACH_LISTEN_PLAYER_KILL_ENEMY_EVENTS );
  929. SetGoal( 1 );
  930. SetMapNameFilter( "cp_snakewater_final1" );
  931. }
  932. virtual void Event_EntityKilled( CBaseEntity *pVictim, CBaseEntity *pAttacker, CBaseEntity *pInflictor, IGameEvent *event )
  933. {
  934. if ( TFGameRules() && ( TFGameRules()->State_Get() == GR_STATE_RND_RUNNING ) )
  935. {
  936. if ( pAttacker && ( pAttacker->GetTeamNumber() == GetLocalPlayerTeam() ) )
  937. {
  938. C_TFPlayer *pTFAttacker = ToTFPlayer( pAttacker );
  939. C_TFPlayer *pTFVictim = ToTFPlayer( pVictim );
  940. if ( pTFAttacker && pTFAttacker->GetTeam() && pTFVictim && pTFVictim->GetTeam() )
  941. {
  942. // must have 12 or more players on the server
  943. if ( pTFAttacker->GetTeam()->GetNumPlayers() + pTFVictim->GetTeam()->GetNumPlayers() >= 12 )
  944. {
  945. bool bSomeAlive = false;
  946. int nTeamCount = pTFVictim->GetTeam()->GetNumPlayers();
  947. for ( int i = 0; i < nTeamCount; i++ )
  948. {
  949. C_BasePlayer *pTemp = pTFVictim->GetTeam()->GetPlayer( i );
  950. if ( pTemp && ( pTemp != pTFVictim ) && pTemp->IsAlive() )
  951. {
  952. // Found one
  953. bSomeAlive = true;
  954. break;
  955. }
  956. }
  957. if ( !bSomeAlive )
  958. {
  959. AwardAchievement();
  960. }
  961. }
  962. }
  963. }
  964. }
  965. }
  966. };
  967. DECLARE_ACHIEVEMENT( CAchievementTFSnakewater_TeamKill, ACHIEVEMENT_TF_MAPS_SNAKEWATER_TEAM_KILL, "TF_MAPS_SNAKEWATER_TEAM_KILL", 5 );
  968. //----------------------------------------------------------------------------------------------------------------
  969. class CAchievementTFSnakewater_DoubleAirDeaths : public CBaseTFAchievementSimple
  970. {
  971. void Init()
  972. {
  973. SetFlags( ACH_SAVE_GLOBAL | ACH_LISTEN_KILL_EVENTS );
  974. SetGoal( 1 );
  975. SetMapNameFilter( "cp_snakewater_final1" );
  976. ResetTracking();
  977. }
  978. void ResetTracking()
  979. {
  980. m_PotentialPartners.RemoveAll();
  981. m_nKilledLocalPlayer = -1;
  982. }
  983. virtual void ListenForEvents()
  984. {
  985. ListenForGameEvent( "localplayer_respawn" );
  986. ListenForGameEvent( "player_spawn" );
  987. }
  988. void FireGameEvent_Internal( IGameEvent *event )
  989. {
  990. const char *pszEvent = event->GetName();
  991. if ( FStrEq( pszEvent, "localplayer_respawn" ) )
  992. {
  993. ResetTracking();
  994. }
  995. else if ( FStrEq( pszEvent, "player_spawn" ) )
  996. {
  997. int nUserId = event->GetInt( "userid" );
  998. if ( nUserId > 0 )
  999. {
  1000. int iIndex = m_PotentialPartners.Find( nUserId );
  1001. if ( iIndex != m_PotentialPartners.InvalidIndex() )
  1002. {
  1003. m_PotentialPartners.Remove( iIndex );
  1004. }
  1005. }
  1006. }
  1007. }
  1008. virtual void Event_EntityKilled( CBaseEntity *pVictim, CBaseEntity *pAttacker, CBaseEntity *pInflictor, IGameEvent *event )
  1009. {
  1010. C_TFPlayer *pTFAttacker = ToTFPlayer( pAttacker );
  1011. C_TFPlayer *pTFVictim = ToTFPlayer( pVictim );
  1012. C_TFPlayer *pTFLocalPlayer = C_TFPlayer::GetLocalTFPlayer();
  1013. // was the victim rocket jumping?
  1014. if ( event->GetBool( "rocket_jump" ) )
  1015. {
  1016. if ( pTFAttacker && pTFVictim && ( pTFAttacker != pTFVictim ) && ( ( pTFAttacker == pTFLocalPlayer ) || ( pTFVictim == pTFLocalPlayer ) ) )
  1017. {
  1018. int iWeaponID = event->GetInt( "weaponid" );
  1019. if ( ( iWeaponID == TF_WEAPON_ROCKETLAUNCHER ) || ( iWeaponID == TF_WEAPON_ROCKETLAUNCHER_DIRECTHIT ) )
  1020. {
  1021. if ( pTFAttacker == pTFLocalPlayer )
  1022. {
  1023. if ( m_PotentialPartners.Find( pTFVictim->GetUserID() ) == m_PotentialPartners.InvalidIndex() )
  1024. {
  1025. m_PotentialPartners.AddToTail( pTFVictim->GetUserID() );
  1026. }
  1027. }
  1028. else if ( pTFVictim == pTFLocalPlayer )
  1029. {
  1030. m_nKilledLocalPlayer = pTFAttacker->GetUserID();
  1031. }
  1032. // evaluate the achievement
  1033. if ( ( m_nKilledLocalPlayer > -1 ) && ( m_PotentialPartners.Find( m_nKilledLocalPlayer ) != m_PotentialPartners.InvalidIndex() ) )
  1034. {
  1035. AwardAchievement();
  1036. }
  1037. }
  1038. }
  1039. }
  1040. }
  1041. CUtlVector< int > m_PotentialPartners; // userIDs of the players the localPlayer killed
  1042. int m_nKilledLocalPlayer; // userID of the player who killed the localPlayer
  1043. };
  1044. DECLARE_ACHIEVEMENT( CAchievementTFSnakewater_DoubleAirDeaths, ACHIEVEMENT_TF_MAPS_SNAKEWATER_DOUBLE_AIR_DEATHS, "TF_MAPS_SNAKEWATER_DOUBLE_AIR_DEATHS", 5 );
  1045. //----------------------------------------------------------------------------------------------------------------
  1046. class CAchievementTFSnakewater_KillEnemiesInMiddle : public CBaseTFAchievementSimple
  1047. {
  1048. void Init()
  1049. {
  1050. SetFlags( ACH_SAVE_GLOBAL );
  1051. SetGoal( 15 );
  1052. SetStoreProgressInSteam( true );
  1053. SetMapNameFilter( "cp_snakewater_final1" );
  1054. }
  1055. virtual void ListenForEvents()
  1056. {
  1057. ListenForGameEvent( "player_killed_achievement_zone" );
  1058. }
  1059. void FireGameEvent_Internal( IGameEvent *event )
  1060. {
  1061. if ( FStrEq( event->GetName(), "player_killed_achievement_zone" ) )
  1062. {
  1063. CTFPlayer *pLocalPlayer = ToTFPlayer( C_BasePlayer::GetLocalPlayer() );
  1064. CTFPlayer *pAttacker = ToTFPlayer( UTIL_PlayerByIndex( event->GetInt( "attacker" ) ) );
  1065. CTFPlayer *pVictim = ToTFPlayer( UTIL_PlayerByIndex( event->GetInt( "victim" ) ) );
  1066. if ( pLocalPlayer && ( pLocalPlayer == pAttacker ) && pVictim && ( pVictim->GetTeamNumber() != pAttacker->GetTeamNumber() ) )
  1067. {
  1068. IncrementCount();
  1069. }
  1070. }
  1071. }
  1072. };
  1073. DECLARE_ACHIEVEMENT( CAchievementTFSnakewater_KillEnemiesInMiddle, ACHIEVEMENT_TF_MAPS_SNAKEWATER_KILL_ENEMIES_IN_MIDDLE, "TF_MAPS_SNAKEWATER_KILL_ENEMIES_IN_MIDDLE", 5 );
  1074. //----------------------------------------------------------------------------------------------------------------
  1075. class CAchievementTFPowerhouse_WinRounds : public CBaseTFAchievementSimple
  1076. {
  1077. void Init()
  1078. {
  1079. SetFlags( ACH_SAVE_GLOBAL );
  1080. SetGoal( 142 );
  1081. SetStoreProgressInSteam( true );
  1082. SetMapNameFilter( "cp_powerhouse" );
  1083. }
  1084. virtual void ListenForEvents()
  1085. {
  1086. ListenForGameEvent( "teamplay_round_win" );
  1087. }
  1088. void FireGameEvent_Internal( IGameEvent *event )
  1089. {
  1090. if ( 0 == Q_strcmp( event->GetName(), "teamplay_round_win" ) )
  1091. {
  1092. // Were we on the winning team?
  1093. int iTeam = event->GetInt( "team" );
  1094. if ( ( iTeam >= FIRST_GAME_TEAM ) && ( iTeam == GetLocalPlayerTeam() ) )
  1095. {
  1096. IncrementCount();
  1097. }
  1098. }
  1099. }
  1100. };
  1101. DECLARE_ACHIEVEMENT( CAchievementTFPowerhouse_WinRounds, ACHIEVEMENT_TF_MAPS_POWERHOUSE_WIN_ROUNDS, "TF_MAPS_POWERHOUSE_WIN_ROUNDS", 5 );
  1102. //----------------------------------------------------------------------------------------------------------------
  1103. class CAchievementTFPowerhouse_PushBackAndWin : public CBaseTFAchievementSimple
  1104. {
  1105. void Init()
  1106. {
  1107. SetFlags( ACH_SAVE_GLOBAL );
  1108. SetGoal( 1 );
  1109. SetMapNameFilter( "cp_powerhouse" );
  1110. m_bFinalPointContested = false;
  1111. }
  1112. virtual void ListenForEvents()
  1113. {
  1114. ListenForGameEvent( "teamplay_round_win" );
  1115. ListenForGameEvent( "teamplay_point_startcapture" );
  1116. ListenForGameEvent( "teamplay_round_start" );
  1117. ListenForGameEvent( "localplayer_changeteam" );
  1118. }
  1119. void FireGameEvent_Internal( IGameEvent *event )
  1120. {
  1121. const char *pszEventName = event->GetName();
  1122. if ( FStrEq( pszEventName, "teamplay_round_win" ) )
  1123. {
  1124. int iTeam = event->GetInt( "team" );
  1125. if ( ( iTeam >= FIRST_GAME_TEAM ) && ( iTeam == GetLocalPlayerTeam() ) )
  1126. {
  1127. if ( m_bFinalPointContested )
  1128. {
  1129. AwardAchievement();
  1130. }
  1131. }
  1132. }
  1133. else if ( FStrEq( pszEventName, "teamplay_point_startcapture" ) )
  1134. {
  1135. if ( ObjectiveResource() && ( ObjectiveResource()->GetBaseControlPointForTeam( GetLocalPlayerTeam() ) == event->GetInt( "cp" ) ) )
  1136. {
  1137. m_bFinalPointContested = true;
  1138. }
  1139. }
  1140. else if ( FStrEq( pszEventName, "teamplay_round_start" ) || FStrEq( pszEventName, "localplayer_changeteam" ) )
  1141. {
  1142. m_bFinalPointContested = false;
  1143. }
  1144. }
  1145. private:
  1146. bool m_bFinalPointContested;
  1147. };
  1148. DECLARE_ACHIEVEMENT( CAchievementTFPowerhouse_PushBackAndWin, ACHIEVEMENT_TF_MAPS_POWERHOUSE_PUSH_BACK_AND_WIN, "TF_MAPS_POWERHOUSE_PUSH_BACK_AND_WIN", 5 );
  1149. //----------------------------------------------------------------------------------------------------------------
  1150. class CAchievementTFPowerhouse_FastFinalCap : public CBaseTFAchievementSimple
  1151. {
  1152. void Init()
  1153. {
  1154. SetFlags( ACH_SAVE_GLOBAL );
  1155. SetGoal( 1 );
  1156. SetMapNameFilter( "cp_powerhouse" );
  1157. ResetCounts();
  1158. }
  1159. void ResetCounts()
  1160. {
  1161. m_bRecentCapper = false;
  1162. iCapCount = 0;
  1163. iCapTimes[0] = 0.0f;
  1164. iCapTimes[1] = 0.0f;
  1165. }
  1166. virtual void ListenForEvents( void )
  1167. {
  1168. ListenForGameEvent( "teamplay_point_captured" );
  1169. ListenForGameEvent( "teamplay_round_win" );
  1170. ListenForGameEvent( "teamplay_round_start" );
  1171. }
  1172. void FireGameEvent_Internal( IGameEvent *event )
  1173. {
  1174. const char *pszEventName = event->GetName();
  1175. CTFPlayer *pLocalPlayer = ToTFPlayer( C_BasePlayer::GetLocalPlayer() );
  1176. if ( !pLocalPlayer )
  1177. return;
  1178. if ( FStrEq( pszEventName, "teamplay_point_captured" ) )
  1179. {
  1180. m_bRecentCapper = false;
  1181. int iTeam = event->GetInt( "team" );
  1182. if ( ( iTeam >= FIRST_GAME_TEAM ) && ( iTeam == pLocalPlayer->GetTeamNumber() ) )
  1183. {
  1184. iCapTimes[iCapCount % 2] = gpGlobals->curtime;
  1185. iCapCount++;
  1186. const char *cappers = event->GetString( "cappers" );
  1187. for ( int i = 0; i < Q_strlen( cappers ); i++ )
  1188. {
  1189. int iPlayerIndex = (int)cappers[i];
  1190. CTFPlayer *pPlayer = ToTFPlayer( UTIL_PlayerByIndex( iPlayerIndex ) );
  1191. if ( pPlayer == pLocalPlayer )
  1192. {
  1193. m_bRecentCapper = true;
  1194. }
  1195. }
  1196. }
  1197. }
  1198. else if ( FStrEq( pszEventName, "teamplay_round_win" ) )
  1199. {
  1200. // If we're the winners and we were involved in capping the last point, we get this achievement.
  1201. int iTeam = event->GetInt( "team" );
  1202. if ( ( iTeam >= FIRST_GAME_TEAM ) && ( iTeam == pLocalPlayer->GetTeamNumber() ) && m_bRecentCapper )
  1203. {
  1204. if ( fabs( iCapTimes[1] - iCapTimes[0] ) <= 15.0f )
  1205. {
  1206. AwardAchievement();
  1207. }
  1208. }
  1209. ResetCounts();
  1210. }
  1211. else if ( FStrEq( pszEventName, "teamplay_round_start" ) )
  1212. {
  1213. ResetCounts();
  1214. }
  1215. }
  1216. private:
  1217. bool m_bRecentCapper;
  1218. int iCapCount;
  1219. float iCapTimes[2];
  1220. };
  1221. DECLARE_ACHIEVEMENT( CAchievementTFPowerhouse_FastFinalCap, ACHIEVEMENT_TF_MAPS_POWERHOUSE_FAST_FINAL_CAP, "TF_MAPS_POWERHOUSE_FAST_FINAL_CAP", 5 );
  1222. //----------------------------------------------------------------------------------------------------------------
  1223. class CAchievementTFPowerhouse_KillCappingPlayer : public CBaseTFAchievement
  1224. {
  1225. void Init()
  1226. {
  1227. SetFlags( ACH_SAVE_GLOBAL );
  1228. SetGoal( 15 );
  1229. SetStoreProgressInSteam( true );
  1230. SetMapNameFilter( "cp_powerhouse" );
  1231. }
  1232. virtual void ListenForEvents()
  1233. {
  1234. ListenForGameEvent( "killed_capping_player" );
  1235. }
  1236. void FireGameEvent_Internal( IGameEvent *event )
  1237. {
  1238. if ( FStrEq( event->GetName(), "killed_capping_player" ) )
  1239. {
  1240. C_TFPlayer *pLocalPlayer = C_TFPlayer::GetLocalTFPlayer();
  1241. if ( pLocalPlayer )
  1242. {
  1243. int iKiller = event->GetInt( "killer", 0 );
  1244. if ( iKiller == pLocalPlayer->entindex() )
  1245. {
  1246. IncrementCount();
  1247. }
  1248. }
  1249. }
  1250. }
  1251. };
  1252. DECLARE_ACHIEVEMENT( CAchievementTFPowerhouse_KillCappingPlayer, ACHIEVEMENT_TF_MAPS_POWERHOUSE_KILL_CAPPING_PLAYER, "TF_MAPS_POWERHOUSE_KILL_CAPPING_PLAYER", 5 );
  1253. //----------------------------------------------------------------------------------------------------------------
  1254. class CAchievementTFPowerhouse_KillEnemyInWater : public CBaseTFAchievementSimple
  1255. {
  1256. public:
  1257. void Init()
  1258. {
  1259. SetFlags( ACH_SAVE_GLOBAL | ACH_LISTEN_KILL_ENEMY_EVENTS );
  1260. SetGoal( 5 );
  1261. SetStoreProgressInSteam( true );
  1262. SetMapNameFilter( "cp_powerhouse" );
  1263. }
  1264. virtual void Event_EntityKilled( CBaseEntity *pVictim, CBaseEntity *pAttacker, CBaseEntity *pInflictor, IGameEvent *event )
  1265. {
  1266. if ( !pVictim || !pVictim->IsPlayer() )
  1267. return;
  1268. C_BasePlayer *pLocalPlayer = C_BasePlayer::GetLocalPlayer();
  1269. if ( pAttacker == pLocalPlayer && pVictim != pLocalPlayer )
  1270. {
  1271. if ( pVictim->GetWaterLevel() != WL_NotInWater )
  1272. {
  1273. IncrementCount();
  1274. }
  1275. }
  1276. }
  1277. };
  1278. DECLARE_ACHIEVEMENT( CAchievementTFPowerhouse_KillEnemyInWater, ACHIEVEMENT_TF_MAPS_POWERHOUSE_KILL_ENEMY_IN_WATER, "TF_MAPS_POWERHOUSE_KILL_ENEMY_IN_WATER", 5 );
  1279. #endif // CLIENT_DLL