Skip to content

Commit

Permalink
这一周成果
Browse files Browse the repository at this point in the history
  • Loading branch information
Hu1night committed Apr 21, 2024
1 parent 995a119 commit 1386f9e
Show file tree
Hide file tree
Showing 9 changed files with 193 additions and 48 deletions.
2 changes: 2 additions & 0 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -977,6 +977,8 @@ set_src(GAME_SERVER GLOB_RECURSE src/game/server
gamemodes/ctf.h
gamemodes/dm.cpp
gamemodes/dm.h
gamemodes/hunterc.cpp
gamemodes/hunterc.h
gamemodes/huntern.cpp
gamemodes/huntern.h
gamemodes/instagib.cpp
Expand Down
2 changes: 2 additions & 0 deletions autoexec.cfg
Original file line number Diff line number Diff line change
Expand Up @@ -167,6 +167,7 @@ add_gametypefile "gtdm" "itdm" "room_config/modes/gtdm.rcfg"
add_gametypefile "gctf" "ictf" "room_config/modes/gctf.rcfg"
add_gametypefile "catch" "catch" "room_config/modes/catch.rcfg"
add_gametypefile "zcatch" "zcatch" "room_config/modes/zcatch.rcfg"
add_gametypefile "hunterc" "hunterc" "room_config/modes/hunterc.rcfg"

# Lobby override config, room 0 will be have this config applied after room config
sv_lobby_override_config "room_config/lobby.rcfg"
Expand All @@ -179,6 +180,7 @@ sv_roomlist_vote_title "=== ROOM LIST ==="
add_vote "" "info"
add_vote "=== CREATE NEW ROOM ===" "info"
add_vote "HunterN" "create huntern"
add_vote "HunterC" "create hunterc"
add_vote "Deathmatch" "create dm"
add_vote "Team Deathmatch" "create tdm"
add_vote "Capture the Flag" "create ctf"
Expand Down
1 change: 1 addition & 0 deletions datasrc/network.py
Original file line number Diff line number Diff line change
Expand Up @@ -52,6 +52,7 @@
TEAM_SPECTATORS=-1,
TEAM_RED,
TEAM_BLUE,
NUM_TEAMS,
FLAG_MISSING=-3,
FLAG_ATSTAND,
Expand Down
4 changes: 2 additions & 2 deletions src/game/server/gamecontroller.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1871,8 +1871,8 @@ void IGameController::Snap(int SnappingClient)
}
else
{
pGameDataObj->m_FlagCarrierRed = 0;
pGameDataObj->m_FlagCarrierBlue = 0;
pGameDataObj->m_FlagCarrierRed = FLAG_ATSTAND;
pGameDataObj->m_FlagCarrierBlue = FLAG_ATSTAND;
}
}
else
Expand Down
2 changes: 2 additions & 0 deletions src/game/server/gamemodes.h
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@
#include "gamemodes/instagib.h"

#include "gamemodes/huntern.h"
#include "gamemodes/hunterc.h"

#endif

Expand All @@ -26,4 +27,5 @@ REGISTER_GAME_TYPE(ictf, CGameControllerICTF)
REGISTER_GAME_TYPE(catch, CGameControllerCatch)
REGISTER_GAME_TYPE(zcatch, CGameControllerZCatch)
REGISTER_GAME_TYPE(huntern, CGameControllerHunterN)
REGISTER_GAME_TYPE(hunterc, CGameControllerHunterC)
#endif
120 changes: 120 additions & 0 deletions src/game/server/gamemodes/hunterc.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,120 @@
/* (c) Magnus Auvinen. See licence.txt in the root of the distribution for more information. */
/* If you are missing that file, acquire a complete release at teeworlds.com. */
#include "hunterc.h"

#include <game/server/entities/character.h>
#include <game/server/entities/flag.h>
#include <game/server/weapons.h>
//#include <game/server/entities/pickup.h>
#include <game/server/classes.h>

CGameControllerHunterC::CGameControllerHunterC() :
CGameControllerHunterN()
{
m_pGameType = "hunterC";

m_apClassSpawnMsg[4] = "这局你是平民Civic! 消灭敌方队伍胜利! \n猎人双倍伤害 有瞬杀锤子和破片榴";
m_pFlag = nullptr;
}

void CGameControllerHunterC::OnGameStart(bool IsRound)
{
m_GameFlags = HUNTERN_GAMEFLAGS;
m_DoWinchenkClassTick = -1;

int PreselectPlayerCount = 0; // 最近没当过猎人的玩家的计数
int rHunter = 0; // 猎人选择随机数

for(int i = 0; i < MAX_CLIENTS; ++i) // 重置并计数玩家
{
CPlayer *pPlayer = GetPlayerIfInRoom(i);
if(!pPlayer || pPlayer->GetTeam() == TEAM_SPECTATORS
|| (pPlayer->m_RespawnDisabled && (!pPlayer->GetCharacter() || !pPlayer->GetCharacter()->IsAlive())))
continue;

pPlayer->m_AmongUsTeam = TEAM_RED; // 重置队伍
pPlayer->m_HiddenScore = 0; // 重置隐藏分
pPlayer->m_UseHunterWeapon = false; // 默认武器
pPlayer->m_Class = CLASS_CIVIC; // 重置玩家为平民
if(pPlayer->m_Preselect) // 猎人选择伪随机!我们要在m_Preselect的玩家里面选择猎人
++PreselectPlayerCount; // 计数有PreselectPlayerCount个玩家
}

if(m_aTeamSize[TEAM_RED] < 2) // m_aTeamSize[TEAM_RED] = 非队伍模式的人数量
return;

m_NumHunter = (m_aTeamSize[TEAM_RED] - 2) / m_HunterRatio + 1; // 我们要多少个猎人
str_format(m_HunterList, sizeof(m_HunterList), "本回合的 %d 个Hunter是: ", m_NumHunter); // Generate Hunter info message 生成猎人列表消息头

SendChatTarget(-1, "——————欢迎来到HunterN猎人杀——————");
//MatchFlag = -1; // 要成为Jug的玩家不存在 撤了
char aBuf[64];
str_format(aBuf, sizeof(aBuf), "本回合有 %d 个猎人Hunter has been selected.", m_NumHunter);
SendChatTarget(-1, aBuf);
SendChatTarget(-1, "规则:每回合秘密抽选猎人 猎人对战平民 活人看不到死人消息");
SendChatTarget(-1, " 猎人双倍伤害 有瞬杀锤子(平民无锤)和破片榴弹(对自己无伤)");
SendChatTarget(-1, "分辨队友并消灭敌人来取得胜利!Be warned! Sudden Death.");

for(int iHunter = m_NumHunter; iHunter > 0; --iHunter) // 需要选择m_NumHunter个猎人
{
if(PreselectPlayerCount <= 0) // 先检查m_Preselect的玩家够不够(即所有玩家是不是最近都当过猎人了) 如果不够就重置所有玩家的m_Preselect
{
for(int i = 0; i < MAX_CLIENTS; ++i) // 重置所有玩家的m_Preselect
{
CPlayer *pPlayer = GetPlayerIfInRoom(i);
if(!pPlayer || pPlayer->GetTeam() == TEAM_SPECTATORS
|| (pPlayer->m_RespawnDisabled && (!pPlayer->GetCharacter() || !pPlayer->GetCharacter()->IsAlive())))
continue;

pPlayer->m_Preselect = true; // 设置m_Preselect为真(包括猎人 主要是为了随机性)
if(pPlayer->m_Class == CLASS_CIVIC) // 只有平民才可以被计数
++PreselectPlayerCount; // 重置PreselectPlayerCount
}
}

rHunter = rand() % PreselectPlayerCount; // 在PreselectPlayerCount个玩家里选择第rHunter个猎人

for(int i = 0; i < MAX_CLIENTS; ++i) // 在PreselectPlayerCount个玩家里选择第rHunter个玩家为猎人
{
CPlayer *pPlayer = GetPlayerIfInRoom(i);
if(!pPlayer || pPlayer->GetTeam() == TEAM_SPECTATORS
|| (pPlayer->m_RespawnDisabled && (!pPlayer->GetCharacter() || !pPlayer->GetCharacter()->IsAlive()))
|| !pPlayer->m_Preselect || pPlayer->m_Class != CLASS_CIVIC) // 在平民职业的玩家里面选择猎人
continue; // 首先剔除不在选择队列里的玩家

if(rHunter != 0) // 计数玩家
{
rHunter--;
continue;
}

pPlayer->m_Class = CLASS_HUNTER; // 设置猎人Flag
//pPlayer->m_UseHunterWeapon = true; // 使用猎人武器 // 在OnCharachar里面设置
pPlayer->m_AmongUsTeam = TEAM_BLUE; // 设置队伍
pPlayer->m_Preselect = false; // 把m_Preselect设为否 即最近当过猎人
--PreselectPlayerCount;

// Generate Hunter info message 生成猎人列表消息
str_append(m_HunterList, Server()->ClientName(i), sizeof(m_HunterList));
str_append(m_HunterList, ", ", sizeof(m_HunterList));

m_pFlag = new CFlag(GameWorld(), 0, pPlayer->GetCharacter()->m_Pos);

break;
}
}

for(int i = 0; i < MAX_CLIENTS; ++i) // 循环所有旁观者 把猎人列表告诉他们
{
CPlayer *pPlayer = GetPlayerIfInRoom(i);
if(!pPlayer)
continue;

if(pPlayer->GetTeam() == TEAM_SPECTATORS)
SendChatTarget(pPlayer->GetCID(), m_HunterList); // 给膀胱者发
else if(pPlayer->GetCharacter() && pPlayer->GetCharacter()->IsAlive()) // 这个玩家出生了 所以OnCharacterSpawn已经过了
OnResetClass(pPlayer->GetCharacter()); // 在这里给他们Class提示和武器
}

InstanceConsole()->Print(IConsole::OUTPUT_LEVEL_STANDARD, "huntern", m_HunterList);
}
20 changes: 20 additions & 0 deletions src/game/server/gamemodes/hunterc.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
/* (c) Magnus Auvinen. See licence.txt in the root of the distribution for more information. */
/* If you are missing that file, acquire a complete release at teeworlds.com. */
#ifndef GAME_SERVER_GAMEMODES_HUNTERC_H
#define GAME_SERVER_GAMEMODES_HUNTERC_H
#include <game/server/gamemodes/huntern.h>

class CGameControllerHunterC : public CGameControllerHunterN
{
public:
CGameControllerHunterC();

// event
//virtual void OnCharacterSpawn(class CCharacter *pChr) override;

void OnGameStart(bool IsRound) override;

CFlag *m_pFlag;
};

#endif // GAME_SERVER_GAMEMODES_HUNTERC_H
80 changes: 39 additions & 41 deletions src/game/server/gamemodes/huntern.cpp
Original file line number Diff line number Diff line change
@@ -1,7 +1,5 @@
/* (c) Magnus Auvinen. See licence.txt in the root of the distribution for more information. */
/* If you are missing that file, acquire a complete release at teeworlds.com. */
#include <engine/shared/config.h>

#include "huntern.h"
#include <game/server/entities/character.h>
#include <game/server/weapons.h>
Expand Down Expand Up @@ -177,10 +175,11 @@ static void ConRevive(IConsole::IResult *pResult, void *pUserData)
CGameControllerHunterN::CGameControllerHunterN() :
IGameController()
{
m_pGameType = "HunterN";
m_pGameType = "hunterN";
m_GameFlags = HUNTERN_GAMEFLAGS;
// 生存模式,回合模式,SUDDENDEATH,回合终局显示游戏结束,游戏结束/旁观Snap队伍模式

m_DoWinchenkClassTick = -1;
mem_zero(m_aMaprotation, sizeof(m_aMaprotation));

INSTANCE_CONFIG_INT(&m_HunterRatio, "htn_hunt_ratio", 4, 2, MAX_CLIENTS, CFGFLAG_CHAT | CFGFLAG_INSTANCE, "几个玩家里选取一个猎人(整数,默认4,限制2~64)");
Expand Down Expand Up @@ -246,6 +245,11 @@ void CGameControllerHunterN::CycleMap() // 循环地图
}

// Event
void CGameControllerHunterN::OnInit()
{
SetGameState(IGS_END_MATCH, m_GameoverTime); // EndMatch();
}

void CGameControllerHunterN::OnWorldReset() // 重置部分值和职业选择
{
m_GameFlags = HUNTERN_GAMEFLAGS;
Expand Down Expand Up @@ -385,36 +389,31 @@ void CGameControllerHunterN::DoWincheckRound() // check for time based win
return;
}

int PlayerCount = 0;
int TeamRedCount = 0;
int TeamBlueCount = 0;
int TeamPlayerCount[NUM_TEAMS] = {0};
int AliveTeamPlayerCount[NUM_TEAMS] = {0};

for(int i = 0; i < MAX_CLIENTS; ++i) // 计数玩家
{
CPlayer *pPlayer = GetPlayerIfInRoom(i);
if(!pPlayer || pPlayer->GetTeam() == TEAM_SPECTATORS
|| (pPlayer->m_RespawnDisabled
&& (!pPlayer->GetCharacter() || !pPlayer->GetCharacter()->IsAlive())))
if(!pPlayer || pPlayer->GetTeam() == TEAM_SPECTATORS)
continue;

++PlayerCount;
if(pPlayer->m_AmongUsTeam == TEAM_RED)
++TeamRedCount;
else //if(pPlayer->m_AmongUsTeam == TEAM_BLUE)
++TeamBlueCount;
TeamPlayerCount[pPlayer->m_AmongUsTeam]++; // 计数双方队伍人数
if(!pPlayer->m_RespawnDisabled || (pPlayer->GetCharacter() && pPlayer->GetCharacter()->IsAlive()))
AliveTeamPlayerCount[pPlayer->m_AmongUsTeam]++; // 计数活着的玩家
}

if(!IsTimeEnd && (TeamBlueCount && TeamRedCount)) // 如果不是回合限时结束则需某队死光
if(!IsTimeEnd && (AliveTeamPlayerCount[TEAM_RED] && AliveTeamPlayerCount[TEAM_BLUE])) // 如果不是回合限时结束则需某队死光
{
m_DoWinchenkClassTick = 0;
m_DoWinchenkClassTick = -1;
return;
}

// 游戏结束
m_aTeamscore[TEAM_RED] = 0; // 重置
m_aTeamscore[TEAM_BLUE] = 0;
m_aTeamscore[TEAM_RED] = TeamPlayerCount[TEAM_RED]; // 队伍分数形式显示双方人数
m_aTeamscore[TEAM_BLUE] = TeamPlayerCount[TEAM_BLUE];

for(int i = 0; i < MAX_CLIENTS; ++i) // 进行队伍分数 玩家分数和隐藏分操作
for(int i = 0; i < MAX_CLIENTS; ++i) // 进行玩家分数和隐藏分操作
{
CPlayer *pPlayer = GetPlayerIfInRoom(i);
if(!pPlayer)
Expand All @@ -425,29 +424,24 @@ void CGameControllerHunterN::DoWincheckRound() // check for time based win

if(pPlayer->m_HiddenScore) // 玩家拥有隐藏分
pPlayer->m_Score += pPlayer->m_HiddenScore; // 添加隐藏分

if(pPlayer->m_AmongUsTeam == TEAM_RED) // 队伍分数显示双方人数
m_aTeamscore[TEAM_RED] += 1; // 累加队伍分数 用队伍分数显示有几个民
else //if(pPlayer->m_AmongUsTeam == TEAM_BLUE)
m_aTeamscore[TEAM_BLUE] += 1; // 累加队伍分数 用队伍分数显示有几个猎
}

if(!PlayerCount)
if(!AliveTeamPlayerCount[TEAM_RED] && !AliveTeamPlayerCount[TEAM_BLUE])
{
SendChatTarget(-1, "两人幸终!");
}
else if(!TeamBlueCount) // no blue
else if(!AliveTeamPlayerCount[TEAM_BLUE]) // no blue
{
SendChatTarget(-1, m_HunterList);
SendChatTarget(-1, "红队胜利"); // 平民为红队
SendChatTarget(-1, "平民胜利");
//GameWorld()->CreateSoundGlobal(SOUND_CTF_CAPTURE); // 猎人死的时候够吵了

m_aTeamscore[TEAM_BLUE] = -m_aTeamscore[TEAM_BLUE]; // 反转蓝队分数 显示"红队胜利"
}
else if(!TeamRedCount) // no red
else if(!AliveTeamPlayerCount[TEAM_RED]) // no red
{
//SendChatTarget(-1, m_HunterList); // 猎人胜利不显示列表(因为平民被打死的时候已经显示过了)
SendChatTarget(-1, "蓝队胜利"); // 猎人为蓝队
SendChatTarget(-1, "猎人胜利");
GameWorld()->CreateSoundGlobal(SOUND_CTF_CAPTURE);

m_aTeamscore[TEAM_RED] = -m_aTeamscore[TEAM_RED]; // 反转红队分数 就会显示"蓝队胜利"
Expand Down Expand Up @@ -552,15 +546,18 @@ int CGameControllerHunterN::OnCharacterDeath(class CCharacter *pVictim, class CP
if(m_GameState != IGS_GAME_RUNNING) // 如果游戏在正常运行
return DEATH_SKIP_SCORE; // 跳过内置分数逻辑

if(pVictim->GetPlayer()->m_Class == CLASS_HUNTER) // 猎人死亡 进行计数和猎人死亡报告
int VictimCID = pVictim->GetPlayer()->GetCID();

switch(pVictim->GetPlayer()->m_Class) // 猎人死亡 进行计数和猎人死亡报告
{
case CLASS_HUNTER:
--m_NumHunter; // 计数猎人死亡

if(m_EffectHunterDeath)
GameWorld()->CreatePlayerSpawn(pVictim->m_Pos); // 死亡给个出生烟

char aBuf[64];
str_format(aBuf, sizeof(aBuf), "Hunter '%s' was defeated! ", Server()->ClientName(pVictim->GetPlayer()->GetCID()));
str_format(aBuf, sizeof(aBuf), "Hunter '%s' was defeated! ", Server()->ClientName(VictimCID));

if(m_BroadcastHunterDeath == 1 ||
!m_NumHunter) // 如果是最后一个Hunter
Expand Down Expand Up @@ -589,16 +586,17 @@ int CGameControllerHunterN::OnCharacterDeath(class CCharacter *pVictim, class CP
GameWorld()->CreateSoundGlobal(SOUND_CTF_DROP, CmaskOne(pPlayer->GetCID()));
}
}
}
else if(pVictim->GetPlayer()->m_Class == CLASS_CIVIC) // 平民死亡
{
break;
case CLASS_JUGGERNAUT:
//char aBuf[64];
str_format(aBuf, sizeof(aBuf), "Juggernaut '%s' was defeated! ", Server()->ClientName(VictimCID));
SendChatTarget(-1, aBuf);
GameWorld()->CreateSoundGlobal(SOUND_CTF_CAPTURE);
break;
default://case CLASS_CIVIC: // 平民死亡
GameWorld()->CreateSoundGlobal(SOUND_CTF_DROP);
break;
}
/*else if(pVictim->GetPlayer()->m_Class == CLASS_JUGGERNAUT)
{
SendChatTarget(-1, "Juggernaut was defeated!");
GameWorld()->CreateSoundGlobal(SOUND_CTF_CAPTURE);
}*/

if(pKiller != pVictim->GetPlayer()) // 不是自杀
{
Expand All @@ -611,12 +609,12 @@ int CGameControllerHunterN::OnCharacterDeath(class CCharacter *pVictim, class CP
char aBuf[64];
str_format(aBuf, sizeof(aBuf), "你被 '%s' 的%s所杀", Server()->ClientName(pKiller->GetCID()), m_apWeaponName[Weapon + 1]);

SendChatTarget(pVictim->GetPlayer()->GetCID(), aBuf); // 给被弄死的人发
SendChatTarget(VictimCID, aBuf); // 给被弄死的人发
}
}

if(m_NumHunter) // 如果没有猎人(当然是全死光啦) 就不要发猎人列表 等EndMatch
SendChatTarget(pVictim->GetPlayer()->GetCID(), m_HunterList); // 给被弄死的人发猎人列表
SendChatTarget(VictimCID, m_HunterList); // 给被弄死的人发猎人列表

m_DoWinchenkClassTick = ((Server()->TickSpeed() * m_Wincheckdeley) / 1000); // 延时终局

Expand Down
Loading

0 comments on commit 1386f9e

Please sign in to comment.