1
0
mirror of https://github.com/veden/Rampant.git synced 2025-01-20 02:59:47 +02:00
Rampant/libs/SquadDefense.lua

167 lines
5.8 KiB
Lua
Raw Normal View History

2022-01-14 14:08:58 -08:00
-- Copyright (C) 2022 veden
-- This program is free software: you can redistribute it and/or modify
-- it under the terms of the GNU General Public License as published by
-- the Free Software Foundation, either version 3 of the License, or
-- (at your option) any later version.
-- This program is distributed in the hope that it will be useful,
-- but WITHOUT ANY WARRANTY; without even the implied warranty of
-- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-- GNU General Public License for more details.
-- You should have received a copy of the GNU General Public License
-- along with this program. If not, see <https://www.gnu.org/licenses/>.
2019-02-15 20:17:30 -08:00
if aiDefenseG then
return aiDefenseG
end
local aiDefense = {}
-- imports
local constants = require("Constants")
local mapUtils = require("MapUtils")
local unitGroupUtils = require("UnitGroupUtils")
local movementUtils = require("MovementUtils")
2020-05-23 20:47:14 -07:00
local chunkPropertyUtils = require("ChunkPropertyUtils")
2021-04-29 22:24:14 -07:00
local baseUtils = require("BaseUtils")
-- constants
local PLAYER_PHEROMONE = constants.PLAYER_PHEROMONE
2016-10-14 17:00:18 -07:00
local BASE_PHEROMONE = constants.BASE_PHEROMONE
2019-02-10 22:14:17 -08:00
local PLAYER_PHEROMONE_MULTIPLER = constants.PLAYER_PHEROMONE_MULTIPLER
local SQUAD_RETREATING = constants.SQUAD_RETREATING
2020-05-19 19:37:16 -07:00
local COOLDOWN_RETREAT = constants.COOLDOWN_RETREAT
2017-04-21 16:14:04 -07:00
-- imported functions
local findNearbyBase = chunkPropertyUtils.findNearbyBase
2021-04-29 22:24:14 -07:00
2020-05-23 20:47:14 -07:00
local addSquadToChunk = chunkPropertyUtils.addSquadToChunk
2018-01-13 21:48:21 -08:00
2019-10-20 13:45:43 -07:00
local positionFromDirectionAndFlat = mapUtils.positionFromDirectionAndFlat
2017-06-07 17:57:24 -07:00
local getNeighborChunks = mapUtils.getNeighborChunks
2019-03-09 15:16:35 -08:00
local findNearbyRetreatingSquad = unitGroupUtils.findNearbyRetreatingSquad
local createSquad = unitGroupUtils.createSquad
2017-11-20 23:27:03 -08:00
local scoreNeighborsForRetreat = movementUtils.scoreNeighborsForRetreat
local findMovementPosition = movementUtils.findMovementPosition
2020-05-23 20:47:14 -07:00
local getRetreatTick = chunkPropertyUtils.getRetreatTick
local getPlayerBaseGenerator = chunkPropertyUtils.getPlayerBaseGenerator
local setRetreatTick = chunkPropertyUtils.setRetreatTick
local getDeathGeneratorRating = chunkPropertyUtils.getDeathGeneratorRating
2020-05-23 20:47:14 -07:00
local getEnemyStructureCount = chunkPropertyUtils.getEnemyStructureCount
2017-11-20 23:27:03 -08:00
-- module code
2018-01-13 21:48:21 -08:00
local function scoreRetreatLocation(map, neighborChunk)
2019-03-08 22:37:29 -08:00
return (-neighborChunk[BASE_PHEROMONE] +
2021-02-13 20:49:54 -08:00
-(neighborChunk[PLAYER_PHEROMONE] * PLAYER_PHEROMONE_MULTIPLER) +
-(getPlayerBaseGenerator(map, neighborChunk) * 1000)) *
getDeathGeneratorRating(map, neighborChunk)
end
2021-02-19 21:41:30 -08:00
function aiDefense.retreatUnits(chunk, cause, map, tick, radius)
2020-05-19 19:37:16 -07:00
if (tick - getRetreatTick(map, chunk) > COOLDOWN_RETREAT) and (getEnemyStructureCount(map, chunk) == 0) then
2020-05-23 20:47:14 -07:00
setRetreatTick(map, chunk, tick)
2021-02-13 20:49:54 -08:00
local exitPath,exitDirection,
nextExitPath,nextExitDirection = scoreNeighborsForRetreat(chunk,
getNeighborChunks(map,
chunk.x,
chunk.y),
scoreRetreatLocation,
map)
local universe = map.universe
local position = {
x = chunk.x + 16,
y = chunk.y + 16
}
2020-05-23 20:47:14 -07:00
local retreatPosition
2021-02-19 21:41:30 -08:00
local surface = map.surface
2020-05-23 20:47:14 -07:00
if (exitPath == -1) then
return
elseif (nextExitPath ~= -1) then
retreatPosition = findMovementPosition(
surface,
positionFromDirectionAndFlat(
nextExitDirection,
positionFromDirectionAndFlat(
exitDirection,
position
)
)
)
2020-05-23 20:47:14 -07:00
exitPath = nextExitPath
else
retreatPosition = findMovementPosition(
surface,
positionFromDirectionAndFlat(
exitDirection,
position
)
)
2020-05-16 22:06:55 -07:00
end
2020-05-23 20:47:14 -07:00
if retreatPosition then
position.x = retreatPosition.x
position.y = retreatPosition.y
else
return
end
2020-10-18 20:33:01 -07:00
2020-05-23 20:47:14 -07:00
local newSquad = findNearbyRetreatingSquad(map, exitPath)
local created = false
2020-10-18 20:33:01 -07:00
2020-05-23 20:47:14 -07:00
if not newSquad then
2021-02-19 23:31:36 -08:00
if (universe.squadCount < universe.AI_MAX_SQUAD_COUNT) then
2020-05-24 16:41:12 -07:00
created = true
local base = findNearbyBase(map, chunk)
if not base then
return
end
newSquad = createSquad(position, map, nil, false, base)
2020-05-24 16:41:12 -07:00
else
return
2020-10-18 20:33:01 -07:00
end
2020-05-23 20:47:14 -07:00
end
universe.fleeCommand.from = cause
universe.retreatCommand.group = newSquad.group
universe.formRetreatCommand.unit_search_distance = radius
2020-05-23 20:47:14 -07:00
local foundUnits = surface.set_multi_command(universe.formRetreatCommand)
2020-10-18 20:33:01 -07:00
2020-05-23 20:47:14 -07:00
if (foundUnits == 0) then
if created then
newSquad.group.destroy()
end
2020-05-23 20:47:14 -07:00
return
end
2020-10-18 20:33:01 -07:00
if created then
2021-12-05 19:40:39 -08:00
universe.groupNumberToSquad[newSquad.groupNumber] = newSquad
2021-02-19 23:31:36 -08:00
universe.squadCount = universe.squadCount + 1
end
2020-05-23 20:47:14 -07:00
newSquad.status = SQUAD_RETREATING
addSquadToChunk(map, chunk, newSquad)
newSquad.frenzy = true
local squadPosition = newSquad.group.position
newSquad.frenzyPosition.x = squadPosition.x
newSquad.frenzyPosition.y = squadPosition.y
end
end
2019-02-15 20:17:30 -08:00
aiDefenseG = aiDefense
return aiDefense