Skip to content

Commit

Permalink
Introduce simple AI factory behavior (#5508)
Browse files Browse the repository at this point in the history
  • Loading branch information
Garanas authored Oct 10, 2023
1 parent 6116bb7 commit 014846f
Show file tree
Hide file tree
Showing 29 changed files with 1,232 additions and 319 deletions.
10 changes: 5 additions & 5 deletions engine/Sim/CAiBrain.lua
Original file line number Diff line number Diff line change
Expand Up @@ -207,27 +207,27 @@ function CAiBrain:GetCurrentUnits(category)
end

--- Returns current resource income.
-- @param resource 'ENERGY' or 'MASS'.
---@param resource 'ENERGY'|'MASS'.
-- @return Number.
function CAiBrain:GetEconomyIncome(resource)
end

--- Return how much of the resource the brains wants to use.
-- This is used for calculating Paragon's production.
-- @param resource 'ENERGY' or 'MASS'.
---@param resource 'ENERGY'|'MASS'.
-- @return Number.
function CAiBrain:GetEconomyRequested(resource)
end

--- Return current resource amout in storage.
-- @param resource 'ENERGY' or 'MASS'.
---@param resource 'ENERGY'|'MASS'.
-- @return Number.
function CAiBrain:GetEconomyStored(resource)
end

--- Returns the ratio between resource in storage to maximum storage amout.
-- @param resource 'ENERGY' or 'MASS'.
-- @return Float Number 0.0 - 1
---@param resource 'ENERGY' | 'MASS'.
---@return number
function CAiBrain:GetEconomyStoredRatio(resource)
end

Expand Down
25 changes: 24 additions & 1 deletion lua/aibrains/components/economy.lua
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ end
local GetEconomyIncome = moho.aibrain_methods.GetEconomyIncome
local GetEconomyRequested = moho.aibrain_methods.GetEconomyRequested
local GetEconomyTrend = moho.aibrain_methods.GetEconomyTrend
local GetEconomyStoredRatio = moho.aibrain_methods.GetEconomyStoredRatio

local MathMin = math.min

Expand All @@ -24,20 +25,24 @@ local MathMin = math.min
---@field EnergyRequested table<number, number>
---@field EnergyStorage table<number, number>
---@field EnergyTrend table<number, number>
---@field EnergyStoredRatio table<number, number>
---@field MassIncome table<number, number>
---@field MassRequested table<number, number>
---@field MassStorage table<number, number>
---@field MassTrend table<number, number>
---@field MassStoredRatio table<number, number>

---@class AIBrainEconomyOverTimeData
---@field EnergyIncome number
---@field EnergyRequested number
---@field EnergyEfficiencyOverTime number
---@field EnergyTrendOverTime number
---@field EnergyStoredRatioOverTime number
---@field MassIncome number
---@field MassRequested number
---@field MassEfficiencyOverTime number
---@field MassTrendOverTime number
---@field MassStoredRatioOverTime number

---@class AIBrainEconomyComponent : AIBrain
---@field EconomyData AIBrainEconomyData
Expand All @@ -57,10 +62,12 @@ AIBrainEconomyComponent = ClassSimple {
EnergyRequested = {},
EnergyStorage = {},
EnergyTrend = {},
EnergyStoredRatio = {},
MassIncome = {},
MassRequested = {},
MassStorage = {},
MassTrend = {}
MassTrend = {},
MassStoredRatio = {},
}

local economyData = self.EconomyData
Expand All @@ -69,21 +76,25 @@ AIBrainEconomyComponent = ClassSimple {
economyData.EnergyRequested[k] = 0
economyData.EnergyStorage[k] = 0
economyData.EnergyTrend[k] = 0
economyData.EnergyStoredRatio[k] = 0
economyData.MassIncome[k] = 0
economyData.MassRequested[k] = 0
economyData.MassStorage[k] = 0
economyData.MassTrend[k] = 0
economyData.MassStoredRatio[k] = 0
end

self.EconomyOverTimeCurrent = {
EnergyIncome = 0,
EnergyRequested = 0,
EnergyEfficiencyOverTime = 0,
EnergyTrendOverTime = 0,
EnergyStoredRatioOverTime = 0,
MassIncome = 0,
MassRequested = 0,
MassEfficiencyOverTime = 0,
MassTrendOverTime = 0,
MassStoredRatioOverTime = 0,
}

self:EconomyUpdate()
Expand All @@ -102,6 +113,8 @@ AIBrainEconomyComponent = ClassSimple {
local mIncome = 0
local eRequested = 0
local mRequested = 0
local eRatio = 0
local mRatio = 0
local eTrend = 0
local mTrend = 0

Expand All @@ -117,6 +130,8 @@ AIBrainEconomyComponent = ClassSimple {
local EcoDataMassRequested = EcoData.MassRequested
local EcoDataEnergyTrend = EcoData.EnergyTrend
local EcoDataMassTrend = EcoData.MassTrend
local EcoDataEnergyStoredRatio = EcoData.EnergyStoredRatio
local EcoDataMassStoredRatio = EcoData.MassStoredRatio

for point = 1, self.EconomySamples do

Expand All @@ -127,12 +142,16 @@ AIBrainEconomyComponent = ClassSimple {
mRequested = mRequested - EcoDataMassRequested[point]
eTrend = eTrend - EcoDataEnergyTrend[point]
mTrend = mTrend - EcoDataMassTrend[point]
eRatio = eRatio - EcoDataEnergyStoredRatio[point]
mRatio = mRatio - EcoDataMassStoredRatio[point]

-- add new data
EcoDataEnergyIncome[point] = GetEconomyIncome(self, 'ENERGY')
EcoDataMassIncome[point] = GetEconomyIncome(self, 'MASS')
EcoDataEnergyRequested[point] = GetEconomyRequested(self, 'ENERGY')
EcoDataMassRequested[point] = GetEconomyRequested(self, 'MASS')
EcoDataEnergyStoredRatio[point] = GetEconomyStoredRatio(self, 'ENERGY')
EcoDataMassStoredRatio[point] = GetEconomyStoredRatio(self, 'MASS')

-- special case for trend
energyTrend = GetEconomyTrend(self, 'ENERGY')
Expand All @@ -157,6 +176,8 @@ AIBrainEconomyComponent = ClassSimple {
mRequested = mRequested + EcoDataMassRequested[point]
eTrend = eTrend + EcoDataEnergyTrend[point]
mTrend = mTrend + EcoDataMassTrend[point]
eRatio = eRatio + EcoDataEnergyStoredRatio[point]
mRatio = mRatio + EcoDataMassStoredRatio[point]

-- calculate new over time values
local sampleInverse = (1 / self.EconomySamples)
Expand All @@ -169,6 +190,8 @@ AIBrainEconomyComponent = ClassSimple {
economyOverTimeCurrent.MassEfficiencyOverTime = MathMin((mIncome * sampleInverse) / (mRequested * sampleInverse), 2)
economyOverTimeCurrent.EnergyTrendOverTime = eTrend * sampleInverse
economyOverTimeCurrent.MassTrendOverTime = mTrend * sampleInverse
economyOverTimeCurrent.EnergyStoredRatioOverTime = eRatio * sampleInverse
economyOverTimeCurrent.MassStoredRatioOverTime = mRatio * sampleInverse

if Debug then
local army = self:GetArmyIndex()
Expand Down
86 changes: 86 additions & 0 deletions lua/aibrains/conditions/EconomyConditions.lua
Original file line number Diff line number Diff line change
@@ -0,0 +1,86 @@

--******************************************************************************************************
--** Copyright (c) 2022 Willem 'Jip' Wijnia
--**
--** Permission is hereby granted, free of charge, to any person obtaining a copy
--** of this software and associated documentation files (the "Software"), to deal
--** in the Software without restriction, including without limitation the rights
--** to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
--** copies of the Software, and to permit persons to whom the Software is
--** furnished to do so, subject to the following conditions:
--**
--** The above copyright notice and this permission notice shall be included in all
--** copies or substantial portions of the Software.
--**
--** THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
--** IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
--** FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
--** AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
--** LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
--** OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
--** SOFTWARE.
--******************************************************************************************************

--- Compares (using `>`) the ratio of ((energy stored) / (total energy storage))
---@param aiBrain AIBrain | AIBrainEconomyComponent
---@param base AIBase
---@param ratio number # number between 0.0 and 1.0
function GreaterEnergyRatio(aiBrain, base, platoon, ratio)
return aiBrain:GetEconomyStoredRatio('ENERGY') > ratio
end

--- Compares (using `<`) the ratio of ((energy stored) / (total energy storage))
---@param aiBrain AIBrain | AIBrainEconomyComponent
---@param base AIBase
---@param ratio number # number between 0.0 and 1.0
function LessEnergyRatio(aiBrain, base, platoon, ratio)
return aiBrain:GetEconomyStoredRatio('ENERGY') < ratio
end

--- Compares (using `>`) the ratio of ((mass stored) / (total mass storage))
---@param aiBrain AIBrain | AIBrainEconomyComponent
---@param base AIBase
---@param ratio number # number between 0.0 and 1.0
function GreaterMassRatio(aiBrain, base, platoon, ratio)
return aiBrain:GetEconomyStoredRatio('MASS') > ratio
end

--- Compares (using `<`) the ratio of ((mass stored) / (total mass storage))
---@param aiBrain AIBrain | AIBrainEconomyComponent
---@param base AIBase
---@param ratio number # number between 0.0 and 1.0
function LessMassRatio(aiBrain, base, platoon, ratio)
return aiBrain:GetEconomyStoredRatio('MASS') < ratio
end

--- Compares (using `>`) the trend of the ratio of ((energy stored) / (total energy storage))
---@param aiBrain AIBrain | AIBrainEconomyComponent
---@param base AIBase
---@param ratio number # number between 0.0 and 1.0
function GreaterEnergyRatioTrend(aiBrain, base, platoon, ratio)
return aiBrain.EconomyOverTimeCurrent.EnergyStoredRatioOverTime > ratio
end

--- Compares (using `<`) the ratio of ((energy stored) / (total energy storage))
---@param aiBrain AIBrain | AIBrainEconomyComponent
---@param base AIBase
---@param ratio number # number between 0.0 and 1.0
function LessEnergyRatioTrend(aiBrain, base, platoon, ratio)
return aiBrain.EconomyOverTimeCurrent.EnergyStoredRatioOverTime < ratio
end

--- Compares (using `>`) the ratio of ((mass stored) / (total mass storage))
---@param aiBrain AIBrain | AIBrainEconomyComponent
---@param base AIBase
---@param ratio number # number between 0.0 and 1.0
function GreaterMassRatioTrend(aiBrain, base, platoon, ratio)
return aiBrain.EconomyOverTimeCurrent.MassStoredRatioOverTime > ratio
end

--- Compares (using `<`) the ratio of ((mass stored) / (total mass storage))
---@param aiBrain AIBrain | AIBrainEconomyComponent
---@param base AIBase
---@param ratio number # number between 0.0 and 1.0
function LessMassRatioTrend(aiBrain, base, platoon, ratio)
return aiBrain.EconomyOverTimeCurrent.MassStoredRatioOverTime < ratio
end
Original file line number Diff line number Diff line change
@@ -1,16 +1,31 @@
-----------------------------------------------------------------
-- Summary: Contains all builder conditions that directly
-- interface with the refactored engineer manager
--
-- All functions in this file are guaranteed to be efficient
-----------------------------------------------------------------
--******************************************************************************************************
--** Copyright (c) 2022 Willem 'Jip' Wijnia
--**
--** Permission is hereby granted, free of charge, to any person obtaining a copy
--** of this software and associated documentation files (the "Software"), to deal
--** in the Software without restriction, including without limitation the rights
--** to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
--** copies of the Software, and to permit persons to whom the Software is
--** furnished to do so, subject to the following conditions:
--**
--** The above copyright notice and this permission notice shall be included in all
--** copies or substantial portions of the Software.
--**
--** THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
--** IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
--** FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
--** AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
--** LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
--** OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
--** SOFTWARE.
--******************************************************************************************************

--- Compares (using `<`) the count to the number of engineers at a location type
---@param aiBrain AIBrain
---@param base AIBase
---@param count number
---@return boolean
function LessEngineersThan(aiBrain, base, count)
function LessEngineersThan(aiBrain, base, platoon, count)
if base.EngineerManager.EngineerTotalCount() < count then
return true
end
Expand All @@ -23,7 +38,7 @@ end
---@param base AIBase
---@param count number
---@return boolean
function MoreEngineersThan(aiBrain, base, count)
function MoreEngineersThan(aiBrain, base, platoon, count)
if base.EngineerManager.EngineerTotalCount > count then
return true
end
Expand All @@ -37,7 +52,7 @@ end
---@param count number
---@param tech TechCategory
---@return boolean
function LessEngineersByTech(aiBrain, base, count, tech)
function LessEngineersByTech(aiBrain, base, platoon, count, tech)
if base.EngineerManager.EngineerCount[tech] < count then
return true
end
Expand All @@ -51,7 +66,7 @@ end
---@param count number
---@param tech TechCategory
---@return boolean
function MoreEngineersByTech(aiBrain, base, count, tech)
function MoreEngineersByTech(aiBrain, base, platoon, count, tech)
if base.EngineerManager.EngineerCount[tech] > count then
return true
end
Expand All @@ -65,7 +80,7 @@ end
---@param count number
---@param techs TechCategory[]
---@return boolean
function LessEngineersByTechList(aiBrain, base, count, techs)
function LessEngineersByTechList(aiBrain, base, platoon, count, techs)
local engineerManager = base.EngineerManager
for _, tech in techs do
if engineerManager.EngineerCount[tech] < count then
Expand All @@ -82,7 +97,7 @@ end
---@param count number
---@param techs TechCategory[]
---@return boolean
function LessEngineersByTechList(aiBrain, base, count, techs)
function LessEngineersByTechList(aiBrain, base, platoon, count, techs)
local engineerManager = base.EngineerManager
for _, tech in techs do
if engineerManager.EngineerCount[tech] > count then
Expand Down
Loading

0 comments on commit 014846f

Please sign in to comment.