diff --git a/CMakeLists.txt b/CMakeLists.txt index 6b7708e..f1bc459 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -102,7 +102,7 @@ add_executable(shooter engine/animation/AAttractToPoint.h engine/animation/ARotateRelativePoint.h engine/animation/ARotateLeft.h - engine/animation/Interpolation.cpp engine/animation/Animations.h) + engine/animation/Interpolation.cpp engine/animation/Animations.h engine/animation/AShowCreation.h) if(APPLE OR UNIX) include_directories(/usr/local/include) diff --git a/Shooter.cpp b/Shooter.cpp index 86dfb88..e5c481c 100644 --- a/Shooter.cpp +++ b/Shooter.cpp @@ -277,16 +277,24 @@ void Shooter::spawnPlayer(sf::Uint16 id) { world->body(ObjectNameTag(name + "_foot_2"))->setColor(ShooterConsts::DARK_COLORS[colorFootNum]); changeEnemyWeapon("gun", id); + + newPlayer->scale(Vec3D(0.01, 0.01, 0.01)); + Timeline::addAnimation(AnimationListTag(name + "_creation"), newPlayer, Vec3D(100, 100, 100)); } void Shooter::removePlayer(sf::Uint16 id) { std::string name = "Enemy_" + std::to_string(id); - world->removeBody(ObjectNameTag(name)); - world->removeBody(ObjectNameTag(name + "_head")); - world->removeBody(ObjectNameTag(name + "_weapon")); - world->removeBody(ObjectNameTag(name + "_foot_1")); - world->removeBody(ObjectNameTag(name + "_foot_2")); + auto playerToRemove = world->body(ObjectNameTag(name)); + + Timeline::addAnimation(AnimationListTag(name + "_remove"), playerToRemove, Vec3D(0.01, 0.01, 0.01)); + Timeline::addAnimation(AnimationListTag(name + "_remove"), [this, name](){ + world->removeBody(ObjectNameTag(name)); + world->removeBody(ObjectNameTag(name + "_head")); + world->removeBody(ObjectNameTag(name + "_weapon")); + world->removeBody(ObjectNameTag(name + "_foot_1")); + world->removeBody(ObjectNameTag(name + "_foot_2")); + }); } void Shooter::addFireTrace(const Vec3D &from, const Vec3D &to) { @@ -311,12 +319,16 @@ void Shooter::addBonus(const string &bonusName, const Vec3D &position) { ObjectNameTag nameTag(bonusName); world->addBody(std::make_shared(ObjectNameTag(bonusName), "obj/" + name + ".obj", Vec3D{3, 3, 3})); - world->body(ObjectNameTag(bonusName))->translateToPoint(position); - world->body(ObjectNameTag(bonusName))->setCollider(false); - world->body(ObjectNameTag(bonusName))->setTrigger(true); + + auto bonus = world->body(ObjectNameTag(bonusName)); + + bonus->translateToPoint(position); + bonus->setCollider(false); + bonus->setTrigger(true); + bonus->scale(Vec3D(0.01, 0.01, 0.01)); + Timeline::addAnimation(AnimationListTag(bonusName + "_creation"), bonus, Vec3D(100, 100, 100)); Timeline::addAnimation(AnimationListTag(bonusName + "_rotation"), - world->body(ObjectNameTag(bonusName)), - Vec3D{0, 2 * Consts::PI, 0}, 4, + bonus, Vec3D{0, 2 * Consts::PI, 0}, 4, Animation::LoopOut::Continue, Animation::InterpolationType::Linear); } @@ -338,6 +350,7 @@ void Shooter::changeEnemyWeapon(const std::string &weaponName, sf::Uint16 enemyI ObjectNameTag weaponTag("Enemy_" + std::to_string(enemyId) + "_weapon"); auto head = world->body(ObjectNameTag("Enemy_" + std::to_string(enemyId) + "_head")); auto enemy = world->body(ObjectNameTag("Enemy_" + std::to_string(enemyId))); + auto weapon = world->body(weaponTag); // remove old weapon: world->removeBody(weaponTag); diff --git a/engine/Mesh.cpp b/engine/Mesh.cpp index 6721b42..47b080b 100644 --- a/engine/Mesh.cpp +++ b/engine/Mesh.cpp @@ -91,19 +91,18 @@ Mesh::LineTo(ObjectNameTag nameTag, const Vec3D &from, const Vec3D &to, double l return line; } -void Mesh::setTriangles(const vector &t) { - _tris.clear(); - for (auto &tri : t) { - _tris.push_back(tri); - } -} - void Mesh::setTriangles(vector&& t) { _tris = std::move(t); } Mesh::~Mesh() { delete[] _geometry; + _geometry = nullptr; +} + +void Mesh::glFreeFloatArray() { + delete[] _geometry; + _geometry = nullptr; } GLfloat *Mesh::glFloatArray() const { diff --git a/engine/Mesh.h b/engine/Mesh.h index 0d37dda..dc81624 100644 --- a/engine/Mesh.h +++ b/engine/Mesh.h @@ -38,8 +38,6 @@ public: [[nodiscard]] std::vector const &triangles() const { return _tris; } - void setTriangles(const std::vector &t); - void setTriangles(std::vector&& t); [[nodiscard]] size_t size() const { return _tris.size() * 3; } @@ -59,6 +57,7 @@ public: // OpenGL functions GLfloat *glFloatArray() const; + void glFreeFloatArray(); }; #endif //INC_3DZAVR_MESH_H diff --git a/engine/Object.h b/engine/Object.h index ed6897c..abadd6f 100644 --- a/engine/Object.h +++ b/engine/Object.h @@ -36,11 +36,7 @@ private: const ObjectNameTag _nameTag; Matrix4x4 _transformMatrix = Matrix4x4::Identity(); - - std::map> _attachedObjects; - Vec3D _position{0, 0, 0}; - /* * Take into account when you rotate body, * you change '_angle' & '_angleLeftUpLookAt' only for this particular body, @@ -49,67 +45,52 @@ private: */ Vec3D _angle{0, 0, 0}; Vec3D _angleLeftUpLookAt{0, 0, 0}; + + std::map> _attachedObjects; + public: explicit Object(ObjectNameTag nameTag) : _nameTag(std::move(nameTag)) {}; - Object(const Object &object) = default; + Object(const Object &object) : _nameTag(object._nameTag), + _transformMatrix(object._transformMatrix), + _position(object._position), + _angle(object._angle), + _angleLeftUpLookAt(object._angleLeftUpLookAt) {}; // TODO: implement rotations using quaternions (?) void transform(const Matrix4x4 &t); - void transformRelativePoint(const Vec3D &point, const Matrix4x4 &transform); - void translate(const Vec3D &dv); - void translateToPoint(const Vec3D &point); - void attractToPoint(const Vec3D &point, double value); - void scale(const Vec3D &s); - void rotate(const Vec3D &r); - void rotate(const Vec3D &v, double rv); - void rotateToAngle(const Vec3D &v); - void rotateRelativePoint(const Vec3D &s, const Vec3D &r); - void rotateRelativePoint(const Vec3D &s, const Vec3D &v, double r); - void rotateLeft(double rl); - void rotateUp(double ru); - void rotateLookAt(double rlAt); [[nodiscard]] Vec3D left() const { return _transformMatrix.x(); } - [[nodiscard]] Vec3D up() const { return _transformMatrix.y(); } - [[nodiscard]] Vec3D lookAt() const { return _transformMatrix.z(); } - [[nodiscard]] Vec3D position() const { return _position; } - [[nodiscard]] Vec3D angle() const { return _angle; } - [[nodiscard]] Vec3D angleLeftUpLookAt() const { return _angleLeftUpLookAt; } void attach(std::shared_ptr object); - void unattach(const ObjectNameTag &tag); - std::shared_ptr attached(const ObjectNameTag &tag); [[nodiscard]] ObjectNameTag name() const { return _nameTag; } [[nodiscard]] Matrix4x4 model() const { return Matrix4x4::Translation(_position) * _transformMatrix; } - [[nodiscard]] Matrix4x4 invModel() const { return Matrix4x4::View(left(), up(), lookAt(), position()); } // OpenGL function [[nodiscard]] GLfloat *glModel() const; - [[nodiscard]] GLfloat *glInvModel() const; virtual ~Object(); diff --git a/engine/animation/AScale.h b/engine/animation/AScale.h index 2d822ea..f9b3643 100644 --- a/engine/animation/AScale.h +++ b/engine/animation/AScale.h @@ -6,12 +6,13 @@ #define ENGINE_ASCALE_H #include "Animation.h" -#include "../physics/RigidBody.h" +#include "../Object.h" class AScale final : public Animation { private: - const std::weak_ptr _object; + const std::weak_ptr _object; const Vec3D _scalingValue; + Vec3D _prevScaleFactor{1, 1, 1}; void update() override { auto obj = _object.lock(); @@ -20,19 +21,15 @@ private: stop(); return; } - - std::vector newTriangles; - newTriangles.reserve(obj->triangles().size()); - for (auto &t : obj->triangles()) { - newTriangles.emplace_back(t * Matrix4x4::Scale(Vec3D{1, 1, 1} + - (_scalingValue - Vec3D{1, 1, 1}) * progress()) - ); - } - obj->setTriangles(std::move(newTriangles)); + // invert scale + obj->scale(Vec3D(1.0/_prevScaleFactor.x(), 1.0/_prevScaleFactor.y(), 1.0/_prevScaleFactor.z())); + Vec3D scaleFactor = Vec3D{1, 1, 1} + (_scalingValue - Vec3D{1, 1, 1}) * progress(); + obj->scale(scaleFactor); + _prevScaleFactor = scaleFactor; } public: - AScale(std::weak_ptr object, const Vec3D &s, double duration = 1, LoopOut looped = LoopOut::None, + AScale(std::weak_ptr object, const Vec3D &s, double duration = 1, LoopOut looped = LoopOut::None, InterpolationType interpolationType = InterpolationType::Bezier) : Animation(duration, looped, interpolationType), _object(object), _scalingValue(s) { diff --git a/engine/animation/AShowCreation.h b/engine/animation/AShowCreation.h new file mode 100644 index 0000000..e76008e --- /dev/null +++ b/engine/animation/AShowCreation.h @@ -0,0 +1,40 @@ +// +// Created by Иван Ильин on 10.11.2021. +// + +#ifndef SHOOTER_ASHOWCREATION_H +#define SHOOTER_ASHOWCREATION_H + +#include "Animation.h" +#include "../Mesh.h" + +class AShowCreation final : public Animation { +private: + const std::weak_ptr _mesh; + const std::vector _triangles; + + void update() override { + auto mesh = _mesh.lock(); + + if (mesh == nullptr) { + stop(); + return; + } + + std::vector newTriangles; + newTriangles.reserve(_triangles.size()); + for(auto &t : _triangles) { + newTriangles.emplace_back(t[0], t[1], t[1] + (t[2] - t[1]) * progress(), t.color()); + } + mesh->setTriangles(std::move(newTriangles)); + mesh->glFreeFloatArray(); + } + +public: + AShowCreation(std::weak_ptr mesh, double duration = 1, LoopOut looped = LoopOut::None, + InterpolationType interpolationType = InterpolationType::Bezier) : Animation(duration, looped, + interpolationType), + _mesh(mesh), _triangles(mesh.lock()->triangles()) {} +}; + +#endif //SHOOTER_ASHOWCREATION_H diff --git a/engine/animation/Animations.h b/engine/animation/Animations.h index 5d618e4..f5c6a38 100644 --- a/engine/animation/Animations.h +++ b/engine/animation/Animations.h @@ -17,5 +17,6 @@ #include "ATranslate.h" #include "ATranslateToPoint.h" #include "AWait.h" +#include "AShowCreation.h" #endif //SHOOTER_ANIMATIONS_H diff --git a/engine/gui/Button.h b/engine/gui/Button.h index cda8e7e..f6be041 100644 --- a/engine/gui/Button.h +++ b/engine/gui/Button.h @@ -5,6 +5,8 @@ #ifndef ENGINE_BUTTON_H #define ENGINE_BUTTON_H +#include + #include struct tPos final { diff --git a/shooter.vcxproj b/shooter.vcxproj index 0e5898f..e8824f8 100644 --- a/shooter.vcxproj +++ b/shooter.vcxproj @@ -212,6 +212,7 @@ + diff --git a/shooter.vcxproj.filters b/shooter.vcxproj.filters index da25cbf..2714ace 100644 --- a/shooter.vcxproj.filters +++ b/shooter.vcxproj.filters @@ -260,6 +260,9 @@ Файлы заголовков\engine\animation + + Файлы заголовков\engine\animation + Файлы заголовков\engine\network