Generate palette projections at module build; never extract them
ci / ci (pull_request) Successful in 3m44s

*palcus.itp files are Toolset-generated snapshots: category skeleton plus
one descriptor per custom blueprint. Treat them as derived data. Module
source now commits only descriptor-free skeletons; build strips any stale
descriptors and re-inserts descriptors computed from the blueprints in the
source tree (name/STRREF, resref, and CR/faction for creatures), so the
DM Creator lists always match what actually ships in the .mod. Compare
applies the same projection. Extract skips *palcus.itp entirely, so local
Toolset palette churn can no longer leak into module source.

Blueprints with PaletteID 255 (hidden) or no PaletteID are omitted, per
engine convention.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
2026-07-23 11:24:49 +02:00
co-authored by Claude Fable 5
parent 8e7cead5c0
commit 450c3ebc59
5 changed files with 513 additions and 2 deletions
+10 -2
View File
@@ -593,9 +593,14 @@ func envBool(name string) bool {
func collectModuleResources(p *project.Project, moduleHakOrder []string) ([]erf.Resource, error) {
var moduleResources []erf.Resource
palettes, err := collectPaletteDescriptors(p)
if err != nil {
return nil, err
}
for _, rel := range p.Inventory.SourceFiles {
abs := filepath.Join(p.SourceDir(), filepath.FromSlash(rel))
resource, err := resourceFromJSON(abs, moduleHakOrder)
resource, err := resourceFromJSON(abs, moduleHakOrder, palettes)
if err != nil {
return nil, err
}
@@ -1030,7 +1035,7 @@ func compareResourceKeys(a, b erf.Resource) int {
return 0
}
func resourceFromJSON(path string, moduleHakOrder []string) (erf.Resource, error) {
func resourceFromJSON(path string, moduleHakOrder []string, palettes paletteProjection) (erf.Resource, error) {
name, extension, err := splitSourceName(path)
if err != nil {
return erf.Resource{}, err
@@ -1059,6 +1064,9 @@ func resourceFromJSON(path string, moduleHakOrder []string) (erf.Resource, error
if extension == ".ifo" && name == "module" && len(moduleHakOrder) > 0 {
setModuleHAKList(&document, moduleHakOrder)
}
if extension == ".itp" && isPaletteProjectionResref(name) {
projectPaletteDocument(&document, palettes[strings.ToLower(name)])
}
var buf bytes.Buffer
if err := gff.Write(&buf, document); err != nil {