Add in inherited class structure for effects, so effects can have customized behaviors.

pull/28/head
sigonasr2 1 year ago
parent 93cf655a40
commit 0dfb58a777
  1. 28
      Crawler/Animation.cpp
  2. 3
      Crawler/Animation.h
  3. 7
      Crawler/Class.cpp
  4. 61
      Crawler/Crawler.cpp
  5. 12
      Crawler/Crawler.h
  6. 1
      Crawler/Crawler.vcxproj
  7. 6
      Crawler/Crawler.vcxproj.filters
  8. 2
      Crawler/Effect.cpp
  9. 10
      Crawler/Effect.h
  10. 6
      Crawler/EnergyBolt.cpp
  11. 8
      Crawler/FireBolt.cpp
  12. 14
      Crawler/LightningBolt.cpp
  13. 4
      Crawler/LightningBoltEmitter.cpp
  14. 20
      Crawler/Meteor.cpp
  15. 6
      Crawler/Player.cpp
  16. 1
      Crawler/Player.h
  17. 3
      Crawler/State.h
  18. 2
      Crawler/Version.h
  19. BIN
      Crawler/assets/c30010.png
  20. BIN
      Crawler/assets/meteor.png
  21. BIN
      Crawler/assets/meteor.xcf
  22. BIN
      Crawler/assets/nico-wizard.png
  23. BIN
      Crawler/assets/nico-wizard.xcf

@ -189,6 +189,26 @@ void sig::Animation::InitializeAnimations(){
} }
} }
ANIMATION_DATA[AnimationState::WIZARD_ATTACK_N]=pl_wizard_attack_n; ANIMATION_DATA[AnimationState::WIZARD_ATTACK_N]=pl_wizard_attack_n;
Animate2D::FrameSequence pl_wizard_cast_s(0.1);
for(int i=0;i<2;i++){
pl_wizard_cast_s.AddFrame({&game->GFX_Wizard_Sheet,{vi2d{7+i,0}*24,{24,24}}});
}
ANIMATION_DATA[AnimationState::WIZARD_CAST_S]=pl_wizard_cast_s;
Animate2D::FrameSequence pl_wizard_cast_e(0.1);
for(int i=0;i<2;i++){
pl_wizard_cast_e.AddFrame({&game->GFX_Wizard_Sheet,{vi2d{7+i,3}*24,{24,24}}});
}
ANIMATION_DATA[AnimationState::WIZARD_CAST_E]=pl_wizard_cast_e;
Animate2D::FrameSequence pl_wizard_cast_n(0.1);
for(int i=0;i<2;i++){
pl_wizard_cast_n.AddFrame({&game->GFX_Wizard_Sheet,{vi2d{7+i,1}*24,{24,24}}});
}
ANIMATION_DATA[AnimationState::WIZARD_CAST_N]=pl_wizard_cast_n;
Animate2D::FrameSequence pl_wizard_cast_w(0.1);
for(int i=0;i<2;i++){
pl_wizard_cast_w.AddFrame({&game->GFX_Wizard_Sheet,{vi2d{7+i,2}*24,{24,24}}});
}
ANIMATION_DATA[AnimationState::WIZARD_CAST_W]=pl_wizard_cast_w;
//Load slime animations. //Load slime animations.
for(int slime=0;slime<4;slime++){ for(int slime=0;slime<4;slime++){
@ -271,6 +291,10 @@ void sig::Animation::InitializeAnimations(){
lightningsplash.AddFrame({&game->GFX_LightningSplash,{{i*24,0},{24,24}}}); lightningsplash.AddFrame({&game->GFX_LightningSplash,{{i*24,0},{24,24}}});
} }
ANIMATION_DATA[AnimationState::LIGHTNING_SPLASH]=lightningsplash; ANIMATION_DATA[AnimationState::LIGHTNING_SPLASH]=lightningsplash;
Animate2D::FrameSequence meteor;
meteor.AddFrame({&game->GFX_Meteor,{{0,0},{192,192}}});
ANIMATION_DATA[AnimationState::METEOR]=meteor;
} }
void sig::Animation::SetupPlayerAnimations(){ void sig::Animation::SetupPlayerAnimations(){
@ -314,4 +338,8 @@ void sig::Animation::SetupPlayerAnimations(){
game->player.AddAnimation(AnimationState::WIZARD_ATTACK_E); game->player.AddAnimation(AnimationState::WIZARD_ATTACK_E);
game->player.AddAnimation(AnimationState::WIZARD_ATTACK_S); game->player.AddAnimation(AnimationState::WIZARD_ATTACK_S);
game->player.AddAnimation(AnimationState::WIZARD_ATTACK_W); game->player.AddAnimation(AnimationState::WIZARD_ATTACK_W);
game->player.AddAnimation(AnimationState::WIZARD_CAST_N);
game->player.AddAnimation(AnimationState::WIZARD_CAST_E);
game->player.AddAnimation(AnimationState::WIZARD_CAST_S);
game->player.AddAnimation(AnimationState::WIZARD_CAST_W);
} }

@ -19,7 +19,8 @@ enum AnimationState{
WIZARD_ATTACK_S,WIZARD_ATTACK_E,WIZARD_ATTACK_N,WIZARD_ATTACK_W, WIZARD_ATTACK_S,WIZARD_ATTACK_E,WIZARD_ATTACK_N,WIZARD_ATTACK_W,
ENERGY_BOLT,ENERGY_PARTICLE,SPLASH_EFFECT,DOT_PARTICLE, ENERGY_BOLT,ENERGY_PARTICLE,SPLASH_EFFECT,DOT_PARTICLE,
LIGHTNING_BOLT,LIGHTNING_BOLT_PARTICLE1,LIGHTNING_BOLT_PARTICLE2,LIGHTNING_BOLT_PARTICLE3,LIGHTNING_BOLT_PARTICLE4, LIGHTNING_BOLT,LIGHTNING_BOLT_PARTICLE1,LIGHTNING_BOLT_PARTICLE2,LIGHTNING_BOLT_PARTICLE3,LIGHTNING_BOLT_PARTICLE4,
CHAIN_LIGHTNING,LIGHTNING_SPLASH CHAIN_LIGHTNING,LIGHTNING_SPLASH,
WIZARD_CAST_S,WIZARD_CAST_N,WIZARD_CAST_E,WIZARD_CAST_W,METEOR,
}; };
namespace sig{ namespace sig{

@ -102,7 +102,7 @@ bool Warrior::AutoAttack(){
bool Warrior::Ability1(){ bool Warrior::Ability1(){
ACCESS_PLAYER ACCESS_PLAYER
game->AddEffect(Effect(p.pos,0.1,AnimationState::BATTLECRY_EFFECT,p.upperLevel,1,0.3)); game->AddEffect(std::make_unique<Effect>(p.pos,0.1,AnimationState::BATTLECRY_EFFECT,p.upperLevel,1,0.3));
p.AddBuff(BuffType::ATTACK_UP,10,0.1); p.AddBuff(BuffType::ATTACK_UP,10,0.1);
p.AddBuff(BuffType::DAMAGE_REDUCTION,10,0.1); p.AddBuff(BuffType::DAMAGE_REDUCTION,10,0.1);
for(Monster&m:MONSTER_LIST){ for(Monster&m:MONSTER_LIST){
@ -302,6 +302,9 @@ bool Wizard::Ability2(){
} }
bool Wizard::Ability3(){ bool Wizard::Ability3(){
ACCESS_PLAYER
p.SetState(State::CASTING);
game->AddEffect(std::make_unique<Meteor>(p.GetPos(),3,AnimationState::METEOR,p.OnUpperLevel(),vf2d{1,1},2));
return true; return true;
} }
@ -323,7 +326,7 @@ bool Wizard::RightClickAbility(){
p.teleportStartPosition=p.GetPos(); p.teleportStartPosition=p.GetPos();
p.iframe_time=0.35; p.iframe_time=0.35;
for(int i=0;i<16;i++){ for(int i=0;i<16;i++){
game->AddEffect(Effect(p.GetPos()+vf2d{(rand()%160-80)/10.f,(rand()%160-80)/10.f},float(rand()%300)/1000,AnimationState::DOT_PARTICLE,p.upperLevel,0.3,0.2,{float(rand()%1000-500)/100,float(rand()%1000-500)/100},BLACK)); game->AddEffect(std::make_unique<Effect>(p.GetPos()+vf2d{(rand()%160-80)/10.f,(rand()%160-80)/10.f},float(rand()%300)/1000,AnimationState::DOT_PARTICLE,p.upperLevel,0.3,0.2,vf2d{float(rand()%1000-500)/100,float(rand()%1000-500)/100},BLACK));
} }
return true; return true;
} else { } else {

@ -78,6 +78,7 @@ bool Crawler::OnUserCreate(){
GFX_LightningBoltParticle4.Load("assets/lightning_bolt_part4.png"); GFX_LightningBoltParticle4.Load("assets/lightning_bolt_part4.png");
GFX_ChainLightning.Load("assets/chain_lightning.png"); GFX_ChainLightning.Load("assets/chain_lightning.png");
GFX_LightningSplash.Load("assets/lightning_splash_effect.png"); GFX_LightningSplash.Load("assets/lightning_splash_effect.png");
GFX_Meteor.Load("assets/meteor.png");
//Animations //Animations
sig::Animation::InitializeAnimations(); sig::Animation::InitializeAnimations();
@ -163,7 +164,7 @@ void Crawler::HandleUserInput(float fElapsedTime){
}break; }break;
} }
} }
if(player.GetVelocity()==vf2d{0,0}){ if(player.GetVelocity()==vf2d{0,0}&&player.CanMove()){
auto GetPlayerStaircaseDirection=[&](){ auto GetPlayerStaircaseDirection=[&](){
for(LayerTag&layer:MAP_DATA[GetCurrentLevel()].LayerData){ for(LayerTag&layer:MAP_DATA[GetCurrentLevel()].LayerData){
int truncatedPlayerX=int(player.GetX())/24; int truncatedPlayerX=int(player.GetX())/24;
@ -308,6 +309,24 @@ void Crawler::HandleUserInput(float fElapsedTime){
} }
} }
if(player.GetState()==State::CASTING){
setIdleAnimation=false;
switch(player.GetFacingDirection()){
case UP:{
player.UpdateAnimation(AnimationState::WIZARD_CAST_N);
}break;
case DOWN:{
player.UpdateAnimation(AnimationState::WIZARD_CAST_S);
}break;
case LEFT:{
player.UpdateAnimation(AnimationState::WIZARD_CAST_W);
}break;
case RIGHT:{
player.UpdateAnimation(AnimationState::WIZARD_CAST_E);
}break;
}
}
if(player.GetState()!=State::NORMAL){ if(player.GetState()!=State::NORMAL){
setIdleAnimation=false; setIdleAnimation=false;
} }
@ -365,18 +384,18 @@ void Crawler::UpdateEffects(float fElapsedTime){
} }
} }
} }
for(std::vector<Effect>::iterator it=backgroundEffects.begin();it!=backgroundEffects.end();++it){ for(std::vector<std::unique_ptr<Effect>>::iterator it=backgroundEffects.begin();it!=backgroundEffects.end();++it){
Effect&e=*it; Effect*e=(*it).get();
if(!e.Update(fElapsedTime)){ if(!e->Update(fElapsedTime)){
it=backgroundEffects.erase(it); it=backgroundEffects.erase(it);
if(it==backgroundEffects.end()){ if(it==backgroundEffects.end()){
break; break;
} }
} }
} }
for(std::vector<Effect>::iterator it=foregroundEffects.begin();it!=foregroundEffects.end();++it){ for(std::vector<std::unique_ptr<Effect>>::iterator it=foregroundEffects.begin();it!=foregroundEffects.end();++it){
Effect&e=*it; Effect*e=(*it).get();
if(!e.Update(fElapsedTime)){ if(!e->Update(fElapsedTime)){
it=foregroundEffects.erase(it); it=foregroundEffects.erase(it);
if(it==foregroundEffects.end()){ if(it==foregroundEffects.end()){
break; break;
@ -479,19 +498,19 @@ void Crawler::PopulateRenderLists(std::vector<Monster*>&monstersBeforeLower,std:
} }
} }
for(auto it=foregroundEffects.begin();it!=foregroundEffects.end();++it){ for(auto it=foregroundEffects.begin();it!=foregroundEffects.end();++it){
Effect&e=*it; Effect*e=(*it).get();
if(e.OnUpperLevel()){ if(e->OnUpperLevel()){
foregroundEffectsUpper.push_back(&e); foregroundEffectsUpper.push_back(e);
}else{ }else{
foregroundEffectsLower.push_back(&e); foregroundEffectsLower.push_back(e);
} }
} }
for(auto it=backgroundEffects.begin();it!=backgroundEffects.end();++it){ for(auto it=backgroundEffects.begin();it!=backgroundEffects.end();++it){
Effect&e=*it; Effect*e=(*it).get();
if(e.OnUpperLevel()){ if(e->OnUpperLevel()){
backgroundEffectsUpper.push_back(&e); backgroundEffectsUpper.push_back(e);
}else{ }else{
backgroundEffectsLower.push_back(&e); backgroundEffectsLower.push_back(e);
} }
} }
std::sort(monstersBeforeUpper.begin(),monstersBeforeUpper.end(),[](Monster*m1,Monster*m2){return m1->GetPos().y<m2->GetPos().y;}); std::sort(monstersBeforeUpper.begin(),monstersBeforeUpper.end(),[](Monster*m1,Monster*m2){return m1->GetPos().y<m2->GetPos().y;});
@ -748,16 +767,16 @@ void Crawler::RenderHud(){
#endif #endif
} }
void Crawler::AddEffect(Effect foreground,Effect background){ void Crawler::AddEffect(std::unique_ptr<Effect>foreground,std::unique_ptr<Effect> background){
foregroundEffects.push_back(foreground); foregroundEffects.push_back(std::move(foreground));
backgroundEffects.push_back(background); backgroundEffects.push_back(std::move(background));
} }
void Crawler::AddEffect(Effect foreground,bool back){ void Crawler::AddEffect(std::unique_ptr<Effect> foreground,bool back){
if(back){ if(back){
backgroundEffects.push_back(foreground); backgroundEffects.push_back(std::move(foreground));
} else { } else {
foregroundEffects.push_back(foreground); foregroundEffects.push_back(std::move(foreground));
} }
} }

@ -21,18 +21,18 @@ class Crawler : public olc::PixelGameEngine
friend class sig::Animation; friend class sig::Animation;
Camera2D camera; Camera2D camera;
Player player; Player player;
Renderable GFX_Warrior_Sheet,GFX_Slime_Sheet,GFX_Circle, Renderable GFX_Warrior_Sheet,GFX_Slime_Sheet,
GFX_Effect_GroundSlam_Back,GFX_Effect_GroundSlam_Front, GFX_Effect_GroundSlam_Back,GFX_Effect_GroundSlam_Front,
GFX_Heart,GFX_BLOCK_BUBBLE,GFX_Ranger_Sheet,GFX_Wizard_Sheet, GFX_Heart,GFX_BLOCK_BUBBLE,GFX_Ranger_Sheet,GFX_Wizard_Sheet,
GFX_Battlecry_Effect,GFX_Mana,GFX_SonicSlash,GFX_EnergyParticle, GFX_Battlecry_Effect,GFX_Mana,GFX_SonicSlash,GFX_EnergyParticle,
GFX_Splash_Effect,GFX_LightningBolt,GFX_LightningBoltParticle1, GFX_Splash_Effect,GFX_LightningBolt,GFX_LightningBoltParticle1,
GFX_LightningBoltParticle2,GFX_LightningBoltParticle3,GFX_LightningBoltParticle4, GFX_LightningBoltParticle2,GFX_LightningBoltParticle3,GFX_LightningBoltParticle4,
GFX_ChainLightning,GFX_LightningSplash; GFX_ChainLightning,GFX_LightningSplash,GFX_Meteor;
public: public:
Renderable GFX_BulletCircle,GFX_BulletCircleOutline,GFX_EnergyBolt; Renderable GFX_BulletCircle,GFX_BulletCircleOutline,GFX_EnergyBolt,GFX_Circle;
Pathfinding pathfinder; Pathfinding pathfinder;
private: private:
std::vector<Effect>foregroundEffects,backgroundEffects; std::vector<std::unique_ptr<Effect>>foregroundEffects,backgroundEffects;
std::map<MapName,Map>MAP_DATA; std::map<MapName,Map>MAP_DATA;
std::map<std::string,TilesetData>MAP_TILESETS; std::map<std::string,TilesetData>MAP_TILESETS;
vf2d worldShake={}; vf2d worldShake={};
@ -62,9 +62,9 @@ public:
void UpdateBullets(float fElapsedTime); void UpdateBullets(float fElapsedTime);
void RenderWorld(float fElapsedTime); void RenderWorld(float fElapsedTime);
void RenderHud(); void RenderHud();
void AddEffect(Effect foreground,Effect background); void AddEffect(std::unique_ptr<Effect>foreground,std::unique_ptr<Effect>background);
//If back is true, places the effect in the background //If back is true, places the effect in the background
void AddEffect(Effect foreground,bool back=false); void AddEffect(std::unique_ptr<Effect>foreground,bool back=false);
void HurtEnemies(vf2d pos,float radius,int damage,bool upperLevel); void HurtEnemies(vf2d pos,float radius,int damage,bool upperLevel);
vf2d GetWorldMousePos(); vf2d GetWorldMousePos();
bool LeftHeld(); bool LeftHeld();

@ -214,6 +214,7 @@
<ClCompile Include="LightningBolt.cpp" /> <ClCompile Include="LightningBolt.cpp" />
<ClCompile Include="LightningBoltEmitter.cpp" /> <ClCompile Include="LightningBoltEmitter.cpp" />
<ClCompile Include="Map.cpp" /> <ClCompile Include="Map.cpp" />
<ClCompile Include="Meteor.cpp" />
<ClCompile Include="Pathfinding.cpp" /> <ClCompile Include="Pathfinding.cpp" />
<ClCompile Include="pixelGameEngine.cpp" /> <ClCompile Include="pixelGameEngine.cpp" />
<ClCompile Include="Player.cpp" /> <ClCompile Include="Player.cpp" />

@ -22,6 +22,9 @@
<Filter Include="Source Files\Emitters"> <Filter Include="Source Files\Emitters">
<UniqueIdentifier>{0f85b918-f194-4114-9a10-803e204faf2e}</UniqueIdentifier> <UniqueIdentifier>{0f85b918-f194-4114-9a10-803e204faf2e}</UniqueIdentifier>
</Filter> </Filter>
<Filter Include="Source Files\Effects">
<UniqueIdentifier>{94ea6039-63ac-430d-bb96-317bf1b7a305}</UniqueIdentifier>
</Filter>
</ItemGroup> </ItemGroup>
<ItemGroup> <ItemGroup>
<ClInclude Include="olcPixelGameEngine.h"> <ClInclude Include="olcPixelGameEngine.h">
@ -164,6 +167,9 @@
<ClCompile Include="Emitter.cpp"> <ClCompile Include="Emitter.cpp">
<Filter>Source Files</Filter> <Filter>Source Files</Filter>
</ClCompile> </ClCompile>
<ClCompile Include="Meteor.cpp">
<Filter>Source Files\Effects</Filter>
</ClCompile>
</ItemGroup> </ItemGroup>
<ItemGroup> <ItemGroup>
<None Include="cpp.hint" /> <None Include="cpp.hint" />

@ -31,12 +31,12 @@ bool Effect::Update(float fElapsedTime){
void Effect::Draw(){ void Effect::Draw(){
if(additiveBlending)game->SetDecalMode(DecalMode::ADDITIVE); if(additiveBlending)game->SetDecalMode(DecalMode::ADDITIVE);
else game->SetDecalMode(DecalMode::NORMAL);
if(fadeout==0){ if(fadeout==0){
game->view.DrawPartialRotatedDecal(pos,GetFrame().GetSourceImage()->Decal(),rotation,GetFrame().GetSourceRect().size/2,GetFrame().GetSourceRect().pos,GetFrame().GetSourceRect().size,size,col); game->view.DrawPartialRotatedDecal(pos,GetFrame().GetSourceImage()->Decal(),rotation,GetFrame().GetSourceRect().size/2,GetFrame().GetSourceRect().pos,GetFrame().GetSourceRect().size,size,col);
} else { } else {
game->view.DrawPartialRotatedDecal(pos,GetFrame().GetSourceImage()->Decal(),rotation,GetFrame().GetSourceRect().size/2,GetFrame().GetSourceRect().pos,GetFrame().GetSourceRect().size,size,{col.r,col.g,col.b,uint8_t(fadeout/original_fadeoutTime*255)}); game->view.DrawPartialRotatedDecal(pos,GetFrame().GetSourceImage()->Decal(),rotation,GetFrame().GetSourceRect().size/2,GetFrame().GetSourceRect().pos,GetFrame().GetSourceRect().size,size,{col.r,col.g,col.b,uint8_t(fadeout/original_fadeoutTime*255)});
} }
game->SetDecalMode(DecalMode::NORMAL);
} }
Animate2D::Frame Effect::GetFrame(){ Animate2D::Frame Effect::GetFrame(){

@ -15,13 +15,19 @@ struct Effect{
bool additiveBlending=false; bool additiveBlending=false;
Effect(vf2d pos,float lifetime,AnimationState animation,bool upperLevel,float size=1.0f,float fadeout=0.0f,vf2d spd={},Pixel col=WHITE,float rotation=0,float rotationSpd=0,bool additiveBlending=false); Effect(vf2d pos,float lifetime,AnimationState animation,bool upperLevel,float size=1.0f,float fadeout=0.0f,vf2d spd={},Pixel col=WHITE,float rotation=0,float rotationSpd=0,bool additiveBlending=false);
Effect(vf2d pos,float lifetime,AnimationState animation,bool upperLevel,vf2d size={1,1},float fadeout=0.0f,vf2d spd={},Pixel col=WHITE,float rotation=0,float rotationSpd=0,bool additiveBlending=false); Effect(vf2d pos,float lifetime,AnimationState animation,bool upperLevel,vf2d size={1,1},float fadeout=0.0f,vf2d spd={},Pixel col=WHITE,float rotation=0,float rotationSpd=0,bool additiveBlending=false);
bool Update(float fElapsedTime); virtual bool Update(float fElapsedTime);
Animate2D::Frame GetFrame(); Animate2D::Frame GetFrame();
void Draw(); virtual void Draw();
bool OnUpperLevel(); bool OnUpperLevel();
private: private:
Animate2D::Animation<AnimationState>animation; Animate2D::Animation<AnimationState>animation;
Animate2D::AnimationState internal_animState; Animate2D::AnimationState internal_animState;
float original_fadeoutTime; float original_fadeoutTime;
bool upperLevel=false; bool upperLevel=false;
};
struct Meteor:Effect{
Meteor(vf2d pos,float lifetime,AnimationState animation,bool upperLevel,vf2d size={1,1},float fadeout=0.0f,vf2d spd={},Pixel col=WHITE,float rotation=0,float rotationSpd=0,bool additiveBlending=false);
bool Update(float fElapsedTime)override;
void Draw()override;
}; };

@ -13,7 +13,7 @@ void EnergyBolt::Update(float fElapsedTime){
lastParticleSpawn=std::max(0.f,lastParticleSpawn-fElapsedTime); lastParticleSpawn=std::max(0.f,lastParticleSpawn-fElapsedTime);
if(lastParticleSpawn==0){ if(lastParticleSpawn==0){
lastParticleSpawn=0.03; lastParticleSpawn=0.03;
game->AddEffect(Effect(pos,util::random(1),AnimationState::ENERGY_PARTICLE,upperLevel,util::random(2),0.5,{util::random(60)-30,util::random(60)-30})); game->AddEffect(std::make_unique<Effect>(pos,util::random(1),AnimationState::ENERGY_PARTICLE,upperLevel,util::random(2),0.5f,vf2d{util::random(60)-30,util::random(60)-30}));
} }
} }
@ -21,7 +21,7 @@ bool EnergyBolt::PlayerHit(Player& player)
{ {
deactivated=true; deactivated=true;
fadeOutTime=0.2f; fadeOutTime=0.2f;
game->AddEffect(Effect(player.GetPos(),0,AnimationState::SPLASH_EFFECT,upperLevel,player.GetSizeMult(),0.25)); game->AddEffect(std::make_unique<Effect>(player.GetPos(),0,AnimationState::SPLASH_EFFECT,upperLevel,player.GetSizeMult(),0.25));
return false; return false;
} }
@ -29,6 +29,6 @@ bool EnergyBolt::MonsterHit(Monster& monster)
{ {
deactivated=true; deactivated=true;
fadeOutTime=0.2f; fadeOutTime=0.2f;
game->AddEffect(Effect(monster.GetPos(),0,AnimationState::SPLASH_EFFECT,upperLevel,monster.GetSizeMult(),0.25)); game->AddEffect(std::make_unique<Effect>(monster.GetPos(),0,AnimationState::SPLASH_EFFECT,upperLevel,monster.GetSizeMult(),0.25));
return false; return false;
} }

@ -14,7 +14,7 @@ void FireBolt::Update(float fElapsedTime){
lastParticleSpawn=std::max(0.f,lastParticleSpawn-fElapsedTime); lastParticleSpawn=std::max(0.f,lastParticleSpawn-fElapsedTime);
if(lastParticleSpawn==0){ if(lastParticleSpawn==0){
lastParticleSpawn=0.03; lastParticleSpawn=0.03;
game->AddEffect(Effect(pos,util::random(1),AnimationState::ENERGY_PARTICLE,upperLevel,util::random(2),0.3,{util::random(120)-60,-util::random(60)},{255,uint8_t(util::random(250)),0})); game->AddEffect(std::make_unique<Effect>(pos,util::random(1),AnimationState::ENERGY_PARTICLE,upperLevel,util::random(2),0.3,vf2d{util::random(120)-60,-util::random(60)},Pixel{255,uint8_t(util::random(250)),0}));
} }
} }
@ -22,7 +22,7 @@ bool FireBolt::PlayerHit(Player& player)
{ {
deactivated=true; deactivated=true;
fadeOutTime=0.2f; fadeOutTime=0.2f;
game->AddEffect(Effect(player.GetPos(),0,AnimationState::SPLASH_EFFECT,upperLevel,5,0.25,{},{240,120,60})); game->AddEffect(std::make_unique<Effect>(player.GetPos(),0,AnimationState::SPLASH_EFFECT,upperLevel,5,0.25,vf2d{},Pixel{240,120,60}));
return false; return false;
} }
@ -31,7 +31,7 @@ bool FireBolt::MonsterHit(Monster& monster)
deactivated=true; deactivated=true;
fadeOutTime=0.2f; fadeOutTime=0.2f;
for(int i=0;i<72;i++){ for(int i=0;i<72;i++){
game->AddEffect(Effect(monster.GetPos(),util::random(0.5),AnimationState::DOT_PARTICLE,upperLevel,util::random(2),util::random(0.4),{util::random(300)-150,util::random(300)-150},{255,uint8_t(util::random(190)+60),60})); game->AddEffect(std::make_unique<Effect>(monster.GetPos(),util::random(0.5),AnimationState::DOT_PARTICLE,upperLevel,util::random(2),util::random(0.4),vf2d{util::random(300)-150,util::random(300)-150},Pixel{255,uint8_t(util::random(190)+60),60}));
} }
game->SetupWorldShake(0.25); game->SetupWorldShake(0.25);
for(Monster&m:MONSTER_LIST){ for(Monster&m:MONSTER_LIST){
@ -39,6 +39,6 @@ bool FireBolt::MonsterHit(Monster& monster)
m.Hurt(3*damage); m.Hurt(3*damage);
} }
} }
game->AddEffect(Effect(monster.GetPos(),0,AnimationState::SPLASH_EFFECT,upperLevel,5,0.25,{},{240,120,60})); game->AddEffect(std::make_unique<Effect>(monster.GetPos(),0,AnimationState::SPLASH_EFFECT,upperLevel,5,0.25,vf2d{},Pixel{240,120,60}));
return false; return false;
} }

@ -19,16 +19,16 @@ void LightningBolt::Update(float fElapsedTime){
uint8_t brightness=uint8_t(util::random(100)+150); uint8_t brightness=uint8_t(util::random(100)+150);
switch(rand()%4){ switch(rand()%4){
case 0:{ case 0:{
game->AddEffect(Effect(pos+vf2d{util::random(12)-6,util::random(12)-6},util::random(0.1),AnimationState::LIGHTNING_BOLT_PARTICLE1,upperLevel,util::random(0.5)+1,0.1,vel*(util::random(0.1)+0.9),{brightness,brightness,brightness})); game->AddEffect(std::make_unique<Effect>(pos+vf2d{util::random(12)-6,util::random(12)-6},util::random(0.1),AnimationState::LIGHTNING_BOLT_PARTICLE1,upperLevel,util::random(0.5)+1,0.1,vel*(util::random(0.1)+0.9),Pixel{brightness,brightness,brightness}));
}break; }break;
case 1:{ case 1:{
game->AddEffect(Effect(pos+vf2d{util::random(12)-6,util::random(12)-6},util::random(0.1),AnimationState::LIGHTNING_BOLT_PARTICLE2,upperLevel,util::random(0.5)+1,0.1,vel*(util::random(0.1)+0.9),{brightness,brightness,brightness})); game->AddEffect(std::make_unique<Effect>(pos+vf2d{util::random(12)-6,util::random(12)-6},util::random(0.1),AnimationState::LIGHTNING_BOLT_PARTICLE2,upperLevel,util::random(0.5)+1,0.1,vel*(util::random(0.1)+0.9),Pixel{brightness,brightness,brightness}));
}break; }break;
case 2:{ case 2:{
game->AddEffect(Effect(pos+vf2d{util::random(12)-6,util::random(12)-6},util::random(0.1),AnimationState::LIGHTNING_BOLT_PARTICLE3,upperLevel,util::random(0.5)+1,0.1,vel*(util::random(0.1)+0.9),{brightness,brightness,brightness})); game->AddEffect(std::make_unique<Effect>(pos+vf2d{util::random(12)-6,util::random(12)-6},util::random(0.1),AnimationState::LIGHTNING_BOLT_PARTICLE3,upperLevel,util::random(0.5)+1,0.1,vel*(util::random(0.1)+0.9),Pixel{brightness,brightness,brightness}));
}break; }break;
case 3:{ case 3:{
game->AddEffect(Effect(pos+vf2d{util::random(12)-6,util::random(12)-6},util::random(0.1),AnimationState::LIGHTNING_BOLT_PARTICLE4,upperLevel,util::random(0.5)+1,0.1,vel*(util::random(0.1)+0.9),{brightness,brightness,brightness})); game->AddEffect(std::make_unique<Effect>(pos+vf2d{util::random(12)-6,util::random(12)-6},util::random(0.1),AnimationState::LIGHTNING_BOLT_PARTICLE4,upperLevel,util::random(0.5)+1,0.1,vel*(util::random(0.1)+0.9),Pixel{brightness,brightness,brightness}));
}break; }break;
} }
} }
@ -38,7 +38,7 @@ bool LightningBolt::PlayerHit(Player& player)
{ {
deactivated=true; deactivated=true;
fadeOutTime=0.2f; fadeOutTime=0.2f;
game->AddEffect(Effect(player.GetPos(),0.3,AnimationState::LIGHTNING_SPLASH,upperLevel,player.GetSizeMult(),0.25,{},WHITE,util::random(PI))); game->AddEffect(std::make_unique<Effect>(player.GetPos(),0.3,AnimationState::LIGHTNING_SPLASH,upperLevel,player.GetSizeMult(),0.25,vf2d{},WHITE,util::random(PI)));
return false; return false;
} }
@ -46,7 +46,7 @@ bool LightningBolt::MonsterHit(Monster& monster)
{ {
deactivated=true; deactivated=true;
fadeOutTime=0.2f; fadeOutTime=0.2f;
game->AddEffect(Effect(monster.GetPos(),0.3,AnimationState::LIGHTNING_SPLASH,upperLevel,monster.GetSizeMult(),0.25,{},WHITE,util::random(PI))); game->AddEffect(std::make_unique<Effect>(monster.GetPos(),0.3,AnimationState::LIGHTNING_SPLASH,upperLevel,monster.GetSizeMult(),0.25,vf2d{},WHITE,util::random(PI)));
int targetsHit=0; int targetsHit=0;
for(Monster&m:MONSTER_LIST){ for(Monster&m:MONSTER_LIST){
if(&m==&monster||monster.OnUpperLevel()!=m.OnUpperLevel())continue; if(&m==&monster||monster.OnUpperLevel()!=m.OnUpperLevel())continue;
@ -55,7 +55,7 @@ bool LightningBolt::MonsterHit(Monster& monster)
if(dist<=72){ if(dist<=72){
if(m.Hurt(game->GetPlayer().GetAttack()*2)){ if(m.Hurt(game->GetPlayer().GetAttack()*2)){
EMITTER_LIST.push_back(std::make_unique<LightningBoltEmitter>(LightningBoltEmitter(monster.GetPos(),m.GetPos(),0.05,0.25,upperLevel))); EMITTER_LIST.push_back(std::make_unique<LightningBoltEmitter>(LightningBoltEmitter(monster.GetPos(),m.GetPos(),0.05,0.25,upperLevel)));
game->AddEffect(Effect(m.GetPos(),0.5,AnimationState::LIGHTNING_SPLASH,upperLevel,monster.GetSizeMult(),0.25,{},WHITE,util::random(PI))); game->AddEffect(std::make_unique<Effect>(m.GetPos(),0.5,AnimationState::LIGHTNING_SPLASH,upperLevel,monster.GetSizeMult(),0.25,vf2d{},WHITE,util::random(PI)));
targetsHit++; targetsHit++;
} }
} }

@ -22,7 +22,7 @@ void LightningBoltEmitter::DrawLightningBolt(){
float targetDist=lineToTarget.length()*util::random(0.5); float targetDist=lineToTarget.length()*util::random(0.5);
targetAngle+=util::random((PI/2))-PI/4; targetAngle+=util::random((PI/2))-PI/4;
geom2d::line<float>lightningLine=geom2d::line<float>(currentPos,currentPos+vf2d{cos(targetAngle)*targetDist,sin(targetAngle)*targetDist}); geom2d::line<float>lightningLine=geom2d::line<float>(currentPos,currentPos+vf2d{cos(targetAngle)*targetDist,sin(targetAngle)*targetDist});
game->AddEffect(Effect(lightningLine.upoint(0),0,AnimationState::CHAIN_LIGHTNING,upperLevel,{lightningLine.length(),0.2},0.2,{},WHITE,targetAngle,0,true)); game->AddEffect(std::make_unique<Effect>(lightningLine.upoint(0),0,AnimationState::CHAIN_LIGHTNING,upperLevel,vf2d{lightningLine.length(),0.2},0.2,vf2d{},WHITE,targetAngle,0,true));
int iterations=1; int iterations=1;
currentPos+=vf2d{cos(targetAngle)*targetDist,sin(targetAngle)*targetDist}; currentPos+=vf2d{cos(targetAngle)*targetDist,sin(targetAngle)*targetDist};
while(iterations<MAX_ITERATIONS&&geom2d::line<float>(currentPos,endPos).length()>1){ while(iterations<MAX_ITERATIONS&&geom2d::line<float>(currentPos,endPos).length()>1){
@ -31,7 +31,7 @@ void LightningBoltEmitter::DrawLightningBolt(){
float targetDist=lineToTarget.length()*util::random(0.5); float targetDist=lineToTarget.length()*util::random(0.5);
targetAngle+=util::random((PI/2))-PI/4; targetAngle+=util::random((PI/2))-PI/4;
geom2d::line<float>lightningLine=geom2d::line<float>(currentPos,currentPos+vf2d{cos(targetAngle)*targetDist,sin(targetAngle)*targetDist}); geom2d::line<float>lightningLine=geom2d::line<float>(currentPos,currentPos+vf2d{cos(targetAngle)*targetDist,sin(targetAngle)*targetDist});
game->AddEffect(Effect(lightningLine.upoint(0),0,AnimationState::CHAIN_LIGHTNING,upperLevel,{lightningLine.length(),0.2},0.2,{},WHITE,targetAngle,0,true)); game->AddEffect(std::make_unique<Effect>(lightningLine.upoint(0),0,AnimationState::CHAIN_LIGHTNING,upperLevel,vf2d{lightningLine.length(),0.2},0.2,vf2d{},WHITE,targetAngle,0,true));
currentPos+=vf2d{cos(targetAngle)*targetDist,sin(targetAngle)*targetDist}; currentPos+=vf2d{cos(targetAngle)*targetDist,sin(targetAngle)*targetDist};
iterations++; iterations++;
} }

@ -0,0 +1,20 @@
#include "Effect.h"
#include "DEFINES.h"
#include "Crawler.h"
INCLUDE_game
Meteor::Meteor(vf2d pos, float lifetime, AnimationState animation, bool upperLevel, vf2d size, float fadeout, vf2d spd, Pixel col, float rotation, float rotationSpd, bool additiveBlending)
:Effect(pos,lifetime,animation,upperLevel,size,fadeout,spd,col,rotation,rotationSpd,additiveBlending){
}
bool Meteor::Update(float fElapsedTime){
return Effect::Update(fElapsedTime);
}
void Meteor::Draw(){
vf2d scale=vf2d{192,64}/3.f;
vf2d centerPoint=pos-vf2d{game->GFX_Circle.Sprite()->width*scale.x/2,game->GFX_Circle.Sprite()->height*scale.y/2};
game->view.DrawDecal(centerPoint,game->GFX_Circle.Decal(),scale,BLACK);
}

@ -209,7 +209,7 @@ void Player::Update(float fElapsedTime){
z=0; z=0;
float numb=4; float numb=4;
game->HurtEnemies(pos,3*12,GetAttack()*2.5,OnUpperLevel()); game->HurtEnemies(pos,3*12,GetAttack()*2.5,OnUpperLevel());
game->AddEffect(Effect{GetPos(),0.5,AnimationState::GROUND_SLAM_ATTACK_FRONT,upperLevel,1.33f,0.6f},Effect{GetPos(),0.5,AnimationState::GROUND_SLAM_ATTACK_BACK,upperLevel,1.33f,0.6f}); game->AddEffect(std::make_unique<Effect>(GetPos(),0.5,AnimationState::GROUND_SLAM_ATTACK_FRONT,upperLevel,1.33f,0.6f),std::make_unique<Effect>(GetPos(),0.5,AnimationState::GROUND_SLAM_ATTACK_BACK,upperLevel,1.33f,0.6f));
} }
if(lastAnimationFlip>0){ if(lastAnimationFlip>0){
lastAnimationFlip=std::max(0.f,lastAnimationFlip-fElapsedTime); lastAnimationFlip=std::max(0.f,lastAnimationFlip-fElapsedTime);
@ -346,6 +346,10 @@ vf2d Player::GetVelocity(){
return vel; return vel;
} }
bool Player::CanMove(){
return state!=State::CASTING;
}
bool Player::HasIframes(){ bool Player::HasIframes(){
return iframe_time>0; return iframe_time>0;
} }

@ -93,6 +93,7 @@ struct Player{
void UpdateIdleAnimation(Key direction); void UpdateIdleAnimation(Key direction);
//The range is the search range in tiles. //The range is the search range in tiles.
bool CanPathfindTo(vf2d pos,vf2d targetPos,float range=8); bool CanPathfindTo(vf2d pos,vf2d targetPos,float range=8);
bool CanMove();
void AddBuff(BuffType type,float duration,float intensity); void AddBuff(BuffType type,float duration,float intensity);
std::vector<Buff>GetBuffs(BuffType buff); std::vector<Buff>GetBuffs(BuffType buff);

@ -9,5 +9,6 @@ enum State{
MOVE_AWAY, MOVE_AWAY,
BLOCK, BLOCK,
TELEPORT, TELEPORT,
PATH_AROUND PATH_AROUND,
CASTING
}; };

@ -2,7 +2,7 @@
#define VERSION_MAJOR 0 #define VERSION_MAJOR 0
#define VERSION_MINOR 2 #define VERSION_MINOR 2
#define VERSION_PATCH 0 #define VERSION_PATCH 0
#define VERSION_BUILD 639 #define VERSION_BUILD 661
#define stringify(a) stringify_(a) #define stringify(a) stringify_(a)
#define stringify_(a) #a #define stringify_(a) #a

Binary file not shown.

Before

Width:  |  Height:  |  Size: 94 KiB

After

Width:  |  Height:  |  Size: 104 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 14 KiB

Binary file not shown.

Binary file not shown.

Before

Width:  |  Height:  |  Size: 14 KiB

After

Width:  |  Height:  |  Size: 18 KiB

Binary file not shown.
Loading…
Cancel
Save