Deliverator
Graphical Hackificator
People have been asking for a guide on editing Units.artdef so here is a rough guide. Some or all of this might become redundant when the mod tools are released so I'm keeping it rough!
Note: This was written before the Asset Editor was released (as part of the Civ 6 SDK). Now you have the option of using that instead of directly editing the XML.
Units.artdef is just an XML file without the .xml extension. Although it is possible and sometimes easier to edit XML files with a simpler text edit such as Notepad++ it's helpful also to use an XML editor. The best I've found is the freeware 1.1 version of XML Marker. (Don't bother with the 2.2 version which is pretty much the same but costs $125!)
http://symbolclick.com/xmlmarker_1_1_setup.exe
Having installed XML Marker 1.1 we can open Units.artdef. You'll need to change "Files of type:" to be all files since Units.artdef doesn't have the .xml extension.
Navigating to the RootCollections element you can get an overview of the structure of the file.
The three subcollections I have been editing so far are: Units, UnitMemberTypes and UnitTintTypes. More detail on each of these in turn follows:
Units
The m_Name of each of these is the same name as the name of the Unit in the GameData XML files e.g. UNIT_WARRIOR, UNIT_SPEARMAN. Apparently this provides the link between a Unit and its Art Definition. If I wanted to reuse the Apostle unit art for a new unit called UNIT_WIZARD I would need to duplicate the UNIT_APOSTLE entry in Units.artdef and update the m_Name field on my duplicate copy to be UNIT_WIZARD.
The number, type, scale and formation of the UnitMemberTypes (the actual individual unit models used for the unit) can be changed here. So if I want to make a unit consisting of two Swordsmen and an Apostle then I can achieve that purely by editing the entry in the Units collection. Looking at this section taken from the UNIT_SCOUT Units entry you can see that 1 instance of the "Scout" UnitMemberType and 1 instance of the "ScoutDog" UnitMemberType are specified.
UnitMemberTypes
This is where I can actually recombine and vary the attachment elements that make unit each individual unit member. The start point is again to clone an existing UnitMemberType entry taking the Unit you want to use as a base giving it a different name. In XML Marker, Ctrl-E to select the whole of element is useful for duplication. Also the Moar Units mod I've used the prefix "UnitMember_" for names to make it easier to re-find them later.
Here is the entire UnitMember_Minuteman entry from Moar Units with some comments on the significant changes from the Redcoat entry it was based on:
The "Bins" collection for each attachment needs some further explanation. These paths correspond to entries in the Unit_Bins.artdef file. For example in the vanilla Units.artdef you have Bins entries such as "Hats/Spearman" or "Heads/Male". If you look under this path in Unit_Bins.artdef you can see that under each of these you have all different cultural variants e.g. "NorthernEuropean" or "Mughal". This is how cultural variation is applied. The nice part of this is that if I set up a new non-unique unit such the Moar Units Rifleman I can use "Heads/Male" and each civilization will automatically get its own ethnic skin tone. If I don't want any variation cultural or otherwise then I specify specific models that I want to use. For example, in the Moar Units Druzhina Cavalry units I am using one Mughal helmet and one NorthernEuropean helmet like so:
UnitTintTypes
This is effectively UnitColorTypes (or UnitColourTypes if you're not American!). In the Minuteman UnitMemberTypes example above this is where the UnitTintType "Color_Minuteman_Jacket" is specified.
UnitTintTypes are also used to vary the color of the horses - search for the UnitTintTypes called "Horse_Default".
In this example, for the "Color_Spain" entry I've made two colors corresponding to the red and the yellow from the Spain civilization colors. The EasyRGB tool is handy for converting RGB 0-255 to RGB 0-1.
UnitCultures
Update: With Gathering Storm there are now 11 base Unit Cultures:
Asian
Mediterranean
Indian
MiddleEastern
European
African
SouthAmerican
Maori
NativeAmerican
SouthEastAsian
Barbarian
Pre-GS: There are only eight "UnitCultures" in the vanilla ArtDefs (as opposed to "Cultures" which are used for Cities, Districts, Improvements etc by the look of it):
EastAsian (Japan, China)
Mediterranean (Greece, Rome)
Mughal (Arabia, India, Sumeria)
NorthAfrican (Egypt)
NorthernEuropean (America, England, France, Germany, Spain(!?), Russia, Poland)
SouthAfrican (Kongo)
SouthAmerican (Aztec, Brazil)
Barbarian (Barbarian)
This means Norway and Scythia get the "Any" default Culture with regards to Units.artdef.
All the cultural variations you see come from one of these 8 buckets.
It is possible to create a new UnitCulture in the Cultures.artdef and then start to define new cultural variations of units in the Units.artdef.
Note: This was written before the Asset Editor was released (as part of the Civ 6 SDK). Now you have the option of using that instead of directly editing the XML.
Units.artdef is just an XML file without the .xml extension. Although it is possible and sometimes easier to edit XML files with a simpler text edit such as Notepad++ it's helpful also to use an XML editor. The best I've found is the freeware 1.1 version of XML Marker. (Don't bother with the 2.2 version which is pretty much the same but costs $125!)
http://symbolclick.com/xmlmarker_1_1_setup.exe
Having installed XML Marker 1.1 we can open Units.artdef. You'll need to change "Files of type:" to be all files since Units.artdef doesn't have the .xml extension.
Navigating to the RootCollections element you can get an overview of the structure of the file.
The three subcollections I have been editing so far are: Units, UnitMemberTypes and UnitTintTypes. More detail on each of these in turn follows:
Units
The m_Name of each of these is the same name as the name of the Unit in the GameData XML files e.g. UNIT_WARRIOR, UNIT_SPEARMAN. Apparently this provides the link between a Unit and its Art Definition. If I wanted to reuse the Apostle unit art for a new unit called UNIT_WIZARD I would need to duplicate the UNIT_APOSTLE entry in Units.artdef and update the m_Name field on my duplicate copy to be UNIT_WIZARD.
The number, type, scale and formation of the UnitMemberTypes (the actual individual unit models used for the unit) can be changed here. So if I want to make a unit consisting of two Swordsmen and an Apostle then I can achieve that purely by editing the entry in the Units collection. Looking at this section taken from the UNIT_SCOUT Units entry you can see that 1 instance of the "Scout" UnitMemberType and 1 instance of the "ScoutDog" UnitMemberType are specified.
Code:
...
<m_ChildCollections>
<Element>
<m_CollectionName text="Members"/>
<Element>
<m_Fields>
<m_Values>
<Element class="AssetObjects::FloatValue">
<m_fValue>1.000000</m_fValue>
<m_ParamName text="Scale"/>
</Element>
<Element class="AssetObjects::IntValue">
<m_nValue>1</m_nValue>
<m_ParamName text="Count"/>
</Element>
<Element class="AssetObjects::ArtDefReferenceValue">
<m_ElementName text="Scout"/>
<m_RootCollectionName text="UnitMemberTypes"/>
<m_ArtDefPath text="Units.artdef"/>
<m_CollectionIsLocked>true</m_CollectionIsLocked>
<m_TemplateName text="Units"/>
<m_ParamName text="Type"/>
</Element>
</m_Values>
</m_Fields>
<m_ChildCollections/>
<m_Name text="Members1"/>
</Element>
<Element>
<m_Fields>
<m_Values>
<Element class="AssetObjects::FloatValue">
<m_fValue>1.000000</m_fValue>
<m_ParamName text="Scale"/>
</Element>
<Element class="AssetObjects::IntValue">
<m_nValue>1</m_nValue>
<m_ParamName text="Count"/>
</Element>
<Element class="AssetObjects::ArtDefReferenceValue">
<m_ElementName text="ScoutDog"/>
<m_RootCollectionName text="UnitMemberTypes"/>
<m_ArtDefPath text="Units.artdef"/>
<m_CollectionIsLocked>true</m_CollectionIsLocked>
<m_TemplateName text="Units"/>
<m_ParamName text="Type"/>
</Element>
</m_Values>
</m_Fields>
<m_ChildCollections/>
<m_Name text="Members2"/>
</Element>
</Element>
...
UnitMemberTypes
This is where I can actually recombine and vary the attachment elements that make unit each individual unit member. The start point is again to clone an existing UnitMemberType entry taking the Unit you want to use as a base giving it a different name. In XML Marker, Ctrl-E to select the whole of element is useful for duplication. Also the Moar Units mod I've used the prefix "UnitMember_" for names to make it easier to re-find them later.
Here is the entire UnitMember_Minuteman entry from Moar Units with some comments on the significant changes from the Redcoat entry it was based on:
Code:
<Element>
<m_Fields>
<m_Values>
<Element class="AssetObjects::ArtDefReferenceValue">
<m_ElementName text="Redcoat"/>
<m_RootCollectionName text="UnitMovementTypes"/>
<m_ArtDefPath text="Units.artdef"/>
<m_CollectionIsLocked>true</m_CollectionIsLocked>
<m_TemplateName text=""/>
<m_ParamName text="Movement"/>
</Element>
<Element class="AssetObjects::ArtDefReferenceValue">
<m_ElementName text="RedcoatCombat"/>
<m_RootCollectionName text="MemberCombat"/>
<m_ArtDefPath text="Units.artdef"/>
<m_CollectionIsLocked>true</m_CollectionIsLocked>
<m_TemplateName text=""/>
<m_ParamName text="Combat"/>
</Element>
<Element class="AssetObjects::ArtDefReferenceValue">
<m_ElementName text="MEAT"/>
<m_RootCollectionName text="MaterialTypes"/>
<m_ArtDefPath text="VFX.artdef"/>
<m_CollectionIsLocked>true</m_CollectionIsLocked>
<m_TemplateName text=""/>
<m_ParamName text="VFXMaterialType"/>
</Element>
<Element class="AssetObjects::ArtDefReferenceValue">
<m_ElementName text="MEAT"/>
<m_RootCollectionName text="MaterialTypes"/>
<m_ArtDefPath text="VFX.artdef"/>
<m_CollectionIsLocked>true</m_CollectionIsLocked>
<m_TemplateName text=""/>
<m_ParamName text="VFXWeaponImpact"/>
</Element>
<Element class="AssetObjects::FloatValue">
<m_fValue>0.000000</m_fValue>
<m_ParamName text="ImpactHeightOverride"/>
</Element>
</m_Values>
</m_Fields>
<m_ChildCollections>
<Element>
<m_CollectionName text="Cultures"/>
<Element>
<m_Fields>
<m_Values/>
</m_Fields>
<m_ChildCollections>
<Element>
<m_CollectionName text="Variations"/>
<Element>
<m_Fields>
<m_Values>
<Element class="AssetObjects::FloatValue">
<m_fValue>1.100000</m_fValue>
<m_ParamName text="Scale"/>
</Element>
<Element class="AssetObjects::BoolValue">
<m_bValue>false</m_bValue>
<m_ParamName text="IsAttachment"/>
</Element>
</m_Values>
</m_Fields>
<m_ChildCollections>
<Element>
<m_CollectionName text="Attachments"/>
<Element>
<m_Fields>
<m_Values>
<Element class="AssetObjects::StringValue">
<m_Value text="Root"/>
<m_ParamName text="Point"/>
</Element>
<Element class="AssetObjects::ArtDefReferenceValue">
<m_ElementName text="Color_Minuteman_Jacket"/> <!-- A custom color specified in UnitTintTypes - see below -->
<m_RootCollectionName text="UnitTintTypes"/>
<m_ArtDefPath text="Units.artdef"/>
<m_CollectionIsLocked>true</m_CollectionIsLocked>
<m_TemplateName text=""/>
<m_ParamName text="Tint"/>
</Element>
</m_Values>
</m_Fields>
<m_ChildCollections>
<Element>
<m_CollectionName text="Bins"/>
<Element>
<m_Fields>
<m_Values/>
</m_Fields>
<m_ChildCollections/>
<m_Name text="Armor/Redcoat"/>
</Element>
</Element>
</m_ChildCollections>
<m_Name text="Armor"/>
</Element>
<Element>
<m_Fields>
<m_Values>
<Element class="AssetObjects::StringValue">
<m_Value text="WeaponPrimary"/>
<m_ParamName text="Point"/>
</Element>
<Element class="AssetObjects::ArtDefReferenceValue">
<m_ElementName text=""/>
<m_RootCollectionName text="UnitTintTypes"/>
<m_ArtDefPath text=""/>
<m_CollectionIsLocked>true</m_CollectionIsLocked>
<m_TemplateName text=""/>
<m_ParamName text="Tint"/>
</Element>
</m_Values>
</m_Fields>
<m_ChildCollections>
<Element>
<m_CollectionName text="Bins"/>
<Element>
<m_Fields>
<m_Values/>
</m_Fields>
<m_ChildCollections/>
<m_Name text="Rifles/Redcoat"/>
</Element>
</Element>
</m_ChildCollections>
<m_Name text="Weapon"/>
</Element>
<Element>
<m_Fields>
<m_Values>
<Element class="AssetObjects::StringValue">
<m_Value text="Hat"/>
<m_ParamName text="Point"/>
</Element>
<Element class="AssetObjects::ArtDefReferenceValue">
<m_ElementName text=""/>
<m_RootCollectionName text="UnitTintTypes"/>
<m_ArtDefPath text=""/>
<m_CollectionIsLocked>true</m_CollectionIsLocked>
<m_TemplateName text=""/>
<m_ParamName text="Tint"/>
</Element>
</m_Values>
</m_Fields>
<m_ChildCollections> <!-- Each Unit Member will be randomly allocated one of these 3 hats/hair -->
<Element>
<m_CollectionName text="Bins"/>
<Element>
<m_Fields>
<m_Values/>
</m_Fields>
<m_ChildCollections/>
<m_Name text="Hats/Ranger/#/Ranger_HatC"/>
</Element>
<Element>
<m_Fields>
<m_Values/>
</m_Fields>
<m_ChildCollections/>
<m_Name text="Hair/Male"/>
</Element>
<Element>
<m_Fields>
<m_Values/>
</m_Fields>
<m_ChildCollections/>
<m_Name text="Hats/Redcoat/#/Redcoat_HatA"/>
</Element>
</Element>
</m_ChildCollections>
<m_Name text="Hat"/>
</Element>
<Element>
<m_Fields>
<m_Values>
<Element class="AssetObjects::StringValue">
<m_Value text="Root"/>
<m_ParamName text="Point"/>
</Element>
<Element class="AssetObjects::ArtDefReferenceValue">
<m_ElementName text=""/>
<m_RootCollectionName text="UnitTintTypes"/>
<m_ArtDefPath text=""/>
<m_CollectionIsLocked>true</m_CollectionIsLocked>
<m_TemplateName text=""/>
<m_ParamName text="Tint"/>
</Element>
</m_Values>
</m_Fields>
<m_ChildCollections>
<Element>
<m_CollectionName text="Bins"/>
<Element>
<m_Fields>
<m_Values/>
</m_Fields>
<m_ChildCollections/>
<m_Name text="Bodies/Male_MediumBody_Hands"/>
</Element>
</Element>
</m_ChildCollections>
<m_Name text="Body"/>
</Element>
<Element>
<m_Fields>
<m_Values>
<Element class="AssetObjects::StringValue">
<m_Value text="Root"/>
<m_ParamName text="Point"/>
</Element>
<Element class="AssetObjects::ArtDefReferenceValue">
<m_ElementName text="Caucasian_Light"/>
<m_RootCollectionName text="UnitTintTypes"/>
<m_ArtDefPath text="Units.artdef"/>
<m_CollectionIsLocked>true</m_CollectionIsLocked>
<m_TemplateName text=""/>
<m_ParamName text="Tint"/>
</Element>
</m_Values>
</m_Fields>
<m_ChildCollections>
<Element>
<m_CollectionName text="Bins"/>
<Element>
<m_Fields>
<m_Values/>
</m_Fields>
<m_ChildCollections/>
<m_Name text="Heads/Male"/>
</Element>
</Element>
</m_ChildCollections>
<m_Name text="Head"/>
</Element>
</Element>
</m_ChildCollections>
<m_Name text="A"/>
</Element>
</Element>
</m_ChildCollections>
<m_Name text="Any"/>
</Element>
</Element>
</m_ChildCollections>
<m_Name text="UnitMember_Minuteman"/> <!-- Name referenced from Units entry -->
</Element>
The "Bins" collection for each attachment needs some further explanation. These paths correspond to entries in the Unit_Bins.artdef file. For example in the vanilla Units.artdef you have Bins entries such as "Hats/Spearman" or "Heads/Male". If you look under this path in Unit_Bins.artdef you can see that under each of these you have all different cultural variants e.g. "NorthernEuropean" or "Mughal". This is how cultural variation is applied. The nice part of this is that if I set up a new non-unique unit such the Moar Units Rifleman I can use "Heads/Male" and each civilization will automatically get its own ethnic skin tone. If I don't want any variation cultural or otherwise then I specify specific models that I want to use. For example, in the Moar Units Druzhina Cavalry units I am using one Mughal helmet and one NorthernEuropean helmet like so:
Code:
...
<m_ChildCollections>
<Element>
<m_CollectionName text="Bins"/>
<Element>
<m_Fields>
<m_Values/>
</m_Fields>
<m_ChildCollections/>
<m_Name text="Hats/Spearman/NorthernEuropean/Spearman_European_HelmA"/>
</Element>
<Element>
<m_Fields>
<m_Values/>
</m_Fields>
<m_ChildCollections/>
<m_Name text="Hats/Spearman/Mughal/Spearman_MiddleEastern_HelmA"/>
</Element>
</Element>
</m_ChildCollections>
<m_Name text="Hats"/>
...
UnitTintTypes
This is effectively UnitColorTypes (or UnitColourTypes if you're not American!). In the Minuteman UnitMemberTypes example above this is where the UnitTintType "Color_Minuteman_Jacket" is specified.
UnitTintTypes are also used to vary the color of the horses - search for the UnitTintTypes called "Horse_Default".
In this example, for the "Color_Spain" entry I've made two colors corresponding to the red and the yellow from the Spain civilization colors. The EasyRGB tool is handy for converting RGB 0-255 to RGB 0-1.
Code:
<Element>
<m_Fields>
<m_Values/>
</m_Fields>
<m_ChildCollections>
<Element>
<m_CollectionName text="Colors"/>
<Element>
<m_Fields>
<m_Values>
<Element class="AssetObjects::RGBValue">
<m_r>173</m_r>
<m_g>36</m_g>
<m_b>36</m_b>
<m_ParamName text="Color"/>
</Element>
</m_Values>
</m_Fields>
<m_ChildCollections/>
<m_Name text="Colors001"/>
</Element>
<Element>
<m_Fields>
<m_Values>
<Element class="AssetObjects::RGBValue">
<m_r>221</m_r>
<m_g>205</m_g>
<m_b>0</m_b>
<m_ParamName text="Color"/>
</Element>
</m_Values>
</m_Fields>
<m_ChildCollections/>
<m_Name text="Colors002"/>
</Element>
</Element>
</m_ChildCollections>
<m_Name text="Color_Spain"/>
</Element>
UnitCultures
Update: With Gathering Storm there are now 11 base Unit Cultures:
Asian
Mediterranean
Indian
MiddleEastern
European
African
SouthAmerican
Maori
NativeAmerican
SouthEastAsian
Barbarian
Pre-GS: There are only eight "UnitCultures" in the vanilla ArtDefs (as opposed to "Cultures" which are used for Cities, Districts, Improvements etc by the look of it):
EastAsian (Japan, China)
Mediterranean (Greece, Rome)
Mughal (Arabia, India, Sumeria)
NorthAfrican (Egypt)
NorthernEuropean (America, England, France, Germany, Spain(!?), Russia, Poland)
SouthAfrican (Kongo)
SouthAmerican (Aztec, Brazil)
Barbarian (Barbarian)
This means Norway and Scythia get the "Any" default Culture with regards to Units.artdef.
All the cultural variations you see come from one of these 8 buckets.
It is possible to create a new UnitCulture in the Cultures.artdef and then start to define new cultural variations of units in the Units.artdef.
Last edited: