252 lines
6.7 KiB
C++
252 lines
6.7 KiB
C++
#pragma once
|
|
|
|
#include <unordered_set>
|
|
|
|
#include "render/canvas.hpp"
|
|
#include "resource/character.hpp"
|
|
#include "util/measurement.hpp"
|
|
|
|
namespace game
|
|
{
|
|
enum EntityType
|
|
{
|
|
ACTOR,
|
|
CHARACTER,
|
|
CURSOR,
|
|
AUTOCURSOR,
|
|
ITEM,
|
|
PARTICLE
|
|
};
|
|
|
|
class Entity
|
|
{
|
|
public:
|
|
using Anm2 = resource::xml::Anm2;
|
|
using FrameOptional = Anm2::FrameOptional;
|
|
|
|
static constexpr auto UPDATE_RATE = 60.0f;
|
|
static constexpr auto DIGESTION_MAX = 100.0f;
|
|
|
|
enum Mode
|
|
{
|
|
PLAY,
|
|
PLAY_FORCE,
|
|
SET,
|
|
};
|
|
|
|
enum State
|
|
{
|
|
STOPPED,
|
|
PLAYING
|
|
};
|
|
|
|
enum class Transition
|
|
{
|
|
NOW,
|
|
AFTER_CURRENT,
|
|
IF_IDLE
|
|
};
|
|
|
|
enum class Interrupt
|
|
{
|
|
IF_ALLOWED,
|
|
ALWAYS,
|
|
NEVER
|
|
};
|
|
|
|
enum CursorState
|
|
{
|
|
DEFAULT,
|
|
HOVER,
|
|
ACTION
|
|
};
|
|
|
|
enum SpritesheetType
|
|
{
|
|
NORMAL,
|
|
ALTERNATE
|
|
};
|
|
|
|
class Override
|
|
{
|
|
public:
|
|
enum Mode
|
|
{
|
|
SET,
|
|
ADD
|
|
};
|
|
|
|
using Function = void (*)(Override&);
|
|
|
|
int id{-1};
|
|
Anm2::Type type{Anm2::NONE};
|
|
Mode mode{SET};
|
|
FrameOptional frame{};
|
|
std::optional<float> time{};
|
|
Function function{nullptr};
|
|
|
|
FrameOptional frameBase{};
|
|
std::optional<float> timeStart{};
|
|
|
|
float cycles{};
|
|
|
|
Override() = default;
|
|
Override(int, Anm2::Type, Mode, FrameOptional = {}, std::optional<float> = std::nullopt, Function = nullptr,
|
|
float = 0);
|
|
};
|
|
|
|
struct AnimationRequest
|
|
{
|
|
std::string animation{};
|
|
std::string appendID{};
|
|
int index{-1};
|
|
float time{};
|
|
float speedMultiplier{1.0f};
|
|
Mode mode{PLAY};
|
|
Transition transition{Transition::NOW};
|
|
Interrupt interrupt{Interrupt::IF_ALLOWED};
|
|
|
|
inline bool empty() const { return animation.empty() && index == -1; };
|
|
};
|
|
|
|
EntityType entityType{ACTOR};
|
|
|
|
int fps{30};
|
|
std::map<int, Anm2::Spritesheet> spritesheets{};
|
|
std::map<int, Anm2::Layer> layers{};
|
|
std::map<int, Anm2::Null> nulls{};
|
|
std::map<int, Anm2::Event> events{};
|
|
std::map<int, Anm2::Sound> sounds{};
|
|
std::unordered_map<std::string, int> layerMap{};
|
|
std::unordered_map<std::string, int> nullMap{};
|
|
std::unordered_map<std::string, int> eventMap{};
|
|
std::string defaultAnimation{};
|
|
int defaultAnimationID{-1};
|
|
std::vector<Anm2::Animation> animations{};
|
|
std::unordered_map<std::string, int> animationMap{};
|
|
std::unordered_map<int, std::string> animationMapReverse{};
|
|
std::unordered_set<std::string> invalidAnimations{};
|
|
std::string path{};
|
|
bool isValid{};
|
|
Anm2::Flags flags{};
|
|
|
|
State state{STOPPED};
|
|
Mode mode{PLAY};
|
|
glm::vec2 position{};
|
|
float time{};
|
|
bool isShowLayers{};
|
|
bool isShowNulls{};
|
|
bool isVisible{true};
|
|
int animationIndex{-1};
|
|
int playedEventID{-1};
|
|
float startTime{};
|
|
float speedMultiplier{};
|
|
AnimationRequest pendingAnimation{};
|
|
AnimationRequest currentAnimation{};
|
|
AnimationRequest nextAnimation{};
|
|
std::unordered_set<int> playedTriggers{};
|
|
std::vector<Override> overrides{};
|
|
|
|
resource::xml::Character data;
|
|
float weight{};
|
|
int stage{0};
|
|
float calories{};
|
|
float capacity{};
|
|
float digestionProgress{};
|
|
float digestionRate{0.05f};
|
|
int digestionTimer{};
|
|
bool isDigesting{};
|
|
bool isJustDigested{};
|
|
float totalCaloriesConsumed{};
|
|
int totalItemsSpawned{};
|
|
int totalItemsConsumed{};
|
|
float totalPlaytimeSeconds{};
|
|
int talkOverrideID{};
|
|
float talkTimer{};
|
|
bool isTalking{};
|
|
std::vector<int> animationTalkDurations{};
|
|
int blinkOverrideID{};
|
|
float blinkTimer{};
|
|
bool isBlinking{};
|
|
std::vector<int> animationBlinkDurations{};
|
|
bool isStageUp{};
|
|
bool isStageUpDuring{};
|
|
bool isJustStageUp{};
|
|
bool isJustStageFinal{};
|
|
SpritesheetType spritesheetType{};
|
|
std::map<int, Override> interactAreaOverrides{};
|
|
std::unordered_map<int, int> expandAreaOverrideLayerIDs{};
|
|
std::unordered_map<int, int> expandAreaOverrideNullIDs{};
|
|
|
|
CursorState cursorState{DEFAULT};
|
|
int interactTypeID{-1};
|
|
std::optional<glm::vec2> positionOverride{};
|
|
|
|
bool isToBeDeleted{};
|
|
bool isRemoveOnAnimationEnd{};
|
|
bool isHeld{};
|
|
int schemaID{};
|
|
int rotationOverrideID{};
|
|
glm::vec2 velocity{};
|
|
float angularVelocity{};
|
|
float phase{};
|
|
float magnetTime{};
|
|
bool isCollected{};
|
|
bool isMagnetized{};
|
|
|
|
Entity() = default;
|
|
Entity(const Entity&);
|
|
Entity(Entity&&) noexcept;
|
|
Entity& operator=(const Entity&);
|
|
Entity& operator=(Entity&&) noexcept;
|
|
Entity(resource::xml::Anm2, glm::vec2 position = {}, Mode = PLAY, float time = 0.0f, int animationIndex = -1);
|
|
Entity(resource::xml::Character&, glm::ivec2);
|
|
Entity(resource::xml::Anm2, glm::ivec2 position, int id, glm::vec2 velocity = {}, float rotation = 0.0f);
|
|
|
|
bool is_playing(const std::string& name = {});
|
|
glm::vec4 null_frame_rect(int = -1, int animationIndex = -1, float time = -1.0f);
|
|
glm::vec4 rect();
|
|
int animation_index_get(const std::string&);
|
|
resource::xml::Anm2::Animation* animation_get(const std::string&);
|
|
resource::xml::Anm2::Animation* animation_get(int = -1);
|
|
resource::xml::Anm2::Frame frame_generate(resource::xml::Anm2::Item&, float, resource::xml::Anm2::Type,
|
|
int id = -1);
|
|
resource::xml::Anm2::Item* item_get(resource::xml::Anm2::Type, int = -1, int = -1);
|
|
void consume_played_event();
|
|
void play(AnimationRequest);
|
|
bool is_animation_request() const;
|
|
bool is_animation_finished();
|
|
void render(resource::Shader& textureShader, resource::Shader& rectShader, Canvas&);
|
|
|
|
float weight_get(util::measurement::System = util::measurement::METRIC);
|
|
float digestion_rate_get();
|
|
float capacity_percent_get() const;
|
|
float max_capacity() const;
|
|
bool is_over_capacity() const;
|
|
bool is_max_capacity() const;
|
|
int stage_get() const;
|
|
int stage_from_weight_get(float weight) const;
|
|
int stage_max_get() const;
|
|
int stage_count_get() const;
|
|
float stage_progress_get();
|
|
float stage_threshold_get(int stage = -1, util::measurement::System = util::measurement::METRIC) const;
|
|
float stage_threshold_next_get(util::measurement::System = util::measurement::METRIC) const;
|
|
void expand_areas_apply();
|
|
void spritesheet_set(SpritesheetType);
|
|
std::string idle_animation_get() const;
|
|
std::string animation_append_id_get() const;
|
|
|
|
void update();
|
|
|
|
private:
|
|
void anm2_set(const resource::xml::Anm2&);
|
|
void animation_start(int, const AnimationRequest&);
|
|
bool animation_request_apply(AnimationRequest&);
|
|
void pending_animation_apply();
|
|
void animation_update();
|
|
void character_values_clamp();
|
|
void character_update();
|
|
};
|
|
|
|
}
|