Compare commits

...

3 Commits

  1. 2
      olcCodeJam2023Entry/CollectionPoint.h
  2. 2
      olcCodeJam2023Entry/Image.h
  3. 26
      olcCodeJam2023Entry/Scenario.cpp
  4. 12
      olcCodeJam2023Entry/Scenario.h
  5. 18
      olcCodeJam2023Entry/Textbox.cpp
  6. 8
      olcCodeJam2023Entry/Textbox.h
  7. 131
      olcCodeJam2023Entry/Unit.cpp
  8. 60
      olcCodeJam2023Entry/Unit.h
  9. 178
      olcCodeJam2023Entry/VirusAttack.cpp
  10. 14
      olcCodeJam2023Entry/VirusAttack.h
  11. BIN
      olcCodeJam2023Entry/assets/hooded_figure.png
  12. BIN
      olcCodeJam2023Entry/assets/spook_hooded_figure.png
  13. 16
      olcCodeJam2023Entry/olcCodeJam2023Entry.vcxproj
  14. BIN
      olcCodeJam2023Entry/pge.data
  15. 77
      olcCodeJam2023Entry/pge.js
  16. BIN
      olcCodeJam2023Entry/pge.wasm
  17. 4
      olcCodeJam2023Entry/util.cpp
  18. 2
      olcCodeJam2023Entry/util.h

@ -2,7 +2,7 @@
#include "olcPixelGameEngine.h" #include "olcPixelGameEngine.h"
#include "MemoryType.h" #include "MemoryType.h"
class Unit; struct Unit;
class CollectionPoint{ class CollectionPoint{
public: public:

@ -40,5 +40,7 @@ enum Image{
GUIDE, GUIDE,
ROUND_BAR, ROUND_BAR,
SEGMENT_BAR, SEGMENT_BAR,
HOODED_FIGURE,
SPOOK_HOODED_FIGURE,
}; };

@ -1,21 +1,37 @@
#include "Scenario.h" #include "Scenario.h"
Scenario::Scenario(VirusAttack*game) extern VirusAttack*game;
:game(game){}
Scenario::Scenario(){
dialog.SetVisible(false);
}
Scenario::~Scenario(){}
void Scenario::Start(){}
void Scenario::_Update(){ void Scenario::_Update(){
initialWaitTimer=std::max(0.f,initialWaitTimer-game->GetElapsedTime());
Update(); Update();
} }
void Scenario::_Draw(){ void Scenario::_Draw(){
Draw(); Draw();
} }
Stage1::Stage1(VirusAttack*game) Stage1::Stage1(){}
:Scenario(game){}
Stage1::~Stage1(){}
void Stage1::Start(){
game->unitMetersGreyedOut=true;
game->playerInControl=false;
}
void Stage1::Update(){ void Stage1::Update(){
switch(state){
case 0:{
dialog.Initialize("Hello Hacker, thank you for taking on this request for me.",{24,64},"",&game->IMAGES[SEGMENT_BAR],{378,28});
}break;
}
} }
void Stage1::Draw(){ void Stage1::Draw(){

@ -2,19 +2,25 @@
#include "VirusAttack.h" #include "VirusAttack.h"
class Scenario{ class Scenario{
VirusAttack*game;
public: public:
Scenario(VirusAttack*game); Scenario();
virtual ~Scenario();
virtual void Start();
void _Update(); void _Update();
virtual void Update()=0; virtual void Update()=0;
void _Draw(); void _Draw();
virtual void Draw()=0; virtual void Draw()=0;
protected: protected:
int state=0;
Textbox dialog;
float initialWaitTimer=3;
}; };
class Stage1:public Scenario{ class Stage1:public Scenario{
public: public:
Stage1(VirusAttack*game); Stage1();
~Stage1();
void Start()override;
void Update()override; void Update()override;
void Draw()override; void Draw()override;
}; };

@ -4,7 +4,7 @@
Textbox::Textbox(){}; Textbox::Textbox(){};
void Textbox::Initialize(std::string text,vf2d pos,std::string headerText,vf2d maxSize,std::vector<Memory>resourceCost,float letterDisplayDelay) void Textbox::Initialize(std::string text,vf2d pos,std::string headerText,Renderable*boxImg,vf2d maxSize,std::vector<Memory>resourceCost,float letterDisplayDelay)
{ {
if(GetCurrentString()!=text){ //Make sure this is actually a new textbox if(GetCurrentString()!=text){ //Make sure this is actually a new textbox
SetDefaults(); SetDefaults();
@ -28,11 +28,13 @@ void Textbox::SetDefaults(){
displayHeaderText=""; displayHeaderText="";
text=""; text="";
headerText=""; headerText="";
continueWordTimer=0;
} }
void Textbox::Update(PixelGameEngine*pge){ void Textbox::Update(PixelGameEngine*pge){
if(!visible)return; if(!visible)return;
lastLetterTime-=pge->GetElapsedTime(); lastLetterTime-=pge->GetElapsedTime();
continueWordTimer+=pge->GetElapsedTime();
if(lastLetterTime<=0){ if(lastLetterTime<=0){
if(textboxMarker<int(text.length()-1)){ if(textboxMarker<int(text.length()-1)){
std::string tempText=displayText; std::string tempText=displayText;
@ -68,7 +70,7 @@ void Textbox::Update(PixelGameEngine*pge){
} }
void Textbox::Draw(PixelGameEngine*pge,Resources&resources,std::map<Image,std::unique_ptr<Renderable>>&IMAGES,int totalUsedMemory,int memoryLimit){ void Textbox::Draw(PixelGameEngine*pge,Resources&resources,std::vector<Renderable>&IMAGES,int totalUsedMemory,int memoryLimit){
if(visible){ if(visible){
geom2d::rect<float>boxRect={pos-vf2d{3,3},maxSize+vf2d{6,6}}; geom2d::rect<float>boxRect={pos-vf2d{3,3},maxSize+vf2d{6,6}};
if(resourceCost.size()>0){ if(resourceCost.size()>0){
@ -115,31 +117,31 @@ void Textbox::Draw(PixelGameEngine*pge,Resources&resources,std::map<Image,std::u
int totalCost=0; int totalCost=0;
if(util::GetHealthCost(resourceCost)!=-1){ if(util::GetHealthCost(resourceCost)!=-1){
DrawResourceAmount(index,util::GetHealthCost(resourceCost),resources.health); DrawResourceAmount(index,util::GetHealthCost(resourceCost),resources.health);
pge->DrawDecal(contentPos+vf2d{0,index*6.f},IMAGES[RESOURCE]->Decal(),{0.5,0.5},CONSTANT::HEALTH_COLOR); pge->DrawDecal(contentPos+vf2d{0,index*6.f},IMAGES[RESOURCE].Decal(),{0.5,0.5},CONSTANT::HEALTH_COLOR);
totalCost+=util::GetHealthCost(resourceCost); totalCost+=util::GetHealthCost(resourceCost);
index++; index++;
} }
if(util::GetAtkSpdCost(resourceCost)!=-1){ if(util::GetAtkSpdCost(resourceCost)!=-1){
DrawResourceAmount(index,util::GetAtkSpdCost(resourceCost),resources.atkSpd); DrawResourceAmount(index,util::GetAtkSpdCost(resourceCost),resources.atkSpd);
pge->DrawDecal(contentPos+vf2d{0,index*6.f},IMAGES[RESOURCE]->Decal(),{0.5,0.5},CONSTANT::ATKSPD_COLOR); pge->DrawDecal(contentPos+vf2d{0,index*6.f},IMAGES[RESOURCE].Decal(),{0.5,0.5},CONSTANT::ATKSPD_COLOR);
totalCost+=util::GetAtkSpdCost(resourceCost); totalCost+=util::GetAtkSpdCost(resourceCost);
index++; index++;
} }
if(util::GetMoveSpdCost(resourceCost)!=-1){ if(util::GetMoveSpdCost(resourceCost)!=-1){
DrawResourceAmount(index,util::GetMoveSpdCost(resourceCost),resources.moveSpd); DrawResourceAmount(index,util::GetMoveSpdCost(resourceCost),resources.moveSpd);
pge->DrawDecal(contentPos+vf2d{0,index*6.f},IMAGES[RESOURCE]->Decal(),{0.5,0.5},CONSTANT::MOVESPD_COLOR); pge->DrawDecal(contentPos+vf2d{0,index*6.f},IMAGES[RESOURCE].Decal(),{0.5,0.5},CONSTANT::MOVESPD_COLOR);
totalCost+=util::GetMoveSpdCost(resourceCost); totalCost+=util::GetMoveSpdCost(resourceCost);
index++; index++;
} }
if(util::GetRangeCost(resourceCost)!=-1){ if(util::GetRangeCost(resourceCost)!=-1){
DrawResourceAmount(index,util::GetRangeCost(resourceCost),resources.range); DrawResourceAmount(index,util::GetRangeCost(resourceCost),resources.range);
pge->DrawDecal(contentPos+vf2d{0,index*6.f},IMAGES[RESOURCE]->Decal(),{0.5,0.5},CONSTANT::RANGE_COLOR); pge->DrawDecal(contentPos+vf2d{0,index*6.f},IMAGES[RESOURCE].Decal(),{0.5,0.5},CONSTANT::RANGE_COLOR);
totalCost+=util::GetRangeCost(resourceCost); totalCost+=util::GetRangeCost(resourceCost);
index++; index++;
} }
if(util::GetProcedureCost(resourceCost)!=-1){ if(util::GetProcedureCost(resourceCost)!=-1){
DrawResourceAmount(index,util::GetProcedureCost(resourceCost),resources.procedure); DrawResourceAmount(index,util::GetProcedureCost(resourceCost),resources.procedure);
pge->DrawDecal(contentPos+vf2d{0,index*6.f},IMAGES[RESOURCE]->Decal(),{0.5,0.5},CONSTANT::PROCEDURE_COLOR); pge->DrawDecal(contentPos+vf2d{0,index*6.f},IMAGES[RESOURCE].Decal(),{0.5,0.5},CONSTANT::PROCEDURE_COLOR);
totalCost+=util::GetProcedureCost(resourceCost); totalCost+=util::GetProcedureCost(resourceCost);
index++; index++;
} }
@ -171,7 +173,7 @@ void Textbox::SetVisible(bool visible){
} }
} }
void Textbox::UpdateAndDraw(vf2d pos,PixelGameEngine*pge,Resources&resources,std::map<Image,std::unique_ptr<Renderable>>&IMAGES,int totalUsedMemory,int memoryLimit){ void Textbox::UpdateAndDraw(vf2d pos,PixelGameEngine*pge,Resources&resources,std::vector<Renderable>&IMAGES,int totalUsedMemory,int memoryLimit){
UpdatePosition(pos); UpdatePosition(pos);
Update(pge); Update(pge);
Draw(pge,resources,IMAGES,totalUsedMemory,memoryLimit); Draw(pge,resources,IMAGES,totalUsedMemory,memoryLimit);

@ -9,12 +9,14 @@ class Textbox{
std::string displayHeaderText=""; std::string displayHeaderText="";
std::string text=""; std::string text="";
std::string displayText=""; std::string displayText="";
Renderable*boxImg=nullptr;
vf2d pos={}; vf2d pos={};
vf2d maxSize={}; vf2d maxSize={};
float lastLetterTime=0; float lastLetterTime=0;
float letterDisplayDelay=0.01; float letterDisplayDelay=0.01;
int textboxMarker=-1; int textboxMarker=-1;
int lastWordMarker=-1; int lastWordMarker=-1;
float continueWordTimer=0;
std::string lastWord=""; std::string lastWord="";
int lastHeaderWordMarker=-1; int lastHeaderWordMarker=-1;
std::string lastHeaderWord=""; std::string lastHeaderWord="";
@ -23,9 +25,9 @@ class Textbox{
Pixel backCol=CONSTANT::MESSAGE_BOX_DEFAULT_BACKCOL; Pixel backCol=CONSTANT::MESSAGE_BOX_DEFAULT_BACKCOL;
public: public:
Textbox(); Textbox();
void Initialize(std::string text,vf2d pos={},std::string headerText="",vf2d maxSize={120,1},std::vector<Memory>resourceCost={},float letterDisplayDelay=0.01); void Initialize(std::string text,vf2d pos={},std::string headerText="",Renderable*boxImg=nullptr,vf2d maxSize={120,1},std::vector<Memory>resourceCost={},float letterDisplayDelay=0.01);
void UpdateAndDraw(vf2d pos,PixelGameEngine*pge,Resources&resources,std::map<Image,std::unique_ptr<Renderable>>&IMAGES,int totalUsedMemory,int memoryLimit); void UpdateAndDraw(vf2d pos,PixelGameEngine*pge,Resources&resources,std::vector<Renderable>&IMAGES,int totalUsedMemory,int memoryLimit);
std::string&GetCurrentString(); std::string&GetCurrentString();
void SetVisible(bool visible); void SetVisible(bool visible);
vf2d GetSize(); vf2d GetSize();
@ -34,6 +36,6 @@ public:
private: private:
void Update(PixelGameEngine*pge); void Update(PixelGameEngine*pge);
void UpdatePosition(vf2d newPos); void UpdatePosition(vf2d newPos);
void Draw(PixelGameEngine*pge,Resources&resources,std::map<Image,std::unique_ptr<Renderable>>&IMAGES,int totalUsedMemory,int memoryLimit); void Draw(PixelGameEngine*pge,Resources&resources,std::vector<Renderable>&IMAGES,int totalUsedMemory,int memoryLimit);
void SetDefaults(); void SetDefaults();
}; };

@ -6,11 +6,24 @@
#include "olcPGEX_QuickGUI.h" #include "olcPGEX_QuickGUI.h"
#include "Textbox.h" #include "Textbox.h"
Unit::~Unit(){};
LeftShifter::~LeftShifter(){};
RightShifter::~RightShifter(){};
BitRestorer::~BitRestorer(){};
MemorySwapper::~MemorySwapper(){};
Corrupter::~Corrupter(){};
MemoryAllocator::~MemoryAllocator(){};
RAMBank::~RAMBank(){};
MemoryGuard::~MemoryGuard(){};
Refresher::~Refresher(){};
Turret::~Turret(){};
_Platform::~_Platform(){};
std::string LeftShifter::unitName="Left Shifter"; std::string LeftShifter::unitName="Left Shifter";
std::string LeftShifter::unitDescription="Shifts target memory 1 bit to the left."; std::string LeftShifter::unitDescription="Shifts target memory 1 bit to the left.";
std::vector<Memory> LeftShifter::resourceCost={{RANGE,2},{ATKSPD,2},{MOVESPD,6},{PROCEDURE,1},{HEALTH,4}}; std::vector<Memory> LeftShifter::resourceCost={{RANGE,2},{ATKSPD,2},{MOVESPD,6},{PROCEDURE,1},{HEALTH,4}};
LeftShifter::LeftShifter(PixelGameEngine*pge,vf2d pos,std::map<Image,std::unique_ptr<Renderable>>&IMAGES,bool friendly,bool moveable) LeftShifter::LeftShifter(PixelGameEngine*pge,vf2d pos,std::vector<Renderable>&IMAGES,bool friendly,bool moveable)
:Unit(pge,LeftShifter::resourceCost,pos,12,*IMAGES[LEFT_SHIFTER],CONSTANT::ATTACKER_TARGET_COL,CONSTANT::ATTACKER_ATTACK_COL,friendly,moveable){} :Unit(pge,LeftShifter::resourceCost,pos,12,IMAGES[LEFT_SHIFTER],CONSTANT::ATTACKER_TARGET_COL,CONSTANT::ATTACKER_ATTACK_COL,friendly,moveable){}
void LeftShifter::Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits){ void LeftShifter::Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits){
victim<<=1; victim<<=1;
@ -19,8 +32,8 @@ void LeftShifter::Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUni
std::string RightShifter::unitName="Right Shifter"; std::string RightShifter::unitName="Right Shifter";
std::string RightShifter::unitDescription="Shifts target memory 1 bit to the right."; std::string RightShifter::unitDescription="Shifts target memory 1 bit to the right.";
std::vector<Memory> RightShifter::resourceCost={{HEALTH,4},{RANGE,2},{ATKSPD,2},{MOVESPD,6},{PROCEDURE,1}}; std::vector<Memory> RightShifter::resourceCost={{HEALTH,4},{RANGE,2},{ATKSPD,2},{MOVESPD,6},{PROCEDURE,1}};
RightShifter::RightShifter(PixelGameEngine*pge,vf2d pos,std::map<Image,std::unique_ptr<Renderable>>&IMAGES,bool friendly,bool moveable) RightShifter::RightShifter(PixelGameEngine*pge,vf2d pos,std::vector<Renderable>&IMAGES,bool friendly,bool moveable)
:Unit(pge,RightShifter::resourceCost,pos,12,*IMAGES[RIGHT_SHIFTER],CONSTANT::ATTACKER_TARGET_COL,CONSTANT::ATTACKER_ATTACK_COL,friendly,moveable){} :Unit(pge,RightShifter::resourceCost,pos,12,IMAGES[RIGHT_SHIFTER],CONSTANT::ATTACKER_TARGET_COL,CONSTANT::ATTACKER_ATTACK_COL,friendly,moveable){}
void RightShifter::Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits){ void RightShifter::Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits){
victim>>=1; victim>>=1;
@ -29,8 +42,8 @@ void RightShifter::Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUn
std::string BitRestorer::unitName="Bit Restorer"; std::string BitRestorer::unitName="Bit Restorer";
std::string BitRestorer::unitDescription="Randomly restores 1 missing bit to a target."; std::string BitRestorer::unitDescription="Randomly restores 1 missing bit to a target.";
std::vector<Memory> BitRestorer::resourceCost={{PROCEDURE,6},{RANGE,1},{ATKSPD,1},{MOVESPD,2},{HEALTH,2}}; std::vector<Memory> BitRestorer::resourceCost={{PROCEDURE,6},{RANGE,1},{ATKSPD,1},{MOVESPD,2},{HEALTH,2}};
BitRestorer::BitRestorer(PixelGameEngine*pge,vf2d pos,std::map<Image,std::unique_ptr<Renderable>>&IMAGES,bool friendly,bool moveable) BitRestorer::BitRestorer(PixelGameEngine*pge,vf2d pos,std::vector<Renderable>&IMAGES,bool friendly,bool moveable)
:Unit(pge,BitRestorer::resourceCost,pos,12,*IMAGES[BIT_RESTORER],CONSTANT::HEALER_TARGET_COL,CONSTANT::HEALER_ATTACK_COL,friendly,moveable,true,false){} :Unit(pge,BitRestorer::resourceCost,pos,12,IMAGES[BIT_RESTORER],CONSTANT::HEALER_TARGET_COL,CONSTANT::HEALER_ATTACK_COL,friendly,moveable,true,false){}
void BitRestorer::Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits){ void BitRestorer::Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits){
std::vector<int>emptyMemoryPositions; std::vector<int>emptyMemoryPositions;
@ -71,8 +84,8 @@ void BitRestorer::AttemptToHealOtherAllies(std::vector<std::shared_ptr<Unit>>&ot
std::string MemorySwapper::unitName="Memory Swapper"; std::string MemorySwapper::unitName="Memory Swapper";
std::string MemorySwapper::unitDescription="Flips the orientation of all bits of a target around."; std::string MemorySwapper::unitDescription="Flips the orientation of all bits of a target around.";
std::vector<Memory> MemorySwapper::resourceCost={{RANGE,3},{ATKSPD,1},{HEALTH,3},{PROCEDURE,3},{MOVESPD,4}}; std::vector<Memory> MemorySwapper::resourceCost={{RANGE,3},{ATKSPD,1},{HEALTH,3},{PROCEDURE,3},{MOVESPD,4}};
MemorySwapper::MemorySwapper(PixelGameEngine*pge,vf2d pos,std::map<Image,std::unique_ptr<Renderable>>&IMAGES,bool friendly,bool moveable) MemorySwapper::MemorySwapper(PixelGameEngine*pge,vf2d pos,std::vector<Renderable>&IMAGES,bool friendly,bool moveable)
:Unit(pge,MemorySwapper::resourceCost,pos,12,*IMAGES[MEMORY_SWAPPER],CONSTANT::ATTACKER_TARGET_COL,CONSTANT::ATTACKER_ATTACK_COL,friendly,moveable,true){ :Unit(pge,MemorySwapper::resourceCost,pos,12,IMAGES[MEMORY_SWAPPER],CONSTANT::ATTACKER_TARGET_COL,CONSTANT::ATTACKER_ATTACK_COL,friendly,moveable,true){
autoAcquireFriendlyTarget=false; autoAcquireFriendlyTarget=false;
} }
@ -115,8 +128,8 @@ void MemorySwapper::Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherU
std::string Corrupter::unitName="Corrupter"; std::string Corrupter::unitName="Corrupter";
std::string Corrupter::unitDescription="Chooses a random bit and negates it on a target."; std::string Corrupter::unitDescription="Chooses a random bit and negates it on a target.";
std::vector<Memory> Corrupter::resourceCost={{ATKSPD,3},{RANGE,1},{PROCEDURE,8},{MOVESPD,8},{HEALTH,4}}; std::vector<Memory> Corrupter::resourceCost={{ATKSPD,3},{RANGE,1},{PROCEDURE,8},{MOVESPD,8},{HEALTH,4}};
Corrupter::Corrupter(PixelGameEngine*pge,vf2d pos,std::map<Image,std::unique_ptr<Renderable>>&IMAGES,bool friendly,bool moveable) Corrupter::Corrupter(PixelGameEngine*pge,vf2d pos,std::vector<Renderable>&IMAGES,bool friendly,bool moveable)
:Unit(pge,Corrupter::resourceCost,pos,12,*IMAGES[CORRUPTER],CONSTANT::ATTACKER_TARGET_COL,CONSTANT::ATTACKER_ATTACK_COL,friendly,moveable){} :Unit(pge,Corrupter::resourceCost,pos,12,IMAGES[CORRUPTER],CONSTANT::ATTACKER_TARGET_COL,CONSTANT::ATTACKER_ATTACK_COL,friendly,moveable){}
void Corrupter::Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits){ void Corrupter::Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits){
//Chooses a bit at random and corrupts it. //Chooses a bit at random and corrupts it.
@ -127,8 +140,8 @@ void Corrupter::Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits
std::string MemoryAllocator::unitName="Memory Allocator"; std::string MemoryAllocator::unitName="Memory Allocator";
std::string MemoryAllocator::unitDescription="A unit that builds other units."; std::string MemoryAllocator::unitDescription="A unit that builds other units.";
std::vector<Memory> MemoryAllocator::resourceCost={{RANGE,1},{ATKSPD,1},{MOVESPD,2},{PROCEDURE,1},{HEALTH,1}}; std::vector<Memory> MemoryAllocator::resourceCost={{RANGE,1},{ATKSPD,1},{MOVESPD,2},{PROCEDURE,1},{HEALTH,1}};
MemoryAllocator::MemoryAllocator(PixelGameEngine*pge,vf2d pos,std::map<Image,std::unique_ptr<Renderable>>&IMAGES,bool friendly,bool moveable) MemoryAllocator::MemoryAllocator(PixelGameEngine*pge,vf2d pos,std::vector<Renderable>&IMAGES,bool friendly,bool moveable)
:Unit(pge,MemoryAllocator::resourceCost,pos,12,*IMAGES[UNIT_ALLOCATOR],CONSTANT::ATTACKER_TARGET_COL,CONSTANT::ATTACKER_ATTACK_COL,friendly,true,false){ :Unit(pge,MemoryAllocator::resourceCost,pos,12,IMAGES[UNIT_ALLOCATOR],CONSTANT::ATTACKER_TARGET_COL,CONSTANT::ATTACKER_ATTACK_COL,friendly,true,false){
isAllocator=true; isAllocator=true;
} }
@ -150,7 +163,7 @@ void MemoryAllocator::Update(PixelGameEngine*pge,std::map<Sound,std::unique_ptr<
} }
} }
void MemoryAllocator::Draw(TileTransformedView&game,std::map<Image,std::unique_ptr<Renderable>>&IMAGES){ void MemoryAllocator::Draw(TileTransformedView&game,std::vector<Renderable>&IMAGES){
if(IsBuilding()){ if(IsBuilding()){
game.GetPGE()->SetDrawTarget(img.Sprite()); game.GetPGE()->SetDrawTarget(img.Sprite());
game.GetPGE()->Clear(BLANK); game.GetPGE()->Clear(BLANK);
@ -159,12 +172,12 @@ void MemoryAllocator::Draw(TileTransformedView&game,std::map<Image,std::unique_p
game.DrawPartialRotatedDecal(GetGhostPos(),img.Decal(),0,img.Sprite()->Size()/2,{0,0},{float(img.Sprite()->width),float((buildTime/CONSTANT::UNIT_BUILD_TIME)*img.Sprite()->height)},{1,1},GetUnitColor()/3); game.DrawPartialRotatedDecal(GetGhostPos(),img.Decal(),0,img.Sprite()->Size()/2,{0,0},{float(img.Sprite()->width),float((buildTime/CONSTANT::UNIT_BUILD_TIME)*img.Sprite()->height)},{1,1},GetUnitColor()/3);
game.DrawPartialRotatedDecal(GetGhostPos()+vf2d{0.f,(buildTime/CONSTANT::UNIT_BUILD_TIME)*buildTransformUnit->GetImage().Sprite()->height},buildTransformUnit->GetImage().Decal(),0,buildTransformUnit->GetImage().Sprite()->Size()/2,{0.f,(buildTime/CONSTANT::UNIT_BUILD_TIME)*buildTransformUnit->GetImage().Sprite()->height},{float(buildTransformUnit->GetImage().Sprite()->width),float(buildTransformUnit->GetImage().Sprite()->height-(buildTime/CONSTANT::UNIT_BUILD_TIME)*buildTransformUnit->GetImage().Sprite()->height)},{1,1},GetUnitColor()/1.5f); game.DrawPartialRotatedDecal(GetGhostPos()+vf2d{0.f,(buildTime/CONSTANT::UNIT_BUILD_TIME)*buildTransformUnit->GetImage().Sprite()->height},buildTransformUnit->GetImage().Decal(),0,buildTransformUnit->GetImage().Sprite()->Size()/2,{0.f,(buildTime/CONSTANT::UNIT_BUILD_TIME)*buildTransformUnit->GetImage().Sprite()->height},{float(buildTransformUnit->GetImage().Sprite()->width),float(buildTransformUnit->GetImage().Sprite()->height-(buildTime/CONSTANT::UNIT_BUILD_TIME)*buildTransformUnit->GetImage().Sprite()->height)},{1,1},GetUnitColor()/1.5f);
if(fmod(buildTime,1)>0.5){ if(fmod(buildTime,1)>0.5){
game.DrawRotatedDecal(GetGhostPos(),IMAGES[SELECTION_CIRCLE]->Decal(),0,IMAGES[SELECTION_CIRCLE]->Sprite()->Size()/2,vf2d(img.Sprite()->Size())/IMAGES[SELECTION_CIRCLE]->Sprite()->Size(),{0, 202, 217}); game.DrawRotatedDecal(GetGhostPos(),IMAGES[SELECTION_CIRCLE].Decal(),0,IMAGES[SELECTION_CIRCLE].Sprite()->Size()/2,vf2d(img.Sprite()->Size())/IMAGES[SELECTION_CIRCLE].Sprite()->Size(),{0, 202, 217});
} }
} else { } else {
game.DrawRotatedDecal(GetGhostPos(),img.Decal(),0,img.Sprite()->Size()/2,{1,1},GetUnitColor()); game.DrawRotatedDecal(GetGhostPos(),img.Decal(),0,img.Sprite()->Size()/2,{1,1},GetUnitColor());
if(IsSelected()){ if(IsSelected()){
game.DrawRotatedDecal(GetGhostPos(),IMAGES[SELECTION_CIRCLE]->Decal(),0,IMAGES[SELECTION_CIRCLE]->Sprite()->Size()/2,vf2d(img.Sprite()->Size())/IMAGES[SELECTION_CIRCLE]->Sprite()->Size(),WHITE); game.DrawRotatedDecal(GetGhostPos(),IMAGES[SELECTION_CIRCLE].Decal(),0,IMAGES[SELECTION_CIRCLE].Sprite()->Size()/2,vf2d(img.Sprite()->Size())/IMAGES[SELECTION_CIRCLE].Sprite()->Size(),WHITE);
} }
} }
} }
@ -172,15 +185,15 @@ void MemoryAllocator::Draw(TileTransformedView&game,std::map<Image,std::unique_p
std::string RAMBank::unitName="RAM Bank"; std::string RAMBank::unitName="RAM Bank";
std::string RAMBank::unitDescription="Allows for the construction of Memory Allocators."; std::string RAMBank::unitDescription="Allows for the construction of Memory Allocators.";
std::vector<Memory> RAMBank::resourceCost={{PROCEDURE,25},{HEALTH,16}}; std::vector<Memory> RAMBank::resourceCost={{PROCEDURE,25},{HEALTH,16}};
RAMBank::RAMBank(PixelGameEngine*pge,vf2d pos,std::map<Image,std::unique_ptr<Renderable>>&IMAGES,bool friendly) RAMBank::RAMBank(PixelGameEngine*pge,vf2d pos,std::vector<Renderable>&IMAGES,bool friendly)
:Unit(pge,RAMBank::resourceCost,pos,41,*IMAGES[RAM_BANK],WHITE,WHITE,friendly,false :Unit(pge,RAMBank::resourceCost,pos,41,IMAGES[RAM_BANK],WHITE,WHITE,friendly,false
,false,false ,false,false
),randomOffset({util::random(128),util::random(128)}),matrixImg(*IMAGES[MATRIX]), ),randomOffset({util::random(128),util::random(128)}),matrixImg(IMAGES[MATRIX]),
originalImg(*IMAGES[RAM_BANK]){ originalImg(IMAGES[RAM_BANK]){
img.Create(IMAGES[RAM_BANK]->Sprite()->width,IMAGES[RAM_BANK]->Sprite()->height); img.Create(IMAGES[RAM_BANK].Sprite()->width,IMAGES[RAM_BANK].Sprite()->height);
pge->SetDrawTarget(img.Sprite()); pge->SetDrawTarget(img.Sprite());
pge->Clear(BLANK); pge->Clear(BLANK);
pge->DrawSprite({0,0},IMAGES[RAM_BANK]->Sprite()); pge->DrawSprite({0,0},IMAGES[RAM_BANK].Sprite());
pge->SetDrawTarget(nullptr); pge->SetDrawTarget(nullptr);
allocatorManager.colNormal = olc::VERY_DARK_GREEN; allocatorManager.colNormal = olc::VERY_DARK_GREEN;
allocatorManager.colHover = olc::GREEN; allocatorManager.colHover = olc::GREEN;
@ -188,7 +201,7 @@ RAMBank::RAMBank(PixelGameEngine*pge,vf2d pos,std::map<Image,std::unique_ptr<Ren
allocatorManager.colDisable = olc::DARK_GREY; allocatorManager.colDisable = olc::DARK_GREY;
allocatorManager.colBorder = olc::YELLOW; allocatorManager.colBorder = olc::YELLOW;
allocatorManager.colText = olc::WHITE; allocatorManager.colText = olc::WHITE;
allocatorButton = new QuickGUI::ImageButton(allocatorManager,*IMAGES[UNIT_ALLOCATOR],{0.5f,0.5f},pos-vf2d{8,48},{20,20}); allocatorButton = new QuickGUI::ImageButton(allocatorManager,IMAGES[UNIT_ALLOCATOR],{0.5f,0.5f},pos-vf2d{8,48},{20,20});
} }
void RAMBank::Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits){ void RAMBank::Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits){
@ -213,16 +226,16 @@ void RAMBank::Update(PixelGameEngine*pge,std::map<Sound,std::unique_ptr<Audio>>&
pge->SetDrawTarget(nullptr); pge->SetDrawTarget(nullptr);
} }
void RAMBank::DrawHud(TileTransformedView&game,std::map<Image,std::unique_ptr<Renderable>>&IMAGES){ void RAMBank::DrawHud(TileTransformedView&game,std::vector<Renderable>&IMAGES){
if(IsSelected()){ if(IsSelected()){
allocatorManager.DrawDecal(game); allocatorManager.DrawDecal(game);
} }
} }
void RAMBank::Draw(TileTransformedView&game,std::map<Image,std::unique_ptr<Renderable>>&IMAGES){ void RAMBank::Draw(TileTransformedView&game,std::vector<Renderable>&IMAGES){
game.DrawRotatedDecal(GetGhostPos(),img.Decal(),0,img.Sprite()->Size()/2,{1,1},GetUnitColor()); game.DrawRotatedDecal(GetGhostPos(),img.Decal(),0,img.Sprite()->Size()/2,{1,1},GetUnitColor());
if(IsSelected()){ if(IsSelected()){
game.DrawRotatedDecal(GetGhostPos(),IMAGES[SELECTION_CIRCLE]->Decal(),0,IMAGES[SELECTION_CIRCLE]->Sprite()->Size()/2,vf2d(img.Sprite()->Size())/IMAGES[SELECTION_CIRCLE]->Sprite()->Size(),WHITE); game.DrawRotatedDecal(GetGhostPos(),IMAGES[SELECTION_CIRCLE].Decal(),0,IMAGES[SELECTION_CIRCLE].Sprite()->Size()/2,vf2d(img.Sprite()->Size())/IMAGES[SELECTION_CIRCLE].Sprite()->Size(),WHITE);
} }
} }
@ -248,7 +261,7 @@ void RAMBank::UpdateGUIState(TileTransformedView&game,Resources&player_resources
allocatorButton->Enable(buttonEnabled); allocatorButton->Enable(buttonEnabled);
} }
bool RAMBank::ClickHandled(TileTransformedView&game,Resources&player_resources,std::vector<std::shared_ptr<Unit>>&units,std::map<Image,std::unique_ptr<Renderable>>&IMAGES){ bool RAMBank::ClickHandled(TileTransformedView&game,Resources&player_resources,std::vector<std::shared_ptr<Unit>>&units,std::vector<Renderable>&IMAGES){
if(allocatorButton->bPressed){ if(allocatorButton->bPressed){
//First try to take one of each. //First try to take one of each.
if(player_resources.atkSpd>0&&player_resources.health>0&&player_resources.moveSpd>0&&player_resources.procedure>0&&player_resources.range>0){ if(player_resources.atkSpd>0&&player_resources.health>0&&player_resources.moveSpd>0&&player_resources.procedure>0&&player_resources.range>0){
@ -285,8 +298,8 @@ bool RAMBank::ClickHandled(TileTransformedView&game,Resources&player_resources,s
std::string _Platform::unitName="Platform"; std::string _Platform::unitName="Platform";
std::string _Platform::unitDescription="Anchored to the ground, this unit is an intermediate step for larger units."; std::string _Platform::unitDescription="Anchored to the ground, this unit is an intermediate step for larger units.";
std::vector<Memory> _Platform::resourceCost={{HEALTH,6}}; std::vector<Memory> _Platform::resourceCost={{HEALTH,6}};
_Platform::_Platform(PixelGameEngine*pge,vf2d pos,std::map<Image,std::unique_ptr<Renderable>>&IMAGES,bool friendly,bool moveable) _Platform::_Platform(PixelGameEngine*pge,vf2d pos,std::vector<Renderable>&IMAGES,bool friendly,bool moveable)
:Unit(pge,_Platform::resourceCost,pos,24,*IMAGES[PLATFORM],CONSTANT::ATTACKER_TARGET_COL,CONSTANT::ATTACKER_ATTACK_COL,friendly,false){ :Unit(pge,_Platform::resourceCost,pos,24,IMAGES[PLATFORM],CONSTANT::ATTACKER_TARGET_COL,CONSTANT::ATTACKER_ATTACK_COL,friendly,false){
isPlatform=true; isPlatform=true;
} }
@ -306,7 +319,7 @@ void _Platform::Update(PixelGameEngine*pge,std::map<Sound,std::unique_ptr<Audio>
} }
} }
void _Platform::Draw(TileTransformedView&game,std::map<Image,std::unique_ptr<Renderable>>&IMAGES){ void _Platform::Draw(TileTransformedView&game,std::vector<Renderable>&IMAGES){
if(IsBuilding()){ if(IsBuilding()){
game.GetPGE()->SetDrawTarget(img.Sprite()); game.GetPGE()->SetDrawTarget(img.Sprite());
game.GetPGE()->Clear(BLANK); game.GetPGE()->Clear(BLANK);
@ -315,12 +328,12 @@ void _Platform::Draw(TileTransformedView&game,std::map<Image,std::unique_ptr<Ren
game.DrawPartialRotatedDecal(GetGhostPos(),img.Decal(),0,img.Sprite()->Size()/2,{0,0},{float(img.Sprite()->width),float((buildTime/CONSTANT::UNIT_BUILD_TIME)*img.Sprite()->height)},{1,1},GetUnitColor()/3); game.DrawPartialRotatedDecal(GetGhostPos(),img.Decal(),0,img.Sprite()->Size()/2,{0,0},{float(img.Sprite()->width),float((buildTime/CONSTANT::UNIT_BUILD_TIME)*img.Sprite()->height)},{1,1},GetUnitColor()/3);
game.DrawPartialRotatedDecal(GetGhostPos()+vf2d{0.f,(buildTime/CONSTANT::UNIT_BUILD_TIME)*buildTransformUnit->GetImage().Sprite()->height},buildTransformUnit->GetImage().Decal(),0,buildTransformUnit->GetImage().Sprite()->Size()/2,{0.f,(buildTime/CONSTANT::UNIT_BUILD_TIME)*buildTransformUnit->GetImage().Sprite()->height},{float(buildTransformUnit->GetImage().Sprite()->width),float(buildTransformUnit->GetImage().Sprite()->height-(buildTime/CONSTANT::UNIT_BUILD_TIME)*buildTransformUnit->GetImage().Sprite()->height)},{1,1},GetUnitColor()/1.5f); game.DrawPartialRotatedDecal(GetGhostPos()+vf2d{0.f,(buildTime/CONSTANT::UNIT_BUILD_TIME)*buildTransformUnit->GetImage().Sprite()->height},buildTransformUnit->GetImage().Decal(),0,buildTransformUnit->GetImage().Sprite()->Size()/2,{0.f,(buildTime/CONSTANT::UNIT_BUILD_TIME)*buildTransformUnit->GetImage().Sprite()->height},{float(buildTransformUnit->GetImage().Sprite()->width),float(buildTransformUnit->GetImage().Sprite()->height-(buildTime/CONSTANT::UNIT_BUILD_TIME)*buildTransformUnit->GetImage().Sprite()->height)},{1,1},GetUnitColor()/1.5f);
if(fmod(buildTime,1)>0.5){ if(fmod(buildTime,1)>0.5){
game.DrawRotatedDecal(GetGhostPos(),IMAGES[SELECTION_CIRCLE]->Decal(),0,IMAGES[SELECTION_CIRCLE]->Sprite()->Size()/2,vf2d(img.Sprite()->Size())/IMAGES[SELECTION_CIRCLE]->Sprite()->Size(),{0, 202, 217}); game.DrawRotatedDecal(GetGhostPos(),IMAGES[SELECTION_CIRCLE].Decal(),0,IMAGES[SELECTION_CIRCLE].Sprite()->Size()/2,vf2d(img.Sprite()->Size())/IMAGES[SELECTION_CIRCLE].Sprite()->Size(),{0, 202, 217});
} }
} else { } else {
game.DrawRotatedDecal(GetGhostPos(),img.Decal(),0,img.Sprite()->Size()/2,{1,1},GetUnitColor()); game.DrawRotatedDecal(GetGhostPos(),img.Decal(),0,img.Sprite()->Size()/2,{1,1},GetUnitColor());
if(IsSelected()){ if(IsSelected()){
game.DrawRotatedDecal(GetGhostPos(),IMAGES[SELECTION_CIRCLE]->Decal(),0,IMAGES[SELECTION_CIRCLE]->Sprite()->Size()/2,vf2d(img.Sprite()->Size())/IMAGES[SELECTION_CIRCLE]->Sprite()->Size(),WHITE); game.DrawRotatedDecal(GetGhostPos(),IMAGES[SELECTION_CIRCLE].Decal(),0,IMAGES[SELECTION_CIRCLE].Sprite()->Size()/2,vf2d(img.Sprite()->Size())/IMAGES[SELECTION_CIRCLE].Sprite()->Size(),WHITE);
} }
} }
} }
@ -328,8 +341,8 @@ void _Platform::Draw(TileTransformedView&game,std::map<Image,std::unique_ptr<Ren
std::string Refresher::unitName="Refresher"; std::string Refresher::unitName="Refresher";
std::string Refresher::unitDescription="Repairs missing bits to surrounding units."; std::string Refresher::unitDescription="Repairs missing bits to surrounding units.";
std::vector<Memory> Refresher::resourceCost={{ATKSPD,3},{RANGE,1},{PROCEDURE,8},{HEALTH,4}}; std::vector<Memory> Refresher::resourceCost={{ATKSPD,3},{RANGE,1},{PROCEDURE,8},{HEALTH,4}};
Refresher::Refresher(PixelGameEngine*pge,vf2d pos,std::map<Image,std::unique_ptr<Renderable>>&IMAGES,bool friendly,bool moveable) Refresher::Refresher(PixelGameEngine*pge,vf2d pos,std::vector<Renderable>&IMAGES,bool friendly,bool moveable)
:Unit(pge,Refresher::resourceCost,pos,24,*IMAGES[REFRESHER],CONSTANT::ATTACKER_TARGET_COL,CONSTANT::ATTACKER_ATTACK_COL,friendly,false :Unit(pge,Refresher::resourceCost,pos,24,IMAGES[REFRESHER],CONSTANT::ATTACKER_TARGET_COL,CONSTANT::ATTACKER_ATTACK_COL,friendly,false
,true,false){} ,true,false){}
void Refresher::Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits){ void Refresher::Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits){
@ -353,8 +366,8 @@ void Refresher::Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits
std::string Turret::unitName="Turret"; std::string Turret::unitName="Turret";
std::string Turret::unitDescription="Automatically targets attack and movement speed memory ranges before others."; std::string Turret::unitDescription="Automatically targets attack and movement speed memory ranges before others.";
std::vector<Memory> Turret::resourceCost={{ATKSPD,4},{RANGE,5},{HEALTH,6},{PROCEDURE,16}}; std::vector<Memory> Turret::resourceCost={{ATKSPD,4},{RANGE,5},{HEALTH,6},{PROCEDURE,16}};
Turret::Turret(PixelGameEngine*pge,vf2d pos,std::map<Image,std::unique_ptr<Renderable>>&IMAGES,bool friendly,bool moveable) Turret::Turret(PixelGameEngine*pge,vf2d pos,std::vector<Renderable>&IMAGES,bool friendly,bool moveable)
:Unit(pge,Turret::resourceCost,pos,24,*IMAGES[TURRET],CONSTANT::ATTACKER_TARGET_COL,CONSTANT::ATTACKER_ATTACK_COL,friendly,false){} :Unit(pge,Turret::resourceCost,pos,24,IMAGES[TURRET],CONSTANT::ATTACKER_TARGET_COL,CONSTANT::ATTACKER_ATTACK_COL,friendly,false){}
void Turret::Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits){ void Turret::Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits){
if(victim.GetMoveSpd()>0){ if(victim.GetMoveSpd()>0){
@ -388,8 +401,8 @@ void Turret::Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits){
std::string MemoryGuard::unitName="Memory Guard"; std::string MemoryGuard::unitName="Memory Guard";
std::string MemoryGuard::unitDescription="Reduces the chance of bit modification for all surrounding units by 30%"; std::string MemoryGuard::unitDescription="Reduces the chance of bit modification for all surrounding units by 30%";
std::vector<Memory> MemoryGuard::resourceCost={{HEALTH,10},{ATKSPD,4},{RANGE,4},{PROCEDURE,12}}; std::vector<Memory> MemoryGuard::resourceCost={{HEALTH,10},{ATKSPD,4},{RANGE,4},{PROCEDURE,12}};
MemoryGuard::MemoryGuard(PixelGameEngine*pge,vf2d pos,std::map<Image,std::unique_ptr<Renderable>>&IMAGES,bool friendly,bool moveable) MemoryGuard::MemoryGuard(PixelGameEngine*pge,vf2d pos,std::vector<Renderable>&IMAGES,bool friendly,bool moveable)
:Unit(pge,MemoryGuard::resourceCost,pos,24,*IMAGES[MEMORY_GUARD],CONSTANT::ATTACKER_TARGET_COL,CONSTANT::ATTACKER_ATTACK_COL,friendly,false :Unit(pge,MemoryGuard::resourceCost,pos,24,IMAGES[MEMORY_GUARD],CONSTANT::ATTACKER_TARGET_COL,CONSTANT::ATTACKER_ATTACK_COL,friendly,false
,true,false){} ,true,false){}
void MemoryGuard::Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits){ void MemoryGuard::Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits){
@ -438,7 +451,7 @@ Unit::Unit(PixelGameEngine*pge,std::vector<Memory>memory,vf2d pos,float radius,R
targetingLine.Create(25,24,false,false); targetingLine.Create(25,24,false,false);
} }
void Unit::DrawRangeIndicator(PixelGameEngine*pge,TileTransformedView&game,std::map<Image,std::unique_ptr<Renderable>>&IMAGES){ void Unit::DrawRangeIndicator(PixelGameEngine*pge,TileTransformedView&game,std::vector<Renderable>&IMAGES){
if(!CanInteractWithAllies()&&!CanInteractWithEnemies())return; if(!CanInteractWithAllies()&&!CanInteractWithEnemies())return;
float dist=geom2d::line<float>(game.ScreenToWorld(pge->GetMousePos()),GetGhostPos()).length(); float dist=geom2d::line<float>(game.ScreenToWorld(pge->GetMousePos()),GetGhostPos()).length();
float range=12*(GetRange()+1); float range=12*(GetRange()+1);
@ -451,7 +464,7 @@ void Unit::DrawRangeIndicator(PixelGameEngine*pge,TileTransformedView&game,std::
} else { } else {
col={0,196,0}; col={0,196,0};
} }
game.DrawRotatedDecal(GetGhostPos(),IMAGES[RANGE_INDICATOR]->Decal(),0,IMAGES[RANGE_INDICATOR]->Sprite()->Size()/2,{totalRange/12,totalRange/12},col); game.DrawRotatedDecal(GetGhostPos(),IMAGES[RANGE_INDICATOR].Decal(),0,IMAGES[RANGE_INDICATOR].Sprite()->Size()/2,{totalRange/12,totalRange/12},col);
}else }else
if(dist<range*2){ if(dist<range*2){
@ -470,20 +483,20 @@ void Unit::DrawRangeIndicator(PixelGameEngine*pge,TileTransformedView&game,std::
} }
} }
uint8_t transparency=uint8_t((1.f-(dist/(range*2)))*255); uint8_t transparency=uint8_t((1.f-(dist/(range*2)))*255);
game.DrawRotatedDecal(GetGhostPos(),IMAGES[RANGE_INDICATOR]->Decal(),0,IMAGES[RANGE_INDICATOR]->Sprite()->Size()/2,{totalRange/12,totalRange/12},{col.r,col.g,col.b,transparency}); game.DrawRotatedDecal(GetGhostPos(),IMAGES[RANGE_INDICATOR].Decal(),0,IMAGES[RANGE_INDICATOR].Sprite()->Size()/2,{totalRange/12,totalRange/12},{col.r,col.g,col.b,transparency});
} }
} }
void Unit::Draw(TileTransformedView&game,std::map<Image,std::unique_ptr<Renderable>>&IMAGES){ void Unit::Draw(TileTransformedView&game,std::vector<Renderable>&IMAGES){
game.DrawRotatedDecal(GetGhostPos(),img.Decal(),0,img.Sprite()->Size()/2,{1,1},GetUnitColor()); game.DrawRotatedDecal(GetGhostPos(),img.Decal(),0,img.Sprite()->Size()/2,{1,1},GetUnitColor());
if(IsSelected()){ if(IsSelected()){
game.DrawRotatedDecal(GetGhostPos(),IMAGES[SELECTION_CIRCLE]->Decal(),0,IMAGES[SELECTION_CIRCLE]->Sprite()->Size()/2,vf2d(img.Sprite()->Size())/IMAGES[SELECTION_CIRCLE]->Sprite()->Size(),WHITE); game.DrawRotatedDecal(GetGhostPos(),IMAGES[SELECTION_CIRCLE].Decal(),0,IMAGES[SELECTION_CIRCLE].Sprite()->Size()/2,vf2d(img.Sprite()->Size())/IMAGES[SELECTION_CIRCLE].Sprite()->Size(),WHITE);
} }
} }
void Unit::DrawHud(TileTransformedView&game,std::map<Image,std::unique_ptr<Renderable>>&IMAGES){} void Unit::DrawHud(TileTransformedView&game,std::vector<Renderable>&IMAGES){}
void Unit::_DrawHud(TileTransformedView&game,std::map<Image,std::unique_ptr<Renderable>>&IMAGES){ void Unit::_DrawHud(TileTransformedView&game,std::vector<Renderable>&IMAGES){
DrawHud(game,IMAGES); DrawHud(game,IMAGES);
int initialBarX=ghostPos.x-GetMemorySize()/2*CONSTANT::BAR_SQUARE_SIZE.x-CONSTANT::BAR_SQUARE_SIZE.x/2; int initialBarX=ghostPos.x-GetMemorySize()/2*CONSTANT::BAR_SQUARE_SIZE.x-CONSTANT::BAR_SQUARE_SIZE.x/2;
int initialBarY=ghostPos.y-CONSTANT::BAR_SQUARE_SIZE.y-img.Sprite()->height/2-2; int initialBarY=ghostPos.y-CONSTANT::BAR_SQUARE_SIZE.y-img.Sprite()->height/2-2;
@ -539,19 +552,19 @@ void Unit::_DrawHud(TileTransformedView&game,std::map<Image,std::unique_ptr<Rend
} }
} }
void Unit::DrawUnitDamageStats(PixelGameEngine*pge,TileTransformedView&game,std::map<Image,std::unique_ptr<Renderable>>&IMAGES){ void Unit::DrawUnitDamageStats(PixelGameEngine*pge,TileTransformedView&game,std::vector<Renderable>&IMAGES){
if(!target.expired()){ if(!target.expired()){
geom2d::line<float>lineToTarget(pos,target.lock()->pos); geom2d::line<float>lineToTarget(pos,target.lock()->pos);
lineToTarget.start=lineToTarget.rpoint(GetUnitSize().x/2); lineToTarget.start=lineToTarget.rpoint(GetUnitSize().x/2);
lineToTarget.end=lineToTarget.rpoint(lineToTarget.length()-GetUnitSize().x/4); lineToTarget.end=lineToTarget.rpoint(lineToTarget.length()-GetUnitSize().x/4);
util::ApplyMatrixEffect(game.GetPGE(),targetingLine,*IMAGES[TARGETING_LINE],IMAGES[MATRIX]); util::ApplyMatrixEffect(game.GetPGE(),targetingLine,IMAGES[TARGETING_LINE],IMAGES[MATRIX]);
game.DrawPartialRotatedDecal(lineToTarget.upoint(0.5),targetingLine.Decal(),lineToTarget.vector().polar().y,{lineToTarget.length()/2,12},{lineShift*10,0},{lineToTarget.length(),24},{1,1},targetLineCol); game.DrawPartialRotatedDecal(lineToTarget.upoint(0.5),targetingLine.Decal(),lineToTarget.vector().polar().y,{lineToTarget.length()/2,12},{lineShift*10,0},{lineToTarget.length(),24},{1,1},targetLineCol);
} else } else
if(targetLoc!=CONSTANT::UNSELECTED){ if(targetLoc!=CONSTANT::UNSELECTED){
geom2d::line<float>lineToTarget(pos,targetLoc); geom2d::line<float>lineToTarget(pos,targetLoc);
lineToTarget.start=lineToTarget.rpoint(GetUnitSize().x/2); lineToTarget.start=lineToTarget.rpoint(GetUnitSize().x/2);
lineToTarget.end=lineToTarget.rpoint(lineToTarget.length()-GetUnitSize().x/4); lineToTarget.end=lineToTarget.rpoint(lineToTarget.length()-GetUnitSize().x/4);
util::ApplyMatrixEffect(game.GetPGE(),targetingLine,*IMAGES[TARGETING_LINE],IMAGES[MATRIX]); util::ApplyMatrixEffect(game.GetPGE(),targetingLine,IMAGES[TARGETING_LINE],IMAGES[MATRIX]);
game.DrawPartialRotatedDecal(lineToTarget.upoint(0.5),targetingLine.Decal(),lineToTarget.vector().polar().y,{lineToTarget.length()/2,12},{lineShift*10,0},{lineToTarget.length(),24},{1,0.6},CONSTANT::MOVE_LINE_COL); game.DrawPartialRotatedDecal(lineToTarget.upoint(0.5),targetingLine.Decal(),lineToTarget.vector().polar().y,{lineToTarget.length()/2,12},{lineShift*10,0},{lineToTarget.length(),24},{1,0.6},CONSTANT::MOVE_LINE_COL);
} }
if(!appliedTarget.expired()){ if(!appliedTarget.expired()){
@ -559,7 +572,7 @@ void Unit::DrawUnitDamageStats(PixelGameEngine*pge,TileTransformedView&game,std:
lineToTarget.start=lineToTarget.rpoint(GetUnitSize().x/2); lineToTarget.start=lineToTarget.rpoint(GetUnitSize().x/2);
lineToTarget.end=lineToTarget.rpoint(lineToTarget.length()-GetUnitSize().x/4); lineToTarget.end=lineToTarget.rpoint(lineToTarget.length()-GetUnitSize().x/4);
if(reloadTimer>0){ if(reloadTimer>0){
util::ApplyMatrixEffect(game.GetPGE(),attackingLine,*IMAGES[ATTACKING_LINE],IMAGES[MATRIX]); util::ApplyMatrixEffect(game.GetPGE(),attackingLine,IMAGES[ATTACKING_LINE],IMAGES[MATRIX]);
float reloadSpd=1.f/(GetAtkSpd()/2.f); float reloadSpd=1.f/(GetAtkSpd()/2.f);
game.DrawPartialRotatedDecal(lineToTarget.upoint(0.5),attackingLine.Decal(),lineToTarget.vector().polar().y,{lineToTarget.length()/2,12},{lineShift*30,0},{lineToTarget.length(),24},{1,1+(attackFailed?-0.3f:(reloadTimer/reloadSpd)*0.25f)},attackFailed?Pixel{192,192,192,130}:Pixel{attackingLineCol.r,attackingLineCol.g,attackingLineCol.b,uint8_t(IsFriendly()?200:160)}); game.DrawPartialRotatedDecal(lineToTarget.upoint(0.5),attackingLine.Decal(),lineToTarget.vector().polar().y,{lineToTarget.length()/2,12},{lineShift*30,0},{lineToTarget.length(),24},{1,1+(attackFailed?-0.3f:(reloadTimer/reloadSpd)*0.25f)},attackFailed?Pixel{192,192,192,130}:Pixel{attackingLineCol.r,attackingLineCol.g,attackingLineCol.b,uint8_t(IsFriendly()?200:160)});
} }
@ -572,11 +585,11 @@ void Unit::DrawUnitDamageStats(PixelGameEngine*pge,TileTransformedView&game,std:
auto DrawStatDown=[&](Marker&maxStat,int currentStat,vf2d pos,vf2d downDisplayPos,Image img,uint8_t transparency=255){ auto DrawStatDown=[&](Marker&maxStat,int currentStat,vf2d pos,vf2d downDisplayPos,Image img,uint8_t transparency=255){
if(maxStat.size>0){ if(maxStat.size>0){
if(currentStat!=maxStat.size){ if(currentStat!=maxStat.size){
game.DrawDecal(this->pos+pos,IMAGES[img]->Decal(),{1,1},currentStat==0?Pixel{192,64,64,transparency}:Pixel{255,255,255,transparency}); game.DrawDecal(this->pos+pos,IMAGES[img].Decal(),{1,1},currentStat==0?Pixel{192,64,64,transparency}:Pixel{255,255,255,transparency});
if(currentStat>0){ if(currentStat>0){
game.DrawDecal(this->pos+downDisplayPos,IMAGES[DOWN_ARROW]->Decal(),{1,1},{255,255,255,transparency}); game.DrawDecal(this->pos+downDisplayPos,IMAGES[DOWN_ARROW].Decal(),{1,1},{255,255,255,transparency});
} else { } else {
game.DrawDecal(this->pos+downDisplayPos,IMAGES[RED_X]->Decal(),{1,1},{255,255,255,transparency}); game.DrawDecal(this->pos+downDisplayPos,IMAGES[RED_X].Decal(),{1,1},{255,255,255,transparency});
} }
} }
} }
@ -639,7 +652,7 @@ void Unit::_RunAI(PixelGameEngine*pge){
RunAI(pge); RunAI(pge);
} }
void Unit::_Update(PixelGameEngine*pge,std::map<Sound,std::unique_ptr<Audio>>&SOUNDS,Resources&player_resources,Resources&enemy_resources,std::vector<std::unique_ptr<Unit>>&queuedUnits,std::array<float,5>&resourceGainTimer,std::vector<ResourceGainIcon>&resourceGainIcons,std::map<Image,std::unique_ptr<Renderable>>&IMAGES){ void Unit::_Update(PixelGameEngine*pge,std::map<Sound,std::unique_ptr<Audio>>&SOUNDS,Resources&player_resources,Resources&enemy_resources,std::vector<std::unique_ptr<Unit>>&queuedUnits,std::array<float,5>&resourceGainTimer,std::vector<ResourceGainIcon>&resourceGainIcons,std::vector<Renderable>&IMAGES){
if(!target.expired()){ if(!target.expired()){
auto ptrTarget=target.lock(); auto ptrTarget=target.lock();
if(!InRange(ptrTarget)&&CanMove()){ if(!InRange(ptrTarget)&&CanMove()){
@ -684,7 +697,7 @@ void Unit::_Update(PixelGameEngine*pge,std::map<Sound,std::unique_ptr<Audio>>&SO
targetResource.procedure++; targetResource.procedure++;
}break; }break;
} }
resourceGainIcons.push_back({IMAGES[RESOURCE].get(),attachedPoint.lock()->type,GetPos()}); resourceGainIcons.emplace_back(&IMAGES[RESOURCE],attachedPoint.lock()->type,GetPos());
} }
} }
@ -788,7 +801,7 @@ void Unit::SetPos(vf2d newPos){
pos=newPos; pos=newPos;
} }
void Unit::AttemptAttack(std::weak_ptr<Unit>attacker,std::weak_ptr<Unit>unit,std::vector<std::shared_ptr<Unit>>&otherUnits,std::vector<DebuffIcon>&debuffIcons,std::map<Image,std::unique_ptr<Renderable>>&IMAGES){ void Unit::AttemptAttack(std::weak_ptr<Unit>attacker,std::weak_ptr<Unit>unit,std::vector<std::shared_ptr<Unit>>&otherUnits,std::vector<DebuffIcon>&debuffIcons,std::vector<Renderable>&IMAGES){
if(reloadTimer>0)return; if(reloadTimer>0)return;
std::weak_ptr<Unit>finalTarget; std::weak_ptr<Unit>finalTarget;
if(!unit.expired()){ if(!unit.expired()){
@ -809,16 +822,16 @@ void Unit::AttemptAttack(std::weak_ptr<Unit>attacker,std::weak_ptr<Unit>unit,std
bool hadProcedure=finalTarget.lock()->GetProcedure()>0; bool hadProcedure=finalTarget.lock()->GetProcedure()>0;
_Attack(attacker,finalTarget,otherUnits); //Call the parent function first, followed by the child. _Attack(attacker,finalTarget,otherUnits); //Call the parent function first, followed by the child.
if(hadAtkSpd&&finalTarget.lock()->GetAtkSpd()==0){ if(hadAtkSpd&&finalTarget.lock()->GetAtkSpd()==0){
debuffIcons.emplace_back(IMAGES[RLD_ICON].get(),IMAGES[RED_X].get(),finalTarget.lock()->GetPos()-vf2d{util::random(12)-6,4}); debuffIcons.emplace_back(&IMAGES[RLD_ICON],&IMAGES[RED_X],finalTarget.lock()->GetPos()-vf2d{util::random(12)-6,4});
} }
if(hadMoveSpd&&finalTarget.lock()->GetMoveSpd()==0){ if(hadMoveSpd&&finalTarget.lock()->GetMoveSpd()==0){
debuffIcons.emplace_back(IMAGES[SPD_ICON].get(),IMAGES[RED_X].get(),finalTarget.lock()->GetPos()-vf2d{util::random(12)-6,4}); debuffIcons.emplace_back(&IMAGES[SPD_ICON],&IMAGES[RED_X],finalTarget.lock()->GetPos()-vf2d{util::random(12)-6,4});
} }
if(hadRange&&finalTarget.lock()->GetRange()==0){ if(hadRange&&finalTarget.lock()->GetRange()==0){
debuffIcons.emplace_back(IMAGES[RNG_ICON].get(),IMAGES[RED_X].get(),finalTarget.lock()->GetPos()-vf2d{util::random(12)-6,4}); debuffIcons.emplace_back(&IMAGES[RNG_ICON],&IMAGES[RED_X],finalTarget.lock()->GetPos()-vf2d{util::random(12)-6,4});
} }
if(hadProcedure&&finalTarget.lock()->GetProcedure()==0){ if(hadProcedure&&finalTarget.lock()->GetProcedure()==0){
debuffIcons.emplace_back(IMAGES[PRC_ICON].get(),IMAGES[RED_X].get(),finalTarget.lock()->GetPos()-vf2d{util::random(12)-6,4}); debuffIcons.emplace_back(&IMAGES[PRC_ICON],&IMAGES[RED_X],finalTarget.lock()->GetPos()-vf2d{util::random(12)-6,4});
} }
} }
} }
@ -931,7 +944,7 @@ Pixel Unit::GetUnitColor(){
} }
} }
bool Unit::ClickHandled(TileTransformedView&game,Resources&player_resources,std::vector<std::shared_ptr<Unit>>&units,std::map<Image,std::unique_ptr<Renderable>>&IMAGES){ bool Unit::ClickHandled(TileTransformedView&game,Resources&player_resources,std::vector<std::shared_ptr<Unit>>&units,std::vector<Renderable>&IMAGES){
return false; return false;
}; };

@ -41,6 +41,7 @@ struct Memory{
struct Unit{ struct Unit{
public: public:
Unit(PixelGameEngine*pge,std::vector<Memory>memory,vf2d pos,float radius,Renderable&img,Pixel targetLineColor,Pixel attackingLineColor,bool friendly=false,bool moveable=true,bool friendlyInteractable=false,bool enemyInteractable=true); Unit(PixelGameEngine*pge,std::vector<Memory>memory,vf2d pos,float radius,Renderable&img,Pixel targetLineColor,Pixel attackingLineColor,bool friendly=false,bool moveable=true,bool friendlyInteractable=false,bool enemyInteractable=true);
virtual ~Unit();
int GetHealth(); int GetHealth();
int GetRange(); int GetRange();
int GetAtkSpd(); int GetAtkSpd();
@ -52,9 +53,9 @@ public:
std::vector<bool>savedMemory; std::vector<bool>savedMemory;
virtual void Update(PixelGameEngine*pge,std::map<Sound,std::unique_ptr<Audio>>&SOUNDS,std::vector<std::unique_ptr<Unit>>&queuedUnits); virtual void Update(PixelGameEngine*pge,std::map<Sound,std::unique_ptr<Audio>>&SOUNDS,std::vector<std::unique_ptr<Unit>>&queuedUnits);
virtual void Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits)=0; virtual void Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits)=0;
virtual void Draw(TileTransformedView&game,std::map<Image,std::unique_ptr<Renderable>>&IMAGES); virtual void Draw(TileTransformedView&game,std::vector<Renderable>&IMAGES);
virtual void DrawHud(TileTransformedView&game,std::map<Image,std::unique_ptr<Renderable>>&IMAGES); virtual void DrawHud(TileTransformedView&game,std::vector<Renderable>&IMAGES);
void _DrawHud(TileTransformedView&game,std::map<Image,std::unique_ptr<Renderable>>&IMAGES); void _DrawHud(TileTransformedView&game,std::vector<Renderable>&IMAGES);
virtual void OnDeath(std::map<Sound,std::unique_ptr<Audio>>&SOUNDS); virtual void OnDeath(std::map<Sound,std::unique_ptr<Audio>>&SOUNDS);
bool IsFriendly(); bool IsFriendly();
bool IsSelected(); bool IsSelected();
@ -66,14 +67,14 @@ public:
void SetTargetUnit(std::weak_ptr<Unit>target); void SetTargetUnit(std::weak_ptr<Unit>target);
void SetTargetLocation(vf2d targetLoc); void SetTargetLocation(vf2d targetLoc);
void SetPos(vf2d newPos); void SetPos(vf2d newPos);
void AttemptAttack(std::weak_ptr<Unit>attacker,std::weak_ptr<Unit>unit,std::vector<std::shared_ptr<Unit>>&otherUnits,std::vector<DebuffIcon>&debuffIcons,std::map<Image,std::unique_ptr<Renderable>>&IMAGES); void AttemptAttack(std::weak_ptr<Unit>attacker,std::weak_ptr<Unit>unit,std::vector<std::shared_ptr<Unit>>&otherUnits,std::vector<DebuffIcon>&debuffIcons,std::vector<Renderable>&IMAGES);
bool InFogOfWar(); bool InFogOfWar();
bool GhostInFogOfWar(); bool GhostInFogOfWar();
void HideGhost(); void HideGhost();
vf2d GetGhostPos(); vf2d GetGhostPos();
void _Update(PixelGameEngine*pge,std::map<Sound,std::unique_ptr<Audio>>&SOUNDS,Resources&player_resources,Resources&enemy_resources,std::vector<std::unique_ptr<Unit>>&queuedUnits,std::array<float,5>&resourceGainTimer,std::vector<ResourceGainIcon>&resourceGainIcons,std::map<Image,std::unique_ptr<Renderable>>&IMAGES); void _Update(PixelGameEngine*pge,std::map<Sound,std::unique_ptr<Audio>>&SOUNDS,Resources&player_resources,Resources&enemy_resources,std::vector<std::unique_ptr<Unit>>&queuedUnits,std::array<float,5>&resourceGainTimer,std::vector<ResourceGainIcon>&resourceGainIcons,std::vector<Renderable>&IMAGES);
bool IsMoveable(); bool IsMoveable();
void DrawRangeIndicator(PixelGameEngine*pge,TileTransformedView&game,std::map<Image,std::unique_ptr<Renderable>>&IMAGES); void DrawRangeIndicator(PixelGameEngine*pge,TileTransformedView&game,std::vector<Renderable>&IMAGES);
bool CanInteractWithEnemies(); bool CanInteractWithEnemies();
bool CanInteractWithAllies(); bool CanInteractWithAllies();
Renderable&GetImage(); Renderable&GetImage();
@ -82,13 +83,13 @@ public:
virtual void Attacked(std::weak_ptr<Unit>attacker); virtual void Attacked(std::weak_ptr<Unit>attacker);
void _Attacked(std::weak_ptr<Unit>attacker); void _Attacked(std::weak_ptr<Unit>attacker);
std::weak_ptr<Unit>GetCurrentTarget(); std::weak_ptr<Unit>GetCurrentTarget();
void DrawUnitDamageStats(PixelGameEngine*pge,TileTransformedView&game,std::map<Image,std::unique_ptr<Renderable>>&IMAGES); void DrawUnitDamageStats(PixelGameEngine*pge,TileTransformedView&game,std::vector<Renderable>&IMAGES);
bool AutoAcquiresFriendlyTargets(); bool AutoAcquiresFriendlyTargets();
bool CanMove(); bool CanMove();
void SetTargetCollectionPoint(std::weak_ptr<CollectionPoint>targetCP,std::weak_ptr<Unit>self_ptr); void SetTargetCollectionPoint(std::weak_ptr<CollectionPoint>targetCP,std::weak_ptr<Unit>self_ptr);
Pixel GetUnitColor(); Pixel GetUnitColor();
virtual void UpdateGUIState(TileTransformedView&game,Resources&player_resources,Textbox&displayBox,bool&hovered,int totalUsedMemory,int availableMemory); virtual void UpdateGUIState(TileTransformedView&game,Resources&player_resources,Textbox&displayBox,bool&hovered,int totalUsedMemory,int availableMemory);
virtual bool ClickHandled(TileTransformedView&game,Resources&player_resources,std::vector<std::shared_ptr<Unit>>&units,std::map<Image,std::unique_ptr<Renderable>>&IMAGES); //If you return true here, then the left click does not pass back to the main Virus Attack class. virtual bool ClickHandled(TileTransformedView&game,Resources&player_resources,std::vector<std::shared_ptr<Unit>>&units,std::vector<Renderable>&IMAGES); //If you return true here, then the left click does not pass back to the main Virus Attack class.
bool IsAllocator(); bool IsAllocator();
void SetBuildUnit(float buildTime,std::unique_ptr<Unit>finalUnit); void SetBuildUnit(float buildTime,std::unique_ptr<Unit>finalUnit);
bool IsBuilding(); bool IsBuilding();
@ -161,7 +162,8 @@ private:
}; };
struct LeftShifter:Unit{ struct LeftShifter:Unit{
LeftShifter(PixelGameEngine*pge,vf2d pos,std::map<Image,std::unique_ptr<Renderable>>&IMAGES,bool friendly=false,bool moveable=true); LeftShifter(PixelGameEngine*pge,vf2d pos,std::vector<Renderable>&IMAGES,bool friendly=false,bool moveable=true);
~LeftShifter();
void Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits)override; void Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits)override;
static std::vector<Memory> resourceCost; static std::vector<Memory> resourceCost;
static std::string unitName; static std::string unitName;
@ -169,7 +171,8 @@ struct LeftShifter:Unit{
}; };
struct RightShifter:Unit{ struct RightShifter:Unit{
RightShifter(PixelGameEngine*pge,vf2d pos,std::map<Image,std::unique_ptr<Renderable>>&IMAGES,bool friendly=false,bool moveable=true); RightShifter(PixelGameEngine*pge,vf2d pos,std::vector<Renderable>&IMAGES,bool friendly=false,bool moveable=true);
~RightShifter();
void Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits)override; void Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits)override;
static std::vector<Memory> resourceCost; static std::vector<Memory> resourceCost;
static std::string unitName; static std::string unitName;
@ -177,7 +180,8 @@ struct RightShifter:Unit{
}; };
struct BitRestorer:Unit{ struct BitRestorer:Unit{
BitRestorer(PixelGameEngine*pge,vf2d pos,std::map<Image,std::unique_ptr<Renderable>>&IMAGES,bool friendly=false,bool moveable=true); BitRestorer(PixelGameEngine*pge,vf2d pos,std::vector<Renderable>&IMAGES,bool friendly=false,bool moveable=true);
~BitRestorer();
void Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits)override; void Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits)override;
void AttemptToHealOtherAllies(std::vector<std::shared_ptr<Unit>>&otherUnits); void AttemptToHealOtherAllies(std::vector<std::shared_ptr<Unit>>&otherUnits);
static std::vector<Memory> resourceCost; static std::vector<Memory> resourceCost;
@ -186,7 +190,8 @@ struct BitRestorer:Unit{
}; };
struct MemorySwapper:Unit{ struct MemorySwapper:Unit{
MemorySwapper(PixelGameEngine*pge,vf2d pos,std::map<Image,std::unique_ptr<Renderable>>&IMAGES,bool friendly=false,bool moveable=true); MemorySwapper(PixelGameEngine*pge,vf2d pos,std::vector<Renderable>&IMAGES,bool friendly=false,bool moveable=true);
~MemorySwapper();
void Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits)override; void Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits)override;
static std::vector<Memory> resourceCost; static std::vector<Memory> resourceCost;
static std::string unitName; static std::string unitName;
@ -194,7 +199,8 @@ struct MemorySwapper:Unit{
}; };
struct Corrupter:Unit{ struct Corrupter:Unit{
Corrupter(PixelGameEngine*pge,vf2d pos,std::map<Image,std::unique_ptr<Renderable>>&IMAGES,bool friendly=false,bool moveable=true); Corrupter(PixelGameEngine*pge,vf2d pos,std::vector<Renderable>&IMAGES,bool friendly=false,bool moveable=true);
~Corrupter();
void Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits)override; void Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits)override;
static std::vector<Memory> resourceCost; static std::vector<Memory> resourceCost;
static std::string unitName; static std::string unitName;
@ -202,10 +208,11 @@ struct Corrupter:Unit{
}; };
struct MemoryAllocator:Unit{ struct MemoryAllocator:Unit{
MemoryAllocator(PixelGameEngine*pge,vf2d pos,std::map<Image,std::unique_ptr<Renderable>>&IMAGES,bool friendly=false,bool moveable=true); MemoryAllocator(PixelGameEngine*pge,vf2d pos,std::vector<Renderable>&IMAGES,bool friendly=false,bool moveable=true);
~MemoryAllocator();
void Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&units)override; void Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&units)override;
void Update(PixelGameEngine*pge,std::map<Sound,std::unique_ptr<Audio>>&SOUNDS,std::vector<std::unique_ptr<Unit>>&queuedUnits)override; void Update(PixelGameEngine*pge,std::map<Sound,std::unique_ptr<Audio>>&SOUNDS,std::vector<std::unique_ptr<Unit>>&queuedUnits)override;
void Draw(TileTransformedView&game,std::map<Image,std::unique_ptr<Renderable>>&IMAGES)override; void Draw(TileTransformedView&game,std::vector<Renderable>&IMAGES)override;
static std::vector<Memory> resourceCost; static std::vector<Memory> resourceCost;
static std::string unitName; static std::string unitName;
static std::string unitDescription; static std::string unitDescription;
@ -220,31 +227,34 @@ struct RAMBank:Unit{
int soundHandle; int soundHandle;
QuickGUI::Manager allocatorManager; QuickGUI::Manager allocatorManager;
QuickGUI::ImageButton*allocatorButton; QuickGUI::ImageButton*allocatorButton;
RAMBank(PixelGameEngine*pge,vf2d pos,std::map<Image,std::unique_ptr<Renderable>>&IMAGES,bool friendly=false); RAMBank(PixelGameEngine*pge,vf2d pos,std::vector<Renderable>&IMAGES,bool friendly=false);
~RAMBank();
void Update(PixelGameEngine*pge,std::map<Sound,std::unique_ptr<Audio>>&SOUNDS,std::vector<std::unique_ptr<Unit>>&queuedUnits)override; void Update(PixelGameEngine*pge,std::map<Sound,std::unique_ptr<Audio>>&SOUNDS,std::vector<std::unique_ptr<Unit>>&queuedUnits)override;
void Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits)override; void Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits)override;
void Draw(TileTransformedView&game,std::map<Image,std::unique_ptr<Renderable>>&IMAGES)override; void Draw(TileTransformedView&game,std::vector<Renderable>&IMAGES)override;
void OnDeath(std::map<Sound,std::unique_ptr<Audio>>&SOUNDS)override; void OnDeath(std::map<Sound,std::unique_ptr<Audio>>&SOUNDS)override;
bool ClickHandled(TileTransformedView&game,Resources&player_resources,std::vector<std::shared_ptr<Unit>>&units,std::map<Image,std::unique_ptr<Renderable>>&IMAGES)override; bool ClickHandled(TileTransformedView&game,Resources&player_resources,std::vector<std::shared_ptr<Unit>>&units,std::vector<Renderable>&IMAGES)override;
void UpdateGUIState(TileTransformedView&game,Resources&player_resources,Textbox&displayBox,bool&hovered,int totalUsedMemory,int availableMemory)override; void UpdateGUIState(TileTransformedView&game,Resources&player_resources,Textbox&displayBox,bool&hovered,int totalUsedMemory,int availableMemory)override;
void DrawHud(TileTransformedView&game,std::map<Image,std::unique_ptr<Renderable>>&IMAGES)override; void DrawHud(TileTransformedView&game,std::vector<Renderable>&IMAGES)override;
static std::vector<Memory> resourceCost; static std::vector<Memory> resourceCost;
static std::string unitName; static std::string unitName;
static std::string unitDescription; static std::string unitDescription;
}; };
struct _Platform:Unit{ struct _Platform:Unit{
_Platform(PixelGameEngine*pge,vf2d pos,std::map<Image,std::unique_ptr<Renderable>>&IMAGES,bool friendly=false,bool moveable=true); _Platform(PixelGameEngine*pge,vf2d pos,std::vector<Renderable>&IMAGES,bool friendly=false,bool moveable=true);
~_Platform();
void Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits)override; void Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits)override;
void Update(PixelGameEngine*pge,std::map<Sound,std::unique_ptr<Audio>>&SOUNDS,std::vector<std::unique_ptr<Unit>>&queuedUnits)override; void Update(PixelGameEngine*pge,std::map<Sound,std::unique_ptr<Audio>>&SOUNDS,std::vector<std::unique_ptr<Unit>>&queuedUnits)override;
void Draw(TileTransformedView&game,std::map<Image,std::unique_ptr<Renderable>>&IMAGES)override; void Draw(TileTransformedView&game,std::vector<Renderable>&IMAGES)override;
static std::vector<Memory> resourceCost; static std::vector<Memory> resourceCost;
static std::string unitName; static std::string unitName;
static std::string unitDescription; static std::string unitDescription;
}; };
struct MemoryGuard:Unit{ struct MemoryGuard:Unit{
MemoryGuard(PixelGameEngine*pge,vf2d pos,std::map<Image,std::unique_ptr<Renderable>>&IMAGES,bool friendly=false,bool moveable=true); MemoryGuard(PixelGameEngine*pge,vf2d pos,std::vector<Renderable>&IMAGES,bool friendly=false,bool moveable=true);
~MemoryGuard();
void Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits)override; void Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits)override;
static std::vector<Memory> resourceCost; static std::vector<Memory> resourceCost;
static std::string unitName; static std::string unitName;
@ -252,7 +262,8 @@ struct MemoryGuard:Unit{
}; };
struct Refresher:Unit{ struct Refresher:Unit{
Refresher(PixelGameEngine*pge,vf2d pos,std::map<Image,std::unique_ptr<Renderable>>&IMAGES,bool friendly=false,bool moveable=true); Refresher(PixelGameEngine*pge,vf2d pos,std::vector<Renderable>&IMAGES,bool friendly=false,bool moveable=true);
~Refresher();
void Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits)override; void Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits)override;
static std::vector<Memory> resourceCost; static std::vector<Memory> resourceCost;
static std::string unitName; static std::string unitName;
@ -260,7 +271,8 @@ struct Refresher:Unit{
}; };
struct Turret:Unit{ struct Turret:Unit{
Turret(PixelGameEngine*pge,vf2d pos,std::map<Image,std::unique_ptr<Renderable>>&IMAGES,bool friendly=false,bool moveable=true); Turret(PixelGameEngine*pge,vf2d pos,std::vector<Renderable>&IMAGES,bool friendly=false,bool moveable=true);
~Turret();
void Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits)override; void Attack(Unit&victim,std::vector<std::shared_ptr<Unit>>&otherUnits)override;
static std::vector<Memory> resourceCost; static std::vector<Memory> resourceCost;
static std::string unitName; static std::string unitName;

@ -15,22 +15,33 @@
#include "util.h" #include "util.h"
#include "Scenario.h" #include "Scenario.h"
VirusAttack*game;
VirusAttack::VirusAttack() VirusAttack::VirusAttack()
{ {
// Name your application // Name your application
sAppName = "Virus Attack"; sAppName = "Virus Attack";
game=this;
} }
void VirusAttack::InitializeImages(){ void VirusAttack::InitializeImages(){
#undef LoadImage
auto LoadImage=[&](Image img,std::string filepath,bool filter=false,bool clamp=true){ auto LoadImage=[&](Image img,std::string filepath,bool filter=false,bool clamp=true){
IMAGES[img]=std::make_unique<Renderable>(); IMAGES.emplace_back();
IMAGES[img]->Load(filepath,nullptr,filter,clamp); IMAGES[img].Load(filepath,nullptr,filter,clamp);
}; };
LoadImage(TILE,"assets/tile.png",false,false); LoadImage(TILE,"assets/tile.png",false,false);
LoadImage(MINIMAP_HUD,"assets/minimap_hud.png"); LoadImage(MINIMAP_HUD,"assets/minimap_hud.png");
LoadImage(OUTLINE,"assets/outline.png"); LoadImage(OUTLINE,"assets/outline.png");
IMAGES.emplace_back();
IMAGES[MINIMAP_OUTLINE].Create(64,64);
LoadImage(VIRUS_IMG1,"assets/unit.png"); LoadImage(VIRUS_IMG1,"assets/unit.png");
LoadImage(SELECTION_CIRCLE,"assets/selection_circle.png"); LoadImage(SELECTION_CIRCLE,"assets/selection_circle.png");
IMAGES.emplace_back();
IMAGES[MATRIX].Create(64,64,false,false);
IMAGES[MATRIX].Sprite()->SetSampleMode(Sprite::PERIODIC);
LoadImage(MEMORY_COLLECTION_POINT,"assets/memory_collection_point.png"); LoadImage(MEMORY_COLLECTION_POINT,"assets/memory_collection_point.png");
LoadImage(LEFT_SHIFTER,"assets/left_shifter.png"); LoadImage(LEFT_SHIFTER,"assets/left_shifter.png");
LoadImage(RIGHT_SHIFTER,"assets/right_shifter.png"); LoadImage(RIGHT_SHIFTER,"assets/right_shifter.png");
@ -62,6 +73,10 @@ void VirusAttack::InitializeImages(){
LoadImage(GUIDE,"assets/guide.png"); LoadImage(GUIDE,"assets/guide.png");
LoadImage(ROUND_BAR,"assets/round_bar.png"); LoadImage(ROUND_BAR,"assets/round_bar.png");
LoadImage(SEGMENT_BAR,"assets/segmentBar.png",false,false); LoadImage(SEGMENT_BAR,"assets/segmentBar.png",false,false);
LoadImage(HOODED_FIGURE,"assets/hooded_figure.png");
LoadImage(SPOOK_HOODED_FIGURE,"assets/spook_hooded_figure.png");
HOODED_FIGURE_IMG.Load("assets/hooded_figure.png",nullptr);
SPOOK_HOODED_FIGURE_IMG.Load("assets/hooded_figure.png",nullptr);
} }
void VirusAttack::InitializeLevelData(){ void VirusAttack::InitializeLevelData(){
@ -133,7 +148,7 @@ bool VirusAttack::OnUserCreate(){
srand(time(NULL)); srand(time(NULL));
SetPixelMode(Pixel::MASK); SetPixelMode(Pixel::MASK);
game.Initialise(GetScreenSize()); gametv.Initialise(GetScreenSize());
InitializeImages(); InitializeImages();
@ -145,13 +160,6 @@ bool VirusAttack::OnUserCreate(){
memoryAllocatorBox.Initialize(CONSTANT::MEMORY_ALLOCATOR_BOX_DISPLAY_STRING,{},CONSTANT::MEMORY_ALLOCATOR_BOX_HEADER_STRING); memoryAllocatorBox.Initialize(CONSTANT::MEMORY_ALLOCATOR_BOX_DISPLAY_STRING,{},CONSTANT::MEMORY_ALLOCATOR_BOX_HEADER_STRING);
memoryAllocatorBox.SetVisible(false); memoryAllocatorBox.SetVisible(false);
IMAGES[MINIMAP_OUTLINE]=std::make_unique<Renderable>();
IMAGES[MINIMAP_OUTLINE]->Create(64,64);
IMAGES[MATRIX]=std::make_unique<Renderable>();
IMAGES[MATRIX]->Create(64,64,false,false);
IMAGES[MATRIX]->Sprite()->SetSampleMode(Sprite::PERIODIC);
AL.AudioSystemInit(); AL.AudioSystemInit();
InitializeSounds(); InitializeSounds();
@ -171,8 +179,8 @@ void VirusAttack::LoadLevel(LevelName level){
WORLD_SIZE=selectedLevel.size; WORLD_SIZE=selectedLevel.size;
game.SetWorldScale(selectedLevel.worldZoom); gametv.SetWorldScale(selectedLevel.worldZoom);
game.SetWorldOffset(selectedLevel.cameraStart-vf2d(GetScreenSize())/2.f/game.GetWorldScale()); gametv.SetWorldOffset(selectedLevel.cameraStart-vf2d(GetScreenSize())/2.f/gametv.GetWorldScale());
if(bgm==nullptr){ if(bgm==nullptr){
bgm=SOUNDS[selectedLevel.bgm].get(); bgm=SOUNDS[selectedLevel.bgm].get();
@ -196,7 +204,7 @@ void VirusAttack::LoadLevel(LevelName level){
for(auto&u:selectedLevel.unitPlacement){ for(auto&u:selectedLevel.unitPlacement){
#define TranslateUnit(type) \ #define TranslateUnit(type) \
case UnitType::type:{ \ case UnitType::type:{ \
units.push_back(std::make_unique<type>(this,u.pos,IMAGES,u.friendly)); \ units.push_back(std::make_shared<type>(this,u.pos,IMAGES,u.friendly)); \
}break; }break;
switch(u.type){ switch(u.type){
@ -218,7 +226,7 @@ void VirusAttack::LoadLevel(LevelName level){
} }
} }
for(auto&cp:selectedLevel.cpPlacement){ for(auto&cp:selectedLevel.cpPlacement){
collectionPoints.push_back(std::make_unique<CollectionPoint>(this,cp.pos,cp.rot,*IMAGES[MEMORY_COLLECTION_POINT],cp.type)); collectionPoints.push_back(std::make_shared<CollectionPoint>(this,cp.pos,cp.rot,IMAGES[MEMORY_COLLECTION_POINT],cp.type));
} }
randomBackgroundOffset={util::random(128),util::random(128)}; randomBackgroundOffset={util::random(128),util::random(128)};
@ -232,22 +240,22 @@ void VirusAttack::InitializeGUIs(){
unitCreationList.colBorder = olc::YELLOW; unitCreationList.colBorder = olc::YELLOW;
unitCreationList.colText = olc::WHITE; unitCreationList.colText = olc::WHITE;
platformCreationList.CopyThemeFrom(unitCreationList); platformCreationList.CopyThemeFrom(unitCreationList);
leftShifterButton=new QuickGUI::ImageButton(unitCreationList,*IMAGES[LEFT_SHIFTER],{0.5,0.5},{16.f+32*0,float(ScreenHeight()-48)},{20,20}); leftShifterButton=new QuickGUI::ImageButton(unitCreationList,IMAGES[LEFT_SHIFTER],{0.5,0.5},{16.f+32*0,float(ScreenHeight()-48)},{20,20});
rightShifterButton=new QuickGUI::ImageButton(unitCreationList,*IMAGES[RIGHT_SHIFTER],{0.5,0.5},{16.f+32*1,float(ScreenHeight()-48)},{20,20}); rightShifterButton=new QuickGUI::ImageButton(unitCreationList,IMAGES[RIGHT_SHIFTER],{0.5,0.5},{16.f+32*1,float(ScreenHeight()-48)},{20,20});
bitRestorerButton=new QuickGUI::ImageButton(unitCreationList,*IMAGES[BIT_RESTORER],{0.5,0.5},{16.f+32*2,float(ScreenHeight()-48)},{20,20}); bitRestorerButton=new QuickGUI::ImageButton(unitCreationList,IMAGES[BIT_RESTORER],{0.5,0.5},{16.f+32*2,float(ScreenHeight()-48)},{20,20});
memorySwapperButton=new QuickGUI::ImageButton(unitCreationList,*IMAGES[MEMORY_SWAPPER],{0.5,0.5},{16.f+32*3,float(ScreenHeight()-48)},{20,20}); memorySwapperButton=new QuickGUI::ImageButton(unitCreationList,IMAGES[MEMORY_SWAPPER],{0.5,0.5},{16.f+32*3,float(ScreenHeight()-48)},{20,20});
corrupterButton=new QuickGUI::ImageButton(unitCreationList,*IMAGES[CORRUPTER],{0.5,0.5},{16.f+32*4,float(ScreenHeight()-48)},{20,20}); corrupterButton=new QuickGUI::ImageButton(unitCreationList,IMAGES[CORRUPTER],{0.5,0.5},{16.f+32*4,float(ScreenHeight()-48)},{20,20});
platformButton=new QuickGUI::ImageButton(unitCreationList,*IMAGES[PLATFORM],{0.25,0.25},{16.f+32*5,float(ScreenHeight()-48)},{20,20}); platformButton=new QuickGUI::ImageButton(unitCreationList,IMAGES[PLATFORM],{0.25,0.25},{16.f+32*5,float(ScreenHeight()-48)},{20,20});
ramBankButton=new QuickGUI::ImageButton(platformCreationList,*IMAGES[RAM_BANK],{0.125,0.125},{float(ScreenWidth()-48),48.f+32*0},{20,20}); ramBankButton=new QuickGUI::ImageButton(platformCreationList,IMAGES[RAM_BANK],{0.125,0.125},{float(ScreenWidth()-48),48.f+32*0},{20,20});
refresherButton=new QuickGUI::ImageButton(platformCreationList,*IMAGES[REFRESHER],{0.25,0.25},{float(ScreenWidth()-48),48.f+32*1},{20,20}); refresherButton=new QuickGUI::ImageButton(platformCreationList,IMAGES[REFRESHER],{0.25,0.25},{float(ScreenWidth()-48),48.f+32*1},{20,20});
turretButton=new QuickGUI::ImageButton(platformCreationList,*IMAGES[TURRET],{0.25,0.25},{float(ScreenWidth()-48),48.f+32*2},{20,20}); turretButton=new QuickGUI::ImageButton(platformCreationList,IMAGES[TURRET],{0.25,0.25},{float(ScreenWidth()-48),48.f+32*2},{20,20});
memoryGuardButton=new QuickGUI::ImageButton(platformCreationList,*IMAGES[MEMORY_GUARD],{0.25,0.25},{float(ScreenWidth()-48),48.f+32*3},{20,20}); memoryGuardButton=new QuickGUI::ImageButton(platformCreationList,IMAGES[MEMORY_GUARD],{0.25,0.25},{float(ScreenWidth()-48),48.f+32*3},{20,20});
} }
void VirusAttack::InitializeScenarios(){ void VirusAttack::InitializeScenarios(){
scenarios.emplace_back(new Stage1(this)); scenarios.push_back(new Stage1());
scenarios.emplace_back(new Stage1(this)); scenarios.push_back(new Stage1());
} }
void VirusAttack::InitializeSounds(){ void VirusAttack::InitializeSounds(){
@ -296,7 +304,7 @@ bool VirusAttack::UnitCreationClickHandled(){
#define EnableAndHoverCheck(UnitClass,Button,box) \ #define EnableAndHoverCheck(UnitClass,Button,box) \
Button->Enable(CanAfford(player_resources,UnitClass::resourceCost)); \ Button->Enable(CanAfford(player_resources,UnitClass::resourceCost)); \
if(Button->bHover){ \ if(Button->bHover){ \
box.Initialize(UnitClass::unitDescription, GetMousePos(), UnitClass::unitName,{120,36},UnitClass::resourceCost); \ box.Initialize(UnitClass::unitDescription, GetMousePos(), UnitClass::unitName,nullptr,{120,36},UnitClass::resourceCost); \
hovering=true; \ hovering=true; \
if(CanAfford(player_resources,UnitClass::resourceCost)){ \ if(CanAfford(player_resources,UnitClass::resourceCost)){ \
box.SetBackgroundColor(CONSTANT::MESSAGE_BOX_DEFAULT_BACKCOL); \ box.SetBackgroundColor(CONSTANT::MESSAGE_BOX_DEFAULT_BACKCOL); \
@ -345,7 +353,7 @@ void VirusAttack::HandleDraggingSelection(){
bool platformSelected=false; bool platformSelected=false;
bool memoryAllocatorBoxHovered=false; bool memoryAllocatorBoxHovered=false;
for(auto&u:units){ for(auto&u:units){
u->UpdateGUIState(game,player_resources,memoryAllocatorBox,memoryAllocatorBoxHovered,GetTotalUsedMemory(),currentLevel->availableMemory); u->UpdateGUIState(gametv,player_resources,memoryAllocatorBox,memoryAllocatorBoxHovered,GetTotalUsedMemory(),currentLevel->availableMemory);
if(u->IsSelected()){ if(u->IsSelected()){
if(u->IsAllocator()){ if(u->IsAllocator()){
allocatorSelected=true; allocatorSelected=true;
@ -361,7 +369,7 @@ void VirusAttack::HandleDraggingSelection(){
if(GetMouse(0).bPressed){ if(GetMouse(0).bPressed){
if(NotClickingOnMinimap()){ if(NotClickingOnMinimap()){
for(auto&u:units){ for(auto&u:units){
if(u->ClickHandled(game,player_resources,units,IMAGES)){ if(u->ClickHandled(gametv,player_resources,units,IMAGES)){
goto skipLeftClick; //Break out early because this instance reported it handled a click for us. goto skipLeftClick; //Break out early because this instance reported it handled a click for us.
} }
} }
@ -394,12 +402,12 @@ void VirusAttack::HandleDraggingSelection(){
} }
vf2d VirusAttack::GetWorldMousePos(){ vf2d VirusAttack::GetWorldMousePos(){
return game.ScreenToWorld(GetMousePos()); return gametv.ScreenToWorld(GetMousePos());
} }
void VirusAttack::DrawSelectionRectangle(){ void VirusAttack::DrawSelectionRectangle(){
if(startingDragPos!=CONSTANT::UNSELECTED){ if(startingDragPos!=CONSTANT::UNSELECTED){
game.FillRectDecal(startingDragPos,GetWorldMousePos()-startingDragPos,{255,255,0,128}); gametv.FillRectDecal(startingDragPos,GetWorldMousePos()-startingDragPos,{255,255,0,128});
} }
} }
@ -410,7 +418,7 @@ void VirusAttack::HandleRightClickMove(){
for(auto&u:units){ for(auto&u:units){
if(u->IsFriendly()&&u->IsSelected()&&u->CanMove()){ if(u->IsFriendly()&&u->IsSelected()&&u->CanMove()){
vf2d minimapTL=GetScreenSize()-vf2d{64,64}; vf2d minimapTL=GetScreenSize()-vf2d{64,64};
vf2d minimapCenterClick=vf2d(GetMousePos()-minimapTL)/64*WORLD_SIZE*CONSTANT::TILE_SIZE-vf2d(GetScreenSize())/game.GetWorldScale()/2.f+vf2d(GetScreenSize()/2.f)/game.GetWorldScale(); vf2d minimapCenterClick=vf2d(GetMousePos()-minimapTL)/64*WORLD_SIZE*CONSTANT::TILE_SIZE-vf2d(GetScreenSize())/gametv.GetWorldScale()/2.f+vf2d(GetScreenSize()/2.f)/gametv.GetWorldScale();
u->SetTargetLocation(minimapCenterClick); u->SetTargetLocation(minimapCenterClick);
} }
} }
@ -489,13 +497,13 @@ void VirusAttack::IdentifyClosestTarget(std::weak_ptr<Unit>&closestUnit,float&cl
} }
void VirusAttack::DrawMinimap(){ void VirusAttack::DrawMinimap(){
DrawDecal(GetScreenSize()-IMAGES[MINIMAP_HUD]->Sprite()->Size(),IMAGES[MINIMAP_HUD]->Decal(),{1,1}); DrawDecal(GetScreenSize()-IMAGES[MINIMAP_HUD].Sprite()->Size(),IMAGES[MINIMAP_HUD].Decal(),{1,1});
vf2d minimapTL=GetScreenSize()-vf2d{64,64}; vf2d minimapTL=GetScreenSize()-vf2d{64,64};
vi2d worldPixelSize=WORLD_SIZE*CONSTANT::TILE_SIZE; vi2d worldPixelSize=WORLD_SIZE*CONSTANT::TILE_SIZE;
vf2d viewingTilesPct=vf2d{float(ScreenWidth()),float(ScreenHeight())}/CONSTANT::TILE_SIZE/WORLD_SIZE; vf2d viewingTilesPct=vf2d{float(ScreenWidth()),float(ScreenHeight())}/CONSTANT::TILE_SIZE/WORLD_SIZE;
SetDrawTarget(IMAGES[MINIMAP_OUTLINE]->Sprite()); SetDrawTarget(IMAGES[MINIMAP_OUTLINE].Sprite());
Clear(BLANK); Clear(BLANK);
DrawRect((game.GetWorldOffset()/worldPixelSize*64),viewingTilesPct*64/game.GetWorldScale()); DrawRect((gametv.GetWorldOffset()/worldPixelSize*64),viewingTilesPct*64/gametv.GetWorldScale());
for(auto&cp:collectionPoints){ for(auto&cp:collectionPoints){
Pixel col; Pixel col;
switch(cp->type){ switch(cp->type){
@ -526,39 +534,39 @@ void VirusAttack::DrawMinimap(){
if(u->IsAttached()){colorMult=0.5;} if(u->IsAttached()){colorMult=0.5;}
FillRect(u->GetGhostPos()/worldPixelSize*64-squareSize,squareSize*2,(u->IsFriendly()?GREEN:RED)*colorMult); FillRect(u->GetGhostPos()/worldPixelSize*64-squareSize,squareSize*2,(u->IsFriendly()?GREEN:RED)*colorMult);
} }
IMAGES[MINIMAP_OUTLINE]->Decal()->Update(); IMAGES[MINIMAP_OUTLINE].Decal()->Update();
SetDrawTarget(nullptr); SetDrawTarget(nullptr);
DrawDecal(minimapTL,IMAGES[MINIMAP_OUTLINE]->Decal()); DrawDecal(minimapTL,IMAGES[MINIMAP_OUTLINE].Decal());
} }
void VirusAttack::HandlePanAndZoom(float fElapsedTime){ void VirusAttack::HandlePanAndZoom(float fElapsedTime){
float speedScale=std::min(1.f,game.GetWorldScale().x); float speedScale=std::min(1.f,gametv.GetWorldScale().x);
bool canMouseScroll=!memoryAllocatorBox.IsVisible()&&!unitCreationBox.IsVisible()&& bool canMouseScroll=!memoryAllocatorBox.IsVisible()&&!unitCreationBox.IsVisible()&&
(GetMouseY()<=ScreenHeight()-64||GetMouseX()<=ScreenWidth()-64 (GetMouseY()<=ScreenHeight()-64||GetMouseX()<=ScreenWidth()-64
||GetMouseScreenX()>=GetWindowPos().x+GetWindowSize().x||GetMouseScreenY()>=GetWindowPos().y+GetWindowSize().y); ||GetMouseScreenX()>=GetWindowPos().x+GetWindowSize().x||GetMouseScreenY()>=GetWindowPos().y+GetWindowSize().y);
if(GetKey(A).bHeld||canMouseScroll&&GetMouseScreenX()<=GetWindowPos().x+CONSTANT::SCROLL_BOUNDARY){ if(GetKey(A).bHeld||canMouseScroll&&GetMouseScreenX()<=GetWindowPos().x+CONSTANT::SCROLL_BOUNDARY){
vf2d amt=vf2d{-300*fElapsedTime,0}/speedScale; vf2d amt=vf2d{-300*fElapsedTime,0}/speedScale;
game.MoveWorldOffset(amt); gametv.MoveWorldOffset(amt);
} }
if(GetKey(W).bHeld||canMouseScroll&&GetMouseScreenY()<=GetWindowPos().y+CONSTANT::SCROLL_BOUNDARY+24){ if(GetKey(W).bHeld||canMouseScroll&&GetMouseScreenY()<=GetWindowPos().y+CONSTANT::SCROLL_BOUNDARY+24){
game.MoveWorldOffset(vf2d{0,-300*fElapsedTime}/speedScale); gametv.MoveWorldOffset(vf2d{0,-300*fElapsedTime}/speedScale);
} }
if(GetKey(S).bHeld||canMouseScroll&&GetMouseScreenY()>=GetWindowPos().y+GetWindowSize().y-CONSTANT::SCROLL_BOUNDARY){ if(GetKey(S).bHeld||canMouseScroll&&GetMouseScreenY()>=GetWindowPos().y+GetWindowSize().y-CONSTANT::SCROLL_BOUNDARY){
game.MoveWorldOffset(vf2d{0,300*fElapsedTime}/speedScale); gametv.MoveWorldOffset(vf2d{0,300*fElapsedTime}/speedScale);
} }
if(GetKey(D).bHeld||canMouseScroll&&GetMouseScreenX()>=GetWindowPos().x+GetWindowSize().x-CONSTANT::SCROLL_BOUNDARY){ if(GetKey(D).bHeld||canMouseScroll&&GetMouseScreenX()>=GetWindowPos().x+GetWindowSize().x-CONSTANT::SCROLL_BOUNDARY){
vf2d amt=vf2d{300*fElapsedTime,0}/speedScale; vf2d amt=vf2d{300*fElapsedTime,0}/speedScale;
game.MoveWorldOffset(amt); gametv.MoveWorldOffset(amt);
} }
if(GetMouseWheel()>0){ if(GetMouseWheel()>0){
if(game.GetWorldScale().x<2){ if(gametv.GetWorldScale().x<2){
game.ZoomAtScreenPos(1.25,GetMousePos()); gametv.ZoomAtScreenPos(1.25,GetMousePos());
} }
} else } else
if(GetMouseWheel()<0){ if(GetMouseWheel()<0){
if(game.GetWorldScale().x>0.5){ if(gametv.GetWorldScale().x>0.5){
game.ZoomAtScreenPos(0.75,GetMousePos()); gametv.ZoomAtScreenPos(0.75,GetMousePos());
} }
} }
} }
@ -566,12 +574,12 @@ void VirusAttack::HandlePanAndZoom(float fElapsedTime){
void VirusAttack::HandleMinimapClick(){ void VirusAttack::HandleMinimapClick(){
if(startingDragPos==CONSTANT::UNSELECTED&&GetMouse(0).bHeld&&GetMouseX()>=ScreenWidth()-64&&GetMouseY()>=ScreenHeight()-64){ if(startingDragPos==CONSTANT::UNSELECTED&&GetMouse(0).bHeld&&GetMouseX()>=ScreenWidth()-64&&GetMouseY()>=ScreenHeight()-64){
vf2d minimapTL=GetScreenSize()-vf2d{64,64}; vf2d minimapTL=GetScreenSize()-vf2d{64,64};
game.SetWorldOffset(vf2d(GetMousePos()-minimapTL)/64*WORLD_SIZE*CONSTANT::TILE_SIZE-vf2d(GetScreenSize())/game.GetWorldScale()/2.f); gametv.SetWorldOffset(vf2d(GetMousePos()-minimapTL)/64*WORLD_SIZE*CONSTANT::TILE_SIZE-vf2d(GetScreenSize())/gametv.GetWorldScale()/2.f);
} }
vf2d offset=game.GetWorldOffset(); vf2d offset=gametv.GetWorldOffset();
offset.x=std::clamp(float(offset.x),-ScreenWidth()/2/game.GetWorldScale().x,WORLD_SIZE.x*24-(ScreenWidth()/2/game.GetWorldScale().x)); offset.x=std::clamp(float(offset.x),-ScreenWidth()/2/gametv.GetWorldScale().x,WORLD_SIZE.x*24-(ScreenWidth()/2/gametv.GetWorldScale().x));
offset.y=std::clamp(float(offset.y),-ScreenHeight()/2/game.GetWorldScale().y,WORLD_SIZE.y*24-(ScreenHeight()/2/game.GetWorldScale().y)); offset.y=std::clamp(float(offset.y),-ScreenHeight()/2/gametv.GetWorldScale().y,WORLD_SIZE.y*24-(ScreenHeight()/2/gametv.GetWorldScale().y));
game.SetWorldOffset(offset); gametv.SetWorldOffset(offset);
} }
@ -581,8 +589,8 @@ void VirusAttack::UpdateMatrixTexture(float fElapsedTime){
matrixTimer=util::random(0.125); matrixTimer=util::random(0.125);
} }
if(updatePixelsTimer==0){ if(updatePixelsTimer==0){
SetDrawTarget(IMAGES[MATRIX]->Sprite()); SetDrawTarget(IMAGES[MATRIX].Sprite());
Sprite*img=IMAGES[MATRIX]->Sprite(); Sprite*img=IMAGES[MATRIX].Sprite();
for(int y=63;y>=0;y--){ for(int y=63;y>=0;y--){
for(int x=63;x>=0;x--){ for(int x=63;x>=0;x--){
Pixel col=img->GetPixel(x,y); Pixel col=img->GetPixel(x,y);
@ -613,13 +621,13 @@ void VirusAttack::UpdateMatrixTexture(float fElapsedTime){
updatePixelsTimer=0.1; updatePixelsTimer=0.1;
} }
if(activeLetters.size()>0){ if(activeLetters.size()>0){
SetDrawTarget(IMAGES[MATRIX]->Sprite()); SetDrawTarget(IMAGES[MATRIX].Sprite());
for(Letter&letter:activeLetters){ for(Letter&letter:activeLetters){
letter.pos.y+=letter.spd*fElapsedTime; letter.pos.y+=letter.spd*fElapsedTime;
DrawString(letter.pos,std::string(1,letter.c)); DrawString(letter.pos,std::string(1,letter.c));
} }
SetDrawTarget(nullptr); SetDrawTarget(nullptr);
IMAGES[MATRIX]->Decal()->Update(); IMAGES[MATRIX].Decal()->Update();
} }
matrixTimer=std::max(0.f,matrixTimer-fElapsedTime); matrixTimer=std::max(0.f,matrixTimer-fElapsedTime);
updatePixelsTimer=std::max(0.f,updatePixelsTimer-fElapsedTime); updatePixelsTimer=std::max(0.f,updatePixelsTimer-fElapsedTime);
@ -628,7 +636,7 @@ void VirusAttack::UpdateMatrixTexture(float fElapsedTime){
void VirusAttack::RenderCollectionPoints(CollectionPoint*cp){ void VirusAttack::RenderCollectionPoints(CollectionPoint*cp){
geom2d::rect<float>cpRect=geom2d::rect<float>({cp->pos-cp->img.Sprite()->Size()/2,cp->img.Sprite()->Size()}); geom2d::rect<float>cpRect=geom2d::rect<float>({cp->pos-cp->img.Sprite()->Size()/2,cp->img.Sprite()->Size()});
geom2d::rect<float>viewRegion=geom2d::rect<float>({game.GetWorldTL(),game.GetWorldVisibleArea()}); geom2d::rect<float>viewRegion=geom2d::rect<float>({gametv.GetWorldTL(),gametv.GetWorldVisibleArea()});
if(geom2d::overlaps(cpRect,viewRegion)){ if(geom2d::overlaps(cpRect,viewRegion)){
Pixel col; Pixel col;
switch(cp->type){ switch(cp->type){
@ -648,9 +656,9 @@ void VirusAttack::RenderCollectionPoints(CollectionPoint*cp){
col=CONSTANT::PROCEDURE_COLOR; col=CONSTANT::PROCEDURE_COLOR;
}break; }break;
} }
game.DrawRotatedDecal(cp->pos,cp->img.Decal(),cp->rot,cp->img.Sprite()->Size()/2,{1,1},col); gametv.DrawRotatedDecal(cp->pos,cp->img.Decal(),cp->rot,cp->img.Sprite()->Size()/2,{1,1},col);
if(geom2d::overlaps(cpRect,GetWorldMousePos())){ if(geom2d::overlaps(cpRect,GetWorldMousePos())){
game.DrawRotatedDecal(cp->pos,IMAGES[MEMORY_COLLECTION_POINT_HIGHLIGHT]->Decal(),cp->rot,cp->img.Sprite()->Size()/2,{1,1},col); gametv.DrawRotatedDecal(cp->pos,IMAGES[MEMORY_COLLECTION_POINT_HIGHLIGHT].Decal(),cp->rot,cp->img.Sprite()->Size()/2,{1,1},col);
} }
} }
} }
@ -661,9 +669,10 @@ bool VirusAttack::OnUserUpdate(float fElapsedTime){
HandleRightClickMove(); HandleRightClickMove();
HandlePanAndZoom(fElapsedTime); HandlePanAndZoom(fElapsedTime);
HandleMinimapClick(); HandleMinimapClick();
std::vector<Renderable>&images=IMAGES;
currentLevel->scenario->_Update(); currentLevel->scenario->_Update();
AL.vecPos=game.ScreenToWorld(GetScreenSize()/2); AL.vecPos=gametv.ScreenToWorld(GetScreenSize()/2);
AL.fSoundFXVolume=std::min(1.f,game.GetWorldScale().x); AL.fSoundFXVolume=std::min(1.f,gametv.GetWorldScale().x);
AL.OnUserUpdate(fElapsedTime); AL.OnUserUpdate(fElapsedTime);
if(GetKey(P).bPressed){ if(GetKey(P).bPressed){
@ -704,7 +713,7 @@ bool VirusAttack::OnUserUpdate(float fElapsedTime){
std::erase_if(units,[&](std::shared_ptr<Unit>u){ std::erase_if(units,[&](std::shared_ptr<Unit>u){
if(u->GetHealth()==0){ if(u->GetHealth()==0){
u->OnDeath(SOUNDS); u->OnDeath(SOUNDS);
deathAnimations.emplace_back(std::make_unique<DeathAnimation>(this,u->GetPos(),u->GetImage(),*IMAGES[MATRIX],u->IsFriendly())); deathAnimations.emplace_back(std::make_unique<DeathAnimation>(this,u->GetPos(),u->GetImage(),IMAGES[MATRIX],u->IsFriendly()));
return true; return true;
} else { } else {
return false; return false;
@ -717,50 +726,50 @@ bool VirusAttack::OnUserUpdate(float fElapsedTime){
queuedUnits.clear(); queuedUnits.clear();
DrawPartialDecal({0,0},GetScreenSize(),IMAGES[MATRIX]->Decal(),randomBackgroundOffset+game.GetWorldOffset()*(vf2d{32,32}/vf2d(GetScreenSize()))*game.GetWorldScale(),{32,32},Pixel{currentLevel->levelColor.r,currentLevel->levelColor.g,currentLevel->levelColor.b,164}/2); DrawPartialDecal({0,0},GetScreenSize(),IMAGES[MATRIX].Decal(),randomBackgroundOffset+gametv.GetWorldOffset()*(vf2d{32,32}/vf2d(GetScreenSize()))*gametv.GetWorldScale(),{32,32},Pixel{currentLevel->levelColor.r,currentLevel->levelColor.g,currentLevel->levelColor.b,164}/2);
game.DrawPartialDecal({0,0},WORLD_SIZE*CONSTANT::TILE_SIZE,IMAGES[TILE]->Decal(),{0,0},WORLD_SIZE*CONSTANT::TILE_SIZE,currentLevel->levelColor); gametv.DrawPartialDecal({0,0},WORLD_SIZE*CONSTANT::TILE_SIZE,IMAGES[TILE].Decal(),{0,0},WORLD_SIZE*CONSTANT::TILE_SIZE,currentLevel->levelColor);
for(auto&u:units){ for(auto&u:units){
u->DrawRangeIndicator(this,game,IMAGES); u->DrawRangeIndicator(this,gametv,IMAGES);
} }
for(auto&u:units){ for(auto&u:units){
u->Draw(game,IMAGES); u->Draw(gametv,IMAGES);
if(u->IsGuarded()){ if(u->IsGuarded()){
game.DrawDecal(u->GetPos()+vf2d{float(u->GetUnitSize().x/2),-float(u->GetUnitSize().y/2)}-vf2d{float(IMAGES[GUARD_ICON]->Sprite()->width),0.f}*0.375,IMAGES[GUARD_ICON]->Decal(),{0.375,0.375}); gametv.DrawDecal(u->GetPos()+vf2d{float(u->GetUnitSize().x/2),-float(u->GetUnitSize().y/2)}-vf2d{float(IMAGES[GUARD_ICON].Sprite()->width),0.f}*0.375,IMAGES[GUARD_ICON].Decal(),{0.375,0.375});
} }
} }
for(auto&deadUnit:deathAnimations){ for(auto&deadUnit:deathAnimations){
deadUnit->Update(fElapsedTime); deadUnit->Update(fElapsedTime);
deadUnit->Draw(game,this); deadUnit->Draw(gametv,this);
} }
std::erase_if(deathAnimations,[](auto&u){return u->IsDone();}); std::erase_if(deathAnimations,[](auto&u){return u->IsDone();});
for(auto&collectionPoint:collectionPoints){ for(auto&collectionPoint:collectionPoints){
collectionPoint->Update(this,*IMAGES[MATRIX]); collectionPoint->Update(this,IMAGES[MATRIX]);
RenderCollectionPoints(collectionPoint.get()); RenderCollectionPoints(collectionPoint.get());
} }
for(auto&u:units){ for(auto&u:units){
u->DrawUnitDamageStats(this,game,IMAGES); u->DrawUnitDamageStats(this,gametv,IMAGES);
} }
for(DebuffIcon&icon:debuffIcons){ for(DebuffIcon&icon:debuffIcons){
icon.Update(fElapsedTime); icon.Update(fElapsedTime);
icon.Draw(game); icon.Draw(gametv);
} }
for(ResourceGainIcon&icon:resourceGainIcons){ for(ResourceGainIcon&icon:resourceGainIcons){
icon.Update(fElapsedTime); icon.Update(fElapsedTime);
icon.Draw(game); icon.Draw(gametv);
} }
std::erase_if(debuffIcons,[](DebuffIcon&icon){return icon.lifetime<=0;}); std::erase_if(debuffIcons,[](DebuffIcon&icon){return icon.lifetime<=0;});
std::erase_if(resourceGainIcons,[](ResourceGainIcon&icon){return icon.lifetime<=0;}); std::erase_if(resourceGainIcons,[](ResourceGainIcon&icon){return icon.lifetime<=0;});
for(auto&u:units){ for(auto&u:units){
u->_DrawHud(game,IMAGES); u->_DrawHud(gametv,IMAGES);
} }
DrawSelectionRectangle(); DrawSelectionRectangle();
@ -771,7 +780,7 @@ bool VirusAttack::OnUserUpdate(float fElapsedTime){
DrawSystemMemoryBar(fElapsedTime); DrawSystemMemoryBar(fElapsedTime);
DrawResourceBar(fElapsedTime); DrawResourceBar(fElapsedTime);
DrawDecal({float(ScreenWidth()-74-IMAGES[GUIDE]->Sprite()->width*0.75),float(ScreenHeight()+6-IMAGES[GUIDE]->Sprite()->height*0.75)},IMAGES[GUIDE]->Decal(),{0.75,0.75}); DrawDecal({float(ScreenWidth()-74-IMAGES[GUIDE].Sprite()->width*0.75),float(ScreenHeight()+6-IMAGES[GUIDE].Sprite()->height*0.75)},IMAGES[GUIDE].Decal(),{0.75,0.75});
DrawMinimap(); DrawMinimap();
currentLevel->scenario->_Draw(); currentLevel->scenario->_Draw();
@ -861,7 +870,7 @@ void VirusAttack::DrawSystemMemoryBar(float fElapsedTime){
col=CONSTANT::PROCEDURE_COLOR; col=CONSTANT::PROCEDURE_COLOR;
}break; }break;
} }
DrawPartialDecal(barPos+vf2d{barOffset+1,1.f},{barSegmentWidth,3},IMAGES[SEGMENT_BAR]->Decal(),{0,0},{float(playerUsedDisplayMemory[i]),3.f},col); DrawPartialDecal(barPos+vf2d{barOffset+1,1.f},{barSegmentWidth,3},IMAGES[SEGMENT_BAR].Decal(),{0,0},{float(playerUsedDisplayMemory[i]),3.f},col);
barOffset+=barSegmentWidth; barOffset+=barSegmentWidth;
} }
FillRectDecal(barPos+vf2d{barOffset+1,1.f},{2,3},GREEN); FillRectDecal(barPos+vf2d{barOffset+1,1.f},{2,3},GREEN);
@ -886,16 +895,16 @@ void VirusAttack::DrawSystemMemoryBar(float fElapsedTime){
col=CONSTANT::PROCEDURE_COLOR; col=CONSTANT::PROCEDURE_COLOR;
}break; }break;
} }
DrawPartialDecal(barPos+vf2d{barOffset+actualBarWidth+3-barSegmentWidth,1.f},{barSegmentWidth,3},IMAGES[SEGMENT_BAR]->Decal(),{0,0},{float(enemyUsedDisplayMemory[i]),3.f},col); DrawPartialDecal(barPos+vf2d{barOffset+actualBarWidth+3-barSegmentWidth,1.f},{barSegmentWidth,3},IMAGES[SEGMENT_BAR].Decal(),{0,0},{float(enemyUsedDisplayMemory[i]),3.f},col);
barOffset-=barSegmentWidth; barOffset-=barSegmentWidth;
} }
FillRectDecal(barPos+vf2d{barOffset+actualBarWidth+3-2,1.f},{2,3},RED); FillRectDecal(barPos+vf2d{barOffset+actualBarWidth+3-2,1.f},{2,3},RED);
DrawPartialDecal(barPos,{3,5},IMAGES[ROUND_BAR]->Decal(),{0,0},{3,5}); DrawPartialDecal(barPos,{3,5},IMAGES[ROUND_BAR].Decal(),{0,0},{3,5});
for(int i=barPos.x+3;i<barWidth;i++){ for(int i=barPos.x+3;i<barWidth;i++){
DrawPartialDecal(barPos+vf2d{3,0},{barWidth,5},IMAGES[ROUND_BAR]->Decal(),{2,0},{1,5}); DrawPartialDecal(barPos+vf2d{3,0},{barWidth,5},IMAGES[ROUND_BAR].Decal(),{2,0},{1,5});
} }
DrawPartialDecal(barPos+vf2d{3+barWidth,0},{3,5},IMAGES[ROUND_BAR]->Decal(),{2,0},{3,5}); DrawPartialDecal(barPos+vf2d{3+barWidth,0},{3,5},IMAGES[ROUND_BAR].Decal(),{2,0},{3,5});
vf2d textPos=barPos+vf2d{barWidth+6+4,0}; vf2d textPos=barPos+vf2d{barWidth+6+4,0};
if(GetTotalUsedMemory()>lastTotalMemory){ if(GetTotalUsedMemory()>lastTotalMemory){
memoryIncreased=true; memoryIncreased=true;
@ -936,7 +945,7 @@ void VirusAttack::DrawResourceBar(float fElapsedTime){
} }
resourceDisplayValueUpdateTimer[index]=0.01; resourceDisplayValueUpdateTimer[index]=0.01;
} }
DrawDecal({6.f+index*42,1.f},IMAGES[RESOURCE]->Decal(),{1,1},col); DrawDecal({6.f+index*42,1.f},IMAGES[RESOURCE].Decal(),{1,1},col);
DrawShadowStringDecal({6.f+index*42+20,2.f},std::to_string(displayResourceValue),col,PixelLerp(BLACK,resourceIncreased[index]?CONSTANT::INCREASE_VALUE_COLOR:CONSTANT::DECREASE_VALUE_COLOR,resourceGainTimer[index]/2.0f)); DrawShadowStringDecal({6.f+index*42+20,2.f},std::to_string(displayResourceValue),col,PixelLerp(BLACK,resourceIncreased[index]?CONSTANT::INCREASE_VALUE_COLOR:CONSTANT::DECREASE_VALUE_COLOR,resourceGainTimer[index]/2.0f));
}; };
DrawResourceDisplay(0,player_resources.health,player_prev_resources.health,player_display_resources.health,CONSTANT::HEALTH_COLOR); DrawResourceDisplay(0,player_resources.health,player_prev_resources.health,player_display_resources.health,CONSTANT::HEALTH_COLOR);
@ -947,11 +956,11 @@ void VirusAttack::DrawResourceBar(float fElapsedTime){
} }
void VirusAttack::RenderFogOfWar(){ void VirusAttack::RenderFogOfWar(){
for(int y=game.GetTopLeftTile().y/96-1;y<=game.GetBottomRightTile().y/96+1;y++){ for(int y=gametv.GetTopLeftTile().y/96-1;y<=gametv.GetBottomRightTile().y/96+1;y++){
for(int x=game.GetTopLeftTile().x/96-1;x<=game.GetBottomRightTile().x/96+1;x++){ for(int x=gametv.GetTopLeftTile().x/96-1;x<=gametv.GetBottomRightTile().x/96+1;x++){
if(TileManager::visibleTiles.count(vi2d{x,y})==0){ if(TileManager::visibleTiles.count(vi2d{x,y})==0){
if(x>=0&&y>=0&&x<WORLD_SIZE.x/4&&y<WORLD_SIZE.y/4){ if(x>=0&&y>=0&&x<WORLD_SIZE.x/4&&y<WORLD_SIZE.y/4){
game.FillRectDecal(vf2d{float(x),float(y)}*96,{96,96},{0,0,0,128}); gametv.FillRectDecal(vf2d{float(x),float(y)}*96,{96,96},{0,0,0,128});
} }
} }
} }
@ -1039,11 +1048,6 @@ void VirusAttack::CalculateUsedMemory(){
} }
} }
bool VirusAttack::OnUserDestroy(){
std::for_each(scenarios.begin(),scenarios.end(),[](auto&scenario){delete scenario;});
return true;
}
int main() int main()
{ {
VirusAttack app; VirusAttack app;

@ -16,8 +16,6 @@
#include "Textbox.h" #include "Textbox.h"
#include "Level.h" #include "Level.h"
class Scenario;
struct Letter{ struct Letter{
vf2d pos; vf2d pos;
float spd; float spd;
@ -26,8 +24,7 @@ struct Letter{
class VirusAttack : public olc::PixelGameEngine class VirusAttack : public olc::PixelGameEngine
{ {
friend class Stage1; public:
private:
#ifdef SPLASH_ENABLED #ifdef SPLASH_ENABLED
SplashScreen splash; SplashScreen splash;
#endif #endif
@ -41,7 +38,7 @@ private:
std::vector<ResourceGainIcon>resourceGainIcons; std::vector<ResourceGainIcon>resourceGainIcons;
std::vector<Scenario*>scenarios; std::vector<Scenario*>scenarios;
std::map<Image,std::unique_ptr<Renderable>>IMAGES; std::vector<Renderable>IMAGES;
std::map<Sound,std::unique_ptr<Audio>>SOUNDS; std::map<Sound,std::unique_ptr<Audio>>SOUNDS;
olcPGEX_AudioListener AL; olcPGEX_AudioListener AL;
@ -49,7 +46,7 @@ private:
Resources player_resources,player_prev_resources,player_display_resources,enemy_resources; Resources player_resources,player_prev_resources,player_display_resources,enemy_resources;
TileTransformedView game; TileTransformedView gametv;
Textbox unitCreationBox,testBox,memoryAllocatorBox,platformCreationBox; Textbox unitCreationBox,testBox,memoryAllocatorBox,platformCreationBox;
Level*currentLevel; Level*currentLevel;
@ -84,6 +81,10 @@ private:
float memoryDisplayDelay=0; float memoryDisplayDelay=0;
bool memoryIncreased=true; bool memoryIncreased=true;
float memoryChangeTimer=2; float memoryChangeTimer=2;
bool unitMetersGreyedOut=false; //If true, all but health meters show up as dark grey.
bool playerInControl=true;
Renderable HOODED_FIGURE_IMG;
Renderable SPOOK_HOODED_FIGURE_IMG;
vf2d randomBackgroundOffset; vf2d randomBackgroundOffset;
@ -125,5 +126,4 @@ public:
bool OnUserCreate() override; bool OnUserCreate() override;
bool OnUserUpdate(float fElapsedTime) override; bool OnUserUpdate(float fElapsedTime) override;
bool OnUserDestroy() override;
}; };

Binary file not shown.

Before

Width:  |  Height:  |  Size: 779 B

After

Width:  |  Height:  |  Size: 779 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 827 B

After

Width:  |  Height:  |  Size: 827 B

@ -83,6 +83,10 @@
<SubSystem>Console</SubSystem> <SubSystem>Console</SubSystem>
<GenerateDebugInformation>true</GenerateDebugInformation> <GenerateDebugInformation>true</GenerateDebugInformation>
<AdditionalDependencies>soloud_static.lib;sdl2.lib;sdl2main.lib;%(AdditionalDependencies)</AdditionalDependencies> <AdditionalDependencies>soloud_static.lib;sdl2.lib;sdl2main.lib;%(AdditionalDependencies)</AdditionalDependencies>
<HeapReserveSize>40000000</HeapReserveSize>
<HeapCommitSize>40000000</HeapCommitSize>
<StackReserveSize>40000000</StackReserveSize>
<StackCommitSize>40000000</StackCommitSize>
</Link> </Link>
</ItemDefinitionGroup> </ItemDefinitionGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'"> <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
@ -102,6 +106,10 @@
<OptimizeReferences>true</OptimizeReferences> <OptimizeReferences>true</OptimizeReferences>
<GenerateDebugInformation>true</GenerateDebugInformation> <GenerateDebugInformation>true</GenerateDebugInformation>
<AdditionalDependencies>soloud_static.lib;sdl2.lib;sdl2main.lib;%(AdditionalDependencies)</AdditionalDependencies> <AdditionalDependencies>soloud_static.lib;sdl2.lib;sdl2main.lib;%(AdditionalDependencies)</AdditionalDependencies>
<HeapReserveSize>40000000</HeapReserveSize>
<HeapCommitSize>40000000</HeapCommitSize>
<StackReserveSize>40000000</StackReserveSize>
<StackCommitSize>40000000</StackCommitSize>
</Link> </Link>
</ItemDefinitionGroup> </ItemDefinitionGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'"> <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
@ -117,6 +125,10 @@
<SubSystem>Console</SubSystem> <SubSystem>Console</SubSystem>
<GenerateDebugInformation>true</GenerateDebugInformation> <GenerateDebugInformation>true</GenerateDebugInformation>
<AdditionalDependencies>soloud_static.lib;sdl2.lib;sdl2main.lib;%(AdditionalDependencies)</AdditionalDependencies> <AdditionalDependencies>soloud_static.lib;sdl2.lib;sdl2main.lib;%(AdditionalDependencies)</AdditionalDependencies>
<HeapReserveSize>40000000</HeapReserveSize>
<HeapCommitSize>40000000</HeapCommitSize>
<StackReserveSize>40000000</StackReserveSize>
<StackCommitSize>40000000</StackCommitSize>
</Link> </Link>
</ItemDefinitionGroup> </ItemDefinitionGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'"> <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
@ -136,6 +148,10 @@
<OptimizeReferences>true</OptimizeReferences> <OptimizeReferences>true</OptimizeReferences>
<GenerateDebugInformation>true</GenerateDebugInformation> <GenerateDebugInformation>true</GenerateDebugInformation>
<AdditionalDependencies>soloud_static.lib;sdl2.lib;sdl2main.lib;%(AdditionalDependencies)</AdditionalDependencies> <AdditionalDependencies>soloud_static.lib;sdl2.lib;sdl2main.lib;%(AdditionalDependencies)</AdditionalDependencies>
<HeapReserveSize>40000000</HeapReserveSize>
<HeapCommitSize>40000000</HeapCommitSize>
<StackReserveSize>40000000</StackReserveSize>
<StackCommitSize>40000000</StackCommitSize>
</Link> </Link>
</ItemDefinitionGroup> </ItemDefinitionGroup>
<ItemGroup> <ItemGroup>

Binary file not shown.

Before

Width:  |  Height:  |  Size: 24 MiB

After

Width:  |  Height:  |  Size: 23 MiB

@ -190,7 +190,7 @@ Module['FS_createPath']("/", "assets", true, true);
} }
} }
loadPackage({"files": [{"filename": "/assets/MAINICON.ico", "start": 0, "end": 766}, {"filename": "/assets/atk.png", "start": 766, "end": 1443}, {"filename": "/assets/attackLine.png", "start": 1443, "end": 2084}, {"filename": "/assets/bit_restorer.png", "start": 2084, "end": 11632}, {"filename": "/assets/corrupter.png", "start": 11632, "end": 22695}, {"filename": "/assets/cosmos.mp3", "start": 22695, "end": 9174299, "audio": 1}, {"filename": "/assets/down_arrow.png", "start": 9174299, "end": 9174940}, {"filename": "/assets/gravity.mp3", "start": 9174940, "end": 16853462, "audio": 1}, {"filename": "/assets/left_shifter.png", "start": 16853462, "end": 16862667}, {"filename": "/assets/machine2.wav", "start": 16862667, "end": 16941275, "audio": 1}, {"filename": "/assets/material.png", "start": 16941275, "end": 16941970}, {"filename": "/assets/memory_collection_point.png", "start": 16941970, "end": 16942916}, {"filename": "/assets/memory_collection_point_highlight.png", "start": 16942916, "end": 16954993}, {"filename": "/assets/memory_swapper.png", "start": 16954993, "end": 16966443}, {"filename": "/assets/minimap_hud.png", "start": 16966443, "end": 16969901}, {"filename": "/assets/outline.png", "start": 16969901, "end": 16970510}, {"filename": "/assets/prc.png", "start": 16970510, "end": 16979813}, {"filename": "/assets/prc_icon.png", "start": 16979813, "end": 16980565}, {"filename": "/assets/ram_bank.png", "start": 16980565, "end": 16982829}, {"filename": "/assets/range_indicator.png", "start": 16982829, "end": 16991864}, {"filename": "/assets/red_x.png", "start": 16991864, "end": 16992476}, {"filename": "/assets/right_shifter.png", "start": 16992476, "end": 17001700}, {"filename": "/assets/rld.png", "start": 17001700, "end": 17009371}, {"filename": "/assets/rld_icon.png", "start": 17009371, "end": 17010037}, {"filename": "/assets/rng.png", "start": 17010037, "end": 17019169}, {"filename": "/assets/rng_icon.png", "start": 17019169, "end": 17019876}, {"filename": "/assets/selection_circle.png", "start": 17019876, "end": 17020555}, {"filename": "/assets/shell.png", "start": 17020555, "end": 17027429}, {"filename": "/assets/sonar.wav", "start": 17027429, "end": 17283917, "audio": 1}, {"filename": "/assets/spd.png", "start": 17283917, "end": 17292459}, {"filename": "/assets/spd_icon.png", "start": 17292459, "end": 17293150}, {"filename": "/assets/targetLine.png", "start": 17293150, "end": 17293772}, {"filename": "/assets/tile.png", "start": 17293772, "end": 17295107}, {"filename": "/assets/unit.png", "start": 17295107, "end": 17295837}], "remote_package_size": 17295837}); loadPackage({"files": [{"filename": "/assets/MAINICON.ico", "start": 0, "end": 766}, {"filename": "/assets/atk.png", "start": 766, "end": 1443}, {"filename": "/assets/attackLine.png", "start": 1443, "end": 2084}, {"filename": "/assets/bit_restorer.png", "start": 2084, "end": 11632}, {"filename": "/assets/boss1.mp3", "start": 11632, "end": 3289514, "audio": 1}, {"filename": "/assets/boss2.mp3", "start": 3289514, "end": 7202664, "audio": 1}, {"filename": "/assets/corrupter.png", "start": 7202664, "end": 7213727}, {"filename": "/assets/cosmos.mp3", "start": 7213727, "end": 16365331, "audio": 1}, {"filename": "/assets/down_arrow.png", "start": 16365331, "end": 16365972}, {"filename": "/assets/gravity.mp3", "start": 16365972, "end": 24044494, "audio": 1}, {"filename": "/assets/guide.png", "start": 24044494, "end": 24045761}, {"filename": "/assets/hooded_figure.png", "start": 24045761, "end": 24046540}, {"filename": "/assets/left_shifter.png", "start": 24046540, "end": 24055745}, {"filename": "/assets/machine2.wav", "start": 24055745, "end": 24134353, "audio": 1}, {"filename": "/assets/material.png", "start": 24134353, "end": 24135048}, {"filename": "/assets/memory_collection_point.png", "start": 24135048, "end": 24135994}, {"filename": "/assets/memory_collection_point_highlight.png", "start": 24135994, "end": 24148071}, {"filename": "/assets/memory_swapper.png", "start": 24148071, "end": 24159521}, {"filename": "/assets/memoryguard.png", "start": 24159521, "end": 24161773}, {"filename": "/assets/minimap_hud.png", "start": 24161773, "end": 24165231}, {"filename": "/assets/outline.png", "start": 24165231, "end": 24165840}, {"filename": "/assets/ping.mp3", "start": 24165840, "end": 24175138, "audio": 1}, {"filename": "/assets/platform.png", "start": 24175138, "end": 24176218}, {"filename": "/assets/prc.png", "start": 24176218, "end": 24185521}, {"filename": "/assets/prc_icon.png", "start": 24185521, "end": 24186273}, {"filename": "/assets/ram_bank.png", "start": 24186273, "end": 24188537}, {"filename": "/assets/range_indicator.png", "start": 24188537, "end": 24197572}, {"filename": "/assets/red_x.png", "start": 24197572, "end": 24198184}, {"filename": "/assets/refresher.png", "start": 24198184, "end": 24199279}, {"filename": "/assets/right_shifter.png", "start": 24199279, "end": 24208503}, {"filename": "/assets/rld.png", "start": 24208503, "end": 24216174}, {"filename": "/assets/rld_icon.png", "start": 24216174, "end": 24216840}, {"filename": "/assets/rng.png", "start": 24216840, "end": 24225972}, {"filename": "/assets/rng_icon.png", "start": 24225972, "end": 24226679}, {"filename": "/assets/round_bar.png", "start": 24226679, "end": 24227255}, {"filename": "/assets/round_bar_left.png", "start": 24227255, "end": 24227825}, {"filename": "/assets/segmentBar.png", "start": 24227825, "end": 24228402}, {"filename": "/assets/selection_circle.png", "start": 24228402, "end": 24229081}, {"filename": "/assets/shell.png", "start": 24229081, "end": 24235955}, {"filename": "/assets/shieldIcon.png", "start": 24235955, "end": 24236863}, {"filename": "/assets/sonar.wav", "start": 24236863, "end": 24493351, "audio": 1}, {"filename": "/assets/spd.png", "start": 24493351, "end": 24501893}, {"filename": "/assets/spd_icon.png", "start": 24501893, "end": 24502584}, {"filename": "/assets/spook_hooded_figure.png", "start": 24502584, "end": 24503411}, {"filename": "/assets/targetLine.png", "start": 24503411, "end": 24504033}, {"filename": "/assets/tile.png", "start": 24504033, "end": 24505368}, {"filename": "/assets/turret.png", "start": 24505368, "end": 24506376}, {"filename": "/assets/unit.png", "start": 24506376, "end": 24507106}, {"filename": "/assets/voice.mp3", "start": 24507106, "end": 24567843, "audio": 1}], "remote_package_size": 24567843});
})(); })();
@ -1187,31 +1187,31 @@ function dbg(text) {
// === Body === // === Body ===
var ASM_CONSTS = { var ASM_CONSTS = {
5371644: () => { return Module.canvas.getBoundingClientRect().left }, 5372508: () => { return Module.canvas.getBoundingClientRect().left },
5371696: () => { return Module.canvas.getBoundingClientRect().top }, 5372560: () => { return Module.canvas.getBoundingClientRect().top },
5371747: () => { return Module.olc_MOUSEX; }, 5372611: () => { return Module.olc_MOUSEX; },
5371775: () => { return Module.olc_MOUSEY; }, 5372639: () => { return Module.olc_MOUSEY; },
5371803: () => { return Module.olc_MOUSEDOWN }, 5372667: () => { return Module.olc_MOUSEDOWN },
5371833: () => { return Module.olc_MOUSEUP }, 5372697: () => { return Module.olc_MOUSEUP },
5371861: () => { Module.olc_MOUSEDOWN=-1 }, 5372725: () => { Module.olc_MOUSEDOWN=-1 },
5371887: () => { Module.olc_MOUSEUP=-1 }, 5372751: () => { Module.olc_MOUSEUP=-1 },
5371911: () => { window.onunload = Module._olc_OnPageUnload; }, 5372775: () => { window.onunload = Module._olc_OnPageUnload; },
5371955: ($0, $1) => { Module.olc_AspectRatio = $0 / $1; Module.olc_MOUSEDOWN=-1; Module.olc_MOUSEUP=-1; onmousemove = function(e){Module.olc_MOUSEX=e.clientX;Module.olc_MOUSEY=e.clientY;}; onmousedown = function(e){Module.olc_MOUSEDOWN=e.button;}; onmouseup = function(e){Module.olc_MOUSEUP=e.button;}; ontouchmove = function(e){Module.olc_MOUSEX=e.touches[0].clientX;Module.olc_MOUSEY=e.touches[0].clientY;}; ontouchstart = function(e){Module.olc_MOUSEX=e.touches[0].clientX;Module.olc_MOUSEY=e.touches[0].clientY;}; Module.olc_AssumeDefaultShells = (document.querySelectorAll('.emscripten').length >= 3) ? true : false; var olc_ResizeHandler = function() { let isFullscreen = (document.fullscreenElement != null); let width = (isFullscreen) ? window.innerWidth : Module.canvas.parentNode.clientWidth; let height = (isFullscreen) ? window.innerHeight : Module.canvas.parentNode.clientHeight; let viewWidth = width; let viewHeight = width / Module.olc_AspectRatio; if(viewHeight > height) { viewWidth = height * Module.olc_AspectRatio; viewHeight = height; } viewWidth = parseInt(viewWidth); viewHeight = parseInt(viewHeight); setTimeout(function() { if(Module.olc_AssumeDefaultShells) Module.canvas.parentNode.setAttribute('style', 'width: 100%; height: 70vh; margin-left: auto; margin-right: auto;'); Module.canvas.setAttribute('width', viewWidth); Module.canvas.setAttribute('height', viewHeight); Module.canvas.setAttribute('style', `width: ${viewWidth}px; height: ${viewHeight}px;`); Module._olc_PGE_UpdateWindowSize(viewWidth, viewHeight); Module.canvas.focus(); }, 200); }; var olc_Init = function() { if(Module.olc_AspectRatio === undefined) { setTimeout(function() { Module.olc_Init(); }, 50); return; } let resizeObserver = new ResizeObserver(function(entries) { Module.olc_ResizeHandler(); }).observe(Module.canvas.parentNode); let mutationObserver = new MutationObserver(function(mutationsList, observer) { setTimeout(function() { Module.olc_ResizeHandler(); }, 200); }).observe(Module.canvas.parentNode, { attributes: false, childList: true, subtree: false }); window.addEventListener('fullscreenchange', function(e) { setTimeout(function() { Module.olc_ResizeHandler();}, 200); }); }; Module.olc_ResizeHandler = (Module.olc_ResizeHandler != undefined) ? Module.olc_ResizeHandler : olc_ResizeHandler; Module.olc_Init = (Module.olc_Init != undefined) ? Module.olc_Init : olc_Init; Module.olc_Init(); }, 5372819: ($0, $1) => { Module.olc_AspectRatio = $0 / $1; Module.olc_MOUSEDOWN=-1; Module.olc_MOUSEUP=-1; onmousemove = function(e){Module.olc_MOUSEX=e.clientX;Module.olc_MOUSEY=e.clientY;}; onmousedown = function(e){Module.olc_MOUSEDOWN=e.button;}; onmouseup = function(e){Module.olc_MOUSEUP=e.button;}; ontouchmove = function(e){Module.olc_MOUSEX=e.touches[0].clientX;Module.olc_MOUSEY=e.touches[0].clientY;}; ontouchstart = function(e){Module.olc_MOUSEX=e.touches[0].clientX;Module.olc_MOUSEY=e.touches[0].clientY;}; Module.olc_AssumeDefaultShells = (document.querySelectorAll('.emscripten').length >= 3) ? true : false; var olc_ResizeHandler = function() { let isFullscreen = (document.fullscreenElement != null); let width = (isFullscreen) ? window.innerWidth : Module.canvas.parentNode.clientWidth; let height = (isFullscreen) ? window.innerHeight : Module.canvas.parentNode.clientHeight; let viewWidth = width; let viewHeight = width / Module.olc_AspectRatio; if(viewHeight > height) { viewWidth = height * Module.olc_AspectRatio; viewHeight = height; } viewWidth = parseInt(viewWidth); viewHeight = parseInt(viewHeight); setTimeout(function() { if(Module.olc_AssumeDefaultShells) Module.canvas.parentNode.setAttribute('style', 'width: 100%; height: 70vh; margin-left: auto; margin-right: auto;'); Module.canvas.setAttribute('width', viewWidth); Module.canvas.setAttribute('height', viewHeight); Module.canvas.setAttribute('style', `width: ${viewWidth}px; height: ${viewHeight}px;`); Module._olc_PGE_UpdateWindowSize(viewWidth, viewHeight); Module.canvas.focus(); }, 200); }; var olc_Init = function() { if(Module.olc_AspectRatio === undefined) { setTimeout(function() { Module.olc_Init(); }, 50); return; } let resizeObserver = new ResizeObserver(function(entries) { Module.olc_ResizeHandler(); }).observe(Module.canvas.parentNode); let mutationObserver = new MutationObserver(function(mutationsList, observer) { setTimeout(function() { Module.olc_ResizeHandler(); }, 200); }).observe(Module.canvas.parentNode, { attributes: false, childList: true, subtree: false }); window.addEventListener('fullscreenchange', function(e) { setTimeout(function() { Module.olc_ResizeHandler();}, 200); }); }; Module.olc_ResizeHandler = (Module.olc_ResizeHandler != undefined) ? Module.olc_ResizeHandler : olc_ResizeHandler; Module.olc_Init = (Module.olc_Init != undefined) ? Module.olc_Init : olc_Init; Module.olc_Init(); },
5374349: () => { if (typeof(AudioContext) !== 'undefined') { return true; } else if (typeof(webkitAudioContext) !== 'undefined') { return true; } return false; }, 5375213: () => { if (typeof(AudioContext) !== 'undefined') { return true; } else if (typeof(webkitAudioContext) !== 'undefined') { return true; } return false; },
5374496: () => { if ((typeof(navigator.mediaDevices) !== 'undefined') && (typeof(navigator.mediaDevices.getUserMedia) !== 'undefined')) { return true; } else if (typeof(navigator.webkitGetUserMedia) !== 'undefined') { return true; } return false; }, 5375360: () => { if ((typeof(navigator.mediaDevices) !== 'undefined') && (typeof(navigator.mediaDevices.getUserMedia) !== 'undefined')) { return true; } else if (typeof(navigator.webkitGetUserMedia) !== 'undefined') { return true; } return false; },
5374730: ($0) => { if(typeof(Module['SDL2']) === 'undefined') { Module['SDL2'] = {}; } var SDL2 = Module['SDL2']; if (!$0) { SDL2.audio = {}; } else { SDL2.capture = {}; } if (!SDL2.audioContext) { if (typeof(AudioContext) !== 'undefined') { SDL2.audioContext = new AudioContext(); } else if (typeof(webkitAudioContext) !== 'undefined') { SDL2.audioContext = new webkitAudioContext(); } if (SDL2.audioContext) { autoResumeAudioContext(SDL2.audioContext); } } return SDL2.audioContext === undefined ? -1 : 0; }, 5375594: ($0) => { if(typeof(Module['SDL2']) === 'undefined') { Module['SDL2'] = {}; } var SDL2 = Module['SDL2']; if (!$0) { SDL2.audio = {}; } else { SDL2.capture = {}; } if (!SDL2.audioContext) { if (typeof(AudioContext) !== 'undefined') { SDL2.audioContext = new AudioContext(); } else if (typeof(webkitAudioContext) !== 'undefined') { SDL2.audioContext = new webkitAudioContext(); } if (SDL2.audioContext) { autoResumeAudioContext(SDL2.audioContext); } } return SDL2.audioContext === undefined ? -1 : 0; },
5375223: () => { var SDL2 = Module['SDL2']; return SDL2.audioContext.sampleRate; }, 5376087: () => { var SDL2 = Module['SDL2']; return SDL2.audioContext.sampleRate; },
5375291: ($0, $1, $2, $3) => { var SDL2 = Module['SDL2']; var have_microphone = function(stream) { if (SDL2.capture.silenceTimer !== undefined) { clearTimeout(SDL2.capture.silenceTimer); SDL2.capture.silenceTimer = undefined; } SDL2.capture.mediaStreamNode = SDL2.audioContext.createMediaStreamSource(stream); SDL2.capture.scriptProcessorNode = SDL2.audioContext.createScriptProcessor($1, $0, 1); SDL2.capture.scriptProcessorNode.onaudioprocess = function(audioProcessingEvent) { if ((SDL2 === undefined) || (SDL2.capture === undefined)) { return; } audioProcessingEvent.outputBuffer.getChannelData(0).fill(0.0); SDL2.capture.currentCaptureBuffer = audioProcessingEvent.inputBuffer; dynCall('vi', $2, [$3]); }; SDL2.capture.mediaStreamNode.connect(SDL2.capture.scriptProcessorNode); SDL2.capture.scriptProcessorNode.connect(SDL2.audioContext.destination); SDL2.capture.stream = stream; }; var no_microphone = function(error) { }; SDL2.capture.silenceBuffer = SDL2.audioContext.createBuffer($0, $1, SDL2.audioContext.sampleRate); SDL2.capture.silenceBuffer.getChannelData(0).fill(0.0); var silence_callback = function() { SDL2.capture.currentCaptureBuffer = SDL2.capture.silenceBuffer; dynCall('vi', $2, [$3]); }; SDL2.capture.silenceTimer = setTimeout(silence_callback, ($1 / SDL2.audioContext.sampleRate) * 1000); if ((navigator.mediaDevices !== undefined) && (navigator.mediaDevices.getUserMedia !== undefined)) { navigator.mediaDevices.getUserMedia({ audio: true, video: false }).then(have_microphone).catch(no_microphone); } else if (navigator.webkitGetUserMedia !== undefined) { navigator.webkitGetUserMedia({ audio: true, video: false }, have_microphone, no_microphone); } }, 5376155: ($0, $1, $2, $3) => { var SDL2 = Module['SDL2']; var have_microphone = function(stream) { if (SDL2.capture.silenceTimer !== undefined) { clearTimeout(SDL2.capture.silenceTimer); SDL2.capture.silenceTimer = undefined; } SDL2.capture.mediaStreamNode = SDL2.audioContext.createMediaStreamSource(stream); SDL2.capture.scriptProcessorNode = SDL2.audioContext.createScriptProcessor($1, $0, 1); SDL2.capture.scriptProcessorNode.onaudioprocess = function(audioProcessingEvent) { if ((SDL2 === undefined) || (SDL2.capture === undefined)) { return; } audioProcessingEvent.outputBuffer.getChannelData(0).fill(0.0); SDL2.capture.currentCaptureBuffer = audioProcessingEvent.inputBuffer; dynCall('vi', $2, [$3]); }; SDL2.capture.mediaStreamNode.connect(SDL2.capture.scriptProcessorNode); SDL2.capture.scriptProcessorNode.connect(SDL2.audioContext.destination); SDL2.capture.stream = stream; }; var no_microphone = function(error) { }; SDL2.capture.silenceBuffer = SDL2.audioContext.createBuffer($0, $1, SDL2.audioContext.sampleRate); SDL2.capture.silenceBuffer.getChannelData(0).fill(0.0); var silence_callback = function() { SDL2.capture.currentCaptureBuffer = SDL2.capture.silenceBuffer; dynCall('vi', $2, [$3]); }; SDL2.capture.silenceTimer = setTimeout(silence_callback, ($1 / SDL2.audioContext.sampleRate) * 1000); if ((navigator.mediaDevices !== undefined) && (navigator.mediaDevices.getUserMedia !== undefined)) { navigator.mediaDevices.getUserMedia({ audio: true, video: false }).then(have_microphone).catch(no_microphone); } else if (navigator.webkitGetUserMedia !== undefined) { navigator.webkitGetUserMedia({ audio: true, video: false }, have_microphone, no_microphone); } },
5376943: ($0, $1, $2, $3) => { var SDL2 = Module['SDL2']; SDL2.audio.scriptProcessorNode = SDL2.audioContext['createScriptProcessor']($1, 0, $0); SDL2.audio.scriptProcessorNode['onaudioprocess'] = function (e) { if ((SDL2 === undefined) || (SDL2.audio === undefined)) { return; } SDL2.audio.currentOutputBuffer = e['outputBuffer']; dynCall('vi', $2, [$3]); }; SDL2.audio.scriptProcessorNode['connect'](SDL2.audioContext['destination']); }, 5377807: ($0, $1, $2, $3) => { var SDL2 = Module['SDL2']; SDL2.audio.scriptProcessorNode = SDL2.audioContext['createScriptProcessor']($1, 0, $0); SDL2.audio.scriptProcessorNode['onaudioprocess'] = function (e) { if ((SDL2 === undefined) || (SDL2.audio === undefined)) { return; } SDL2.audio.currentOutputBuffer = e['outputBuffer']; dynCall('vi', $2, [$3]); }; SDL2.audio.scriptProcessorNode['connect'](SDL2.audioContext['destination']); },
5377353: ($0, $1) => { var SDL2 = Module['SDL2']; var numChannels = SDL2.capture.currentCaptureBuffer.numberOfChannels; for (var c = 0; c < numChannels; ++c) { var channelData = SDL2.capture.currentCaptureBuffer.getChannelData(c); if (channelData.length != $1) { throw 'Web Audio capture buffer length mismatch! Destination size: ' + channelData.length + ' samples vs expected ' + $1 + ' samples!'; } if (numChannels == 1) { for (var j = 0; j < $1; ++j) { setValue($0 + (j * 4), channelData[j], 'float'); } } else { for (var j = 0; j < $1; ++j) { setValue($0 + (((j * numChannels) + c) * 4), channelData[j], 'float'); } } } }, 5378217: ($0, $1) => { var SDL2 = Module['SDL2']; var numChannels = SDL2.capture.currentCaptureBuffer.numberOfChannels; for (var c = 0; c < numChannels; ++c) { var channelData = SDL2.capture.currentCaptureBuffer.getChannelData(c); if (channelData.length != $1) { throw 'Web Audio capture buffer length mismatch! Destination size: ' + channelData.length + ' samples vs expected ' + $1 + ' samples!'; } if (numChannels == 1) { for (var j = 0; j < $1; ++j) { setValue($0 + (j * 4), channelData[j], 'float'); } } else { for (var j = 0; j < $1; ++j) { setValue($0 + (((j * numChannels) + c) * 4), channelData[j], 'float'); } } } },
5377958: ($0, $1) => { var SDL2 = Module['SDL2']; var numChannels = SDL2.audio.currentOutputBuffer['numberOfChannels']; for (var c = 0; c < numChannels; ++c) { var channelData = SDL2.audio.currentOutputBuffer['getChannelData'](c); if (channelData.length != $1) { throw 'Web Audio output buffer length mismatch! Destination size: ' + channelData.length + ' samples vs expected ' + $1 + ' samples!'; } for (var j = 0; j < $1; ++j) { channelData[j] = HEAPF32[$0 + ((j*numChannels + c) << 2) >> 2]; } } }, 5378822: ($0, $1) => { var SDL2 = Module['SDL2']; var numChannels = SDL2.audio.currentOutputBuffer['numberOfChannels']; for (var c = 0; c < numChannels; ++c) { var channelData = SDL2.audio.currentOutputBuffer['getChannelData'](c); if (channelData.length != $1) { throw 'Web Audio output buffer length mismatch! Destination size: ' + channelData.length + ' samples vs expected ' + $1 + ' samples!'; } for (var j = 0; j < $1; ++j) { channelData[j] = HEAPF32[$0 + ((j*numChannels + c) << 2) >> 2]; } } },
5378438: ($0) => { var SDL2 = Module['SDL2']; if ($0) { if (SDL2.capture.silenceTimer !== undefined) { clearTimeout(SDL2.capture.silenceTimer); } if (SDL2.capture.stream !== undefined) { var tracks = SDL2.capture.stream.getAudioTracks(); for (var i = 0; i < tracks.length; i++) { SDL2.capture.stream.removeTrack(tracks[i]); } SDL2.capture.stream = undefined; } if (SDL2.capture.scriptProcessorNode !== undefined) { SDL2.capture.scriptProcessorNode.onaudioprocess = function(audioProcessingEvent) {}; SDL2.capture.scriptProcessorNode.disconnect(); SDL2.capture.scriptProcessorNode = undefined; } if (SDL2.capture.mediaStreamNode !== undefined) { SDL2.capture.mediaStreamNode.disconnect(); SDL2.capture.mediaStreamNode = undefined; } if (SDL2.capture.silenceBuffer !== undefined) { SDL2.capture.silenceBuffer = undefined } SDL2.capture = undefined; } else { if (SDL2.audio.scriptProcessorNode != undefined) { SDL2.audio.scriptProcessorNode.disconnect(); SDL2.audio.scriptProcessorNode = undefined; } SDL2.audio = undefined; } if ((SDL2.audioContext !== undefined) && (SDL2.audio === undefined) && (SDL2.capture === undefined)) { SDL2.audioContext.close(); SDL2.audioContext = undefined; } }, 5379302: ($0) => { var SDL2 = Module['SDL2']; if ($0) { if (SDL2.capture.silenceTimer !== undefined) { clearTimeout(SDL2.capture.silenceTimer); } if (SDL2.capture.stream !== undefined) { var tracks = SDL2.capture.stream.getAudioTracks(); for (var i = 0; i < tracks.length; i++) { SDL2.capture.stream.removeTrack(tracks[i]); } SDL2.capture.stream = undefined; } if (SDL2.capture.scriptProcessorNode !== undefined) { SDL2.capture.scriptProcessorNode.onaudioprocess = function(audioProcessingEvent) {}; SDL2.capture.scriptProcessorNode.disconnect(); SDL2.capture.scriptProcessorNode = undefined; } if (SDL2.capture.mediaStreamNode !== undefined) { SDL2.capture.mediaStreamNode.disconnect(); SDL2.capture.mediaStreamNode = undefined; } if (SDL2.capture.silenceBuffer !== undefined) { SDL2.capture.silenceBuffer = undefined } SDL2.capture = undefined; } else { if (SDL2.audio.scriptProcessorNode != undefined) { SDL2.audio.scriptProcessorNode.disconnect(); SDL2.audio.scriptProcessorNode = undefined; } SDL2.audio = undefined; } if ((SDL2.audioContext !== undefined) && (SDL2.audio === undefined) && (SDL2.capture === undefined)) { SDL2.audioContext.close(); SDL2.audioContext = undefined; } },
5379610: ($0, $1, $2) => { var w = $0; var h = $1; var pixels = $2; if (!Module['SDL2']) Module['SDL2'] = {}; var SDL2 = Module['SDL2']; if (SDL2.ctxCanvas !== Module['canvas']) { SDL2.ctx = Module['createContext'](Module['canvas'], false, true); SDL2.ctxCanvas = Module['canvas']; } if (SDL2.w !== w || SDL2.h !== h || SDL2.imageCtx !== SDL2.ctx) { SDL2.image = SDL2.ctx.createImageData(w, h); SDL2.w = w; SDL2.h = h; SDL2.imageCtx = SDL2.ctx; } var data = SDL2.image.data; var src = pixels >> 2; var dst = 0; var num; if (typeof CanvasPixelArray !== 'undefined' && data instanceof CanvasPixelArray) { num = data.length; while (dst < num) { var val = HEAP32[src]; data[dst ] = val & 0xff; data[dst+1] = (val >> 8) & 0xff; data[dst+2] = (val >> 16) & 0xff; data[dst+3] = 0xff; src++; dst += 4; } } else { if (SDL2.data32Data !== data) { SDL2.data32 = new Int32Array(data.buffer); SDL2.data8 = new Uint8Array(data.buffer); SDL2.data32Data = data; } var data32 = SDL2.data32; num = data32.length; data32.set(HEAP32.subarray(src, src + num)); var data8 = SDL2.data8; var i = 3; var j = i + 4*num; if (num % 8 == 0) { while (i < j) { data8[i] = 0xff; i = i + 4 | 0; data8[i] = 0xff; i = i + 4 | 0; data8[i] = 0xff; i = i + 4 | 0; data8[i] = 0xff; i = i + 4 | 0; data8[i] = 0xff; i = i + 4 | 0; data8[i] = 0xff; i = i + 4 | 0; data8[i] = 0xff; i = i + 4 | 0; data8[i] = 0xff; i = i + 4 | 0; } } else { while (i < j) { data8[i] = 0xff; i = i + 4 | 0; } } } SDL2.ctx.putImageData(SDL2.image, 0, 0); }, 5380474: ($0, $1, $2) => { var w = $0; var h = $1; var pixels = $2; if (!Module['SDL2']) Module['SDL2'] = {}; var SDL2 = Module['SDL2']; if (SDL2.ctxCanvas !== Module['canvas']) { SDL2.ctx = Module['createContext'](Module['canvas'], false, true); SDL2.ctxCanvas = Module['canvas']; } if (SDL2.w !== w || SDL2.h !== h || SDL2.imageCtx !== SDL2.ctx) { SDL2.image = SDL2.ctx.createImageData(w, h); SDL2.w = w; SDL2.h = h; SDL2.imageCtx = SDL2.ctx; } var data = SDL2.image.data; var src = pixels >> 2; var dst = 0; var num; if (typeof CanvasPixelArray !== 'undefined' && data instanceof CanvasPixelArray) { num = data.length; while (dst < num) { var val = HEAP32[src]; data[dst ] = val & 0xff; data[dst+1] = (val >> 8) & 0xff; data[dst+2] = (val >> 16) & 0xff; data[dst+3] = 0xff; src++; dst += 4; } } else { if (SDL2.data32Data !== data) { SDL2.data32 = new Int32Array(data.buffer); SDL2.data8 = new Uint8Array(data.buffer); SDL2.data32Data = data; } var data32 = SDL2.data32; num = data32.length; data32.set(HEAP32.subarray(src, src + num)); var data8 = SDL2.data8; var i = 3; var j = i + 4*num; if (num % 8 == 0) { while (i < j) { data8[i] = 0xff; i = i + 4 | 0; data8[i] = 0xff; i = i + 4 | 0; data8[i] = 0xff; i = i + 4 | 0; data8[i] = 0xff; i = i + 4 | 0; data8[i] = 0xff; i = i + 4 | 0; data8[i] = 0xff; i = i + 4 | 0; data8[i] = 0xff; i = i + 4 | 0; data8[i] = 0xff; i = i + 4 | 0; } } else { while (i < j) { data8[i] = 0xff; i = i + 4 | 0; } } } SDL2.ctx.putImageData(SDL2.image, 0, 0); },
5381079: ($0, $1, $2, $3, $4) => { var w = $0; var h = $1; var hot_x = $2; var hot_y = $3; var pixels = $4; var canvas = document.createElement("canvas"); canvas.width = w; canvas.height = h; var ctx = canvas.getContext("2d"); var image = ctx.createImageData(w, h); var data = image.data; var src = pixels >> 2; var dst = 0; var num; if (typeof CanvasPixelArray !== 'undefined' && data instanceof CanvasPixelArray) { num = data.length; while (dst < num) { var val = HEAP32[src]; data[dst ] = val & 0xff; data[dst+1] = (val >> 8) & 0xff; data[dst+2] = (val >> 16) & 0xff; data[dst+3] = (val >> 24) & 0xff; src++; dst += 4; } } else { var data32 = new Int32Array(data.buffer); num = data32.length; data32.set(HEAP32.subarray(src, src + num)); } ctx.putImageData(image, 0, 0); var url = hot_x === 0 && hot_y === 0 ? "url(" + canvas.toDataURL() + "), auto" : "url(" + canvas.toDataURL() + ") " + hot_x + " " + hot_y + ", auto"; var urlBuf = _malloc(url.length + 1); stringToUTF8(url, urlBuf, url.length + 1); return urlBuf; }, 5381943: ($0, $1, $2, $3, $4) => { var w = $0; var h = $1; var hot_x = $2; var hot_y = $3; var pixels = $4; var canvas = document.createElement("canvas"); canvas.width = w; canvas.height = h; var ctx = canvas.getContext("2d"); var image = ctx.createImageData(w, h); var data = image.data; var src = pixels >> 2; var dst = 0; var num; if (typeof CanvasPixelArray !== 'undefined' && data instanceof CanvasPixelArray) { num = data.length; while (dst < num) { var val = HEAP32[src]; data[dst ] = val & 0xff; data[dst+1] = (val >> 8) & 0xff; data[dst+2] = (val >> 16) & 0xff; data[dst+3] = (val >> 24) & 0xff; src++; dst += 4; } } else { var data32 = new Int32Array(data.buffer); num = data32.length; data32.set(HEAP32.subarray(src, src + num)); } ctx.putImageData(image, 0, 0); var url = hot_x === 0 && hot_y === 0 ? "url(" + canvas.toDataURL() + "), auto" : "url(" + canvas.toDataURL() + ") " + hot_x + " " + hot_y + ", auto"; var urlBuf = _malloc(url.length + 1); stringToUTF8(url, urlBuf, url.length + 1); return urlBuf; },
5382068: ($0) => { if (Module['canvas']) { Module['canvas'].style['cursor'] = UTF8ToString($0); } }, 5382932: ($0) => { if (Module['canvas']) { Module['canvas'].style['cursor'] = UTF8ToString($0); } },
5382151: () => { if (Module['canvas']) { Module['canvas'].style['cursor'] = 'none'; } }, 5383015: () => { if (Module['canvas']) { Module['canvas'].style['cursor'] = 'none'; } },
5382220: () => { return window.innerWidth; }, 5383084: () => { return window.innerWidth; },
5382250: () => { return window.innerHeight; } 5383114: () => { return window.innerHeight; }
}; };
@ -1422,6 +1422,28 @@ var ASM_CONSTS = {
abort(`Assertion failed: ${UTF8ToString(condition)}, at: ` + [filename ? UTF8ToString(filename) : 'unknown filename', line, func ? UTF8ToString(func) : 'unknown function']); abort(`Assertion failed: ${UTF8ToString(condition)}, at: ` + [filename ? UTF8ToString(filename) : 'unknown filename', line, func ? UTF8ToString(func) : 'unknown function']);
} }
var exceptionCaught = [];
var exceptionLast = 0;
var uncaughtExceptionCount = 0;
function ___cxa_rethrow() {
var info = exceptionCaught.pop();
if (!info) {
abort('no exception to throw');
}
var ptr = info.excPtr;
if (!info.get_rethrown()) {
// Only pop if the corresponding push was through rethrow_primary_exception
exceptionCaught.push(info);
info.set_rethrown(true);
info.set_caught(false);
uncaughtExceptionCount++;
}
exceptionLast = ptr;
assert(false, 'Exception thrown, but exception catching is not enabled. Compile with -sNO_DISABLE_EXCEPTION_CATCHING or -sEXCEPTION_CATCHING_ALLOWED=[..] to catch.');
}
/** @constructor */ /** @constructor */
function ExceptionInfo(excPtr) { function ExceptionInfo(excPtr) {
this.excPtr = excPtr; this.excPtr = excPtr;
@ -1493,9 +1515,7 @@ var ASM_CONSTS = {
}; };
} }
var exceptionLast = 0;
var uncaughtExceptionCount = 0;
function ___cxa_throw(ptr, type, destructor) { function ___cxa_throw(ptr, type, destructor) {
var info = new ExceptionInfo(ptr); var info = new ExceptionInfo(ptr);
// Initialize ExceptionInfo content after it was allocated in __cxa_allocate_exception. // Initialize ExceptionInfo content after it was allocated in __cxa_allocate_exception.
@ -10161,6 +10181,7 @@ function checkIncomingModuleAPI() {
} }
var wasmImports = { var wasmImports = {
"__assert_fail": ___assert_fail, "__assert_fail": ___assert_fail,
"__cxa_rethrow": ___cxa_rethrow,
"__cxa_throw": ___cxa_throw, "__cxa_throw": ___cxa_throw,
"__syscall_fcntl64": ___syscall_fcntl64, "__syscall_fcntl64": ___syscall_fcntl64,
"__syscall_ioctl": ___syscall_ioctl, "__syscall_ioctl": ___syscall_ioctl,

Binary file not shown.

@ -4,14 +4,14 @@ namespace util{
float random(float range){ float random(float range){
return float(rand())/RAND_MAX*range; return float(rand())/RAND_MAX*range;
} }
void ApplyMatrixEffect(PixelGameEngine*pge,Renderable&r,Renderable&originalImg,std::unique_ptr<Renderable>&matrixImg){ void ApplyMatrixEffect(PixelGameEngine*pge,Renderable&r,Renderable&originalImg,Renderable&matrixImg){
pge->SetDrawTarget(r.Sprite()); pge->SetDrawTarget(r.Sprite());
pge->Clear(BLANK); pge->Clear(BLANK);
for(int y=0;y<r.Sprite()->height;y++){ for(int y=0;y<r.Sprite()->height;y++){
for(int x=0;x<r.Sprite()->width;x++){ for(int x=0;x<r.Sprite()->width;x++){
Pixel col=originalImg.Sprite()->GetPixel(x,y); Pixel col=originalImg.Sprite()->GetPixel(x,y);
if(col==WHITE){ if(col==WHITE){
pge->Draw({x,y},matrixImg->Sprite()->GetPixel(x,y)); pge->Draw({x,y},matrixImg.Sprite()->GetPixel(x,y));
} else { } else {
pge->Draw({x,y},originalImg.Sprite()->GetPixel(x,y)); pge->Draw({x,y},originalImg.Sprite()->GetPixel(x,y));
} }

@ -4,7 +4,7 @@
namespace util{ namespace util{
float random(float range); float random(float range);
void ApplyMatrixEffect(PixelGameEngine*pge,Renderable&r,Renderable&originalImg,std::unique_ptr<Renderable>&matrixImg); void ApplyMatrixEffect(PixelGameEngine*pge,Renderable&r,Renderable&originalImg,Renderable&matrixImg);
bool CanAfford(Resources&resources,std::vector<Memory>&unitCosts); bool CanAfford(Resources&resources,std::vector<Memory>&unitCosts);
int GetHealthCost(std::vector<Memory>&unitCosts); int GetHealthCost(std::vector<Memory>&unitCosts);
int GetAtkSpdCost(std::vector<Memory>&unitCosts); int GetAtkSpdCost(std::vector<Memory>&unitCosts);

Loading…
Cancel
Save