1
0
mirror of https://github.com/veden/Rampant.git synced 2025-02-03 13:11:54 +02:00

need to move settlers to two step pathfinding

This commit is contained in:
Aaron Veden 2019-10-13 22:49:52 -07:00
parent 1536f7f70c
commit b032668f74
14 changed files with 721 additions and 515 deletions

View File

@ -98,10 +98,7 @@ function upgrade.attempt(natives)
-- game.map_settings.path_finder.short_cache_size = constants.PATH_FINDER_SHORT_CACHE_SIZE -- game.map_settings.path_finder.short_cache_size = constants.PATH_FINDER_SHORT_CACHE_SIZE
-- game.map_settings.path_finder.long_cache_size = constants.PATH_FINDER_LONG_REQUEST_RATIO -- game.map_settings.path_finder.long_cache_size = constants.PATH_FINDER_LONG_REQUEST_RATIO
game.map_settings.unit_group.max_group_radius = constants.UNIT_GROUP_MAX_RADIUS -- game.map_settings.unit_group.max_group_radius = constants.UNIT_GROUP_MAX_RADIUS
game.map_settings.unit_group.max_member_speedup_when_behind = constants.UNIT_GROUP_MAX_SPEED_UP
game.map_settings.unit_group.max_member_slowdown_when_ahead = constants.UNIT_GROUP_MAX_SLOWDOWN
game.map_settings.unit_group.max_group_slowdown_factor = constants.UNIT_GROUP_SLOWDOWN_FACTOR
game.surfaces[natives.activeSurface].print("Rampant - Version 0.15.10") game.surfaces[natives.activeSurface].print("Rampant - Version 0.15.10")
global.version = constants.VERSION_22 global.version = constants.VERSION_22
@ -119,8 +116,8 @@ function upgrade.attempt(natives)
natives.unitRefundAmount = 0 natives.unitRefundAmount = 0
-- natives.attackWaveThreshold = 0 -- natives.attackWaveThreshold = 0
game.map_settings.unit_group.member_disown_distance = constants.UNIT_GROUP_DISOWN_DISTANCE -- game.map_settings.unit_group.member_disown_distance = constants.UNIT_GROUP_DISOWN_DISTANCE
game.map_settings.unit_group.tick_tolerance_when_member_arrives = constants.UNIT_GROUP_TICK_TOLERANCE -- game.map_settings.unit_group.tick_tolerance_when_member_arrives = constants.UNIT_GROUP_TICK_TOLERANCE
-- used for breaking up how many squads are processing per logic cycle -- used for breaking up how many squads are processing per logic cycle
natives.regroupIndex = 1 natives.regroupIndex = 1
@ -313,14 +310,28 @@ function upgrade.attempt(natives)
game.surfaces[natives.activeSurface].print("Rampant - Version 0.17.28") game.surfaces[natives.activeSurface].print("Rampant - Version 0.17.28")
global.version = 95 global.version = 95
end end
if (global.version < 96) then if (global.version < 99) then
game.map_settings.unit_group.min_group_radius = constants.UNIT_GROUP_MAX_RADIUS * 0.5
game.map_settings.unit_group.max_group_radius = constants.UNIT_GROUP_MAX_RADIUS
game.map_settings.unit_group.member_disown_distance = constants.UNIT_GROUP_DISOWN_DISTANCE
game.map_settings.unit_group.tick_tolerance_when_member_arrives = constants.UNIT_GROUP_TICK_TOLERANCE
game.map_settings.unit_group.max_member_speedup_when_behind = constants.UNIT_GROUP_MAX_SPEED_UP
game.map_settings.unit_group.max_member_slowdown_when_ahead = constants.UNIT_GROUP_MAX_SLOWDOWN
game.map_settings.unit_group.max_group_slowdown_factor = constants.UNIT_GROUP_SLOWDOWN_FACTOR
for i=#natives.squads,1,-1 do for i=#natives.squads,1,-1 do
natives.squads[i].penalties = {} natives.squads[i].penalties = {}
if not natives.squads[i].chunk then
natives.squads[i].chunk = SENTINEL_IMPASSABLE_CHUNK
end
end end
game.surfaces[natives.activeSurface].print("Rampant - Version 0.17.29") game.surfaces[natives.activeSurface].print("Rampant - Version 0.17.29")
global.version = 96 global.version = 99
end end
return starting ~= global.version, natives return starting ~= global.version, natives

View File

@ -1,3 +1,12 @@
---------------------------------------------------------------------------------------------------
Version: 0.17.29
Date: 10. 13. 2019
Improvements:
- Pathfinding now looks two steps ahead and using the compound command
- Squad formation now has a gathering delay to allow all members to make the initial group
Bugfixes:
- Fixed old savegames penalties having nil chunk index
--------------------------------------------------------------------------------------------------- ---------------------------------------------------------------------------------------------------
Version: 0.17.28 Version: 0.17.28
Date: 8. 17. 2019 Date: 8. 17. 2019

View File

@ -56,6 +56,8 @@ local DEFINES_COMMAND_FLEE = defines.command.flee
local DEFINES_COMMAND_STOP = defines.command.stop local DEFINES_COMMAND_STOP = defines.command.stop
local DEFINES_COMPOUND_COMMAND_RETURN_LAST = defines.compound_command.return_last local DEFINES_COMPOUND_COMMAND_RETURN_LAST = defines.compound_command.return_last
local DEFINES_COMPOUND_COMMAND_AND = defines.compound_command.logical_and
local DEFINES_COMPOUND_COMMAND_OR = defines.compound_command.logical_or
local CHUNK_SIZE = constants.CHUNK_SIZE local CHUNK_SIZE = constants.CHUNK_SIZE
@ -240,6 +242,10 @@ local function rebuildMap()
x=0, x=0,
y=0 y=0
} }
map.position2 = {
x=0,
y=0
}
map.scentStaging = {} map.scentStaging = {}
@ -307,15 +313,30 @@ local function rebuildMap()
map.attackCommand = { map.attackCommand = {
type = DEFINES_COMMAND_ATTACK_AREA, type = DEFINES_COMMAND_ATTACK_AREA,
destination = map.position, destination = map.position,
radius = CHUNK_SIZE, radius = CHUNK_SIZE * 1.5,
distraction = DEFINES_DISTRACTION_BY_ANYTHING
}
map.attack2Command = {
type = DEFINES_COMMAND_ATTACK_AREA,
destination = map.position2,
radius = CHUNK_SIZE * 1.5,
distraction = DEFINES_DISTRACTION_BY_ANYTHING distraction = DEFINES_DISTRACTION_BY_ANYTHING
} }
map.moveCommand = { map.moveCommand = {
type = DEFINES_COMMAND_GO_TO_LOCATION, type = DEFINES_COMMAND_GO_TO_LOCATION,
destination = map.position, destination = map.position,
radius = 6, radius = 1,
pathfind_flags = { prefer_straight_paths = true }, pathfind_flags = { prefer_straight_paths = true, cache = true },
distraction = DEFINES_DISTRACTION_BY_ENEMY
}
map.move2Command = {
type = DEFINES_COMMAND_GO_TO_LOCATION,
destination = map.position2,
radius = 1,
pathfind_flags = { prefer_straight_paths = true, cache = true },
distraction = DEFINES_DISTRACTION_BY_ENEMY distraction = DEFINES_DISTRACTION_BY_ENEMY
} }
@ -346,6 +367,33 @@ local function rebuildMap()
} }
} }
map.compoundMoveMoveCommand = {
type = DEFINES_COMMMAD_COMPOUND,
structure_type = DEFINES_COMPOUND_COMMAND_RETURN_LAST,
commands = {
map.moveCommand,
map.move2Command
}
}
map.compoundMoveAttackCommand = {
type = DEFINES_COMMMAD_COMPOUND,
structure_type = DEFINES_COMPOUND_COMMAND_RETURN_LAST,
commands = {
map.moveCommand,
map.attack2Command
}
}
map.compoundAttackAttackCommand = {
type = DEFINES_COMMMAD_COMPOUND,
structure_type = DEFINES_COMPOUND_COMMAND_RETURN_LAST,
commands = {
map.attackCommand,
map.attack2Command
}
}
map.retreatCommand = { map.retreatCommand = {
type = DEFINES_COMMAND_GROUP, type = DEFINES_COMMAND_GROUP,
group = nil, group = nil,
@ -856,6 +904,25 @@ local function onInit()
hookEvents() hookEvents()
end end
local function onCommandDebugger(event)
for i=1,#natives.squads do
if (natives.squads[i].group.valid) and (natives.squads[i].group.group_number == event.unit_number) then
local msg
if (event.result == defines.behavior_result.in_progress) then
msg = "progress"
elseif (event.result == defines.behavior_result.fail) then
msg = "fail"
elseif (event.result == defines.behavior_result.success) then
msg = "success"
elseif (event.result == defines.behavior_result.deleted) then
msg = "deleted"
end
print(msg, event.unit_number)
return
end
end
end
local function onForceCreated(event) local function onForceCreated(event)
map.activePlayerForces[#map.activePlayerForces+1] = event.force.name map.activePlayerForces[#map.activePlayerForces+1] = event.force.name
end end
@ -894,6 +961,8 @@ script.on_event({defines.events.on_built_entity,
defines.events.on_robot_built_entity, defines.events.on_robot_built_entity,
defines.events.script_raised_built}, onBuild) defines.events.script_raised_built}, onBuild)
-- script.on_event(defines.events.on_ai_command_completed, onCommandDebugger)
script.on_event(defines.events.on_rocket_launched, onRocketLaunch) script.on_event(defines.events.on_rocket_launched, onRocketLaunch)
script.on_event(defines.events.on_entity_died, onDeath) script.on_event(defines.events.on_entity_died, onDeath)
script.on_event(defines.events.on_chunk_generated, onChunkGenerated) script.on_event(defines.events.on_chunk_generated, onChunkGenerated)

View File

@ -84,11 +84,11 @@ if settings.startup["rampant-enableSwarm"].value then
{unit.collision_box[1][1] * 0.20, unit.collision_box[1][2] * 0.20}, {unit.collision_box[1][1] * 0.20, unit.collision_box[1][2] * 0.20},
{unit.collision_box[2][1] * 0.20, unit.collision_box[2][2] * 0.20} {unit.collision_box[2][1] * 0.20, unit.collision_box[2][2] * 0.20}
} }
-- if unit.collision_mask == nil then if unit.collision_mask == nil then
-- unit.collision_mask = {"player-layer", "train-layer", "not-colliding-with-itself"} unit.collision_mask = {"player-layer", "train-layer", "not-colliding-with-itself"}
-- else else
-- unit.collision_mask[#unit.collision_mask+1] = "not-colliding-with-itself" unit.collision_mask[#unit.collision_mask+1] = "not-colliding-with-itself"
-- end end
unit.ai_settings = { destroy_when_commands_fail = false, allow_try_return_to_spawner = false, path_resolution_modifier = -8, do_seperation = false } unit.ai_settings = { destroy_when_commands_fail = false, allow_try_return_to_spawner = false, path_resolution_modifier = -8, do_seperation = false }
end end
@ -98,7 +98,7 @@ end
if settings.startup["rampant-enableShrinkNestsAndWorms"].value then if settings.startup["rampant-enableShrinkNestsAndWorms"].value then
for k, unit in pairs(data.raw["unit-spawner"]) do for k, unit in pairs(data.raw["unit-spawner"]) do
if (string.find(k, "biter") or string.find(k, "spitter")) and unit.collision_box then if (string.find(k, "biter") or string.find(k, "spitter")) and unit.collision_box then
unit.collision_mask = {"player-layer", "train-layer", "not-colliding-with-itself"} -- unit.collision_mask = {"player-layer", "train-layer"}
unit.collision_box = { unit.collision_box = {
{unit.collision_box[1][1] * 0.50, unit.collision_box[1][2] * 0.50}, {unit.collision_box[1][1] * 0.50, unit.collision_box[1][2] * 0.50},
{unit.collision_box[2][1] * 0.50, unit.collision_box[2][2] * 0.50} {unit.collision_box[2][1] * 0.50, unit.collision_box[2][2] * 0.50}

View File

@ -13,6 +13,7 @@ local chunkPropertyUtils = require("ChunkPropertyUtils")
-- constants -- constants
local CHUNK_SIZE_DIVIDER = constants.CHUNK_SIZE_DIVIDER
local DEFINES_WIRE_TYPE_RED = defines.wire_type.red local DEFINES_WIRE_TYPE_RED = defines.wire_type.red
local DEFINES_WIRE_TYPE_GREEN = defines.wire_type.green local DEFINES_WIRE_TYPE_GREEN = defines.wire_type.green
@ -327,8 +328,10 @@ end
function chunkUtils.colorChunk(x, y, tileType, surface) function chunkUtils.colorChunk(x, y, tileType, surface)
local tiles = {} local tiles = {}
for xi=x+5, x + 27 do local lx = math.floor(x * CHUNK_SIZE_DIVIDER) * CHUNK_SIZE
for yi=y+5, y + 27 do local ly = math.floor(y * CHUNK_SIZE_DIVIDER) * CHUNK_SIZE
for xi=lx+5, lx + 27 do
for yi=ly+5, ly + 27 do
tiles[#tiles+1] = {name=tileType, position={xi, yi}} tiles[#tiles+1] = {name=tileType, position={xi, yi}}
end end
end end

View File

@ -475,15 +475,15 @@ constants.PATH_FINDER_SHORT_CACHE_SIZE = 25
constants.PATH_FINDER_LONG_REQUEST_RATIO = 5 constants.PATH_FINDER_LONG_REQUEST_RATIO = 5
constants.PATH_FINDER_MIN_STEPS_TO_CHECK_PATH = 1000 constants.PATH_FINDER_MIN_STEPS_TO_CHECK_PATH = 1000
constants.MAX_FAILED_BEHAVIORS = 10 constants.MAX_FAILED_BEHAVIORS = 100
constants.UNIT_GROUP_DISOWN_DISTANCE = 10 constants.UNIT_GROUP_DISOWN_DISTANCE = 100
constants.UNIT_GROUP_TICK_TOLERANCE = 360 constants.UNIT_GROUP_TICK_TOLERANCE = 3600000
constants.UNIT_GROUP_MAX_RADIUS = 20 constants.UNIT_GROUP_MAX_RADIUS = 25
constants.UNIT_GROUP_MAX_SPEED_UP = 1.1 constants.UNIT_GROUP_MAX_SPEED_UP = 2
constants.UNIT_GROUP_MAX_SLOWDOWN = 1.0 constants.UNIT_GROUP_MAX_SLOWDOWN = 1.0
constants.UNIT_GROUP_SLOWDOWN_FACTOR = 0.9 constants.UNIT_GROUP_SLOWDOWN_FACTOR = 1.0
-- sentinels -- sentinels

View File

@ -201,5 +201,35 @@ function mapUtils.positionFromDirectionAndChunk(direction, startPosition, endPos
return endPosition return endPosition
end end
function mapUtils.positionFromDirectionAndFlat(direction, startPosition, endPosition)
local lx = startPosition.x
local ly = startPosition.y
if (direction == 1) then
lx = lx - CHUNK_SIZE
ly = ly - CHUNK_SIZE
elseif (direction == 2) then
ly = ly - CHUNK_SIZE
elseif (direction == 3) then
lx = lx + CHUNK_SIZE
ly = ly - CHUNK_SIZE
elseif (direction == 4) then
lx = lx - CHUNK_SIZE
elseif (direction == 5) then
lx = lx + CHUNK_SIZE
elseif (direction == 6) then
lx = lx - CHUNK_SIZE
ly = ly + CHUNK_SIZE
elseif (direction == 7) then
ly = ly + CHUNK_SIZE
elseif (direction == 8) then
lx = lx + CHUNK_SIZE
ly = ly + CHUNK_SIZE
end
endPosition.x = lx
endPosition.y = ly
-- return lx, ly
end
mapUtilsG = mapUtils mapUtilsG = mapUtils
return mapUtils return mapUtils

View File

@ -20,6 +20,7 @@ local SENTINEL_IMPASSABLE_CHUNK = constants.SENTINEL_IMPASSABLE_CHUNK
-- imported functions -- imported functions
local canMoveChunkDirection = mapUtils.canMoveChunkDirection local canMoveChunkDirection = mapUtils.canMoveChunkDirection
local getNeighborChunks = mapUtils.getNeighborChunks
-- local recycleBiters = unitGroupUtils.recycleBiters -- local recycleBiters = unitGroupUtils.recycleBiters
@ -33,11 +34,19 @@ local distortPosition = mathUtils.distortPosition
function movementUtils.findMovementPosition(surface, position, distort) function movementUtils.findMovementPosition(surface, position, distort)
local pos = position local pos = position
if not surface.can_place_entity({name="chunk-scanner-squad-movement-rampant", position=position}) then if not surface.can_place_entity({name="chunk-scanner-squad-movement-rampant", position=position}) then
pos = surface.find_non_colliding_position("chunk-scanner-squad-movement-rampant", position, 15, 2, true) pos = surface.find_non_colliding_position("chunk-scanner-squad-movement-rampant", position, 4, 2, true)
end end
return (distort and distortPosition(pos)) or pos return (distort and distortPosition(pos)) or pos
end end
function movementUtils.findMovementXY(surface, x, y)
local pos = position
if not surface.can_place_entity({name="chunk-scanner-squad-movement-rampant", position={}}) then
pos = surface.find_non_colliding_position("chunk-scanner-squad-movement-rampant", position, 4, 2, true)
end
return pos
end
function movementUtils.addMovementPenalty(units, chunk) function movementUtils.addMovementPenalty(units, chunk)
local penalties = units.penalties local penalties = units.penalties
for i=1,#penalties do for i=1,#penalties do
@ -76,6 +85,10 @@ function movementUtils.scoreNeighborsForAttack(map, natives, chunk, neighborDire
local highestScore = -MAGIC_MAXIMUM_NUMBER local highestScore = -MAGIC_MAXIMUM_NUMBER
local highestDirection local highestDirection
local nextHighestChunk = SENTINEL_IMPASSABLE_CHUNK
local nextHighestScore = -MAGIC_MAXIMUM_NUMBER
local nextHighestDirection
for x=1,8 do for x=1,8 do
local neighborChunk = neighborDirectionChunks[x] local neighborChunk = neighborDirectionChunks[x]
@ -89,7 +102,23 @@ function movementUtils.scoreNeighborsForAttack(map, natives, chunk, neighborDire
end end
end end
return highestChunk, highestDirection if (highestChunk ~= SENTINEL_IMPASSABLE_CHUNK) then
neighborDirectionChunks = getNeighborChunks(map, highestChunk.x, highestChunk.y)
for x=1,8 do
local neighborChunk = neighborDirectionChunks[x]
if (neighborChunk ~= SENTINEL_IMPASSABLE_CHUNK) and canMoveChunkDirection(map, x, highestChunk, neighborChunk) then
local score = scoreFunction(natives, squad, neighborChunk)
if (score > nextHighestScore) then
nextHighestScore = score
nextHighestChunk = neighborChunk
nextHighestDirection = x
end
end
end
end
return highestChunk, highestDirection, nextHighestChunk, nextHighestDirection
end end

View File

@ -71,6 +71,7 @@ local addMovementPenalty = movementUtils.addMovementPenalty
local lookupMovementPenalty = movementUtils.lookupMovementPenalty local lookupMovementPenalty = movementUtils.lookupMovementPenalty
local calculateKamikazeThreshold = unitGroupUtils.calculateKamikazeThreshold local calculateKamikazeThreshold = unitGroupUtils.calculateKamikazeThreshold
local positionFromDirectionAndChunk = mapUtils.positionFromDirectionAndChunk local positionFromDirectionAndChunk = mapUtils.positionFromDirectionAndChunk
local positionFromDirectionAndFlat = mapUtils.positionFromDirectionAndFlat
local euclideanDistanceNamed = mathUtils.euclideanDistanceNamed local euclideanDistanceNamed = mathUtils.euclideanDistanceNamed
@ -94,11 +95,12 @@ end
local function scoreAttackLocation(natives, squad, neighborChunk) local function scoreAttackLocation(natives, squad, neighborChunk)
local damage local damage
local movementPheromone = neighborChunk[MOVEMENT_PHEROMONE]
if (neighborChunk[MOVEMENT_PHEROMONE] >= 0) then if (movementPheromone >= 0) then
damage = neighborChunk[MOVEMENT_PHEROMONE] + (neighborChunk[BASE_PHEROMONE] ) + (neighborChunk[PLAYER_PHEROMONE] * PLAYER_PHEROMONE_MULTIPLER) damage = movementPheromone + (neighborChunk[BASE_PHEROMONE] ) + (neighborChunk[PLAYER_PHEROMONE] * PLAYER_PHEROMONE_MULTIPLER)
else else
damage = (neighborChunk[BASE_PHEROMONE] * (1 - (neighborChunk[MOVEMENT_PHEROMONE] / -natives.retreatThreshold))) + (neighborChunk[PLAYER_PHEROMONE] * PLAYER_PHEROMONE_MULTIPLER) damage = (neighborChunk[BASE_PHEROMONE] * (1 - (movementPheromone / -natives.retreatThreshold))) + (neighborChunk[PLAYER_PHEROMONE] * PLAYER_PHEROMONE_MULTIPLER)
end end
return damage - lookupMovementPenalty(squad, neighborChunk) return damage - lookupMovementPenalty(squad, neighborChunk)
@ -111,7 +113,7 @@ end
local function settleMove(map, squad, natives, surface) local function settleMove(map, squad, natives, surface)
local attackPosition = map.position local targetPosition = map.position
local group = squad.group local group = squad.group
local groupPosition = group.position local groupPosition = group.position
@ -202,62 +204,107 @@ local function settleMove(map, squad, natives, surface)
position = findMovementPosition(surface, position = findMovementPosition(surface,
positionFromDirectionAndChunk(attackDirection, positionFromDirectionAndChunk(attackDirection,
groupPosition, groupPosition,
attackPosition, targetPosition,
(largeGroup and 1.1) or 0.9)) (largeGroup and 1.1) or 0.9))
end end
if position then if position then
squad.cycles = (largeGroup and 6) or 4 squad.cycles = (largeGroup and 6) or 4
attackPosition.x = position.x targetPosition.x = position.x
attackPosition.y = position.y targetPosition.y = position.y
group.set_command(cmd) group.set_command(cmd)
group.start_moving() group.start_moving()
end end
end end
local function attackMove(map, squad, natives, surface) local function attackMove(map, squad, natives, surface)
local attackPosition = map.position local targetPosition = map.position
local targetPosition2 = map.position2
local group = squad.group local group = squad.group
local groupPosition = group.position local groupPosition = group.position
local x, y = positionToChunkXY(groupPosition) local x, y = positionToChunkXY(groupPosition)
local chunk = getChunkByXY(map, x, y) local chunk = getChunkByXY(map, x, y)
local attackScorer = scoreAttackLocation local attackScorer = scoreAttackLocation
local squadChunk = squad.chunk
if (squad.attackScoreFunction == ATTACK_SCORE_KAMIKAZE) then if (squad.attackScoreFunction == ATTACK_SCORE_KAMIKAZE) then
attackScorer = scoreAttackKamikazeLocation attackScorer = scoreAttackKamikazeLocation
end end
if squad.chunk and (squad.chunk ~= SENTINEL_IMPASSABLE_CHUNK) and (squad.chunk ~= chunk) then if (squadChunk ~= SENTINEL_IMPASSABLE_CHUNK) and (squadChunk ~= chunk) then
addMovementPenalty(squad, squad.chunk) addMovementPenalty(squad, squadChunk)
end end
local attackChunk, attackDirection = scoreNeighborsForAttack(map, if (chunk ~= SENTINEL_IMPASSABLE_CHUNK)then
addSquadToChunk(map, chunk, squad)
end
squad.frenzy = (squad.frenzy and (euclideanDistanceNamed(groupPosition, squad.frenzyPosition) < 100))
local attackChunk, attackDirection, nextAttackChunk, nextAttackDirection = scoreNeighborsForAttack(map,
natives, natives,
chunk, chunk,
getNeighborChunks(map, x, y), getNeighborChunks(map, x, y),
attackScorer, attackScorer,
squad) squad)
if (chunk ~= SENTINEL_IMPASSABLE_CHUNK)then
addSquadToChunk(map, chunk, squad)
end
if (attackChunk ~= SENTINEL_IMPASSABLE_CHUNK) then if (attackChunk ~= SENTINEL_IMPASSABLE_CHUNK) then
local playerBaseGenerator = getPlayerBaseGenerator(map, attackChunk)
local playerPheromone = attackChunk[PLAYER_PHEROMONE]
local cmd
local position
local largeGroup = (#squad.group.members > 80)
if (playerBaseGenerator == 0) and (playerPheromone < natives.attackPlayerThreshold) then positionFromDirectionAndFlat(attackDirection, groupPosition, targetPosition)
squad.frenzy = (squad.frenzy and (euclideanDistanceNamed(groupPosition, squad.frenzyPosition) < 100))
local position = findMovementPosition(surface, targetPosition)
if not position then
cmd = map.wonderCommand
group.set_command(cmd)
return
end
if ((getPlayerBaseGenerator(map, attackChunk) == 0) and
(attackChunk[PLAYER_PHEROMONE] < natives.attackPlayerThreshold)) then
if (nextAttackChunk ~= SENTINEL_IMPASSABLE_CHUNK) then
positionFromDirectionAndFlat(nextAttackDirection, targetPosition, targetPosition2)
local position2 = findMovementPosition(surface, targetPosition2)
if position2 then
if ((getPlayerBaseGenerator(map, nextAttackChunk) == 0) and
(nextAttackChunk[PLAYER_PHEROMONE] < natives.attackPlayerThreshold)) then
cmd = map.compoundMoveMoveCommand
if squad.rabid or squad.frenzy then
cmd.commands[1].distraction = DEFINES_DISTRACTION_BY_ANYTHING
cmd.commands[2].distraction = DEFINES_DISTRACTION_BY_ANYTHING
else
cmd.commands[1].distraction = DEFINES_DISTRACTION_BY_ENEMY
cmd.commands[2].distraction = DEFINES_DISTRACTION_BY_ENEMY
end
else
cmd = map.compoundMoveAttackCommand
cmd.commands[1].distraction = DEFINES_DISTRACTION_BY_ANYTHING
end
else
cmd = map.moveCommand cmd = map.moveCommand
if squad.rabid or squad.frenzy then if squad.rabid or squad.frenzy then
cmd.distraction = DEFINES_DISTRACTION_BY_ANYTHING cmd.distraction = DEFINES_DISTRACTION_BY_ANYTHING
else else
cmd.distraction = DEFINES_DISTRACTION_BY_ENEMY cmd.distraction = DEFINES_DISTRACTION_BY_ENEMY
end end
end
else else
cmd = map.attackCommand cmd = map.attackCommand
end
else
if (nextAttackChunk ~= SENTINEL_IMPASSABLE_CHUNK) then
positionFromDirectionAndFlat(nextAttackDirection, targetPosition, targetPosition2)
local position2 = findMovementPosition(surface, targetPosition2)
if position2 then
cmd = map.compoundAttackAttackCommand
else
cmd = map.attackCommand
end
else
cmd = map.attackCommand
end
if not squad.rabid then if not squad.rabid then
squad.frenzy = true squad.frenzy = true
@ -266,26 +313,16 @@ local function attackMove(map, squad, natives, surface)
end end
end end
position = findMovementPosition(surface,
positionFromDirectionAndChunk(attackDirection,
groupPosition,
attackPosition,
(largeGroup and 1.1) or 0.9))
if position then
squad.cycles = (largeGroup and 6) or 4
attackPosition.x = position.x
attackPosition.y = position.y
group.set_command(cmd) group.set_command(cmd)
group.start_moving() else
end cmd = map.wonderCommand
group.set_command(cmd)
end end
end end
function squadAttack.squadsDispatch(map, surface, natives) function squadAttack.squadsDispatch(map, surface, natives)
local squads = natives.squads local squads = natives.squads
-- local attackPosition = map.position -- local targetPosition = map.position
-- local attackCmd = map.attackAreaCommand -- local attackCmd = map.attackAreaCommand
-- local settleCmd = map.settleCommand -- local settleCmd = map.settleCommand
@ -324,15 +361,16 @@ function squadAttack.squadsDispatch(map, surface, natives)
if (status == SQUAD_RAIDING) then if (status == SQUAD_RAIDING) then
if (groupState == DEFINES_GROUP_FINISHED) or if (groupState == DEFINES_GROUP_FINISHED) or
(groupState == DEFINES_GROUP_GATHERING) or (groupState == DEFINES_GROUP_GATHERING) -- or
((groupState == DEFINES_GROUP_MOVING) and (cycles <= 0)) -- ((groupState == DEFINES_GROUP_MOVING) and (cycles <= 0))
then then
-- print(group.group_number, groupState)
attackMove(map, squad, natives, surface) attackMove(map, squad, natives, surface)
end end
elseif (status == SQUAD_SETTLING) then elseif (status == SQUAD_SETTLING) then
if (groupState == DEFINES_GROUP_FINISHED) or if (groupState == DEFINES_GROUP_FINISHED) or
(groupState == DEFINES_GROUP_GATHERING) or (groupState == DEFINES_GROUP_GATHERING) -- or
((groupState == DEFINES_GROUP_MOVING) and (cycles <= 0)) -- ((groupState == DEFINES_GROUP_MOVING) and (cycles <= 0))
then then
settleMove(map, squad, natives, surface) settleMove(map, squad, natives, surface)
end end
@ -368,28 +406,34 @@ function squadAttack.squadsDispatch(map, surface, natives)
end end
function squadAttack.squadsBeginAttack(natives) function squadAttack.squadsBeginAttack(natives)
local squads = natives.pendingAttack local pending = natives.pendingAttack
for i=1,#squads do local squads = natives.squads
local squad = squads[i] for i=#pending,1,-1 do
local squad = pending[i]
local group = squad.group local group = squad.group
if group and group.valid then if group and group.valid then
if (squad.cycles ~= 0) then
squad.cycles = squad.cycles - 1
else
local kamikazeThreshold = calculateKamikazeThreshold(#squad.group.members, natives) local kamikazeThreshold = calculateKamikazeThreshold(#squad.group.members, natives)
if not squad.kamikaze then if not squad.kamikaze then
squad.kamikaze = (mRandom() < kamikazeThreshold) squad.kamikaze = (mRandom() < kamikazeThreshold)
end end
if squad.settlers then if squad.settlers then
squad.status = SQUAD_SETTLING squad.status = SQUAD_SETTLING
natives.squads[#natives.squads+1] = squad squads[#squads+1] = squad
else else
if squad.kamikaze and (mRandom() < (kamikazeThreshold * 0.75)) then if squad.kamikaze and (mRandom() < (kamikazeThreshold * 0.75)) then
squad.attackScoreFunction = ATTACK_SCORE_KAMIKAZE squad.attackScoreFunction = ATTACK_SCORE_KAMIKAZE
end end
squad.status = SQUAD_RAIDING squad.status = SQUAD_RAIDING
natives.squads[#natives.squads+1] = squad squads[#squads+1] = squad
end
tRemove(pending, i)
end end
end end
end end
natives.pendingAttack = {} -- natives.pendingAttack = {}
end end
squadAttackG = squadAttack squadAttackG = squadAttack

View File

@ -121,12 +121,12 @@ function unitGroupUtils.createSquad(position, surface, group, settlers)
kamikaze = false, kamikaze = false,
frenzyPosition = {x = 0, frenzyPosition = {x = 0,
y = 0}, y = 0},
cycles = 60, cycles = 10,
maxDistance = 0, maxDistance = 0,
attackScoreFunction = 1, attackScoreFunction = 1,
originPosition = {x = 0, originPosition = {x = 0,
y = 0}, y = 0},
chunk = nil chunk = SENTINEL_IMPASSABLE_CHUNK
} }
if position then if position then

View File

@ -84,11 +84,22 @@
(copyDirectory "prototypes" modFolder))) (copyDirectory "prototypes" modFolder)))
(define (copy) (define (copy)
(set! packageName (string-append (string-replace (hash-ref configuration 'name) " " "_")
"_"
(hash-ref configuration 'version)))
(print 'copying)
(copyFiles modFolder)) (copyFiles modFolder))
(define (zipIt) (define (zipIt)
(set! packageName (string-append (string-replace (hash-ref configuration 'name) " " "_")
"_"
(hash-ref configuration 'version)))
(print 'zipping)
(makeZip modFolder)) (makeZip modFolder))
(define (runStart) (define (runStart)
(set! packageName (string-append (string-replace (hash-ref configuration 'name) " " "_")
"_"
(hash-ref configuration 'version)))
(copyFiles modFolder) (copyFiles modFolder)
(system*/exit-code "factorio"))) (system*/exit-code "factorio")))