Jump to content


Replying to DoW1 Mod Project Basic Mod Workflow Checklist


Post Options

    • Can't make it out? Click here to generate a new image

  or Cancel


Topic Summary

thudo

Posted 16 July 2019 - 05:53 PM

EXTRA - Updated: July XX, 2019.

 

TBD.


thudo

Posted 09 July 2019 - 09:29 PM

SCAR- Updated: July XX, 2019.

 

TBD.


thudo

Posted 01 July 2019 - 05:36 AM

MISC - Updated: July 16, 2019.

 

This section deals with some odds and ends to consider when debugging issues with your mod.

 

 

Initial Launch Troubleshooting

 

When starting the game from the desktop these could be possible issues to examine and correct:

 

Hint #1: Note this example warning in the warnings.log:

MOD -- Warning: Failed to open folder 'Ultramarines\Locale\english\Data'.
MOD -- Warning: Failed to open folder 'Ultramarines\Data_Shared_Textures\Full'.
MOD -- Warning: Failed to open folder 'Ultramarines\Data_Sound\Full'.
MOD -- Warning: Failed to open folder 'Ultramarines\Data_Music'.
MOD -- Warning: Failed to open folder 'Ultramarines\Data_Whm\High'.

Solution: These errors are generated when in your project's .MODULE file has excess "DataFolder.X" row entries which are not required. Instead, only use this line: "DataFolder.1 = Data". This could also occur with "ArchiveFile.X" rows so please comment them out (use ";;" to disable each line) or remove all "ArchiveFile.X" line rows.

 

As example in your project's .MODULE file this:

DataFolder.1 = %LOCALE%\Data
DataFolder.2 = Data
DataFolder.3 = Data_Shared_Textures\%TEXTURE-LEVEL%
DataFolder.4 = Data_Sound\%SOUND-LEVEL%
DataFolder.5 = Data_Music
DataFolder.6 = Data_Whm\%MODEL-LEVEL%

and/or this:

ArchiveFile.1 = %LOCALE%\DXP2DataLoc
ArchiveFile.2 = %LOCALE%\DXP2DataKeys
ArchiveFile.3 = DXP2Data
ArchiveFile.4 = DXP2Data-SharedTextures-%TEXTURE-LEVEL%
ArchiveFile.5 = %LOCALE%\DXP2Data-Sound-Speech
ArchiveFile.6 = DXP2Data-Sound-%SOUND-LEVEL%
ArchiveFile.7 = DXP2Data-Music
ArchiveFile.8 = DXP2Data-Whm-%MODEL-LEVEL%

should be condensed to this:

DataFolder.1 = Data

This will simplify the deployment and pathing of your project's assets.

 

 

Hint #2: Note this example warning in the warnings.log:

LOCALIZER -- Requested string ID '18210121' does not fit in a valid key range!
LOCALIZER -- Requested string ID '691600' does not exist!

Solution: Missing UCS # (not found anywhere in either the vanilla UCS or your project's UCS files). Use a program like Beyond Compare or Total Commander to locate these missing UCS #s to determine if these missing values need to be placed in your project's own .UCS file OR rename these values in the impacted AE object as "$0" which nulls/disables the value.

 

Note: Go to the UCS section here to ensure you have followed the best practice instructions to ensure your UCS entries are consistent and accounted for.

 

 

Hint #3: Note this example warning in the warnings.log:

SIM -- Attempted to load duplicate blueprint, EBPs\Environment\gameplay\ultra_marine_bomb.rgd (1137)

Solution: This AE object "ultra_marine_bomb" has the same name as used by another loaded object possibly in your EBPS\RACES\[MOD_NAME]\TROOPS folder. Only use unique names for loaded AE objects so rename the one in EBPs\Environment\gameplay (so outside your EBPS\RACES\[MOD_NAME]\TROOPS).

 

 

SCAR specific errors

 

A few SCAR errors you should identify and correct in your project usually found as you are starting to load a map:

 

 

Hint #1: Note this example warning in either the warnings.log or scarlog.txt found in [root Soulstorm folder]\logfiles\[last game run instance]:

[string "DATA:Scar/WinConditions/AIDonations.scar"]:577: `}' expected (to close `{' at line 16) near `ultra_marine_race'

Solution: Broken script logic in this impacted .SCAR file. Open this file in Notepad (it is a text file after all) and correct the broken logic.


thudo

Posted 01 July 2019 - 12:29 AM

AI - Updated: March 18, 2023.

 

This section will cover various AI issues and how to best to troubleshoot them using example scenarios.

 

In an fashion, an assumption will be made that the developer trying to debug their Dawn of War AI has a "modest" understanding of LUA coding and basic scripting logic but this cannot always be the case.

 

 

Master AI Documentation

 

Find attached below the master documented which I created a decade+ ago which will make you go through step-by-step the AI workflow and give you an understanding how the basic script logic works and relates to the various parts. Please consult the attached text file to get a good broad overview of scripting AI in Dawn of War.

 

This document will be updated if required but I find if you have any concerns how to do something in the LUA logic for your project's AI chances are another project has likely done something similar and you can "adopt its scripts" for use within your own. This, of course, depends on whether it suits your needs "as is" or if "new features" are required to be added to it.

 

 

Common AI issues

 

Note: Please ensure you are first running the game in -DEV mode as per instructions in the first message of this thread.

 

In this section, there are two logs you will need to consult: warnings.txt found in both [root Soulstorm folder] and [root Soulstorm folder]\logfiles\[last game run instance] and ailog.txt in [root Soulstorm folder]\logfiles\[last game run instance]. The ailog.txt, however, should largely be consulted first since most of the following warnings will be dumped there first.

 

We will break down Dawn of War AI errors based on the .ai files which should be examined causing problem.

 

Also, throughout the course of this section we will be using the Ultramarines faction mod project as an example.

 

Loader.ai

 

This file is located in your project's [Mod Name]\Data\ai\races\[Faction AI race root folder]

 

Hint #1:

Failed to import lua file 'Data:AI/Races/ultra_marine_race/Tactics/UltraMarineMyCoolUnitTactic.ai'
 *ALERT: failed to import 'Races/ultra_marine_race/Tactics/UltraMarineMyCoolUnitTactic.ai', file failed to open
  Lua             Races/ultra_marine_race/Loader.ai Ln   36 (LoadRace)
  Lua             Races/RaceLoader.ai            Ln   94 (?)
  Lua             Core/cpu_manager.ai            Ln  405 (Initialize)
  Lua             DATA:AI/default.ai             Ln  115 (InitializeAI)
  main            DATA:AI/default.ai             Ln  133 ((null))
Error loading script file 'DATA:AI/default.ai' for race 'ultra_marine_race'!

Solution: Check your Loader.ai file (example above is "Races/ultra_marine_race/Loader.ai Ln   36") and see what line is loading which missing .ai file. This means you are trying to load an invalid .ai file.


Hint #2:

CpuManager: No unit stats available for: ultra_marine_squad_builder!!! Using default tactic...
Warning: ultra_marine_squad_builder has no unit strength!
 *ALERT: MilitaryManager:Update() threw exception (lua runtime error)
  Lua             Core/cpu_manager.ai            Ln 1564 (?)
  Lua             Core/cpu_manager.ai            Ln  419 (Initialize)
  Lua             DATA:AI/default.ai             Ln  115 (InitializeAI)
  main            DATA:AI/default.ai             Ln  133 ((null))
Error loading script file 'DATA:AI/default.ai' for race 'ultra_marine_race'!

Solution: A syntax error exists and must be corrected first before any of the rest of your .ai files are loaded since the Loader.ai is the focal point to which all other .ai files in your project are called from.
 

 

Hint #3:

*ALERT: [string "Races/ultra_marine_race/Loader.ai"]:118: attempt to perform arithmetic on global `a' (a nil value)

Solution: Using the example, at Line 118 of the Loader.ai the script logic was expecting a numeric value but found an invalid letter "a" instead.

 

 

Hint #4:

*ALERT: [string "Core/utility.ai"]:93: Assertion failed at Races/RaceLoader.ai, line 69
Error loading script file 'DATA:AI/default.ai' for race 'ultra_marine_race'!

Solution: Incomplete or invalid line found in your Loader.ai. Please correct the syntax so the command is valid.
 

 

[Faction name]unitstats.ai

 

This file is located in your project's [Mod Name]\Data\ai\races\[Faction AI race root folder]\info

 

Hint #1:

*ALERT: AIStats:LoadUnitStats() threw exception (cannot find entity blueprint 'ultra_marine_scout')
  Lua             Core/cpu_manager.ai            Ln  413 (Initialize)
  Lua             DATA:AI/default.ai             Ln  115 (InitializeAI)
  main            DATA:AI/default.ai             Ln  133 ((null))
Error loading script file 'DATA:AI/default.ai' for race 'ultra_marine_race'!

Solution: Check your Unitstats.ai file and ensure all your EBPS and SBPS units match up correctly. The above example means the SBPS entity in your unitstats.ai is not accurated linked to the expected EBPS entity (which they should be in your project's AE code).

 

 

Hint #2:

AI Unit Stats: 'ultra_marine_squad_builder' -- invalid ebp name 'ultra_marine_builde'!
 *ALERT: AIStats:LoadUnitStats() threw exception (cannot find entity blueprint 'ultra_marine_builde')
  Lua             Core/cpu_manager.ai            Ln  413 (Initialize)
  Lua             DATA:AI/default.ai             Ln  115 (InitializeAI)
  main            DATA:AI/default.ai             Ln  133 ((null))
Error loading script file 'DATA:AI/default.ai' for race 'ultra_marine_race'!

Solution: Check your Unitstats.ai file and ensure the EBPS name that was flagged is actually named correct and is valid for this entry + associated properly with its SBPS entity.

 

 

Hint #3:

*ALERT: AIStats:LoadUnitStats() threw exception (unable to make cast)
  Lua             Core/cpu_manager.ai            Ln  413 (Initialize)
  Lua             DATA:AI/default.ai             Ln  115 (InitializeAI)
  main            DATA:AI/default.ai             Ln  133 ((null))
Error loading script file 'DATA:AI/default.ai' for race 'ultra_marine_race'!

Solution: This one is specifically related to your Unitstats.ai file which could mean a EBPS/SBPS entity is missing Effectiveness values or something invalid located only in Unitstats.ai.

 

 

Hint #4:

Warning: ultra_marine_squad_honour_guard has no unit strength!

Solution: This one is specifically related to your Unitstats.ai file where near the top of this .ai file you are missing this required line:

UnitStrengths.ultra_marine_squad_honour_guard = XXXX 

where XXXX is the assigned ArmyStrength value in comparison to other units in vanilla or faction mod projects.

 

 

Hint #5:

*ALERT: [string "Races/ultra_marine_race/Info/UltraMarineUnitstats.ai"]:8: unexpected symbol near `='
  Lua             Races/ultra_marine_race/Loader.ai Ln   44 (LoadGlobalInfo)
  Lua             Races/RaceLoader.ai            Ln   81 (?)
  Lua             Core/cpu_manager.ai            Ln  400 (Initialize)
  Lua             DATA:AI/default.ai             Ln  115 (InitializeAI)
  main            DATA:AI/default.ai             Ln  133 ((null))
Error loading script file 'DATA:AI/default.ai' for race 'ultra_marine_race'!

Solution: A general missing syntax error where a character is missing that was expected to complete the line. In this case it is in the Unitstats.ai file where this line:

UnitStrengths.ultra_marine_squad_cool_crew =

has to be:

UnitStrengths.ultra_marine_squad_cool_crew = 35

This is because a value was expected to close this particular line.

 

 

Hint #6:

*ALERT: no static 'UC_LightInfantryMd' in class 'UnitStatsAI'
  main            Races/ultra_marine_race/Info/UltraMarineUnitstats.ai Ln   43 ((null))
  C               =[C]                           Ln   -1 (import)
  Lua             Races/ultra_marine_race/Loader.ai Ln   44 (LoadGlobalInfo)
  Lua             Races/RaceLoader.ai            Ln   81 (?)
  Lua             Core/cpu_manager.ai            Ln  400 (Initialize)
  Lua             DATA:AI/default.ai             Ln  115 (InitializeAI)
  main            DATA:AI/default.ai             Ln  133 ((null))
Error loading script file 'DATA:AI/default.ai' for race 'ultra_marine_race'!

Solution: Check your Unitstats.ai file and ensure one of your Class types (based on the line reported above, as example) is corrected as there are standard Class Types the game uses.

 

 

Hint #7:

'ultra_marine_scout': upgrade 'ultra_marine_marine_shotgun' is an invalid upgrade for this entity type!

Solution: In your faction mod's AI Unitstats.ai the hardpoint associated with the unit is not valid based on the loaded EBPS unit. Please ensure your AI is updated here with the correct weapon\ names assigned to the EBPS unit.
 

 

[Faction name]buildbasestrategy.ai

 

This file is located in your project's [Mod Name]\Data\ai\races\[Faction AI race root folder]\strategies

 

Hint #1:

Cannot get prerequisites: Trying to build an invalid research: ultra_marine_support_research
Cannot get prerequisites: Trying to build an invalid addon: ultra_marine_captain_upgrade

Solution: Check that your AE project actually uses these entities and they can be buildable even by a human player. If the above research and addon are part of your project BUT non-buildable in-game then the above warnings will be dumped. In this instance, the AI should not be asked to build the above research or addon.

 

 

Hint #2:

*ALERT: [string "Core/utility.ai"]:93: Assertion failed at Core/Strategies/Strategy.ai, line 31
Error loading script file 'DATA:AI/default.ai' for race 'ultra_marine_race'!

Solution: Syntax error in your project's BuildBaseStrategy .ai file likely related to a misspelled declaration not following process or accidental capitalization.

 

 

[Faction name]buildbasestrategyinfo.ai

 

This file is located in your project's [Mod Name]\Data\ai\races\[Faction AI race root folder]\strategies

 

Hint #1:

Trying to add a limit to a non-existant squad: ultra_marine_squad_honour_guar

Solution: Check your [race name]strategyinfo.ai file to see if such a squad is actually a valid one. As example, go to ultramarinestrategyinfo.ai and note the "SquadLimits" section for this specific error:

                ultra_marine_squad_honour_guar = 1,

In this case, based on the Ultramarines faction AI's Unitstats.ai file the correct valid SBPS squad name is actually:

                ultra_marine_squad_honour_guard = 1,

So use only valid SBPS squad names here.

 

 

Hint #2:

*ALERT: [string "Core/utility.ai"]:93: Assertion failed at Core/Strategies/BuildOrderStrategy.ai, line 211
Error loading script file 'DATA:AI/default.ai' for race 'ultra_marine_race'!

Solution: Syntax error in your project's BuildBaseStrategyInfo .ai file likely related to a misspelled declaration not following process or accidental capitalization.

 

[Faction name]tactic .ai files

 

These files are located in your project's [Mod Name]\Data\ai\races\[Faction AI race root folder]\tactics

 

Hint #1:

*ALERT: MilitaryManager:Update() threw exception (lua runtime error)
  Lua             Core/cpu_manager.ai            Ln 1564 (?)
  Lua             Core/cpu_manager.ai            Ln  419 (Initialize)
  Lua             DATA:AI/default.ai             Ln  115 (InitializeAI)
  main            DATA:AI/default.ai             Ln  133 ((null))
Error loading script file 'DATA:AI/default.ai' for race 'ultra_marine_race'!

or

*ALERT: MilitaryManager:Update() threw exception (lua runtime error)
  Lua             Core/cpu_manager.ai            Ln 1564 (?)
  Lua             Core/cpu_manager.ai            Ln 1416 (Update)
  Lua             DATA:AI/default.ai             Ln   53 (AI_Think)

Solution: This error generally means there is a syntax framework error in a loaded .ai of yours. It can be caused by something like this:

function UltraMarineBuilderTactic:__init( quad_ai ) super( squad_ai )

The correct syntax should be:

function UltraMarineBuilderTactic:__init( squad_ai ) super( squad_ai )

Be mindful of your script logic and keep to conventions. If you cannot find it, comment out large sections of your loader.ai especially in the CreateTactic(oSquadAI) section. This will allow you to better troubleshoot which .ai file is causing the problem.

 

 

Hint #2:

*ALERT: [string "Races/ultra_marine_race/Tactics/UltraMarineInfantryTactic.ai"]:155: `)' expected near `then'
  Lua             Races/ultra_marine_race/Loader.ai Ln   27 (LoadRace)
  Lua             Races/RaceLoader.ai            Ln   94 (?)
  Lua             Core/cpu_manager.ai            Ln  405 (Initialize)
  Lua             DATA:AI/default.ai             Ln  115 (InitializeAI)
  main            DATA:AI/default.ai             Ln  133 ((null))
Error loading script file 'DATA:AI/default.ai' for race 'ultra_marine_race'!

Solution: Locate this .ai file (example above is the .ai file mentioned in your loader.ai at this part "Races/ultra_marine_race/Loader.ai Ln   36") and correct the missing ")" required to properly secure the Function.


Hint #3:

*ALERT: [string "Races/ultra_marine_race/Tactics/UltraMarine..."]:153: stack overflow: [string "Races/ultra_marine_race/Tactics/UltraMarine..."]:153
[string "Races/ultra_marine_race/Tactics/UltraMarine..."]:163

Solution: Stack Overflows are likely caused by a unit that has the same ability applied twice or more which basically overflows the AI's buffer trying to preform duplicate tasks. ie. [My_Mod]InfantryTactic has frag_grenades ability active while the same named ability is called in an attachable commander unit with same abilities.

 

Best to keep ability names exclusive from generic abilities, disable any InitAbilities/DoAbilities, or disable the AI attachment logic.
 

 

Hint #4:

Warning: Ability ID in function DoAbility of player 1001 not defined!

Solution: In one of your AI Tactic files there is a DoAbility script which has broken logic that is undeclared and missing being bound to an actual ability name attached to your EBPS unit.

 

As an example in this Ultramarine Commander Tactic .ai file this is incorrect:

function UltraMarineCommanderTactic:InitAbilities()

end

function UltraMarineCommanderTactic:DoAbilities()

    Ability.DoAbility( self.squad_ai, UltraMarineCommander.nuke_id, Ability.Filters.IsInCombat )
end

Notice there is no actual AE ability name being declared/assigned in the InitAbilities() section leaving that ability "UltraMarineCommander.nuke_id" in DoAbilities() orphaned, thus, generating the warning message(s).

To fix this we must assign "UltraMarineCommander.nuke_id" to a EBPS unit's proper AE ability name as follows:

function UltraMarineCommanderTactic:InitAbilities()

    if (UltraMarineCommander.nuke_id == nil) then
        UltraMarineCommander.nuke_id = cpu_manager.stats:GetAbilityID( "ultra_marine_nuke" )
    end
end

function UltraMarineCommanderTactic:DoAbilities()

    Ability.DoAbility( self.squad_ai, UltraMarineCommander.nuke_id, Ability.Filters.IsInCombat )
end

Now it is properly assigned, however, be careful that "ultra_marine_nuke" is actually the real AE ability name assigned to this EBPS unit assigned this tactic .ai file otherwise the game will Crash to Desktop (CTD). More on this below.

Note: The "Player 1001" basically means the error is being reported for Player1 (Player0 tends to be Slot 0 where a human player traditionally starts in a 1vs1 skirmish games).
 

 

Hint #5:

*ALERT: expected class to derive from or a newline
  Lua             Races/ultra_marine_race/Loader.ai Ln   32 (LoadRace)
  Lua             Races/RaceLoader.ai            Ln   94 (?)
  Lua             Core/cpu_manager.ai            Ln  405 (Initialize)
  Lua             DATA:AI/default.ai             Ln  115 (InitializeAI)
  main            DATA:AI/default.ai             Ln  133 ((null))
Error loading script file 'DATA:AI/default.ai' for race 'ultra_marine_race'!

Solution: Check your Loader.ai file (example above is "Races/ultra_marine_race/Loader.ai Ln   32") and see what line is loading which .ai file. It is likely a bad .ai with incorrect declared values like a Tactic file with invalid syntax which is incorrect for your project.

An example that can cause this is from a loaded Tactic .ai:

 

This is incorrect:

class 'UltraMarineCommanderTactic' (UltraMarinInfantryTactic)

while this is correct:

class 'UltraMarineCommanderTactic' (UltraMarineInfantryTactic)

Note that the corrected name is derived from the loaded ultramarineinfantrytactic.ai (which uses "UltraMarineInfantryTactic" internally) so your project should use something unique and propagated to your other Infantry-based tactic files.
 

 

Misc / Generic AI Errors

 

Below are some odd and end AI warnings/errors to watch for.

 

Hint #1:

*ALERT: [string "Races/ultra_marine_race/Strategies/UltraMarineBuildBaseSt..."]:400: `end' expected (to close `function' at line 227) near `<eof>'
  Lua             Races/ultra_marine_race/Loader.ai Ln   23 (LoadRace)
  Lua             Races/RaceLoader.ai            Ln   94 (?)
  Lua             Core/cpu_manager.ai            Ln  405 (Initialize)
  Lua             DATA:AI/default.ai             Ln  115 (InitializeAI)
  main            DATA:AI/default.ai             Ln  133 ((null))
Error loading script file 'DATA:AI/default.ai' for race 'ultra_marine_race'!

Solution: Locate this .ai file (example above is the .ai file mentioned in your loader.ai at this part "Races/ultra_marine_race/Loader.ai Ln   36") and correct the missing "end" required to close the function.


Hint #2:

RaceLoader: Create build base strategy of race AI ultra_marine_race...
*ALERT: [string "Races/ultra_marine_race/Loader.ai"]:53: attempt to call global `MarineBuildBaseStrategy' (a nil value)
*ALERT: [string "Races/ultra_marine_race/Strategies/Ultra..."]:247: attempt to index global `tBuildType' (a nil value)
Error loading script file 'DATA:AI/default.ai' for race 'ultra_marine_race'!

Solution: Not properly declared functions or values. Need to ensure they are valid and have a link to script logic. As example for Ultramarines.. "MarineBuildBaseStrategy" should have been "UltraMarineBuildBaseStrategy" as "MarineBuildBaseStrategy" is not valid for the Ultramarines project since "UltraMarineBuildBaseStrategy" is already declared in both the project's loader.ai and the its UltraMarineBuildBaseStrategy.ai file.

For the missing link to `tBuildType' that is due because the call was not first declared so it would need this before any kind of tBuildType is asked for.

                local tBuildType = CpuBuildType()

It can then be associated with an Addon or Research, etc..
 

 

Added: March 18, 2023

Hint #3:

*ALERT: AIStats:LoadUnitStats() threw exception (not a table inside stats table)
Lua Core/cpu_manager.ai Ln 413 (Initialize)
Lua DATA:AI/default.ai Ln 115 (InitializeAI)
main DATA:AI/default.ai Ln 133 ((null))

Solution: Check your entire AI path that it is valid. The above error will occur if your faction's AI is not in the correct folder path. ie.

This is incorrect:

Data\ai\ultra_marine_race\

This is correct:

Data\ai\races\ultra_marine_race\

So ensure your full AI path in the project is in the correct standard that is expected.

 

 

Cause of "most" AI (Crash to Desktop) CTDs

These are more elusive and frustrating as if a severe AI issue is found the game will crash to desktop without warning.

There is a method to firmly determine if its a BuildStrategy or Tactic causing the mysterious CTD but that is covered in the AI dox in the attachment below.

In this case, let's cover some basic Dawn of War CTDs and perhaps where to look to fix them.
 

 

Hint #1: Invalid or misspelled names of key declarations like those in Unitstats.ai. As example in the ultramarines Unitstats.ai:

UltraMarineUnitStats =
{
    race = "ultra_marine_race",

If any of the above have a spelling mistake will cause a CTD.

 

Hint #2: Giving a unit an ability in its own tactic file that it does not have OR the ability itself is misspelled in the unit's tactic file.

As example:

If in your unit's EBPS in the ability section:

GameData["ability_ext"]["abilities"]["ability_01"] = "abilities\\ultra_marine_rally.lua"

But then in this unit's loaded Tactic .ai file you have this:

function UltraMarineCommanderTactic:InitAbilities()

    if (UltraMarineCommander.rally_id == nil) then
        UltraMarineCommander.rally_id = cpu_manager.stats:GetAbilityID( "ultra_marine_rall" )
    end
end

When this unit shows up on the map for the first time the entire game will CTD.

The correct syntax is:

function UltraMarineCommanderTactic:InitAbilities()

    if (UltraMarineCommander.rally_id == nil) then
        UltraMarineCommander.rally_id = cpu_manager.stats:GetAbilityID( "ultra_marine_rally" )
    end
end

So it is critical to ensure all your declared and valid abilities for an EBPS unit have a tactic associated.

 

 

Hint #3: Any invalid abilities placed in your project's generic Infantry Tactic .ai file under this section.. once more, using Ultramarines as an example:

function UltraMarineInfantryTactic:AddTargetAbilities()
    table.insert(InfantryTactic.TargetAbilities, { nil, "ultra_marine_cool_bombs", Ability.Filters.CloseInfantryEnemy, 1, 0 })
end

If the mod project OR any loaded mod project (including vanilla factions) do not have this ability anywhere the game will immediate CTD when the first Infantry unit is created on the battlefield for your project.

It is important to ensure all ability names are valid as well as their context of use / proper function is coded correctly so the AI can use their abilities to the best of their potential.
 

 

Hint #4: Any hard-coded Build Order items in your project's BuildBaseStrategyInfo .ai file within the "BuildPrograms" section must be 100% accurate.

If a single one of these is misspelled or not present and then called in the loaded Tier (below showing only Tier1 items) then the game will immediately CTD.

Using Ultramarines as an example these are all valid units:

                { 1, 220, 50, 0, 1,    "Unit",     "ultra_marine_squad_commander" },
                { 1, 100, 0, 0, 1,     "Unit",     "ultra_marine_squad_scout" }, -- Force a capturing squad
                { 1, 190, 0, 0, 1,     "Unit",     "ultra_marine_squad_marine" },
                { 1, 400, 0, 0, 1,     "Building", "ultra_marine_hq" },
                { 1, 150, 0, 700, 1,   "Research", "ultra_marine_squad_cap_research" },
                { 1, 250, 150, 900, 1, "Research", "ultra_marine_tier2_research" },

However if in, say, Tier2 there is a bad item like the following research when the AI reaches Tier2 it will immediately crash as the AI scans all forthcoming items in the current Tier first but cannot compensate here if even one is invalid, thus, will crash.

                { 2, 150, 0, 650, 1,   "Research", "ultra_marine_i_am_cool_research" },

So its absolutely paramount to ensure all items under "BuildPrograms" are accurate.
 

 

Hint #5: Under your project's BuildBaseStrategy .ai there are various obstacles to avoid crashing. The main ones are sections which call Buildings and their Addons directly. We will use the Ultramarines project as an example.

 

At the top of your project's BuildBaseStrategy .ai file it is critical to ensure all Detector Units (used to spot enemy Infiltrated units) are valid. Make sure all SBPS units in your project are the correct name AND can actually find infiltrators.

function UltraMarineBuildBaseStrategy:__init( baseinfo ) super( baseinfo )
    self:AddDetectorUnit("ultra_marine_squad_very_cool_unit")

This can especially be tested against a vanilla Tau enemy as they have early Tier1 infantry which are shrouded.

 

So be aware the above must be a valid SBPS unit in your project and should be able to detect enemy infiltrators.

 

Next, this is declaring all valid Buildings for your project:

function UltraMarineBuildBaseStrategy:GetBuildingName( sType )

Here, the most critical buildings that are mandatory by the AI to be declared are the HQ, Generators, Large Generator, Listening Post, and Vehicle Buildings. Both Mines and Turrets are optional and can generally be omitted if your project does not use them.
 
There are some projects which have no Generators, Large Generators or Vehicle Buildings so there are methods to "trick the AI" not to build such placeholder structures while the player sees nothing themselves in the game's UI so it appears clean.

This one declares all valid building Addons within your project:

function UltraMarineBuildBaseStrategy:GetAddonBuilding( sType )

Every building that has an addon must be declared here especially if the addon is called for anywhere directly by your project's AI in a build order sequence or dynamically.

Do not use an addon name or associate it with a valid building unless they are both valid to one another otherwise the game will immediately crash.

Another section is where dynamic builds can be undertaken:

function UltraMarineBuildBaseStrategy:BuildFlexible()

If you are ever using squad quantities used as a prereq to build a research or addon, etc then make sure all squad names are valid. A single invalid one will crash the game.

 

Once more, an example from the ultramarine's project:

Note the invalid squad name declared in the array:

function UltraMarineBuildBaseStrategy:BuildFlexible()

    -- Dynamic research item syntax: ResearchName, MinTier, RequisitionCost, PowerCost, MinSquadCap, MinSupportCap, SquadName, SquadMinCount
    local iBasicInfantrySquads = self:CountSquads("ultra_marine_squad_scout") + self:CountSquads("ultra_marine_squad_marine") + self:CountSquads("ultra_marine_squad_dumb_doofus")

    -- Compute tier 1 researches
    if (self.tierLevel >= 1) then

        if (iBasicInfantrySquads >= 1) then
            self:DynamicResearch("ultra_marine_tier2_research", 1, 250, 150, 0, 0, nil, 0)
        end
    end

That one invalid squad name will crash the game in Tier1 so ensure all declared squad SBPS names are valid.

The same goes for all other buildable items like Researches, Addons, and Buildings. If any of those are also invalid you will likely crash the game in the Tier they are called. Examples of invalid dynamic calls:

        self:DynamicResearch("ultra_marine_pathetic_research", 1, 150, 100, 0, 0, nil, 0)
        self:DynamicAddon("ultra_marine_silly_addon_1", 100, 1, 100, 100, 0, 0, nil, nil, false)
        self:DynamicBuild("ultra_marine_dumb_hq", 2, 1, 100, 100, 0, 0)

Note: you will not crash the game if such items are actually loaded in the project in their respective AE folders but if they are simply never buildable or unobtainable then you likely get the error mentioned before:

Cannot get prerequisites: Trying to build an invalid research: ultra_marine_cool_support_research
Cannot get prerequisites: Trying to build an invalid addon: ultra_marine_captain_upgrade

The above research and addon are actually part of the project but cannot ever be built since they are unavailable for anything to build them since they are not active.

If you feel such items should be buildable an exception might be to add these to a bypass like these examples in your BuildBaseStrategy .ai in this function:

function UltraMarineBuildBaseStrategy:__init( baseinfo ) super( baseinfo )

    -- dark40k - set items that need bypass for CpuPrerequisites
    CpuPrerequisites2.AddSpecialItem("ultra_marine_cool_support_research", CpuPrerequisites.BT_Research)
    CpuPrerequisites2.AddSpecialItem("ultra_marine_captain_upgrade", CpuPrerequisites.BT_Addon)

Other items like _Squad and _Building are also covered for exceptions. That is, however, a seperate topic and should be covered in the AI dox attached.
 

 

Other Common AI issues

 

Here are lesser problematic common AI issues.

 

In this section, there are two logs you will need to consult: warnings.txt found in both [root Soulstorm folder] and [root Soulstorm folder]\logfiles\[last game run instance] and ailog.txt in [root Soulstorm folder]\logfiles\[last game run instance].

 

Hint #1:

info is null:false bad ability name: all_run!
info is null:false bad ability name: all_autorepair
info is null:false bad ability name: all_bumpertank

Solution: False-Positive STEAM-only AI warning. This does not impact the AI itself. These warnings never show up for the older/legacy CD/DVD versions.


thudo

Posted 01 July 2019 - 12:29 AM

ICONS - Updated: July 02, 2019.

 

Recommended File Paths

 

For all enabled/active icons:

 

[Mod Name]\Data\Art\ui\ingame\[mod name_icons]

 

For disabled/inactive icons:

 

[Mod Name]\Data\Art\ui\ingame_disabled\[mod name_icons]

 

Bonus #1: when adding an Advanced Build Menu for your builders to build extra buildings beyond the hard-coded 11 slots this icon path should exist with a suitable icon so long as such an option is enabled in AE:

 

For all enabled/active command icons:

 

[Mod Name]\Data\Art\ui\ingame\command_icons

 

For disabled/inactive command icons:

 

[Mod Name]\Data\Art\ui\ingame_disabled\command_icons

 

The icon filename should be named: "build_structure_advanced2" and generally looks as follows:

 

W3egv85.jpg

 

Bonus #2: When adding SCAR game modes like HEROES, AI Donations, and other SCAR-based logic use this section for those icons:

 

[Mod Name]\Data\Art\ui\ingame\event_cue_icons\custom

 

Such icons can look as follows:

 

a1RM7F5.jpg   18YcYMN.jpg   EW1GSbm.jpg

 

 

Icon File Format and Dimensions

 

Dawn of War primarily uses for its icons the TGA or Truevision TARGA (Type 2) format so all icons should be saved in this format.

 

As for Dimensions, 64x64 is traditionally used with a Bit Depth of 32.

 

 

Filename Sorting and Naming Convention

 

This will help keep the icons for your project neat and organized so they can be found quickly.

 

Sort your icons based on their function as follows:

 

ability_XXXX_icon

addon_XXXX_icon

building_XXXX_icon

commander_XXXX_icon

hero_XXXX_icon

infantry_XXXX_icon

infantry_builder_XXXX_icon

infantry_command_squad_XXXX_icon

infantry_sergeant_XXXX_icon

research_XXXX_icon

upgrade_XXXX_icon  <-- meant for weapon upgrades

vehicle_XXXX_icon

 

Note that the last part of the filename "_icon" is used just to ensure its identified correctly as such especially if you need to search for them.

 

 

How Icon Upgrades Work

 

When one of your unit upgrades a hardpoint you'll notice that when this happens in the game UI menu the unit's main image turns PINK. This is due to the required icon filenames missing.

 

Firstly, ensure you have these icons present (using an Infantry entity as example):

 

infantry_XXXX_icon

infantry_XXXX_icon__multi

infantry_XXXX_icon__[weapon name in the entity's combat_ext EBPS]

infantry_XXXX_icon__[another weapon name in the entity's combat_ext EBPS]

 

For the third and forth icons above, the weapon name added to the file comes from the unit's EBPS file found in the combat_ext section only for weapons that are not in the first Hardpoint section.

 

This should only be added if needed: there is no need to always add such icons except for visible weapon icon upgrades OR if after the unit upgrades the unit's main image turns PINK.

 

As an example.. here is the Devastator squad from the Ultramarines project using RGDedit (raw AE code format):

Spoiler
Notice the second weapon "ultra_marine_heavy_bolter_tactical".. that would mean the icon would be called "infantry_devastator_icon__ultra_marine_heavy_bolter_tactical".

 

So if this icon exists in the enabled icon folder then when the Devastator Squad upgrades to that hardpoint, the unit's main image in-game will not turn PINK and will use the icon graphic represented in "infantry_devastator_icon__ultra_marine_heavy_bolter_tactical".

 

Hint #1: If in your Unit's EBPS combat_ext section you have complex upgrades set this way:

GameData["combat_ext"]["complex_upgrades"] = true

..then there is no requirement for any __multi or unit's own __weapon_name squad icons as by having complex upgrades set to True negates such icon options.

 

Hint #2: There is no need to make DISABLED versions of both __multi or __weapon_name squad icons as the game only handles the unit's main image icon which must have its own ENABLED and DISABLED variants.

 

 

How On and Off Icons Work for Toggle Abilities

 

Within your ability's icon_name section at the bottom of its AE code ability the name should be as follows:

 

ability_XXXX_icon

 

So the raw code would look like:

 

GameData["ui_info"]["icon_name"] = "ultra_marine_icons/ability_xxxx_icon"

 

However, in your actual icon section you should have two icon files:

 

ability_XXXX_icon_off

ability_XXXX_icon_on

 

Each of the above should be graphically edited to signify what the ability would look like ENABLED and DISABLED.

 

Bonus: if this toggle is impacted by a No Ability Aura that can impact the unit then you also need to add both of the above in your:

 

[Mod Name]\Data\Art\ui\ingame_disabled\[mod name_icons] folder

 

If this is the case, both "ability_XXXX_icon_off" and "ability_XXXX_icon_on" will need to coloured in a way so they both look as if they are coloured/tinted like the rest of the disabled icons.

 

If the above is not done, when a No Ability Aura/Modifier is applied, the ability icon will become PINK.

 

 

Ability Template PSD (for use in Photoshop)

 

Attached below is a PSD file which can be used in Photoshop to create a basic ability icon.

 

This should include most border colours, action/event avatars, and some assorted backgrounds to use.


thudo

Posted 01 July 2019 - 12:29 AM

SOUND and SPEECH - Updated: April 15, 2021.

 

This section deals with most of the DoW1 speech workflow process in which one can adhere to the "best practices" expected so your speech integration goes as smooth as possible.

 

 

Spottings Folder Standards

 

These are all the major 30/40K faction spotting folders which should be in your:

 

[Mod Name]\Data\sound\speech\races\[mod name]\shared\spotting

 

Spoiler

 

Each folder should have its own associated .con file found in this main spotting folder.

 

This is a blank 0Kb file like "alpha_legion.con" you can make yourself using, say, Notepad which tells the game to point to the folder name in question as a valid target.

 

Update

(Sept 25, 2020) - Added Soul Drinkers to Spotting Naming Standards list below.

(April 15, 2021) - Added Angry Marines to Spotting Naming Standards list below.

 

Per Faction Spotting Naming Standards

 

In each of the above folders, if you have written then voiced all the factions then the file naming conventions to be used should be as follows:

 

Spoiler

 

Note: some overlap may occur and some spotting voices can be re-used/re-purposed for like-wise factions if your project does not have all the unique voices.

 

ie.. since there are two Eldar-based factions where one is the default vanilla race and the other is the Eldar Craftworld faction mod we can use the "Spotting_Eldar" for both since they are obviously related.

 

 

Speech Workflow Template for individual Units and Faction Spotting

 

Attached is a ZIP file which contains the main speech paths and workflow for adding your speech files to your faction mod.

 

It contains everything you need to directly add the paths to your [Mod Name]\Data\ path.

 

Firstly, it adds the "eventspeech.lua" file meant for [Mod Name]\Data\soundscripts\speechlogic which controls which spotting folders are used when a specific enemy faction is spotted for the first time. This file will change over time as we find new factions to add or corrects mistakes.

 

Secondly, it adds a sample faction speech path so you can quickly build your logical paths for each individual units (based on the four unit types: Builder, Commander, Infantry, and Vehicle) and your faction's main battlefield spotting folders. It is set up in a way to be fairly clear and ready to be used while maintaining our standards.

 

There is CMD batch file contained in each main root folder so when you copy your final FDA files relevant for each path there you can merely run the CMD and it will move/copy all files to where they need to go.

 

Update (Jul 14, 2019) - zip file is now at 1.1 as I added some needed _rat files in the various paths within \sound to ensure any custom work is played correctly.

 

 

WAV to FDA then back to WAV Speech Conversion Tool

 

Also provided below is a very helpful batch tool that, depending what file type you copy your files into, the CMD will properly convert them either from WAV->FDA or FDA-> WAV. When converting from WAV->FDA then you are ready to move those FDAs to the mod's speech paths as mentioned in the previous section so they can quickly be placed in their correct folders.

 

 

Understanding the Per Unit Speech Workflow

 

Generally, as mentioned above, there are four main unit types (Builder, Commander, Infantry, and Vehicle) and while most speech events like Unit_Complete, Selection, Move, Attack, and Death are universal across all unit types, some deviate by incorporating building options or the ability to Join or Detach from squads. For the sake of covering all bases, the Vehicle template has Jump (for units like Landspeeders which can jump around the battlefield) and Load/Unload (for units like Dreadnoughts which can garrison into building to then deepstrike). Regardless, use or omit as you wish but note what you need based on your project's design.

 

Notice however the Ability\ folder has two generic ability paths: Targeted and Protective. Use these folders as a template to add your own custom ability speech paths. As a rule, Targeted is more for direct-attack abilities while Protective is generally for healing auras. Nevertheless, use both these folders as a template.

 

Part of this Speech Workflow Template package is already built into the three speech events which you want muted/localized so they do not constantly get played: this is Charge, Combat, and Death. These three should not be played anywhere across the battlefield UNLESS the player's view is in the general area otherwise it becomes too overwhelming and would drown out other voices/sounds/music.

 

 

Troubleshooting Sound/Speech Issues

 

Here is a small most common broken sound/speech issues.

 

Note: Please ensure you are first running the game in -DEV mode as per instructions in the first message of this thread.

 

In this section, the log you will need to consult is soundmessages.txt found in [root Soulstorm folder]\logfiles\[last game run instance] or warnings.log (found in both [root Soulstorm folder] and [root Soulstorm folder]\logfiles\[last game run instance]).

 

Hint #1: Note this example warning in the soundmessages.txt:

No samples for patch, Data:Sound\speech\races\lotd\marine_tactical\charge
Using default patch for speech\races\lotd\marine_tactical\charge

Solution: While the Sound/Speech path may exist in your project the FDA or .RAT or .CON is missing - you should ensure these are both present and valid.

 

Hint #2: Note this example warning in the soundmessages.txt:

Failed to preload patch 'races\witch_hunters\valkyrie\valkyrie_drop_off'
    sound_valkyrie_landing
    art/ebps/races/witch_hunters/troops/valkyrie
Using default patch for races\witch_hunters\valkyrie\valkyrie_drop_off

Solution: Replace the missing speech path which is not present with the appropriate content..

 

Hint #3: Note this example warning in the soundmessages.txt:

FDA CODEC -- 'DATA:Sound\Speech\Races\Chaos_Marines\Possessed_Alternative\strategic_point_capture\401006.fda': 'Not a valid chunky file!'

Solution: This FDA is corrupt or damaged and will need to be re-evaluated to see why it does not play correctly in-game. Please convert it back from FDA->WAV (using the attached Speech Conversion Tool below) and check it to ensure it is a valid music file. Use other working FDAs as a template.

 

 

Hint #4: Note this example warning in the warnings.log:

SOUND -- failed to load playlist 'Data:SoundPlaylistMusic.lua'

Solution: There is missing syntax in this .LUA file (its a text file and can be edited in Notepad) located in your [Mod Name]\Data folder which usually means a missing " or , somewhere.


thudo

Posted 01 July 2019 - 12:21 AM

ART - Updated: July 15, 2019.
 
This section will consist of various common and less common art issues found.
 
Note: Please ensure you are first running the game in -DEV mode as per instructions in the first message of this thread.
 
In this section, the log you will need to consult is both warnings.log (found in both [root Soulstorm folder] and [root Soulstorm folder]\logfiles\[last game run instance]) and artmessages.txt found only in [root Soulstorm folder]\logfiles\[last game run instance].
 
 
Troubleshooting Art Issues (related to Models/Events/FX)
 
Below are sample dump warnings to help you identify key art problems in the project you likely are not aware of.
 
Hint #1: Note this example warning found in either warnings.log or artmessages.txt:

RENDER ANIM -- 'art/ebps/races/ultra_marine/texture_share/chapter_master_wargear': Not a valid chunk header!

Solution: Broken .RSH texture file associated with a loaded whm file. Replace this damaged .RSH with a valid one in the correct texture_share path.

 

 
Hint #2a: Note this example warning found in either warnings.log or artmessages.txt:

RENDER ANIM -- 'art/ebps/races/ultra_marine/texture_share/ig_heavy_flamer_chimera': Unable to open file!

Solution: Missing .RSH texture file associated with a loaded whm file. Locate the missing .RSH and copy it back into the required texture_share path.

 

 

Hint #2b: Note this example warning found in either warnings.log or artmessages.txt:

RENDER ANIM -- art/ebps/races/ultra_marine/troops/am_myrmidae_engine: Unable to open file!

Solution: Missing .WHE/WHM model files being called within one of your AE .RGD EBPS files. Locate the missing .WHE/WHM model files and copy them back into the required /troops path.

 

 

Hint #3: Note this example warning found in either warnings.log or artmessages.txt:

RENDER ANIM -- 'art/ebps/races/space_marines/texture_share/rhino_codex_weaponsûv·mw': Unable to open file!

Solution: This is a unique path issue where within the .WHM file there is a corrupt call to a.RSH texture file. You should either have your designated 3D/OE art dev fix this path in the affected .WHM or use Dark40K's FFE Tool and manually locate this broken path in the .WHM and correct it yourself if possible (make sure to back up the .WHM first before attempting any changes to a file being edited by the FFE Tool).
 
 
Hint #4: Note this example warnings found in only artmessages.txt:

FX -- Texture 'DATA:ART/FX/0' is missing, using default!
FX -- Texture 'DATA:ART/FX/' is missing, using default!

Solution: In your project, look for a data\art\fx\space_marines and delete the folder and its contents \upgrade_fx within that folder -- these are not needed.
 
 
Hint #5: Note this example warning found in only artmessages.txt:

FX -- Texture 'DATA:ART/FX/INQUISITION_DAEMONHUNT/TEXTURES/LIGHT_GLOW_BLUE' is missing, using default!

Solution: Missing .DDS or .TGA/.JPG/.BMP graphic file in the path requested above.
 
 
Hint #6: Note this example warning found in only artmessages.txt:

FX -- type (inquisition_daemonhunt\units\grey_knights\blue_light) not found. Replacing it with default FX (badfx).
    blue_halo_psycanon_l
    art/ebps/races/mymod/troops/my_new_3d_model

Solution: Missing .LUA FX file missing in the path being called from either .WHE/.WHM model files. Please locate and copy the missing .LUA FX file (in the above example case the file is called "blue_light.lua"). You can then edit the .LUA FX file in Notepad (it is a text file) and search the LUA for any related .DDS or .TGA/.GIF/.JPG/.BMP graphic files) and ensure those are added in your project based on the path mentioned in the FX .LUA. Typically, most missing graphic files in .LUA FX files are either .DDS or .TGA and those called are likely used by the vanilla game anyway however its best to check if such files are really needed by re-running the game and looking for any messages like those mentioned in Hint#5.
 
 
Hint #7: Note this example warnings found in only artmessages.txt:

EVENTS -- 'Weapon Damage': Unable to load event 'art/events/guard/abilities/fanaticism'!
EVENTS -- 'Combat Weapon': Unable to load event 'art/events/missile pods'!
EVENTS -- 'Event Manager': Unable to load event 'art/events/structure_fx/relocation'!
EVENTS -- 'Deep Strike': Unable to load event 'art/events/1'!

Solution: Missing .EVENTS file in your project. Please locate and copy the missing .EVENTS file then open the copied .events file in Notepad (for read-only viewing) and notice any sound files or FX luas (which themselves are associated with related .DDS or .TGA/.GIF/.JPG/.BMP graphic files) and ensure those are added in your project's paths.
 
 
Hint #8: Note this example warning found in either warnings.log or artmessages.txt:

'ranger': XRef'ed Anim 'vis_no_flag' in model 'art/ebps/races/mymod/troops/my_new_3d_model' is missing!

Solution: A .WHE/.WHM (example used is "my_new_3d_model") is being called by one of your models. Essentially, this error is generated because one of your models is calling xref animations from another .WHE/.WHM file as a reference so your model can properly move/preform in game. Please locate this missing .WHE/.WHM and then re-test your impacted model in-game to ensure it is using the correct reference model.
 
 
Hint #9: Note this example warning found in only the warnings.log:

Error: D3DERR_INVALIDCALL
   Desc: Invalid call
    Code: 2156, Facility: 2166, Severity: 1
   Call: [m_pStdTexture->LockRect( mip_level, &lockRect, &rect, flags )]

Solution: .RSH texture file needs to be re-saved back properly as its dimensions or bit depth are wrong. Use other known-working .DDS/.TGA graphic files used by yours or another project as an example to fix this broken .RSH texture file in your project.
 
 
Hint #10: Note this example warnings found in only artmessages.txt:

'art/ebps/races/mechanicus/troops/am_knight': Missing game action 'jump_setup'!
'art/ebps/races/mechanicus/troops/am_knight': Missing game action 'jump_goup'!
'art/ebps/races/mechanicus/troops/am_knight': Missing game action 'jump_flying'!
'art/ebps/races/mechanicus/troops/am_knight': Missing game action 'jump_godown'!
'art/ebps/races/mechanicus/troops/am_knight': Missing game action 'jump_breakdown'!

Solution: The "am_knight" .WHE file is missing the motions/actions/animations associated with jumping or teleporting and the model will look broken in-game when these actions are done. These require a 3D/OE dev to correct.

 

 

Hint #11: Note this example warning found in only warnings.log:

SKINBATCHING -- Maximum unit shader IB size exceeded. Current size: 20970, requested addition: 5178, max size: 24576. Please reduce the poly count.
Lock of skin batcher failed. This is a sad day for skin batchers everywhere.

Solution: This is due to one or more of your project's loaded models having larger-than-normal-sized textures assigned to it that exceed what the game expects. While this does require a 3D/OE dev to correct it only happens to some users and should not otherwise impact your gaming experience since it has no ill effects on performance and is more for informational purposes.

 

 

Hint #12: Note this example warning found in only warnings.log:

Texture format [1] is not renderable on this system.
Could not create a texture of type 1, w: 256, h: 256, mipmap: 0, dynamic: 1, renderable: 1.
SMAP -- Creation of 256x128 render target failed, trying 307894464x16912412.

or

SVOL -- Shadow volumes can only be used when there is a stencil buffer (and in 32bit mode).

Solution: Graphic settings in your Local.ini are generating this error due to incompatible values. Visual art in the game may not look as optimal so be very cautious for artifacts appearing on models.


thudo

Posted 01 July 2019 - 12:20 AM

UCS - Updated: October 25, 2019.
 
This section corresponds to the [Mod Name]\Locale file path which gives the player all the info required to use and navigate your mod project. The main language supported is English but once your .ucs is complete it can be moved to the other language folders.
 
The UCS file is a text file and can be edited in Notepad.
 
 
Reserve your UCS # Range
 
Right now we store all UCS ranges for all major DoW1 faction mods HERE so pick a range that is not in conflict with any of those or vanilla #s.
 
Hint: Best practice here when choosing the size of your range is to always give yourself at least ~3000 lines as its always the best policy to give yourself more than you need OR at least ensure there are more lines available after your range ends without conflicting.
 
 
Organize the Sections
 
In your .ucs file organize it based on the following sections and the range of lines you should consider allocating.
 
Note: the values provided below are only meant as a guide so make sure to first secure your range and use those #s below only as a general rang to work with,

00000 - 00008  Name and Description of the Mod Project
00009 - 00198  Buildings
00199 - 00398  Addons
00399 - 00498  Builders
00499 - 00698  Squads
00699 - 00898  Squads Sergeants
00899 - 01098  Commanders
01099 - 01398  Vehicles
01399 - 01898  Researches
01899 - 02298  Weapons
02299 - 02898  Abilities
02899 - 02999  Miscellaneous Section (for odds and ends)

Hint: The above range spans between the different sections is only a suggestion so it should always depend on how large your project could potentially become. The best advice is to always give more then you need between the sections. All projects have the possibly to grow so always keep that in mind since its more difficult to make additional space (apart from just adding more range lines at the end).
 
Here is a quick example taken from the Ultramarines project's main ucs file as to how the initial starting part of its ucs look like:

15300000    Ultramarines
15300001    Makes the Ultramarines Space Marine chapter available as a playable race.
15300002    
15300003    
15300004    
15300005    
15300006    
15300007    
15300008    
15300009    -- Buildings
15300010    Bastion of Ultramarines

As you can see, sections usually start with a "-- [Description on Section]" to denote the forthcoming area just as a method to keep things neat and organized.
 
 
General Best UCS Format Practices
 
Hint #1: Try not to exceed 110-120 lines starting from the first word to the right of the range #s. If you go over a certain limit, depending on the resolution played, the text in-game will carry over to the next line so it could look cluttered.
 
As example.. this is far too long and will prematurely return to the next line:

15300904    - Can be upgraded with far more powerful ranged and close combat weapons only available from the One and Only Best Armoury Ever to exist this side of Ultramar!

While this is about right:

15300904    - Can be upgraded with more much more powerful ranged and close combat weapons from the Armoury.

Hint #2: Recommend starting on the "0" line for each new item and be as verbose as you can while NOT exceeding 9 rows if at all possible. This will help prevent accidentally overlapping into the next item.
 
An example for a Commander Unit:

15300900    [Name of Unit]
15300901    - Heavy Infantry.
15300902    - Healer unit.
15300903    - Enhances regeneration rates of nearby infantry.
15300904    - Has the ability to teleport short distances after the Personal Teleporters research is built.
15300905    - Mounts a Shoulder Missile System to quickly dispatch heavily armoured foes at great range.
15300906    - Can be upgraded with more powerful ranged and close combat weapons from the Armoury.
15300907    - Effective against Infantry, Heavy Infantry, Daemons, Commanders, Aircraft or Vehicles.  
15300908    - Limit of 1.

Note the context of the rows which should provide enough information to the player so there are no unanswered questions about this item.
 
Mind you, "Limit of 1" should be reserved for Commanders or highly specialized units and not for standard squads.
 
Bonus: Here is what the above looks like in the RGD file of the EBPS entity:

GameData["ui_ext"]["ui_info"]["help_text_list"]["text_01"] = "$15300901"
GameData["ui_ext"]["ui_info"]["help_text_list"]["text_02"] = "$15300902"
GameData["ui_ext"]["ui_info"]["help_text_list"]["text_03"] = "$15300903"
GameData["ui_ext"]["ui_info"]["help_text_list"]["text_04"] = "$15300904"
GameData["ui_ext"]["ui_info"]["help_text_list"]["text_05"] = "$15300905"
GameData["ui_ext"]["ui_info"]["help_text_list"]["text_06"] = "$15300906"
GameData["ui_ext"]["ui_info"]["help_text_list"]["text_07"] = "$15300907"
GameData["ui_ext"]["ui_info"]["help_text_list"]["text_08"] = "$15300908"
GameData["ui_ext"]["ui_info"]["screen_name_id"] = "$15300900"

And in the RDG file of the SBPS entity:

GameData["squad_ui_ext"]["ui_info"]["help_text_list"]["text_01"] = "$15300901"
GameData["squad_ui_ext"]["ui_info"]["help_text_list"]["text_02"] = "$15300902"
GameData["squad_ui_ext"]["ui_info"]["help_text_list"]["text_03"] = "$15300903"
GameData["squad_ui_ext"]["ui_info"]["help_text_list"]["text_04"] = "$15300904"
GameData["squad_ui_ext"]["ui_info"]["help_text_list"]["text_05"] = "$15300905"
GameData["squad_ui_ext"]["ui_info"]["help_text_list"]["text_06"] = "$15300906"
GameData["squad_ui_ext"]["ui_info"]["help_text_list"]["text_07"] = "$15300907"
GameData["squad_ui_ext"]["ui_info"]["help_text_list"]["text_08"] = "$15300908"
GameData["squad_ui_ext"]["ui_info"]["screen_name_id"] = "$15300900"

The two views above are based from using RGDEdit.

 

Hint #3: For Abilities that require instructional info for targeting take note of the following where we leave the 8th spot blank by defaulting the value to "$0" so while in the UCS it looks as such (using the Ultramarines project as example once more):

15302020    Frag Grenades
15302021    - Throws a grenade at the targeted location or enemy.
15302022    - Left-click and target a location or enemy squad to activate.
15302023    - Damages enemy Infantry and stuns them temporarily.
15302024    - Has no effect on Vehicles or Buildings.
15302025    
15302026    
15302027    
15302028    Left-click on enemy infantry to throw a Frag Grenade at them.
15302029    This ability can only be targeted directly on enemy infantry units!

In the Ability's EBPS entity note the "text_08" is left blank ("$0" is basically considered a null value) and the UCS # instead in the sequence is used for the instructional info how to use the ability when the mouse is clicked to target:

GameData["ui_info"]["help_text_list"]["text_01"] = "$15302021"
GameData["ui_info"]["help_text_list"]["text_02"] = "$15302022"
GameData["ui_info"]["help_text_list"]["text_03"] = "$15302023"
GameData["ui_info"]["help_text_list"]["text_04"] = "$15302024"
GameData["ui_info"]["help_text_list"]["text_05"] = "$15302025"
GameData["ui_info"]["help_text_list"]["text_06"] = "$15302026"
GameData["ui_info"]["help_text_list"]["text_07"] = "$15302027"
GameData["ui_info"]["help_text_list"]["text_08"] = "$0"
GameData["ui_info"]["screen_name_id"] = "$15302020"
GameData["ui_instructional_msg"] = "$15302028"
GameData["ui_invalid_target_msg"] = "$15302029"

The final UCS value of "$15302029" is reserved if the player accidentally clicks on an area of the map or an invalid target which the ability does not correspond to.

 

Update (Oct 25, 2019) -

 

UCS Template File

Find attached below a quick UCS Maker which can auto-create a .ucs file based on the range you input.

 

Instructions for use:

 

1) Unzip to a temporary location

2) Edit the run.bat, inputting the desired UCS line range, and then...

3) Simply run the now edited run.bat and this will auto-create the .ucs you can then use in your mod's \Locale\[Language] folder.


thudo

Posted 01 July 2019 - 12:20 AM

AE - Updated: May 02, 2020.
 
This section will endeavour to reveal some "best practices" when it comes to the AE (Attrib Editor) which is fundamentally in binary format (.RGD) but can be exported to .LUA (which can then be edited in Notepad but ONLY for reviewing).
 
Below is attached the entire vanilla AE matrix which goes up to Soulstorm 1.20. Use it only as a reference to grab code ideas from OR to incorporate into your project (see the part below dealing with keep code exclusive to your project).
 
There is also attached RGDEdit 0.73 which is what I use to direct-edit RGDs so be careful how you make your changes directly per RGD. Always make backups if you have concerns.
 
Further, you can look into Corsix ModStudio for a more UI Menu-driven Attribute Editor. Download it HERE!
 
 
Firstly, ensure your Dawn of War: Soulstorm is free of AE (Attribute Editor) Errors
 
Find attached the zip file "SS1.2_AE_Design_Fixes-FINAL_Dec04.2010" and unzip into your [root Soulstorm folder]\DXP2\Data.
 
By doing this first before running your Dawn of War Soulstorm games you will remove any needless background AE issues that came with the vanilla game AND will allow you to troubleshoot your mod's AE bugs when the time comes and only bugs dealing with your project.
 
As mentioned from THIS thread, the goal here is to ensure you do not generate a "designmessages.txt" file when running your mod.
 
Here is a quick example list of common AE warnings that will show up in designmessages.txt which is located in [root Soulstorm folder]\logfiles\[last game run instance].
 

Updated: May 02, 2020 - Added more problematic modifiers as additional examples
Hint #1a: Bad modifiers being wrongly applied.

Modifier modifiers\morale_degeneration.lua can't use squad_target_type modifiers with an application type of type_modifierapplicationtype\tp_mod_apply_to_entity.lua, data:attrib\weapon\ultra_marine_daemon_fire.rgd
Modifier modifiers\enable_infiltration.lua can't use entity_target_type modifiers with an application type of type_modifierapplicationtype\tp_mod_apply_to_squad_type.lua, data:attrib\ebps\races\ultra_marine\troops\ultra_marine_callidus.rgd
Modifier modifiers\enable_squad_voice.lua can't use squad_target_type modifiers with an application type of type_modifierapplicationtype\tp_mod_apply_to_entity_type.lua, data:attrib\ebps\races\ultra_marine\troops\ultra_marine_falchion.rgd
Modifier modifiers\disable_abilities_ui.lua can't use squad_target_type modifiers with an application type of type_modifierapplicationtype\tp_mod_apply_to_structure_type.lua, data:attrib\ebps\races\ultra_marine\troops\ultra_marine_resource4.rgd
Modifier modifiers\max_damage_weapon_modifier.lua can't use weapon_target_type modifiers with an application type of type_modifierapplicationtype\tp_mod_apply_to_entity_type.lua, data:attrib\research\ultra_marine_oath_research.rgd
Modifier modifiers\min_damage_weapon_modifier.lua can't use weapon_target_type modifiers with an application type of type_modifierapplicationtype\tp_mod_apply_to_entity_type.lua, data:attrib\research\ultra_marine_oath_research.rgd
Modifier modifiers\accuracy_weapon_modifier.lua can't use weapon_target_type modifiers with an application type of type_modifierapplicationtype\tp_mod_apply_to_entity_type.lua, data:attrib\research\ultra_marine_targeter_research.rgd

Solution: Check the vanilla attrib provided and locate the proper use of modifiers targeting other modifiers incorrectly.
 
For example, using the first code modifier error, this is incorrect:

GameData["area_effect"]["weapon_damage"]["modifiers"]["modifier_03"] = Reference([[tables\time_modify_entry.lua]])
GameData["area_effect"]["weapon_damage"]["modifiers"]["modifier_03"]["max_lifetime"] = 8.000000
GameData["area_effect"]["weapon_damage"]["modifiers"]["modifier_03"]["modifier"] = Reference([[modifiers\morale_degeneration.lua]])
GameData["area_effect"]["weapon_damage"]["modifiers"]["modifier_03"]["modifier"]["application_type"] = Reference([[type_modifierapplicationtype\tp_mod_apply_to_entity.lua]])
GameData["area_effect"]["weapon_damage"]["modifiers"]["modifier_03"]["modifier"]["exclusive"] = false
GameData["area_effect"]["weapon_damage"]["modifiers"]["modifier_03"]["modifier"]["modifier_class_name"] = Reference([[type_modifier\tp_modifier.lua]])
GameData["area_effect"]["weapon_damage"]["modifiers"]["modifier_03"]["modifier"]["probability_of_applying"] = 1.000000
GameData["area_effect"]["weapon_damage"]["modifiers"]["modifier_03"]["modifier"]["shield_of_faith"] = false
GameData["area_effect"]["weapon_damage"]["modifiers"]["modifier_03"]["modifier"]["target_type_name"] = ""
GameData["area_effect"]["weapon_damage"]["modifiers"]["modifier_03"]["modifier"]["usage_type"] = Reference([[type_modifierusagetype\tp_mod_usage_addition.lua]])
GameData["area_effect"]["weapon_damage"]["modifiers"]["modifier_03"]["modifier"]["value"] = 1.000000

and this is correct:

GameData["area_effect"]["weapon_damage"]["modifiers"]["modifier_03"] = Reference([[tables\time_modify_entry.lua]])
GameData["area_effect"]["weapon_damage"]["modifiers"]["modifier_03"]["max_lifetime"] = 8.000000
GameData["area_effect"]["weapon_damage"]["modifiers"]["modifier_03"]["modifier"] = Reference([[modifiers\morale_degeneration.lua]])
GameData["area_effect"]["weapon_damage"]["modifiers"]["modifier_03"]["modifier"]["application_type"] = Reference([[type_modifierapplicationtype\tp_mod_apply_to_squad.lua]])
GameData["area_effect"]["weapon_damage"]["modifiers"]["modifier_03"]["modifier"]["exclusive"] = false
GameData["area_effect"]["weapon_damage"]["modifiers"]["modifier_03"]["modifier"]["modifier_class_name"] = Reference([[type_modifier\tp_modifier.lua]])
GameData["area_effect"]["weapon_damage"]["modifiers"]["modifier_03"]["modifier"]["probability_of_applying"] = 1.000000
GameData["area_effect"]["weapon_damage"]["modifiers"]["modifier_03"]["modifier"]["shield_of_faith"] = false
GameData["area_effect"]["weapon_damage"]["modifiers"]["modifier_03"]["modifier"]["target_type_name"] = ""
GameData["area_effect"]["weapon_damage"]["modifiers"]["modifier_03"]["modifier"]["usage_type"] = Reference([[type_modifierusagetype\tp_mod_usage_addition.lua]])
GameData["area_effect"]["weapon_damage"]["modifiers"]["modifier_03"]["modifier"]["value"] = 1.000000

Ensure the correct modifiers are used.
 
 
Hint #1b: Bad application to a modifier being wrongly applied but a suggestion is made by the game engine to correct:

cover modifier has an invalid application type, the application type must be 'apply_to_entity', data:attrib\ebps\races\catachan\troops\copia de catachan_leaders_melta_guardsman.rgd

Solution: Correct the modifier based on what it recommends as the applicator is not valid.
 
 
Hint #2: Duplicate filters detected.

Duplicate value for 'armour_type' 'tp_commander' in 'target_filter', data:attrib\abilities\ultra_marine_burning_codex.rgd

Solution: Remove the duplicate armour type as all should be unique in the array.
 
 
Hint #3: Modifiers which are invalid regardless of use.

Modifier modifiers\ability_righteous_fervor_event.lua is invalid, data:attrib\abilities\ultra_marine_custodes_stand.rgd

Solution: None. This ability is considered invalid outside of the vanilla Sisters so please remove it from your project.
 
 
Hint #4: Invalid event modifiers which can safely be renamed.

Modifier modifiers\ability_laud_hailers_foeaura_event.lua is invalid, data:attrib\abilities\ultra_marine_custodes_stand.rgd
Loading error in event_manager_ext.  Unknown modifier type(ability_laud_hailers_foeaura_event)., data:attrib\ebps\races\ultra_marine\troops\ultra_marine_dead.rgd

Solution: Rename all incidents of "ability_laud_hailers_foeaura_event" to "ability_bonesong_event".
 
 
Hint #5a: Invalid _ext section in EBPS unit.

Modifier nil is invalid, data:attrib\sbps\races\ultra_marine\ultra_marine_squad_saint.rgd

Solution: Remove all lines associated with this section in the EBPS unit associated with the squad: GameData["squad_modifier_apply_ext"] = Reference([[sbpextensions\squad_modifier_apply_ext.lua]])

 

Hint #5b: Another Invalid _ext section in EBPS unit.

Unknown area effect filter type , data:attrib\ebps\races\ultra_marine\troops\ultra_marine_saint.rgd
Unknown sweep type , data:attrib\ebps\races\ultra_marine\troops\ultra_marine_saint.rgd

Solution: Remove this section entirely from your EBPS entity as it does not work correctly:

GameData["miraculous_intervention_ext"] = Reference([[ebpextensions\miraculous_intervention_ext.lua]])
GameData["miraculous_intervention_ext"]["recharge_time"] = 100.000000

This _ext code does not function correct and should be omitted from your project.
 

 

Updated: May 02, 2020

Hint #6: Invalid, missing or outdated "squad_jump_ext" squad code

 

Soulstorm introduced a new section "screaming_jets_area_effect" for teleportation or jump-capable units so if such code is not included in your unit's SBPS section the following errors can occur:

Unknown area effect type , data:attrib\sbps\races\ultra_marine\ultra_marine_squad_assault.rgd
Unknown area effect filter type , data:attrib\sbps\races\ultra_marine\ultra_marine_squad_assault.rgd
Unknown sweep type , data:attrib\sbps\races\ultra_marine\ultra_marine_squad_assault.rgd

Solution: Check the vanilla attrib provided and locate the proper use of the "squad_jump_ext" SBPS section and update your code accordingly and add the missing "screaming_jets_area_effect" part. Do not forget to add the three ui sections at the end of the "squad_jump_ext":

GameData["squad_jump_ext"]["ui_description"] = "$0"
GameData["squad_jump_ext"]["ui_icon_name"] = ""
GameData["squad_jump_ext"]["ui_title"] = "$0"

The above code is likely missing as it was added in Soulstorm.

 

 

Hint #7: Undeclared type_armour in your project being called.

Invalid family 'type_armour\tp_living_metal.lua'. Did you add the family to the family scripts?, data:attrib\weapon\ultra_marine_multi_melta.rgd
Invalid family 'type_armour\tp_titan.lua'. Did you add the family to the family scripts?, data:attrib\weapon\ultra_marine_marine_multi_melta.rgd
Invalid family 'type_armour\tp_building_super.lua'. Did you add the family to the family scripts?, data:attrib\weapon\ultra_marine_multi_melta.rgd

Solution: Unless your project does not touch the vanilla game (which uses a pre-determined set) and can add custom type_armours then remove all three lines or any type_armour\XXX.lua that is not supported.
 
 
Hint #8: Weapon _combat Muzzle / Origin coordinates reporting duplicate values.

muzzle is the same as origin for weapon 'weapon\ultra_marine_heavy_bolter_predator_r.lua'. Setting muzzle to 1 metre in front of the origin, data:attrib\ebps\races\ultra_marine\troops\ultra_marine_predator.rgd

Solution: This mostly impacts projectile-based weapons like Missile Launchers so non-projectile based weapon will be an easier fix but for projectile firing weapons you have to exercise caution.
The above issue comes up when you have duplicate values for both origin and muzzle on the same hardpoint.

To resolve (as an example)

GameData["combat_ext"]["hardpoints"]["hardpoint_03"]["weapon_table"]["weapon_01"]["muzzle"]["x"] = -1.550000
GameData["combat_ext"]["hardpoints"]["hardpoint_03"]["weapon_table"]["weapon_01"]["muzzle"]["y"] = 2.700000
GameData["combat_ext"]["hardpoints"]["hardpoint_03"]["weapon_table"]["weapon_01"]["muzzle"]["z"] = 0.000000
GameData["combat_ext"]["hardpoints"]["hardpoint_03"]["weapon_table"]["weapon_01"]["name_for_this_weapon_choice"] = "<None>"
GameData["combat_ext"]["hardpoints"]["hardpoint_03"]["weapon_table"]["weapon_01"]["origin"] = Reference([[tables\position.lua]])
GameData["combat_ext"]["hardpoints"]["hardpoint_03"]["weapon_table"]["weapon_01"]["origin"]["x"] = -1.550000
GameData["combat_ext"]["hardpoints"]["hardpoint_03"]["weapon_table"]["weapon_01"]["origin"]["y"] = 2.700000
GameData["combat_ext"]["hardpoints"]["hardpoint_03"]["weapon_table"]["weapon_01"]["origin"]["z"] = 0.000000

to this:

GameData["combat_ext"]["hardpoints"]["hardpoint_03"]["weapon_table"]["weapon_01"]["muzzle"]["x"] = -1.550000
GameData["combat_ext"]["hardpoints"]["hardpoint_03"]["weapon_table"]["weapon_01"]["muzzle"]["y"] = 2.700000
GameData["combat_ext"]["hardpoints"]["hardpoint_03"]["weapon_table"]["weapon_01"]["muzzle"]["z"] = 0.300000
GameData["combat_ext"]["hardpoints"]["hardpoint_03"]["weapon_table"]["weapon_01"]["name_for_this_weapon_choice"] = "<None>"
GameData["combat_ext"]["hardpoints"]["hardpoint_03"]["weapon_table"]["weapon_01"]["origin"] = Reference([[tables\position.lua]])
GameData["combat_ext"]["hardpoints"]["hardpoint_03"]["weapon_table"]["weapon_01"]["origin"]["x"] = -1.550000
GameData["combat_ext"]["hardpoints"]["hardpoint_03"]["weapon_table"]["weapon_01"]["origin"]["y"] = 2.700000
GameData["combat_ext"]["hardpoints"]["hardpoint_03"]["weapon_table"]["weapon_01"]["origin"]["z"] = 0.000000

Note: As mentioned, please be careful when changing this value for projectile-based weapons like Missile Launchers or Plasma Cannons as sometimes changing the above can cause Crash to Desktops (CTD) on some maps especially near certain start_pos or starting HQs. One such map for testing this is the vanilla map "2p_Deadmans_Crossing" where near the top-left of the map where Player1 starts this is a classic area for bad muzzle/origin coordinates for projectile weapons to cause the game to CTD.
 
Added: September 07, 2019
Check the end of your warnings.log for the following or similar error right after your game mysteriously CTDs when armies are fighting each other:

Crash TerrainHM::ClampPosToTerrain
x: -1.#IND00, z: -1.#IND00
minX: -256.000000, maxX: 258.000000
minZ: -256.000000, maxZ: 258.000000

For projectile-based weapons you likely want to be more gentler/less aggressive with the values so perhaps try this:

GameData["combat_ext"]["hardpoints"]["hardpoint_03"]["weapon_table"]["weapon_01"]["muzzle"]["x"] = -1.550000
GameData["combat_ext"]["hardpoints"]["hardpoint_03"]["weapon_table"]["weapon_01"]["muzzle"]["y"] = 2.700000
GameData["combat_ext"]["hardpoints"]["hardpoint_03"]["weapon_table"]["weapon_01"]["muzzle"]["z"] = 0.000010
GameData["combat_ext"]["hardpoints"]["hardpoint_03"]["weapon_table"]["weapon_01"]["name_for_this_weapon_choice"] = "<None>"
GameData["combat_ext"]["hardpoints"]["hardpoint_03"]["weapon_table"]["weapon_01"]["origin"] = Reference([[tables\position.lua]])
GameData["combat_ext"]["hardpoints"]["hardpoint_03"]["weapon_table"]["weapon_01"]["origin"]["x"] = -1.550000
GameData["combat_ext"]["hardpoints"]["hardpoint_03"]["weapon_table"]["weapon_01"]["origin"]["y"] = 2.700000
GameData["combat_ext"]["hardpoints"]["hardpoint_03"]["weapon_table"]["weapon_01"]["origin"]["z"] = 0.000000

For the above, you will need to test your unit's projectile weapon to ensure it fires it in the correct direction, the launcher is correctly positioned on the model (ie. facing the right way and not, say, backwards-facing), and does not cause a CTD when it fires on specific parts of the map (mentioned above).
 
 
Do not use CAPITAL letters
 
- All RDG filenames and most calls inside the logic should ALWAYS be in lower caps. One exception would be the hardpoint OE name found in the EBPS' combat_ext.

GameData["combat_ext"]["hardpoints"]["hardpoint_01"]["weapon_table"]["weapon_01"]["name_for_this_weapon_choice"] = "Space_Marines_Bolter"

The above is fine but this is not:

GameData["combat_ext"]["hardpoints"]["hardpoint_01"]["weapon_table"]["weapon_01"]["weapon"] = "weapon\\ultra_marine_BOLTER_tactical.lua"

This EBPS entity is calling a weapon RGD filename outside itself and should always be in lower case.
 
One of the key reasons to ensure No Capitals is the AI will not function correctly or as efficiently as it could be.
 
 
Ensure Code Exclusivity In Your Project
 
Like your Art folder, always avoid making outside calls to vanilla sources with your project.
 
An example of this would simply be calling a vanilla weapon within your custom EBPS entity within your project:

GameData["combat_ext"]["hardpoints"]["hardpoint_01"]["weapon_table"]["weapon_01"]["weapon"] = "weapon\\space_marine_bolter_tactical.lua"

Note that the weapon is calling the vanilla Space Marines faction built in as part of the game which we should not change.
 
It should be (using the Ultramarines faction mod project as an example):

GameData["combat_ext"]["hardpoints"]["hardpoint_01"]["weapon_table"]["weapon_01"]["weapon"] = "weapon\\ultra_marine_bolter_tactical.lua"

This would also hold true for abilities (using the Ultramarines faction mod project as an example once more) :

GameData["ability_ext"]["abilities"]["ability_01"] = "abilities\\marines_frag_grenades.lua"
GameData["ability_ext"]["abilities"]["ability_02"] = "abilities\\marines_krak_grenades.lua"

Should be:

GameData["ability_ext"]["abilities"]["ability_01"] = "abilities\\ultra_marine_frag_grenades.lua"
GameData["ability_ext"]["abilities"]["ability_02"] = "abilities\\ultra_marine_krak_grenades.lua"

So avoid using outside calls to the vanilla game and keep it exclusive to your project.
 
 
Best Practice Coding Issues to Avoid
 
Hint #1: There should be no calls within your AE code for a .RGD filename: it should ALWAYS be .lua.
 
So this (using the Ultramarines faction mod project as an example):

GameData["ability_ext"]["abilities"]["ability_01"] = "abilities\\ultra_marine_healing_aura.rgd"
GameData["ability_ext"]["abilities"]["ability_02"] = "abilities\\ultra_marine_speed_decrease1.rgd"

Should be:

GameData["ability_ext"]["abilities"]["ability_01"] = "abilities\\ultra_marine_healing_aura.lua"
GameData["ability_ext"]["abilities"]["ability_02"] = "abilities\\ultra_marine_speed_decrease1.lua"

Hint #2: Watch for invalid path names (ie. weapons\\) which do not follow convention and should be immediately corrected.
 
So this:


GameData["combat_ext"]["hardpoints"]["hardpoint_01"]["weapon_table"]["weapon_01"]["weapon"] = "weapons\\ultra_marine_bolter_tactical.lua"

Should be:

GameData["combat_ext"]["hardpoints"]["hardpoint_01"]["weapon_table"]["weapon_01"]["weapon"] = "weapon\\ultra_marine_bolter_tactical.lua"

Path changes which do not adhere to the standards can also break the AI and cause it to not build or properly use that affected entity (ie. not upgrade the unit's weapon hardpoints).
 
Hint #3: Do not abbreviate the paths but use them in their entirety.
 
As example for the Ultramarines project, these are invalid:

GameData["ability_ext"]["abilities"]["ability_01"] = "ultra_marine_healing_aura.lua"
GameData["combat_ext"]["hardpoints"]["hardpoint_01"]["weapon_table"]["weapon_01"]["weapon"] = "ultra_marine_bolter_tactical.lua"
GameData["spawner_ext"]["squad_table"]["squad_01"] = "ultra_marine_squad_tactical.lua"
GameData["research_ext"]["research_table"]["research_01"] = "ultra_marine_health_upgrade_research.lua"

And these are correct:

GameData["ability_ext"]["abilities"]["ability_01"] = "abilities\\ultra_marine_healing_aura.lua"
GameData["combat_ext"]["hardpoints"]["hardpoint_01"]["weapon_table"]["weapon_01"]["weapon"] = "weapon\\ultra_marine_bolter_tactical.lua"
GameData["spawner_ext"]["squad_table"]["squad_01"] = "sbps\\races\\ultra_marine\\ultra_marine_squad_tactical.lua"
GameData["research_ext"]["research_table"]["research_01"] = "research\\ultra_marine_health_upgrade_research.lua"

So ensure you use the full path.
 
Hint #4: For your SBPS units, ensure your formations .LUA names are correct and valid. If not, if this SBPS unit is created in the game it will immediately crash the game back to your desktop. As example:
 
This incorrect:

GameData["squad_formation_ext"] = Reference([[sbpextensions\squad_formation_ext.lua]])
GameData["squad_formation_ext"]["idle_formation"] = "formations\\bloc.lua"

This is correct:

GameData["squad_formation_ext"] = Reference([[sbpextensions\squad_formation_ext.lua]])
GameData["squad_formation_ext"]["idle_formation"] = "formations\\block.lua"

So please make sure your formations are valid.
 
 
The AEP Tool
 
I've included the vaunted AeP tool used to compare \attrib builds so please read the provided instructions in the zip as to how to get the most out of it. It is a VERY useful tool!


thudo

Posted 01 July 2019 - 12:20 AM

Update - Oct 25, 2019

 

The intent of this thread is to give new DoW1 mod developers a reference point to building their projects with the objective to of ensuring we keep to what could be considered as being "best practices".

 

I will constantly be updating this as I tweak the sections especially based off feedback.

 

It will be broken down into various sections..

 

AE (Attribute Editor)

UCS

Art

Sound and Speech

Icons

AI

MISC

SCAR

 

..and possibly more but we'll see...

 

 

Launch Dawn Of War in DEV Mode

 

To fully troubleshoot your mod project you must always enter in DEV mode to see any background problems that you would otherwise not see the normal method.

 

Attached below is a CMD that you should unzip into where your root Soulstorm folder is then rename the filename to suit the name of your .module name (just to readily identify it with ease).

 

With this CMD it contains the following:

del *_ErrorLog.txt
del *_MiniDump.dmp
del %~dp0Mod_Name\data\ai\mapdb\*.dat
start soulstorm.exe -dev -nomovies -modname Mod_Name

The first two lines will clear all useless dump files which accumulate over time in your Soulstorm root which are basically not needed and 99% of the time never divulge anything useful.

 

The third line clears out all MapDB config info if that game mode is enabled for your mod. These should be cleared from time to time if present. Note the label there "Mod_Name": use the folder name of your mod in your root Soulstorm path.

 

Finally, the fourth line is the actual commandline which runs with the relevant args but the final variable "Mod_Name" should be the name of your .module so your mod will successfully launch with the correct switches.

 

 

What does using -DEV unlock?

 

Check THIS thread as it is covered in detail and should be quite valuable to all mod project developers.


Review the complete topic (launches new window)