using System; using System.ComponentModel; using System.Drawing; using System.IO; using System.Runtime.Serialization.Formatters.Binary; using System.Security; using System.Text.RegularExpressions; using System.Windows.Forms; using DevComponents.DotNetBar.Charts.Style; namespace DevComponents.DotNetBar.Charts { #region XmlSerializableFont static public class XmlSerializableFont { static public string ConvertToString(Font font) { if (font != null) { TypeConverter converter = TypeDescriptor.GetConverter(typeof(Font)); return (converter.ConvertToString(font)); } return (null); } static public Font ConvertFromString(string fontString) { TypeConverter converter = TypeDescriptor.GetConverter(typeof(Font)); Font font = (Font)converter.ConvertFromString(fontString); return (font); } } #endregion #region XmlSerializableImageList static public class XmlSerializableImageList { static public string ConvertToString(ImageList list) { TypeConverter converter = TypeDescriptor.GetConverter(typeof(ImageList)); return (converter.ConvertToString(list)); } static public ImageList ConvertFromString(string listString) { TypeConverter converter = TypeDescriptor.GetConverter(typeof(ImageList)); ImageList list = (ImageList)converter.ConvertFromString(listString); return (list); } } #endregion #region SerialElementCollection public delegate void Pv(SerialElement se); public delegate void Pc(SerialElement se); public class SerialElementCollection : CustomCollection { #region Private variables private int _ReadIndex = -1; private SerialElement _ReadSe; private string _Name; private int _ValueIndex; #endregion #region Internal properties #region Eof internal bool Eof { get { return (_ReadIndex >= Count); } } #endregion #region Name internal string Name { get { return (_Name); } set { _Name = value; } } #endregion #region ReadIndex internal int ReadIndex { get { return (_ReadIndex); } set { _ReadIndex = value; } } #endregion #region ReadSe internal SerialElement ReadSe { get { return (_ReadSe); } } #endregion #endregion #region AddStartElement /// /// Adds a 'Start' element to the collection. /// /// /// public SerialElement AddStartElement(string name) { SerialElement se = new SerialElement(SerElementType.Start, name); Items.Add(se); return (se); } #endregion #region AddEndElement /// /// Adds an 'End' element to the collection. /// /// /// public SerialElement AddEndElement(string name) { SerialElement se = new SerialElement(SerElementType.End, name); Items.Add(se); return (se); } #endregion #region AddValue /// /// Adds the given object element to the collection. /// /// /// public SerialElement AddValue(object value) { SerialElement se = new SerialElement(null, value); Items.Add(se); return (se); } /// /// Adds the given value to the collection (surrounded /// by a 'Start' and 'End' element pair). /// /// /// public void AddValue(string name, object value) { Items.Add(new SerialElement(SerElementType.ValueStart, name)); Items.Add(new SerialElement(name, value)); Items.Add(new SerialElement(SerElementType.ValueEnd, name)); } /// /// Adds the given value to the collection (surrounded /// by a 'Start' and 'End' element pair) - but only if the /// value is not equal to the given defaultValue. /// /// /// /// public void AddValue(string name, object value, object defaultValue) { if ((defaultValue == null && value != null) || (defaultValue != null && defaultValue.Equals(value) == false)) { AddValue(name, value); } } /// /// Adds the given value Image to the collection (surrounded /// by a 'Start' and 'End' element pair). /// /// /// public void AddValue(string name, Image image) { if (image != null) AddValue(name, ImageToString(image)); } #endregion #region ImageToString private String ImageToString(Image image) { BinaryFormatter bf = new BinaryFormatter(); MemoryStream ms = new MemoryStream(); bf.Serialize(ms, image); return (Convert.ToBase64String(ms.ToArray())); } #endregion #region AddDataValue /// /// Adds the given 'Data' value to the collection (surrounded /// by a 'Start' and 'End' element pair). /// /// /// public void AddDataValue(string name, object value) { Items.Add(new SerialElement(SerElementType.ValueStart, name)); Items.Add(new SerialElement(SerElementType.DataValue, name, value)); Items.Add(new SerialElement(SerElementType.ValueEnd, name)); } /// /// Adds the given 'Data' value to the collection (surrounded /// by a 'Start' and 'End' element pair) - but only if the /// value is not equal to the given defaultValue. /// /// /// /// public void AddDataValue(string name, object value, object defaultValue) { if ((defaultValue == null && value != null) || (defaultValue != null && defaultValue.Equals(value) == false)) { AddDataValue(name, value); } } #endregion #region AddElement /// /// Adds the given SerialElementCollection to the /// collection, if the given collection is non-empty. /// /// /// public SerialElement AddElement(SerialElementCollection sec) { if (sec != null && sec.Count > 0) { int count = sec.Count; if (sec[count - 1].SerType == SerElementType.End) count--; if (sec[0].SerType == SerElementType.Start) count--; if (count > 0) { SerialElement se = new SerialElement(sec); Items.Add(se); return (se); } } return (null); } /// /// Adds the given style to the collection, if /// it is not Empty. /// /// /// public SerialElement AddElement(BaseVisualStyle style) { if (style != null && style.IsEmpty == false) return (AddElement(style.GetSerialData(""))); return (null); } #endregion #region PutSerialData internal void PutSerialData(IProcessSerialElement ipse) { while (Read()) { SerialElement se = ReadSe; switch (se.SerType) { case SerElementType.Start: case SerElementType.ValueStart: string name = se.Name; PutSerialData(ipse); if (se.Name.Equals(name) == false) throw new Exception("Expecting " + name + " End"); break; case SerElementType.Value: se.ValueIndex = _ValueIndex++; ipse.ProcessValue(se); break; case SerElementType.Collection: int valueIndex = _ValueIndex; _ValueIndex = 0; ipse.ProcessCollection(se); _ValueIndex = valueIndex; break; case SerElementType.End: case SerElementType.ValueEnd: return; } } } #region SkipSerialData private void SkipSerialData() { while (Read()) { SerialElement se = ReadSe; switch (se.SerType) { case SerElementType.Start: case SerElementType.ValueStart: string name = se.Name; SkipSerialData(); if (se.Name.Equals(name) == false) throw new Exception("Expecting " + name + " End"); break; case SerElementType.End: case SerElementType.ValueEnd: return; } } } #endregion #endregion #region Read internal bool Read() { _ReadIndex++; _ReadSe = (_ReadIndex < Count) ? Items[_ReadIndex] : null; return (_ReadSe != null); } #endregion #region Rewind internal void Rewind() { _ReadIndex = -1; } #endregion #region GetItemValue internal string GetItemValue(string text) { foreach (SerialElement se in this) { if (se.SerType == SerElementType.Value) { if (se.Name.Equals(text)) return (se.StringValue); } } return (null); } #endregion } #endregion #region SerialElement public class SerialElement { #region Private variables private SerElementType _SerType; private string _Name; private object _Value; private SerialElementCollection _Sec; private int _ArrayCount; private int _ValueIndex; #endregion #region Constructors public SerialElement(SerElementType type, string name) { _SerType = type; _Name = name; } public SerialElement(string name, object value) { _SerType = SerElementType.Value; _Name = name; _Value = value; } public SerialElement(SerElementType type, string name, object value) { _SerType = type; _Name = name; _Value = value; } public SerialElement(SerialElementCollection sec) { _SerType = SerElementType.Collection; _Sec = sec; } #endregion #region Public properties /// /// Element name /// public string Name { get { return (_Name); } set { _Name = value; } } /// /// Element type. /// public SerElementType SerType { get { return (_SerType); } set { _SerType = value; } } /// /// Element value /// public object Value { get { return (_Value); } set { _Value = value; } } /// /// Element sub-collection. /// public SerialElementCollection Sec { get { return (_Sec); } set { _Sec = value; } } #endregion #region Internal properties #region ArrayCount internal int ArrayCount { get { return (_ArrayCount); } set { _ArrayCount = value; } } #endregion #region ColorValue internal Color ColorValue { get { return (GetValueColor()); } } #endregion #region DataValue internal object DataValue { get { if (Value is string) { string s = (string)Value; if (s.StartsWith("\"") && s.EndsWith("\"")) return (s.Substring(1, s.Length - 2)); if (s.StartsWith("#") && s.EndsWith("#")) return (DateTime.Parse(s.Substring(1, s.Length - 2))); if (s.StartsWith("{") && s.EndsWith("}")) return (ColorTranslator.FromHtml(s.Substring(1, s.Length - 2))); if (s.StartsWith("[") && s.EndsWith("]")) { s = s.Substring(1, s.Length - 2); string[] t = s.Split(','); TypeCode tc = TypeCode.Double; if (t.Length > 1) tc = (TypeCode)int.Parse(t[1]); return (GetNumericValue(t[0], tc)); } if (s.Equals("xsi:nil=\"true\"")) return (null); return (s); } return (null); } } #endregion #region StringValue internal string StringValue { get { if (Value is string) { string s = (string)Value; if (s.StartsWith("\"") && s.EndsWith("\"")) return (s.Substring(1, s.Length - 2)); return (s); } return (""); } } #endregion #region ValueIndex internal int ValueIndex { get { return (_ValueIndex); } set { _ValueIndex = value; } } #endregion #endregion #region GetValueColor internal Color GetValueColor() { string s = StringValue; if (string.IsNullOrEmpty(s) == false) { if (s.IndexOf('=') >= 0) { string pattern = @"A=(?\d+)\s*,\s*R=(?\d+)\s*,\s*G=(?\d+)\s*,\s*B=(?\d+)"; Match match = Regex.Match(s, pattern); if (match.Success == true) { Color color = Color.FromArgb( int.Parse(match.Groups["A"].Value), int.Parse(match.Groups["R"].Value), int.Parse(match.Groups["G"].Value), int.Parse(match.Groups["B"].Value)); return (color); } } else { return (Color)Color.FromName(s); } } return (Color.Empty); } #endregion #region GetValueString internal string GetValueString() { string s = GetValueStringEx(); string encodedXml = SecurityElement.Escape(s); return (encodedXml); } internal string GetValueStringEx() { object value = Value; if (value == null) return ("xsi:nil=\"true\""); if (value is string) return ((string)value); if (value is DateTime) return (((DateTime)value).ToString("o")); if (value is Color) { Color color = (Color)value; string s = color.ToString(); int start = s.IndexOf('[') + 1; int end = s.IndexOf(']'); s = s.Substring(start, end - start); return (s); } return (value.ToString()); } #endregion #region GetDataValueString internal string GetDataValueString() { object value = Value; if (value == null) return ("xsi:nil=\"true\""); if (value is string) return ("\"" + value + "\""); if (value is DateTime) return ("#" + ((DateTime)value).ToString("o") + "#"); if (value is Color) return ("{" + ColorTranslator.ToHtml((Color)value) + "}"); if (Value is Enum == false) { TypeCode typeCode; if (IsNumericValue(out typeCode)) { string s = value.ToString(); return ("[" + s + "," + (int)typeCode + "]"); } } return (value.ToString()); } #endregion #region GetValueEnum internal object GetValueEnum(Type type) { return (Enum.Parse(type, StringValue)); } #endregion #region GetValuePoint internal Point GetValuePoint() { string svalue = StringValue; if (string.IsNullOrEmpty(svalue) == false) { string pattern = @"(?X=\d+)\s,\s(?Y=\d+)"; Match match = Regex.Match(svalue, pattern); if (match.Success == true) { Point pt = new Point( int.Parse(match.Groups["x"].Value), int.Parse(match.Groups["y"].Value)); return (pt); } } return (Point.Empty); } #endregion #region GetValuePointF internal PointF GetValuePointF() { string svalue = StringValue; if (string.IsNullOrEmpty(svalue) == false) { string pattern = @"(?X=\d+)\s,\s(?Y=\d+)"; Match match = Regex.Match(svalue, pattern); if (match.Success == true) { PointF ptf = new PointF( float.Parse(match.Groups["x"].Value), float.Parse(match.Groups["y"].Value)); return (ptf); } } return (PointF.Empty); } #endregion #region GetValueSize internal Size GetValueSize() { string svalue = StringValue; if (string.IsNullOrEmpty(svalue) == false) { string pattern = @"Width=(?\d+)\s*,\s*Height=(?\d+)"; Match match = Regex.Match(svalue, pattern); if (match.Success == true) { Size size = new Size( int.Parse(match.Groups["width"].Value), int.Parse(match.Groups["height"].Value)); return (size); } } return (Size.Empty); } #endregion #region GetValueRect internal Rectangle GetValueRect() { string svalue = StringValue; if (string.IsNullOrEmpty(svalue) == false) { string pattern = @"(?X=\d+)\s,\s(?Y=\d+)\s,\s(?Width=\d+)\s,\s(?Height=\d+)"; Match match = Regex.Match(svalue, pattern); if (match.Success == true) { Rectangle rect = new Rectangle( int.Parse(match.Groups["x"].Value), int.Parse(match.Groups["y"].Value), int.Parse(match.Groups["width"].Value), int.Parse(match.Groups["height"].Value)); return (rect); } } return (Rectangle.Empty); } #endregion #region GetValueImage internal Image GetValueImage() { string svalue = StringValue; if (string.IsNullOrEmpty(svalue) == false) return (StringToImage(svalue)); return (null); } #region StringToImage private Image StringToImage(String data) { MemoryStream ms = new MemoryStream(Convert.FromBase64String(data)); BinaryFormatter bf = new BinaryFormatter(); Image image = (Image)bf.Deserialize(ms); return (image); } #endregion #endregion #region IsNumericValue private bool IsNumericValue(out TypeCode typeCode) { typeCode = Type.GetTypeCode(Value.GetType()); switch (typeCode) { case TypeCode.Byte: case TypeCode.Decimal: case TypeCode.Double: case TypeCode.Int16: case TypeCode.Int32: case TypeCode.Int64: case TypeCode.SByte: case TypeCode.Single: case TypeCode.UInt16: case TypeCode.UInt32: case TypeCode.UInt64: return (true); } return (false); } #endregion #region GetNumericValue private object GetNumericValue(string s, TypeCode typeCode) { switch (typeCode) { case TypeCode.Byte: return (Byte.Parse(s)); case TypeCode.Decimal: return (Decimal.Parse(s)); case TypeCode.Double: return (Double.Parse(s)); case TypeCode.Int16: return (Int16.Parse(s)); case TypeCode.Int32: return (Int32.Parse(s)); case TypeCode.Int64: return (Int64.Parse(s)); case TypeCode.SByte: return (SByte.Parse(s)); case TypeCode.Single: return (Single.Parse(s)); case TypeCode.UInt16: return (UInt16.Parse(s)); case TypeCode.UInt32: return (UInt32.Parse(s)); case TypeCode.UInt64: return (UInt64.Parse(s)); } return (false); } #endregion } #endregion #region Interfaces internal interface IProcessSerialElement { void ProcessValue(SerialElement se); void ProcessCollection(SerialElement se); } #endregion #region SerElementType enum public enum SerElementType { Start, End, ValueStart, ValueEnd, Value, DataValue, Collection, } #endregion #region StreamWriterNC public class StreamWriterNC : IDisposable { #region Private variables private Stream _Stream; #endregion public StreamWriterNC(Stream stream) { _Stream = stream; stream.Position = 0; } #region Public properties public Stream Stream { get { return (_Stream); } internal set { _Stream = value; } } #endregion #region Write public void Write(string s) { byte[] bytes = new byte[s.Length * sizeof(char)]; Buffer.BlockCopy(s.ToCharArray(), 0, bytes, 0, bytes.Length); _Stream.Write(bytes, 0, bytes.Length); } #endregion #region WriteLine public void WriteLine(string s) { Write(s + "\n"); } public void WriteLine() { Write("\n"); } #endregion #region Dispose public void Dispose() { _Stream.Flush(); } #endregion } #endregion }