1
0
mirror of https://github.com/veden/Rampant.git synced 2025-02-11 13:39:05 +02:00
Rampant/libs/ChunkProcessor.lua

207 lines
6.1 KiB
Lua
Raw Normal View History

2019-02-15 20:17:30 -08:00
if (chunkProcessorG) then
return chunkProcessorG
end
local chunkProcessor = {}
-- imports
local chunkUtils = require("ChunkUtils")
2017-05-31 18:46:53 -07:00
local constants = require("Constants")
-- constants
local CHUNK_SIZE = constants.CHUNK_SIZE
-- imported functions
local registerEnemyBaseStructure = chunkUtils.registerEnemyBaseStructure
local unregisterEnemyBaseStructure = chunkUtils.unregisterEnemyBaseStructure
local createChunk = chunkUtils.createChunk
local initialScan = chunkUtils.initialScan
local chunkPassScan = chunkUtils.chunkPassScan
2020-05-19 19:37:16 -07:00
local next = next
local table_size = table_size
2019-02-10 22:14:17 -08:00
2019-10-20 13:45:43 -07:00
local tRemove = table.remove
local tInsert = table.insert
local mCeil = math.ceil
2019-10-20 13:45:43 -07:00
-- module code
local function findInsertionPoint(processQueue, chunk)
local low = 1
local high = #processQueue
local pivot
while (low <= high) do
pivot = mCeil((low + high) * 0.5)
local pivotChunk = processQueue[pivot]
if (pivotChunk.dOrigin > chunk.dOrigin) then
high = pivot - 1
elseif (pivotChunk.dOrigin <= chunk.dOrigin) then
low = pivot + 1
2019-02-10 22:14:17 -08:00
end
end
return low
2019-02-10 22:14:17 -08:00
end
local function removeProcessQueueChunk(processQueue, chunk)
local insertionPoint = findInsertionPoint(processQueue, chunk)
for i=insertionPoint,1,-1 do
if (processQueue[i] == chunk) then
tRemove(processQueue, i)
end
end
end
2021-02-19 21:41:30 -08:00
function chunkProcessor.processPendingChunks(map, tick, flush)
2018-01-13 21:48:21 -08:00
local processQueue = map.processQueue
2020-05-19 19:37:16 -07:00
local pendingChunks = map.pendingChunks
2021-02-19 23:31:36 -08:00
local area = map.universe.area
2019-02-10 22:14:17 -08:00
local topOffset = area[1]
local bottomOffset = area[2]
2019-11-29 16:49:22 -08:00
local event = map.chunkProcessorIterator
if not event then
event = next(pendingChunks, nil)
end
local endCount = 1
2020-05-19 19:37:16 -07:00
if flush then
endCount = table_size(pendingChunks)
event = next(pendingChunks, nil)
2020-05-19 19:37:16 -07:00
end
2021-02-13 20:49:54 -08:00
for _=1,endCount do
2020-05-19 19:37:16 -07:00
if not event then
map.chunkProcessorIterator = nil
if (table_size(pendingChunks) == 0) then
-- this is needed as the next command remembers the max length a table has been
map.pendingChunks = {}
2019-05-15 22:11:43 -07:00
end
2020-05-19 19:37:16 -07:00
break
else
if not flush and (event.tick > tick) then
map.chunkProcessorIterator = event
return
end
2020-05-19 19:37:16 -07:00
local topLeft = event.area.left_top
local x = topLeft.x
local y = topLeft.y
topOffset[1] = x
topOffset[2] = y
bottomOffset[1] = x + CHUNK_SIZE
bottomOffset[2] = y + CHUNK_SIZE
if not map[x] then
map[x] = {}
end
2020-05-19 19:37:16 -07:00
if map[x][y] then
local chunk = initialScan(map[x][y], map, tick)
if (chunk == -1) then
removeProcessQueueChunk(processQueue, map[x][y])
map[x][y] = nil
end
else
local chunk = createChunk(x, y)
map[x][y] = chunk
chunk = initialScan(chunk, map, tick)
2020-05-19 19:37:16 -07:00
if (chunk ~= -1) then
map[x][y] = chunk
tInsert(
processQueue,
findInsertionPoint(processQueue, chunk),
chunk
)
else
map[x][y] = nil
2020-05-19 19:37:16 -07:00
end
2019-05-15 22:11:43 -07:00
end
local newEvent = next(pendingChunks, event)
2020-05-19 19:37:16 -07:00
pendingChunks[event] = nil
event = newEvent
2019-11-29 16:49:22 -08:00
end
end
2020-05-19 19:37:16 -07:00
map.chunkProcessorIterator = event
end
function chunkProcessor.processPendingUpgrades(map, tick)
local pendingUpgrades = map.pendingUpgrades
local entity = map.pendingUpgradeIterator
local entityData
if not entity then
entity, entityData = next(pendingUpgrades, nil)
else
entityData = pendingUpgrades[entity]
end
if entity then
if entity.valid then
map.pendingUpgradeIterator = next(pendingUpgrades, entity)
pendingUpgrades[entity] = nil
local universe = map.universe
local query = universe.upgradeEntityQuery
query.position = entityData.position or entity.position
query.name = entityData.name
local surface = entity.surface
unregisterEnemyBaseStructure(map, entity)
entity.destroy()
local createdEntity = surface.create_entity(query)
if createdEntity and createdEntity.valid then
registerEnemyBaseStructure(map, createdEntity, tick, entityData.base)
if remote.interfaces["kr-creep"] then
remote.call("kr-creep", "spawn_creep_at_position", surface, query.position)
end
end
else
map.pendingUpgradeIterator = next(pendingUpgrades, entity)
pendingUpgrades[entity] = nil
end
end
end
2021-02-19 21:41:30 -08:00
function chunkProcessor.processScanChunks(map)
2021-02-19 23:31:36 -08:00
local area = map.universe.area
2019-11-29 16:49:22 -08:00
local topOffset = area[1]
local bottomOffset = area[2]
2019-10-20 13:45:43 -07:00
local removals = map.chunkRemovals
local chunkCount = 0
2019-10-20 13:45:43 -07:00
local chunkToPassScan = map.chunkToPassScan
2019-11-29 16:49:22 -08:00
2021-04-21 20:46:50 -07:00
for preScanChunk in pairs(chunkToPassScan) do
local x = preScanChunk.x
local y = preScanChunk.y
2019-02-10 22:14:17 -08:00
2019-10-19 12:13:48 -07:00
topOffset[1] = x
topOffset[2] = y
bottomOffset[1] = x + CHUNK_SIZE
bottomOffset[2] = y + CHUNK_SIZE
2021-04-21 20:46:50 -07:00
if (chunkPassScan(preScanChunk, map) == -1) then
2019-10-19 12:13:48 -07:00
map[x][y] = nil
2019-10-20 13:45:43 -07:00
chunkCount = chunkCount + 1
2021-04-21 20:46:50 -07:00
removals[chunkCount] = preScanChunk
2019-10-19 12:13:48 -07:00
end
2019-11-29 16:49:22 -08:00
2021-04-21 20:46:50 -07:00
chunkToPassScan[preScanChunk] = nil
end
2019-10-20 13:45:43 -07:00
if (chunkCount > 0) then
2019-03-10 12:28:43 -07:00
local processQueue = map.processQueue
for ri=chunkCount,1,-1 do
removeProcessQueueChunk(processQueue, removals[ri])
2019-03-10 12:28:43 -07:00
end
end
end
2019-02-15 20:17:30 -08:00
chunkProcessorG = chunkProcessor
return chunkProcessor