Browse Source

Merge branch 'dev' of github.com:sendssf/THUAI6 into dev

tags/v0.1.0
sendssf 2 years ago
parent
commit
fbfca4cda7
53 changed files with 952 additions and 883 deletions
  1. +5
    -5
      CAPI/cpp/API/include/structures.h
  2. +4
    -4
      CAPI/cpp/API/include/utils.hpp
  3. +8
    -8
      CAPI/cpp/API/src/DebugAPI.cpp
  4. +91
    -67
      CAPI/cpp/API/src/logic.cpp
  5. +5
    -1
      CAPI/cpp/API/src/main.cpp
  6. +200
    -332
      CAPI/cpp/proto/Message2Clients.pb.cc
  7. +92
    -236
      CAPI/cpp/proto/Message2Clients.pb.h
  8. +8
    -8
      CAPI/python/PyAPI/DebugAPI.py
  9. +0
    -3
      CAPI/python/PyAPI/structures.py
  10. +0
    -3
      CAPI/python/PyAPI/utils.py
  11. +2
    -2
      CAPI/python/requirements.txt
  12. +1
    -1
      CAPI/python/run.sh
  13. +4
    -4
      dependency/proto/Message2Clients.proto
  14. +0
    -0
      dependency/proto/Proto.sln
  15. +205
    -0
      dependency/py/rank.py
  16. +10
    -2
      dependency/shell/compile.sh
  17. +1
    -1
      dependency/shell/run.sh
  18. +7
    -7
      docs/GameRules.md
  19. +1
    -1
      docs/使用文档.md
  20. +97
    -0
      docs/游戏机制与平衡性调整更新草案.md
  21. +10
    -0
      docs/版本更新说明.md
  22. +9
    -0
      logic/Client/MainWindow.xaml
  23. +70
    -70
      logic/Client/MainWindow.xaml.cs
  24. +0
    -1
      logic/GameClass/GameObj/Bullet/BombedBullet.cs
  25. +6
    -8
      logic/GameClass/GameObj/Bullet/Bullet.Ghost.cs
  26. +6
    -7
      logic/GameClass/GameObj/Bullet/Bullet.cs
  27. +0
    -1
      logic/GameClass/GameObj/Character/Character.Skill.cs
  28. +2
    -3
      logic/GameClass/GameObj/Character/Character.cs
  29. +9
    -20
      logic/GameClass/GameObj/GameObj.cs
  30. +0
    -1
      logic/GameClass/GameObj/Map/Chest.cs
  31. +17
    -1
      logic/GameClass/GameObj/Map/Door.cs
  32. +0
    -1
      logic/GameClass/GameObj/Map/Doorway.cs
  33. +0
    -1
      logic/GameClass/GameObj/Map/EmergencyExit.cs
  34. +0
    -1
      logic/GameClass/GameObj/Map/Generator.cs
  35. +0
    -1
      logic/GameClass/GameObj/Map/Wall.cs
  36. +0
    -1
      logic/GameClass/GameObj/Map/Window.cs
  37. +17
    -11
      logic/GameClass/GameObj/Moveable.cs
  38. +0
    -1
      logic/GameClass/GameObj/OutOfBoundBlock.cs
  39. +0
    -1
      logic/GameClass/GameObj/PickedProp.cs
  40. +23
    -24
      logic/GameClass/GameObj/Prop.cs
  41. +4
    -4
      logic/GameEngine/MoveEngine.cs
  42. +7
    -7
      logic/Gaming/ActionManager.cs
  43. +8
    -8
      logic/Gaming/AttackManager.cs
  44. +8
    -7
      logic/Gaming/CharacterManager .cs
  45. +6
    -6
      logic/Gaming/PropManager.cs
  46. +0
    -1
      logic/Preparation/Interface/IGameObj.cs
  47. +1
    -2
      logic/Preparation/Interface/IMoveable.cs
  48. +0
    -1
      logic/Preparation/Utility/GameData.cs
  49. +1
    -5
      logic/Server/CopyInfo.cs
  50. +1
    -1
      logic/Server/GameServer.cs
  51. +1
    -1
      logic/cmd/PlaybackServer.cmd
  52. +1
    -1
      logic/cmd/gameServerAndClient.cmd
  53. +4
    -0
      logic/cmd/video.cmd

+ 5
- 5
CAPI/cpp/API/include/structures.h View File

@@ -197,7 +197,7 @@ namespace THUAI6

PlayerType playerType; // 玩家类型
std::vector<PropType> props;
PlaceType place; // 所处格子的类型
// PlaceType place; // 所处格子的类型
BulletType bulletType;

PlayerState playerState;
@@ -232,9 +232,9 @@ namespace THUAI6
double facingDirection; // 朝向
int64_t guid; // 全局唯一ID
PlayerType team; // 子弹所属队伍
PlaceType place; // 所处格子的类型
double bombRange; // 炸弹爆炸范围
int32_t speed; // 子弹速度
// PlaceType place; // 所处格子的类型
double bombRange; // 炸弹爆炸范围
int32_t speed; // 子弹速度
};

struct BombedBullet
@@ -253,7 +253,7 @@ namespace THUAI6
int32_t y;
int64_t guid;
PropType type;
PlaceType place;
// PlaceType place;
double facingDirection; // 朝向
};



+ 4
- 4
CAPI/cpp/API/include/utils.hpp View File

@@ -227,7 +227,7 @@ namespace Proto2THUAI6
tricker->timeUntilSkillAvailable.clear();
for (int i = 0; i < trickerMsg.time_until_skill_available().size(); i++)
tricker->timeUntilSkillAvailable.push_back(trickerMsg.time_until_skill_available(i));
tricker->place = placeTypeDict[trickerMsg.place()];
// tricker->place = placeTypeDict[trickerMsg.place()];
tricker->playerState = playerStateDict[trickerMsg.player_state()];
tricker->props.clear();
for (int i = 0; i < trickerMsg.prop().size(); i++)
@@ -269,7 +269,7 @@ namespace Proto2THUAI6
student->props.clear();
for (int i = 0; i < studentMsg.prop().size(); i++)
student->props.push_back(propTypeDict[studentMsg.prop(i)]);
student->place = placeTypeDict[studentMsg.place()];
// student->place = placeTypeDict[studentMsg.place()];
student->playerState = playerStateDict[studentMsg.player_state()];
student->determination = studentMsg.determination();
student->addiction = studentMsg.addiction();
@@ -286,7 +286,7 @@ namespace Proto2THUAI6
prop->x = propMsg.x();
prop->y = propMsg.y();
prop->type = propTypeDict[propMsg.type()];
prop->place = placeTypeDict[propMsg.place()];
// prop->place = placeTypeDict[propMsg.place()];
prop->guid = propMsg.guid();
prop->facingDirection = propMsg.facing_direction();
return prop;
@@ -313,7 +313,7 @@ namespace Proto2THUAI6
bullet->facingDirection = bulletMsg.facing_direction();
bullet->guid = bulletMsg.guid();
bullet->team = playerTypeDict[bulletMsg.team()];
bullet->place = placeTypeDict[bulletMsg.place()];
// bullet->place = placeTypeDict[bulletMsg.place()];
bullet->bombRange = bulletMsg.bomb_range();
bullet->speed = bulletMsg.speed();
return bullet;


+ 8
- 8
CAPI/cpp/API/src/DebugAPI.cpp View File

@@ -684,7 +684,7 @@ void StudentDebugAPI::PrintStudent() const
{
logger->info("******Student Info******");
logger->info("playerID={}, GUID={}, x={}, y={}", student->playerID, student->guid, student->x, student->y);
logger->info("speed={}, view range={}, place={}, radius={}", student->speed, student->viewRange, THUAI6::placeTypeDict[student->place], student->radius);
logger->info("speed={}, view range={}, radius={}", student->speed, student->viewRange, student->radius);
std::string skillTime = "";
for (const auto& time : student->timeUntilSkillAvailable)
skillTime += std::to_string(time) + ", ";
@@ -709,7 +709,7 @@ void TrickerDebugAPI::PrintStudent() const
{
logger->info("******Student Info******");
logger->info("playerID={}, GUID={}, x={}, y={}", student->playerID, student->guid, student->x, student->y);
logger->info("speed={}, view range={}, place={}, radius={}", student->speed, student->viewRange, THUAI6::placeTypeDict[student->place], student->radius);
logger->info("speed={}, view range={}, radius={}", student->speed, student->viewRange, student->radius);
std::string skillTime = "";
for (const auto& time : student->timeUntilSkillAvailable)
skillTime += std::to_string(time) + ", ";
@@ -734,7 +734,7 @@ void StudentDebugAPI::PrintTricker() const
{
logger->info("******Tricker Info******");
logger->info("playerID={}, GUID={}, x={}, y={}", tricker->playerID, tricker->guid, tricker->x, tricker->y);
logger->info("speed={}, view range={}, place={}, radius={}", tricker->speed, tricker->viewRange, THUAI6::placeTypeDict[tricker->place], tricker->radius);
logger->info("speed={}, view range={}, radius={}", tricker->speed, tricker->viewRange, tricker->radius);
std::string skillTime = "";
for (const auto& time : tricker->timeUntilSkillAvailable)
skillTime += std::to_string(time) + ", ";
@@ -758,7 +758,7 @@ void TrickerDebugAPI::PrintTricker() const
{
logger->info("******Tricker Info******");
logger->info("playerID={}, GUID={}, x={}, y={}", tricker->playerID, tricker->guid, tricker->x, tricker->y);
logger->info("speed={}, view range={}, place={}, radius={}", tricker->speed, tricker->viewRange, THUAI6::placeTypeDict[tricker->place], tricker->radius);
logger->info("speed={}, view range={}, radius={}", tricker->speed, tricker->viewRange, tricker->radius);
std::string skillTime = "";
for (const auto& time : tricker->timeUntilSkillAvailable)
skillTime += std::to_string(time) + ", ";
@@ -781,7 +781,7 @@ void StudentDebugAPI::PrintProp() const
for (auto prop : logic.GetProps())
{
logger->info("******Prop Info******");
logger->info("GUID={}, x={}, y={}, place={}, facing direction={}", prop->guid, prop->x, prop->y, THUAI6::placeTypeDict[prop->place], prop->facingDirection);
logger->info("GUID={}, x={}, y={}, facing direction={}", prop->guid, prop->x, prop->y, prop->facingDirection);
logger->info("*********************\n");
}
}
@@ -791,7 +791,7 @@ void TrickerDebugAPI::PrintProp() const
for (auto prop : logic.GetProps())
{
logger->info("******Prop Info******");
logger->info("GUID={}, x={}, y={}, place={}, facing direction={}", prop->guid, prop->x, prop->y, THUAI6::placeTypeDict[prop->place], prop->facingDirection);
logger->info("GUID={}, x={}, y={}, facing direction={}", prop->guid, prop->x, prop->y, prop->facingDirection);
logger->info("*********************\n");
}
}
@@ -801,7 +801,7 @@ void StudentDebugAPI::PrintSelfInfo() const
auto student = logic.StudentGetSelfInfo();
logger->info("******Self Info******");
logger->info("playerID={}, GUID={}, x={}, y={}", student->playerID, student->guid, student->x, student->y);
logger->info("speed={}, view range={}, place={}, radius={}", student->speed, student->viewRange, THUAI6::placeTypeDict[student->place], student->radius);
logger->info("speed={}, view range={}, radius={}", student->speed, student->viewRange, student->radius);
std::string skillTime = "";
for (const auto& time : student->timeUntilSkillAvailable)
skillTime += std::to_string(time) + ", ";
@@ -824,7 +824,7 @@ void TrickerDebugAPI::PrintSelfInfo() const
auto tricker = logic.TrickerGetSelfInfo();
logger->info("******Self Info******");
logger->info("playerID={}, GUID={}, x={}, y={}", tricker->playerID, tricker->guid, tricker->x, tricker->y);
logger->info("speed={}, view range={}, place={}, radius={}", tricker->speed, tricker->viewRange, THUAI6::placeTypeDict[tricker->place], tricker->radius);
logger->info("speed={}, view range={}, radius={}", tricker->speed, tricker->viewRange, tricker->radius);
std::string skillTime = "";
for (const auto& time : tricker->timeUntilSkillAvailable)
skillTime += std::to_string(time) + ", ";


+ 91
- 67
CAPI/cpp/API/src/logic.cpp View File

@@ -315,68 +315,81 @@ void Logic::ProcessMessage()
{
auto messageThread = [this]()
{
logger->info("Message thread start!");
pComm->AddPlayer(playerID, playerType, studentType, trickerType);
while (gameState != THUAI6::GameState::GameEnd)
try
{
auto clientMsg = pComm->GetMessage2Client(); // 在获得新消息之前阻塞
logger->debug("Get message from server!");
gameState = Proto2THUAI6::gameStateDict[clientMsg.game_state()];
switch (gameState)
logger->info("Message thread start!");
pComm->AddPlayer(playerID, playerType, studentType, trickerType);
while (gameState != THUAI6::GameState::GameEnd)
{
case THUAI6::GameState::GameStart:
logger->info("Game Start!");
auto clientMsg = pComm->GetMessage2Client(); // 在获得新消息之前阻塞
logger->debug("Get message from server!");
gameState = Proto2THUAI6::gameStateDict[clientMsg.game_state()];
switch (gameState)
{
case THUAI6::GameState::GameStart:
logger->info("Game Start!");

// 读取地图
for (const auto& item : clientMsg.obj_message())
if (Proto2THUAI6::messageOfObjDict[item.message_of_obj_case()] == THUAI6::MessageOfObj::MapMessage)
{
auto map = std::vector<std::vector<THUAI6::PlaceType>>();
auto mapResult = item.map_message();
for (int i = 0; i < item.map_message().row_size(); i++)
// 读取地图
for (const auto& item : clientMsg.obj_message())
if (Proto2THUAI6::messageOfObjDict[item.message_of_obj_case()] == THUAI6::MessageOfObj::MapMessage)
{
std::vector<THUAI6::PlaceType> row;
for (int j = 0; j < mapResult.row(i).col_size(); j++)
auto map = std::vector<std::vector<THUAI6::PlaceType>>();
auto mapResult = item.map_message();
for (int i = 0; i < item.map_message().row_size(); i++)
{
if (Proto2THUAI6::placeTypeDict.count(mapResult.row(i).col(j)) == 0)
logger->error("Unknown place type!");
row.push_back(Proto2THUAI6::placeTypeDict[mapResult.row(i).col(j)]);
std::vector<THUAI6::PlaceType> row;
for (int j = 0; j < mapResult.row(i).col_size(); j++)
{
if (Proto2THUAI6::placeTypeDict.count(mapResult.row(i).col(j)) == 0)
logger->error("Unknown place type!");
row.push_back(Proto2THUAI6::placeTypeDict[mapResult.row(i).col(j)]);
}
map.push_back(std::move(row));
}
map.push_back(std::move(row));
bufferState->gameMap = std::move(map);
currentState->gameMap = bufferState->gameMap;
logger->info("Map loaded!");
break;
}
bufferState->gameMap = std::move(map);
currentState->gameMap = bufferState->gameMap;
logger->info("Map loaded!");
break;
if (currentState->gameMap.empty())
{
logger->error("Map not loaded!");
throw std::runtime_error("Map not loaded!");
}
if (currentState->gameMap.empty())
{
logger->error("Map not loaded!");
throw std::runtime_error("Map not loaded!");
}
LoadBuffer(clientMsg);
LoadBuffer(clientMsg);

AILoop = true;
UnBlockAI();
AILoop = true;
UnBlockAI();

break;
case THUAI6::GameState::GameRunning:
break;
case THUAI6::GameState::GameRunning:

LoadBuffer(clientMsg);
break;
default:
logger->debug("Unknown GameState!");
break;
LoadBuffer(clientMsg);
break;
default:
logger->debug("Unknown GameState!");
break;
}
}
{
std::lock_guard<std::mutex> lock(mtxBuffer);
bufferUpdated = true;
counterBuffer = -1;
}
cvBuffer.notify_one();
logger->info("Game End!");
AILoop = false;
}
catch (const std::exception& e)
{
std::lock_guard<std::mutex> lock(mtxBuffer);
bufferUpdated = true;
counterBuffer = -1;
std::cerr << "C++ Exception: " << e.what() << std::endl;
AILoop = false;
}
catch (...)
{
std::cerr << "Unknown Exception!" << std::endl;
AILoop = false;
}
cvBuffer.notify_one();
logger->info("Game End!");
AILoop = false;
};
std::thread(messageThread).detach();
}
@@ -576,7 +589,7 @@ void Logic::LoadBufferCase(const protobuf::MessageOfObj& item)
else if (Proto2THUAI6::newsTypeDict[news.news_case()] == THUAI6::NewsType::BinaryMessage)
{
messageQueue.emplace(std::make_pair(news.to_id(), news.binary_message()));
logger->debug("Add News!");
logger->debug("Add Binary News!");
}
else
logger->error("Unknown NewsType!");
@@ -699,7 +712,7 @@ bool Logic::HaveView(int gridX, int gridY, int selfX, int selfY, int viewRange)
void Logic::Main(CreateAIFunc createAI, std::string IP, std::string port, bool file, bool print, bool warnOnly)
{
// 建立日志组件
auto fileLogger = std::make_shared<spdlog::sinks::basic_file_sink_mt>("logs/logic-log.txt", true);
auto fileLogger = std::make_shared<spdlog::sinks::basic_file_sink_mt>(fmt::format("logs/logic-{}-log.txt", playerID), true);
auto printLogger = std::make_shared<spdlog::sinks::stdout_color_sink_mt>();
std::string pattern = "[logic] [%H:%M:%S.%e] [%l] %v";
fileLogger->set_pattern(pattern);
@@ -747,30 +760,41 @@ void Logic::Main(CreateAIFunc createAI, std::string IP, std::string port, bool f
// 构造AI线程
auto AIThread = [&]()
{
try
{
std::unique_lock<std::mutex> lock(mtxAI);
cvAI.wait(lock, [this]()
{ return AIStart; });
}
auto ai = createAI(playerID);

while (AILoop)
{
if (asynchronous)
{
Wait();
timer->StartTimer();
timer->Play(*ai);
timer->EndTimer();
std::unique_lock<std::mutex> lock(mtxAI);
cvAI.wait(lock, [this]()
{ return AIStart; });
}
else
auto ai = createAI(playerID);

while (AILoop)
{
Update();
timer->StartTimer();
timer->Play(*ai);
timer->EndTimer();
if (asynchronous)
{
Wait();
timer->StartTimer();
timer->Play(*ai);
timer->EndTimer();
}
else
{
Update();
timer->StartTimer();
timer->Play(*ai);
timer->EndTimer();
}
}
}
catch (const std::exception& e)
{
std::cerr << "C++ Exception: " << e.what() << std::endl;
}
catch (...)
{
std::cerr << "Unknown Exception!" << std::endl;
}
};

// 连接服务器


+ 5
- 1
CAPI/cpp/API/src/main.cpp View File

@@ -115,7 +115,11 @@ int THUAI6Main(int argc, char** argv, CreateAIFunc AIBuilder)
}
catch (const std::exception& e)
{
std::cerr << e.what() << '\n';
std::cerr << "C++ Exception: " << e.what() << '\n';
}
catch (...)
{
std::cerr << "Unknown Exception\n";
}
return 0;
}


+ 200
- 332
CAPI/cpp/proto/Message2Clients.pb.cc
File diff suppressed because it is too large
View File


+ 92
- 236
CAPI/cpp/proto/Message2Clients.pb.h View File

@@ -318,21 +318,20 @@ namespace protobuf
kSpeedFieldNumber = 3,
kDeterminationFieldNumber = 4,
kAddictionFieldNumber = 5,
kPlaceFieldNumber = 7,
kGuidFieldNumber = 10,
kPlayerStateFieldNumber = 9,
kGuidFieldNumber = 10,
kBulletTypeFieldNumber = 12,
kLearningSpeedFieldNumber = 13,
kTreatSpeedFieldNumber = 14,
kPlayerIdFieldNumber = 15,
kTreatSpeedFieldNumber = 14,
kViewRangeFieldNumber = 16,
kRadiusFieldNumber = 17,
kDangerAlertFieldNumber = 19,
kScoreFieldNumber = 20,
kDangerAlertFieldNumber = 19,
kTreatProgressFieldNumber = 21,
kRescueProgressFieldNumber = 22,
kStudentTypeFieldNumber = 23,
kFacingDirectionFieldNumber = 24,
kStudentTypeFieldNumber = 23,
};
// repeated double time_until_skill_available = 6;
int time_until_skill_available_size() const;
@@ -452,14 +451,14 @@ namespace protobuf
void _internal_set_addiction(int32_t value);

public:
// .protobuf.PlaceType place = 7;
void clear_place();
::protobuf::PlaceType place() const;
void set_place(::protobuf::PlaceType value);
// .protobuf.PlayerState player_state = 9;
void clear_player_state();
::protobuf::PlayerState player_state() const;
void set_player_state(::protobuf::PlayerState value);

private:
::protobuf::PlaceType _internal_place() const;
void _internal_set_place(::protobuf::PlaceType value);
::protobuf::PlayerState _internal_player_state() const;
void _internal_set_player_state(::protobuf::PlayerState value);

public:
// int64 guid = 10;
@@ -471,16 +470,6 @@ namespace protobuf
int64_t _internal_guid() const;
void _internal_set_guid(int64_t value);

public:
// .protobuf.PlayerState player_state = 9;
void clear_player_state();
::protobuf::PlayerState player_state() const;
void set_player_state(::protobuf::PlayerState value);

private:
::protobuf::PlayerState _internal_player_state() const;
void _internal_set_player_state(::protobuf::PlayerState value);

public:
// .protobuf.BulletType bullet_type = 12;
void clear_bullet_type();
@@ -501,16 +490,6 @@ namespace protobuf
int32_t _internal_learning_speed() const;
void _internal_set_learning_speed(int32_t value);

public:
// int32 treat_speed = 14;
void clear_treat_speed();
int32_t treat_speed() const;
void set_treat_speed(int32_t value);

private:
int32_t _internal_treat_speed() const;
void _internal_set_treat_speed(int32_t value);

public:
// int64 player_id = 15;
void clear_player_id();
@@ -521,6 +500,16 @@ namespace protobuf
int64_t _internal_player_id() const;
void _internal_set_player_id(int64_t value);

public:
// int32 treat_speed = 14;
void clear_treat_speed();
int32_t treat_speed() const;
void set_treat_speed(int32_t value);

private:
int32_t _internal_treat_speed() const;
void _internal_set_treat_speed(int32_t value);

public:
// int32 view_range = 16;
void clear_view_range();
@@ -541,16 +530,6 @@ namespace protobuf
int32_t _internal_radius() const;
void _internal_set_radius(int32_t value);

public:
// double danger_alert = 19;
void clear_danger_alert();
double danger_alert() const;
void set_danger_alert(double value);

private:
double _internal_danger_alert() const;
void _internal_set_danger_alert(double value);

public:
// int32 score = 20;
void clear_score();
@@ -561,6 +540,16 @@ namespace protobuf
int32_t _internal_score() const;
void _internal_set_score(int32_t value);

public:
// double danger_alert = 19;
void clear_danger_alert();
double danger_alert() const;
void set_danger_alert(double value);

private:
double _internal_danger_alert() const;
void _internal_set_danger_alert(double value);

public:
// int32 treat_progress = 21;
void clear_treat_progress();
@@ -581,16 +570,6 @@ namespace protobuf
int32_t _internal_rescue_progress() const;
void _internal_set_rescue_progress(int32_t value);

public:
// .protobuf.StudentType student_type = 23;
void clear_student_type();
::protobuf::StudentType student_type() const;
void set_student_type(::protobuf::StudentType value);

private:
::protobuf::StudentType _internal_student_type() const;
void _internal_set_student_type(::protobuf::StudentType value);

public:
// double facing_direction = 24;
void clear_facing_direction();
@@ -601,6 +580,16 @@ namespace protobuf
double _internal_facing_direction() const;
void _internal_set_facing_direction(double value);

public:
// .protobuf.StudentType student_type = 23;
void clear_student_type();
::protobuf::StudentType student_type() const;
void set_student_type(::protobuf::StudentType value);

private:
::protobuf::StudentType _internal_student_type() const;
void _internal_set_student_type(::protobuf::StudentType value);

public:
// @@protoc_insertion_point(class_scope:protobuf.MessageOfStudent)

@@ -623,21 +612,20 @@ namespace protobuf
int32_t speed_;
int32_t determination_;
int32_t addiction_;
int place_;
int64_t guid_;
int player_state_;
int64_t guid_;
int bullet_type_;
int32_t learning_speed_;
int32_t treat_speed_;
int64_t player_id_;
int32_t treat_speed_;
int32_t view_range_;
int32_t radius_;
double danger_alert_;
int32_t score_;
double danger_alert_;
int32_t treat_progress_;
int32_t rescue_progress_;
int student_type_;
double facing_direction_;
int student_type_;
mutable ::PROTOBUF_NAMESPACE_ID::internal::CachedSize _cached_size_;
};
union
@@ -812,18 +800,17 @@ namespace protobuf
kXFieldNumber = 1,
kYFieldNumber = 2,
kSpeedFieldNumber = 3,
kPlaceFieldNumber = 6,
kGuidFieldNumber = 9,
kTrickerTypeFieldNumber = 8,
kScoreFieldNumber = 10,
kGuidFieldNumber = 9,
kPlayerIdFieldNumber = 11,
kScoreFieldNumber = 10,
kViewRangeFieldNumber = 12,
kRadiusFieldNumber = 13,
kPlayerStateFieldNumber = 14,
kTrickDesireFieldNumber = 15,
kClassVolumeFieldNumber = 16,
kPlayerStateFieldNumber = 14,
kBulletTypeFieldNumber = 18,
kFacingDirectionFieldNumber = 17,
kBulletTypeFieldNumber = 18,
};
// repeated double time_until_skill_available = 5;
int time_until_skill_available_size() const;
@@ -923,14 +910,14 @@ namespace protobuf
void _internal_set_speed(int32_t value);

public:
// .protobuf.PlaceType place = 6;
void clear_place();
::protobuf::PlaceType place() const;
void set_place(::protobuf::PlaceType value);
// .protobuf.TrickerType tricker_type = 8;
void clear_tricker_type();
::protobuf::TrickerType tricker_type() const;
void set_tricker_type(::protobuf::TrickerType value);

private:
::protobuf::PlaceType _internal_place() const;
void _internal_set_place(::protobuf::PlaceType value);
::protobuf::TrickerType _internal_tricker_type() const;
void _internal_set_tricker_type(::protobuf::TrickerType value);

public:
// int64 guid = 9;
@@ -943,14 +930,14 @@ namespace protobuf
void _internal_set_guid(int64_t value);

public:
// .protobuf.TrickerType tricker_type = 8;
void clear_tricker_type();
::protobuf::TrickerType tricker_type() const;
void set_tricker_type(::protobuf::TrickerType value);
// int64 player_id = 11;
void clear_player_id();
int64_t player_id() const;
void set_player_id(int64_t value);

private:
::protobuf::TrickerType _internal_tricker_type() const;
void _internal_set_tricker_type(::protobuf::TrickerType value);
int64_t _internal_player_id() const;
void _internal_set_player_id(int64_t value);

public:
// int32 score = 10;
@@ -962,16 +949,6 @@ namespace protobuf
int32_t _internal_score() const;
void _internal_set_score(int32_t value);

public:
// int64 player_id = 11;
void clear_player_id();
int64_t player_id() const;
void set_player_id(int64_t value);

private:
int64_t _internal_player_id() const;
void _internal_set_player_id(int64_t value);

public:
// int32 view_range = 12;
void clear_view_range();
@@ -992,6 +969,16 @@ namespace protobuf
int32_t _internal_radius() const;
void _internal_set_radius(int32_t value);

public:
// .protobuf.PlayerState player_state = 14;
void clear_player_state();
::protobuf::PlayerState player_state() const;
void set_player_state(::protobuf::PlayerState value);

private:
::protobuf::PlayerState _internal_player_state() const;
void _internal_set_player_state(::protobuf::PlayerState value);

public:
// double trick_desire = 15;
void clear_trick_desire();
@@ -1013,14 +1000,14 @@ namespace protobuf
void _internal_set_class_volume(double value);

public:
// .protobuf.PlayerState player_state = 14;
void clear_player_state();
::protobuf::PlayerState player_state() const;
void set_player_state(::protobuf::PlayerState value);
// double facing_direction = 17;
void clear_facing_direction();
double facing_direction() const;
void set_facing_direction(double value);

private:
::protobuf::PlayerState _internal_player_state() const;
void _internal_set_player_state(::protobuf::PlayerState value);
double _internal_facing_direction() const;
void _internal_set_facing_direction(double value);

public:
// .protobuf.BulletType bullet_type = 18;
@@ -1032,16 +1019,6 @@ namespace protobuf
::protobuf::BulletType _internal_bullet_type() const;
void _internal_set_bullet_type(::protobuf::BulletType value);

public:
// double facing_direction = 17;
void clear_facing_direction();
double facing_direction() const;
void set_facing_direction(double value);

private:
double _internal_facing_direction() const;
void _internal_set_facing_direction(double value);

public:
// @@protoc_insertion_point(class_scope:protobuf.MessageOfTricker)

@@ -1062,18 +1039,17 @@ namespace protobuf
int32_t x_;
int32_t y_;
int32_t speed_;
int place_;
int64_t guid_;
int tricker_type_;
int32_t score_;
int64_t guid_;
int64_t player_id_;
int32_t score_;
int32_t view_range_;
int32_t radius_;
int player_state_;
double trick_desire_;
double class_volume_;
int player_state_;
int bullet_type_;
double facing_direction_;
int bullet_type_;
mutable ::PROTOBUF_NAMESPACE_ID::internal::CachedSize _cached_size_;
};
union
@@ -1249,7 +1225,6 @@ namespace protobuf
kTeamFieldNumber = 6,
kGuidFieldNumber = 5,
kBombRangeFieldNumber = 8,
kPlaceFieldNumber = 7,
kSpeedFieldNumber = 9,
};
// .protobuf.BulletType type = 1;
@@ -1321,16 +1296,6 @@ namespace protobuf
double _internal_bomb_range() const;
void _internal_set_bomb_range(double value);

public:
// .protobuf.PlaceType place = 7;
void clear_place();
::protobuf::PlaceType place() const;
void set_place(::protobuf::PlaceType value);

private:
::protobuf::PlaceType _internal_place() const;
void _internal_set_place(::protobuf::PlaceType value);

public:
// int32 speed = 9;
void clear_speed();
@@ -1360,7 +1325,6 @@ namespace protobuf
int team_;
int64_t guid_;
double bomb_range_;
int place_;
int32_t speed_;
mutable ::PROTOBUF_NAMESPACE_ID::internal::CachedSize _cached_size_;
};
@@ -1785,9 +1749,8 @@ namespace protobuf
kTypeFieldNumber = 1,
kXFieldNumber = 2,
kFacingDirectionFieldNumber = 4,
kYFieldNumber = 3,
kPlaceFieldNumber = 6,
kGuidFieldNumber = 5,
kYFieldNumber = 3,
};
// .protobuf.PropType type = 1;
void clear_type();
@@ -1818,26 +1781,6 @@ namespace protobuf
double _internal_facing_direction() const;
void _internal_set_facing_direction(double value);

public:
// int32 y = 3;
void clear_y();
int32_t y() const;
void set_y(int32_t value);

private:
int32_t _internal_y() const;
void _internal_set_y(int32_t value);

public:
// .protobuf.PlaceType place = 6;
void clear_place();
::protobuf::PlaceType place() const;
void set_place(::protobuf::PlaceType value);

private:
::protobuf::PlaceType _internal_place() const;
void _internal_set_place(::protobuf::PlaceType value);

public:
// int64 guid = 5;
void clear_guid();
@@ -1848,6 +1791,16 @@ namespace protobuf
int64_t _internal_guid() const;
void _internal_set_guid(int64_t value);

public:
// int32 y = 3;
void clear_y();
int32_t y() const;
void set_y(int32_t value);

private:
int32_t _internal_y() const;
void _internal_set_y(int32_t value);

public:
// @@protoc_insertion_point(class_scope:protobuf.MessageOfProp)

@@ -1863,9 +1816,8 @@ namespace protobuf
int type_;
int32_t x_;
double facing_direction_;
int32_t y_;
int place_;
int64_t guid_;
int32_t y_;
mutable ::PROTOBUF_NAMESPACE_ID::internal::CachedSize _cached_size_;
};
union
@@ -5502,30 +5454,6 @@ namespace protobuf
return _internal_mutable_time_until_skill_available();
}

// .protobuf.PlaceType place = 7;
inline void MessageOfStudent::clear_place()
{
_impl_.place_ = 0;
}
inline ::protobuf::PlaceType MessageOfStudent::_internal_place() const
{
return static_cast<::protobuf::PlaceType>(_impl_.place_);
}
inline ::protobuf::PlaceType MessageOfStudent::place() const
{
// @@protoc_insertion_point(field_get:protobuf.MessageOfStudent.place)
return _internal_place();
}
inline void MessageOfStudent::_internal_set_place(::protobuf::PlaceType value)
{
_impl_.place_ = value;
}
inline void MessageOfStudent::set_place(::protobuf::PlaceType value)
{
_internal_set_place(value);
// @@protoc_insertion_point(field_set:protobuf.MessageOfStudent.place)
}

// repeated .protobuf.PropType prop = 8;
inline int MessageOfStudent::_internal_prop_size() const
{
@@ -6105,30 +6033,6 @@ namespace protobuf
return _internal_mutable_time_until_skill_available();
}

// .protobuf.PlaceType place = 6;
inline void MessageOfTricker::clear_place()
{
_impl_.place_ = 0;
}
inline ::protobuf::PlaceType MessageOfTricker::_internal_place() const
{
return static_cast<::protobuf::PlaceType>(_impl_.place_);
}
inline ::protobuf::PlaceType MessageOfTricker::place() const
{
// @@protoc_insertion_point(field_get:protobuf.MessageOfTricker.place)
return _internal_place();
}
inline void MessageOfTricker::_internal_set_place(::protobuf::PlaceType value)
{
_impl_.place_ = value;
}
inline void MessageOfTricker::set_place(::protobuf::PlaceType value)
{
_internal_set_place(value);
// @@protoc_insertion_point(field_set:protobuf.MessageOfTricker.place)
}

// repeated .protobuf.PropType prop = 7;
inline int MessageOfTricker::_internal_prop_size() const
{
@@ -6649,30 +6553,6 @@ namespace protobuf
// @@protoc_insertion_point(field_set:protobuf.MessageOfBullet.team)
}

// .protobuf.PlaceType place = 7;
inline void MessageOfBullet::clear_place()
{
_impl_.place_ = 0;
}
inline ::protobuf::PlaceType MessageOfBullet::_internal_place() const
{
return static_cast<::protobuf::PlaceType>(_impl_.place_);
}
inline ::protobuf::PlaceType MessageOfBullet::place() const
{
// @@protoc_insertion_point(field_get:protobuf.MessageOfBullet.place)
return _internal_place();
}
inline void MessageOfBullet::_internal_set_place(::protobuf::PlaceType value)
{
_impl_.place_ = value;
}
inline void MessageOfBullet::set_place(::protobuf::PlaceType value)
{
_internal_set_place(value);
// @@protoc_insertion_point(field_set:protobuf.MessageOfBullet.place)
}

// double bomb_range = 8;
inline void MessageOfBullet::clear_bomb_range()
{
@@ -6993,30 +6873,6 @@ namespace protobuf
// @@protoc_insertion_point(field_set:protobuf.MessageOfProp.guid)
}

// .protobuf.PlaceType place = 6;
inline void MessageOfProp::clear_place()
{
_impl_.place_ = 0;
}
inline ::protobuf::PlaceType MessageOfProp::_internal_place() const
{
return static_cast<::protobuf::PlaceType>(_impl_.place_);
}
inline ::protobuf::PlaceType MessageOfProp::place() const
{
// @@protoc_insertion_point(field_get:protobuf.MessageOfProp.place)
return _internal_place();
}
inline void MessageOfProp::_internal_set_place(::protobuf::PlaceType value)
{
_impl_.place_ = value;
}
inline void MessageOfProp::set_place(::protobuf::PlaceType value)
{
_internal_set_place(value);
// @@protoc_insertion_point(field_set:protobuf.MessageOfProp.place)
}

// -------------------------------------------------------------------

// MessageOfPickedProp


+ 8
- 8
CAPI/python/PyAPI/DebugAPI.py View File

@@ -318,7 +318,7 @@ class StudentDebugAPI(IStudentAPI, IGameTimer):
self.__logger.info(
f"playerID={student.playerID}, GUID={student.guid}, x={student.x}, y={student.y}")
self.__logger.info(
f"speed={student.speed}, view range={student.viewRange}, place={student.place.name}, radius={student.radius}")
f"speed={student.speed}, view range={student.viewRange}, radius={student.radius}")
self.__logger.info(
f"score={student.score}, facing direction={student.facingDirection}, skill time={student.timeUntilSkillAvailable}")
studentProp = ""
@@ -342,7 +342,7 @@ class StudentDebugAPI(IStudentAPI, IGameTimer):
self.__logger.info(
f"playerID={tricker.playerID}, GUID={tricker.guid}, x={tricker.x}, y={tricker.y}")
self.__logger.info(
f"speed={tricker.speed}, view range={tricker.viewRange}, place={tricker.place.name}, radius={tricker.radius}")
f"speed={tricker.speed}, view range={tricker.viewRange}, radius={tricker.radius}")
self.__logger.info(
f"score={tricker.score}, facing direction={tricker.facingDirection}, skill time={tricker.timeUntilSkillAvailable}")
trickerProp = ""
@@ -362,7 +362,7 @@ class StudentDebugAPI(IStudentAPI, IGameTimer):
for prop in self.__logic.GetProps():
self.__logger.info("******Prop Info******")
self.__logger.info(
f"GUID={prop.guid}, x={prop.x}, y={prop.y}, place={prop.place.name}, facing direction={prop.facingDirection}")
f"GUID={prop.guid}, x={prop.x}, y={prop.y}, facing direction={prop.facingDirection}")
self.__logger.info("*********************")

def PrintSelfInfo(self) -> None:
@@ -371,7 +371,7 @@ class StudentDebugAPI(IStudentAPI, IGameTimer):
self.__logger.info(
f"playerID={student.playerID}, GUID={student.guid}, x={student.x}, y={student.y}")
self.__logger.info(
f"speed={student.speed}, view range={student.viewRange}, place={student.place.name}, radius={student.radius}")
f"speed={student.speed}, view range={student.viewRange}, radius={student.radius}")
self.__logger.info(
f"score={student.score}, facing direction={student.facingDirection}, skill time={student.timeUntilSkillAvailable}")
studentProp = ""
@@ -773,7 +773,7 @@ class TrickerDebugAPI(ITrickerAPI, IGameTimer):
self.__logger.info(
f"playerID={student.playerID}, GUID={student.guid}, x={student.x}, y={student.y}")
self.__logger.info(
f"speed={student.speed}, view range={student.viewRange}, place={student.place.name}, radius={student.radius}")
f"speed={student.speed}, view range={student.viewRange}, radius={student.radius}")
self.__logger.info(
f"score={student.score}, facing direction={student.facingDirection}, skill time={student.timeUntilSkillAvailable}")
studentProp = ""
@@ -797,7 +797,7 @@ class TrickerDebugAPI(ITrickerAPI, IGameTimer):
self.__logger.info(
f"playerID={tricker.playerID}, GUID={tricker.guid}, x={tricker.x}, y={tricker.y}")
self.__logger.info(
f"speed={tricker.speed}, view range={tricker.viewRange}, place={tricker.place.name}, radius={tricker.radius}")
f"speed={tricker.speed}, view range={tricker.viewRange}, radius={tricker.radius}")
self.__logger.info(
f"score={tricker.score}, facing direction={tricker.facingDirection}, skill time={tricker.timeUntilSkillAvailable}")
trickerProp = ""
@@ -817,7 +817,7 @@ class TrickerDebugAPI(ITrickerAPI, IGameTimer):
for prop in self.__logic.GetProps():
self.__logger.info("******Prop Info******")
self.__logger.info(
f"GUID={prop.guid}, x={prop.x}, y={prop.y}, place={prop.place.name}, facing direction={prop.facingDirection}")
f"GUID={prop.guid}, x={prop.x}, y={prop.y}, facing direction={prop.facingDirection}")
self.__logger.info("*********************")

def PrintSelfInfo(self) -> None:
@@ -826,7 +826,7 @@ class TrickerDebugAPI(ITrickerAPI, IGameTimer):
self.__logger.info(
f"playerID={tricker.playerID}, GUID={tricker.guid}, x={tricker.x}, y={tricker.y}")
self.__logger.info(
f"speed={tricker.speed}, view range={tricker.viewRange}, place={tricker.place.name}, radius={tricker.radius}")
f"speed={tricker.speed}, view range={tricker.viewRange}, radius={tricker.radius}")
self.__logger.info(
f"score={tricker.score}, facing direction={tricker.facingDirection}, skill time={tricker.timeUntilSkillAvailable}")
trickerProp = ""


+ 0
- 3
CAPI/python/PyAPI/structures.py View File

@@ -156,7 +156,6 @@ class Player:
self.timeUntilSkillAvailable: List[float] = []
self.playerType: PlayerType = PlayerType.NullPlayerType
self.prop: List[PropType] = []
self.place: PlaceType = PlaceType.NullPlaceType
self.bulletType: BulletType = BulletType.NullBulletType
self.playerState: PlayerState = PlayerState.NullState

@@ -190,7 +189,6 @@ class Prop:
self.y: int = 0
self.guid: int = 0
self.type: PropType = PropType.NullPropType
self.place: PlaceType = PlaceType.NullPlaceType
self.facingDirection: float = 0.0


@@ -202,7 +200,6 @@ class Bullet:
self.facingDirection: float = 0.0
self.guid: int = 0
self.team: PlayerType = PlayerType.NullPlayerType
self.place: PlaceType = PlaceType.NullPlaceType
self.bombRange: float = 0.0
self.speed: int = 0



+ 0
- 3
CAPI/python/PyAPI/utils.py View File

@@ -179,7 +179,6 @@ class Proto2THUAI6(NoInstance):
tricker.bulletType = Proto2THUAI6.bulletTypeDict[trickerMsg.bullet_type]
for time in trickerMsg.time_until_skill_available:
tricker.timeUntilSkillAvailable.append(time)
tricker.place = Proto2THUAI6.placeTypeDict[trickerMsg.place]
tricker.playerState = Proto2THUAI6.playerStateDict[trickerMsg.player_state]
for item in trickerMsg.prop:
tricker.prop.append(Proto2THUAI6.propTypeDict[item])
@@ -211,7 +210,6 @@ class Proto2THUAI6(NoInstance):
student.dangerAlert = studentMsg.danger_alert
for time in studentMsg.time_until_skill_available:
student.timeUntilSkillAvailable.append(time)
student.place = Proto2THUAI6.placeTypeDict[studentMsg.place]
for item in studentMsg.prop:
student.prop.append(Proto2THUAI6.propTypeDict[item])
student.studentType = Proto2THUAI6.studentTypeDict[studentMsg.student_type]
@@ -255,7 +253,6 @@ class Proto2THUAI6(NoInstance):
bullet.facingDirection = bulletMsg.facing_direction
bullet.guid = bulletMsg.guid
bullet.team = Proto2THUAI6.playerTypeDict[bulletMsg.team]
bullet.place = Proto2THUAI6.placeTypeDict[bulletMsg.place]
bullet.bombRange = bulletMsg.bomb_range
return bullet



+ 2
- 2
CAPI/python/requirements.txt View File

@@ -1,3 +1,3 @@
grpcio==1.52.0
grpcio-tools==1.52.0
grpcio==1.54.0
grpcio-tools==1.54.0
numpy

+ 1
- 1
CAPI/python/run.sh View File

@@ -1,7 +1,7 @@
#!/usr/bin/env bash

python PyAPI/main.py -I 172.22.32.1 -P 8888 -p 0 -d -o&
# python PyAPI/main.py -I 172.22.32.1 -P 8888 -p 1 -o&
python PyAPI/main.py -I 172.22.32.1 -P 8888 -p 1 -d -o&
# python PyAPI/main.py -I 172.22.32.1 -P 8888 -p 2&
# python PyAPI/main.py -I 172.22.32.1 -P 8888 -p 3&
# python PyAPI/main.py -I 172.22.32.1 -P 8888 -p 4&

+ 4
- 4
dependency/proto/Message2Clients.proto View File

@@ -12,7 +12,7 @@ message MessageOfStudent
int32 determination = 4; // 剩余的学习毅力,相当于血量
int32 addiction = 5; // 沉迷程度,相当于淘汰进度
repeated double time_until_skill_available = 6;
PlaceType place = 7;
// PlaceType place = 7;
repeated PropType prop = 8;
PlayerState player_state = 9;
int64 guid = 10;
@@ -37,7 +37,7 @@ message MessageOfTricker
int32 y = 2;
int32 speed = 3;
repeated double time_until_skill_available = 5;
PlaceType place = 6;
// PlaceType place = 6;
repeated PropType prop = 7;
TrickerType tricker_type = 8;
int64 guid = 9;
@@ -61,7 +61,7 @@ message MessageOfBullet
double facing_direction = 4;
int64 guid = 5;
PlayerType team = 6;
PlaceType place = 7;
// PlaceType place = 7;
double bomb_range = 8;
int32 speed = 9;
}
@@ -83,7 +83,7 @@ message MessageOfProp // 可拾取道具的信息
int32 y = 3;
double facing_direction = 4;
int64 guid = 5;
PlaceType place = 6;
// PlaceType place = 6;
}




+ 0
- 0
dependency/proto/Proto.sln View File


+ 205
- 0
dependency/py/rank.py View File

@@ -0,0 +1,205 @@
import os
import json
import re

winGamesMap = {}
totalGamesMap = {}
studentTotalGame = {}
trickerTotalGame = {}
winRateMap = {}
studentWinMap = {}
trickerWinMap = {}
studentWinRateMap = {}
trickerWinRateMap = {}

winGamesMap1 = {}
totalGamesMap1 = {}
studentTotalGame1 = {}
trickerTotalGame1 = {}
winRateMap1 = {}
studentWinMap1 = {}
trickerWinMap1 = {}
studentWinRateMap1 = {}
trickerWinRateMap1 = {}

studentWinNum = 0
trickerWinNum = 0
totalGameNum = 0

studentWinNum1 = 0
trickerWinNum1 = 0
totalGameNum1 = 0

teamIDtoName = {
"951c89eb-aa9c-45d4-af10-ad9785a047d6": "无名万物之始", "2e504ec6-50b1-4985-b2fd-995927ea9717": "LQ说什么都队", "fb472ad6-65e0-494b-a7be-f6f25ecda018": "是啊我诶",
"3376909b-5ddb-41ab-994c-3c5b5ba60158": "叛逃者联盟",
"9b0f2257-734c-42e2-8061-c267e3d0d231": "ChatGPA",
"2de908c9-1b99-4811-ae00-68140d1c4527": "昊天上帝和他的三个神父",
"94866510-af51-439c-a41a-b4cb42596e25": "少年毕不了业",
"4613ef48-4988-4508-a258-66857a3250b8": "PKT48TeamTS",
"8e14b2a3-fc37-4fb6-b8ac-a722a10707d7": "京ICP备2022019669号-1 2022 EESAST",
"e8db213c-a636-483f-a6ed-84310b3093a4": "拉拉队",
"04abd472-ed7a-4840-8680-87d20db52721": "努力少女戏尔危",
"2bc1b761-ace3-4403-af83-e46ca328bcd0": "测试",
"4c1d6333-e25c-4b0f-bc06-9851db446bd7": "摆烂吧,少女",
"7f819704-99c0-41d8-bc61-26eec0bd73bb": "一会吃萤火虫",
"de915bbf-0751-4a9d-ab30-a470807406b2": "小小做题家",
"28baa2bf-5130-4a1e-ab9c-36e8faf87f84": "数析少女队",
"5c868c42-3b07-4280-a825-a6f80e0d5a2c": "沙壁北京",
"ed03d1ac-810a-4547-b54a-d56cd5213364": "我会出手队",
"5d59e45f-cb0e-4294-90f4-282adb1d476d": "闪电骑士团",
"637e20c1-a904-4f6f-b706-2cea7c4daf5e": "Mukava Poikaa",
"7185eb49-0cb0-43c0-a469-a39e636d66d4": "劝退吧,少女",
"d2a7ba71-4a86-4278-a362-8a8953a368f8": "纵火犯在何方",
"4e266301-7749-4699-b2de-511d458cf537": "土木清华没有水",
"454f37bd-2f54-4463-94d9-2df9aedb4f21": "电电做不队",
"a2573713-28e4-4af7-8c53-ab21f385f789": "王牌飞行队",
"194c3ddf-6846-47ec-a262-ca24f5639531": "快乐Debug",
"97cf5969-e8ff-410e-b85c-0c8359923289": "卷动量守恒",
"4646739a-9ff5-4854-a3b2-27d5b85ea504": "龙井队",
"c431d105-a2b3-4659-b713-6bc97132ec7f": "疯狂Thurs队",
"9ee48de1-a76a-40eb-b267-59c985bbe6cb": "蒸馍",
"5ef8ffbb-0776-4a74-a84f-3d80d5b4c2ae": "你说什么都队",
"65f94306-69c7-42a2-8c68-44cb45749aae": "closeAI",
"ab0406ae-6a0e-4c1e-9d36-eb14115de076": "N/A",
"82cbff06-9ed1-429b-afc3-7e050318bf93": "代码一行都不队",
"6b52346c-4528-424b-ac75-22fa573ebaad": "pqfobj",
"93e7f3f1-d47f-4588-b433-72877089f0bd": "你说得队",
"2f6f9ce3-f2d3-4799-b291-38dc04d048a0": "少女终末旅行",
"07c0ad6c-f612-4375-9b79-52bb89c79d76": "大括号换行委员会",
"bdf5b1c5-4dbc-4589-a6bc-8c5932c04de7": "孤客若风",
"f0d75eee-34a6-4484-8e23-720d26db747d": "/",
"acea715f-d5b0-4113-b6c3-9f6d7822f2e9": "难崩"
}

dirs = os.listdir(".")
for dir in dirs:
if dir.startswith("Team"):
dirdir = dir.replace("Team_", "")
dirdir = dirdir.split("--vs--")
try:
with open(f"{dir}/result.json", 'r') as f:
result = json.load(f)
for i in (0, 1):
if dirdir[i] not in winGamesMap:
winGamesMap[dirdir[i]] = 0
if dirdir[i] not in totalGamesMap:
totalGamesMap[dirdir[i]] = 0
if dirdir[i] not in studentWinMap:
studentWinMap[dirdir[i]] = 0
if dirdir[i] not in trickerWinMap:
trickerWinMap[dirdir[i]] = 0
if dirdir[i] not in studentTotalGame:
studentTotalGame[dirdir[i]] = 0
if dirdir[i] not in trickerTotalGame:
trickerTotalGame[dirdir[i]] = 0
if dirdir[i] not in winGamesMap1:
winGamesMap1[dirdir[i]] = 0
if dirdir[i] not in totalGamesMap1:
totalGamesMap1[dirdir[i]] = 0
if dirdir[i] not in studentWinMap1:
studentWinMap1[dirdir[i]] = 0
if dirdir[i] not in trickerWinMap1:
trickerWinMap1[dirdir[i]] = 0
if dirdir[i] not in studentTotalGame1:
studentTotalGame1[dirdir[i]] = 0
if dirdir[i] not in trickerTotalGame1:
trickerTotalGame1[dirdir[i]] = 0

totalGamesMap[dirdir[0]] += 1
totalGamesMap[dirdir[1]] += 1
studentTotalGame[dirdir[0]] += 1
trickerTotalGame[dirdir[1]] += 1

totalGameNum += 1

if result["Student"] < result["Tricker"]:
winGamesMap[dirdir[1]] += 1
trickerWinMap[dirdir[1]] += 1
trickerWinNum += 1

elif result["Student"] > result["Tricker"]:
winGamesMap[dirdir[0]] += 1
studentWinMap[dirdir[0]] += 1
studentWinNum += 1

else:
winGamesMap[dirdir[0]] += 0.5
winGamesMap[dirdir[1]] += 0.5

if result["Student"] != 0 and result["Tricker"] != 0:

totalGameNum1 += 1
totalGamesMap1[dirdir[0]] += 1
totalGamesMap1[dirdir[1]] += 1
studentTotalGame1[dirdir[0]] += 1
trickerTotalGame1[dirdir[1]] += 1

if result["Student"] < result["Tricker"]:
winGamesMap1[dirdir[1]] += 1
trickerWinMap1[dirdir[1]] += 1
trickerWinNum1 += 1

elif result["Student"] > result["Tricker"]:
winGamesMap1[dirdir[0]] += 1
studentWinMap1[dirdir[0]] += 1
studentWinNum1 += 1

else:
winGamesMap1[dirdir[0]] += 0.5
winGamesMap1[dirdir[1]] += 0.5

except:
pass

for i in totalGamesMap:
winRateMap[i] = winGamesMap[i] / totalGamesMap[i]
if studentTotalGame[i] == 0:
studentWinRateMap[i] = 0
else:
studentWinRateMap[i] = studentWinMap[i] / studentTotalGame[i]
if trickerTotalGame[i] == 0:
trickerWinRateMap[i] = 0
else:
trickerWinRateMap[i] = trickerWinMap[i] / trickerTotalGame[i]


sortedMap = sorted(winRateMap.items(), key=lambda kv: (
kv[1], kv[0]), reverse=True)

print("************************ALL GAMES(with 0 player)************************")

for i in sortedMap:
width = 33 - len(re.findall('([\u4e00-\u9fa5])', teamIDtoName[i[0]]))
print(
f"Team {teamIDtoName[i[0]]:{width}}({i[0]}) wins {winGamesMap[i[0]]:4}/{totalGamesMap[i[0]]:<2} games({i[1]:.3f}), student wins {studentWinMap[i[0]]:2}/{studentTotalGame[i[0]]:<2}({studentWinRateMap[i[0]]:.3f}), tricker wins {trickerWinMap[i[0]]:2}/{trickerTotalGame[i[0]]:<2}({trickerWinRateMap[i[0]]:.3f})")

print(
f"Total games: {totalGameNum}, student wins {studentWinNum}, tricker wins {trickerWinNum}")

for i in totalGamesMap1:
if totalGamesMap1[i] == 0:
winRateMap1[i] = 0
else:
winRateMap1[i] = winGamesMap1[i] / totalGamesMap1[i]
if studentTotalGame1[i] == 0:
studentWinRateMap1[i] = 0
else:
studentWinRateMap1[i] = studentWinMap1[i] / studentTotalGame1[i]
if trickerTotalGame1[i] == 0:
trickerWinRateMap1[i] = 0
else:
trickerWinRateMap1[i] = trickerWinMap1[i] / trickerTotalGame1[i]


sortedMap1 = sorted(winRateMap1.items(), key=lambda kv: (
kv[1], kv[0]), reverse=True)

print("************************NON-0 GAMES(no 0 player)************************")

for i in sortedMap1:
width = 33 - len(re.findall('([\u4e00-\u9fa5])', teamIDtoName[i[0]]))
print(f"Team {teamIDtoName[i[0]]:{width}}({i[0]}) wins {winGamesMap1[i[0]]:4}/{totalGamesMap1[i[0]]:<2} games({i[1]:.3f}), student wins {studentWinMap1[i[0]]:2}/{studentTotalGame1[i[0]]:<2}({studentWinRateMap1[i[0]]:.3f}), tricker wins {trickerWinMap1[i[0]]:2}/{trickerTotalGame1[i[0]]:<2}({trickerWinRateMap1[i[0]]:.3f})")

print(
f"Total games: {totalGameNum1}, student wins {studentWinNum1}, tricker wins {trickerWinNum1}")

+ 10
- 2
dependency/shell/compile.sh View File

@@ -13,8 +13,16 @@ do
flag=0
fi
mv ./compile_log$i.txt $bind/compile_log$i.txt
elif [ ! -f "${bind}/player${i}.py" ]; then
flag=0
elif [ -f "${bind}/player${i}.py" ]; then
pushd ../python
cp -f $bind/player$i.py ./PyAPI/AI.py
python3 -m compileall ./PyAPI
if [ ! -f ./PyAPI/__pycache__/AI.cpython-39.pyc ]; then
flag=0
else
rm -rf ./PyAPI/__pycache__/AI.cpython-39.pyc
fi
popd
fi
let "i++"
done


+ 1
- 1
dependency/shell/run.sh View File

@@ -51,7 +51,7 @@ if [ -f $playback_dir/start.lock ]; then
while [ $? -eq 0 ]
do
sleep 1
ps -p $server_pid
ps -p $server_pid > /dev/null 2>&1
done
touch $playback_dir/finish.lock
echo "Finish"


+ 7
- 7
docs/GameRules.md View File

@@ -1,5 +1,5 @@
# 规则
V5.5
V5.6
- [规则](#规则)
- [简则](#简则)
- [地图](#地图)
@@ -192,7 +192,7 @@ $$
| :------------ | :--------------------- | :--------------------- | :--------------------- | :--------------------- |
| 移动速度/s | 3960 | 3600 | 3852 | 3600 |
| 隐蔽度 | 1.5 | 1 | 0.8 | 0.75|
| 警戒范围 | 22,100 | 17000 | 15300 | 17000
| 警戒范围 | 22100 | 17000 | 15300 | 17000|
| 视野范围 | 15600 | 13000 | 13000 | 14300|
| 开锁门速度/ms | 4000 | 4000 | 4000 |4000 |
| 翻窗速度/s | 2540 | 2540 | 2794 | 2540|
@@ -246,14 +246,14 @@ $$
| :------------ | :--------------------- | :--------------------- | :--------------------- | :--------------------- |
| 移动速度/s | 2700 | 3150 | 2880 | 3000 |
| 最大毅力值 | 30000000 | 3000000 | 3300000 | 3200000 |
| 最大沉迷度 | 600000 | 54,000 | 78,000 | 66,000 |
| 学习一科速度 | 0 | 73 | 135 | 123 |
| 最大沉迷度 | 600000 | 54000 | 78000 | 66000 |
| 学习速度/ms | 0 | 73 | 135 | 123 |
| 勉励速度/ms | 80 | 90 | 100 | 120 |
| 隐蔽度 | 0.5 | 0.9 | 0.9 | 0.8 |
| 警戒范围 | 7500 | 15000 | 13,500 | 15000 |
| 视野范围 | 9,000 | 11000 | 9,000 | 10000 |
| 警戒范围 | 7500 | 15000 | 13500 | 15000 |
| 视野范围 | 9000 | 11000 | 9000 | 10000 |
| 开锁门速度/ms | 4000 | 4000 | 4000 | 2800 |
| 翻窗速度/ms | 1270 | 3048 | 2116 | 2540 |
| 翻窗速度/ms | 611 | 1466 | 1018 | 1222 |
| 翻箱速度/ms | 1000 | 1000 | 1000 | 900 |

#### 运动员


+ 1
- 1
docs/使用文档.md View File

@@ -170,7 +170,7 @@ start cmd /k win64\Client.exe --cl --playbackFile .\video.thuaipb --playbackSpee

## WPF简易调试界面

![client](https://raw.githubusercontent.com/shangfengh/THUAI6/new/resource/clientsmaller.png)
![client](https://raw.githubusercontent.com/eesast/THUAI6/dev/resource/clientsmaller.png)

### 界面介绍



+ 97
- 0
docs/游戏机制与平衡性调整更新草案.md View File

@@ -0,0 +1,97 @@
# 游戏机制与平衡性调整更新草案
v1.2

## 说明
- 该草案尚未完全确定,请大家不要过分依靠该文档进行修改自己的代码
- 有任何问题都可以在选手群中提出建议和讨论

## 游戏接口
删除structures.h中Player的属性place

## 游戏规则

## 游戏机制

## 攻击
- 飞刀FlyingKnife
- 前摇变为600ms
- 搞蛋鬼的一般攻击CommonAttackOfTricker
- 改为“不能攻击未写完的作业”
- 蹦蹦炸弹BombBomb
- 未攻击至目标时的后摇改为1200ms
- 增强为“可以攻击未写完的作业”
- 增强为“可以攻击使门被打开(可以重新被锁上)”
- strike(新增)
- 可以攻击未写完的作业

修改后:
| 攻击(子弹)类型 |搞蛋鬼的一般攻击CommonAttackOfTricker|飞刀FlyingKnife | 蹦蹦炸弹BombBomb | 小炸弹JumpyDumpty | strike |
| :--------------------- | :---------------------| :--------------------- | :--------------------- | :--------------------- | :--------------------- |
| 子弹爆炸范围 | 0 | 0 | 2000 | 1000 | 0 |
| 子弹攻击距离 | 2200 | 78000 | 2200 | 4400 | 2000 |
| 攻击力 | 1500000 | 1200000 | 1800000 | 900000 | 1600000 |
| 移动速度/s | 7400 | 18500 | 6000 | 8600 | 6250 |
| 前摇(ms) | 297 | 600 | 366 | - | 320 |
|未攻击至目标时的后摇(ms)| 800 | 0 | 1200 | - | 800 |
|攻击至目标时的后摇(ms) | 3700 | 0 | 3700 | - | 3700 |
| CD(ms) | 800 | 400 | 3000 | - | 800 |
| 最大子弹容量 | 1 | 1 | 1 | - | 1 |


## 职业
- 所有角色开锁门速度加速至1.25倍
- 所有角色翻箱速度加速至1.25倍

### 学生
- 先前学生翻窗数据有误

- Teacher
- 警戒范围由7500改为13000
- 翻窗速度改为1000
- 技能惩罚(Punish)强化为“使用瞬间,在**视野距离范围内(不是可视范围)的**翻窗、开锁门、攻击前后摇、**使用技能期间**的捣蛋鬼会被眩晕(3070+**500***已受伤害/基本伤害(1500000))ms”
- 技能喝茶(HaveTea)(新增)
- CD:90s
- 使用瞬间,向当前方向瞬移3000(可以穿墙),如果会碰撞则失败。
- Robot(新增)
- 无技能
- 特性
- 不可被眩晕
- 不可毕业
- 不可救人
- 无牵制得分
- 不可使用道具(可以捡起和扔道具)
- TechOtaku(新增)
- 一名TechOtaku最多可以在场上同时最多拥有3个Robot,无法共享视野
0. SummonGolem
- CD:40s,持续时间:6s
- 在持续时间中,学生进入人物状态进入UsingSpecialSkill(不能移动),进入其他状态会导致制作机器人失败。
- 在持续时间中,学生面前生成道具CraftingBench;学生进入其他状态或该道具被碰撞后,CraftingBench消失且制作机器人失败。
- 持续时间结束后,道具CraftingBench所在位置生成一个Robot,CraftingBench消失
1. UseRobot
- CD:0s,持续时间:0s
- TechOtaku的Robot的PlayerId = TechOtaku的PlayerId + n×5(一局游戏理论人数),其中1<=n<=3(自己的n为0)
- 新造的Robot的PlayerId的n总是尽量小
- 每使用一次UseRobot,TechOtaku就切换一次操控的角色,若之前操控角色的PlayerId =TechOtaku的PlayerId + j×5,其PlayerId变为PlayerId =TechOtaku的PlayerId + ((j+1)mod 4 )×5,若其不可用,则再次进行这样的操作
修改后:

| 学生职业 | 教师Teacher | 健身狂Athlete |学霸StraightAStudent | 开心果Sunshine | 机器人Robot | 技术宅TechOtaku |
| :------------ | :------------------ | :------------------ | :------------------ | :------------------ | :------------------ | :------------------ |
| 移动速度/s | 2700 | 3150 | 2880 | 3000 | 2700 | 2880 |
| 最大毅力值 | 30000000 | 3000000 | 3300000 | 3200000 | 900000 | 2700000 |
| 最大沉迷度 | 600000 | 54000 | 78000 | 60000 | 0 | 60000 |
| 学习速度/ms | 0 | 73 | 135 | 123 | 100 | 130 |
| 勉励速度/ms | 80 | 90 | 100 | 120 | 0 | 100 |
| 隐蔽度 | 0.5 | 0.9 | 0.9 | 0.8 | 0.8 | 1.1 |
| 警戒范围 | 13000 | 15000 | 13500 | 15000 | 0 | 15000 |
| 视野范围 | 9000 | 11000 | 9000 | 10000 | 0 | 9000 |
| 开锁门速度/ms | 5000 | 5000 | 5000 | 3500 | 0 | 5000 |
| 翻窗速度/ms | 1000 | 1466 | 1018 | 1222 | 1 | 1100 |
| 翻箱速度/ms | 1250 | 1250 | 1250 | 1125 | 1000 | 1100 |

### 捣蛋鬼
- Assassin
- 技能隐身(BecomeInvisible)添加约束条件“使用隐身技能后,人物状态进入UsingSpecialSkill,进入其他状态会使得隐身状态解除"
- 喧哗者ANoisyPerson
- 普通攻击改为strike
- Klee
- 被动技能Lucky!(新增):开局获得随机的一个道具(不会是钥匙)

+ 10
- 0
docs/版本更新说明.md View File

@@ -0,0 +1,10 @@
# 版本更新说明

# 说明
- 只说明对于选手较为重要的修改

# 等待更新的更改
- docs:添加了 游戏机制与平衡性调整更新草案.pdf
- docs:添加了 版本更新说明.pdf
- docs&hotfix: 修正了GameRules.pdf中学生翻窗速度的错误
- remove: 删除了Place属性

+ 9
- 0
logic/Client/MainWindow.xaml View File

@@ -10,8 +10,17 @@

<Window.Resources>
<ImageBrush x:Key="Logo" ImageSource="Logo.png"/>
<RoutedUICommand x:Key="maximize_Pressed" Text="maximize_Pressed"/>
</Window.Resources>

<Window.CommandBindings>
<CommandBinding Command="{StaticResource maximize_Pressed}" Executed="ClickToMaxmize"/>
</Window.CommandBindings>

<Window.InputBindings>
<KeyBinding Key="F11" Command="{StaticResource maximize_Pressed}"/>
</Window.InputBindings>

<Grid Name="MainGrid" Margin="0,0,0,0">
<!--Title行删去了两个赋值语句,等之后补回来-->
<Grid.RowDefinitions>


+ 70
- 70
logic/Client/MainWindow.xaml.cs View File

@@ -572,96 +572,96 @@ namespace Client

private bool CanSee(MessageOfStudent msg)
{
if (msg.PlayerState == PlayerState.Quit || msg.PlayerState == PlayerState.Graduated)
return false;
if (isSpectatorMode || isPlaybackMode)
return true;
if (humanOrButcher && human != null)
{
if (msg.Place == human.Place)
return true;
if (msg.PlayerId == playerID + Preparation.Utility.GameData.numOfPeople)//robot and its owner
return true;
}
else if (!humanOrButcher && butcher != null)
{
if (msg.Place == butcher.Place)
return true;
}
if (msg.Place == Protobuf.PlaceType.Grass)
return false;
//if (msg.PlayerState == PlayerState.Quit || msg.PlayerState == PlayerState.Graduated)
// return false;
//if (isSpectatorMode || isPlaybackMode)
// return true;
//if (humanOrButcher && human != null)
//{
// if (msg.Place == human.Place)
// return true;
// if (msg.PlayerId == playerID + Preparation.Utility.GameData.numOfPeople)//robot and its owner
// return true;
//}
//else if (!humanOrButcher && butcher != null)
//{
// if (msg.Place == butcher.Place)
// return true;
//}
//if (msg.Place == Protobuf.PlaceType.Grass)
// return false;
return true;
}

private bool CanSee(MessageOfTricker msg)
{
if (isSpectatorMode || isPlaybackMode)
return true;
if (!humanOrButcher && butcher != null)
{
if (butcher.Guid == msg.Guid) // 自己能看见自己
return true;
}
if (humanOrButcher && human != null)
{
if (msg.TrickerType == Protobuf.TrickerType.Assassin)
{
foreach (var buff in msg.Buff)
{
if (buff == Protobuf.TrickerBuffType.TrickerInvisible)
return false;
}
}
if (msg.Place == human.Place)
return true;
}
if (msg.Place == Protobuf.PlaceType.Grass)
return false;
//if (isSpectatorMode || isPlaybackMode)
// return true;
//if (!humanOrButcher && butcher != null)
//{
// if (butcher.Guid == msg.Guid) // 自己能看见自己
// return true;
//}
//if (humanOrButcher && human != null)
//{
// if (msg.TrickerType == Protobuf.TrickerType.Assassin)
// {
// foreach (var buff in msg.Buff)
// {
// if (buff == Protobuf.TrickerBuffType.TrickerInvisible)
// return false;
// }
// }
// if (msg.Place == human.Place)
// return true;
//}
//if (msg.Place == Protobuf.PlaceType.Grass)
// return false;
return true;
}

private bool CanSee(MessageOfProp msg)
{
if (isSpectatorMode || isPlaybackMode)
return true;
if (humanOrButcher && human != null)
{
if (msg.Place == human.Place)
return true;
}
else if (!humanOrButcher && butcher != null)
{
if (msg.Place == butcher.Place)
return true;
}
if (msg.Place == Protobuf.PlaceType.Grass)
return false;
//if (isSpectatorMode || isPlaybackMode)
// return true;
//if (humanOrButcher && human != null)
//{
// if (msg.Place == human.Place)
// return true;
//}
//else if (!humanOrButcher && butcher != null)
//{
// if (msg.Place == butcher.Place)
// return true;
//}
//if (msg.Place == Protobuf.PlaceType.Grass)
// return false;
return true;
}

private bool CanSee(MessageOfBullet msg)
{
if (isSpectatorMode || isPlaybackMode)
return true;
if (humanOrButcher && human != null)
{
if (msg.Place == human.Place)
return true;
}
else if (!humanOrButcher && butcher != null)
{
if (msg.Place == butcher.Place)
return true;
}
if (msg.Place == Protobuf.PlaceType.Grass)
return false;
//if (isSpectatorMode || isPlaybackMode)
// return true;
//if (humanOrButcher && human != null)
//{
// if (msg.Place == human.Place)
// return true;
//}
//else if (!humanOrButcher && butcher != null)
//{
// if (msg.Place == butcher.Place)
// return true;
//}
//if (msg.Place == Protobuf.PlaceType.Grass)
// return false;
return true;
}

private bool CanSee(MessageOfBombedBullet msg)
{
if (isSpectatorMode || isPlaybackMode)
return true;
//if (isSpectatorMode || isPlaybackMode)
// return true;
//if (humanOrButcher && human != null)
//{
// if (msg.Place == human.Place)


+ 0
- 1
logic/GameClass/GameObj/Bullet/BombedBullet.cs View File

@@ -13,7 +13,6 @@ namespace GameClass.GameObj
public BombedBullet(Bullet bullet) :
base(bullet.Position, bullet.Radius, GameObjType.BombedBullet)
{
this.place = bullet.Place;
this.bulletHasBombed = bullet;
this.MappingID = bullet.ID;
this.FacingDirection = bullet.FacingDirection;


+ 6
- 8
logic/GameClass/GameObj/Bullet/Bullet.Ghost.cs View File

@@ -5,8 +5,8 @@ namespace GameClass.GameObj
{
internal sealed class CommonAttackOfGhost : Bullet
{
public CommonAttackOfGhost(Character player, PlaceType placeType, XY pos, int radius = GameData.bulletRadius) :
base(player, radius, placeType, pos)
public CommonAttackOfGhost(Character player, XY pos, int radius = GameData.bulletRadius) :
base(player, radius, pos)
{
}
public override double BulletBombRange => 0;
@@ -52,8 +52,8 @@ namespace GameClass.GameObj

internal sealed class FlyingKnife : Bullet
{
public FlyingKnife(Character player, PlaceType placeType, XY pos, int radius = GameData.bulletRadius) :
base(player, radius, placeType, pos)
public FlyingKnife(Character player, XY pos, int radius = GameData.bulletRadius) :
base(player, radius, pos)
{
}
public override double BulletBombRange => 0;
@@ -100,8 +100,7 @@ namespace GameClass.GameObj

internal sealed class BombBomb : Bullet
{
public BombBomb(Character player, PlaceType placeType, XY pos, int radius = GameData.bulletRadius) :
base(player, radius, placeType, pos)
public BombBomb(Character player, XY pos, int radius = GameData.bulletRadius) : base(player, radius, pos)
{
}
public override double BulletBombRange => GameData.basicBulletBombRange;
@@ -146,8 +145,7 @@ namespace GameClass.GameObj
}
internal sealed class JumpyDumpty : Bullet
{
public JumpyDumpty(Character player, PlaceType placeType, XY pos, int radius = GameData.bulletRadius) :
base(player, radius, placeType, pos)
public JumpyDumpty(Character player, XY pos, int radius = GameData.bulletRadius) : base(player, radius, pos)
{
}
public override double BulletBombRange => GameData.basicBulletBombRange / 2;


+ 6
- 7
logic/GameClass/GameObj/Bullet/Bullet.cs View File

@@ -41,10 +41,9 @@ namespace GameClass.GameObj
return true;
return false;
}
public Bullet(Character player, int radius, PlaceType placeType, XY Position) :
public Bullet(Character player, int radius, XY Position) :
base(Position, radius, GameObjType.Bullet)
{
this.place = placeType;
this.CanMove = true;
this.moveSpeed = this.Speed;
this.hasSpear = player.TryUseSpear();
@@ -57,18 +56,18 @@ namespace GameClass.GameObj

public static class BulletFactory
{
public static Bullet? GetBullet(Character character, PlaceType place, XY pos)
public static Bullet? GetBullet(Character character, XY pos)
{
switch (character.BulletOfPlayer)
{
case BulletType.FlyingKnife:
return new FlyingKnife(character, place, pos);
return new FlyingKnife(character, pos);
case BulletType.CommonAttackOfGhost:
return new CommonAttackOfGhost(character, place, pos);
return new CommonAttackOfGhost(character, pos);
case BulletType.JumpyDumpty:
return new JumpyDumpty(character, place, pos);
return new JumpyDumpty(character, pos);
case BulletType.BombBomb:
return new BombBomb(character, place, pos);
return new BombBomb(character, pos);
default:
return null;
}


+ 0
- 1
logic/GameClass/GameObj/Character/Character.Skill.cs View File

@@ -57,7 +57,6 @@ namespace GameClass.GameObj
protected Character(XY initPos, int initRadius, CharacterType characterType) :
base(initPos, initRadius, GameObjType.Character)
{
this.place = PlaceType.Null;
this.CanMove = true;
this.score = 0;
this.buffManager = new BuffManager();


+ 2
- 3
logic/GameClass/GameObj/Character/Character.cs View File

@@ -58,10 +58,10 @@ namespace GameClass.GameObj
/// 进行一次攻击
/// </summary>
/// <returns>攻击操作发出的子弹</returns>
public Bullet? Attack(XY pos, PlaceType place)
public Bullet? Attack(XY pos)
{
if (TrySubBulletNum())
return BulletFactory.GetBullet(this, place, pos);
return BulletFactory.GetBullet(this, pos);
else
return null;
}
@@ -365,7 +365,6 @@ namespace GameClass.GameObj
CanMove = false;
IsResetting = true;
Position = GameData.PosWhoDie;
place = PlaceType.Grass;
}
}
#endregion


+ 9
- 20
logic/GameClass/GameObj/GameObj.cs View File

@@ -14,35 +14,24 @@ namespace GameClass.GameObj

protected readonly XY birthPos;

private GameObjType type;
private readonly GameObjType type;
public GameObjType Type => type;

private static long currentMaxID = 0; // 目前游戏对象的最大ID
public const long invalidID = long.MaxValue; // 无效的ID
public const long noneID = long.MinValue;
public long ID { get; }

private XY position;
public XY Position
{
get => position;
protected
set
{
lock (gameObjLock)
{
position = value;
}
}
}

protected PlaceType place;
public PlaceType Place { get => place; }
protected XY position;
public virtual XY Position { get; set; }

private XY facingDirection = new(1, 0);
public XY FacingDirection
{
get => facingDirection;
get
{
lock (gameObjLock)
return facingDirection;
}
set
{
lock (gameObjLock)
@@ -85,7 +74,7 @@ namespace GameClass.GameObj
public virtual bool IgnoreCollideExecutor(IGameObj targetObj) => false;
public GameObj(XY initPos, int initRadius, GameObjType initType)
{
this.Position = this.birthPos = initPos;
this.position = this.birthPos = initPos;
this.Radius = initRadius;
this.type = initType;
ID = Interlocked.Increment(ref currentMaxID);


+ 0
- 1
logic/GameClass/GameObj/Map/Chest.cs View File

@@ -11,7 +11,6 @@ namespace GameClass.GameObj
public Chest(XY initPos) :
base(initPos, GameData.numOfPosGridPerCell / 2, GameObjType.Chest)
{
this.place = PlaceType.Chest;
this.CanMove = false;
}
public override bool IsRigid => true;


+ 17
- 1
logic/GameClass/GameObj/Map/Door.cs View File

@@ -11,9 +11,25 @@ namespace GameClass.GameObj
public Door(XY initPos, PlaceType placeType) :
base(initPos, GameData.numOfPosGridPerCell / 2, GameObjType.Door)
{
this.place = placeType;
switch (placeType)
{
case PlaceType.Door3:
doorNum = 3;
break;
case PlaceType.Door5:
doorNum = 5;
break;
case PlaceType.Door6:
default:
doorNum = 6;
break;
}
this.CanMove = false;
}

private readonly int doorNum;
public int DoorNum => doorNum;

public override bool IsRigid => !isOpen;
public override ShapeType Shape => ShapeType.Square;



+ 0
- 1
logic/GameClass/GameObj/Map/Doorway.cs View File

@@ -11,7 +11,6 @@ namespace GameClass.GameObj
public Doorway(XY initPos) :
base(initPos, GameData.numOfPosGridPerCell / 2, GameObjType.Doorway)
{
this.place = PlaceType.Doorway;
this.CanMove = false;
}
public override bool IsRigid => true;


+ 0
- 1
logic/GameClass/GameObj/Map/EmergencyExit.cs View File

@@ -11,7 +11,6 @@ namespace GameClass.GameObj
public EmergencyExit(XY initPos) :
base(initPos, GameData.numOfPosGridPerCell / 2, GameObjType.EmergencyExit)
{
this.place = PlaceType.EmergencyExit;
this.CanMove = false;
}
public override bool IsRigid => true;


+ 0
- 1
logic/GameClass/GameObj/Map/Generator.cs View File

@@ -10,7 +10,6 @@ namespace GameClass.GameObj
public Generator(XY initPos) :
base(initPos, GameData.numOfPosGridPerCell / 2, GameObjType.Generator)
{
this.place = PlaceType.Generator;
this.CanMove = false;
}
public override bool IsRigid => true;


+ 0
- 1
logic/GameClass/GameObj/Map/Wall.cs View File

@@ -10,7 +10,6 @@ namespace GameClass.GameObj
public Wall(XY initPos) :
base(initPos, GameData.numOfPosGridPerCell / 2, GameObjType.Wall)
{
this.place = PlaceType.Wall;
this.CanMove = false;
}
public override bool IsRigid => true;


+ 0
- 1
logic/GameClass/GameObj/Map/Window.cs View File

@@ -11,7 +11,6 @@ namespace GameClass.GameObj
public Window(XY initPos) :
base(initPos, GameData.numOfPosGridPerCell / 2, GameObjType.Window)
{
this.place = PlaceType.Window;
this.CanMove = false;
}
public override bool IsRigid => true;


+ 17
- 11
logic/GameClass/GameObj/Moveable.cs View File

@@ -12,6 +12,22 @@ namespace GameClass.GameObj
protected readonly object moveObjLock = new();
public object MoveLock => moveObjLock;

public override XY Position
{
get
{
lock (gameObjLock)
return position;
}
set
{
lock (gameObjLock)
{
position = value;
}
}
}

private bool isMoving;
public bool IsMoving
{
@@ -48,27 +64,17 @@ namespace GameClass.GameObj
public int OrgMoveSpeed { get; protected set; }

// 移动,改变坐标
public long MovingSetPos(XY moveVec, PlaceType place)
public long MovingSetPos(XY moveVec)
{
if (moveVec.x != 0 || moveVec.y != 0)
lock (gameObjLock)
{
FacingDirection = moveVec;
this.Position += moveVec;
this.place = place;
}
return moveVec * moveVec;
}

public void ReSetPos(XY pos, PlaceType place)
{
lock (gameObjLock)
{
this.Position = pos;
this.place = place;
}
}

/// <summary>
/// 设置移动速度
/// </summary>


+ 0
- 1
logic/GameClass/GameObj/OutOfBoundBlock.cs View File

@@ -11,7 +11,6 @@ namespace GameClass.GameObj
public OutOfBoundBlock(XY initPos) :
base(initPos, int.MaxValue, GameObjType.OutOfBoundBlock)
{
this.place = PlaceType.Wall;
this.CanMove = false;
}



+ 0
- 1
logic/GameClass/GameObj/PickedProp.cs View File

@@ -17,7 +17,6 @@ namespace GameClass.GameObj
public PickedProp(Prop prop) :
base(prop.Position, prop.Radius, GameObjType.PickedProp)
{
this.place = prop.Place;
this.PropHasPicked = prop;
this.MappingID = prop.ID;
}


+ 23
- 24
logic/GameClass/GameObj/Prop.cs View File

@@ -19,10 +19,9 @@ namespace GameClass.GameObj

public abstract PropType GetPropType();

public Prop(XY initPos, PlaceType place, int radius = GameData.PropRadius) :
public Prop(XY initPos, int radius = GameData.PropRadius) :
base(initPos, radius, GameObjType.Prop)
{
this.place = place;
this.CanMove = false;
this.moveSpeed = GameData.PropMoveSpeed;
}
@@ -43,8 +42,8 @@ namespace GameClass.GameObj
/// </summary>
public sealed class AddSpeed : Prop
{
public AddSpeed(XY initPos, PlaceType placeType) :
base(initPos, placeType)
public AddSpeed(XY initPos) :
base(initPos)
{
}
public override PropType GetPropType() => PropType.AddSpeed;
@@ -54,24 +53,24 @@ namespace GameClass.GameObj
/// </summary>
public sealed class AddLifeOrClairaudience : Prop
{
public AddLifeOrClairaudience(XY initPos, PlaceType placeType) :
base(initPos, placeType)
public AddLifeOrClairaudience(XY initPos) :
base(initPos)
{
}
public override PropType GetPropType() => PropType.AddLifeOrClairaudience;
}
public sealed class AddHpOrAp : Prop
{
public AddHpOrAp(XY initPos, PlaceType placeType) :
base(initPos, placeType)
public AddHpOrAp(XY initPos) :
base(initPos)
{
}
public override PropType GetPropType() => PropType.AddHpOrAp;
}
public sealed class RecoveryFromDizziness : Prop
{
public RecoveryFromDizziness(XY initPos, PlaceType placeType) :
base(initPos, placeType)
public RecoveryFromDizziness(XY initPos) :
base(initPos)
{
}
public override PropType GetPropType() => PropType.RecoveryFromDizziness;
@@ -81,35 +80,35 @@ namespace GameClass.GameObj
/// </summary>
public sealed class ShieldOrSpear : Prop
{
public ShieldOrSpear(XY initPos, PlaceType placeType) : base(initPos, placeType)
public ShieldOrSpear(XY initPos) : base(initPos)
{
}
public override PropType GetPropType() => PropType.ShieldOrSpear;
}
public sealed class Key3 : Prop
{
public Key3(XY initPos, PlaceType placeType) : base(initPos, placeType)
public Key3(XY initPos) : base(initPos)
{
}
public override PropType GetPropType() => PropType.Key3;
}
public sealed class Key5 : Prop
{
public Key5(XY initPos, PlaceType placeType) : base(initPos, placeType)
public Key5(XY initPos) : base(initPos)
{
}
public override PropType GetPropType() => PropType.Key5;
}
public sealed class Key6 : Prop
{
public Key6(XY initPos, PlaceType placeType) : base(initPos, placeType)
public Key6(XY initPos) : base(initPos)
{
}
public override PropType GetPropType() => PropType.Key6;
}
public sealed class NullProp : Prop
{
public NullProp(PlaceType placeType = PlaceType.Wall) : base(new XY(1, 1), placeType)
public NullProp() : base(new XY(1, 1))
{
}
public override PropType GetPropType() => PropType.Null;
@@ -143,26 +142,26 @@ namespace GameClass.GameObj
// #endregion
public static class PropFactory
{
public static Prop GetProp(PropType propType, XY pos, PlaceType place)
public static Prop GetProp(PropType propType, XY pos)
{
switch (propType)
{
case PropType.AddSpeed:
return new AddSpeed(pos, place);
return new AddSpeed(pos);
case PropType.AddLifeOrClairaudience:
return new AddLifeOrClairaudience(pos, place);
return new AddLifeOrClairaudience(pos);
case PropType.ShieldOrSpear:
return new ShieldOrSpear(pos, place);
return new ShieldOrSpear(pos);
case PropType.AddHpOrAp:
return new AddHpOrAp(pos, place);
return new AddHpOrAp(pos);
case PropType.RecoveryFromDizziness:
return new RecoveryFromDizziness(pos, place);
return new RecoveryFromDizziness(pos);
case PropType.Key3:
return new Key3(pos, place);
return new Key3(pos);
case PropType.Key5:
return new Key5(pos, place);
return new Key5(pos);
case PropType.Key6:
return new Key6(pos, place);
return new Key6(pos);
default:
return new NullProp();
}


+ 4
- 4
logic/GameEngine/MoveEngine.cs View File

@@ -70,7 +70,7 @@ namespace GameEngine
XY nextPos = obj.Position + moveVec;
double maxLen = collisionChecker.FindMax(obj, nextPos, moveVec);
maxLen = Math.Min(maxLen, obj.MoveSpeed / GameData.numOfStepPerSecond);
obj.MovingSetPos(new XY(moveVec, maxLen), GetPlaceType(nextPos));
obj.MovingSetPos(new XY(moveVec, maxLen));
}

public void MoveObj(IMoveable obj, int moveTime, double direction)
@@ -90,7 +90,7 @@ namespace GameEngine

double moveVecLength = 0.0;
XY res = new(direction, moveVecLength);
double deltaLen = moveVecLength - Math.Sqrt(obj.MovingSetPos(res, GetPlaceType(obj.Position + res))); // 转向,并用deltaLen存储行走的误差
double deltaLen = moveVecLength - Math.Sqrt(obj.MovingSetPos(res)); // 转向,并用deltaLen存储行走的误差
IGameObj? collisionObj = null;
bool isDestroyed = false;

@@ -156,7 +156,7 @@ namespace GameEngine
} while (flag);

if (threadNum == 0 || ((ICharacter)obj).ThreadNum == threadNum)
deltaLen += moveVecLength - Math.Sqrt(obj.MovingSetPos(res, GetPlaceType(obj.Position + res)));
deltaLen += moveVecLength - Math.Sqrt(obj.MovingSetPos(res));

return true;
},
@@ -175,7 +175,7 @@ namespace GameEngine
if ((collisionObj = collisionChecker.CheckCollisionWhenMoving(obj, res)) == null)
{
if (threadNum == 0 || ((ICharacter)obj).ThreadNum == threadNum)
obj.MovingSetPos(res, GetPlaceType(obj.Position + res));
obj.MovingSetPos(res);
}
else
{


+ 7
- 7
logic/Gaming/ActionManager.cs View File

@@ -267,7 +267,7 @@ namespace Gaming
{
Prop prop = chestToOpen.PropInChest[i];
chestToOpen.PropInChest[i] = new NullProp();
prop.ReSetPos(player.Position, gameMap.GetPlaceType(player.Position));
prop.Position = player.Position;
gameMap.Add(prop);
}
}
@@ -295,7 +295,7 @@ namespace Gaming
if (characterInWindow != null)
{
if (player.IsGhost() && !characterInWindow.IsGhost())
characterManager.BeAttacked((Student)(characterInWindow), player.Attack(characterInWindow.Position, PlaceType.Null));
characterManager.BeAttacked((Student)(characterInWindow), player.Attack(characterInWindow.Position));
return false;
}*/

@@ -323,7 +323,7 @@ namespace Gaming
return;
}

player.ReSetPos(windowToPlayer + windowForClimb.Position, PlaceType.Window);
player.Position = windowToPlayer + windowForClimb.Position;
player.MoveSpeed = player.SpeedOfClimbingThroughWindows;

moveEngine.MoveObj(player, (int)(windowToPlayer.Length() * 3.0 * 1000 / player.MoveSpeed), (-1 * windowToPlayer).Angle());
@@ -339,7 +339,7 @@ namespace Gaming
)
.Start();
XY PosJumpOff = windowForClimb.Position - 2 * windowToPlayer;
player.ReSetPos(PosJumpOff, gameMap.GetPlaceType(PosJumpOff));
player.Position = PosJumpOff;
player.MoveSpeed = player.ReCalculateBuff(BuffType.AddSpeed, player.OrgMoveSpeed, GameData.MaxSpeed, GameData.MinSpeed);
windowForClimb.WhoIsClimbing = null;
// gameMap.Remove(addWall);
@@ -367,15 +367,15 @@ namespace Gaming
switch (prop.GetPropType())
{
case PropType.Key3:
if (doorToLock.Place == PlaceType.Door3)
if (doorToLock.DoorNum == 3)
flag = true;
break;
case PropType.Key5:
if (doorToLock.Place == PlaceType.Door5)
if (doorToLock.DoorNum == 5)
flag = true;
break;
case PropType.Key6:
if (doorToLock.Place == PlaceType.Door6)
if (doorToLock.DoorNum == 6)
flag = true;
break;
default:


+ 8
- 8
logic/Gaming/AttackManager.cs View File

@@ -48,7 +48,7 @@ namespace Gaming
{
case GameObjType.Character:

if ((!(((Character)objBeingShot).IsGhost())) && bullet.Parent.IsGhost())
if ((!(((Character)objBeingShot).IsGhost())) && bullet.Parent!.IsGhost())
{
characterManager.BeAttacked((Student)objBeingShot, bullet);
}
@@ -57,7 +57,7 @@ namespace Gaming
break;
case GameObjType.Generator:
if (bullet.CanBeBombed(GameObjType.Generator))
((Generator)objBeingShot).Repair(-bullet.AP * GameData.factorDamageGenerator, (Character)bullet.Parent);
((Generator)objBeingShot).Repair(-bullet.AP * GameData.factorDamageGenerator, (Character)bullet.Parent!);
break;
default:
break;
@@ -101,12 +101,12 @@ namespace Gaming
{
if (objBeingShot == null)
{
characterManager.BackSwing((Character)bullet.Parent, bullet.Backswing);
characterManager.BackSwing((Character)bullet.Parent!, bullet.Backswing);
return;
}

BombObj(bullet, objBeingShot);
characterManager.BackSwing((Character)bullet.Parent, bullet.RecoveryFromHit);
characterManager.BackSwing((Character)bullet.Parent!, bullet.RecoveryFromHit);
return;
}

@@ -122,7 +122,7 @@ namespace Gaming

if (bullet.TypeOfBullet == BulletType.BombBomb && objBeingShot != null)
{
bullet.Parent.BulletOfPlayer = BulletType.JumpyDumpty;
bullet.Parent!.BulletOfPlayer = BulletType.JumpyDumpty;
Debugger.Output(bullet.Parent, bullet.Parent.CharacterType.ToString() + " " + bullet.Parent.BulletNum.ToString());
Attack((Character)bullet.Parent, bullet.FacingDirection.Angle() + Math.PI / 2.0);
Attack((Character)bullet.Parent, bullet.FacingDirection.Angle() + Math.PI * 3.0 / 2.0);
@@ -159,10 +159,10 @@ namespace Gaming

if (objBeingShot == null)
{
characterManager.BackSwing((Character)bullet.Parent, bullet.Backswing);
characterManager.BackSwing((Character)bullet.Parent!, bullet.Backswing);
}
else
characterManager.BackSwing((Character)bullet.Parent, bullet.RecoveryFromHit);
characterManager.BackSwing((Character)bullet.Parent!, bullet.RecoveryFromHit);
}

public bool Attack(Character player, double angle)
@@ -178,7 +178,7 @@ namespace Gaming
(int)(Math.Abs((player.Radius + BulletFactory.BulletRadius(player.BulletOfPlayer)) * Math.Sin(angle))) * ((Math.Sin(angle) > 0) ? 1 : -1)
);

Bullet? bullet = player.Attack(res, gameMap.GetPlaceType(res));
Bullet? bullet = player.Attack(res);

if (bullet != null)
{


+ 8
- 7
logic/Gaming/CharacterManager .cs View File

@@ -25,11 +25,11 @@ namespace Gaming
switch (player.PlayerState)
{
case PlayerStateType.OpeningTheChest:
((Chest)player.WhatInteractingWith).StopOpen();
((Chest)player.WhatInteractingWith!).StopOpen();
player.ChangePlayerState(value, gameObj);
break;
case PlayerStateType.OpeningTheDoorway:
Doorway doorway = (Doorway)player.WhatInteractingWith;
Doorway doorway = (Doorway)player.WhatInteractingWith!;
doorway.OpenDegree += gameMap.Timer.nowTime() - doorway.OpenStartTime;
doorway.OpenStartTime = 0;
player.ChangePlayerState(value, gameObj);
@@ -302,7 +302,7 @@ namespace Gaming
if (character.CanBeAwed())
{
if (BeStunned(character, GameData.basicStunnedTimeOfStudent))
bullet.Parent.AddScore(GameData.TrickerScoreStudentBeStunned(GameData.basicStunnedTimeOfStudent));
bullet.Parent!.AddScore(GameData.TrickerScoreStudentBeStunned(GameData.basicStunnedTimeOfStudent));
return true;
}
return false;
@@ -321,7 +321,7 @@ namespace Gaming
Debugger.Output(student, "is being shot!");
#endif
if (student.NoHp()) return; // 原来已经死了
if (!bullet.Parent.IsGhost()) return;
if (!bullet.Parent!.IsGhost()) return;

if (student.CharacterType == CharacterType.StraightAStudent)
{
@@ -407,15 +407,16 @@ namespace Gaming
Prop? prop = player.UseProp(i);
if (prop != null)
{
prop.ReSetPos(player.Position, gameMap.GetPlaceType(player.Position));
prop.Position = player.Position;
gameMap.Add(prop);
}
}
if (player.CharacterType == CharacterType.Robot)
{
if (((Golem)player).Parent != null && ((Golem)player).Parent.CharacterType == CharacterType.TechOtaku)
var parent = ((Golem)player).Parent;
if (parent != null && parent.CharacterType == CharacterType.TechOtaku)
{
((SummonGolem)(((Golem)player).Parent.FindIActiveSkill(ActiveSkillType.SummonGolem))).GolemSummoned = null;
((SummonGolem)(parent.FindIActiveSkill(ActiveSkillType.SummonGolem))).GolemSummoned = null;
player.FindIActiveSkill(ActiveSkillType.UseRobot).IsBeingUsed = false;
}
return;


+ 6
- 6
logic/Gaming/PropManager.cs View File

@@ -124,13 +124,13 @@ namespace Gaming
if (prop.GetPropType() == PropType.Null)
return;

prop.ReSetPos(player.Position, gameMap.GetPlaceType(player.Position));
prop.Position = player.Position;
gameMap.Add(prop);
}

private Prop ProduceOnePropNotKey(Random r, XY Pos)
private static Prop ProduceOnePropNotKey(Random r, XY Pos)
{
return PropFactory.GetProp((PropType)r.Next(GameData.numOfTeachingBuilding + 1, GameData.numOfPropSpecies + 1), Pos, gameMap.GetPlaceType(Pos));
return PropFactory.GetProp((PropType)r.Next(GameData.numOfTeachingBuilding + 1, GameData.numOfPropSpecies + 1), Pos);
}

private Chest GetChest(Random r)
@@ -153,7 +153,7 @@ namespace Gaming
{
++cou;
Chest chest = GetChest(r);
chest.PropInChest[1] = new Key3(chest.Position, PlaceType.Chest);
chest.PropInChest[1] = new Key3(chest.Position);
chest.PropInChest[0] = ProduceOnePropNotKey(r, chest.Position);
}
cou = 0;
@@ -161,7 +161,7 @@ namespace Gaming
{
++cou;
Chest chest = GetChest(r);
chest.PropInChest[1] = new Key5(chest.Position, PlaceType.Chest);
chest.PropInChest[1] = new Key5(chest.Position);
chest.PropInChest[0] = ProduceOnePropNotKey(r, chest.Position);
}
cou = 0;
@@ -169,7 +169,7 @@ namespace Gaming
{
++cou;
Chest chest = GetChest(r);
chest.PropInChest[1] = new Key6(chest.Position, PlaceType.Chest);
chest.PropInChest[1] = new Key6(chest.Position);
chest.PropInChest[0] = ProduceOnePropNotKey(r, chest.Position);
}



+ 0
- 1
logic/Preparation/Interface/IGameObj.cs View File

@@ -7,7 +7,6 @@ namespace Preparation.Interface
public GameObjType Type { get; }
public long ID { get; }
public XY Position { get; } // if Square, Pos equals the center
public PlaceType Place { get; }
public XY FacingDirection { get; }
public bool IsRigid { get; }
public ShapeType Shape { get; }


+ 1
- 2
logic/Preparation/Interface/IMoveable.cs View File

@@ -9,8 +9,7 @@ namespace Preparation.Interface
public int MoveSpeed { get; }
public bool IsMoving { get; set; }
public bool IsAvailable { get; }
public long MovingSetPos(XY moveVec, PlaceType place);
public void ReSetPos(XY pos, PlaceType place);
public long MovingSetPos(XY moveVec);
public bool WillCollideWith(IGameObj? targetObj, XY nextPos) // 检查下一位置是否会和目标物碰撞
{
if (targetObj == null)


+ 0
- 1
logic/Preparation/Utility/GameData.cs View File

@@ -1,6 +1,5 @@
using Preparation.Interface;
using System;
using System.Net.NetworkInformation;

namespace Preparation.Utility
{


+ 1
- 5
logic/Server/CopyInfo.cs View File

@@ -61,7 +61,6 @@ namespace Server
Speed = player.MoveSpeed,
Determination = player.HP,
Addiction = player.GamingAddiction,
Place = Transformation.ToPlaceType((Preparation.Utility.PlaceType)player.Place),
Guid = player.ID,

PlayerState = Transformation.ToPlayerState((PlayerStateType)player.PlayerState),
@@ -108,7 +107,6 @@ namespace Server
X = player.Position.x,
Y = player.Position.y,
Speed = player.MoveSpeed,
Place = Transformation.ToPlaceType((Preparation.Utility.PlaceType)player.Place),

TrickerType = Transformation.ToTrickerType(player.CharacterType),
Guid = player.ID,
@@ -152,7 +150,6 @@ namespace Server
FacingDirection = bullet.FacingDirection.Angle(),
Guid = bullet.ID,
Team = (bullet.Parent!.IsGhost()) ? PlayerType.TrickerPlayer : PlayerType.StudentPlayer,
Place = Transformation.ToPlaceType((Preparation.Utility.PlaceType)bullet.Place),
BombRange = bullet.BulletBombRange,
Speed = bullet.Speed
}
@@ -170,8 +167,7 @@ namespace Server
X = prop.Position.x,
Y = prop.Position.y,
FacingDirection = prop.FacingDirection.Angle(),
Guid = prop.ID,
Place = Transformation.ToPlaceType((Preparation.Utility.PlaceType)prop.Place)
Guid = prop.ID
}
};
return msg;


+ 1
- 1
logic/Server/GameServer.cs View File

@@ -123,7 +123,7 @@ namespace Server
mwr?.Flush();
if (options.ResultFileName != DefaultArgumentOptions.FileName)
SaveGameResult(options.ResultFileName.EndsWith(".json") ? options.ResultFileName : options.ResultFileName + ".json");
SendGameResult();
// SendGameResult();
this.endGameSem.Release();
}
public void ReportGame(GameState gameState, bool requiredGaming = true)


+ 1
- 1
logic/cmd/PlaybackServer.cmd View File

@@ -1,2 +1,2 @@
@echo off
start cmd /k ..\Server\bin\Debug\net6.0\Server.exe --port 8888 --fileName .\ladder1.thuaipb --playback --playbackSpeed 4.0
start cmd /k ..\Server\bin\Debug\net6.0\Server.exe --port 8888 --fileName .\cannot.thuaipb --playback --playbackSpeed 2.0

+ 1
- 1
logic/cmd/gameServerAndClient.cmd View File

@@ -1,6 +1,6 @@
@echo off

start cmd /k ..\Server\bin\Debug\net6.0\Server.exe --ip 0.0.0.0 --port 8888 --studentCount 0 --trickerCount 1 --gameTimeInSecond 600 --fileName test
start cmd /k ..\Server\bin\Debug\net6.0\Server.exe --ip 0.0.0.0 --port 8888 --studentCount 4 --trickerCount 1 --gameTimeInSecond 600 --fileName test

ping -n 2 127.0.0.1 > NUL


+ 4
- 0
logic/cmd/video.cmd View File

@@ -0,0 +1,4 @@
@echo off


start cmd /k ..\Client\bin\Debug\net6.0-windows\Client.exe --ip thuai6.eesast.com --port 8889 --characterID 2030

Loading…
Cancel
Save