Working damage dealing, a super cool reload effect and hit markers!
This commit is contained in:
+1
-1
Submodule assets updated: 8ffd0a99b9...4d36fdced7
@@ -9,8 +9,8 @@ namespace Events
|
|||||||
|
|
||||||
struct PlayerDamage : Event
|
struct PlayerDamage : Event
|
||||||
{
|
{
|
||||||
//NOTE: this struct is missing information on what the damageSource is
|
EntityWrapper Inflictor;
|
||||||
EntityWrapper Player;
|
EntityWrapper Victim;
|
||||||
double Damage;
|
double Damage;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|||||||
@@ -9,7 +9,8 @@ namespace Events
|
|||||||
|
|
||||||
struct Shoot : Event
|
struct Shoot : Event
|
||||||
{
|
{
|
||||||
EntityWrapper Player;
|
EntityWrapper Inflictor;
|
||||||
|
double Damage;
|
||||||
};
|
};
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,12 +1,15 @@
|
|||||||
#include "Sound/EPlaySoundOnEntity.h"
|
#include "Sound/EPlaySoundOnEntity.h"
|
||||||
|
#include "Collision/Collision.h"
|
||||||
#include "Rendering/AnimationSystem.h"
|
#include "Rendering/AnimationSystem.h"
|
||||||
#include "WeaponBehaviour.h"
|
#include "WeaponBehaviour.h"
|
||||||
#include "../SpawnerSystem.h"
|
#include "../SpawnerSystem.h"
|
||||||
|
#include "Core/EPlayerDamage.h"
|
||||||
|
#include "Core/EShoot.h"
|
||||||
|
|
||||||
class AssaultWeaponBehaviour : public WeaponBehaviour
|
class AssaultWeaponBehaviour : public WeaponBehaviour
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
AssaultWeaponBehaviour(SystemParams systemParams, Octree<EntityAABB>* collisionOctree, EntityWrapper weaponEntity);
|
AssaultWeaponBehaviour(SystemParams systemParams, IRenderer* renderer, Octree<EntityAABB>* collisionOctree, EntityWrapper weaponEntity);
|
||||||
|
|
||||||
virtual void Fire() override;
|
virtual void Fire() override;
|
||||||
virtual void CeaseFire() override;
|
virtual void CeaseFire() override;
|
||||||
@@ -19,16 +22,23 @@ private:
|
|||||||
// State
|
// State
|
||||||
bool m_Firing = false;
|
bool m_Firing = false;
|
||||||
bool m_Reloading = false;
|
bool m_Reloading = false;
|
||||||
|
double m_ReloadTimer = 0.0;
|
||||||
|
EntityWrapper m_ReloadImpersonator;
|
||||||
double m_TimeSinceLastFire = 0.0;
|
double m_TimeSinceLastFire = 0.0;
|
||||||
|
|
||||||
EventRelay<WeaponBehaviour, Events::AnimationComplete> m_EAnimationComplete;
|
EventRelay<WeaponBehaviour, Events::AnimationComplete> m_EAnimationComplete;
|
||||||
bool OnAnimationComplete(Events::AnimationComplete& e);
|
bool OnAnimationComplete(Events::AnimationComplete& e);
|
||||||
|
|
||||||
|
bool hasAmmo();
|
||||||
void fireRound();
|
void fireRound();
|
||||||
void spawnTracer();
|
void spawnTracer();
|
||||||
float traceRayDistance(glm::vec3 origin, glm::vec3 direction);
|
float traceRayDistance(glm::vec3 origin, glm::vec3 direction);
|
||||||
void playSound();
|
void playSound();
|
||||||
void viewPunch();
|
void viewPunch();
|
||||||
|
void finishReload();
|
||||||
void playShootAnimation();
|
void playShootAnimation();
|
||||||
void playIdleAnimation();
|
void playIdleAnimation();
|
||||||
|
void playReloadAnimation();
|
||||||
|
bool shoot(double damage);
|
||||||
|
void showHitMarker();
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -2,16 +2,18 @@
|
|||||||
#define WeaponBehaviour_h__
|
#define WeaponBehaviour_h__
|
||||||
|
|
||||||
#include "Core/System.h"
|
#include "Core/System.h"
|
||||||
|
#include "Rendering/IRenderer.h"
|
||||||
#include "Core/Octree.h"
|
#include "Core/Octree.h"
|
||||||
#include "Collision/EntityAABB.h"
|
#include "Collision/EntityAABB.h"
|
||||||
|
|
||||||
class WeaponBehaviour : public System
|
class WeaponBehaviour : public System
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
WeaponBehaviour(SystemParams systemParams, Octree<EntityAABB>* collisionOctree, EntityWrapper weaponEntity)
|
WeaponBehaviour(SystemParams systemParams, IRenderer* renderer, Octree<EntityAABB>* collisionOctree, EntityWrapper player)
|
||||||
: System(systemParams)
|
: System(systemParams)
|
||||||
|
, m_Renderer(renderer)
|
||||||
, m_CollisionOctree(collisionOctree)
|
, m_CollisionOctree(collisionOctree)
|
||||||
, m_Entity(weaponEntity)
|
, m_Player(player)
|
||||||
{ }
|
{ }
|
||||||
virtual ~WeaponBehaviour() = default;
|
virtual ~WeaponBehaviour() = default;
|
||||||
|
|
||||||
@@ -24,8 +26,9 @@ public:
|
|||||||
virtual void Update(double dt) { }
|
virtual void Update(double dt) { }
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
|
IRenderer* m_Renderer;
|
||||||
Octree<EntityAABB>* m_CollisionOctree;
|
Octree<EntityAABB>* m_CollisionOctree;
|
||||||
EntityWrapper m_Entity;
|
EntityWrapper m_Player;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
@@ -35,8 +35,6 @@ private:
|
|||||||
// Events
|
// Events
|
||||||
EventRelay<WeaponSystem, Events::PlayerSpawned> m_EPlayerSpawned;
|
EventRelay<WeaponSystem, Events::PlayerSpawned> m_EPlayerSpawned;
|
||||||
bool OnPlayerSpawned(Events::PlayerSpawned& e);
|
bool OnPlayerSpawned(Events::PlayerSpawned& e);
|
||||||
EventRelay<WeaponSystem, Events::Shoot> m_EShoot;
|
|
||||||
bool OnShoot(Events::Shoot& e);
|
|
||||||
EventRelay<WeaponSystem, Events::InputCommand> m_EInputCommand;
|
EventRelay<WeaponSystem, Events::InputCommand> m_EInputCommand;
|
||||||
bool OnInputCommand(Events::InputCommand& e);
|
bool OnInputCommand(Events::InputCommand& e);
|
||||||
|
|
||||||
|
|||||||
@@ -7,4 +7,5 @@
|
|||||||
<BaseDamage>5</BaseDamage>
|
<BaseDamage>5</BaseDamage>
|
||||||
<RPM>120</RPM>
|
<RPM>120</RPM>
|
||||||
<ViewPunch>0.01</ViewPunch>
|
<ViewPunch>0.01</ViewPunch>
|
||||||
|
<ReloadTime>2</ReloadTime>
|
||||||
</AssaultWeapon>
|
</AssaultWeapon>
|
||||||
@@ -25,6 +25,9 @@
|
|||||||
<xs:element name="ViewPunch" type="t:float" minOccurs="0">
|
<xs:element name="ViewPunch" type="t:float" minOccurs="0">
|
||||||
<xs:annotation><xs:documentation>View punch in radians for each bullet fired</xs:documentation></xs:annotation>
|
<xs:annotation><xs:documentation>View punch in radians for each bullet fired</xs:documentation></xs:annotation>
|
||||||
</xs:element>
|
</xs:element>
|
||||||
|
<xs:element name="ReloadTime" type="t:double" minOccurs="0">
|
||||||
|
<xs:annotation><xs:documentation>Time it takes to reload the weapon in seconds</xs:documentation></xs:annotation>
|
||||||
|
</xs:element>
|
||||||
</xs:all>
|
</xs:all>
|
||||||
</xs:complexType>
|
</xs:complexType>
|
||||||
</xs:element>
|
</xs:element>
|
||||||
|
|||||||
@@ -0,0 +1,20 @@
|
|||||||
|
<?xml version="1.0" encoding="UTF-8" standalone="no" ?>
|
||||||
|
<Entity name="HitMarker" xmlns:c="components" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../Types/Entity.xsd">
|
||||||
|
|
||||||
|
<Components>
|
||||||
|
<c:Lifetime>
|
||||||
|
<Lifetime>0.1</Lifetime>
|
||||||
|
</c:Lifetime>
|
||||||
|
<c:Sprite>
|
||||||
|
<DiffuseTexture>Textures/Weapons/Crosshair/SmallThickHoleDot.png</DiffuseTexture>
|
||||||
|
<DepthSort>false</DepthSort>
|
||||||
|
</c:Sprite>
|
||||||
|
<c:Transform>
|
||||||
|
<Scale X="0.031" Y="0.031" Z="1"/>
|
||||||
|
<Orientation X="0" Y="0" Z="0.782"/>
|
||||||
|
</c:Transform>
|
||||||
|
</Components>
|
||||||
|
|
||||||
|
<Children/>
|
||||||
|
|
||||||
|
</Entity>
|
||||||
@@ -124,10 +124,14 @@
|
|||||||
<Origin X="0" Y="0.772000015" Z="0"/>
|
<Origin X="0" Y="0.772000015" Z="0"/>
|
||||||
<Size X="1" Y="1.60000002" Z="1"/>
|
<Size X="1" Y="1.60000002" Z="1"/>
|
||||||
</c:AABB>
|
</c:AABB>
|
||||||
|
<c:AssaultWeapon>
|
||||||
|
<RPM>600</RPM>
|
||||||
|
</c:AssaultWeapon>
|
||||||
<c:Collidable/>
|
<c:Collidable/>
|
||||||
<c:Model/>
|
<c:DashAbility/>
|
||||||
|
<c:Health/>
|
||||||
<c:Physics>
|
<c:Physics>
|
||||||
<Gravity>false</Gravity>
|
<Velocity X="2.30999646e-23" Y="0" Z="1.05272533e-23"/>
|
||||||
</c:Physics>
|
</c:Physics>
|
||||||
<c:Player>
|
<c:Player>
|
||||||
<MovementSpeed>5</MovementSpeed>
|
<MovementSpeed>5</MovementSpeed>
|
||||||
@@ -138,8 +142,7 @@
|
|||||||
</Team>
|
</Team>
|
||||||
</c:Team>
|
</c:Team>
|
||||||
<c:Transform>
|
<c:Transform>
|
||||||
<Position X="-1.68112314" Y="0.0288829971" Z="3.06287026"/>
|
<Position X="0" Y="0.0288832653" Z="2.64837074"/>
|
||||||
<Orientation X="0" Y="2.14675093" Z="0"/>
|
|
||||||
</c:Transform>
|
</c:Transform>
|
||||||
</Components>
|
</Components>
|
||||||
<Children>
|
<Children>
|
||||||
@@ -147,7 +150,7 @@
|
|||||||
<Components>
|
<Components>
|
||||||
<c:Camera/>
|
<c:Camera/>
|
||||||
<c:Transform>
|
<c:Transform>
|
||||||
<Position X="0" Y="1.37700009" Z="0"/>
|
<Position X="0" Y="1.27700007" Z="0"/>
|
||||||
</c:Transform>
|
</c:Transform>
|
||||||
</Components>
|
</Components>
|
||||||
<Children>
|
<Children>
|
||||||
@@ -156,10 +159,9 @@
|
|||||||
<c:Text>
|
<c:Text>
|
||||||
<Resource>Fonts/DroidSans.ttf,100</Resource>
|
<Resource>Fonts/DroidSans.ttf,100</Resource>
|
||||||
<Color A="1" B="0" G="1" R="0"/>
|
<Color A="1" B="0" G="1" R="0"/>
|
||||||
<Visible>false</Visible>
|
|
||||||
</c:Text>
|
</c:Text>
|
||||||
<c:Transform>
|
<c:Transform>
|
||||||
<Position X="0" Y="0.247910097" Z="-0.447844714"/>
|
<Position X="0.100000001" Y="0.248000011" Z="-0.248000011"/>
|
||||||
<Scale X="0.100000001" Y="0.113000005" Z="0.5"/>
|
<Scale X="0.100000001" Y="0.113000005" Z="0.5"/>
|
||||||
<Orientation X="0" Y="3.14199996" Z="0"/>
|
<Orientation X="0" Y="3.14199996" Z="0"/>
|
||||||
</c:Transform>
|
</c:Transform>
|
||||||
@@ -170,6 +172,7 @@
|
|||||||
<Components>
|
<Components>
|
||||||
<c:Model>
|
<c:Model>
|
||||||
<Resource>Models/Widgets/Camera.mesh</Resource>
|
<Resource>Models/Widgets/Camera.mesh</Resource>
|
||||||
|
<Visible>false</Visible>
|
||||||
</c:Model>
|
</c:Model>
|
||||||
<c:Transform>
|
<c:Transform>
|
||||||
<Position X="0" Y="0.0331346765" Z="-0.0792061687"/>
|
<Position X="0" Y="0.0331346765" Z="-0.0792061687"/>
|
||||||
@@ -178,6 +181,100 @@
|
|||||||
</Components>
|
</Components>
|
||||||
<Children/>
|
<Children/>
|
||||||
</Entity>
|
</Entity>
|
||||||
|
<Entity name="HUD">
|
||||||
|
<Components>
|
||||||
|
<c:Transform>
|
||||||
|
<Position X="0" Y="0" Z="-0.5"/>
|
||||||
|
</c:Transform>
|
||||||
|
</Components>
|
||||||
|
<Children>
|
||||||
|
<Entity name="HealthBar">
|
||||||
|
<Components>
|
||||||
|
<c:Fill>
|
||||||
|
<Percentage>1</Percentage>
|
||||||
|
<Color A="0" B="1" G="0" R="0"/>
|
||||||
|
</c:Fill>
|
||||||
|
<c:HealthHUD/>
|
||||||
|
<c:Model>
|
||||||
|
<Resource>Models/Core/UnitHexagon.mesh</Resource>
|
||||||
|
<Color A="1" B="0.70588237" G="0.70588237" R="0.70588237"/>
|
||||||
|
</c:Model>
|
||||||
|
<c:Transform>
|
||||||
|
<Position X="-0.383000016" Y="-0.185000002" Z="0"/>
|
||||||
|
<Scale X="0.150000006" Y="0.150000006" Z="0.150000006"/>
|
||||||
|
<Orientation X="0" Y="0.594000041" Z="0"/>
|
||||||
|
</c:Transform>
|
||||||
|
</Components>
|
||||||
|
<Children/>
|
||||||
|
</Entity>
|
||||||
|
<Entity name="Crosshair">
|
||||||
|
<Components>
|
||||||
|
<c:Sprite>
|
||||||
|
<DiffuseTexture>Textures/Weapons/Crosshair/SmallThickHoleDot.png</DiffuseTexture>
|
||||||
|
<DepthSort>false</DepthSort>
|
||||||
|
</c:Sprite>
|
||||||
|
<c:Transform>
|
||||||
|
<Position X="0" Y="0" Z="0.200000003"/>
|
||||||
|
<Scale X="0.0250000004" Y="0.0250000004" Z="0"/>
|
||||||
|
</c:Transform>
|
||||||
|
</Components>
|
||||||
|
<Children/>
|
||||||
|
</Entity>
|
||||||
|
</Children>
|
||||||
|
</Entity>
|
||||||
|
<Entity name="Hands">
|
||||||
|
<Components>
|
||||||
|
<c:Animation>
|
||||||
|
<AnimationName1>Idle</AnimationName1>
|
||||||
|
<Time1>1.9569972344146196</Time1>
|
||||||
|
<Speed1>1</Speed1>
|
||||||
|
</c:Animation>
|
||||||
|
<c:Model>
|
||||||
|
<Resource>Models/Characters/Assault/FirstPerson.mesh</Resource>
|
||||||
|
<Transparent>true</Transparent>
|
||||||
|
</c:Model>
|
||||||
|
<c:Transform/>
|
||||||
|
</Components>
|
||||||
|
<Children>
|
||||||
|
<Entity name="WeaponModel">
|
||||||
|
<Components>
|
||||||
|
<c:BoneAttachment>
|
||||||
|
<BoneName>R_Arm_Weapon_Joint</BoneName>
|
||||||
|
</c:BoneAttachment>
|
||||||
|
<c:Model>
|
||||||
|
<Resource>Models/Weapons/Blue/AssaultWeaponBlue.mesh</Resource>
|
||||||
|
<Transparent>true</Transparent>
|
||||||
|
</c:Model>
|
||||||
|
<c:Transform>
|
||||||
|
<Position X="0.120748013" Y="-0.228470564" Z="-0.151475638"/>
|
||||||
|
<Orientation X="0.010404693" Y="-0.00268176314" Z="0.0428441502"/>
|
||||||
|
</c:Transform>
|
||||||
|
</Components>
|
||||||
|
<Children>
|
||||||
|
<Entity name="WeaponMuzzle">
|
||||||
|
<Components>
|
||||||
|
<c:Spawner>
|
||||||
|
<EntityFile>Schema/Entities/RayBlue.xml</EntityFile>
|
||||||
|
</c:Spawner>
|
||||||
|
<c:Transform>
|
||||||
|
<Position X="0.00325386273" Y="0.0970000029" Z="-0.843000054"/>
|
||||||
|
</c:Transform>
|
||||||
|
</Components>
|
||||||
|
<Children/>
|
||||||
|
</Entity>
|
||||||
|
</Children>
|
||||||
|
</Entity>
|
||||||
|
<Entity name="FirstPersonReloadSpawner">
|
||||||
|
<Components>
|
||||||
|
<c:Spawner>
|
||||||
|
<EntityFile>Schema/Entities/WeaponReloadEffect.xml</EntityFile>
|
||||||
|
</c:Spawner>
|
||||||
|
<c:Transform/>
|
||||||
|
</Components>
|
||||||
|
<Children/>
|
||||||
|
</Entity>
|
||||||
|
</Children>
|
||||||
|
</Entity>
|
||||||
</Children>
|
</Children>
|
||||||
</Entity>
|
</Entity>
|
||||||
<Entity name="ThirdPersonCamera">
|
<Entity name="ThirdPersonCamera">
|
||||||
@@ -196,15 +293,52 @@
|
|||||||
</Entity>
|
</Entity>
|
||||||
<Entity name="PlayerModel">
|
<Entity name="PlayerModel">
|
||||||
<Components>
|
<Components>
|
||||||
|
<c:Animation>
|
||||||
|
<AnimationName1>Idle</AnimationName1>
|
||||||
|
<Time1>1.8055945618467364</Time1>
|
||||||
|
<Speed1>1</Speed1>
|
||||||
|
</c:Animation>
|
||||||
|
<c:AnimationOffset>
|
||||||
|
<AnimationName>AimRifle</AnimationName>
|
||||||
|
<Time>0.5</Time>
|
||||||
|
</c:AnimationOffset>
|
||||||
|
<c:HiddenForLocalPlayer/>
|
||||||
<c:Model>
|
<c:Model>
|
||||||
<Resource>Models/Characters/Assault/AssaultHeadless.mesh</Resource>
|
<Resource>Models/Characters/Assault/AssaultAnimations.mesh</Resource>
|
||||||
<Color A="1" B="0" G="0" R="1"/>
|
<Color A="1" B="0" G="0" R="1"/>
|
||||||
</c:Model>
|
</c:Model>
|
||||||
<c:Transform>
|
<c:Transform/>
|
||||||
<Orientation X="0" Y="3.14159274" Z="0"/>
|
|
||||||
</c:Transform>
|
|
||||||
</Components>
|
</Components>
|
||||||
<Children/>
|
<Children>
|
||||||
|
<Entity name="ThirdPersonWeaponModel">
|
||||||
|
<Components>
|
||||||
|
<c:BoneAttachment>
|
||||||
|
<BoneName>R_Arm_Weapon_Joint</BoneName>
|
||||||
|
</c:BoneAttachment>
|
||||||
|
<c:Model>
|
||||||
|
<Resource>Models/Weapons/Blue/AssaultWeaponBlue.mesh</Resource>
|
||||||
|
<Visible>false</Visible>
|
||||||
|
</c:Model>
|
||||||
|
<c:Transform>
|
||||||
|
<Position X="0.158578917" Y="1.02878916" Z="-0.215411991"/>
|
||||||
|
<Orientation X="-0.0626687407" Y="-0.0361274257" Z="0.120101407"/>
|
||||||
|
</c:Transform>
|
||||||
|
</Components>
|
||||||
|
<Children>
|
||||||
|
<Entity name="ThirdPersonWeaponMuzzle">
|
||||||
|
<Components>
|
||||||
|
<c:Spawner>
|
||||||
|
<EntityFile>Schema/Entities/RayBlue.xml</EntityFile>
|
||||||
|
</c:Spawner>
|
||||||
|
<c:Transform>
|
||||||
|
<Position X="0.00644115033" Y="0.096679531" Z="-0.436609417"/>
|
||||||
|
</c:Transform>
|
||||||
|
</Components>
|
||||||
|
<Children/>
|
||||||
|
</Entity>
|
||||||
|
</Children>
|
||||||
|
</Entity>
|
||||||
|
</Children>
|
||||||
</Entity>
|
</Entity>
|
||||||
<Entity name="AABBStanding">
|
<Entity name="AABBStanding">
|
||||||
<Components>
|
<Components>
|
||||||
|
|||||||
@@ -23,7 +23,9 @@
|
|||||||
<Blue/>
|
<Blue/>
|
||||||
</Team>
|
</Team>
|
||||||
</c:Team>
|
</c:Team>
|
||||||
<c:Transform/>
|
<c:Transform>
|
||||||
|
<Position X="0" Y="0.0288832653" Z="2.64837074"/>
|
||||||
|
</c:Transform>
|
||||||
</Components>
|
</Components>
|
||||||
|
|
||||||
<Children>
|
<Children>
|
||||||
@@ -90,24 +92,33 @@
|
|||||||
</Entity>
|
</Entity>
|
||||||
<Entity name="Crosshair">
|
<Entity name="Crosshair">
|
||||||
<Components>
|
<Components>
|
||||||
<c:Model>
|
<c:Sprite>
|
||||||
<Resource>Models/Weapons/CrosshairQuad.mesh</Resource>
|
<DiffuseTexture>Textures/Weapons/Crosshair/SmallThickHoleDot.png</DiffuseTexture>
|
||||||
</c:Model>
|
<DepthSort>false</DepthSort>
|
||||||
|
</c:Sprite>
|
||||||
<c:Transform>
|
<c:Transform>
|
||||||
<Position X="0" Y="0" Z="0.200000003"/>
|
<Position X="0" Y="0" Z="0.200000003"/>
|
||||||
<Scale X="0.00600000005" Y="1" Z="0.00600000005"/>
|
<Scale X="0.0250000004" Y="0.0250000004" Z="0"/>
|
||||||
<Orientation X="1.57000005" Y="0" Z="0"/>
|
|
||||||
</c:Transform>
|
</c:Transform>
|
||||||
</Components>
|
</Components>
|
||||||
<Children/>
|
<Children/>
|
||||||
</Entity>
|
</Entity>
|
||||||
|
<Entity name="HitMarkerSpawner">
|
||||||
|
<Components>
|
||||||
|
<c:Spawner>
|
||||||
|
<EntityFile>Schema/Entities/HitMarker.xml</EntityFile>
|
||||||
|
</c:Spawner>
|
||||||
|
<c:Transform/>
|
||||||
|
</Components>
|
||||||
|
<Children/>
|
||||||
|
</Entity>
|
||||||
</Children>
|
</Children>
|
||||||
</Entity>
|
</Entity>
|
||||||
<Entity name="Hands">
|
<Entity name="Hands">
|
||||||
<Components>
|
<Components>
|
||||||
<c:Animation>
|
<c:Animation>
|
||||||
<AnimationName1>Idle</AnimationName1>
|
<AnimationName1>Idle</AnimationName1>
|
||||||
<Time1>0.52743271827223559</Time1>
|
<Time1>0.1719161089749548</Time1>
|
||||||
<Speed1>1</Speed1>
|
<Speed1>1</Speed1>
|
||||||
</c:Animation>
|
</c:Animation>
|
||||||
<c:Model>
|
<c:Model>
|
||||||
@@ -124,10 +135,11 @@
|
|||||||
</c:BoneAttachment>
|
</c:BoneAttachment>
|
||||||
<c:Model>
|
<c:Model>
|
||||||
<Resource>Models/Weapons/Blue/AssaultWeaponBlue.mesh</Resource>
|
<Resource>Models/Weapons/Blue/AssaultWeaponBlue.mesh</Resource>
|
||||||
|
<Transparent>true</Transparent>
|
||||||
</c:Model>
|
</c:Model>
|
||||||
<c:Transform>
|
<c:Transform>
|
||||||
<Position X="0.120747946" Y="-0.232330009" Z="-0.151475713"/>
|
<Position X="0.120747983" Y="-0.228997007" Z="-0.151475653"/>
|
||||||
<Orientation X="0.0104046576" Y="-0.00268170447" Z="0.0428439789"/>
|
<Orientation X="0.0104046585" Y="-0.00268164417" Z="0.0428441912"/>
|
||||||
</c:Transform>
|
</c:Transform>
|
||||||
</Components>
|
</Components>
|
||||||
<Children>
|
<Children>
|
||||||
@@ -144,6 +156,15 @@
|
|||||||
</Entity>
|
</Entity>
|
||||||
</Children>
|
</Children>
|
||||||
</Entity>
|
</Entity>
|
||||||
|
<Entity name="FirstPersonReloadSpawner">
|
||||||
|
<Components>
|
||||||
|
<c:Spawner>
|
||||||
|
<EntityFile>Schema/Entities/WeaponReloadEffect.xml</EntityFile>
|
||||||
|
</c:Spawner>
|
||||||
|
<c:Transform/>
|
||||||
|
</Components>
|
||||||
|
<Children/>
|
||||||
|
</Entity>
|
||||||
</Children>
|
</Children>
|
||||||
</Entity>
|
</Entity>
|
||||||
</Children>
|
</Children>
|
||||||
@@ -166,7 +187,7 @@
|
|||||||
<Components>
|
<Components>
|
||||||
<c:Animation>
|
<c:Animation>
|
||||||
<AnimationName1>Idle</AnimationName1>
|
<AnimationName1>Idle</AnimationName1>
|
||||||
<Time1>0.69666320633760392</Time1>
|
<Time1>1.8038469763698401</Time1>
|
||||||
<Speed1>1</Speed1>
|
<Speed1>1</Speed1>
|
||||||
</c:Animation>
|
</c:Animation>
|
||||||
<c:AnimationOffset>
|
<c:AnimationOffset>
|
||||||
@@ -188,10 +209,11 @@
|
|||||||
</c:BoneAttachment>
|
</c:BoneAttachment>
|
||||||
<c:Model>
|
<c:Model>
|
||||||
<Resource>Models/Weapons/Blue/AssaultWeaponBlue.mesh</Resource>
|
<Resource>Models/Weapons/Blue/AssaultWeaponBlue.mesh</Resource>
|
||||||
|
<Visible>false</Visible>
|
||||||
</c:Model>
|
</c:Model>
|
||||||
<c:Transform>
|
<c:Transform>
|
||||||
<Position X="0.162715688" Y="1.02479136" Z="-0.215626657"/>
|
<Position X="0.15859656" Y="1.02875519" Z="-0.21540691"/>
|
||||||
<Orientation X="-0.0629899353" Y="-0.0542047173" Z="0.11849726"/>
|
<Orientation X="-0.0626692101" Y="-0.0361935496" Z="0.120095037"/>
|
||||||
</c:Transform>
|
</c:Transform>
|
||||||
</Components>
|
</Components>
|
||||||
<Children>
|
<Children>
|
||||||
|
|||||||
@@ -0,0 +1,31 @@
|
|||||||
|
<?xml version="1.0" encoding="UTF-8" standalone="no" ?>
|
||||||
|
<Entity name="WeaponModel" xmlns:c="components" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../Types/Entity.xsd">
|
||||||
|
|
||||||
|
<Components>
|
||||||
|
<c:BoneAttachment>
|
||||||
|
<BoneName>R_Arm_Weapon_Joint</BoneName>
|
||||||
|
</c:BoneAttachment>
|
||||||
|
<c:Lifetime>
|
||||||
|
<Lifetime>2</Lifetime>
|
||||||
|
</c:Lifetime>
|
||||||
|
<c:ExplosionEffect>
|
||||||
|
<ColorByDistance>true</ColorByDistance>
|
||||||
|
<Velocity X="3.33300018" Y="0.0320000015" Z="0"/>
|
||||||
|
<ExplosionOrigin X="0" Y="0.0790000036" Z="-0.329000026"/>
|
||||||
|
<ExponentialAccelaration>true</ExponentialAccelaration>
|
||||||
|
<EndColor A="0" B="19.6078434" G="19.6078434" R="1"/>
|
||||||
|
<Randomness>true</Randomness>
|
||||||
|
</c:ExplosionEffect>
|
||||||
|
<c:Model>
|
||||||
|
<Resource>Models/Weapons/Blue/AssaultWeaponBlue.mesh</Resource>
|
||||||
|
<Transparent>true</Transparent>
|
||||||
|
</c:Model>
|
||||||
|
<c:Transform>
|
||||||
|
<Position X="0.120747991" Y="-0.229502052" Z="-0.151475638"/>
|
||||||
|
<Orientation X="0.0104046296" Y="-0.00268167513" Z="0.0428442545"/>
|
||||||
|
</c:Transform>
|
||||||
|
</Components>
|
||||||
|
|
||||||
|
<Children/>
|
||||||
|
|
||||||
|
</Entity>
|
||||||
@@ -65,7 +65,6 @@ void EntityFilePreprocessor::parseComponentInfo()
|
|||||||
|
|
||||||
// Name
|
// Name
|
||||||
compInfo.Name = XS::ToString(element->getName());
|
compInfo.Name = XS::ToString(element->getName());
|
||||||
bool brk = compInfo.Name == "HiddenForLocalPlayer";
|
|
||||||
// Known allocation
|
// Known allocation
|
||||||
compInfo.Meta->Allocation = m_ComponentCounts[compInfo.Name];
|
compInfo.Meta->Allocation = m_ComponentCounts[compInfo.Name];
|
||||||
// Annotation
|
// Annotation
|
||||||
|
|||||||
@@ -390,8 +390,9 @@ bool Client::OnInputCommand(const Events::InputCommand & e)
|
|||||||
bool Client::OnPlayerDamage(const Events::PlayerDamage & e)
|
bool Client::OnPlayerDamage(const Events::PlayerDamage & e)
|
||||||
{
|
{
|
||||||
Packet packet(MessageType::OnPlayerDamage, m_SendPacketID);
|
Packet packet(MessageType::OnPlayerDamage, m_SendPacketID);
|
||||||
|
packet.WritePrimitive(m_ClientIDToServerID.at(e.Inflictor.ID));
|
||||||
|
packet.WritePrimitive(m_ClientIDToServerID.at(e.Victim.ID));
|
||||||
packet.WritePrimitive(e.Damage);
|
packet.WritePrimitive(e.Damage);
|
||||||
packet.WritePrimitive(m_ClientIDToServerID.at(e.Player.ID));
|
|
||||||
send(packet);
|
send(packet);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -299,8 +299,9 @@ void Server::parseOnInputCommand(Packet& packet)
|
|||||||
void Server::parseOnPlayerDamage(Packet & packet)
|
void Server::parseOnPlayerDamage(Packet & packet)
|
||||||
{
|
{
|
||||||
Events::PlayerDamage e;
|
Events::PlayerDamage e;
|
||||||
|
e.Inflictor = EntityWrapper(m_World, packet.ReadPrimitive<EntityID>());
|
||||||
|
e.Victim = EntityWrapper(m_World, packet.ReadPrimitive<EntityID>());
|
||||||
e.Damage = packet.ReadPrimitive<double>();
|
e.Damage = packet.ReadPrimitive<double>();
|
||||||
e.Player = EntityWrapper(m_World, packet.ReadPrimitive<EntityID>());
|
|
||||||
m_EventBroker->Publish(e);
|
m_EventBroker->Publish(e);
|
||||||
//LOG_DEBUG("Server::parseOnPlayerDamage: Command is %s. Value is %f. PlayerID is %i.", e.DamageAmount, e.PlayerDamagedID, e.TypeOfDamage.c_str());
|
//LOG_DEBUG("Server::parseOnPlayerDamage: Command is %s. Value is %f. PlayerID is %i.", e.DamageAmount, e.PlayerDamagedID, e.TypeOfDamage.c_str());
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -15,13 +15,13 @@ void HealthSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapper& comp
|
|||||||
|
|
||||||
bool HealthSystem::OnPlayerDamaged(Events::PlayerDamage& e)
|
bool HealthSystem::OnPlayerDamaged(Events::PlayerDamage& e)
|
||||||
{
|
{
|
||||||
ComponentWrapper cHealth = e.Player["Health"];
|
ComponentWrapper cHealth = e.Victim["Health"];
|
||||||
double& health = cHealth["Health"];
|
double& health = cHealth["Health"];
|
||||||
health -= e.Damage;
|
health -= e.Damage;
|
||||||
|
|
||||||
if (health <= 0.0) {
|
if (health <= 0.0) {
|
||||||
Events::PlayerDeath ePlayerDeath;
|
Events::PlayerDeath ePlayerDeath;
|
||||||
ePlayerDeath.Player = e.Player;
|
ePlayerDeath.Player = e.Victim;
|
||||||
m_EventBroker->Publish(ePlayerDeath);
|
m_EventBroker->Publish(ePlayerDeath);
|
||||||
//Note: we will delete the entity in PlayerDeathSystem
|
//Note: we will delete the entity in PlayerDeathSystem
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -41,7 +41,9 @@ void PlayerDeathSystem::createDeathEffect(EntityWrapper player)
|
|||||||
playerEntityModel.Copy(deathEffectEW["Model"]);
|
playerEntityModel.Copy(deathEffectEW["Model"]);
|
||||||
playerEntityAnimation.Copy(deathEffectEW["Animation"]);
|
playerEntityAnimation.Copy(deathEffectEW["Animation"]);
|
||||||
//freeze the animation
|
//freeze the animation
|
||||||
deathEffectEW["Animation"]["Speed"] = 0.0;
|
deathEffectEW["Animation"]["Speed1"] = 0.0;
|
||||||
|
deathEffectEW["Animation"]["Speed2"] = 0.0;
|
||||||
|
deathEffectEW["Animation"]["Speed3"] = 0.0;
|
||||||
|
|
||||||
//copy the models position,orientation
|
//copy the models position,orientation
|
||||||
deathEffectEW["Transform"]["Position"] = (glm::vec3)player["Transform"]["Position"];
|
deathEffectEW["Transform"]["Position"] = (glm::vec3)player["Transform"]["Position"];
|
||||||
@@ -50,8 +52,10 @@ void PlayerDeathSystem::createDeathEffect(EntityWrapper player)
|
|||||||
//deathEffectEW["ExplosionEffect"]["ExplosionOrigin"] = glm::vec3(0, 0, 0);
|
//deathEffectEW["ExplosionEffect"]["ExplosionOrigin"] = glm::vec3(0, 0, 0);
|
||||||
|
|
||||||
//camera (with lifetime) behind the player
|
//camera (with lifetime) behind the player
|
||||||
auto cam = deathEffectEW.FirstChildByName("Camera");
|
if (player == LocalPlayer) {
|
||||||
Events::SetCamera eSetCamera;
|
auto cam = deathEffectEW.FirstChildByName("Camera");
|
||||||
eSetCamera.CameraEntity = cam;
|
Events::SetCamera eSetCamera;
|
||||||
m_EventBroker->Publish(eSetCamera);
|
eSetCamera.CameraEntity = cam;
|
||||||
|
m_EventBroker->Publish(eSetCamera);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -54,7 +54,7 @@ bool SoundSystem::OnInputCommand(const Events::InputCommand & e)
|
|||||||
}
|
}
|
||||||
if (e.Command == "TakeDamage" && e.Value > 0) {
|
if (e.Command == "TakeDamage" && e.Value > 0) {
|
||||||
Events::PlayerDamage ev;
|
Events::PlayerDamage ev;
|
||||||
ev.Player = LocalPlayer;
|
ev.Victim = LocalPlayer;
|
||||||
ev.Damage = 1.0;
|
ev.Damage = 1.0;
|
||||||
m_EventBroker->Publish(ev);
|
m_EventBroker->Publish(ev);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -48,10 +48,12 @@ EntityWrapper SpawnerSystem::Spawn(EntityWrapper spawner, EntityWrapper parent /
|
|||||||
EntityFileParser parser(entityFile);
|
EntityFileParser parser(entityFile);
|
||||||
EntityWrapper spawnedEntity(world, parser.MergeEntities(world, parent.ID));
|
EntityWrapper spawnedEntity(world, parser.MergeEntities(world, parent.ID));
|
||||||
|
|
||||||
// Set its position and orientation to that of the SpawnPoint
|
if (spawnPoint != parent) {
|
||||||
spawnedEntity["Transform"]["Position"] = Transform::AbsolutePosition(spawnPoint.World, spawnPoint.ID);
|
// Set its position and orientation to that of the SpawnPoint
|
||||||
// TODO: Quaternions, bitch
|
spawnedEntity["Transform"]["Position"] = Transform::AbsolutePosition(spawnPoint.World, spawnPoint.ID);
|
||||||
spawnedEntity["Transform"]["Orientation"] = glm::eulerAngles(Transform::AbsoluteOrientation(spawnPoint));
|
// TODO: Quaternions, bitch
|
||||||
|
spawnedEntity["Transform"]["Orientation"] = glm::eulerAngles(Transform::AbsoluteOrientation(spawnPoint));
|
||||||
|
}
|
||||||
|
|
||||||
return spawnedEntity;
|
return spawnedEntity;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,9 +1,9 @@
|
|||||||
#include "Systems/Weapon/AssaultWeaponBehaviour.h"
|
#include "Systems/Weapon/AssaultWeaponBehaviour.h"
|
||||||
|
|
||||||
AssaultWeaponBehaviour::AssaultWeaponBehaviour(SystemParams systemParams, Octree<EntityAABB>* collisionOctree, EntityWrapper weaponEntity)
|
AssaultWeaponBehaviour::AssaultWeaponBehaviour(SystemParams systemParams, IRenderer* renderer, Octree<EntityAABB>* collisionOctree, EntityWrapper player)
|
||||||
: WeaponBehaviour(systemParams, collisionOctree, weaponEntity)
|
: WeaponBehaviour(systemParams, renderer, collisionOctree, player)
|
||||||
{
|
{
|
||||||
m_FirstPersonModel = m_Entity.FirstChildByName("Hands");
|
m_FirstPersonModel = m_Player.FirstChildByName("Hands");
|
||||||
EVENT_SUBSCRIBE_MEMBER(m_EAnimationComplete, &AssaultWeaponBehaviour::OnAnimationComplete);
|
EVENT_SUBSCRIBE_MEMBER(m_EAnimationComplete, &AssaultWeaponBehaviour::OnAnimationComplete);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -12,7 +12,6 @@ void AssaultWeaponBehaviour::Fire()
|
|||||||
m_TimeSinceLastFire = 0.0;
|
m_TimeSinceLastFire = 0.0;
|
||||||
m_Firing = true;
|
m_Firing = true;
|
||||||
fireRound();
|
fireRound();
|
||||||
playShootAnimation();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void AssaultWeaponBehaviour::CeaseFire()
|
void AssaultWeaponBehaviour::CeaseFire()
|
||||||
@@ -22,29 +21,48 @@ void AssaultWeaponBehaviour::CeaseFire()
|
|||||||
|
|
||||||
void AssaultWeaponBehaviour::Reload()
|
void AssaultWeaponBehaviour::Reload()
|
||||||
{
|
{
|
||||||
ComponentWrapper& cAssaultWeapon = m_Entity["AssaultWeapon"];
|
if (m_Reloading) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
int& magAmmo = cAssaultWeapon["MagazineAmmo"];
|
ComponentWrapper& cAssaultWeapon = m_Player["AssaultWeapon"];
|
||||||
|
int magAmmo = cAssaultWeapon["MagazineAmmo"];
|
||||||
int magSize = cAssaultWeapon["MagazineSize"];
|
int magSize = cAssaultWeapon["MagazineSize"];
|
||||||
int& ammo = cAssaultWeapon["Ammo"];
|
int ammo = cAssaultWeapon["Ammo"];
|
||||||
|
|
||||||
// Don't reload if we're already fully loaded
|
// Don't reload if we're already fully loaded
|
||||||
if (magAmmo == magSize) {
|
if (magAmmo == magSize) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Throw away rounds in magazine to incentivise ammo sharing
|
// Don't reload if we're completly out of ammo
|
||||||
int toLoad = glm::min(magSize, ammo);
|
if (ammo == 0) {
|
||||||
magAmmo = toLoad;
|
return;
|
||||||
ammo -= toLoad;
|
}
|
||||||
|
|
||||||
|
m_Reloading = true;
|
||||||
|
m_ReloadTimer = cAssaultWeapon["ReloadTime"];
|
||||||
|
playReloadAnimation();
|
||||||
}
|
}
|
||||||
|
|
||||||
void AssaultWeaponBehaviour::Update(double dt)
|
void AssaultWeaponBehaviour::Update(double dt)
|
||||||
{
|
{
|
||||||
if (m_Firing) {
|
if (m_Reloading) {
|
||||||
m_TimeSinceLastFire += dt;
|
m_ReloadTimer -= dt;
|
||||||
|
// Re-enable glow on reload impersonator half-way through the animation
|
||||||
|
if (m_ReloadTimer <= (double)m_Player["AssaultWeapon"]["ReloadTime"] / 2.0) {
|
||||||
|
if (m_ReloadImpersonator.Valid()) {
|
||||||
|
m_ReloadImpersonator["Model"]["GlowMap"] = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (m_ReloadTimer <= 0) {
|
||||||
|
finishReload();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
ComponentWrapper& cAssaultWeapon = m_Entity["AssaultWeapon"];
|
if (m_Firing && !m_Reloading) {
|
||||||
|
m_TimeSinceLastFire += dt;
|
||||||
|
ComponentWrapper& cAssaultWeapon = m_Player["AssaultWeapon"];
|
||||||
if (m_TimeSinceLastFire >= 1.0 / ((double)cAssaultWeapon["RPM"] / 60.0)) {
|
if (m_TimeSinceLastFire >= 1.0 / ((double)cAssaultWeapon["RPM"] / 60.0)) {
|
||||||
fireRound();
|
fireRound();
|
||||||
}
|
}
|
||||||
@@ -53,6 +71,13 @@ void AssaultWeaponBehaviour::Update(double dt)
|
|||||||
if (!m_Firing && !m_Reloading) {
|
if (!m_Firing && !m_Reloading) {
|
||||||
playIdleAnimation();
|
playIdleAnimation();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Disable glow map on weapon if it's out of ammo
|
||||||
|
// Make real first person weapon model visible again
|
||||||
|
EntityWrapper firstPersonWeaponModel = m_Player.FirstChildByName("WeaponModel");
|
||||||
|
if (firstPersonWeaponModel.Valid()) {
|
||||||
|
firstPersonWeaponModel["Model"]["GlowMap"] = hasAmmo();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
bool AssaultWeaponBehaviour::OnAnimationComplete(Events::AnimationComplete& e)
|
bool AssaultWeaponBehaviour::OnAnimationComplete(Events::AnimationComplete& e)
|
||||||
@@ -70,9 +95,20 @@ bool AssaultWeaponBehaviour::OnAnimationComplete(Events::AnimationComplete& e)
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool AssaultWeaponBehaviour::hasAmmo()
|
||||||
|
{
|
||||||
|
ComponentWrapper& cAssaultWeapon = m_Player["AssaultWeapon"];
|
||||||
|
int& magAmmo = cAssaultWeapon["MagazineAmmo"];
|
||||||
|
return magAmmo > 0;
|
||||||
|
}
|
||||||
|
|
||||||
void AssaultWeaponBehaviour::fireRound()
|
void AssaultWeaponBehaviour::fireRound()
|
||||||
{
|
{
|
||||||
ComponentWrapper& cAssaultWeapon = m_Entity["AssaultWeapon"];
|
if (m_Reloading) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
ComponentWrapper& cAssaultWeapon = m_Player["AssaultWeapon"];
|
||||||
|
|
||||||
int& magAmmo = cAssaultWeapon["MagazineAmmo"];
|
int& magAmmo = cAssaultWeapon["MagazineAmmo"];
|
||||||
int ammo = cAssaultWeapon["Ammo"];
|
int ammo = cAssaultWeapon["Ammo"];
|
||||||
@@ -88,6 +124,11 @@ void AssaultWeaponBehaviour::fireRound()
|
|||||||
spawnTracer();
|
spawnTracer();
|
||||||
playSound();
|
playSound();
|
||||||
viewPunch();
|
viewPunch();
|
||||||
|
playShootAnimation();
|
||||||
|
bool hit = shoot(cAssaultWeapon["BaseDamage"]);
|
||||||
|
if (hit) {
|
||||||
|
showHitMarker();
|
||||||
|
}
|
||||||
|
|
||||||
m_TimeSinceLastFire = 0.0;
|
m_TimeSinceLastFire = 0.0;
|
||||||
}
|
}
|
||||||
@@ -99,25 +140,32 @@ void AssaultWeaponBehaviour::spawnTracer()
|
|||||||
}
|
}
|
||||||
|
|
||||||
EntityWrapper spawner;
|
EntityWrapper spawner;
|
||||||
if (m_Entity == LocalPlayer) {
|
if (m_Player == LocalPlayer) {
|
||||||
spawner = m_Entity.FirstChildByName("WeaponMuzzle");
|
spawner = m_Player.FirstChildByName("WeaponMuzzle");
|
||||||
} else {
|
} else {
|
||||||
spawner = m_Entity.FirstChildByName("ThirdPersonWeaponMuzzle");
|
spawner = m_Player.FirstChildByName("ThirdPersonWeaponMuzzle");
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!spawner.Valid()) {
|
if (!spawner.Valid()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
Events::SpawnerSpawn e;
|
float distance = traceRayDistance(Transform::AbsolutePosition(spawner), Transform::AbsoluteOrientation(spawner) * glm::vec3(0, 0, -1));
|
||||||
e.Spawner = spawner;
|
EntityWrapper ray = SpawnerSystem::Spawn(spawner);
|
||||||
m_EventBroker->Publish(e);
|
((glm::vec3&)ray["Transform"]["Scale"]).z = (distance / 100.f);
|
||||||
}
|
}
|
||||||
|
|
||||||
float AssaultWeaponBehaviour::traceRayDistance(glm::vec3 origin, glm::vec3 direction)
|
float AssaultWeaponBehaviour::traceRayDistance(glm::vec3 origin, glm::vec3 direction)
|
||||||
{
|
{
|
||||||
// TODO: Cast a ray and size tracer appropriately
|
// TODO: Cast a ray and size tracer appropriately
|
||||||
return 100.f;
|
float distance;
|
||||||
|
glm::vec3 pos;
|
||||||
|
auto entity = Collision::EntityFirstHitByRay(Ray(origin, direction), m_CollisionOctree, distance, pos);
|
||||||
|
if (entity) {
|
||||||
|
return distance;
|
||||||
|
} else {
|
||||||
|
return 100.f;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void AssaultWeaponBehaviour::playSound()
|
void AssaultWeaponBehaviour::playSound()
|
||||||
@@ -127,32 +175,52 @@ void AssaultWeaponBehaviour::playSound()
|
|||||||
}
|
}
|
||||||
|
|
||||||
Events::PlaySoundOnEntity e;
|
Events::PlaySoundOnEntity e;
|
||||||
e.EmitterID = m_Entity.ID;
|
e.EmitterID = m_Player.ID;
|
||||||
e.FilePath = "Audio/laser/laser1.wav";
|
e.FilePath = "Audio/laser/laser1.wav";
|
||||||
m_EventBroker->Publish(e);
|
m_EventBroker->Publish(e);
|
||||||
}
|
}
|
||||||
|
|
||||||
void AssaultWeaponBehaviour::viewPunch()
|
void AssaultWeaponBehaviour::viewPunch()
|
||||||
{
|
{
|
||||||
EntityWrapper playerCamera = m_Entity.FirstChildByName("Camera");
|
EntityWrapper playerCamera = m_Player.FirstChildByName("Camera");
|
||||||
if (!playerCamera.Valid()) {
|
if (!playerCamera.Valid()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
float viewPunch = m_Entity["AssaultWeapon"]["ViewPunch"];
|
float viewPunch = m_Player["AssaultWeapon"]["ViewPunch"];
|
||||||
ComponentWrapper cTransform = playerCamera["Transform"];
|
ComponentWrapper cTransform = playerCamera["Transform"];
|
||||||
glm::vec3& orientation = cTransform["Orientation"];
|
glm::vec3& orientation = cTransform["Orientation"];
|
||||||
orientation.x += viewPunch;
|
orientation.x += viewPunch;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void AssaultWeaponBehaviour::finishReload()
|
||||||
|
{
|
||||||
|
ComponentWrapper& cAssaultWeapon = m_Player["AssaultWeapon"];
|
||||||
|
int& magAmmo = cAssaultWeapon["MagazineAmmo"];
|
||||||
|
int magSize = cAssaultWeapon["MagazineSize"];
|
||||||
|
int& ammo = cAssaultWeapon["Ammo"];
|
||||||
|
|
||||||
|
// Throw away rounds in magazine to incentivise ammo sharing
|
||||||
|
int toLoad = glm::min(magSize, ammo);
|
||||||
|
magAmmo = toLoad;
|
||||||
|
ammo -= toLoad;
|
||||||
|
|
||||||
|
// Make real first person weapon model visible again
|
||||||
|
EntityWrapper firstPersonWeaponModel = m_Player.FirstChildByName("WeaponModel");
|
||||||
|
firstPersonWeaponModel["Model"]["Visible"] = true;
|
||||||
|
|
||||||
|
m_Reloading = false;
|
||||||
|
}
|
||||||
|
|
||||||
void AssaultWeaponBehaviour::playShootAnimation()
|
void AssaultWeaponBehaviour::playShootAnimation()
|
||||||
{
|
{
|
||||||
EntityWrapper firstPersonWeapon = m_Entity.FirstChildByName("Hands");
|
ComponentWrapper cAnimation = m_FirstPersonModel["Animation"];
|
||||||
ComponentWrapper cAnimation = firstPersonWeapon["Animation"];
|
if (cAnimation["AnimationName1"] != "ShootRifle") {
|
||||||
cAnimation["AnimationName1"] = "ShootRifle";
|
cAnimation["AnimationName1"] = "ShootRifle";
|
||||||
cAnimation["Weight1"] = 1.0;
|
cAnimation["Weight1"] = 1.0;
|
||||||
cAnimation["Time1"] = 0.0;
|
cAnimation["Time1"] = 0.0;
|
||||||
cAnimation["Speed1"] = 1.0;
|
cAnimation["Speed1"] = 1.0;
|
||||||
cAnimation["Loop1"] = true;
|
cAnimation["Loop1"] = true;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void AssaultWeaponBehaviour::playIdleAnimation()
|
void AssaultWeaponBehaviour::playIdleAnimation()
|
||||||
@@ -168,11 +236,11 @@ void AssaultWeaponBehaviour::playIdleAnimation()
|
|||||||
std::string animationToPlay = "Idle";
|
std::string animationToPlay = "Idle";
|
||||||
double speedToSet = 1.0;
|
double speedToSet = 1.0;
|
||||||
|
|
||||||
ComponentWrapper cPlayer = m_Entity["Player"];
|
ComponentWrapper cPlayer = m_Player["Player"];
|
||||||
glm::vec3 movementDirection = cPlayer["CurrentWishDirection"];
|
glm::vec3 movementDirection = cPlayer["CurrentWishDirection"];
|
||||||
if (glm::length2(movementDirection) > 0) {
|
if (glm::length2(movementDirection) > 0) {
|
||||||
animationToPlay = "Run";
|
animationToPlay = "Run";
|
||||||
ComponentWrapper cPhysics = m_Entity["Physics"];
|
ComponentWrapper cPhysics = m_Player["Physics"];
|
||||||
speedToSet = glm::length((glm::vec3)cPhysics["Velocity"]) / (float)cPlayer["MovementSpeed"];
|
speedToSet = glm::length((glm::vec3)cPhysics["Velocity"]) / (float)cPlayer["MovementSpeed"];
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -188,3 +256,85 @@ void AssaultWeaponBehaviour::playIdleAnimation()
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void AssaultWeaponBehaviour::playReloadAnimation()
|
||||||
|
{
|
||||||
|
// Play animation
|
||||||
|
ComponentWrapper cAnimation = m_FirstPersonModel["Animation"];
|
||||||
|
cAnimation["AnimationName1"] = "ReloadSwitch";
|
||||||
|
cAnimation["Weight1"] = 1.0;
|
||||||
|
cAnimation["Time1"] = 0.0;
|
||||||
|
cAnimation["Speed1"] = 0.5;
|
||||||
|
cAnimation["Loop1"] = true;
|
||||||
|
|
||||||
|
// Hide weapon model and spawn the exploding version
|
||||||
|
EntityWrapper firstPersonWeaponModel = m_Player.FirstChildByName("WeaponModel");
|
||||||
|
EntityWrapper reloadSpawner = m_Player.FirstChildByName("FirstPersonReloadSpawner");
|
||||||
|
m_ReloadImpersonator = SpawnerSystem::Spawn(reloadSpawner, reloadSpawner);
|
||||||
|
firstPersonWeaponModel["Model"].Copy(m_ReloadImpersonator["Model"]);
|
||||||
|
firstPersonWeaponModel["Model"]["Visible"] = false;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool AssaultWeaponBehaviour::shoot(double damage)
|
||||||
|
{
|
||||||
|
// Only do shooting clientside
|
||||||
|
if (!IsClient) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Only handle shooting for the local player
|
||||||
|
if (m_Player != LocalPlayer) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Make sure the player isn't shooting from the grave
|
||||||
|
if (!m_Player.Valid()) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Screen center, based on current resolution!
|
||||||
|
Rectangle screenResolution = m_Renderer->GetViewportSize();
|
||||||
|
glm::vec2 centerScreen = glm::vec2(screenResolution.Width / 2, screenResolution.Height / 2);
|
||||||
|
|
||||||
|
// Pick middle of screen
|
||||||
|
PickData pickData = m_Renderer->Pick(centerScreen);
|
||||||
|
if (pickData.Entity == EntityID_Invalid) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
EntityWrapper victim(m_World, pickData.Entity);
|
||||||
|
|
||||||
|
// Don't let us shoot ourselves in the foot
|
||||||
|
if (victim == LocalPlayer) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Only care about players being hit
|
||||||
|
if (!victim.HasComponent("Player")) {
|
||||||
|
victim = victim.FirstParentWithComponent("Player");
|
||||||
|
}
|
||||||
|
if (!victim.Valid()) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check for friendly fire
|
||||||
|
if ((ComponentInfo::EnumType)victim["Team"]["Team"] == (ComponentInfo::EnumType)m_Player["Team"]["Team"]) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Deal damage!
|
||||||
|
Events::PlayerDamage ePlayerDamage;
|
||||||
|
ePlayerDamage.Victim = victim;
|
||||||
|
ePlayerDamage.Damage = damage;
|
||||||
|
m_EventBroker->Publish(ePlayerDamage);
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
void AssaultWeaponBehaviour::showHitMarker()
|
||||||
|
{
|
||||||
|
// Show hit marker
|
||||||
|
EntityWrapper hitMarkerSpawner = m_Player.FirstChildByName("HitMarkerSpawner");
|
||||||
|
if (hitMarkerSpawner.Valid()) {
|
||||||
|
SpawnerSystem::Spawn(hitMarkerSpawner, hitMarkerSpawner);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|||||||
@@ -8,7 +8,6 @@ WeaponSystem::WeaponSystem(SystemParams params, IRenderer* renderer, Octree<Enti
|
|||||||
, m_CollisionOctree(collisionOctree)
|
, m_CollisionOctree(collisionOctree)
|
||||||
{
|
{
|
||||||
EVENT_SUBSCRIBE_MEMBER(m_EInputCommand, &WeaponSystem::OnInputCommand);
|
EVENT_SUBSCRIBE_MEMBER(m_EInputCommand, &WeaponSystem::OnInputCommand);
|
||||||
EVENT_SUBSCRIBE_MEMBER(m_EShoot, &WeaponSystem::OnShoot);
|
|
||||||
EVENT_SUBSCRIBE_MEMBER(m_EPlayerSpawned, &WeaponSystem::OnPlayerSpawned);
|
EVENT_SUBSCRIBE_MEMBER(m_EPlayerSpawned, &WeaponSystem::OnPlayerSpawned);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -60,6 +59,14 @@ bool WeaponSystem::OnInputCommand(Events::InputCommand& e)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Reload
|
||||||
|
if (e.Command == "Reload" && e.Value != 0) {
|
||||||
|
if (m_ActiveWeapons.find(player) != m_ActiveWeapons.end()) {
|
||||||
|
auto weapon = m_ActiveWeapons.at(player);
|
||||||
|
weapon->Reload();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -69,7 +76,7 @@ void WeaponSystem::selectWeapon(EntityWrapper player, ComponentInfo::EnumType sl
|
|||||||
if (slot == 1) {
|
if (slot == 1) {
|
||||||
// TODO: if class...
|
// TODO: if class...
|
||||||
if (m_ActiveWeapons.count(player) == 0) {
|
if (m_ActiveWeapons.count(player) == 0) {
|
||||||
m_ActiveWeapons.insert(std::make_pair(player, std::make_shared<AssaultWeaponBehaviour>(m_SystemParams, m_CollisionOctree, player)));
|
m_ActiveWeapons.insert(std::make_pair(player, std::make_shared<AssaultWeaponBehaviour>(m_SystemParams, m_Renderer, m_CollisionOctree, player)));
|
||||||
} else {
|
} else {
|
||||||
//m_ActiveWeapons.erase(player);
|
//m_ActiveWeapons.erase(player);
|
||||||
}
|
}
|
||||||
@@ -87,52 +94,3 @@ bool WeaponSystem::OnPlayerSpawned(Events::PlayerSpawned& e)
|
|||||||
// TODO: Select the active one specified by player component
|
// TODO: Select the active one specified by player component
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool WeaponSystem::OnShoot(Events::Shoot& eShoot)
|
|
||||||
{
|
|
||||||
if (!eShoot.Player.Valid()) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Only run further picking code for the local player!
|
|
||||||
if (eShoot.Player != LocalPlayer) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Screen center, based on current resolution!
|
|
||||||
// TODO: check if player has enough ammo and if weapon has a cooldown or not
|
|
||||||
Rectangle screenResolution = m_Renderer->GetViewportSize();
|
|
||||||
glm::vec2 centerScreen = glm::vec2(screenResolution.Width / 2, screenResolution.Height / 2);
|
|
||||||
|
|
||||||
// TODO: check if player has enough ammo and if weapon has a cooldown or not
|
|
||||||
|
|
||||||
// Pick middle of screen
|
|
||||||
PickData pickData = m_Renderer->Pick(centerScreen);
|
|
||||||
if (pickData.Entity == EntityID_Invalid) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
EntityWrapper player(m_World, pickData.Entity);
|
|
||||||
|
|
||||||
// Only care about players being hit
|
|
||||||
if (!player.HasComponent("Player")) {
|
|
||||||
player = player.FirstParentWithComponent("Player");
|
|
||||||
}
|
|
||||||
if (!player.Valid()) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Check for friendly fire
|
|
||||||
EntityWrapper shooter = eShoot.Player;
|
|
||||||
if ((ComponentInfo::EnumType)player["Team"]["Team"] == (ComponentInfo::EnumType)shooter["Team"]["Team"]) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// TODO: Weapon damage calculations etc
|
|
||||||
Events::PlayerDamage ePlayerDamage;
|
|
||||||
ePlayerDamage.Player = player;
|
|
||||||
ePlayerDamage.Damage = 100;
|
|
||||||
m_EventBroker->Publish(ePlayerDamage);
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
@@ -71,7 +71,7 @@ GameHealthSystemTest::GameHealthSystemTest()
|
|||||||
//damage player with 50
|
//damage player with 50
|
||||||
Events::PlayerDamage e;
|
Events::PlayerDamage e;
|
||||||
e.Damage = 50.0f;
|
e.Damage = 50.0f;
|
||||||
e.Player = EntityWrapper(m_World, player.EntityID);
|
e.Victim = EntityWrapper(m_World, player.EntityID);
|
||||||
m_EventBroker->Publish(e);
|
m_EventBroker->Publish(e);
|
||||||
|
|
||||||
//heal some other player with 40
|
//heal some other player with 40
|
||||||
|
|||||||
Reference in New Issue
Block a user