Skip to content
Open

GO #1

Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 9 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
cmake-build-debug/
CMakeCache.txt
cmake_install.cmake
Makefile
TanksGame

*.o

/build/
8 changes: 8 additions & 0 deletions .idea/.gitignore

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions .idea/.name

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 2 additions & 0 deletions .idea/TankiGame.iml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

345 changes: 345 additions & 0 deletions .idea/editor.xml

Large diffs are not rendered by default.

7 changes: 7 additions & 0 deletions .idea/misc.xml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

6 changes: 6 additions & 0 deletions .idea/vcs.xml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

4 changes: 4 additions & 0 deletions .vscode/settings.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
{
"C_Cpp.default.compileCommands": "${workspaceFolder}/cmake-build-debug/compile_commands.json",
"C_Cpp.default.configurationProvider": "ms-vscode.cmake-tools"
}
41 changes: 41 additions & 0 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
cmake_minimum_required(VERSION 3.16)
project(TanksGame LANGUAGES CXX)

set(CMAKE_CXX_STANDARD 20)
set(CMAKE_CXX_STANDARD_REQUIRED ON)

set(CMAKE_AUTOMOC ON)
set(CMAKE_AUTORCC ON)
set(CMAKE_AUTOUIC ON)

find_package(Qt5 REQUIRED COMPONENTS Core Widgets Multimedia)

add_executable(TanksGame
src/main.cpp
src/GameScene.cpp
src/GameModel.cpp
src/InputController.cpp
include/GameScene.h
include/GameModel.h
include/InputController.h
src/Bonus.cpp
src/Tank.cpp
src/TankView.cpp
src/EnemyTank.cpp
src/KamikazeEnemy.cpp
src/LightEnemy.cpp
src/HeavyEnemy.cpp
src/TwinShooterEnemy.cpp
src/Wall.cpp
src/BrickWall.cpp
src/Bullet.cpp
include/TankView.h
)

target_link_libraries(TanksGame PRIVATE
Qt5::Core
Qt5::Widgets
)

target_link_libraries(TanksGame PRIVATE Qt5::Multimedia)
target_include_directories(TanksGame PUBLIC ${CMAKE_SOURCE_DIR}/include)
24 changes: 24 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
@@ -1 +1,25 @@
# Tanks

игра «ТанкиNSU», написанная с использованием Qt5

## Структура проекта
- `include/` — все заголовочные файлы (.h)
- `src/` — реализации (.cpp)
- `CMakeLists.txt` — конфигурация сборки CMake


## Краткая инструкция по сборке
Требования:
- C++ компилятор с поддержкой C++20
- CMake >= 3.16
- Qt5

Сборка из корня проекта :

```bash
mkdir -p cmake-build-debug
cd cmake-build-debug
cmake ..
cmake --build . --config Debug -- -j 4
```

31 changes: 31 additions & 0 deletions include/Bonus.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
#pragma once

#include <QGraphicsEllipseItem>

class GameScene;

class Bonus : public QGraphicsEllipseItem {
public:
explicit Bonus(qreal x, qreal y, qreal w = 16.0, qreal h = 16.0);
~Bonus() override = default;

virtual void Apply(GameScene* scene) = 0;
};

class HealthBonus : public Bonus {
public:
explicit HealthBonus(qreal x, qreal y);
void Apply(GameScene* scene) override;
};

class MineBonus : public Bonus {
public:
explicit MineBonus(qreal x, qreal y);
void Apply(GameScene* scene) override;
};

class ScoreBonus : public Bonus {
public:
explicit ScoreBonus(qreal x, qreal y);
void Apply(GameScene* scene) override;
};
9 changes: 9 additions & 0 deletions include/BrickWall.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
#pragma once
#include <QGraphicsPixmapItem>

class BrickWall : public QGraphicsPixmapItem {
public:
BrickWall(qreal x, qreal y);
QRectF GetRect() const;
static constexpr int kDurability = 3;
};
26 changes: 26 additions & 0 deletions include/Bullet.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
#pragma once

#include <QGraphicsPixmapItem>

enum class Direction;
enum class BulletOwner {
Player,
Enemy,
};

class Bullet final : public QGraphicsPixmapItem {
public:
explicit Bullet(qreal x, qreal y, Direction direction, BulletOwner owner);

void Move();
Direction GetDirection() const;
BulletOwner GetOwner() const;
QRectF GetBoundingRect() const;

private:
Direction m_direction;
BulletOwner m_owner;

static constexpr qreal kSpeed = 5.0;
static constexpr qreal kSize = 6.0;
};
44 changes: 44 additions & 0 deletions include/CloneFactory.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
#pragma once

#include <map>
#include <memory>
#include <functional>
#include <typeindex>
#include "Factory.hpp"

template <
class AbstractProduct,
class ProductCreator = std::function<std::unique_ptr<AbstractProduct>(const AbstractProduct*)>,
template<typename, class> class FactoryErrorPolicy = DefaultFactoryError
>
class CloneFactory {
public:
using CreatorType = ProductCreator;
using TypeKey = std::type_index;

bool Register(const std::type_info& ti, CreatorType creator) {
TypeKey key(ti);
auto res = associations_.emplace(key, std::move(creator));
return res.second;
}

bool Unregister(const std::type_info& ti) {
TypeKey key(ti);
return associations_.erase(key) > 0;
}

std::unique_ptr<AbstractProduct> CreateObject(const AbstractProduct* model) {
if (!model) {
return FactoryErrorPolicy<TypeKey, AbstractProduct>::OnUnknownType(TypeKey(typeid(void)));
}
TypeKey key(typeid(*model));
auto it = associations_.find(key);
if (it != associations_.end()) {
return (it->second)(model);
}
return FactoryErrorPolicy<TypeKey, AbstractProduct>::OnUnknownType(key);
}

private:
std::map<TypeKey, CreatorType> associations_;
};
53 changes: 53 additions & 0 deletions include/EnemyTank.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
#pragma once
#include <QGraphicsPixmapItem>
#include <QList>
#include <memory>
#include <vector>

class QPainter;
#include "Tank.h"

class Bullet;


class EnemyTank : public QGraphicsPixmapItem {
public:
explicit EnemyTank(qreal x, qreal y);

virtual void Update();
virtual QRectF GetFutureRect(Direction direction) const;
Direction GetDirection() const { return m_direction; }

void SetDirection(Direction dir);
void ResetMoveTimer(int frames) { moveCooldown = frames; }
void ResetFireTimer(int frames) { fireCooldown = frames; }
int GetMoveCooldown() const { return moveCooldown; }
int GetFireCooldown() const { return fireCooldown; }

virtual qreal GetSpeed() const { return Speed; }
virtual qreal GetWidth() const { return Width; }
virtual qreal GetHeight() const { return Height; }


int GetHP() const { return hp; }
void TakeDamage(int dmg);
bool IsDead() const { return hp <= 0; }


virtual std::vector<std::unique_ptr<Bullet>> Fire(Direction dir);

private:
static constexpr qreal Speed = 30.0;
static constexpr qreal Width = 32.0;
static constexpr qreal Height = 32.0;

protected:
virtual void UpdatePixmap();
void DrawGun(QPainter& painter, int center, int gunLength) const;

Direction m_direction = Direction::Down;
int moveCooldown = 0;
int fireCooldown = 0;
int hp = 1;
};

57 changes: 57 additions & 0 deletions include/Factory.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
#pragma once

#include <functional>
#include <map>
#include <memory>
#include <exception>

template <class IdentifierType, class ProductType>
class DefaultFactoryError {
public:
class Exception : public std::exception {
public:
Exception(const IdentifierType& unknownId) : unknownId_(unknownId) {}
virtual const char* what() const noexcept override {
return "unknown type ident";
}
const IdentifierType& GetId() const { return unknownId_; }
private:
IdentifierType unknownId_;
};

protected:
static std::unique_ptr<ProductType> OnUnknownType(const IdentifierType& id) {
throw Exception(id);
}
};

template <
class AbstractProduct,
class IdentifierType,
class ProductCreator = std::function<std::unique_ptr<AbstractProduct>()>,
template <typename, class> class FactoryErrorPolicy = DefaultFactoryError
>
class Factory : public FactoryErrorPolicy<IdentifierType, AbstractProduct> {
public:
using CreatorType = ProductCreator;

bool Register(const IdentifierType& id, CreatorType creator) {
auto res = associations_.emplace(id, std::move(creator));
return res.second;
}

bool Unregister(const IdentifierType& id) {
return associations_.erase(id) > 0;
}

std::unique_ptr<AbstractProduct> CreateObject(const IdentifierType& id) {
auto it = associations_.find(id);
if (it != associations_.end()) {
return (it->second)();
}
return FactoryErrorPolicy<IdentifierType, AbstractProduct>::OnUnknownType(id);
}

private:
std::map<IdentifierType, CreatorType> associations_;
};
Loading