Added hammock project to debug streaming issues
[pithos-ms-client] / trunk / hammock / src / net35 / ICSharpCode.SharpZipLib.Silverlight / Serialization / SerializationInfo.cs
1 using System;
2 using System.Collections.Generic;
3 using System.Linq;
4 using System.Xml.Linq;
5
6 namespace ICSharpCode.SharpZipLib.Silverlight.Serialization
7 {
8     /// <summary>
9     /// Code originally authored by Rockford Lhotka:
10     /// http://www.lhotka.net/weblog/SilverlightSerialization.aspx,
11     /// presented here with minor naming and code changes.
12     /// </summary>
13     public class SerializationInfo
14     {
15         private class ValueEntry
16         {
17             public string Name { get; private set; }
18             public object Value { get; private set; }
19
20             public ValueEntry(string name, object value)
21             {
22                 Name = name;
23                 Value = value;
24             }
25         }
26
27         private readonly Dictionary<string, ValueEntry> _values = new Dictionary<string, ValueEntry>();
28
29         internal SerializationInfo(int referenceId)
30         {
31             ReferenceId = referenceId;
32         }
33
34         internal int ReferenceId { get; private set; }
35         
36         public string TypeName { get; set; }
37
38         public void AddValue(string name, object value)
39         {
40             _values.Add(name, new ValueEntry(name, value));
41         }
42
43         public object GetValue(string name)
44         {
45             ValueEntry result;
46             return _values.TryGetValue(name, out result) ? result.Value : null;
47         }
48
49         internal XElement ToXElement()
50         {
51             var root = new XElement("o");
52             root.Add(new XAttribute("i", ReferenceId));
53             root.Add(new XAttribute("t", TypeName));
54             
55             foreach (var item in _values)
56             {
57                 var info = item.Value.Value as SerializationInfo;
58                 if (info == null)
59                 {
60                     var list = item.Value.Value as List<SerializationInfo>;
61                     if (list == null)
62                     {
63                         if (item.Value.Value != null)
64                             root.Add(new XElement("f",
65                                                   new XAttribute("n", item.Value.Name),
66                                                   new XAttribute("v", item.Value.Value)));
67                     }
68                     else
69                     {
70                         var listElement = new XElement("l",
71                                                        new XAttribute("n", item.Value.Name));
72                         foreach (var listItem in list)
73                             listElement.Add(new XElement("r",
74                                                          new XAttribute("i", listItem.ReferenceId)));
75                         root.Add(listElement);
76                     }
77                 }
78                 else
79                     root.Add(new XElement("r",
80                                           new XAttribute("n", item.Value.Name),
81                                           new XAttribute("i", info.ReferenceId)));
82             }
83             return root;
84         }
85
86         internal SerializationInfo(XElement data)
87         {
88             ReferenceId = Convert.ToInt32(data.Attribute("i").Value);
89             if (data.Name == "o")
90             {
91                 TypeName = data.Attribute("t").Value;
92             }
93         }
94
95         internal void Deserialize(XElement data, XmlFormatter formatter)
96         {
97             foreach (var item in data.Elements())
98             {
99                 if (item.Name == "f")
100                 {
101                     var entry = new ValueEntry(item.Attribute("n").Value, item.Attribute("v").Value);
102                     _values.Add(entry.Name, entry);
103                 }
104                 else if (item.Name == "l")
105                 {
106                     var listItems = item.Elements().Select(content => new SerializationInfo(content)).ToList();
107
108                     var entry = new ValueEntry(item.Attribute("n").Value, listItems);
109                     _values.Add(entry.Name, entry);
110                 }
111                 else
112                 {
113                     var referenceId = Convert.ToInt32(item.Attribute("i").Value);
114                     var entry = new ValueEntry(
115                         item.Attribute("n").Value, 
116                         new SerializationInfo(referenceId));
117                     _values.Add(entry.Name, entry);
118                 }
119             }
120         }
121     }
122 }