mirror of
https://github.com/veden/Rampant.git
synced 2024-12-24 20:14:35 +02:00
FACTO-287: Re-added kamikaze state and pheromone
This commit is contained in:
parent
4d6966c380
commit
63eed3e08b
@ -1,4 +1,6 @@
|
||||
Version: 3.2.3
|
||||
Improvements:
|
||||
- Re-added kamikaze squad state to prevent unit group dancing and then disbanding
|
||||
Bugfixes:
|
||||
- Fixed occasionally compression number wouldn't appear on unit group
|
||||
- Fixed squad compression could take place when attacking
|
||||
|
@ -49,6 +49,7 @@ local BASE_PHEROMONE = Constants.BASE_PHEROMONE
|
||||
local PLAYER_PHEROMONE = Constants.PLAYER_PHEROMONE
|
||||
local RESOURCE_PHEROMONE = Constants.RESOURCE_PHEROMONE
|
||||
local ENEMY_PHEROMONE = Constants.ENEMY_PHEROMONE
|
||||
local KAMIKAZE_PHEROMONE = Constants.KAMIKAZE_PHEROMONE
|
||||
local BUILDING_PHEROMONES = Constants.BUILDING_PHEROMONES
|
||||
|
||||
local CHUNK_SIZE = Constants.CHUNK_SIZE
|
||||
@ -396,11 +397,12 @@ function ChunkUtils.createChunk(map, topX, topY)
|
||||
id = newChunkId(),
|
||||
map = map
|
||||
}
|
||||
chunk[CHUNK_TICK] = 0
|
||||
chunk[BASE_PHEROMONE] = 0
|
||||
chunk[PLAYER_PHEROMONE] = 0
|
||||
chunk[RESOURCE_PHEROMONE] = 0
|
||||
chunk[ENEMY_PHEROMONE] = 0
|
||||
chunk[CHUNK_TICK] = 0
|
||||
chunk[KAMIKAZE_PHEROMONE] = 0
|
||||
|
||||
return chunk
|
||||
end
|
||||
|
@ -189,11 +189,12 @@ constants.PLAYER_GENERATOR_PERSISTANCE = 0.92
|
||||
|
||||
-- chunk attributes
|
||||
|
||||
constants.BASE_PHEROMONE = 1
|
||||
constants.PLAYER_PHEROMONE = 2
|
||||
constants.RESOURCE_PHEROMONE = 3
|
||||
constants.ENEMY_PHEROMONE = 4
|
||||
constants.CHUNK_TICK = 5
|
||||
constants.CHUNK_TICK = 1
|
||||
constants.BASE_PHEROMONE = 2
|
||||
constants.PLAYER_PHEROMONE = 3
|
||||
constants.RESOURCE_PHEROMONE = 4
|
||||
constants.ENEMY_PHEROMONE = 5
|
||||
constants.KAMIKAZE_PHEROMONE = 6
|
||||
|
||||
-- constants.PATH_RATING = 7
|
||||
|
||||
|
@ -39,6 +39,7 @@ local BASE_PHEROMONE = Constants.BASE_PHEROMONE
|
||||
local PLAYER_PHEROMONE = Constants.PLAYER_PHEROMONE
|
||||
local RESOURCE_PHEROMONE = Constants.RESOURCE_PHEROMONE
|
||||
local ENEMY_PHEROMONE = Constants.ENEMY_PHEROMONE
|
||||
local KAMIKAZE_PHEROMONE = Constants.KAMIKAZE_PHEROMONE
|
||||
|
||||
local CHUNK_TICK = Constants.CHUNK_TICK
|
||||
|
||||
@ -575,6 +576,7 @@ function MapUtils.processPheromone(chunk, tick, player)
|
||||
local chunkDeath = getCombinedDeathGenerator(chunk)
|
||||
local chunkResource = -MAGIC_MAXIMUM_NUMBER
|
||||
local chunkEnemy = chunk[ENEMY_PHEROMONE]
|
||||
local chunkKamikaze = chunk[KAMIKAZE_PHEROMONE]
|
||||
|
||||
local chunkCount = 1
|
||||
|
||||
@ -590,6 +592,10 @@ function MapUtils.processPheromone(chunk, tick, player)
|
||||
chunkPlayer = chunkPlayer + neighbor[PLAYER_PHEROMONE]
|
||||
chunkEnemy = chunkEnemy + neighbor[ENEMY_PHEROMONE]
|
||||
chunkDeath = chunkDeath + getCombinedDeathGenerator(neighbor)
|
||||
tempPheromone = neighbor[KAMIKAZE_PHEROMONE]
|
||||
if chunkKamikaze < tempPheromone then
|
||||
chunkKamikaze = tempPheromone
|
||||
end
|
||||
tempPheromone = neighbor[BASE_PHEROMONE]
|
||||
if chunkBase < tempPheromone then
|
||||
chunkBase = tempPheromone
|
||||
@ -612,12 +618,12 @@ function MapUtils.processPheromone(chunk, tick, player)
|
||||
|
||||
local chunkDeathRating = getCombinedDeathGeneratorRating(chunk) * getPathRating(chunk)
|
||||
|
||||
chunk[PLAYER_PHEROMONE] = chunkDeathRating * mMax(
|
||||
chunk[PLAYER_PHEROMONE] = mMax(
|
||||
chunk.playerGenerator or 0,
|
||||
(chunkPlayer / chunkCount) * 0.98
|
||||
)
|
||||
|
||||
chunk[BASE_PHEROMONE] = chunkDeathRating * mMax(
|
||||
chunk[BASE_PHEROMONE] = mMax(
|
||||
chunk.playerBaseGenerator or 0,
|
||||
chunkBase * 0.9
|
||||
)
|
||||
@ -627,6 +633,14 @@ function MapUtils.processPheromone(chunk, tick, player)
|
||||
(chunkEnemy / chunkCount) * 0.9
|
||||
)
|
||||
|
||||
chunk[KAMIKAZE_PHEROMONE] = mMax(
|
||||
chunkKamikaze,
|
||||
chunk[PLAYER_PHEROMONE] + chunk[BASE_PHEROMONE]
|
||||
) * 0.95
|
||||
|
||||
chunk[PLAYER_PHEROMONE] = chunk[PLAYER_PHEROMONE] * chunkDeathRating
|
||||
chunk[BASE_PHEROMONE] = chunk[BASE_PHEROMONE] * chunkDeathRating
|
||||
|
||||
local resourcePheromoneGenerator = chunk.resourceGenerator or 0
|
||||
if (resourcePheromoneGenerator > 0) then
|
||||
chunkResource = linearInterpolation(resourcePheromoneGenerator, 15000, 20000)
|
||||
|
@ -45,6 +45,7 @@ local COMMAND_TIMEOUT = Constants.COMMAND_TIMEOUT
|
||||
local PLAYER_PHEROMONE = Constants.PLAYER_PHEROMONE
|
||||
local BASE_PHEROMONE = Constants.BASE_PHEROMONE
|
||||
local ENEMY_PHEROMONE = Constants.ENEMY_PHEROMONE
|
||||
local KAMIKAZE_PHEROMONE = Constants.KAMIKAZE_PHEROMONE
|
||||
local RESOURCE_PHEROMONE = Constants.RESOURCE_PHEROMONE
|
||||
|
||||
local HALF_CHUNK_SIZE = Constants.HALF_CHUNK_SIZE
|
||||
@ -161,6 +162,23 @@ local function scoreSiegeLocation(neighborChunk)
|
||||
return score, preferred
|
||||
end
|
||||
|
||||
local function scoreSiegeKamikazeLocation(neighborChunk)
|
||||
local preferred = false
|
||||
if (
|
||||
not neighborChunk.playerBaseGenerator
|
||||
and not neighborChunk.playerGenerator
|
||||
)
|
||||
then
|
||||
preferred = true
|
||||
end
|
||||
local settle = neighborChunk[KAMIKAZE_PHEROMONE]
|
||||
+ neighborChunk[RESOURCE_PHEROMONE] * 0.5
|
||||
|
||||
local score = settle - neighborChunk[ENEMY_PHEROMONE]
|
||||
|
||||
return score, preferred
|
||||
end
|
||||
|
||||
local function scoreAttackLocation(neighborChunk)
|
||||
local preferred = false
|
||||
if (
|
||||
@ -178,6 +196,22 @@ local function scoreAttackLocation(neighborChunk)
|
||||
return damage, preferred
|
||||
end
|
||||
|
||||
local function scoreAttackKamikazeLocation(neighborChunk)
|
||||
local preferred = false
|
||||
if (
|
||||
neighborChunk.playerBaseGenerator
|
||||
or neighborChunk.playerGenerator
|
||||
)
|
||||
then
|
||||
preferred = true
|
||||
end
|
||||
local damage = neighborChunk[KAMIKAZE_PHEROMONE]
|
||||
if preferred then
|
||||
damage = damage * 2
|
||||
end
|
||||
return damage, preferred
|
||||
end
|
||||
|
||||
local function findMovementPosition(surface, position)
|
||||
return surface.find_non_colliding_position(
|
||||
"behemoth-biter",
|
||||
@ -238,7 +272,15 @@ local function addMovementPenalty(squad, chunk)
|
||||
squad.maxDistance = calculateSettlerMaxDistance()
|
||||
|
||||
squad.status = SQUAD_SETTLING
|
||||
elseif not squad.kamikaze then
|
||||
squad.kamikaze = true
|
||||
squad.penalties = {}
|
||||
else
|
||||
for entity in pairs(squad.group.members) do
|
||||
if entity.valid then
|
||||
entity.destroy()
|
||||
end
|
||||
end
|
||||
squad.group.destroy()
|
||||
end
|
||||
end
|
||||
@ -405,6 +447,9 @@ local function settleMove(squad)
|
||||
local scoreFunction = scoreResourceLocation
|
||||
if (squad.type == BASE_AI_STATE_SIEGE) then
|
||||
scoreFunction = scoreSiegeLocation
|
||||
if squad.kamikaze then
|
||||
scoreFunction = scoreSiegeKamikazeLocation
|
||||
end
|
||||
end
|
||||
local squadChunk = squad.chunk
|
||||
if squadChunk ~= -1 then
|
||||
@ -549,6 +594,9 @@ local function attackMove(squad)
|
||||
end
|
||||
|
||||
local attackScorer = scoreAttackLocation
|
||||
if squad.kamikaze then
|
||||
attackScorer = scoreAttackKamikazeLocation
|
||||
end
|
||||
|
||||
squad.frenzy = (squad.frenzy and (euclideanDistanceNamed(groupPosition, squad.frenzyPosition) < 100))
|
||||
local searchPath = scoreNeighbors(
|
||||
|
@ -26,6 +26,13 @@ local Universe
|
||||
|
||||
-- Constants
|
||||
|
||||
local BASE_PHEROMONE = Constants.BASE_PHEROMONE
|
||||
local PLAYER_PHEROMONE = Constants.PLAYER_PHEROMONE
|
||||
local RESOURCE_PHEROMONE = Constants.RESOURCE_PHEROMONE
|
||||
local ENEMY_PHEROMONE = Constants.ENEMY_PHEROMONE
|
||||
local KAMIKAZE_PHEROMONE = Constants.KAMIKAZE_PHEROMONE
|
||||
local CHUNK_TICK = Constants.CHUNK_TICK
|
||||
|
||||
local MINIMUM_EXPANSION_DISTANCE = Constants.MINIMUM_EXPANSION_DISTANCE
|
||||
local DEFINES_COMMAND_GROUP = defines.command.group
|
||||
local DEFINES_COMMAND_WANDER = defines.command.wander
|
||||
@ -552,6 +559,20 @@ function Upgrade.attempt()
|
||||
|
||||
Universe.modAddedTick = game.tick
|
||||
end
|
||||
if global.gameVersion < 2 then
|
||||
global.gameVersion = 2
|
||||
|
||||
for _, map in pairs(Universe.maps) do
|
||||
for _, chunk in pairs(map.processQueue) do
|
||||
chunk[CHUNK_TICK] = 0
|
||||
chunk[BASE_PHEROMONE] = 0
|
||||
chunk[PLAYER_PHEROMONE] = 0
|
||||
chunk[RESOURCE_PHEROMONE] = 0
|
||||
chunk[ENEMY_PHEROMONE] = 0
|
||||
chunk[KAMIKAZE_PHEROMONE] = 0
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
function Upgrade.init(universe)
|
||||
|
@ -215,7 +215,8 @@ function tests.exportAiState()
|
||||
chunk.hiveCount or 0,
|
||||
chunk.trapCount or 0,
|
||||
chunk.utilityCount or 0,
|
||||
global.universe.chunkToVictory[chunk.id] or 0
|
||||
global.universe.chunkToVictory[chunk.id] or 0,
|
||||
chunk[constants.KAMIKAZE_PHEROMONE]
|
||||
}, ",") .. "\n"
|
||||
end
|
||||
game.write_file("rampantState.txt", s, false)
|
||||
|
@ -58,7 +58,8 @@
|
||||
hives
|
||||
traps
|
||||
utility
|
||||
vg)
|
||||
vg
|
||||
kamikaze)
|
||||
#:transparent)
|
||||
|
||||
(struct Chunk (x
|
||||
@ -92,7 +93,8 @@
|
||||
hives
|
||||
traps
|
||||
utility
|
||||
vg)
|
||||
vg
|
||||
kamikaze)
|
||||
#:transparent)
|
||||
|
||||
(require threading)
|
||||
@ -143,7 +145,8 @@
|
||||
"H:" (~v (Chunk-hives chunk)) "\n"
|
||||
"T:" (~v (Chunk-traps chunk)) "\n"
|
||||
"U:" (~v (Chunk-utility chunk)) "\n"
|
||||
"vg:" (~v (Chunk-vg chunk)) "\n"))
|
||||
"vg:" (~v (Chunk-vg chunk)) "\n"
|
||||
"kam:" (~v (Chunk-kamikaze chunk)) "\n")))
|
||||
|
||||
(define (normalizeRange xs)
|
||||
(let* ((sDev (stddev xs))
|
||||
@ -187,7 +190,8 @@
|
||||
(H (map Chunk-hives chunks))
|
||||
(T (map Chunk-traps chunks))
|
||||
(U (map Chunk-utility chunks))
|
||||
(vg (map Chunk-vg chunks)))
|
||||
(vg (map Chunk-vg chunks))
|
||||
(kamikaze (map Chunk-kamikaze chunks)))
|
||||
|
||||
(ChunkRange (MinMax (apply min xs) (apply max xs))
|
||||
(MinMax (apply min ys) (apply max ys))
|
||||
@ -220,7 +224,8 @@
|
||||
(MinMax (apply min H) (apply max H))
|
||||
(MinMax (apply min T) (apply max T))
|
||||
(MinMax (apply min U) (apply max U))
|
||||
(MinMax (apply min vg) (apply max vg)))
|
||||
(MinMax (apply min vg) (apply max vg))
|
||||
(normalizeRange kamikaze)
|
||||
))
|
||||
|
||||
(define (readState filePath)
|
||||
|
@ -279,7 +279,7 @@
|
||||
|
||||
(new radio-box%
|
||||
[label "Show Layer"]
|
||||
[choices (list "movement" "base" "player" "resource" "enemy" "passable" "tick" "rating" "nests" "worms" "rally" "retreat" "resourceGen" "playerGen" "deathGen" "scoreResourceKamikaze" "scoreResource" "scoreSiegeKamikaze" "scoreSiege" "scoreAttackKamikaze" "scoreAttack" "pollution" "aNe" "aRNe" "squads" "baseAlign" "hives" "traps" "utility" "vg")]
|
||||
[choices (list "movement" "base" "player" "resource" "enemy" "passable" "tick" "rating" "nests" "worms" "rally" "retreat" "resourceGen" "playerGen" "deathGen" "scoreResourceKamikaze" "scoreResource" "scoreSiegeKamikaze" "scoreSiege" "scoreAttackKamikaze" "scoreAttack" "pollution" "aNe" "aRNe" "squads" "baseAlign" "hives" "traps" "utility" "vg" "kamikaze")]
|
||||
[selection 0]
|
||||
[parent botPanel]
|
||||
(callback (lambda (radioButton event)
|
||||
|
Loading…
Reference in New Issue
Block a user