diff --git a/Assets/Models/GameObjects/Units/Structures/IceSheets/iceSheet.blend b/Assets/Models/GameObjects/Units/Structures/IceSheets/iceSheet.blend new file mode 100644 index 0000000..9399603 Binary files /dev/null and b/Assets/Models/GameObjects/Units/Structures/IceSheets/iceSheet.blend differ diff --git a/Assets/Models/GameObjects/Units/Structures/IceSheets/iceSheet.jpg b/Assets/Models/GameObjects/Units/Structures/IceSheets/iceSheet.jpg new file mode 100644 index 0000000..2df3706 Binary files /dev/null and b/Assets/Models/GameObjects/Units/Structures/IceSheets/iceSheet.jpg differ diff --git a/Assets/Models/GameObjects/Units/Structures/IceSheets/iceSheet.xml b/Assets/Models/GameObjects/Units/Structures/IceSheets/iceSheet.xml new file mode 100644 index 0000000..7169156 --- /dev/null +++ b/Assets/Models/GameObjects/Units/Structures/IceSheets/iceSheet.xml @@ -0,0 +1,550 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/Assets/Models/GameObjects/Units/Vehicles/Icebreakers/icebreaker.blend b/Assets/Models/GameObjects/Units/Vehicles/Icebreakers/icebreaker.blend new file mode 100644 index 0000000..5d1e474 Binary files /dev/null and b/Assets/Models/GameObjects/Units/Vehicles/Icebreakers/icebreaker.blend differ diff --git a/Assets/Models/GameObjects/Units/Vehicles/Icebreakers/icebreaker.jpg b/Assets/Models/GameObjects/Units/Vehicles/Icebreakers/icebreaker.jpg new file mode 100644 index 0000000..d431a59 Binary files /dev/null and b/Assets/Models/GameObjects/Units/Vehicles/Icebreakers/icebreaker.jpg differ diff --git a/Assets/Models/GameObjects/Units/Vehicles/Icebreakers/icebreaker.xml b/Assets/Models/GameObjects/Units/Vehicles/Icebreakers/icebreaker.xml new file mode 100644 index 0000000..90602dd --- /dev/null +++ b/Assets/Models/GameObjects/Units/Vehicles/Icebreakers/icebreaker.xml @@ -0,0 +1,162 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/Assets/Scripts/GameObjects/Units/unitData.lua b/Assets/Scripts/GameObjects/Units/unitData.lua index 415ed52..e420bf1 100644 --- a/Assets/Scripts/GameObjects/Units/unitData.lua +++ b/Assets/Scripts/GameObjects/Units/unitData.lua @@ -28,14 +28,16 @@ UnitId = { CHAMPION_CARRIER = 12, MISSILE_SUBMARINE = 13, STEALTH_SUBMARINE = 14, - LAND_FACTORY = 15, - NAVAL_FACTORY = 16, - TRADE_CENTER = 17, - LAB = 18, - POINT_DEFENSE = 19, - EXTRACTOR = 20, - REFINERY = 21, - FORT = 22 + ICEBREAKER = 15, + LAND_FACTORY = 16, + NAVAL_FACTORY = 17, + TRADE_CENTER = 18, + LAB = 19, + POINT_DEFENSE = 20, + EXTRACTOR = 21, + REFINERY = 22, + FORT = 23, + ICE_SHEET = 24 } WeaponClass = {HITSCAN = 0, SHELL = 1, TORPEDO = 2, CRUISE_MISSILE = 3, HACK = 4} UnitClass = { @@ -48,14 +50,16 @@ UnitClass = { CRUISER = 6, CARRIER = 7, SUBMARINE = 8, - LAND_FACTORY = 9, - NAVAL_FACTORY = 10, - TRADE_CENTER = 11, - LAB = 12, - POINT_DEFENSE = 13, - EXTRACTOR = 14, - REFINERY = 15, - FORT = 16 + ICEBREAKER = 9, + LAND_FACTORY = 10, + NAVAL_FACTORY = 11, + TRADE_CENTER = 12, + LAB = 13, + POINT_DEFENSE = 14, + EXTRACTOR = 15, + REFINERY = 16, + FORT = 17, + ICE_SHEET = 18 } UnitType = {UNDERWATER = 0, SEA_LEVEL = 1, HOVER = 2, LAND = 3, AIR = 4} @@ -810,6 +814,29 @@ units = { maxTurnAngle = .1, garrisonCategory = 3 }, + { + unitClass = UnitClass.ICEBREAKER, + unitType = UnitType.SEA_LEVEL, + isVehicle = true, + health = 500, + buildTime = 1000, + cost = 500, + size = {x = 12.6, y = 8.5, z = 32.8}, + hitboxOffset = {x = 0, y = 2.07, z = .8}, + lineOfSight = 25, + name = 'Icebreaker', + --colorNodes = {'stealthSubmarine.001'}, + basePath = PATH .. vehiclePrefix .. 'Icebreakers/', + meshPath = 'icebreaker.xml', + albedoPath = 'icebreaker.jpg', + selectionSfx = PATH .. 'Sounds/Units/Submarines/selection.ogg', + deathSfx = PATH .. 'Sounds/SFX/Explosions/explosion01.ogg', + speed = .1, + destinationOffset = .1, + anglePrecision = .1, + maxTurnAngle = .1, + garrisonCategory = 3 + }, { buildableUnits = { {id = UnitId.WAR_MECH, buildable = true, trigger = 87}, @@ -1019,4 +1046,19 @@ units = { selectionSfx = PATH .. 'Sounds/Units/Sample/selection.ogg', deathSfx = PATH .. 'Sounds/SFX/Explosions/explosion01.ogg', }, + { + unitClass = UnitClass.ICE_SHEET, + unitType = UnitType.SEA_LEVEL, + isVehicle = false, + health = 1000, + size = {x = 7, y = 1.5, z = 7}, + hitboxOffset = {x = 0, y = 0, z = 0}, + lineOfSight = 5, + name = 'Ice sheet', + basePath = PATH .. structurePrefix .. 'IceSheets/', + meshPath = 'iceSheet.xml', + albedoPath = 'iceSheet.jpg', + selectionSfx = PATH .. 'Sounds/Units/Sample/selection.ogg', + deathSfx = PATH .. 'Sounds/SFX/Ice/break.ogg', + }, } diff --git a/gameObject.h b/gameObject.h index 2bb7ba1..b281b21 100644 --- a/gameObject.h +++ b/gameObject.h @@ -23,7 +23,7 @@ namespace battleship{ virtual void reinit(); virtual void update(); virtual void select(){} - void placeAt(vb01::Vector3); + virtual void placeAt(vb01::Vector3); void orientAt(vb01::Quaternion); std::string getGameObjTableName(); void updateGameStats(Unit*); diff --git a/gameObjectFactory.cpp b/gameObjectFactory.cpp index 2e4193c..4712284 100644 --- a/gameObjectFactory.cpp +++ b/gameObjectFactory.cpp @@ -26,30 +26,34 @@ namespace battleship{ Unit* GameObjectFactory::createUnit(Player *player, int id, Vector3 pos, Quaternion rot, int buildStatus){ sol::state_view SOL_LUA_VIEW = generateView(); int unitClass = SOL_LUA_VIEW["units"][id + 1]["unitClass"]; + bool vehicle = SOL_LUA_VIEW["units"][id + 1]["isVehicle"]; - switch((UnitClass)unitClass){ - case UnitClass::FORT: - case UnitClass::LAND_FACTORY: - case UnitClass::NAVAL_FACTORY: - return new Factory(player, id, pos, rot, buildStatus, Unit::State::STAND_GROUND); - case UnitClass::POINT_DEFENSE: - 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::LAB: - return new ResearchStruct(player, id, pos, rot, buildStatus); - case UnitClass::TRADE_CENTER: - case UnitClass::REFINERY: - return new Structure(player, id, pos, rot, buildStatus, Unit::State::STAND_GROUND); - case UnitClass::ENGINEER: - return new Engineer(player, id, pos, rot, Unit::State::STAND_GROUND); - case UnitClass::RESOURCE_ROVER: - return new ResourceRover(player, id, pos, rot, Unit::State::STAND_GROUND); - case UnitClass::SUBMARINE: - return new Submarine(player, id, pos, rot, Unit::State::STAND_GROUND); - default: - return new Vehicle(player, id, pos, rot, Unit::State::STAND_GROUND); - } + if(vehicle) + switch((UnitClass)unitClass){ + case UnitClass::ENGINEER: + return new Engineer(player, id, pos, rot, Unit::State::STAND_GROUND); + case UnitClass::RESOURCE_ROVER: + return new ResourceRover(player, id, pos, rot, Unit::State::STAND_GROUND); + case UnitClass::SUBMARINE: + return new Submarine(player, id, pos, rot, Unit::State::STAND_GROUND); + default: + return new Vehicle(player, id, pos, rot, Unit::State::STAND_GROUND); + } + else + switch((UnitClass)unitClass){ + case UnitClass::FORT: + case UnitClass::LAND_FACTORY: + case UnitClass::NAVAL_FACTORY: + return new Factory(player, id, pos, rot, buildStatus, Unit::State::STAND_GROUND); + case UnitClass::POINT_DEFENSE: + 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::LAB: + return new ResearchStruct(player, id, pos, rot, buildStatus); + default: + return new Structure(player, id, pos, rot, buildStatus, Unit::State::STAND_GROUND); + } } Projectile* GameObjectFactory::createProjectile(Unit *unit, int id, Vector3 pos, Quaternion rot){ diff --git a/map.h b/map.h index 3dfb454..c39d2cf 100755 --- a/map.h +++ b/map.h @@ -39,6 +39,7 @@ namespace battleship{ Type type; vb01::Vector3 pos; std::vector edges; + Unit *blockedBy = nullptr; std::vector underWaterCellIds; Cell(){} diff --git a/pathfinder.cpp b/pathfinder.cpp index df64892..2b021eb 100644 --- a/pathfinder.cpp +++ b/pathfinder.cpp @@ -1,7 +1,7 @@ #include #include "pathfinder.h" -#include "unit.h" +#include "vehicle.h" namespace battleship{ using namespace std; @@ -16,7 +16,7 @@ namespace battleship{ return pathfinder; } - vector Pathfinder::findPath(vector &cells, vector &heuristics, int source, int dest, int unitType){ + vector Pathfinder::findPath(vector &cells, vector &heuristics, int source, int dest, Vehicle *vehicle){ const int size = cells.size(); u32 *distances = new u32[size]; vector *paths = new vector[size]; @@ -67,10 +67,30 @@ namespace battleship{ } bool canMoveToStrichCell = true; - bool ship = ((UnitType)unitType == UnitType::UNDERWATER || (UnitType)unitType == UnitType::SEA_LEVEL); - if((ship && cells[vertStrich].type != Map::Cell::WATER) || ((UnitType)unitType == UnitType::LAND && cells[vertStrich].type != Map::Cell::LAND)) - continue; + if(vehicle){ + UnitType unitType = vehicle->getType(); + bool ship = (unitType == UnitType::UNDERWATER || unitType == UnitType::SEA_LEVEL); + Unit *blockingUnit = cells[vertStrich].blockedBy; + + if( + (unitType == UnitType::LAND && (blockingUnit || cells[vertStrich].type != Map::Cell::LAND)) || + ( + ship && + ( + cells[vertStrich].type != Map::Cell::WATER || + ( + blockingUnit && + blockingUnit->getUnitClass() == UnitClass::ICE_SHEET && + vehicle->getUnitClass() != UnitClass::ICEBREAKER + ) + ) + ) + ) + { + continue; + } + } if(distances[vertStrich] + cells[vertStrich].edges[i].weight < distances[edgeNode]){ distances[edgeNode] = distances[vertStrich] + cells[vertStrich].edges[i].weight; diff --git a/pathfinder.h b/pathfinder.h index b071db5..13f38af 100644 --- a/pathfinder.h +++ b/pathfinder.h @@ -8,10 +8,12 @@ #include namespace battleship{ + class Vehicle; + class Pathfinder{ public: static Pathfinder* getSingleton(); - std::vector findPath(std::vector&, std::vector&, int, int, int = -1); + std::vector findPath(std::vector&, std::vector&, int, int, Vehicle* = nullptr); inline vb01::u32 getImpassibleNodeVal(){return impassibleNodeVal;} inline void setImpassibleNodeVal(vb01::u32 val){this->impassibleNodeVal = val;} private: diff --git a/pathfinderTest.cpp b/pathfinderTest.cpp index cd116a3..5bb56ed 100644 --- a/pathfinderTest.cpp +++ b/pathfinderTest.cpp @@ -66,7 +66,7 @@ namespace battleship{ int src = 0, dest = cells.size() - 1; vector heur; - vector path = pathfinder->findPath(cells, heur, src, dest, 3); + vector path = pathfinder->findPath(cells, heur, src, dest); CPPUNIT_ASSERT(path == vector({0, 1, 2, 4, 3, 6})); int sumPathWeights = calcPathLength(path); @@ -82,7 +82,7 @@ namespace battleship{ for(int i = 0; i < numIterations; i++){ s64 t0 = getTime(); - pathfinder->findPath(cells, heur, src, dest, 3); + pathfinder->findPath(cells, heur, src, dest); s64 t1 = getTime(); sumTime += t1 - t0; } diff --git a/unit.cpp b/unit.cpp index 4fb36a3..7293d40 100755 --- a/unit.cpp +++ b/unit.cpp @@ -15,6 +15,7 @@ #include "unit.h" #include "util.h" #include "game.h" +#include "map.h" #include "vehicle.h" #include "gameObjectFactory.h" #include "activeGameState.h" @@ -822,6 +823,29 @@ namespace battleship{ } } + //TODO select only the closest cells based on unit size + void Unit::placeAt(Vector3 p){ + GameObject::placeAt(p); + + Map *map = Map::getSingleton(); + vector &cells = map->getCells(); + Vector3 cellSize = map->getCellSize(); + + for(Map::Cell &cell : cells){ + if(cell.blockedBy && cell.blockedBy != this) continue; + + Vector3 cellDir = (cell.pos - pos); + float forwAngle = std::min(dirVec.getAngleBetween(cellDir.norm()), (-dirVec).getAngleBetween(cellDir.norm())); + float forwDist = cellDir.getLength() * cos(forwAngle); + + float leftAngle = std::min(leftVec.getAngleBetween(cellDir.norm()), (-leftVec).getAngleBetween(cellDir.norm())); + float leftDist = cellDir.getLength() * cos(leftAngle); + + bool within = (forwDist < .5 * (length + cellSize.x) && leftDist < .5 * (width + cellSize.z)); + cell.blockedBy = (within ? this : nullptr); + } + } + vector Unit::getSelectingPlayers(){ vector players = Game::getSingleton()->getPlayers(), selectingPlayers; diff --git a/unit.h b/unit.h index 59832c9..ab3c099 100755 --- a/unit.h +++ b/unit.h @@ -74,6 +74,7 @@ namespace battleship{ CRUISER, CARRIER, SUBMARINE, + ICEBREAKER, LAND_FACTORY, NAVAL_FACTORY, TRADE_CENTER, @@ -81,7 +82,8 @@ namespace battleship{ POINT_DEFENSE, EXTRACTOR, REFINERY, - FORT + FORT, + ICE_SHEET }; class Unit : public GameObject{ @@ -196,6 +198,7 @@ namespace battleship{ std::vector buildableUnits; State state = State::STAND_GROUND; + void placeAt(vb01::Vector3); std::vector getSelectingPlayers(); void removeOrder(int); virtual bool validateLaunchOrder(){return !getWeaponsByOrder(Order::TYPE::LAUNCH).empty();} diff --git a/vehicle.cpp b/vehicle.cpp index 15caff3..a535eaa 100644 --- a/vehicle.cpp +++ b/vehicle.cpp @@ -268,7 +268,7 @@ namespace battleship{ for(Map::Cell &cell : cells) heuristics.push_back(145 * (cells[dest].pos.getDistanceFrom(cell.pos))); - vector path = Pathfinder::getSingleton()->findPath(cells, heuristics, source, dest, (int)type); + vector path = Pathfinder::getSingleton()->findPath(cells, heuristics, source, dest, this); bool pathTruncated = false; for(int i = 0; i < path.size(); i++){