/*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/>.
*/

#include "Weapon.hpp"
#include "Engines/Physics/PhysicsWorld.hpp"
#include "WeaponEther.hpp"
#include "Engines/Sound/SoundInterface.hpp"
#include "Network/Serialization/WeaponStatus.hpp"

#include "Engines/Sound/SoundEffectsList.hpp"

Weapon::Weapon(WeaponEther &ether, unsigned int id) : PhysicsObject(),
m_ether(&ether), m_inEtherID(id), m_soundInterface(nullptr), m_disabled(false)
{

}

void Weapon::collideWorld(bool ground)
{
    //Play ground impact sound
    if (ground && !m_disabled &&
        m_physicsWorld != nullptr && m_soundInterface != nullptr)
    {
        std::string groundMaterial = m_physicsWorld->getGroundMaterial();
        if (groundMaterial != MATERIAL_NONE)
            m_soundInterface->playSoundEffect("impact_" + groundMaterial,
                                              CHARACTER_AGNOSTIC);
    }

    setVelocity(Vector(0.f, 0.f));
    m_disabled = true;

    queueForRemoval();
}

void Weapon::collide(PhysicsObject &obj)
{
    if (!m_disabled)
    {
        obj.takeAHit(5.f, (getVelocity().x > 0.f) ? HitDirection::FromLeft
                                                  : HitDirection::FromRight);
        setVelocity(Vector(0.f, 0.f));
        m_disabled = true;
    }

    queueForRemoval();
}

void Weapon::pushDamage(float strength, HitDirection side,
                        const Player &source, DamageTracker &/*damage*/)
{
    //Apply the damage immediately (it would be unwise to use a tracker
    //since the weapon will be destroyed immediately)
    takeAHit(strength, side, &source);
}

void Weapon::queueForRemoval()
{
    //Tell the weapon tracker that this weapon is ready to be removed next frame
    m_ether->queueForRemoval(m_inEtherID);
}

void Weapon::removeFromWorld()
{
    if (m_physicsWorld != nullptr)
        m_physicsWorld->removeObject((*this));
}

void Weapon::setSoundInterface(SoundInterface *soundInterface)
{
    m_soundInterface = soundInterface;
}
