mirror of
https://github.com/ChuXunYu/OnlineRpg.git
synced 2026-01-31 11:55:46 +00:00
2
This commit is contained in:
160
src/server/GameServer.cpp
Normal file
160
src/server/GameServer.cpp
Normal file
@@ -0,0 +1,160 @@
|
||||
#include "server/GameServer.h"
|
||||
#include "server/ClientHandler.h"
|
||||
#include "server/GameLobby.h"
|
||||
#include "server/BattleRoomManager.h"
|
||||
#include <iostream>
|
||||
|
||||
GameServer::GameServer(int port, const std::string& dbPath)
|
||||
: m_port(port), m_nextClientId(1), m_isRunning(false) {
|
||||
|
||||
// 初始化数据库
|
||||
m_database = std::make_shared<Database>(dbPath);
|
||||
|
||||
// 初始化游戏模块
|
||||
m_lobby = std::make_shared<GameLobby>(this);
|
||||
m_battleManager = std::make_shared<BattleRoomManager>(this);
|
||||
}
|
||||
|
||||
GameServer::~GameServer() {
|
||||
stop();
|
||||
}
|
||||
|
||||
bool GameServer::start() {
|
||||
if (!m_database->isOpen()) {
|
||||
std::cerr << "无法打开数据库" << std::endl;
|
||||
return false;
|
||||
}
|
||||
|
||||
// 创建并绑定服务器socket
|
||||
if (!m_serverSocket.create()) {
|
||||
std::cerr << "创建服务器socket失败" << std::endl;
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!m_serverSocket.bind("0.0.0.0", m_port)) {
|
||||
std::cerr << "绑定端口失败:" << m_port << std::endl;
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!m_serverSocket.listen(10)) {
|
||||
std::cerr << "监听端口失败:" << m_port << std::endl;
|
||||
return false;
|
||||
}
|
||||
|
||||
m_isRunning = true;
|
||||
|
||||
std::cout << "服务器启动成功" << std::endl;
|
||||
std::cout << "监听端口:" << m_port << std::endl;
|
||||
std::cout << "数据库:" << (m_database->isOpen() ? "已连接" : "失败") << std::endl;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void GameServer::stop() {
|
||||
if (!m_isRunning) {
|
||||
return;
|
||||
}
|
||||
|
||||
m_isRunning = false;
|
||||
std::cout << "正在停止服务器..." << std::endl;
|
||||
|
||||
// 停止所有客户端
|
||||
{
|
||||
std::lock_guard<std::mutex> lock(m_clientsMutex);
|
||||
for (auto& pair : m_clients) {
|
||||
pair.second->stop();
|
||||
}
|
||||
m_clients.clear();
|
||||
}
|
||||
|
||||
// 关闭服务器socket
|
||||
m_serverSocket.close();
|
||||
|
||||
std::cout << "服务器已停止" << std::endl;
|
||||
}
|
||||
|
||||
void GameServer::run() {
|
||||
std::cout << "服务器正在接受连接..." << std::endl;
|
||||
|
||||
while (m_isRunning) {
|
||||
std::string clientAddr;
|
||||
int clientPort;
|
||||
SocketFd clientFd = m_serverSocket.accept(clientAddr, clientPort);
|
||||
|
||||
if (clientFd < 0) {
|
||||
if (m_isRunning) {
|
||||
std::cerr << "接受客户端连接失败" << std::endl;
|
||||
}
|
||||
continue;
|
||||
}
|
||||
|
||||
std::cout << "客户端已连接,来自 " << clientAddr << ":" << clientPort << std::endl;
|
||||
|
||||
// 创建ClientHandler
|
||||
int clientId = m_nextClientId++;
|
||||
|
||||
auto handler = std::make_shared<ClientHandler>(clientId, clientFd, this);
|
||||
|
||||
// 添加到客户端列表
|
||||
{
|
||||
std::lock_guard<std::mutex> lock(m_clientsMutex);
|
||||
m_clients[clientId] = handler;
|
||||
}
|
||||
|
||||
// 启动处理线程
|
||||
handler->start();
|
||||
|
||||
std::cout << "新客户端已连接:ID=" << clientId << ",FD=" << clientFd << std::endl;
|
||||
}
|
||||
}
|
||||
|
||||
int GameServer::addClient(std::shared_ptr<ClientHandler> client) {
|
||||
std::lock_guard<std::mutex> lock(m_clientsMutex);
|
||||
int clientId = m_nextClientId++;
|
||||
m_clients[clientId] = client;
|
||||
return clientId;
|
||||
}
|
||||
|
||||
void GameServer::removeClient(int clientId) {
|
||||
std::lock_guard<std::mutex> lock(m_clientsMutex);
|
||||
auto it = m_clients.find(clientId);
|
||||
if (it != m_clients.end()) {
|
||||
std::cout << "Removing client: ID=" << clientId << std::endl;
|
||||
m_clients.erase(it);
|
||||
}
|
||||
}
|
||||
|
||||
std::shared_ptr<ClientHandler> GameServer::getClientByUsername(const std::string& username) {
|
||||
std::lock_guard<std::mutex> lock(m_clientsMutex);
|
||||
for (auto& pair : m_clients) {
|
||||
if (pair.second->getUsername() == username) {
|
||||
return pair.second;
|
||||
}
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
std::vector<std::string> GameServer::getOnlinePlayers() {
|
||||
std::vector<std::string> players;
|
||||
std::lock_guard<std::mutex> lock(m_clientsMutex);
|
||||
|
||||
for (const auto& pair : m_clients) {
|
||||
const std::string& username = pair.second->getUsername();
|
||||
if (!username.empty() && pair.second->getState() == ClientState::Lobby) {
|
||||
players.push_back(username);
|
||||
}
|
||||
}
|
||||
|
||||
return players;
|
||||
}
|
||||
|
||||
void GameServer::broadcastToLobby(const std::string& message, int excludeClientId) {
|
||||
std::lock_guard<std::mutex> lock(m_clientsMutex);
|
||||
|
||||
for (auto& pair : m_clients) {
|
||||
if (pair.first != excludeClientId &&
|
||||
pair.second->getState() == ClientState::Lobby) {
|
||||
pair.second->sendMessage(message);
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user