public static string FormatValue(object v) { if (v == null) { return(""); } var t = v.GetType(); // Color.ToString() does the wrong thing; force it to format as rgb[a] hex if (t == typeof(Color)) { return(HSLColor.ToHexString((Color)v)); } // HSLColor.ToString() does the wrong thing; force it to format as rgb[a] hex if (t == typeof(HSLColor)) { return(((HSLColor)v).ToHexString()); } if (t == typeof(ImageFormat)) { return(((ImageFormat)v).ToString()); } if (t == typeof(Rectangle)) { var r = (Rectangle)v; return("{0},{1},{2},{3}".F(r.X, r.Y, r.Width, r.Height)); } if (t.IsArray && t.GetArrayRank() == 1) { return(((Array)v).Cast <object>().Select(FormatValue).JoinWith(", ")); } if (t.IsGenericType && t.GetGenericTypeDefinition() == typeof(HashSet <>)) { return(((System.Collections.IEnumerable)v).Cast <object>().Select(FormatValue).JoinWith(", ")); } // This is only for documentation generation if (t.IsGenericType && t.GetGenericTypeDefinition() == typeof(Dictionary <,>)) { var result = ""; var dict = (System.Collections.IDictionary)v; foreach (var kvp in dict) { var key = ((System.Collections.DictionaryEntry)kvp).Key; var value = ((System.Collections.DictionaryEntry)kvp).Value; var formattedKey = FormatValue(key); var formattedValue = FormatValue(value); result += "{0}: {1}{2}".F(formattedKey, formattedValue, Environment.NewLine); } return(result); } if (t.IsGenericType && t.GetGenericTypeDefinition() == typeof(Primitives.Cache <,>)) { return(""); // TODO } if (t == typeof(DateTime)) { return(((DateTime)v).ToString("yyyy-MM-dd HH-mm-ss", CultureInfo.InvariantCulture)); } // Try the TypeConverter var conv = TypeDescriptor.GetConverter(t); if (conv.CanConvertTo(typeof(string))) { try { return(conv.ConvertToInvariantString(v)); } catch { } } return(v.ToString()); }