void GameServer::handleDisconnections() { for (auto itr = mPeers.begin(); itr != mPeers.end(); ) { if ((*itr)->timedOut) { // Inform everyone of the disconnection, erase for (sf::Int32 identifier : (*itr)->aircraftIdentifiers) { sendToAll(sf::Packet() << static_cast<sf::Int32>(Server::PlayerDisconnect) << identifier); mAircraftInfo.erase(identifier); } mConnectedPlayers--; mAircraftCount -= (*itr)->aircraftIdentifiers.size(); itr = mPeers.erase(itr); // Go back to a listening state if needed if (mConnectedPlayers < mMaxConnectedPlayers) { mPeers.push_back(PeerPtr(new RemotePeer())); setListening(true); } broadcastMessage("An ally has disconnected."); } else { ++itr; } } }
void GameServer::executionThread() { setListening(true); sf::Time stepInterval = sf::seconds(1.f / 60.f); sf::Time stepTime = sf::Time::Zero; sf::Time tickInterval = sf::seconds(1.f / 20.f); sf::Time tickTime = sf::Time::Zero; sf::Clock stepClock, tickClock; while (!mWaitingThreadEnd) { handleIncomingPackets(); handleIncomingConnections(); stepTime += stepClock.getElapsedTime(); stepClock.restart(); tickTime += tickClock.getElapsedTime(); tickClock.restart(); // Fixed update step while (stepTime >= stepInterval) { mBattleFieldRect.top += mBattleFieldScrollSpeed * stepInterval.asSeconds(); stepTime -= stepInterval; } // Fixed tick step while (tickTime >= tickInterval) { tick(); tickTime -= tickInterval; } // Sleep to prevent server from consuming 100% CPU sf::sleep(sf::milliseconds(100)); } }
void GameServer::handleIncomingConnections() { if (!mListeningState) return; if (mListenerSocket.accept(mPeers[mConnectedPlayers]->socket) == sf::TcpListener::Done) { // order the new client to spawn its own plane ( player 1 ) mAircraftInfo[mAircraftIdentifierCounter].position = sf::Vector2f(mBattleFieldRect.width / 2, mBattleFieldRect.top + mBattleFieldRect.height / 2); mAircraftInfo[mAircraftIdentifierCounter].hitpoints = 100; mAircraftInfo[mAircraftIdentifierCounter].missileAmmo = 2; sf::Packet packet; packet << static_cast<sf::Int32>(Server::SpawnSelf); packet << mAircraftIdentifierCounter; packet << mAircraftInfo[mAircraftIdentifierCounter].position.x; packet << mAircraftInfo[mAircraftIdentifierCounter].position.y; mPeers[mConnectedPlayers]->aircraftIdentifiers.push_back(mAircraftIdentifierCounter); broadcastMessage("New player!"); informWorldState(mPeers[mConnectedPlayers]->socket); notifyPlayerSpawn(mAircraftIdentifierCounter++); mPeers[mConnectedPlayers]->socket.send(packet); mPeers[mConnectedPlayers]->ready = true; mPeers[mConnectedPlayers]->lastPacketTime = now(); // prevent initial timeouts mAircraftCount++; mConnectedPlayers++; if (mConnectedPlayers >= mMaxConnectedPlayers) setListening(false); else // Add a new waiting peer mPeers.push_back(PeerPtr(new RemotePeer())); } }
void Server::execute(){ /* Enable the server to begin accepting clients */ setListening(true); do{ handleConnections(); }while( current_connected_players != max_connected_players ); /* Randomly assign player ids */ assignIds(); /* Signal all players that the game is ready to Begin */ broadcastPacket(PacketFactory::GAMESTART); /* Send out the packets for the Dictionary Data */ broadcastPacket(PacketFactory::TROOPDEF); bool keep_playing = true; // send init packet for first turn sendPacket(PacketFactory::TURNSTART, 0); while( keep_playing ){ keep_playing = handlePacket(); // std::cout << "keep_playing" << keep_playing << std::endl; } }
void Server::handleConnections() { if(accepting_clients == sf::Socket::Disconnected) return; if (acceptor.accept(players[current_connected_players]->socket) == sf::Socket::Done) { std::cout << players[current_connected_players]->socket.getRemoteAddress() << std::endl; current_connected_players++; if (current_connected_players >= max_connected_players) setListening(false); else players.push_back(new RemotePlayer()); } }
bool SocketWrapper::setListen(int backlog) { if (isListening()) { HAGGLE_DBG("Already listening."); return false; } if (SOCKET_ERROR == listen(sock, backlog)) { HAGGLE_DBG("Could not set listen."); return false; } setListening(true); return true; }