#pragma once #include "olcPixelGameEngine.h" #include "olcPGEX_TransformedView.h" #include "Constant.h" #include "Image.h" #include "Sound.h" #include "olcPGEX_AudioSource.h" #include "DebuffIcon.h" #include "CollectionPoint.h" #include "Resources.h" #include "Textbox.h" #include "Memory.h" #include "GameFlags.h" #include "olcPGEX_QuickGUI.h" enum class UnitType{ LeftShifter, RightShifter, BitRestorer, MemorySwapper, Corrupter, MemoryAllocator, RAMBank, MemoryGuard, Refresher, Turret, _Platform, }; struct Marker{ size_t index; size_t size; }; struct Unit{ friend class Scenario; public: Unit(PixelGameEngine*pge,std::vectormemory,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 GetRange(); int GetAtkSpd(); int GetMoveSpd(); int GetProcedure(); int GetMemorySize(); std::vectormemory; std::vectorghostMemory; std::vectorsavedMemory; virtual void Update(PixelGameEngine*pge,std::vector>&SOUNDS,std::vector>&queuedUnits); virtual void Attack(Unit&victim,std::vector>&otherUnits,std::vector>&SOUNDS)=0; virtual void Draw(TileTransformedView&game,std::vector>&IMAGES); virtual void DrawHud(TileTransformedView&game,std::vector>&IMAGES); void _DrawHud(TileTransformedView&game,std::vector>&IMAGES,bool unitMetersGreyedOut); void _OnDeath(std::vector>&SOUNDS); virtual void OnDeath(std::vector>&SOUNDS); bool IsFriendly(); bool IsSelected(); void Select(); void Deselect(); vf2d GetPos(); bool IsDead(); vf2d GetUnitSize(); void SetTargetUnit(std::weak_ptrtarget); void SetTargetLocation(vf2d targetLoc); void SetPos(vf2d newPos); void AttemptAttack(std::weak_ptrattacker,std::weak_ptrunit,std::vector>&otherUnits,std::vector&debuffIcons,std::vector>&IMAGES,std::vector>&SOUNDS); bool InFogOfWar(); bool GhostInFogOfWar(); void HideGhost(); vf2d GetGhostPos(); void _Update(PixelGameEngine*pge,std::vector>&SOUNDS,Resources&player_resources,Resources&enemy_resources,std::vector>&queuedUnits,std::array&resourceGainTimer,std::vector&resourceGainIcons,std::vector>&IMAGES,GameFlags&flags); bool IsMoveable(); void DrawRangeIndicator(PixelGameEngine*pge,TileTransformedView&game,std::vector>&IMAGES); bool CanInteractWithEnemies(); bool CanInteractWithAllies(); Renderable&GetImage(); virtual void RunAI(PixelGameEngine*pge); void _RunAI(PixelGameEngine*pge); virtual void Attacked(std::weak_ptrattacker); void _Attacked(std::weak_ptrattacker); std::weak_ptrGetCurrentTarget(); void DrawUnitDamageStats(PixelGameEngine*pge,TileTransformedView&game,std::vector>&IMAGES); bool AutoAcquiresFriendlyTargets(); bool CanMove(); void SetTargetCollectionPoint(std::weak_ptrtargetCP,std::weak_ptrself_ptr); Pixel GetUnitColor(); 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>&units,std::vector>&IMAGES); //If you return true here, then the left click does not pass back to the main Virus Attack class. bool IsAllocator(); void SetBuildUnit(float buildTime,std::shared_ptrfinalUnit,std::vector>&SOUNDS); bool IsBuilding(); void SetGuardTime(float time); bool IsGuarded(); void SaveMemory(); bool IsPlatform(); bool IsAttached(); bool IsRAMBank(); void RandomHit(std::vector>&SOUNDS); //3 of chance odds of making a sound. Unit*GetBuildUnit(); Marker health={}; Marker range={}; Marker atkSpd={}; Marker moveSpd={}; Marker procedure={}; std::vector& operator <<=(const int n){ for(int i=0;i& operator >>=(const int n){ for(int i=GetMemorySize()-1;i>0;i--){ memory[i]=memory[i-1]; } memory[0]=0; return memory; } protected: bool friendly; Renderable&img; std::weak_ptrtarget; std::weak_ptrappliedTarget; vf2d targetLoc=CONSTANT::UNSELECTED; bool InRange(std::shared_ptrtarget); bool InRange(Unit*target); bool InRange(vf2d pos); float reloadTimer=0; bool attackFailed=false; bool autoAcquireFriendlyTarget=true; bool isAllocator=false; bool isPlatform=false; std::shared_ptrbuildTransformUnit; float buildTime=0; bool isRAMBank=false; private: Renderable targetingLine; Renderable attackingLine; Pixel targetLineCol,attackingLineCol; vf2d pos; vf2d ghostPos; float radius; int GetBits(Marker&m); bool selected=false; bool dead=false; void _Attack(std::weak_ptrattacker,std::weak_ptrfinalTarget,std::vector>&otherUnits,std::vector>&SOUNDS); bool moveable=true; bool friendlyInteractable=false; bool enemyInteractable=true; float lineShift=0; void ApplyMatrixEffect(Renderable&r); std::weak_ptrattachedPoint; std::weak_ptrattachTarget; bool willAttachWhenReachingDestination=false; std::weak_ptrself_ptr; float collectionTime=0; UnitType type; float guardTime=0; }; struct LeftShifter:Unit{ LeftShifter(PixelGameEngine*pge,vf2d pos,std::vector>&IMAGES,bool friendly=false,bool moveable=true); void Attack(Unit&victim,std::vector>&otherUnits,std::vector>&SOUNDS)override; static std::vector resourceCost; static std::string unitName; static std::string unitDescription; }; struct RightShifter:Unit{ RightShifter(PixelGameEngine*pge,vf2d pos,std::vector>&IMAGES,bool friendly=false,bool moveable=true); void Attack(Unit&victim,std::vector>&otherUnits,std::vector>&SOUNDS)override; static std::vector resourceCost; static std::string unitName; static std::string unitDescription; }; struct BitRestorer:Unit{ BitRestorer(PixelGameEngine*pge,vf2d pos,std::vector>&IMAGES,bool friendly=false,bool moveable=true); void Attack(Unit&victim,std::vector>&otherUnits,std::vector>&SOUNDS)override; void AttemptToHealOtherAllies(std::vector>&otherUnits,std::vector>&SOUNDS); static std::vector resourceCost; static std::string unitName; static std::string unitDescription; }; struct MemorySwapper:Unit{ MemorySwapper(PixelGameEngine*pge,vf2d pos,std::vector>&IMAGES,bool friendly=false,bool moveable=true); void Attack(Unit&victim,std::vector>&otherUnits,std::vector>&SOUNDS)override; static std::vector resourceCost; static std::string unitName; static std::string unitDescription; }; struct Corrupter:Unit{ Corrupter(PixelGameEngine*pge,vf2d pos,std::vector>&IMAGES,bool friendly=false,bool moveable=true); void Attack(Unit&victim,std::vector>&otherUnits,std::vector>&SOUNDS)override; static std::vector resourceCost; static std::string unitName; static std::string unitDescription; }; struct MemoryAllocator:Unit{ MemoryAllocator(PixelGameEngine*pge,vf2d pos,std::vector>&IMAGES,bool friendly=false,bool moveable=true); void Attack(Unit&victim,std::vector>&units,std::vector>&SOUNDS)override; void Update(PixelGameEngine*pge,std::vector>&SOUNDS,std::vector>&queuedUnits)override; void Draw(TileTransformedView&game,std::vector>&IMAGES)override; static std::vector resourceCost; static std::string unitName; static std::string unitDescription; }; struct RAMBank:Unit{ vf2d randomOffset; Renderable img; Renderable&originalImg; Renderable&matrixImg; bool soundStarted=false; int soundHandle=-1; QuickGUI::Manager allocatorManager; QuickGUI::ImageButton*allocatorButton; RAMBank(PixelGameEngine*pge,vf2d pos,std::vector>&IMAGES,bool friendly=false); void Update(PixelGameEngine*pge,std::vector>&SOUNDS,std::vector>&queuedUnits)override; void Attack(Unit&victim,std::vector>&otherUnits,std::vector>&SOUNDS)override; void Draw(TileTransformedView&game,std::vector>&IMAGES)override; void OnDeath(std::vector>&SOUNDS)override; bool ClickHandled(TileTransformedView&game,Resources&player_resources,std::vector>&units,std::vector>&IMAGES)override; void UpdateGUIState(TileTransformedView&game,Resources&player_resources,Textbox&displayBox,bool&hovered,int totalUsedMemory,int availableMemory)override; void DrawHud(TileTransformedView&game,std::vector>&IMAGES)override; static std::vector resourceCost; static std::string unitName; static std::string unitDescription; }; struct _Platform:Unit{ _Platform(PixelGameEngine*pge,vf2d pos,std::vector>&IMAGES,bool friendly=false,bool moveable=true); void Attack(Unit&victim,std::vector>&otherUnits,std::vector>&SOUNDS)override; void Update(PixelGameEngine*pge,std::vector>&SOUNDS,std::vector>&queuedUnits)override; void Draw(TileTransformedView&game,std::vector>&IMAGES)override; static std::vector resourceCost; static std::string unitName; static std::string unitDescription; }; struct MemoryGuard:Unit{ bool soundStarted=false; int soundHandle=-1; MemoryGuard(PixelGameEngine*pge,vf2d pos,std::vector>&IMAGES,bool friendly=false,bool moveable=true); void Update(PixelGameEngine*pge,std::vector>&SOUNDS,std::vector>&queuedUnits)override; void Attack(Unit&victim,std::vector>&otherUnits,std::vector>&SOUNDS)override; void OnDeath(std::vector>&SOUNDS)override; static std::vector resourceCost; static std::string unitName; static std::string unitDescription; }; struct Refresher:Unit{ bool soundStarted=false; int soundHandle=-1; Refresher(PixelGameEngine*pge,vf2d pos,std::vector>&IMAGES,bool friendly=false,bool moveable=true); void Update(PixelGameEngine*pge,std::vector>&SOUNDS,std::vector>&queuedUnits)override; void Attack(Unit&victim,std::vector>&otherUnits,std::vector>&SOUNDS)override; void OnDeath(std::vector>&SOUNDS)override; static std::vector resourceCost; static std::string unitName; static std::string unitDescription; }; struct Turret:Unit{ bool soundStarted=false; int soundHandle=-1; Turret(PixelGameEngine*pge,vf2d pos,std::vector>&IMAGES,bool friendly=false,bool moveable=true); void Update(PixelGameEngine*pge,std::vector>&SOUNDS,std::vector>&queuedUnits)override; void Attack(Unit&victim,std::vector>&otherUnits,std::vector>&SOUNDS)override; void OnDeath(std::vector>&SOUNDS)override; static std::vector resourceCost; static std::string unitName; static std::string unitDescription; };