From 992ba1a9a2321fff7e5fb6af785603e99c168d93 Mon Sep 17 00:00:00 2001 From: Paul Chote Date: Mon, 6 Mar 2023 21:00:59 +0000 Subject: [PATCH] Remove HasEmbeddedPalette from sequences. --- .../Graphics/DefaultSpriteSequence.cs | 38 ------------- .../SpriteLoaders/EmbeddedSpritePalette.cs | 35 ++++++++++++ .../SpriteLoaders/PngSheetLoader.cs | 1 - .../PaletteFromEmbeddedSpritePalette.cs | 29 ++++++---- .../RemoveSequenceHasEmbeddedPalette.cs | 56 +++++++++++++++++++ OpenRA.Mods.Common/UpdateRules/UpdatePath.cs | 1 + OpenRA.Mods.D2k/SpriteLoaders/R8Loader.cs | 2 +- mods/d2k/rules/palettes.yaml | 8 +-- mods/d2k/sequences/misc.yaml | 5 -- 9 files changed, 114 insertions(+), 61 deletions(-) create mode 100644 OpenRA.Mods.Common/SpriteLoaders/EmbeddedSpritePalette.cs create mode 100644 OpenRA.Mods.Common/UpdateRules/Rules/20221203/RemoveSequenceHasEmbeddedPalette.cs diff --git a/OpenRA.Mods.Common/Graphics/DefaultSpriteSequence.cs b/OpenRA.Mods.Common/Graphics/DefaultSpriteSequence.cs index 5fb633c4fe..e89ed23827 100644 --- a/OpenRA.Mods.Common/Graphics/DefaultSpriteSequence.cs +++ b/OpenRA.Mods.Common/Graphics/DefaultSpriteSequence.cs @@ -19,26 +19,6 @@ using OpenRA.Primitives; namespace OpenRA.Mods.Common.Graphics { - public class EmbeddedSpritePalette - { - readonly uint[] filePalette = null; - readonly Dictionary framePalettes = null; - - public EmbeddedSpritePalette(uint[] filePalette = null, Dictionary framePalettes = null) - { - this.filePalette = filePalette; - this.framePalettes = framePalettes; - } - - public bool TryGetPaletteForFrame(int frame, out uint[] palette) - { - if (framePalettes == null || !framePalettes.TryGetValue(frame, out palette)) - palette = filePalette; - - return palette != null; - } - } - public class DefaultSpriteSequenceLoader : ISpriteSequenceLoader { static readonly MiniYaml NoData = new MiniYaml(null); @@ -256,11 +236,6 @@ namespace OpenRA.Mods.Common.Graphics [Desc("X, Y offset to apply to the depth sprite.")] static readonly SpriteSequenceField DepthSpriteOffset = new SpriteSequenceField(nameof(DepthSpriteOffset), float2.Zero); - [Desc("Make a custom palette embedded in the sprite available to the PaletteFromEmbeddedSpritePalette trait.")] - static readonly SpriteSequenceField HasEmbeddedPalette = new SpriteSequenceField(nameof(HasEmbeddedPalette), false); - - public readonly uint[] EmbeddedPalette; - protected virtual string GetSpriteFilename(ModData modData, string tileset, string image, string sequence, MiniYaml data, MiniYaml defaults) { return LoadField(Filename, data, defaults); @@ -502,19 +477,6 @@ namespace OpenRA.Mods.Common.Graphics }).ToArray(); } - if (LoadField(HasEmbeddedPalette, data, defaults)) - { - var filename = GetSpriteFilename(modData, tileSet, image, sequence, data, defaults); - if (filename == null) - throw new YamlException($"Sequence {image}.{sequence} does not define a filename."); - - var metadata = cache.FrameMetadata(filename); - var i = frames != null ? frames[0] : start; - var palettes = metadata?.GetOrDefault(); - if (palettes == null || !palettes.TryGetPaletteForFrame(i, out EmbeddedPalette)) - throw new YamlException($"Cannot export palette from {filename}: frame {i} does not define an embedded palette."); - } - var boundSprites = SpriteBounds(sprites, frames, start, facings, length, stride, transpose); if (shadowStart > 0) boundSprites = boundSprites.Concat(SpriteBounds(sprites, frames, shadowStart, facings, length, stride, transpose)); diff --git a/OpenRA.Mods.Common/SpriteLoaders/EmbeddedSpritePalette.cs b/OpenRA.Mods.Common/SpriteLoaders/EmbeddedSpritePalette.cs new file mode 100644 index 0000000000..0079f67e4e --- /dev/null +++ b/OpenRA.Mods.Common/SpriteLoaders/EmbeddedSpritePalette.cs @@ -0,0 +1,35 @@ +#region Copyright & License Information +/* + * Copyright (c) The OpenRA Developers and Contributors + * This file is part of OpenRA, which is free software. It is made + * available to you under the terms of the GNU General Public License + * as published by the Free Software Foundation, either version 3 of + * the License, or (at your option) any later version. For more + * information, see COPYING. + */ +#endregion + +using System.Collections.Generic; + +namespace OpenRA.Mods.Common.SpriteLoaders +{ + public class EmbeddedSpritePalette + { + readonly uint[] filePalette; + readonly Dictionary framePalettes; + + public EmbeddedSpritePalette(uint[] filePalette = null, Dictionary framePalettes = null) + { + this.filePalette = filePalette; + this.framePalettes = framePalettes; + } + + public bool TryGetPaletteForFrame(int frame, out uint[] palette) + { + if (framePalettes == null || !framePalettes.TryGetValue(frame, out palette)) + palette = filePalette; + + return palette != null; + } + } +} diff --git a/OpenRA.Mods.Common/SpriteLoaders/PngSheetLoader.cs b/OpenRA.Mods.Common/SpriteLoaders/PngSheetLoader.cs index fb2f87d3f8..05e1e518ec 100644 --- a/OpenRA.Mods.Common/SpriteLoaders/PngSheetLoader.cs +++ b/OpenRA.Mods.Common/SpriteLoaders/PngSheetLoader.cs @@ -16,7 +16,6 @@ using System.IO; using System.Linq; using OpenRA.FileFormats; using OpenRA.Graphics; -using OpenRA.Mods.Common.Graphics; using OpenRA.Primitives; namespace OpenRA.Mods.Common.SpriteLoaders diff --git a/OpenRA.Mods.Common/Traits/Palettes/PaletteFromEmbeddedSpritePalette.cs b/OpenRA.Mods.Common/Traits/Palettes/PaletteFromEmbeddedSpritePalette.cs index cf2ad3361e..8918f672b1 100644 --- a/OpenRA.Mods.Common/Traits/Palettes/PaletteFromEmbeddedSpritePalette.cs +++ b/OpenRA.Mods.Common/Traits/Palettes/PaletteFromEmbeddedSpritePalette.cs @@ -10,10 +10,9 @@ #endregion using System.Collections.Generic; -using System.Linq; using OpenRA.FileSystem; using OpenRA.Graphics; -using OpenRA.Mods.Common.Graphics; +using OpenRA.Mods.Common.SpriteLoaders; using OpenRA.Traits; namespace OpenRA.Mods.Common.Traits @@ -27,13 +26,11 @@ namespace OpenRA.Mods.Common.Traits public readonly string Name = null; [FieldLoader.Require] - [Desc("Sequence image holding the palette definition")] - public readonly string Image = null; + [Desc("Filename of sprite that contains the palette definition.")] + public readonly string Filename = null; - [FieldLoader.Require] - [SequenceReference(nameof(Image))] - [Desc("Sequence holding the palette definition")] - public readonly string Sequence = null; + [Desc("Image frame associated with the palette definition, if relevant.")] + public readonly int Frame = 0; [Desc("Allow palette modifiers to change the palette.")] public readonly bool AllowModifiers = true; @@ -47,8 +44,12 @@ namespace OpenRA.Mods.Common.Traits ImmutablePalette IProvidesCursorPaletteInfo.ReadPalette(IReadOnlyFileSystem fileSystem) { - var sequence = (DefaultSpriteSequence)Game.ModData.DefaultSequences.Values.First().GetSequence(Image, Sequence); - return new ImmutablePalette(sequence.EmbeddedPalette); + FrameLoader.GetFrames(fileSystem, Filename, Game.ModData.SpriteLoaders, out var metadata); + var palettes = metadata?.GetOrDefault(); + if (palettes == null || !palettes.TryGetPaletteForFrame(Frame, out var embeddedPalette)) + throw new YamlException($"Cannot export palette from {Filename}: frame {Frame} does not define an embedded palette"); + + return new ImmutablePalette(embeddedPalette); } } @@ -59,8 +60,12 @@ namespace OpenRA.Mods.Common.Traits public void LoadPalettes(WorldRenderer wr) { - var sequence = (DefaultSpriteSequence)wr.World.Map.Rules.Sequences.GetSequence(info.Image, info.Sequence); - wr.AddPalette(info.Name, new ImmutablePalette(sequence.EmbeddedPalette), info.AllowModifiers); + FrameLoader.GetFrames(wr.World.Map, info.Filename, Game.ModData.SpriteLoaders, out var metadata); + var palettes = metadata?.GetOrDefault(); + if (palettes == null || !palettes.TryGetPaletteForFrame(info.Frame, out var embeddedPalette)) + throw new YamlException($"Cannot export palette from {info.Filename}: frame {info.Frame} does not define an embedded palette"); + + wr.AddPalette(info.Name, new ImmutablePalette(embeddedPalette), info.AllowModifiers); } public IEnumerable PaletteNames { get { yield return info.Name; } } diff --git a/OpenRA.Mods.Common/UpdateRules/Rules/20221203/RemoveSequenceHasEmbeddedPalette.cs b/OpenRA.Mods.Common/UpdateRules/Rules/20221203/RemoveSequenceHasEmbeddedPalette.cs new file mode 100644 index 0000000000..f2f9bb7347 --- /dev/null +++ b/OpenRA.Mods.Common/UpdateRules/Rules/20221203/RemoveSequenceHasEmbeddedPalette.cs @@ -0,0 +1,56 @@ +#region Copyright & License Information +/* + * Copyright (c) The OpenRA Developers and Contributors + * This file is part of OpenRA, which is free software. It is made + * available to you under the terms of the GNU General Public License + * as published by the Free Software Foundation, either version 3 of + * the License, or (at your option) any later version. For more + * information, see COPYING. + */ +#endregion + +using System.Collections.Generic; + +namespace OpenRA.Mods.Common.UpdateRules.Rules +{ + public class RemoveSequenceHasEmbeddedPalette : UpdateRule + { + public override string Name => "Remove sequence HasEmbeddedPalette property."; + + public override string Description => + "The PaletteFromEmbeddedSpritePalette trait no longer references a sequence.\n" + + "Image and Sequence are replaced by Filename and Frame."; + + readonly HashSet locations = new HashSet(); + + public override IEnumerable AfterUpdate(ModData modData) + { + if (locations.Count > 0) + yield return "The PaletteFromEmbeddedSpritePalette trait no longer references a sequence.\n" + + "You must manually define Filename (and Frame if needed) on the following actors:\n" + + UpdateUtils.FormatMessageList(locations); + + locations.Clear(); + } + + public override IEnumerable UpdateSequenceNode(ModData modData, MiniYamlNode imageNode) + { + foreach (var sequenceNode in imageNode.Value.Nodes) + sequenceNode.RemoveNodes("HasEmbeddedPalette"); + + yield break; + } + + public override IEnumerable UpdateActorNode(ModData modData, MiniYamlNode actorNode) + { + foreach (var traitNode in actorNode.ChildrenMatching("PaletteFromEmbeddedSpritePalette")) + { + traitNode.RemoveNodes("Image"); + traitNode.RemoveNodes("Sequence"); + locations.Add($"{actorNode.Key} ({actorNode.Location.Filename})"); + } + + yield break; + } + } +} diff --git a/OpenRA.Mods.Common/UpdateRules/UpdatePath.cs b/OpenRA.Mods.Common/UpdateRules/UpdatePath.cs index 4d147fc582..928e988716 100644 --- a/OpenRA.Mods.Common/UpdateRules/UpdatePath.cs +++ b/OpenRA.Mods.Common/UpdateRules/UpdatePath.cs @@ -95,6 +95,7 @@ namespace OpenRA.Mods.Common.UpdateRules new ProductionTabsWidgetAddTabButtonCollection(), new RemoveTSRefinery(), new RenameMcvCrateAction(), + new RemoveSequenceHasEmbeddedPalette(), }) }; diff --git a/OpenRA.Mods.D2k/SpriteLoaders/R8Loader.cs b/OpenRA.Mods.D2k/SpriteLoaders/R8Loader.cs index b59519f134..ace673c48c 100644 --- a/OpenRA.Mods.D2k/SpriteLoaders/R8Loader.cs +++ b/OpenRA.Mods.D2k/SpriteLoaders/R8Loader.cs @@ -12,7 +12,7 @@ using System.Collections.Generic; using System.IO; using OpenRA.Graphics; -using OpenRA.Mods.Common.Graphics; +using OpenRA.Mods.Common.SpriteLoaders; using OpenRA.Primitives; namespace OpenRA.Mods.D2k.SpriteLoaders diff --git a/mods/d2k/rules/palettes.yaml b/mods/d2k/rules/palettes.yaml index 2ae100dd4a..3cafaf843e 100644 --- a/mods/d2k/rules/palettes.yaml +++ b/mods/d2k/rules/palettes.yaml @@ -24,8 +24,8 @@ AllowModifiers: false PaletteFromEmbeddedSpritePalette@moveflash-base: Name: moveflash-base - Image: moveflsh - Sequence: idle + Filename: DATA.R8 + Frame: 3874 PaletteFromScaledPalette@moveflash: Name: moveflash BasePalette: moveflash-base @@ -47,8 +47,8 @@ Offset: -64 PaletteFromEmbeddedSpritePalette@shroud: Name: shroud - Image: shroud - Sequence: palette + Filename: DATA.R8 + Frame: 38 D2kFogPalette@fog: Name: fog BasePalette: shroud diff --git a/mods/d2k/sequences/misc.yaml b/mods/d2k/sequences/misc.yaml index 829d86caa4..816c9ce734 100644 --- a/mods/d2k/sequences/misc.yaml +++ b/mods/d2k/sequences/misc.yaml @@ -534,7 +534,6 @@ moveflsh: Tick: 80 BlendMode: Multiply ZOffset: 2047 - HasEmbeddedPalette: True resources: spicea: @@ -563,10 +562,6 @@ shroud: BlendMode: Subtractive Offset: -16,-16 Length: 14 - palette: - Filename: DATA.R8 - Start: 38 - HasEmbeddedPalette: True shrouda: Filename: DATA.R8 Start: 40