Attack refined

This commit is contained in:
Maximilian Giller 2023-07-10 22:34:04 +02:00
parent 36aa2fa245
commit ac435f8e4f
7 changed files with 107 additions and 32 deletions

View file

@ -17,13 +17,13 @@
#define DEFAULT_MAX_PLAYER_NUMBER 4 #define DEFAULT_MAX_PLAYER_NUMBER 4
#define MIN_PLAYER_COUNT 2 #define MIN_PLAYER_COUNT 2
#define REDUCED_POINT_DELTA_FOR_ATTACK 20 #define REDUCED_POINT_DELTA_FOR_ATTACK 20
#define ATTACK_PER_SECOND 5.f #define ATTACK_PER_SECOND 1.f
#define PLAYER_ALIVE_THRESHOLD -10 #define PLAYER_ALIVE_THRESHOLD -10
// World // World
#define WORLD_GRAVITY b2Vec2(0.f, -9.8f) #define WORLD_GRAVITY b2Vec2(0.f, -9.8f)
#define SKY_HEIGHT_SCALE 5.f #define SKY_HEIGHT_SCALE 5.f
#define CONSIDER_COLLECTABLE_DEPTH_MOVEMENT false // Might cost perfomance and is currently not in use #define CONSIDER_COLLECTABLE_DEPTH_MOVEMENT false // Might cost performance and is currently not in use
// FPS // FPS
#define FRAME_RATE 60 #define FRAME_RATE 60
@ -53,7 +53,6 @@
#define DEF_TV_IS_ABSOLUTE_VIEW_SIZE_PADDING false #define DEF_TV_IS_ABSOLUTE_VIEW_SIZE_PADDING false
#define DEF_TV_VIEW_SIZE_PADDING sf::Vector2f(2.f, 2.f) #define DEF_TV_VIEW_SIZE_PADDING sf::Vector2f(2.f, 2.f)
#define MP_VIEW_ADD_NEW_PLAYERS true #define MP_VIEW_ADD_NEW_PLAYERS true
#define MP_VIEW_REMOVE_DISCONNECTED_PLAYERS true
#define MP_VIEW_BORDER_COLOR sf::Color::Black #define MP_VIEW_BORDER_COLOR sf::Color::Black
// Simulations // Simulations

View file

@ -27,15 +27,6 @@ void MultiplayerView::update()
} }
} }
// Remove old
if (MP_VIEW_REMOVE_DISCONNECTED_PLAYERS)
{
for (const auto &player: PlayerCollection::getInstance()->getRemovedPlayers())
{
removePlayer(player);
}
}
GameObject::update(); GameObject::update();
} }

View file

@ -205,8 +205,9 @@ void Game::handleWinning()
LOG(INFO) << "Player " << winner->getPlayerId() << " won the game with " << winner->getPoints() << " points."; LOG(INFO) << "Player " << winner->getPlayerId() << " won the game with " << winner->getPoints() << " points.";
// Stop game and show winner // Stop game and show winner
auto players = PlayerCollection::getInstance()->getPlayers();
LevelLoader::cleanUp(); LevelLoader::cleanUp();
auto winnerScreen = std::make_shared<WinnerScreen>(winner); auto winnerScreen = std::make_shared<WinnerScreen>(players);
GlobalLayer::getInstance()->add(winnerScreen); GlobalLayer::getInstance()->add(winnerScreen);
addGameObject(GlobalLayer::getInstance()); addGameObject(GlobalLayer::getInstance());
} }

View file

@ -104,10 +104,8 @@ void Player::updateRadiusBasedOnPoints()
void Player::consume(int consumedPoints) void Player::consume(int consumedPoints)
{ {
this->points += consumedPoints; setPoints(getPoints() + consumedPoints);
LOG(INFO) << "Player " << playerId << " consumed " << consumedPoints << " points. Total: " << this->points; LOG(INFO) << "Player " << playerId << " consumed " << consumedPoints << " points. Total: " << this->points;
updateRadiusBasedOnPoints();
} }
std::string Player::getSkinName() const std::string Player::getSkinName() const
@ -143,7 +141,7 @@ void Player::setCollidingPlayers(const std::vector<int>& collidingPlayerIds)
void Player::handlePlayerCollisions() void Player::handlePlayerCollisions()
{ {
if (collidingPlayers.empty()) if (collidingPlayers.empty() || !isAlive)
{ {
return; return;
} }
@ -159,19 +157,12 @@ void Player::handlePlayerCollisions()
} }
// Reduce points if necessary // Reduce points if necessary
float damage = numAttackingPlayers * ATTACK_PER_SECOND * FRAME_TIME.asSeconds(); float damage = numAttackingPlayers * ATTACK_PER_SECOND * FRAME_TIME.asSeconds() * (getPoints() + 1 + abs(PLAYER_ALIVE_THRESHOLD));
points -= damage;
if (damage > 0) { if (damage > 0) {
LOG(INFO) << "Player " << playerId << " lost " << damage << " points due to collisions. Total: " << points; LOG(INFO) << "Player " << playerId << " lost " << damage << " points due to collisions. Total: " << points - damage;
} }
if (points <= PLAYER_ALIVE_THRESHOLD) setPoints(points - damage);
{
setAlive(false);
}
updateRadiusBasedOnPoints();
} }
bool Player::getAlive() const bool Player::getAlive() const
@ -213,3 +204,22 @@ void Player::draw(sf::RenderWindow *window)
coordinates->isometric().y - text.getLocalBounds().height / 2.f); coordinates->isometric().y - text.getLocalBounds().height / 2.f);
window->draw(text); window->draw(text);
} }
void Player::setPoints(float newPoints)
{
points = newPoints;
updateRadiusBasedOnPoints();
if (points > highestPoints)
{
highestPoints = points;
} else if (points <= PLAYER_ALIVE_THRESHOLD)
{
setAlive(false);
}
}
int Player::getMaxPoints() const
{
return highestPoints;
}

View file

@ -31,6 +31,8 @@ public:
[[nodiscard]] int getPoints() const; [[nodiscard]] int getPoints() const;
int getMaxPoints() const;
void consume(int consumedPoints); void consume(int consumedPoints);
std::string getSkinName() const; std::string getSkinName() const;
@ -54,12 +56,15 @@ private:
std::shared_ptr<VersatileSprite> skinSprite; std::shared_ptr<VersatileSprite> skinSprite;
std::vector<std::shared_ptr<Player>> collidingPlayers; std::vector<std::shared_ptr<Player>> collidingPlayers;
void setPoints(float newPoints);
bool passiveMode = true; bool passiveMode = true;
bool isAlive = true; bool isAlive = true;
std::string skinName; std::string skinName;
float points = DEFAULT_PLAYER_POINTS; float points = DEFAULT_PLAYER_POINTS;
float highestPoints = DEFAULT_PLAYER_POINTS;
int playerId; int playerId;
static inline int playerCreationCounter = 0; static inline int playerCreationCounter = 0;

View file

@ -4,8 +4,27 @@
#include "../texture_config.h" #include "../texture_config.h"
#include "../game/game.h" #include "../game/game.h"
WinnerScreen::WinnerScreen(const std::shared_ptr<Player> &winner) WinnerScreen::WinnerScreen(std::vector<std::shared_ptr<Player>> players)
: winner(winner) {
// Sort players by points descending
std::sort(players.begin(), players.end(), [](const std::shared_ptr<Player> &a, const std::shared_ptr<Player> &b)
{
return a->getPoints() > b->getPoints();
});
// Get winner
winner = players[0];
createWinnerTribute(winner);
if (players.size() > 1)
{
// Remove winner from list
players.erase(players.begin());
listRemainingScores(players);
}
}
void WinnerScreen::createWinnerTribute(const std::shared_ptr<Player> &winner)
{ {
// Winner title // Winner title
auto winnerTitle = std::make_shared<sf::Text>(); auto winnerTitle = std::make_shared<sf::Text>();
@ -18,7 +37,8 @@ WinnerScreen::WinnerScreen(const std::shared_ptr<Player> &winner)
add(winnerTitle); add(winnerTitle);
// Add graphic of the winner // Add graphic of the winner
auto winnerGraphic = std::make_shared<VersatileSprite>(winner->getSkinName(), sf::Vector2f(500, 500 * ISOMETRIC_SKEW)); auto winnerGraphic = std::make_shared<VersatileSprite>(winner->getSkinName(),
sf::Vector2f(500, 500 * ISOMETRIC_SKEW));
auto center = REFERENCE_SIZE / 2.f; auto center = REFERENCE_SIZE / 2.f;
auto winnerPosition = center - winnerGraphic->getSize() / 2.f; auto winnerPosition = center - winnerGraphic->getSize() / 2.f;
winnerGraphic->coordinates->setIsometric(IsometricCoordinates(winnerPosition)); winnerGraphic->coordinates->setIsometric(IsometricCoordinates(winnerPosition));
@ -33,6 +53,19 @@ WinnerScreen::WinnerScreen(const std::shared_ptr<Player> &winner)
points->setPosition(REFERENCE_SIZE.x / 2 - points->getGlobalBounds().width / 2, REFERENCE_SIZE.y - 400); points->setPosition(REFERENCE_SIZE.x / 2 - points->getGlobalBounds().width / 2, REFERENCE_SIZE.y - 400);
add(points); add(points);
// Show points below
if (winner->getMaxPoints() != winner->getPoints())
{
auto highestPoints = std::make_shared<sf::Text>();
highestPoints->setFont(*FontManager::getInstance()->getDefaultFont());
highestPoints->setString("Highest Points: " + std::to_string(winner->getPoints()));
highestPoints->setCharacterSize(20);
highestPoints->setFillColor(sf::Color::Yellow);
highestPoints->setPosition(REFERENCE_SIZE.x / 2 - highestPoints->getGlobalBounds().width / 2,
REFERENCE_SIZE.y - 360);
add(highestPoints);
}
// Show press button to continue // Show press button to continue
auto input = winner->getInput(); auto input = winner->getInput();
auto confirmButton = DEVICE_GROUP_CONFIRM.at(input->deviceGroup); auto confirmButton = DEVICE_GROUP_CONFIRM.at(input->deviceGroup);
@ -51,7 +84,39 @@ void WinnerScreen::update()
GameObject::update(); GameObject::update();
auto input = winner->getInput(); auto input = winner->getInput();
if (input->isPerformingAction(GameAction::CONFIRM)) { if (input->isPerformingAction(GameAction::CONFIRM))
{
Game::getInstance()->showJoinScreen(); Game::getInstance()->showJoinScreen();
} }
} }
void WinnerScreen::listRemainingScores(const std::vector<std::shared_ptr<Player>> &remainingPlayers)
{
int leftPadding = 150;
int topPadding = 500;
int betweenPadding = 50;
int height = 64;
int index = 0;
for (const auto &player: remainingPlayers)
{
// Player skin
auto playerGraphic = std::make_shared<VersatileSprite>(player->getSkinName(),
sf::Vector2f(height / ISOMETRIC_SKEW, height));
playerGraphic->coordinates->setIsometric(
IsometricCoordinates(leftPadding, topPadding + index * (height + betweenPadding)));
add(playerGraphic);
// Points
auto points = std::make_shared<sf::Text>();
points->setFont(*FontManager::getInstance()->getDefaultFont());
points->setString(std::to_string(player->getMaxPoints()));
points->setCharacterSize(20);
points->setFillColor(sf::Color::White);
points->setPosition(leftPadding + playerGraphic->getSize().x + 10,
topPadding + index * (height + betweenPadding) + height / 2.f -
points->getGlobalBounds().height / 2.f);
add(points);
index++;
}
}

View file

@ -9,12 +9,16 @@
class WinnerScreen : public Screen class WinnerScreen : public Screen
{ {
public: public:
WinnerScreen(const std::shared_ptr<Player> &winner); WinnerScreen(std::vector<std::shared_ptr<Player>> players);
void update() override; void update() override;
private: private:
std::shared_ptr<Player> winner; std::shared_ptr<Player> winner;
void createWinnerTribute(const std::shared_ptr<Player> &winner);
void listRemainingScores(const std::vector<std::shared_ptr<Player>>& remainingPlayers);
}; };