diff --git a/src/game/gamecore.cpp b/src/game/gamecore.cpp index 581d587e4..6306f03df 100644 --- a/src/game/gamecore.cpp +++ b/src/game/gamecore.cpp @@ -1,6 +1,5 @@ // copyright (c) 2007 magnus auvinen, see licence.txt for more info #include "gamecore.h" -#include "server/entities/character.h" const char *CTuningParams::m_apNames[] = { @@ -209,7 +208,7 @@ void CCharacterCore::Tick(bool UseInput) } // Check against other players first - if(m_pWorld && m_pWorld->m_Tuning.m_PlayerHooking)//TODO:TEAM + if(m_pWorld && m_pWorld->m_Tuning.m_PlayerHooking) { float Dist = 0.0f; for(int i = 0; i < MAX_CLIENTS; i++) diff --git a/src/game/gamecore.h b/src/game/gamecore.h index c3bfa2356..d16c50c5e 100644 --- a/src/game/gamecore.h +++ b/src/game/gamecore.h @@ -174,6 +174,7 @@ class CCharacterCore { CWorldCore *m_pWorld; CCollision *m_pCollision; + public: vec2 m_Pos; vec2 m_Vel; diff --git a/src/game/server/entities/character.cpp b/src/game/server/entities/character.cpp index 9a7c376f5..7f88104ab 100644 --- a/src/game/server/entities/character.cpp +++ b/src/game/server/entities/character.cpp @@ -298,7 +298,7 @@ void CCharacter::FireWeapon() m_NumObjectsHit = 0; GameServer()->CreateSound(m_Pos, SOUND_HAMMER_FIRE); - if (!g_Config.m_SvHit) break;//TODO:TEAM + if (!g_Config.m_SvHit) break; CCharacter *aEnts[64]; int Hits = 0; @@ -310,7 +310,7 @@ void CCharacter::FireWeapon() CCharacter *Target = aEnts[i]; //for DDRace mod or any other mod, which needs hammer hits through the wall remove second condition - if ((Target == this) /*|| GameServer()->Collision()->IntersectLine(ProjStartPos, Target->m_Pos, NULL, NULL)*/) + if ((Target == this || Target->Team() != this->Team()) /*|| GameServer()->Collision()->IntersectLine(ProjStartPos, Target->m_Pos, NULL, NULL)*/) continue; // set his velocity to fast upward (for now) diff --git a/src/game/server/entities/projectile.cpp b/src/game/server/entities/projectile.cpp index 01ecfff37..2c877d073 100644 --- a/src/game/server/entities/projectile.cpp +++ b/src/game/server/entities/projectile.cpp @@ -99,8 +99,9 @@ void CProjectile::Tick() if(m_LifeSpan > -1) m_LifeSpan--; - if( (TargetChr && ((g_Config.m_SvHit || m_Owner == -1) || TargetChr == OwnerChar)) || Collide)//TODO:TEAM + if( (TargetChr && (g_Config.m_SvHit || m_Owner == -1 || TargetChr == OwnerChar)) || Collide)//TODO:TEAM { + //if(OwnerChar != 0 && OwnerChar->Team() != TargetChr->Team()) return; if(m_Explosive/*??*/ && (!TargetChr || (TargetChr && !m_Freeze))) { GameServer()->CreateExplosion(ColPos, m_Owner, m_Weapon, (m_Owner == -1)?true:false); diff --git a/src/game/server/gamecontext.cpp b/src/game/server/gamecontext.cpp index 4853782b2..32c3a20f8 100644 --- a/src/game/server/gamecontext.cpp +++ b/src/game/server/gamecontext.cpp @@ -143,9 +143,10 @@ void CGameContext::CreateExplosion(vec2 p, int Owner, int Weapon, bool NoDamage) ForceDir = normalize(Diff); l = 1-clamp((l-InnerRadius)/(Radius-InnerRadius), 0.0f, 1.0f); float Dmg = 6 * l; - if((int)Dmg)//TODO:TEAM + if((int)Dmg) if((g_Config.m_SvHit||NoDamage) || Owner == apEnts[i]->m_pPlayer->GetCID()) { + if(apEnts[i]->Team() != GetPlayerChar(Owner)->Team()) continue; apEnts[i]->TakeDamage(ForceDir*Dmg*2, (int)Dmg, Owner, Weapon); if(!g_Config.m_SvHit||NoDamage) break; } diff --git a/src/game/server/gamemodes/DDRace.h b/src/game/server/gamemodes/DDRace.h index ba772aade..2b6175448 100644 --- a/src/game/server/gamemodes/DDRace.h +++ b/src/game/server/gamemodes/DDRace.h @@ -3,7 +3,7 @@ #ifndef DDRACE_H #define DDRACE_H #include -#include +#include class CGameControllerDDRace : public IGameController diff --git a/src/game/teams.cpp b/src/game/teams.cpp new file mode 100644 index 000000000..ebdf21d57 --- /dev/null +++ b/src/game/teams.cpp @@ -0,0 +1,103 @@ +#include "teams.h" + + +CTeams::CTeams(CGameContext *pGameContext) : m_pGameContext(pGameContext) { + for(int i = 0; i < MAX_CLIENTS; ++i) { + m_Team[i] = 0; + m_TeamState[i] = EMPTY; + m_TeeFinished[i] = false; + } +} + +void CTeams::OnCharacterStart(int id) { + int Tick = Server()->Tick(); + if(m_Team[id] == 0) { + CCharacter* Char = Character(id); + Char->m_RaceState = RACE_STARTED; + Char->m_StartTime = Tick; + Char->m_RefreshTime = Tick; + } else { + if(m_TeamState[m_Team[id]] <= CLOSED) { + ChangeTeamState(m_Team[id], STARTED); + + for(int i = 0; i < MAX_CLIENTS; ++i) { + if(m_Team[i] == m_Team[id]) { + CCharacter* Char = Character(i); + + Char->m_RaceState = RACE_STARTED; + Char->m_StartTime = Tick; + Char->m_RefreshTime = Tick; + } + } + } + } +} + +void CTeams::OnCharacterFinish(int id) { + if(m_Team[id] == 0) { + Character(id)->OnFinish(); + } else { + m_TeeFinished[id] = true; + if(TeamFinished(m_Team[id])) { + ChangeTeamState(m_Team[id], FINISHED);//TODO: Make it better + for(int i = 0; i < MAX_CLIENTS; ++i) { + if(SameTeam(i, id)) { + CCharacter * Char = Character(i); + if(Char != 0) { + Char->OnFinish(); + m_TeeFinished[i] = false; + } //else { + // m_Team[id] = 0; //i saw zomby =) + //} + } + } + + } + } +} + +bool CTeams::SetCharacterTeam(int id, int Team) { + //TODO: Send error message + if(id < 0 || id >= MAX_CLIENTS || Team < 0 || Team >= MAX_CLIENTS) { + return false; + } + if(m_TeamState[Team] >= CLOSED) { + return false; + } + if(m_Team[id] != 0 && m_TeamState[m_Team[id]] != EMPTY) { + bool NoOneInOldTeam = true; + for(int i = 0; i < MAX_CLIENTS; ++i) { + if(SameTeam(i, id)) { + NoOneInOldTeam = false;//all good exists someone in old team + break; + } + } + if(NoOneInOldTeam) { + m_TeamState[m_Team[id]] = EMPTY; + } + } + m_Team[id] = Team; + if(m_TeamState[Team] == EMPTY) { + ChangeTeamState(Team, OPEN); + } + return true; +} + +void CTeams::ChangeTeamState(int Team, int State) { + m_TeamState[Team] = State; +} + + + +bool CTeams::TeamFinished(int Team) { + for(int i = 0; i < MAX_CLIENTS; ++i) { + if(m_Team[i] == Team && !m_TeeFinished[i]) { + return false; + } + } + return true; +} + +bool CTeams::SameTeam(int Cid1, int Cid2) { + return m_Team[Cid1] = m_Team[Cid2]; +} diff --git a/src/game/teams.h b/src/game/teams.h new file mode 100644 index 000000000..e3d0f86dd --- /dev/null +++ b/src/game/teams.h @@ -0,0 +1,47 @@ +#ifndef GAME_SERVER_TEAMS_H +#define GAME_SERVER_TEAMS_H + +#include +#include + +class CTeams { + int m_Team[MAX_CLIENTS]; + int m_TeamState[MAX_CLIENTS]; + bool m_TeeFinished[MAX_CLIENTS]; + + class CGameContext * m_pGameContext; + +public: + enum { + EMPTY, + OPEN, + CLOSED, + STARTED, + FINISHED + }; + + CTeams(CGameContext *pGameContext); + + //helper methods + CCharacter* Character(int id) { return GameServer()->GetPlayerChar(id); } + + class CGameContext *GameServer() { return m_pGameContext; } + class IServer *Server() { return m_pGameContext->Server(); } + + void OnCharacterStart(int id); + void OnCharacterFinish(int id); + + bool SetCharacterTeam(int id, int Team); + + void ChangeTeamState(int Team, int State); + + bool TeamFinished(int Team); + + bool SameTeam(int Cid1, int Cid2); + + int GetTeam(int Cid) { + return m_Team[Cid]; + } +}; + +#endif \ No newline at end of file