diff --git a/2dgk_zad3/2dgk_zad3/2dgk_zad3.vcxproj b/2dgk_zad3/2dgk_zad3/2dgk_zad3.vcxproj
index c0a36d3..c4612ad 100644
--- a/2dgk_zad3/2dgk_zad3/2dgk_zad3.vcxproj
+++ b/2dgk_zad3/2dgk_zad3/2dgk_zad3.vcxproj
@@ -203,6 +203,7 @@
+
@@ -249,4 +250,9 @@
+
+
+
+
+
\ No newline at end of file
diff --git a/2dgk_zad3/2dgk_zad3/2dgk_zad3.vcxproj.filters b/2dgk_zad3/2dgk_zad3/2dgk_zad3.vcxproj.filters
index 74e4d9b..e8a8395 100644
--- a/2dgk_zad3/2dgk_zad3/2dgk_zad3.vcxproj.filters
+++ b/2dgk_zad3/2dgk_zad3/2dgk_zad3.vcxproj.filters
@@ -147,6 +147,9 @@
Header Files
+
+ Header Files
+
diff --git a/2dgk_zad3/2dgk_zad3/Constants.h b/2dgk_zad3/2dgk_zad3/Constants.h
index 816a48e..5792a3f 100644
--- a/2dgk_zad3/2dgk_zad3/Constants.h
+++ b/2dgk_zad3/2dgk_zad3/Constants.h
@@ -1,22 +1,21 @@
#pragma once
-namespace KapitanGame {
- namespace Constants {
- constexpr const char* WINDOW_TITLE = "2DGK - Zadanie 3 (Lab 11-12)";
- //Analog joystick dead zone
- constexpr int JOYSTICK_DEAD_ZONE = 8000;
- //Screen dimension constants
- constexpr int WINDOW_DEAD_ZONE = 100;
- constexpr int SCREEN_WIDTH = 640;
- constexpr int SCREEN_HEIGHT = 480;
- constexpr float SCREEN_RATIO = static_cast(SCREEN_WIDTH) / SCREEN_HEIGHT;
- constexpr int TILE_WIDTH = 32;
- constexpr int TILE_HEIGHT = 32;
- constexpr float SPEED = 200.f;
- constexpr float SMOOTH = 0.4f;
- constexpr float JUMP_SPEED = 300.f;
- constexpr float GRAVITY = 450.f;
- constexpr float MAX_JUMP_VELOCITY = 1000.f;
- constexpr float MAX_GRAVITY = 1000.f;
- }
+namespace KapitanGame::Constants
+{
+ constexpr const char* WINDOW_TITLE = "2DGK - Zadanie 3 (Lab 11-12)";
+ //Analog joystick dead zone
+ constexpr int JOYSTICK_DEAD_ZONE = 8000;
+ //Screen dimension constants
+ constexpr int WINDOW_DEAD_ZONE = 100;
+ constexpr int SCREEN_WIDTH = 640;
+ constexpr int SCREEN_HEIGHT = 480;
+ constexpr float SCREEN_RATIO = static_cast(SCREEN_WIDTH) / SCREEN_HEIGHT;
+ constexpr int TILE_WIDTH = 32;
+ constexpr int TILE_HEIGHT = 32;
+ constexpr float SPEED = 200.f;
+ constexpr float SMOOTH = 0.4f;
+ constexpr float JUMP_SPEED = 300.f;
+ constexpr float HORIZONTAL_DISTANCE_TO_MAX_JUMP_HEIGHT = TILE_WIDTH * 4.f;
+ constexpr float MAX_JUMP_HEIGHT = TILE_HEIGHT * 4.f;
+ constexpr float MAX_GRAVITY = 1000.f;
}
diff --git a/2dgk_zad3/2dgk_zad3/KCircle.cpp b/2dgk_zad3/2dgk_zad3/KCircle.cpp
index 51d562c..2533f88 100644
--- a/2dgk_zad3/2dgk_zad3/KCircle.cpp
+++ b/2dgk_zad3/2dgk_zad3/KCircle.cpp
@@ -1,5 +1,6 @@
#include "KCircle.h"
+#include
#include
#include "KRect.h"
@@ -13,13 +14,11 @@ namespace KapitanGame {
bool KCircle::IsCollision(const KCollider* other) const
{
- const auto circle = dynamic_cast(other);
- if (circle != nullptr)
+ if (const auto circle = dynamic_cast(other); circle != nullptr)
return IsCollision(circle);
- const auto rect = dynamic_cast(other);
- if (rect != nullptr)
+ if (const auto rect = dynamic_cast(other); rect != nullptr)
return IsCollision(rect);
throw std::runtime_error("unsupported shape");
@@ -27,12 +26,10 @@ namespace KapitanGame {
KVector2D KCircle::GetSeparationVector(const KCollider* other) const
{
- const auto circle = dynamic_cast(other);
- if (circle != nullptr)
+ if (const auto circle = dynamic_cast(other); circle != nullptr)
return GetSeparationVector(circle);
- const auto rect = dynamic_cast(other);
- if (rect != nullptr)
+ if (const auto rect = dynamic_cast(other); rect != nullptr)
return GetSeparationVector(rect);
throw std::runtime_error("unsupported shape");
diff --git a/2dgk_zad3/2dgk_zad3/KCircle.h b/2dgk_zad3/2dgk_zad3/KCircle.h
index a4db204..3081a5a 100644
--- a/2dgk_zad3/2dgk_zad3/KCircle.h
+++ b/2dgk_zad3/2dgk_zad3/KCircle.h
@@ -11,8 +11,8 @@ namespace KapitanGame {
class KCircle final : public KCollider
{
public:
- KCircle(KObject* parent, const float radius);
- float GetRadius() const;
+ KCircle(KObject* parent, float radius);
+ [[nodiscard]] float GetRadius() const;
private:
KVector2D GetSeparationVector(const KCircle* other) const;
KVector2D GetSeparationVector(const KRect* other) const;
@@ -21,9 +21,9 @@ namespace KapitanGame {
public:
bool IsCollision(const KCollider* other) const override;
KVector2D GetSeparationVector(const KCollider* other) const override;
- KVector2D GetSeparationVector(const SDL_FRect& map) const override;
- float GetWidth() const override;
- float GetHeight() const override;
+ [[nodiscard]] KVector2D GetSeparationVector(const SDL_FRect& map) const override;
+ [[nodiscard]] float GetWidth() const override;
+ [[nodiscard]] float GetHeight() const override;
private:
float Radius{ 1.f };
};
diff --git a/2dgk_zad3/2dgk_zad3/KCollider.h b/2dgk_zad3/2dgk_zad3/KCollider.h
index 77e8e07..eb14f63 100644
--- a/2dgk_zad3/2dgk_zad3/KCollider.h
+++ b/2dgk_zad3/2dgk_zad3/KCollider.h
@@ -23,10 +23,10 @@ namespace KapitanGame {
virtual ~KCollider() = default;
virtual bool IsCollision(const KCollider* other) const = 0;
virtual KVector2D GetSeparationVector(const KCollider* other) const = 0;
- virtual KVector2D GetSeparationVector(const SDL_FRect& map) const = 0;
- virtual float GetWidth() const = 0;
- virtual float GetHeight() const = 0;
- KObject* GetParent() const;
+ [[nodiscard]] virtual KVector2D GetSeparationVector(const SDL_FRect& map) const = 0;
+ [[nodiscard]] virtual float GetWidth() const = 0;
+ [[nodiscard]] virtual float GetHeight() const = 0;
+ [[nodiscard]] KObject* GetParent() const;
private:
KObject* Parent;
};
diff --git a/2dgk_zad3/2dgk_zad3/KExit.h b/2dgk_zad3/2dgk_zad3/KExit.h
index 60c5d45..2c09a9b 100644
--- a/2dgk_zad3/2dgk_zad3/KExit.h
+++ b/2dgk_zad3/2dgk_zad3/KExit.h
@@ -10,11 +10,11 @@ namespace KapitanGame
public:
KExit(const KVector2D& position, const KTexture& texture)
: KObject(position, texture),
- Collider(this, texture.GetWidth() * 1.f, texture.GetHeight() * 1.f)
+ Collider(this, static_cast(texture.GetWidth()), static_cast(texture.GetHeight()))
{
}
- const KCollider* GetCollider() const override;
+ [[nodiscard]] const KCollider* GetCollider() const override;
private:
KRect Collider;
};
diff --git a/2dgk_zad3/2dgk_zad3/KFont.cpp b/2dgk_zad3/2dgk_zad3/KFont.cpp
index 7bbb11d..16dea77 100644
--- a/2dgk_zad3/2dgk_zad3/KFont.cpp
+++ b/2dgk_zad3/2dgk_zad3/KFont.cpp
@@ -1,5 +1,7 @@
#include "KFont.h"
+#include
+
#include "KTexture.h"
namespace KapitanGame
@@ -48,16 +50,49 @@ namespace KapitanGame
KTexture KFont::GetTextTexture(const std::string& text, const SDL_Color textColor, SDL_Renderer* renderer) const
{
KTexture texture;
- SDL_Surface* textSurface = TTF_RenderText_Solid(Font, text.c_str(), textColor);
- if (textSurface == nullptr)
+ constexpr int spacing = 1;
+ int width, height = width = 0;
+ std::istringstream inputText;
+ inputText.str(text);
+ for(std::string line; std::getline(inputText, line);)
{
- printf("Unable to render text surface! SDL_ttf Error: %s\n", TTF_GetError());
+ int w, h;
+ TTF_SizeText(Font, line.c_str(), &w, &h);
+ if (w > width) width = w;
+ height += w+spacing;
}
- else
+ if (height > 0)
+ height -= spacing;
+ inputText.clear();
+ inputText.seekg(0);
+ SDL_Surface* textureSurface = SDL_CreateRGBSurfaceWithFormat(0, width, height, 8, SDL_PIXELFORMAT_INDEX8);
{
- texture.LoadFromSurface(textSurface, renderer);
- SDL_FreeSurface(textSurface);
+ const SDL_Palette* palette = textureSurface->format->palette;
+ palette->colors[0].r = 255 - textColor.r;
+ palette->colors[0].g = 255 - textColor.g;
+ palette->colors[0].b = 255 - textColor.b;
+ palette->colors[1].r = textColor.r;
+ palette->colors[1].g = textColor.g;
+ palette->colors[1].b = textColor.b;
+ palette->colors[1].a = textColor.a;
}
+ SDL_SetColorKey(textureSurface, SDL_TRUE, 0);
+ int y = 0;
+ for (std::string line; std::getline(inputText, line);) {
+ if (SDL_Surface* textSurface = TTF_RenderText_Solid(Font, line.c_str(), textColor); textSurface == nullptr)
+ {
+ printf("Unable to render text surface! SDL_ttf Error: %s\n", TTF_GetError());
+ }
+ else
+ {
+ SDL_Rect destRect{0, y, textSurface->w, textSurface->h};
+ SDL_BlitSurface(textSurface, nullptr, textureSurface, &destRect);
+ y += textSurface->h + spacing;
+ SDL_FreeSurface(textSurface);
+ }
+ }
+ texture.LoadFromSurface(textureSurface, renderer);
+ SDL_FreeSurface(textureSurface);
return texture;
}
diff --git a/2dgk_zad3/2dgk_zad3/KGame.cpp b/2dgk_zad3/2dgk_zad3/KGame.cpp
index 830be5a..418d9e5 100644
--- a/2dgk_zad3/2dgk_zad3/KGame.cpp
+++ b/2dgk_zad3/2dgk_zad3/KGame.cpp
@@ -11,18 +11,13 @@
#include "KCamera.h"
#include "KCirclePawn.h"
#include "KExit.h"
-#include "KRectPawn.h"
#include "KTexture.h"
#include "KTile.h"
#include "KVector2d.h"
#include "KWall.h"
-#ifndef M_PI
-#define M_PI 3.14159265358979323846
-#endif
-
namespace KapitanGame {
- KGame::KGame() : Time(0), PreviousTime(0), Map()
+ KGame::KGame() : Time(0), PreviousTime(0), Map(), Settings(Constants::MAX_JUMP_HEIGHT, Constants::HORIZONTAL_DISTANCE_TO_MAX_JUMP_HEIGHT)
{
//Initialize SDL
if (SDL_Init(SDL_INIT_VIDEO) < 0)
@@ -109,7 +104,10 @@ namespace KapitanGame {
if (mapWidth < static_cast(line.length() * Constants::TILE_WIDTH))
mapWidth = static_cast(line.length()) * Constants::TILE_WIDTH;
for (auto i = 0ull; i < line.length(); ++i) {
- KVector2D position{ static_cast(i * Constants::TILE_WIDTH + Constants::TILE_WIDTH / 2) , static_cast(y * Constants::TILE_HEIGHT + Constants::TILE_HEIGHT / 2) };
+ KVector2D position{
+ static_cast(i * Constants::TILE_WIDTH + Constants::TILE_WIDTH / 2), // NOLINT(bugprone-integer-division)
+ static_cast(y * Constants::TILE_HEIGHT + Constants::TILE_HEIGHT / 2) // NOLINT(bugprone-integer-division)
+ };
switch (line[i])
{
case '#':
@@ -150,7 +148,7 @@ namespace KapitanGame {
break;
}
- PlayerControllers.emplace_back(std::make_shared(player, this));
+ PlayerControllers.emplace_back(std::make_shared(player));
PlayerControllers.back()->SetupInputBindings(Input);
}
Textures.emplace("wall.bmp", KTexture());
@@ -168,11 +166,8 @@ namespace KapitanGame {
Fonts.erase("PressStart2P-Regular");
success = false;
}
- //Textures.emplace("Text_Score", Fonts["Roboto-Thin"].GetTextWithOutlineTexture("0:0", { 0xFF,0xFF,0xFF,0xFF }, { 0,0,0,0xFF }, 1, Renderer));
- //Textures.emplace("Text_Winner", KTexture());
- std::ifstream configFile("config.json");
- if (configFile.fail()) {
+ if (std::ifstream configFile("config.json"); configFile.fail()) {
printf("Failed to load config.json!\n");
success = false;
}
@@ -218,8 +213,7 @@ namespace KapitanGame {
camera.Update(Pawns, Map);
- VelocityTextureDirty = true;
- GravityTextureDirty = true;
+ SettingsTextTextureDirty = true;
Time = PreviousTime = SDL_GetTicks();
printf("\n");
@@ -229,7 +223,7 @@ namespace KapitanGame {
{
PreviousTime = Time;
Time = SDL_GetTicks();
- float deltaTime = (Time - PreviousTime) * 0.001f;
+ float deltaTime = static_cast(Time - PreviousTime) * 0.001f;
Input.HandleInputPreEvents();
@@ -255,31 +249,28 @@ namespace KapitanGame {
if (devMode >= 1) {
if (Input.IsKeyboardButtonPressed(SDL_SCANCODE_F2))
{
- CollisionEnabled = !CollisionEnabled;
+ Settings.CollisionEnabled = !Settings.CollisionEnabled;
}
if (Input.IsKeyboardButtonHeld(SDL_SCANCODE_F3))
{
- Settings.JumpVelocity -= 0.1f;
- if (Settings.JumpVelocity < 0) Settings.JumpVelocity = 0;
- VelocityTextureDirty = true;
+ Settings.MaxJumpHeight -= 0.1f;
+ //Settings.SetMaxJumpHeight(Settings.GetMaxJumpHeight() - 0.1f);
+ SettingsTextTextureDirty = true;
}
if (Input.IsKeyboardButtonHeld(SDL_SCANCODE_F4))
{
- Settings.JumpVelocity += 0.1f;
- if (Settings.JumpVelocity > Constants::MAX_JUMP_VELOCITY) Settings.JumpVelocity = Constants::MAX_JUMP_VELOCITY;
- VelocityTextureDirty = true;
+ Settings.MaxJumpHeight += 0.1f;
+ SettingsTextTextureDirty = true;
}
if (Input.IsKeyboardButtonHeld(SDL_SCANCODE_F5))
{
- Settings.Gravity -= 0.1f;
- if (Settings.Gravity < 0) Settings.Gravity = 0;
- GravityTextureDirty = true;
+ Settings.HorizontalDistanceToMaxJumpHeight -= 0.1f;
+ SettingsTextTextureDirty = true;
}
if (Input.IsKeyboardButtonHeld(SDL_SCANCODE_F6))
{
- Settings.Gravity += 0.1f;
- if (Settings.Gravity > Constants::MAX_GRAVITY) Settings.Gravity = Constants::MAX_GRAVITY;
- GravityTextureDirty = true;
+ Settings.HorizontalDistanceToMaxJumpHeight += 0.1f;
+ SettingsTextTextureDirty = true;
}
}
@@ -291,7 +282,7 @@ namespace KapitanGame {
if (!Playing) break;
pawn->MovementStep(deltaTime);
}
- if (CollisionEnabled) {
+ if (Settings.CollisionEnabled) {
for (const auto& pawn : Pawns) {
if (!Playing) break;
pawn->CollisionDetectionStep(Objects);
@@ -309,14 +300,19 @@ namespace KapitanGame {
camera.Update(Pawns, Map);
}
- if (VelocityTextureDirty) {
- Textures.insert_or_assign("Text_Velocity", Fonts["PressStart2P-Regular"].GetTextTexture(Utils::StringFormat("Velocity: %f", Settings.JumpVelocity), { 0,0,0,0xFF }, Renderer));
- VelocityTextureDirty = false;
- }
- if (GravityTextureDirty) {
- Textures.insert_or_assign("Text_Gravity", Fonts["PressStart2P-Regular"].GetTextTexture(Utils::StringFormat("Gravity: %f", Settings.Gravity), { 0,0,0,0xFF }, Renderer));
- GravityTextureDirty = false;
- }
+ //if (SettingsTextTextureDirty) {
+ Textures.insert_or_assign("Text_Settings", Fonts["PressStart2P-Regular"].GetTextTexture(
+ Utils::StringFormat(
+ "Max Jump Height: %f\nHorizontal Distance to Max Jump Height: %f\nInitial Jump Velocity: %f\nGravity: %f\nPlayer Position X: %f\nPlayer Position Y: %f",
+ static_cast(Settings.MaxJumpHeight),
+ static_cast(Settings.HorizontalDistanceToMaxJumpHeight),
+ static_cast(Settings.JumpInitialVelocity),
+ static_cast(Settings.Gravity),
+ Pawns.back()->GetPosition().X,
+ Pawns.back()->GetPosition().Y), {0, 0, 0, 0xFF},
+ Renderer));
+ //SettingsTextTextureDirty = false;
+ //}
if (!Playing)
@@ -326,16 +322,6 @@ namespace KapitanGame {
LoadLevel();
debugCamera.SetDebug(Map);
camera.Update(Pawns, Map);
- if (ShowWinner)
- {
- for (auto i : Utils::KPlayerIterator())
- {
- Scores[static_cast(i)] = 0;
- }
- //Textures.erase("Text_Score");
- //Textures.emplace("Text_Score", Fonts["Roboto-Thin"].GetTextWithOutlineTexture(Utils::StringFormat("%d:%d", Scores[0], Scores[1]), { 0xFF,0xFF,0xFF,0xFF }, { 0,0,0,0xFF }, 1, Renderer));
- ShowWinner = false;
- }
Playing = true;
continue;
}
@@ -355,22 +341,10 @@ namespace KapitanGame {
for (const auto& pawn : Pawns) {
pawn->Render(Renderer, cameraInUse);
}
- if (const auto exit = Exit.lock()) {
- const float exitX = camera.GetViewport().x + Constants::SCREEN_WIDTH / 2.f - Textures["arrow.bmp"].GetWidth() / 2.f - exit->GetPosition().X + exit->GetCollider()->GetWidth() / 2.f;
- const float exitY = camera.GetViewport().y + 25.f - exit->GetPosition().Y + exit->GetCollider()->GetHeight() / 2.f;
- const double degrees = atan2(-exitX, exitY) * (180.f / M_PI);
- Textures["arrow.bmp"].RenderEx(Renderer, Constants::SCREEN_WIDTH / 2.f - Textures["arrow.bmp"].GetWidth() / 2.f, 25.f, degrees);
- }
- }
- if (ShowWinner)
- {
- Textures["Text_Winner"].Render(Renderer, Constants::SCREEN_WIDTH / 2.f - Textures["Text_Winner"].GetWidth() / 2.f, 25.f);
}
- //Textures["Text_Score"].Render(Renderer, Constants::SCREEN_WIDTH / 2.f - Textures["Text_Score"].GetWidth() / 2.f, Constants::SCREEN_HEIGHT - 10.f - Textures["Text_Score"].GetHeight());
if (devMode >= 1) {
- Textures["Text_Velocity"].Render(Renderer, 10.f, 25.f);
- Textures["Text_Gravity"].Render(Renderer, 10.f, 30.f + Textures["Text_Velocity"].GetHeight());
+ Textures["Text_Settings"].Render(Renderer, 10.f, 25.f);
}
if (devMode >= 2)
{
diff --git a/2dgk_zad3/2dgk_zad3/KGame.h b/2dgk_zad3/2dgk_zad3/KGame.h
index d54b48f..6a4d391 100644
--- a/2dgk_zad3/2dgk_zad3/KGame.h
+++ b/2dgk_zad3/2dgk_zad3/KGame.h
@@ -20,7 +20,6 @@ namespace KapitanGame {
public:
KGame();
~KGame();
- void Win(KPlayer player);
KGame(const KGame& other) = delete;
KGame(KGame&& other) noexcept = delete;
KGame& operator=(const KGame& other) = delete;
@@ -40,12 +39,9 @@ namespace KapitanGame {
uint32_t Time;
uint32_t PreviousTime;
SDL_FRect Map;
- bool CollisionEnabled = true;
- bool ShowWinner = false;
std::weak_ptr Exit;
KSettings Settings;
- bool VelocityTextureDirty;
- bool GravityTextureDirty;
+ bool SettingsTextTextureDirty = true;
bool LoadLevel();
bool LoadMedia();
@@ -53,7 +49,6 @@ namespace KapitanGame {
int LvlCounter = 1;
bool Playing = true;
uint32_t RestartTick = -1;
- short Scores[static_cast(KPlayer::Player2) + 1] = { 0,0 };
};
}
diff --git a/2dgk_zad3/2dgk_zad3/KInput.cpp b/2dgk_zad3/2dgk_zad3/KInput.cpp
index 0b5544b..a13b3c6 100644
--- a/2dgk_zad3/2dgk_zad3/KInput.cpp
+++ b/2dgk_zad3/2dgk_zad3/KInput.cpp
@@ -121,6 +121,7 @@ namespace KapitanGame {
}
}
break;
+ default: break;
}
}
diff --git a/2dgk_zad3/2dgk_zad3/KObject.cpp b/2dgk_zad3/2dgk_zad3/KObject.cpp
index d9cbed9..f11f666 100644
--- a/2dgk_zad3/2dgk_zad3/KObject.cpp
+++ b/2dgk_zad3/2dgk_zad3/KObject.cpp
@@ -1,5 +1,7 @@
#include "KObject.h"
+#include
+
#include "KCamera.h"
namespace KapitanGame
@@ -13,7 +15,7 @@ namespace KapitanGame
void KObject::Render(SDL_Renderer* renderer, const KCamera& camera) const
{
- Texture.Render(renderer, Position.X - Texture.GetWidth() / 2.f - camera.GetViewport().x, Position.Y - Texture.GetHeight() / 2.f - camera.GetViewport().y, nullptr, camera.GetScale());
+ Texture.Render(renderer, Position.X - Texture.GetWidth() / 2.f - camera.GetViewport().x, Position.Y - Texture.GetHeight() / 2.f - camera.GetViewport().y, nullptr, camera.GetScale()); // NOLINT(clang-diagnostic-implicit-int-float-conversion, bugprone-narrowing-conversions, cppcoreguidelines-narrowing-conversions)
}
KVector2D KObject::GetPosition() const
diff --git a/2dgk_zad3/2dgk_zad3/KObject.h b/2dgk_zad3/2dgk_zad3/KObject.h
index 14482fa..b663278 100644
--- a/2dgk_zad3/2dgk_zad3/KObject.h
+++ b/2dgk_zad3/2dgk_zad3/KObject.h
@@ -1,5 +1,6 @@
#pragma once
#include
+#include
#include "KTexture.h"
#include "KVector2d.h"
@@ -15,8 +16,8 @@ namespace KapitanGame
KObject(const KVector2D& position, const KTexture& texture);
virtual ~KObject() = default;
void Render(SDL_Renderer* renderer, const KCamera& camera) const;
- KVector2D GetPosition() const;
- virtual const KCollider* GetCollider() const = 0;
+ [[nodiscard]] KVector2D GetPosition() const;
+ [[nodiscard]] virtual const KCollider* GetCollider() const = 0;
const int Id;
static std::atomic IdCounter;
protected:
diff --git a/2dgk_zad3/2dgk_zad3/KPawn.cpp b/2dgk_zad3/2dgk_zad3/KPawn.cpp
index c8cc29a..72c2f3b 100644
--- a/2dgk_zad3/2dgk_zad3/KPawn.cpp
+++ b/2dgk_zad3/2dgk_zad3/KPawn.cpp
@@ -68,6 +68,10 @@ namespace KapitanGame
CanDoubleJump = true;
HasJumped = false;
}
+ if (separationVector.Y > 0)
+ {
+ Velocity.Y = 0;
+ }
}
void KPawn::AddXMovementInput(const float& input)
@@ -77,8 +81,8 @@ namespace KapitanGame
void KPawn::StopJump() {
if (!CanJump) {
- if (Velocity.Y < -Settings->ShortJumpVelocity())
- Velocity.Y = -Settings->ShortJumpVelocity();
+ if (Velocity.Y < -Settings->ShortJumpVelocity)
+ Velocity.Y = -Settings->ShortJumpVelocity;
}
}
@@ -90,12 +94,12 @@ namespace KapitanGame
if (CanJump) {
CanJump = false;
HasJumped = true;
- Velocity.Y = -Settings->JumpVelocity;
+ Velocity.Y = -Settings->JumpInitialVelocity;
}
else if (HasJumped && CanDoubleJump)
{
CanDoubleJump = false;
- Velocity.Y = -Settings->JumpVelocity;
+ Velocity.Y = -Settings->JumpInitialVelocity;
}
}
}
diff --git a/2dgk_zad3/2dgk_zad3/KPawn.h b/2dgk_zad3/2dgk_zad3/KPawn.h
index f255102..dbb3eca 100644
--- a/2dgk_zad3/2dgk_zad3/KPawn.h
+++ b/2dgk_zad3/2dgk_zad3/KPawn.h
@@ -1,5 +1,6 @@
#pragma once
#include
+#include
#include
#include "KObject.h"
@@ -7,7 +8,7 @@
namespace KapitanGame
{
- struct KSettings;
+ class KSettings;
class KPlayerController;
class KPawn : public KObject
diff --git a/2dgk_zad3/2dgk_zad3/KPlayerController.cpp b/2dgk_zad3/2dgk_zad3/KPlayerController.cpp
index e7010d7..06665ba 100644
--- a/2dgk_zad3/2dgk_zad3/KPlayerController.cpp
+++ b/2dgk_zad3/2dgk_zad3/KPlayerController.cpp
@@ -1,6 +1,5 @@
#include "KPlayerController.h"
-#include "KGame.h"
#include "KInput.h"
namespace KapitanGame {
diff --git a/2dgk_zad3/2dgk_zad3/KPlayerController.h b/2dgk_zad3/2dgk_zad3/KPlayerController.h
index 3b1913c..9b3b7ad 100644
--- a/2dgk_zad3/2dgk_zad3/KPlayerController.h
+++ b/2dgk_zad3/2dgk_zad3/KPlayerController.h
@@ -4,15 +4,13 @@
#include "KVector2d.h"
namespace KapitanGame {
- class KGame;
class KInput;
class KPlayerController : public std::enable_shared_from_this
{
public:
- KPlayerController(const KPlayer player, KGame* const game)
- : Player(player),
- Game(game)
+ explicit KPlayerController(const KPlayer player)
+ : Player(player)
{
}
@@ -21,7 +19,6 @@ namespace KapitanGame {
void StartJump();
void StopJump();
void Update(float deltaTime);
- void NotifyWin() const;
void Possess(KPawn* pawn);
void UnPossess();
const KPlayer& GetPlayer() const;
@@ -29,7 +26,6 @@ namespace KapitanGame {
KVector2D Input{ 0.f, 0.f };
const KPlayer Player;
KPawn* Pawn{};
- KGame* Game;
bool InputStartJump{};
bool InputStopJump{};
};
diff --git a/2dgk_zad3/2dgk_zad3/KRect.h b/2dgk_zad3/2dgk_zad3/KRect.h
index 66cd3ca..825aa05 100644
--- a/2dgk_zad3/2dgk_zad3/KRect.h
+++ b/2dgk_zad3/2dgk_zad3/KRect.h
@@ -15,20 +15,21 @@ namespace KapitanGame {
Height(height)
{
}
- float GetWidth() const override;
- float GetHeight() const override;
+
+ [[nodiscard]] float GetWidth() const override;
+ [[nodiscard]] float GetHeight() const override;
static KVector2D GetSeparationVector(float left, float right, float top, float bottom);
bool IsCollision(const KCollider* other) const override;
KVector2D GetSeparationVector(const KCollider* other) const override;
- KVector2D GetSeparationVector(const SDL_FRect& map) const override;
+ [[nodiscard]] KVector2D GetSeparationVector(const SDL_FRect& map) const override;
private:
KVector2D GetSeparationVector(const KCircle* other) const;
KVector2D GetSeparationVector(const KRect* other) const;
bool IsCollision(const KCircle* other) const;
- float GetLeft() const;
- float GetRight() const;
- float GetBottom() const;
- float GetTop() const;
+ [[nodiscard]] float GetLeft() const;
+ [[nodiscard]] float GetRight() const;
+ [[nodiscard]] float GetBottom() const;
+ [[nodiscard]] float GetTop() const;
bool IsCollision(const KRect* other) const;
float Width;
float Height;
diff --git a/2dgk_zad3/2dgk_zad3/KSettings.cpp b/2dgk_zad3/2dgk_zad3/KSettings.cpp
index 1597b37..89deca4 100644
--- a/2dgk_zad3/2dgk_zad3/KSettings.cpp
+++ b/2dgk_zad3/2dgk_zad3/KSettings.cpp
@@ -1,9 +1,98 @@
#include "KSettings.h"
+#include
+#include
+#include "Constants.h"
+
namespace KapitanGame
{
- float KSettings::ShortJumpVelocity() const
+ KSettings::KSettings(const float maxJumpHeight, const float horizontalDistanceToMaxJumpHeight) : MaxJumpHeightValue(maxJumpHeight),
+ HorizontalDistanceToMaxJumpHeightValue(horizontalDistanceToMaxJumpHeight),
+ TimeToMaxHeightValue(NAN),
+ GravityValue(NAN),
+ JumpInitialVelocityValue(NAN),
+ ShortJumpVelocityValue(NAN),
+ CollisionEnabledValue(true),
+ Dirty(true),
+ MaxJumpHeight(this, &KSettings::GetMaxJumpHeight, &KSettings::SetMaxJumpHeight),
+ HorizontalDistanceToMaxJumpHeight(this, &KSettings::GetHorizontalDistanceToMaxJumpHeight, &KSettings::SetHorizontalDistanceToMaxJumpHeight),
+ TimeToMaxHeight(this, &KSettings::GetTimeToMaxHeight),
+ Gravity(this, &KSettings::GetGravity),
+ JumpInitialVelocity(this, &KSettings::GetJumpInitialVelocity),
+ ShortJumpVelocity(this, &KSettings::GetShortJumpVelocity),
+ CollisionEnabled(this, &KSettings::GetCollisionEnabled, &KSettings::SetCollisionEnabled)
{
- return JumpVelocity / 2.f;
+ }
+
+ void KSettings::SetCollisionEnabled(const bool value)
+ {
+ if (value != CollisionEnabledValue)
+ CollisionEnabledValue = value;
+ }
+
+ void KSettings::SetMaxJumpHeight(const float h)
+ {
+ if (h <= 0.f && MaxJumpHeightValue <= 0.f) return;
+ if (MaxJumpHeightValue != h) { // NOLINT(clang-diagnostic-float-equal)
+ MaxJumpHeightValue = std::max(h, 0.f);
+ Dirty = true;
+ }
+ }
+
+ void KSettings::SetHorizontalDistanceToMaxJumpHeight(const float xn)
+ {
+ if (xn <= 0.f && HorizontalDistanceToMaxJumpHeightValue <= 0.f) return;
+ if (HorizontalDistanceToMaxJumpHeightValue != xn) { // NOLINT(clang-diagnostic-float-equal)
+ HorizontalDistanceToMaxJumpHeightValue = std::max(xn, 0.f);
+ Dirty = true;
+ }
+ }
+
+ // ReSharper disable once CppMemberFunctionMayBeConst
+ bool KSettings::GetCollisionEnabled()
+ {
+ return CollisionEnabledValue;
+ }
+
+ float KSettings::GetTimeToMaxHeight()
+ {
+ if (Dirty)
+ TimeToMaxHeightValue = HorizontalDistanceToMaxJumpHeightValue / Constants::SPEED;
+ return TimeToMaxHeightValue;
+ }
+
+ float KSettings::GetGravity()
+ {
+ if (Dirty) {
+ const auto timeToMaxHeight = GetTimeToMaxHeight();
+ GravityValue = 2.0f * MaxJumpHeightValue / (timeToMaxHeight * timeToMaxHeight);
+ }
+ return GravityValue;
+ }
+
+ float KSettings::GetJumpInitialVelocity()
+ {
+ if (Dirty)
+ JumpInitialVelocityValue = 2.0f * MaxJumpHeightValue / GetTimeToMaxHeight();
+ return JumpInitialVelocityValue;
+ }
+
+ float KSettings::GetShortJumpVelocity()
+ {
+ if (Dirty)
+ ShortJumpVelocityValue = GetJumpInitialVelocity() / 2.f;
+ return ShortJumpVelocityValue;
+ }
+
+ // ReSharper disable once CppMemberFunctionMayBeConst
+ float KSettings::GetMaxJumpHeight()
+ {
+ return MaxJumpHeightValue;
+ }
+
+ // ReSharper disable once CppMemberFunctionMayBeConst
+ float KSettings::GetHorizontalDistanceToMaxJumpHeight()
+ {
+ return HorizontalDistanceToMaxJumpHeightValue;
}
}
diff --git a/2dgk_zad3/2dgk_zad3/KSettings.h b/2dgk_zad3/2dgk_zad3/KSettings.h
index 31b189d..2c160ac 100644
--- a/2dgk_zad3/2dgk_zad3/KSettings.h
+++ b/2dgk_zad3/2dgk_zad3/KSettings.h
@@ -1,14 +1,37 @@
#pragma once
-#include "Constants.h"
+#include "Property.h"
namespace KapitanGame
{
- struct KSettings
+ class KSettings final
{
- float Gravity = Constants::GRAVITY;
- float JumpVelocity = Constants::JUMP_SPEED;
+ float MaxJumpHeightValue;
+ float HorizontalDistanceToMaxJumpHeightValue;
+ float TimeToMaxHeightValue;
+ float GravityValue;
+ float JumpInitialVelocityValue;
+ float ShortJumpVelocityValue;
+ bool CollisionEnabledValue;
+ bool Dirty;
- [[nodiscard]] float ShortJumpVelocity() const;
+ public:
+
+ KSettings(float maxJumpHeight, float horizontalDistanceToMaxJumpHeight);
+ const Property MaxJumpHeight, HorizontalDistanceToMaxJumpHeight;
+ const ReadOnlyProperty TimeToMaxHeight, Gravity, JumpInitialVelocity, ShortJumpVelocity;
+ const Property CollisionEnabled;
+
+ private:
+ void SetCollisionEnabled(bool value);
+ void SetMaxJumpHeight(float h);
+ void SetHorizontalDistanceToMaxJumpHeight(float xn);
+ bool GetCollisionEnabled();
+ float GetTimeToMaxHeight();
+ float GetGravity();
+ float GetJumpInitialVelocity();
+ float GetShortJumpVelocity();
+ float GetMaxJumpHeight();
+ float GetHorizontalDistanceToMaxJumpHeight();
};
}
diff --git a/2dgk_zad3/2dgk_zad3/KTexture.cpp b/2dgk_zad3/2dgk_zad3/KTexture.cpp
index ac7798c..244cccf 100644
--- a/2dgk_zad3/2dgk_zad3/KTexture.cpp
+++ b/2dgk_zad3/2dgk_zad3/KTexture.cpp
@@ -1,5 +1,7 @@
#include "KTexture.h"
+#include
+
namespace KapitanGame {
KTexture::KTexture() : Texture(nullptr), Width(0), Height(0)
{
@@ -142,4 +144,4 @@ namespace KapitanGame {
{
return Height;
}
-}
\ No newline at end of file
+}
diff --git a/2dgk_zad3/2dgk_zad3/Property.h b/2dgk_zad3/2dgk_zad3/Property.h
new file mode 100644
index 0000000..f4c6a5e
--- /dev/null
+++ b/2dgk_zad3/2dgk_zad3/Property.h
@@ -0,0 +1,54 @@
+#pragma once
+namespace KapitanGame
+{
+ template
+ class ReadOnlyProperty {
+ protected:
+ C* Owner;
+ T(C::* Getter)();
+ public:
+ ReadOnlyProperty() : Owner(), Getter() {}
+ ReadOnlyProperty(C* owner, T(C::* getter)()) : Owner(owner), Getter(getter) {}
+
+ [[nodiscard]] T Get() const {
+ return (Owner->*Getter)();
+ }
+
+ // ReSharper disable once CppNonExplicitConversionOperator
+ operator T() const {
+ return Get();
+ }
+ };
+
+ template
+ class Property : public ReadOnlyProperty {
+ void(C::* Setter)(T);
+ public:
+ Property() : ReadOnlyProperty(), Setter() {}
+ Property(C* owner, T(C::* getter)(), void(C::* setter)(T)) : ReadOnlyProperty(owner,getter), Setter(setter) {}
+ void Set(T value) const {
+ (this->Owner->*Setter)(value);
+ }
+
+ const Property& operator = (T value) const { // NOLINT(misc-unconventional-assign-operator)
+ Set(value);
+ return *this;
+ }
+ const Property& operator -= (T value) const { // NOLINT(misc-unconventional-assign-operator)
+ Set(this->Get() - value);
+ return *this;
+ }
+ const Property& operator += (T value) const { // NOLINT(misc-unconventional-assign-operator)
+ Set(this->Get() + value);
+ return *this;
+ }
+ const Property& operator *= (T value) const { // NOLINT(misc-unconventional-assign-operator)
+ Set(this->Get() * value);
+ return *this;
+ }
+ const Property& operator /= (T value) const { // NOLINT(misc-unconventional-assign-operator)
+ Set(this->Get() / value);
+ return *this;
+ }
+ };
+}