diff --git a/Assets/Scripts/Core/options.lua b/Assets/Scripts/Core/options.lua index 7dbb7b3..1d78aed 100644 --- a/Assets/Scripts/Core/options.lua +++ b/Assets/Scripts/Core/options.lua @@ -36,6 +36,9 @@ mappings = { {bind = 32, trigger = 66, action = true, bindType = 0, inOptions = true}, {bind = 33, trigger = 256, action = true, bindType = 0, inOptions = true}, {bind = 47, trigger = 69, action = true, bindType = 0, inOptions = false}, + {bind = 48, trigger = 84, action = true, bindType = 0, inOptions = false}, + {bind = 49, trigger = 89, action = true, bindType = 0, inOptions = false}, + {bind = 50, trigger = 85, action = true, bindType = 0, inOptions = false}, {bind = 7, trigger = 312, action = false, bindType = 2, inOptions = false}, {bind = 8, trigger = 313, action = false, bindType = 2, inOptions = false}, diff --git a/Assets/Scripts/Core/player.lua b/Assets/Scripts/Core/player.lua index 8fbb056..cf4ba0f 100644 --- a/Assets/Scripts/Core/player.lua +++ b/Assets/Scripts/Core/player.lua @@ -211,6 +211,12 @@ function Player:sendTaskforce() self:selectUnits(taskForceTanks) self:selectUnits(taskForceArtillery) + taskForce = self:getSelectedUnits() + + for i = 1, #taskForce do + taskForce[i]:setState(0) + end + players = Game.getSingleton():getPlayers() enemySpawnPoint = nil diff --git a/Assets/Scripts/GameObjects/Units/unitData.lua b/Assets/Scripts/GameObjects/Units/unitData.lua index 7ff03c8..37a82fc 100644 --- a/Assets/Scripts/GameObjects/Units/unitData.lua +++ b/Assets/Scripts/GameObjects/Units/unitData.lua @@ -63,7 +63,7 @@ units = { cost = 500, size = {x = 2.9, y = 8.22, z = 2.42}, hitboxOffset = {x = 0, y = 0, z = 0}, - lineOfSight = 5, + lineOfSight = 20, name = 'War mech', basePath = PATH .. vehiclePrefix .. 'WarMechs/', meshPath = 'warMech.xml', @@ -76,7 +76,7 @@ units = { garrisonCategory = 1 }, { - weapons = {{type = WeaponClass.HITSCAN, rateOfFire = 500, fireSfx = PATH .. 'Sounds/Units/Tanks/attack.ogg', damage = 200, maxRange = 20}}, + weapons = {{type = WeaponClass.HITSCAN, rateOfFire = 500, fireSfx = PATH .. 'Sounds/Units/Tanks/attack.ogg', damage = 200, maxRange = 25}}, unitClass = UnitClass.TANK, unitType = UnitType.LAND, armor = {ArmorType.STEEL}, @@ -86,7 +86,7 @@ units = { cost = 500, size = {x = 2.9, y = 8.22, z = 2.42}, hitboxOffset = {x = 0, y = 0, z = 0}, - lineOfSight = 5, + lineOfSight = 25, name = 'Tank', basePath = PATH .. vehiclePrefix .. 'Tanks/', meshPath = 'tank.xml', @@ -99,7 +99,7 @@ units = { garrisonCategory = 2 }, { - weapons = {{type = WeaponClass.HITSCAN, rateOfFire = 2000, fireSfx = PATH .. 'Sounds/Units/Tanks/attack.ogg', damage = 5000, maxRange = 45}}, + weapons = {{type = WeaponClass.HITSCAN, rateOfFire = 2000, fireSfx = PATH .. 'Sounds/Units/Tanks/attack.ogg', damage = 5000, maxRange = 30}}, unitClass = UnitClass.ARTILLERY, unitType = UnitType.LAND, armor = {ArmorType.MECHANIC}, @@ -109,7 +109,7 @@ units = { cost = 500, size = {x = 2.9, y = 8.22, z = 2.42}, hitboxOffset = {x = 0, y = 0, z = 0}, - lineOfSight = 5, + lineOfSight = 30, name = 'Artillery', basePath = PATH .. vehiclePrefix .. 'Artillery/', meshPath = 'artillery.xml', @@ -506,7 +506,7 @@ units = { cost = 500, size = {x = 2, y = 10, z = 2}, hitboxOffset = {x = 0, y = 0, z = 0}, - lineOfSight = 5, + lineOfSight = 55, name = 'Point defense', basePath = PATH .. structurePrefix .. 'PointDefenses/', meshPath = 'pointDefense.xml', diff --git a/activeGameState.cpp b/activeGameState.cpp index 8978eff..5b07799 100755 --- a/activeGameState.cpp +++ b/activeGameState.cpp @@ -323,6 +323,12 @@ namespace battleship{ } } + void ActiveGameState::enableUnitState(Unit::State state){ + vector selectedUnits = mainPlayer->getSelectedUnits(); + + for(Unit *unit : selectedUnits) + unit->setState(state); + } void ActiveGameState::onAction(int bind, bool isPressed) { GameObjectFrameController *ufCtr = GameObjectFrameController::getSingleton(); @@ -416,6 +422,15 @@ namespace battleship{ } break; + case Bind::ENABLE_CHASE_STATE: + if(isPressed) enableUnitState(Unit::State::CHASE); + break; + case Bind::ENABLE_STAND_GROUND_STATE: + if(isPressed) enableUnitState(Unit::State::STAND_GROUND); + break; + case Bind::ENABLE_HOLD_FIRE_STATE: + if(isPressed) enableUnitState(Unit::State::HOLD_FIRE); + break; case Bind::DESELECT: if(ufCtr->isPlacingFrames()) ufCtr->setRotatingFrames(isPressed); if (!isPressed) deselectUnits(); diff --git a/activeGameState.h b/activeGameState.h index 35196c4..1b01121 100755 --- a/activeGameState.h +++ b/activeGameState.h @@ -42,6 +42,7 @@ namespace battleship{ void castRayToTerrain(); void issueOrder(Order::TYPE, std::vector, bool); bool isInLineOfSight(vb01::Vector3, float, Unit*); + void enableUnitState(Unit::State); inline bool canSelectHoveredOnGameObj(){return gameObjHoveredOn && gameObjHoveredOn->isSelectable() && gameObjHoveredOn->getPlayer() == mainPlayer;} GuiAppState *guiState; diff --git a/binds.h b/binds.h index ec5ef1b..97c66ac 100644 --- a/binds.h +++ b/binds.h @@ -50,7 +50,10 @@ namespace battleship{ CREATE_WATERBODY, GENERATE_WEIGHTS, TOGGLE_CELL_MARKERS, - EJECT_GARRISON + EJECT_GARRISON, + ENABLE_CHASE_STATE, + ENABLE_STAND_GROUND_STATE, + ENABLE_HOLD_FIRE_STATE }; } diff --git a/defConfigs.h b/defConfigs.h index 347bbd5..96afc13 100755 --- a/defConfigs.h +++ b/defConfigs.h @@ -26,7 +26,7 @@ namespace battleship{ const static int numAppStates = 4; const static int numStaticBinds[numAppStates]{6, 0, 5, 19}; - const static int numConfBinds[numAppStates]{0, 1, 23, 0}; + const static int numConfBinds[numAppStates]{0, 1, 26, 0}; const static int maxStaticBinds = 19; const static int maxConfBinds = 23; const static int numScripts = 5; diff --git a/engineer.cpp b/engineer.cpp index 3d1efd5..98d60c7 100644 --- a/engineer.cpp +++ b/engineer.cpp @@ -9,7 +9,7 @@ namespace battleship{ using namespace vb01; using namespace gameBase; - Engineer::Engineer(Player *player, int id, Vector3 pos, Quaternion rot) : Vehicle(player, id, pos, rot){} + Engineer::Engineer(Player *player, int id, Vector3 pos, Quaternion rot, Unit::State state) : Vehicle(player, id, pos, rot, state){} void Engineer::build(Order order){ if(pathPoints.empty()){ diff --git a/engineer.h b/engineer.h index 54c48ea..b0082e3 100644 --- a/engineer.h +++ b/engineer.h @@ -10,7 +10,7 @@ namespace battleship{ class Engineer : public Vehicle{ public: - Engineer(Player*, int, vb01::Vector3, vb01::Quaternion); + Engineer(Player*, int, vb01::Vector3, vb01::Quaternion, Unit::State); void build(Order); private: vb01::s64 lastIncrementTime = 0; diff --git a/extractor.cpp b/extractor.cpp index fb5b8c4..19c5692 100644 --- a/extractor.cpp +++ b/extractor.cpp @@ -11,7 +11,7 @@ namespace battleship{ using namespace vb01; using namespace gameBase; - Extractor::Extractor(Player *player, int id, Vector3 pos, Quaternion rot, int buildStatus, ResourceDeposit *rd) : Structure(player, id, pos, rot, buildStatus){ + Extractor::Extractor(Player *player, int id, Vector3 pos, Quaternion rot, int buildStatus, ResourceDeposit *rd, Unit::State state) : Structure(player, id, pos, rot, buildStatus, state){ if(!rd){ vector deposits; diff --git a/extractor.h b/extractor.h index 120e331..a070765 100644 --- a/extractor.h +++ b/extractor.h @@ -10,7 +10,7 @@ namespace battleship{ class Extractor : public Structure{ public: - Extractor(Player*, int, vb01::Vector3, vb01::Quaternion, int, ResourceDeposit *rd = nullptr); + Extractor(Player*, int, vb01::Vector3, vb01::Quaternion, int, ResourceDeposit *rd = nullptr, Unit::State = Unit::State::STAND_GROUND); ~Extractor(); void update(); void draw(); diff --git a/factory.cpp b/factory.cpp index bbb4d75..dfe72c1 100644 --- a/factory.cpp +++ b/factory.cpp @@ -13,7 +13,7 @@ namespace battleship{ using namespace std; using namespace gameBase; - Factory::Factory(Player *player, int id, Vector3 pos, Quaternion rot, int buildStatus) : Structure(player, id, pos, rot, buildStatus){} + Factory::Factory(Player *player, int id, Vector3 pos, Quaternion rot, int buildStatus, Unit::State state) : Structure(player, id, pos, rot, buildStatus, state){} void Factory::update(){ Structure::update(); diff --git a/factory.h b/factory.h index 042fd2d..851ae22 100644 --- a/factory.h +++ b/factory.h @@ -15,7 +15,7 @@ namespace battleship{ class Factory : public Structure{ public: - Factory(Player*, int, vb01::Vector3, vb01::Quaternion, int = 0); + Factory(Player*, int, vb01::Vector3, vb01::Quaternion, int = 0, Unit::State = Unit::State::STAND_GROUND); ~Factory(){} void update(); int getNumQueueUnitsById(int); diff --git a/gameManager.cpp b/gameManager.cpp index 09d541a..51cbe10 100755 --- a/gameManager.cpp +++ b/gameManager.cpp @@ -55,6 +55,7 @@ namespace battleship{ SOL_LUA_STATE.new_usertype( "Unit", sol::constructors(), + "setState", &Unit::setState, "getOrder", &Unit::getOrder, "getNumOrders", &Unit::getNumOrders, "getPos", &GameObject::getPos, @@ -82,6 +83,7 @@ namespace battleship{ SOL_LUA_STATE.new_usertype( "Player", sol::constructors(), + "getSelectedUnits", &Player::getSelectedUnits, "addUnit", &Player::addUnit, "getUnit", &Player::getUnit, "getNumUnits", &Player::getNumUnits, diff --git a/gameObject.cpp b/gameObject.cpp index b557994..d7b6962 100644 --- a/gameObject.cpp +++ b/gameObject.cpp @@ -19,6 +19,8 @@ namespace battleship{ using namespace gameBase; using namespace configData; + GameObject::GameObject(Type t, int i, Player *pl, vb01::Vector3 vec, vb01::Quaternion quat) : type(t), id(i), player(pl), pos(vec), rot(quat){} + void GameObject::reinit(){ placeAt(pos); orientAt(rot); diff --git a/gameObject.h b/gameObject.h index 28b8ab0..03da68b 100644 --- a/gameObject.h +++ b/gameObject.h @@ -18,7 +18,7 @@ namespace battleship{ public: enum class Type{UNIT, PROJECTILE, RESOURCE_DEPOSIT}; - GameObject(Type t, int i, Player *pl, vb01::Vector3 vec, vb01::Quaternion quat) : type(t), id(i), player(pl), pos(vec), rot(quat){} + GameObject(Type, int, Player*, vb01::Vector3, vb01::Quaternion); ~GameObject(){} virtual void reinit(); virtual void update(); diff --git a/gameObjectFactory.cpp b/gameObjectFactory.cpp index e1dbf7b..83fbc5f 100644 --- a/gameObjectFactory.cpp +++ b/gameObjectFactory.cpp @@ -27,21 +27,21 @@ namespace battleship{ case UnitClass::FORT: case UnitClass::LAND_FACTORY: case UnitClass::NAVAL_FACTORY: - return new Factory(player, id, pos, rot, buildStatus); + return new Factory(player, id, pos, rot, buildStatus, Unit::State::STAND_GROUND); case UnitClass::POINT_DEFENSE: - return new PointDefense(player, id, pos, rot, buildStatus); + return new PointDefense(player, id, pos, rot, buildStatus, Unit::State::STAND_GROUND); case UnitClass::EXTRACTOR: return new Extractor(player, id, pos, rot, buildStatus); case UnitClass::MARKET: case UnitClass::LAB: case UnitClass::REFINERY: - return new Structure(player, id, pos, rot, buildStatus); + return new Structure(player, id, pos, rot, buildStatus, Unit::State::STAND_GROUND); case UnitClass::ENGINEER: - return new Engineer(player, id, pos, rot); + return new Engineer(player, id, pos, rot, Unit::State::STAND_GROUND); case UnitClass::RESOURCE_ROVER: - return new ResourceRover(player, id, pos, rot); + return new ResourceRover(player, id, pos, rot, Unit::State::STAND_GROUND); default: - return new Vehicle(player, id, pos, rot); + return new Vehicle(player, id, pos, rot, Unit::State::STAND_GROUND); } } diff --git a/mapListbox.h b/mapListbox.h new file mode 100644 index 0000000..ffe9c16 --- /dev/null +++ b/mapListbox.h @@ -0,0 +1,15 @@ +#ifndef MAP_LISTBOX_H +#define MAP_LISTBOX_H + +#include + +namespace battleship{ + class MapListbox : public vb01Gui::Listbox{ + public: + MapListbox(vb01::Vector2, vb01::Vector2, std::vector&, int, std::string, bool); + private: + void onClose(); + }; +} + +#endif diff --git a/pointDefense.cpp b/pointDefense.cpp index 8c05e3d..42da4ff 100644 --- a/pointDefense.cpp +++ b/pointDefense.cpp @@ -3,7 +3,7 @@ namespace battleship{ using namespace vb01; - PointDefense::PointDefense(Player *player, int id, Vector3 pos, Quaternion rot, int buildStatus) : Structure(player, id, pos, rot, buildStatus){ + PointDefense::PointDefense(Player *player, int id, Vector3 pos, Quaternion rot, int buildStatus, Unit::State state) : Structure(player, id, pos, rot, buildStatus, state){ turretDir = dirVec; } diff --git a/pointDefense.h b/pointDefense.h index b02a176..3004f58 100644 --- a/pointDefense.h +++ b/pointDefense.h @@ -6,7 +6,7 @@ namespace battleship{ class PointDefense : public Structure{ public: - PointDefense(Player*, int, vb01::Vector3, vb01::Quaternion, int); + PointDefense(Player*, int, vb01::Vector3, vb01::Quaternion, int, Unit::State); private: vb01::Vector3 turretDir; diff --git a/resourceRover.cpp b/resourceRover.cpp index 696a66f..d507268 100644 --- a/resourceRover.cpp +++ b/resourceRover.cpp @@ -13,7 +13,7 @@ namespace battleship{ using namespace vb01; using namespace gameBase; - ResourceRover::ResourceRover(Player *player, int id, Vector3 pos, Quaternion rot) : Vehicle(player, id, pos, rot) { + ResourceRover::ResourceRover(Player *player, int id, Vector3 pos, Quaternion rot, Unit::State state) : Vehicle(player, id, pos, rot, state) { sol::table unitTable = generateView()["units"][id + 1]; capacity = unitTable["capacity"]; loadSpeed = unitTable["loadSpeed"]; diff --git a/resourceRover.h b/resourceRover.h index 5e06627..b8d4cee 100644 --- a/resourceRover.h +++ b/resourceRover.h @@ -11,7 +11,7 @@ namespace battleship{ class ResourceRover : public Vehicle{ public: - ResourceRover(Player*, int, vb01::Vector3, vb01::Quaternion); + ResourceRover(Player*, int, vb01::Vector3, vb01::Quaternion, Unit::State = Unit::State::STAND_GROUND); ~ResourceRover(); void update(); private: diff --git a/structure.cpp b/structure.cpp index 9070efd..52b5cd2 100644 --- a/structure.cpp +++ b/structure.cpp @@ -10,7 +10,7 @@ using namespace vb01; using namespace std; namespace battleship{ - Structure::Structure(Player *player, int id, Vector3 pos, Quaternion rot, int bldSt) : buildStatus(bldSt), Unit(player, id, pos, rot){ + Structure::Structure(Player *player, int id, Vector3 pos, Quaternion rot, int bldSt, Unit::State state) : Unit(player, id, pos, rot, state), buildStatus(bldSt){ Vector2 size = Vector2(lenHpBar, 10); buildStatusBackground = Unit::createBar(Vector2::VEC_ZERO, size, Vector4(0, 0, 0, 1)); buildStatusForeground = Unit::createBar(Vector2::VEC_ZERO, size, Vector4(0, 0, 1, 1)); diff --git a/structure.h b/structure.h index 1a2eea7..10bd58a 100644 --- a/structure.h +++ b/structure.h @@ -10,7 +10,7 @@ namespace vb01{ namespace battleship{ class Structure : public Unit{ public: - Structure(Player*, int, vb01::Vector3, vb01::Quaternion, int = 0); + Structure(Player*, int, vb01::Vector3, vb01::Quaternion, int = 0, Unit::State = Unit::State::STAND_GROUND); ~Structure(); virtual void update(); inline int getBuildStatus(){return buildStatus;} diff --git a/unit.cpp b/unit.cpp index b6f0edd..a7a2f63 100755 --- a/unit.cpp +++ b/unit.cpp @@ -95,9 +95,7 @@ namespace battleship{ lastFireTime = getTime(); } - Unit::Unit(Player *player, int id, Vector3 pos, Quaternion rot) : GameObject(GameObject::Type::UNIT, id, player, pos, rot){ - this->id = id; - this->player = player; + Unit::Unit(Player *player, int id, Vector3 pos, Quaternion rot, State st) : GameObject(GameObject::Type::UNIT, id, player, pos, rot), state(st){ selectable = true; initProperties(); @@ -295,12 +293,33 @@ namespace battleship{ } } + void Unit::targetUnitsAutomatically(){ + vector players = Game::getSingleton()->getPlayers(); + vector units; + + for(Player *pl : players) + if(!(pl == player || pl->getTeam() == player->getTeam())){ + vector un = pl->getUnits(); + units.insert(units.end(), un.begin(), un.end()); + } + + if(orders.empty()) + for(Unit *unit : units) + if(unit->getPos().getDistanceFrom(pos) < lineOfSight){ + setOrder(Order(Order::TYPE::ATTACK, vector{Order::Target(unit)}, Vector3::VEC_ZERO, -1, false)); + break; + } + } + void Unit::update() { GameObject::update(); ActiveGameState *activeState = (ActiveGameState*)GameManager::getSingleton()->getStateManager()->getAppStateByType(AppStateType::ACTIVE_STATE); Player *mainPlayer = (activeState ? activeState->getPlayer() : nullptr); + if(state != State::HOLD_FIRE) + targetUnitsAutomatically(); + vector selectingPlayers = getSelectingPlayers(); bool mainPlayerSelecting = (find(selectingPlayers.begin(), selectingPlayers.end(), mainPlayer) != selectingPlayers.end()); bool mainPlayerOwner = (player == mainPlayer); diff --git a/unit.h b/unit.h index a72ea33..1f6c007 100755 --- a/unit.h +++ b/unit.h @@ -46,11 +46,12 @@ namespace battleship{ TYPE type; int lineId = -1; + bool playerAssigned = true; vb01::Vector3 direction; std::vector targets; Order(){} - Order(TYPE t, std::vector targ, vb01::Vector3 dir, int lid = -1) : type(t), lineId(lid), targets(targ), direction(dir){} + Order(TYPE t, std::vector targ, vb01::Vector3 dir, int lid = -1, bool pa = true) : type(t), playerAssigned(pa), lineId(lid), targets(targ), direction(dir){} }; enum class MoveDir {LEFT, UP, FORW}; @@ -116,8 +117,9 @@ namespace battleship{ }; enum class Armor {CAST, COMBINED, MECHANIC, SHELL, STEEL}; + enum class State {CHASE, STAND_GROUND, HOLD_FIRE}; - Unit(Player*, int, vb01::Vector3, vb01::Quaternion); + Unit(Player*, int, vb01::Vector3, vb01::Quaternion, State = State::STAND_GROUND); virtual ~Unit(); virtual void update(); virtual void halt(); @@ -127,6 +129,7 @@ namespace battleship{ std::vector getProjectiles(); virtual void addOrder(Order); bool canGarrison(Vehicle*); + inline void setState(State s){state = s;} inline Engineer* toEngineer(){return (Engineer*)this;} inline Structure* toStructure(){return (Structure*)this;} inline Factory* toFactory(){return (Factory*)this;} @@ -162,15 +165,17 @@ namespace battleship{ UnitClass unitClass; UnitType type; std::vector orders; - int health, maxHealth, id, playerId, lenHpBar = 200; + int health, maxHealth, playerId, lenHpBar = 200; s64 orderLineDispTime = 0, lastFireTime = 0; float lineOfSight; std::vector garrisonSlots; std::vector armorTypes; std::vector weapons; + State state = State::STAND_GROUND; std::vector getSelectingPlayers(); void removeOrder(int); + virtual void targetUnitsAutomatically(); virtual void reinit(); virtual void initProperties(); virtual void destroySound(); diff --git a/vehicle.cpp b/vehicle.cpp index d147c85..e95470f 100644 --- a/vehicle.cpp +++ b/vehicle.cpp @@ -17,7 +17,7 @@ using namespace vb01; using namespace std; namespace battleship{ - Vehicle::Vehicle(Player *player, int id, Vector3 pos, Quaternion rot) : Unit(player, id, pos, rot){ + Vehicle::Vehicle(Player *player, int id, Vector3 pos, Quaternion rot, Unit::State state) : Unit(player, id, pos, rot, state){ initProperties(); debugMat = new Material(Root::getSingleton()->getLibPath() + "texture"); @@ -290,7 +290,7 @@ namespace battleship{ Unit::attack(order); int currNumOrders = orders.size(); - if(prevNumOrders != currNumOrders) return; + if(weapons.empty() || prevNumOrders != currNumOrders) return; Order::Target target = order.targets[0]; Vector3 targVec = (target.unit ? target.unit->getPos() : target.pos) - pos; @@ -298,10 +298,16 @@ namespace battleship{ Weapon *weapon = weapons[0]; float minDist = weapon->getMaxRange(); - if(distToTarg > minDist) - navigateToTarget(.5 * Map::getSingleton()->getCellSize().x); - else - pursuingTarget = false; + if(order.playerAssigned || (!order.playerAssigned && state == Unit::State::CHASE)){ + if(distToTarg > minDist) + navigateToTarget(.5 * Map::getSingleton()->getCellSize().x); + else + pursuingTarget = false; + } + else if(!order.playerAssigned && state == Unit::State::STAND_GROUND && distToTarg > minDist){ + removeOrder(0); + return; + } float angleToTarg = targVec.norm().getAngleBetween(dirVec); diff --git a/vehicle.h b/vehicle.h index 241c58c..15a34ec 100644 --- a/vehicle.h +++ b/vehicle.h @@ -10,7 +10,7 @@ namespace vb01{ namespace battleship{ class Vehicle : public Unit{ public: - Vehicle(Player*, int, vb01::Vector3, vb01::Quaternion); + Vehicle(Player*, int, vb01::Vector3, vb01::Quaternion, Unit::State); ~Vehicle(); virtual void update(); void move(Order);