/*Copyright (C) 2010-2023 Duncan Deveaux

This file is part of Hikou no mizu.

Hikou no mizu is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.

Hikou no mizu is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
GNU General Public License for more details.

You should have received a copy of the GNU General Public License
along with Hikou no mizu.  If not, see <http://www.gnu.org/licenses/>.
*/

#ifndef DEF_DAMAGE_STATUS
#define DEF_DAMAGE_STATUS

#include "Engines/Physics/PhysicsObject.hpp" ///< HitDirection
#include "Tools/Timer.hpp"
#include <cstdint>
#include <vector>
#include <list>

class Player;
class DamageDealer;
struct TimedDamage;

/// Describes a pending damage to be applied
/// in the near future by the DamageDealer
class DamageStatus
{
    public:
        DamageStatus();

        /// Read the damage information
        bool readFromDamage(const Timer::TimePoint &serverTime,
                            const TimedDamage &damage,
                            const std::vector<const Player*> &players);

        /// Reconstruct a Damage from the serialized DamageStatus
        bool writeToDamage(const Timer::TimePoint &clientTime,
                           const std::vector<Player*> &players,
                           TimedDamage &dst) const;

        /// Read/write from buffer
        bool readFromBuffer(std::list<std::uint8_t> &bytes);
        bool writeToBuffer(std::list<std::uint8_t> &dst) const;

        /// Read a list of DamageStatus from a damage dealer's queued damages
        static std::vector<DamageStatus> readDamageStatusList(
                                    const Timer::TimePoint &serverTime,
                                    const std::list<TimedDamage> &damages,
                                    const std::vector<const Player*> &players);

        /// Apply the serialized list of damages to a local damage dealer
        static void applyDamageStatusList(DamageDealer &dealer,
                                    const Timer::TimePoint &clientTime,
                                    const std::vector<DamageStatus> &damages,
                                    const std::vector<Player*> &players);

    private:
        Timer::duration_uint64_us m_timeToDamage;
        HitDirection m_direction;
        float m_strength;
        std::uint8_t m_sourcePlayer;
        std::uint8_t m_targetPlayer;
};

#endif
