Modding:Working with LSX files (2024)

Modding:Working with LSX files (1)This page is a modding page, and follows its own rules and standards separate from the rest of the wiki.
bg3.wiki modding
Modding homepage
  • Modding resources
Modding resources

Armor/Clothing Texture Maps

Body Models

Custom polymorph

Dependencies

Face and body textures

Fixing bone errors

Fixing neck seams

Fixing UV errors

Getting Started with BG3 Modding

Hair Meshes

Head Models

Mod troubleshooting

Modding class icons

NPC Head Models

Tiefling Horn Models

Non-VT Shaders

Race UUID

Sample Templates

Texture formatting

Tools

TreasureTables References

Tutorials

VertexColorMaskSlots

Working with LSX files

Modding guides

Blender Export Settings

Coding An Item

Compatibility Framework

Creating a custom cloth collider

Creating and Exporting Meshes in Blender

Creating Armor Mods

Creating Item Icons

Creating meta.lsx

Creating mods

Creating Outfit Textures

Editing a Character Creation Preset

Editing Equipment.txt

Hair Mod File Setup

Hair Mod Mesh Setup

Hotloading

How To Find A Virtual Texture

Installing mods

Localization

Packaging mods

Texture formatting

Unpacking and converting files

Working with LSX files

Hair modding

Creating Custom Hair with Hair Tool

Creating hair merged.lsf with custom texture

Creating meta.lsx

Custom Hair Highlights

Hair Meshes

Hair Mod File Setup

Hair Mod Mesh Setup

Head modding

Creating meta.lsx

Face and body textures

Fixing neck seams

Head Modding

Head Models

Head Troubleshooting

NPC Head Models

Armor/clothing modding

Armor/Clothing Texture Maps

Coding An Item

Creating and Exporting Meshes in Blender

Creating Armor Mods

Creating Item Icons

Creating meta.lsx

Fixing bone errors

How To Find A Virtual Texture

Texture formatting

TreasureTables References

Use Outfit Builder To Refit Outfits

VertexColorMaskSlots

Race/class modding

Creating Race Mods

Editing a Character Creation Preset

  • v
  • t
  • e

I'll try to give people a head start here in working with lsx files, which are just xml files, and getting a head start with modifying Progressions.lsx. This gives you the power to modify & add classes & what they get on level up.

Contents

  • 1 Folder structure
  • 2 Working with .lsx, or rather .xml files
  • 3 How does BG3 load resources?
  • 4 Progressions.lsx

Folder structure[edit | edit source]

There's already tutorials on here on how to setup the folder structure, overall it's very beneficial to package your mod as .pak instead of an archive which the user extracts in to their data folder. BG3 uses an override system which I will get into more detail with later on, extracting everything in the data folder seems to somewhat circumvent this behavior since one seems to be forced to put stuff in some variation of Gustav, GustavDev, Shared, SharedDev. Be sure to really take a look at the folder structure because missing one little detail will make your mod not load & it's overall a tedious process to debug.

Working with .lsx, or rather .xml files[edit | edit source]

Depending on experience level & what your goals are different strategies can be taken to modify the files. For my mod, which is doing sweeping changes I use python. It also helps me to query the data & find what I'm looking for directly instead of trying to look through the same file in multiple locations. The advantage of doing it programmatically is that you can just re-run the script if a patch updates the same nodes you've changed. At the bottom I've included the script I use to generate my mod, python is a bit outside the scope of this tutorial but it should give you a skeleton & the general workflow for how to work with the files. The mod in question adds level 13 to all base classes, this makes it so you can take level 12 in a mod which increases max level without the game crashing when you level up next time. It gives feat on every level, and triples the spell slots/sorcery points/ki points etc on level up.

How does BG3 load resources?[edit | edit source]

As hinted on earlier it's very important to learn how resources are loaded and overridden. Imagine you extract the game .paks, you look through the folder structure, and inside Data/Public/Shared/Progressions/Progressions.lsx you find xml data for levels. You modify it to your hearts content, perhaps you remove stuff, add some stuff, and then you just let it sit there inside that folder hierarchy. What will happen is that it will completely replace that file as seen in the .pak file. Perhaps you noticed that there's only level 1-6 in this file, and you thought it smart to add levels 7-12. But the problem is that level 7-12 is another Progressions.lsx inside the SharedDev subfolder structure, and that one is loaded after the one in Shared and just overwrote your 7-12. While this seems like a downer it should also give you a hint on how the system works. There's a load order, even inside the shipped .paks with the game, and you generally don't want to mess with that, because the patches are also playing ball with that load order. Generally, whenever you see Gustav/GustavDev/Shared/SharedDev in paths you should replace that with your mod name when you copy it over to your mod project. Generally you should only include sections of the files which you're actually changing, exclude everything else, and they will instead be filled by the game. This gives you the best chance that your mod is still working whenever a patch arrives, or if another mod is overriding stuff in the same file.

So how are these files merged? It seems to be different depending on files, .txt files such as Data.txt merge based on the key of the key / value pair. .lsx which I'll focus on however are merged base on their UUID, so when you look over the xml whatever group has an UUID child is the granularity that you will be overriding on.

Progressions.lsx[edit | edit source]

So finally we'll get to the structure of this file which is integral to all the level ups in the game. It's important to know that this file is split into multiple locations, for the base game without patches it's split between Shared/Public/Shared/Progressions/Progressions.lsx, which contains level 1-6 & I presume the EA state of the game. 7-12 and modifications to the progression is instead in Shared/Public/SharedDev/Progressions/Progressions.lsx. Patches which changes progression have their own versions which takes precedence. As a rule of thumb I would never change the type attribute of any nodes, although I haven't really tried it. Lets break down a level 1 of a class, in this case I'll take Cleric, because it has a lot of variation, even if it's very large:

 <node id="Progression"> <attribute id="Boosts" type="LSString" value="Proficiency(LightArmor);Proficiency(MediumArmor);Proficiency(Shields);Proficiency(Morningstars);Proficiency(Flails)"/> <attribute id="IsMulticlass" type="bool" value="true"/> <attribute id="Level" type="uint8" value="1"/> <attribute id="Name" type="LSString" value="Cleric"/> <attribute id="PassivesAdded" type="LSString" value="DomainSpells;UnlockedSpellSlotLevel1"/> <attribute id="ProgressionType" type="uint8" value="0"/> <attribute id="Selectors" type="LSString" value="SelectSpells(2f43a103-5bf1-4534-b14f-663decc0c525,3,0,,,,AlwaysPrepared);AddSpells(269d1a3b-eed8-4131-8901-a562238f5289)"/> <attribute id="TableUUID" type="guid" value="64474b62-b4f5-46b3-b94a-c676c6da3116"/> <attribute id="UUID" type="guid" value="366cde9c-db0c-43ce-a49c-fb140e084b3c"/> <children> <node id="SubClasses"> <children> <node id="SubClass"> <attribute id="Object" type="guid" value="4b5da2f5-b999-4623-8bff-a63df5560fb3"/> </node> <node id="SubClass"> <attribute id="Object" type="guid" value="c54d7591-b305-4f22-b2a7-1bf5c4a3470a"/> </node> <node id="SubClass"> <attribute id="Object" type="guid" value="f013d01b-3310-43f7-81bf-a51130442b5e"/> </node> <node id="SubClass"> <attribute id="Object" type="guid" value="ebe18794-b5e1-41c4-befa-4b9d6922b0ec"/> </node> <node id="SubClass"> <attribute id="Object" type="guid" value="6dec76d0-df22-411c-8a78-3d6fb843ae50"/> </node> <node id="SubClass"> <attribute id="Object" type="guid" value="89bacf1b-8f15-4972-ada7-bf59c7c78441"/> </node> <node id="SubClass"> <attribute id="Object" type="guid" value="b9ccf90e-b35b-4b73-b896-8ed2d32ae8c6"/> </node> </children> </node> </children> </node>

The first attribute, which has the id Boosts, is one of the most important ones. It's a series of function calls which declares what the you actually get when you reach this particular level. In this case getting level 1 Cleric gives us a series of proficiencies, what can be specified here is also currently outside the scope of this tutorial, but it's actually pretty straightforward & easy to deduce. If you want your modified level up get something else, look at the level in the file for another level up which has what you want & append it to yours.

The second attribute, which has the attribute IsMulticlass, is optional & defaults to false, but in this case it's true. What that means is that this level up is actually for when multi classing into Cleric, this is not the specification for a level 1 character starting with Cleric.

The third attribute, Level, simply specifies that this declaration concerns level 1. The fourth attribute, Name, is simply the identifier for the class. The fifth attribute I haven't deduced yet, but surely related to passives granted.

The sixth attribute, ProgressionType, is an integer which decides what type of progression it is. 0 means that it's a base class, 1 means that it's a sub class, and 3 means that it's related to a race.

The seventh attribute, Selectors, decides what you can choose from / get for this level up. SelectSpells(2f43a103-5bf1-4534-b14f-663decc0c525,3,0,,,,AlwaysPrepared); for example, starts with a UUID into SpellLists.lsx, which is a set of the level 1 cantrips for for Cleric in this case. 3 means that you get to choose 3, the other values haven't been deduced yet but AlwaysPrepared probably does what it says on the tin. AddSpells(269d1a3b-eed8-4131-8901-a562238f5289) is also an UUID into SpellLists.lsx, this is the Cleric level 1 spells.

The eighth attribute, TableUUID, is an UUID which essentially ties together everything for the progression. This is also a bit outside of the scope of this tutorial and something I haven't fully deduced, but the starting point is inside ClassDescriptions.lsx which associates a table with the general description for a class.

The ninth, UUID, is simply the unique identifier for this level up, if you want to override something you must have an identical UUID to it, and if you want to add something it in turn must have a freshly generated UUID.

Lastly we have a child structure which is merely an array of subclasses, if you want to add a new sub class copy the structure & change the UUID value, the UUID maps to an entry inside ClassDescriptions.lsx.

In addition to the base classes you'd expect there's also MulticlassSpellSlots, this seems to just be a placeholder which kicks in when you multiclass with spell casters to make sure they get extra spell slots dependent on general character level instead.


You might also run across an attribute with an id of AllowImprovement, adding this to a base class level & setting it to true makes sure that you get a feat for that level up.

Python example for working with .lsx

  • v
  • t
  • e

Modding homepage

Modding homepage
  • Modding homepage
Modding resources

Armor/Clothing Texture Maps

Body Models

Custom polymorph

Dependencies

Face and body textures

Fixing bone errors

Fixing neck seams

Fixing UV errors

Getting Started with BG3 Modding

Hair Meshes

Head Models

Mod troubleshooting

Modding class icons

NPC Head Models

Tiefling Horn Models

Non-VT Shaders

Race UUID

Sample Templates

Texture formatting

Tools

TreasureTables References

Tutorials

VertexColorMaskSlots

Working with LSX files

Modding guides

Blender Export Settings

Coding An Item

Compatibility Framework

Creating a custom cloth collider

Creating and Exporting Meshes in Blender

Creating Armor Mods

Creating Item Icons

Creating meta.lsx

Creating mods

Creating Outfit Textures

Editing a Character Creation Preset

Editing Equipment.txt

Hair Mod File Setup

Hair Mod Mesh Setup

Hotloading

How To Find A Virtual Texture

Installing mods

Localization

Packaging mods

Texture formatting

Unpacking and converting files

Working with LSX files

Hair modding

Creating Custom Hair with Hair Tool

Creating hair merged.lsf with custom texture

Creating meta.lsx

Custom Hair Highlights

Hair Meshes

Hair Mod File Setup

Hair Mod Mesh Setup

Head modding

Creating meta.lsx

Face and body textures

Fixing neck seams

Head Modding

Head Models

Head Troubleshooting

NPC Head Models

Armor/clothing modding

Armor/Clothing Texture Maps

Coding An Item

Creating and Exporting Meshes in Blender

Creating Armor Mods

Creating Item Icons

Creating meta.lsx

Fixing bone errors

How To Find A Virtual Texture

Texture formatting

TreasureTables References

Use Outfit Builder To Refit Outfits

VertexColorMaskSlots

Modding:Working with LSX files (2024)
Top Articles
Latest Posts
Article information

Author: Kimberely Baumbach CPA

Last Updated:

Views: 5878

Rating: 4 / 5 (61 voted)

Reviews: 92% of readers found this page helpful

Author information

Name: Kimberely Baumbach CPA

Birthday: 1996-01-14

Address: 8381 Boyce Course, Imeldachester, ND 74681

Phone: +3571286597580

Job: Product Banking Analyst

Hobby: Cosplaying, Inline skating, Amateur radio, Baton twirling, Mountaineering, Flying, Archery

Introduction: My name is Kimberely Baumbach CPA, I am a gorgeous, bright, charming, encouraging, zealous, lively, good person who loves writing and wants to share my knowledge and understanding with you.