diff --git a/SabreTools.Library/DatFiles/Listxml.cs b/SabreTools.Library/DatFiles/Listxml.cs index 7a9f4972..1ae2c859 100644 --- a/SabreTools.Library/DatFiles/Listxml.cs +++ b/SabreTools.Library/DatFiles/Listxml.cs @@ -205,7 +205,7 @@ namespace SabreTools.Library.DatFiles { Name = reader.GetAttribute("name"), Tag = reader.GetAttribute("tag"), - ChipType = reader.GetAttribute("type"), + ChipType = reader.GetAttribute("type").AsChipType(), Clock = reader.GetAttribute("clock"), Source = new Source @@ -293,8 +293,8 @@ namespace SabreTools.Library.DatFiles datItems.Add(new Feature { Type = reader.GetAttribute("type").AsFeatureType(), - Status = reader.GetAttribute("status"), - Overall = reader.GetAttribute("overall"), + Status = reader.GetAttribute("status").AsEmulationStatus(), + Overall = reader.GetAttribute("overall").AsEmulationStatus(), }); reader.Read(); @@ -1441,7 +1441,7 @@ namespace SabreTools.Library.DatFiles xtw.WriteStartElement("chip"); xtw.WriteRequiredAttributeString("name", chip.Name); xtw.WriteOptionalAttributeString("tag", chip.Tag); - xtw.WriteOptionalAttributeString("type", chip.ChipType); + xtw.WriteOptionalAttributeString("type", chip.ChipType.FromChipType()); xtw.WriteOptionalAttributeString("clock", chip.Clock); xtw.WriteEndElement(); break; @@ -1570,8 +1570,8 @@ namespace SabreTools.Library.DatFiles var feature = datItem as Feature; xtw.WriteStartElement("feature"); xtw.WriteOptionalAttributeString("type", feature.Type.FromFeatureType()); - xtw.WriteOptionalAttributeString("status", feature.Status); - xtw.WriteOptionalAttributeString("overall", feature.Overall); + xtw.WriteOptionalAttributeString("status", feature.Status.FromEmulationStatus()); + xtw.WriteOptionalAttributeString("overall", feature.Overall.FromEmulationStatus()); xtw.WriteEndElement(); break; diff --git a/SabreTools.Library/DatFiles/SabreDat.cs b/SabreTools.Library/DatFiles/SabreDat.cs index f68ff5d5..228eff48 100644 --- a/SabreTools.Library/DatFiles/SabreDat.cs +++ b/SabreTools.Library/DatFiles/SabreDat.cs @@ -399,7 +399,7 @@ namespace SabreTools.Library.DatFiles { Name = reader.GetAttribute("name"), Tag = reader.GetAttribute("tag"), - ChipType = reader.GetAttribute("chiptype"), + ChipType = reader.GetAttribute("chiptype").AsChipType(), Clock = reader.GetAttribute("clock"), Source = new Source @@ -1253,7 +1253,7 @@ namespace SabreTools.Library.DatFiles xtw.WriteAttributeString("type", "chip"); xtw.WriteRequiredAttributeString("name", chip.Name); xtw.WriteOptionalAttributeString("tag", chip.Tag); - xtw.WriteOptionalAttributeString("chiptype", chip.ChipType); + xtw.WriteOptionalAttributeString("chiptype", chip.ChipType.FromChipType()); xtw.WriteOptionalAttributeString("clock", chip.Clock); xtw.WriteEndElement(); break; @@ -1394,8 +1394,8 @@ namespace SabreTools.Library.DatFiles xtw.WriteStartElement("file"); xtw.WriteAttributeString("type", "feature"); xtw.WriteOptionalAttributeString("type", feature.Type.FromFeatureType()); - xtw.WriteOptionalAttributeString("status", feature.Status); - xtw.WriteOptionalAttributeString("overall", feature.Overall); + xtw.WriteOptionalAttributeString("status", feature.Status.FromEmulationStatus()); + xtw.WriteOptionalAttributeString("overall", feature.Overall.FromEmulationStatus()); xtw.WriteEndElement(); break; diff --git a/SabreTools.Library/DatItems/Adjuster.cs b/SabreTools.Library/DatItems/Adjuster.cs index 0152db3a..12d2f83f 100644 --- a/SabreTools.Library/DatItems/Adjuster.cs +++ b/SabreTools.Library/DatItems/Adjuster.cs @@ -31,7 +31,7 @@ namespace SabreTools.Library.DatItems /// /// Conditions associated with the adjustment /// - [JsonProperty("conditions")] + [JsonProperty("conditions", DefaultValueHandling = DefaultValueHandling.Ignore)] public List Conditions { get; set; } #endregion diff --git a/SabreTools.Library/DatItems/Chip.cs b/SabreTools.Library/DatItems/Chip.cs index 5caae13c..9ea35ba7 100644 --- a/SabreTools.Library/DatItems/Chip.cs +++ b/SabreTools.Library/DatItems/Chip.cs @@ -5,6 +5,7 @@ using System.Linq; using SabreTools.Library.Filtering; using SabreTools.Library.Tools; using Newtonsoft.Json; +using Newtonsoft.Json.Converters; namespace SabreTools.Library.DatItems { @@ -25,19 +26,20 @@ namespace SabreTools.Library.DatItems /// /// Internal tag /// - [JsonProperty("tag")] + [JsonProperty("tag", DefaultValueHandling = DefaultValueHandling.Ignore)] public string Tag { get; set; } /// /// Type of the chip /// - [JsonProperty("chiptype")] - public string ChipType { get; set; } // TODO: (cpu|audio) + [JsonProperty("chiptype", DefaultValueHandling = DefaultValueHandling.Ignore)] + [JsonConverter(typeof(StringEnumConverter))] + public ChipType ChipType { get; set; } /// /// Clock speed /// - [JsonProperty("clock")] + [JsonProperty("clock", DefaultValueHandling = DefaultValueHandling.Ignore)] public string Clock { get; set; } #endregion @@ -70,7 +72,7 @@ namespace SabreTools.Library.DatItems Tag = mappings[Field.DatItem_Tag]; if (mappings.Keys.Contains(Field.DatItem_ChipType)) - ChipType = mappings[Field.DatItem_ChipType]; + ChipType = mappings[Field.DatItem_ChipType].AsChipType(); if (mappings.Keys.Contains(Field.DatItem_Clock)) Clock = mappings[Field.DatItem_Clock]; @@ -204,9 +206,9 @@ namespace SabreTools.Library.DatItems return false; // DatItem_ChipType - if (filter.DatItem_ChipType.MatchesPositiveSet(ChipType) == false) + if (filter.DatItem_ChipType.MatchesPositive(ChipType.NULL, ChipType) == false) return false; - if (filter.DatItem_ChipType.MatchesNegativeSet(ChipType) == true) + if (filter.DatItem_ChipType.MatchesNegative(ChipType.NULL, ChipType) == true) return false; // DatItem_Clock @@ -235,7 +237,7 @@ namespace SabreTools.Library.DatItems Tag = null; if (fields.Contains(Field.DatItem_ChipType)) - ChipType = null; + ChipType = ChipType.NULL; if (fields.Contains(Field.DatItem_Clock)) Clock = null; diff --git a/SabreTools.Library/DatItems/Configuration.cs b/SabreTools.Library/DatItems/Configuration.cs index 15074105..b5e694a4 100644 --- a/SabreTools.Library/DatItems/Configuration.cs +++ b/SabreTools.Library/DatItems/Configuration.cs @@ -37,19 +37,19 @@ namespace SabreTools.Library.DatItems /// /// Conditions associated with the configuration /// - [JsonProperty("conditions")] + [JsonProperty("conditions", DefaultValueHandling = DefaultValueHandling.Ignore)] public List Conditions { get; set; } /// /// Locations associated with the configuration /// - [JsonProperty("locations")] + [JsonProperty("locations", DefaultValueHandling = DefaultValueHandling.Ignore)] public List Locations { get; set; } /// /// Settings associated with the configuration /// - [JsonProperty("settings")] + [JsonProperty("settings", DefaultValueHandling = DefaultValueHandling.Ignore)] public List Settings { get; set; } #endregion diff --git a/SabreTools.Library/DatItems/DipSwitch.cs b/SabreTools.Library/DatItems/DipSwitch.cs index f990cd5d..5f764018 100644 --- a/SabreTools.Library/DatItems/DipSwitch.cs +++ b/SabreTools.Library/DatItems/DipSwitch.cs @@ -37,19 +37,19 @@ namespace SabreTools.Library.DatItems /// /// Conditions associated with the dipswitch /// - [JsonProperty("conditions")] + [JsonProperty("conditions", DefaultValueHandling = DefaultValueHandling.Ignore)] public List Conditions { get; set; } /// /// Locations associated with the dipswitch /// - [JsonProperty("locations")] + [JsonProperty("locations", DefaultValueHandling = DefaultValueHandling.Ignore)] public List Locations { get; set; } /// /// Settings associated with the dipswitch /// - [JsonProperty("values")] + [JsonProperty("values", DefaultValueHandling = DefaultValueHandling.Ignore)] public List Values { get; set; } #endregion diff --git a/SabreTools.Library/DatItems/Enums.cs b/SabreTools.Library/DatItems/Enums.cs index 50acafb3..17f3f17d 100644 --- a/SabreTools.Library/DatItems/Enums.cs +++ b/SabreTools.Library/DatItems/Enums.cs @@ -2,6 +2,22 @@ namespace SabreTools.Library.DatItems { + /// + /// Determine the chip type + /// + [Flags] + public enum ChipType + { + /// + /// This is a fake flag that is used for filter only + /// + NULL = 0, + + // TODO: (cpu|audio) + CPU = 1 << 0, + Audio = 1 << 1, + } + /// /// Determines which type of duplicate a file is /// @@ -17,6 +33,21 @@ namespace SabreTools.Library.DatItems External = 1 << 3, } + /// + /// Determine the emulation status + /// + [Flags] + public enum EmulationStatus + { + /// + /// This is a fake flag that is used for filter only + /// + NULL = 0, + + Unemulated = 1 << 0, + Imperfect = 1 << 1, + } + /// /// Determine the feature type /// diff --git a/SabreTools.Library/DatItems/Feature.cs b/SabreTools.Library/DatItems/Feature.cs index 5cee5d39..811e4d65 100644 --- a/SabreTools.Library/DatItems/Feature.cs +++ b/SabreTools.Library/DatItems/Feature.cs @@ -2,8 +2,9 @@ using System.Linq; using SabreTools.Library.Filtering; -using Newtonsoft.Json; using SabreTools.Library.Tools; +using Newtonsoft.Json; +using Newtonsoft.Json.Converters; namespace SabreTools.Library.DatItems { @@ -18,20 +19,23 @@ namespace SabreTools.Library.DatItems /// /// Type of feature /// - [JsonProperty("type")] + [JsonProperty("type", DefaultValueHandling = DefaultValueHandling.Ignore)] + [JsonConverter(typeof(StringEnumConverter))] public FeatureType Type { get; set; } /// /// Emulation status /// - [JsonProperty("status")] - public string Status { get; set; } // TODO: (unemulated|imperfect) + [JsonProperty("status", DefaultValueHandling = DefaultValueHandling.Ignore)] + [JsonConverter(typeof(StringEnumConverter))] + public EmulationStatus Status { get; set; } /// /// Overall status /// - [JsonProperty("overall")] - public string Overall { get; set; } // TODO: (unemulated|imperfect) + [JsonProperty("overall", DefaultValueHandling = DefaultValueHandling.Ignore)] + [JsonConverter(typeof(StringEnumConverter))] + public EmulationStatus Overall { get; set; } #endregion @@ -51,10 +55,10 @@ namespace SabreTools.Library.DatItems Type = mappings[Field.DatItem_FeatureType].AsFeatureType(); if (mappings.Keys.Contains(Field.DatItem_FeatureStatus)) - Status = mappings[Field.DatItem_FeatureStatus]; + Status = mappings[Field.DatItem_FeatureStatus].AsEmulationStatus(); if (mappings.Keys.Contains(Field.DatItem_FeatureOverall)) - Overall = mappings[Field.DatItem_FeatureOverall]; + Overall = mappings[Field.DatItem_FeatureOverall].AsEmulationStatus(); } #endregion @@ -147,15 +151,15 @@ namespace SabreTools.Library.DatItems return false; // Filter on status - if (filter.DatItem_FeatureStatus.MatchesPositiveSet(Status) == false) + if (filter.DatItem_FeatureStatus.MatchesPositive(EmulationStatus.NULL, Status) == false) return false; - if (filter.DatItem_FeatureStatus.MatchesNegativeSet(Status) == true) + if (filter.DatItem_FeatureStatus.MatchesNegative(EmulationStatus.NULL, Status) == true) return false; // Filter on overall - if (filter.DatItem_FeatureOverall.MatchesPositiveSet(Overall) == false) + if (filter.DatItem_FeatureOverall.MatchesPositive(EmulationStatus.NULL, Overall) == false) return false; - if (filter.DatItem_FeatureOverall.MatchesNegativeSet(Overall) == true) + if (filter.DatItem_FeatureOverall.MatchesNegative(EmulationStatus.NULL, Overall) == true) return false; return true; @@ -175,10 +179,10 @@ namespace SabreTools.Library.DatItems Type = FeatureType.NULL; if (fields.Contains(Field.DatItem_FeatureStatus)) - Status = null; + Status = EmulationStatus.NULL; if (fields.Contains(Field.DatItem_FeatureOverall)) - Overall = null; + Overall = EmulationStatus.NULL; } #endregion diff --git a/SabreTools.Library/DatItems/Slot.cs b/SabreTools.Library/DatItems/Slot.cs index 84d4685b..64e529ec 100644 --- a/SabreTools.Library/DatItems/Slot.cs +++ b/SabreTools.Library/DatItems/Slot.cs @@ -25,7 +25,7 @@ namespace SabreTools.Library.DatItems /// /// Slot options associated with the slot /// - [JsonProperty("slotoptions")] + [JsonProperty("slotoptions", DefaultValueHandling = DefaultValueHandling.Ignore)] public List SlotOptions { get; set; } #endregion diff --git a/SabreTools.Library/DatItems/SoftwareList.cs b/SabreTools.Library/DatItems/SoftwareList.cs index 91242fc2..3b24806f 100644 --- a/SabreTools.Library/DatItems/SoftwareList.cs +++ b/SabreTools.Library/DatItems/SoftwareList.cs @@ -5,6 +5,7 @@ using System.Linq; using SabreTools.Library.Filtering; using SabreTools.Library.Tools; using Newtonsoft.Json; +using Newtonsoft.Json.Converters; namespace SabreTools.Library.DatItems { @@ -26,6 +27,7 @@ namespace SabreTools.Library.DatItems /// Status of the softare list according to the machine /// [JsonProperty("status", DefaultValueHandling = DefaultValueHandling.Ignore)] + [JsonConverter(typeof(StringEnumConverter))] public SoftwareListStatus Status { get; set; } /// diff --git a/SabreTools.Library/DatItems/Sound.cs b/SabreTools.Library/DatItems/Sound.cs index 16d9bb6c..78cba145 100644 --- a/SabreTools.Library/DatItems/Sound.cs +++ b/SabreTools.Library/DatItems/Sound.cs @@ -17,7 +17,7 @@ namespace SabreTools.Library.DatItems /// /// Number of channels /// - [JsonProperty("channels")] + [JsonProperty("channels", DefaultValueHandling = DefaultValueHandling.Ignore)] public string Channels { get; set; } // TODO: Int32? #endregion diff --git a/SabreTools.Library/Filtering/Filter.cs b/SabreTools.Library/Filtering/Filter.cs index 4953124d..546edb3e 100644 --- a/SabreTools.Library/Filtering/Filter.cs +++ b/SabreTools.Library/Filtering/Filter.cs @@ -270,7 +270,7 @@ namespace SabreTools.Library.Filtering // Chip public FilterItem DatItem_Tag { get; private set; } = new FilterItem(); - public FilterItem DatItem_ChipType { get; private set; } = new FilterItem(); + public FilterItem DatItem_ChipType { get; private set; } = new FilterItem() { Positive = ChipType.NULL, Negative = ChipType.NULL }; public FilterItem DatItem_Clock { get; private set; } = new FilterItem(); // Configuration @@ -296,8 +296,8 @@ namespace SabreTools.Library.Filtering // Feature public FilterItem DatItem_FeatureType { get; private set; } = new FilterItem() { Positive = FeatureType.NULL, Negative = FeatureType.NULL }; - public FilterItem DatItem_FeatureStatus { get; private set; } = new FilterItem(); - public FilterItem DatItem_FeatureOverall { get; private set; } = new FilterItem(); + public FilterItem DatItem_FeatureStatus { get; private set; } = new FilterItem() { Positive = EmulationStatus.NULL, Negative = EmulationStatus.NULL }; + public FilterItem DatItem_FeatureOverall { get; private set; } = new FilterItem() { Positive = EmulationStatus.NULL, Negative = EmulationStatus.NULL }; // Ram Option @@ -1590,9 +1590,9 @@ namespace SabreTools.Library.Filtering case Field.DatItem_ChipType: if (negate) - DatItem_ChipType.NegativeSet.Add(value); + DatItem_ChipType.Negative |= value.AsChipType(); else - DatItem_ChipType.PositiveSet.Add(value); + DatItem_ChipType.Positive |= value.AsChipType(); break; case Field.DatItem_Clock: @@ -1707,16 +1707,16 @@ namespace SabreTools.Library.Filtering case Field.DatItem_FeatureStatus: if (negate) - DatItem_FeatureStatus.NegativeSet.Add(value); + DatItem_FeatureStatus.Negative |= value.AsEmulationStatus(); else - DatItem_FeatureStatus.PositiveSet.Add(value); + DatItem_FeatureStatus.Positive |= value.AsEmulationStatus(); break; case Field.DatItem_FeatureOverall: if (negate) - DatItem_FeatureOverall.NegativeSet.Add(value); + DatItem_FeatureOverall.Negative |= value.AsEmulationStatus(); else - DatItem_FeatureOverall.PositiveSet.Add(value); + DatItem_FeatureOverall.Positive |= value.AsEmulationStatus(); break; // Ram Option diff --git a/SabreTools.Library/Tools/Converters.cs b/SabreTools.Library/Tools/Converters.cs index ffb45f72..5b2aa280 100644 --- a/SabreTools.Library/Tools/Converters.cs +++ b/SabreTools.Library/Tools/Converters.cs @@ -66,6 +66,33 @@ namespace SabreTools.Library.Tools #region String to Enum + /// + /// Get ChipType value from input string + /// + /// String to get value from + /// ChipType value corresponding to the string + public static ChipType AsChipType(this string chipType) + { +#if NET_FRAMEWORK + switch (chipType?.ToLowerInvariant()) + { + case "cpu": + return ChipType.CPU; + case "audio": + return ChipType.Audio; + default: + return ChipType.NULL; + } +#else + return chipType?.ToLowerInvariant() switch + { + "cpu" => ChipType.CPU, + "audio" => ChipType.Audio, + _ => ChipType.NULL, + }; +#endif + } + /// /// Get DatFormat value from input string /// @@ -145,10 +172,37 @@ namespace SabreTools.Library.Tools } } + /// + /// Get EmulationStatus value from input string + /// + /// String to get value from + /// EmulationStatus value corresponding to the string + public static EmulationStatus AsEmulationStatus(this string emulationStatus) + { +#if NET_FRAMEWORK + switch (emulationStatus?.ToLowerInvariant()) + { + case "unemulated": + return EmulationStatus.Unemulated; + case "imperfect": + return EmulationStatus.Imperfect; + default: + return EmulationStatus.NULL; + } +#else + return emulationStatus?.ToLowerInvariant() switch + { + "unemulated" => EmulationStatus.Unemulated, + "imperfect" => EmulationStatus.Imperfect, + _ => EmulationStatus.NULL, + }; +#endif + } + /// /// Get FeatureType value from input string /// - /// String to get value from + /// String to get value from /// FeatureType value corresponding to the string public static FeatureType AsFeatureType(this string featureType) { @@ -2018,6 +2072,60 @@ namespace SabreTools.Library.Tools // TODO: DatFormat -> string // TODO: Field -> string + /// + /// Get string value from input ChipType + /// + /// ChipType to get value from + /// String value corresponding to the ChipType + public static string FromChipType(this ChipType chipType) + { +#if NET_FRAMEWORK + switch (chipType) + { + case ChipType.CPU: + return "cpu"; + case ChipType.Audio: + return "audio"; + default: + return null; + } +#else + return chipType switch + { + ChipType.CPU => "cpu", + ChipType.Audio => "audio", + _ => null, + }; +#endif + } + + /// + /// Get string value from input EmulationStatus + /// + /// EmulationStatus to get value from + /// String value corresponding to the EmulationStatus + public static string FromEmulationStatus(this EmulationStatus emulationStatus) + { +#if NET_FRAMEWORK + switch (emulationStatus) + { + case EmulationStatus.Unemulated: + return "unemulated"; + case EmulationStatus.Imperfect: + return "imperfect"; + default: + return null; + } +#else + return emulationStatus switch + { + EmulationStatus.Unemulated => "unemulated", + EmulationStatus.Imperfect => "imperfect", + _ => null, + }; +#endif + } + /// /// Get string value from input FeatureType ///