using System.Diagnostics.CodeAnalysis; using System.Text.Json; using System.Text.Json.Serialization; namespace Terminal.Gui.Configuration; /// Json converter from the class. [RequiresUnreferencedCode ("AOT")] internal class AttributeJsonConverter : JsonConverter { private static AttributeJsonConverter? _instance; /// public static AttributeJsonConverter Instance { get { if (_instance is null) { _instance = new AttributeJsonConverter (); } return _instance; } } public override Attribute Read (ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options) { if (reader.TokenType != JsonTokenType.StartObject) { throw new JsonException ($"Unexpected StartObject token when parsing Attribute: {reader.TokenType}."); } var attribute = new Attribute (); Color? foreground = null; Color? background = null; TextStyle? style = null; string propertyName = string.Empty; while (reader.Read ()) { if (reader.TokenType == JsonTokenType.EndObject) { if (foreground is null || background is null) { throw new JsonException ($"{propertyName}: Both Foreground and Background colors must be provided."); } if (style.HasValue) { return new Attribute (foreground.Value, background.Value, style.Value); } else { return new Attribute (foreground.Value, background.Value); } } if (reader.TokenType != JsonTokenType.PropertyName) { throw new JsonException ($"{propertyName}: Unexpected token when parsing Attribute: {reader.TokenType}."); } propertyName = reader.GetString ()!; reader.Read (); var property = $"\"{reader.GetString ()}\""; try { switch (propertyName?.ToLower ()) { case "foreground": foreground = JsonSerializer.Deserialize (property, ConfigurationManager.SerializerContext.Color); break; case "background": background = JsonSerializer.Deserialize (property, ConfigurationManager.SerializerContext.Color); break; case "style": style = JsonSerializer.Deserialize (property, ConfigurationManager.SerializerContext.TextStyle); break; default: throw new JsonException ($"{propertyName}: Unknown Attribute property ."); } } catch (JsonException ex) { throw new JsonException ($"{propertyName}: \"{property}\" - {ex.Message}"); } } throw new JsonException ($"{propertyName}: Bad Attribute."); } public override void Write (Utf8JsonWriter writer, Attribute value, JsonSerializerOptions options) { writer.WriteStartObject (); writer.WritePropertyName (nameof (Attribute.Foreground)); ColorJsonConverter.Instance.Write (writer, value.Foreground, options); writer.WritePropertyName (nameof (Attribute.Background)); ColorJsonConverter.Instance.Write (writer, value.Background, options); if (value.Style != TextStyle.None) { writer.WritePropertyName (nameof (Attribute.Style)); JsonSerializer.Serialize (writer, value.Style, ConfigurationManager.SerializerContext.TextStyle); } writer.WriteEndObject (); } }