From 19538fbb905817793415b08ce15aea3894a75eb9 Mon Sep 17 00:00:00 2001 From: Iain McCoy Date: Mon, 22 Aug 2005 16:23:29 +0000 Subject: 2005-08-23 Iain McCoy * demo/runtimetest.cs: consume the new ObjectWriter interface * xamlc.cs: consume the new CodeWriter interface * System.Windows.Serialization/XamlParser.cs: rearrange class so that it presents a ReadNextNode() method, repeated calling of which will produce the next node with information about the Xaml file being parsed * Test/XamlParser.cs: rewrite tests so that they use the new interface of the parser * System.Windows.Serialization/CodeWriter.cs: changed code generator so that it consumes the event stream from the parser * Test/CodeWriter.cs: made tests friendly to the new way CodeWriter works * System.Windows.Serialization/CodeWriter.cs: changed object builder so that it consumes the event stream from the parser * Test/ObjectWriter.cs: made tests friendly to the new way ObjectWriter works 2005-08-07 Iain McCoy * System.Windows.Serialization/data-classes-builder.pl, System.Windows.Serialization/data-classes.txt: add stuff to generate the zillion little classes to carry information around * PresentationFramework.dll.sources, Makefile: invoke data-classes-builder.pl as needed. svn path=/trunk/mcs/; revision=48670 --- mcs/class/PresentationFramework/ChangeLog | 25 + mcs/class/PresentationFramework/Makefile | 71 +++ .../Mono.Windows.Serialization/CodeWriter.cs | 175 ++++-- .../Mono.Windows.Serialization/ObjectWriter.cs | 143 ++++- .../Mono.Windows.Serialization/XamlParser.cs | 350 ++++++++--- .../PresentationFramework.dll.sources | 38 ++ .../data-classes-builder.pl | 199 +++++++ .../System.Windows.Serialization/data-classes.txt | 34 ++ mcs/class/PresentationFramework/Test/CodeWriter.cs | 164 ++---- .../PresentationFramework/Test/ObjectWriter.cs | 87 ++- mcs/class/PresentationFramework/Test/XamlParser.cs | 648 ++++++++++++--------- 11 files changed, 1365 insertions(+), 569 deletions(-) create mode 100644 mcs/class/PresentationFramework/System.Windows.Serialization/data-classes-builder.pl create mode 100644 mcs/class/PresentationFramework/System.Windows.Serialization/data-classes.txt (limited to 'mcs/class/PresentationFramework') diff --git a/mcs/class/PresentationFramework/ChangeLog b/mcs/class/PresentationFramework/ChangeLog index 7e2c8d14dd2..77bc2be83da 100644 --- a/mcs/class/PresentationFramework/ChangeLog +++ b/mcs/class/PresentationFramework/ChangeLog @@ -1,3 +1,28 @@ +2005-08-23 Iain McCoy + + * System.Windows.Serialization/XamlParser.cs: rearrange class so that + it presents a ReadNextNode() method, repeated calling of which will + produce the next node with information about the Xaml file being + parsed + * Test/XamlParser.cs: rewrite tests so that they use the new interface + of the parser + * System.Windows.Serialization/CodeWriter.cs: changed code generator + so that it consumes the event stream from the parser + * Test/CodeWriter.cs: made tests friendly to the new way CodeWriter + works + * System.Windows.Serialization/CodeWriter.cs: changed object builder + so that it consumes the event stream from the parser + * Test/ObjectWriter.cs: made tests friendly to the new way ObjectWriter + works + +2005-08-07 Iain McCoy + + * System.Windows.Serialization/data-classes-builder.pl, + System.Windows.Serialization/data-classes.txt: add stuff to generate + the zillion little classes to carry information around + * PresentationFramework.dll.sources, Makefile: invoke + data-classes-builder.pl as needed. + 2005-07-25 Iain McCoy * Test/CodeWriter.cs: updated tests to reflect change in code diff --git a/mcs/class/PresentationFramework/Makefile b/mcs/class/PresentationFramework/Makefile index 85ee60e45cf..759fda4305c 100644 --- a/mcs/class/PresentationFramework/Makefile +++ b/mcs/class/PresentationFramework/Makefile @@ -15,4 +15,75 @@ Test/TestVocab.dll: ../../tools/xamlc/demo/TestVocab/*.cs cp ../../tools/xamlc/demo/TestVocab.dll Test/TestVocab.dll cp Test/TestVocab.dll TestVocab.dll +library_CLEAN_FILES = System.Windows.Serialization/XamlAttributeNode.cs \ +System.Windows.Serialization/XamlClrEventNode.cs \ +System.Windows.Serialization/XamlConstructorParametersEndNode.cs \ +System.Windows.Serialization/XamlConstructorParametersStartNode.cs \ +System.Windows.Serialization/XamlConstructorParameterTypeNode.cs \ +System.Windows.Serialization/XamlDefAttributeKeyTypeNode.cs \ +System.Windows.Serialization/XamlDefAttributeNode.cs \ +System.Windows.Serialization/XamlDefTagNode.cs \ +System.Windows.Serialization/XamlDocumentEndNode.cs \ +System.Windows.Serialization/XamlDocumentStartNode.cs \ +System.Windows.Serialization/XamlElementStartNode.cs \ +System.Windows.Serialization/XamlElementEndNode.cs \ +System.Windows.Serialization/XamlEndAttributesNode.cs \ +System.Windows.Serialization/XamlKeyElementEndNode.cs \ +System.Windows.Serialization/XamlKeyElementStartNode.cs \ +System.Windows.Serialization/XamlLanguageNode.cs \ +System.Windows.Serialization/XamlLiteralContentNode.cs \ +System.Windows.Serialization/XamlNode.cs \ +System.Windows.Serialization/XamlPIMappingNode.cs \ +System.Windows.Serialization/XamlPropertyArrayEndNode.cs \ +System.Windows.Serialization/XamlPropertyArrayStartNode.cs \ +System.Windows.Serialization/XamlPropertyComplexEndNode.cs \ +System.Windows.Serialization/XamlPropertyComplexStartNode.cs \ +System.Windows.Serialization/XamlPropertyIDictionaryEndNode.cs \ +System.Windows.Serialization/XamlPropertyIDictionaryStartNode.cs \ +System.Windows.Serialization/XamlPropertyIListEndNode.cs \ +System.Windows.Serialization/XamlPropertyIListStartNode.cs \ +System.Windows.Serialization/XamlPropertyNode.cs \ +System.Windows.Serialization/XamlPropertyWithTypeNode.cs \ +System.Windows.Serialization/XamlRoutedEventNode.cs \ +System.Windows.Serialization/XamlTextNode.cs \ +System.Windows.Serialization/XamlUnknownAttributeNode.cs \ +System.Windows.Serialization/XamlUnknownTagEndNode.cs \ +System.Windows.Serialization/XamlUnknownTagStartNode.cs + +System.Windows.Serialization/XamlAttributeNode.cs, \ +System.Windows.Serialization/XamlClrEventNode.cs, \ +System.Windows.Serialization/XamlConstructorParametersEndNode.cs, \ +System.Windows.Serialization/XamlConstructorParametersStartNode.cs, \ +System.Windows.Serialization/XamlConstructorParameterTypeNode.cs, \ +System.Windows.Serialization/XamlDefAttributeKeyTypeNode.cs, \ +System.Windows.Serialization/XamlDefAttributeNode.cs, \ +System.Windows.Serialization/XamlDefTagNode.cs, \ +System.Windows.Serialization/XamlDocumentEndNode.cs, \ +System.Windows.Serialization/XamlDocumentStartNode.cs, \ +System.Windows.Serialization/XamlElementStartNode.cs, \ +System.Windows.Serialization/XamlElementEndNode.cs, \ +System.Windows.Serialization/XamlEndAttributesNode.cs, \ +System.Windows.Serialization/XamlKeyElementEndNode.cs, \ +System.Windows.Serialization/XamlKeyElementStartNode.cs, \ +System.Windows.Serialization/XamlLanguageNode.cs, \ +System.Windows.Serialization/XamlLiteralContentNode.cs, \ +System.Windows.Serialization/XamlNode.cs, \ +System.Windows.Serialization/XamlPIMappingNode.cs, \ +System.Windows.Serialization/XamlPropertyArrayEndNode.cs, \ +System.Windows.Serialization/XamlPropertyArrayStartNode.cs, \ +System.Windows.Serialization/XamlPropertyComplexEndNode.cs, \ +System.Windows.Serialization/XamlPropertyComplexStartNode.cs, \ +System.Windows.Serialization/XamlPropertyIDictionaryEndNode.cs, \ +System.Windows.Serialization/XamlPropertyIDictionaryStartNode.cs, \ +System.Windows.Serialization/XamlPropertyIListEndNode.cs, \ +System.Windows.Serialization/XamlPropertyIListStartNode.cs, \ +System.Windows.Serialization/XamlPropertyNode.cs, \ +System.Windows.Serialization/XamlPropertyWithTypeNode.cs, \ +System.Windows.Serialization/XamlRoutedEventNode.cs, \ +System.Windows.Serialization/XamlTextNode.cs, \ +System.Windows.Serialization/XamlUnknownAttributeNode.cs, \ +System.Windows.Serialization/XamlUnknownTagEndNode.cs, \ +System.Windows.Serialization/XamlUnknownTagStartNode.cs: System.Windows.Serialization/data-classes.txt System.Windows.Serialization/data-classes-builder.pl + (cd System.Windows.Serialization && perl data-classes-builder.pl) + include ../../build/library.make diff --git a/mcs/class/PresentationFramework/Mono.Windows.Serialization/CodeWriter.cs b/mcs/class/PresentationFramework/Mono.Windows.Serialization/CodeWriter.cs index b7c93d0a492..244c321857c 100644 --- a/mcs/class/PresentationFramework/Mono.Windows.Serialization/CodeWriter.cs +++ b/mcs/class/PresentationFramework/Mono.Windows.Serialization/CodeWriter.cs @@ -30,12 +30,15 @@ using System; using System.Diagnostics; using System.Reflection; using System.IO; +using System.Xml; using System.Collections; using System.CodeDom; using System.CodeDom.Compiler; +using System.Windows.Serialization; +using System.Windows; namespace Mono.Windows.Serialization { - public class CodeWriter : IXamlWriter { + public class CodeWriter { TextWriter writer; ICodeGenerator generator; bool isPartial; @@ -47,16 +50,101 @@ namespace Mono.Windows.Serialization { CodeCompileUnit code; CodeTypeDeclaration type; CodeConstructor constructor; - + + public static string Parse(XmlTextReader reader, ICodeGenerator generator, bool isPartial) + { + CodeWriter cw = new CodeWriter(reader, generator, isPartial); + return ((StringWriter)cw.writer).ToString(); + } + // pushes: the code writer - public CodeWriter(ICodeGenerator generator, TextWriter writer, bool isPartial) + private void init(ICodeGenerator generator, bool isPartial) { this.generator = generator; - this.writer = writer; this.isPartial = isPartial; + this.writer = new StringWriter(); code = new CodeCompileUnit(); - objects.Add(code); + push(code); + } + + + private CodeWriter(XmlTextReader reader, ICodeGenerator generator, bool isPartial) + { + init(generator, isPartial); + XamlParser p = new XamlParser(reader); + XamlNode n; + while (true) { + n = p.GetNextNode(); + if (n == null) + break; + Debug.WriteLine("CodeWriter: INCOMING " + n.GetType()); + if (n is XamlDocumentStartNode) { + Debug.WriteLine("CodeWriter: document begins"); + // do nothing + } else if (n is XamlElementStartNode && n.Depth == 0) { + Debug.WriteLine("CodeWriter: element begins as top-level"); + CreateTopLevel(((XamlElementStartNode)n).ElementType, ((XamlElementStartNode)n).name); + } else if (n is XamlElementStartNode && ((XamlElementStartNode)n).propertyObject) { + Debug.WriteLine("CodeWriter: element begins as property value"); + CreatePropertyObject(((XamlElementStartNode)n).ElementType, ((XamlElementStartNode)n).name); + } else if (n is XamlElementStartNode) { + Debug.WriteLine("CodeWriter: element begins"); + CreateObject(((XamlElementStartNode)n).ElementType, ((XamlElementStartNode)n).name); + } else if (n is XamlPropertyNode && ((XamlPropertyNode)n).PropInfo != null) { + Debug.WriteLine("CodeWriter: normal property begins"); + CreateProperty(((XamlPropertyNode)n).PropInfo); + } else if (n is XamlPropertyNode && ((XamlPropertyNode)n).DP != null) { + Debug.WriteLine("CodeWriter: dependency property begins"); + DependencyProperty dp = ((XamlPropertyNode)n).DP; + Type typeAttachedTo = dp.OwnerType; + string propertyName = ((XamlPropertyNode)n).PropertyName; + + CreateDependencyProperty(typeAttachedTo, propertyName, dp.PropertyType); + } else if (n is XamlClrEventNode && !(((XamlClrEventNode)n).EventMember is EventInfo)) { + Debug.WriteLine("CodeWriter: delegate property"); + CreatePropertyDelegate(((XamlClrEventNode)n).Value, ((PropertyInfo)((XamlClrEventNode)n).EventMember).PropertyType); + EndProperty(); + + + } else if (n is XamlClrEventNode) { + Debug.WriteLine("CodeWriter: event"); + CreateEvent((EventInfo)((XamlClrEventNode)n).EventMember); + CreateEventDelegate(((XamlClrEventNode)n).Value, ((EventInfo)((XamlClrEventNode)n).EventMember).EventHandlerType); + EndEvent(); + + } else if (n is XamlTextNode && ((XamlTextNode)n).mode == XamlParseMode.Object){ + Debug.WriteLine("CodeWriter: text for object"); + CreateObjectText(((XamlTextNode)n).TextContent); + } else if (n is XamlTextNode && ((XamlTextNode)n).mode == XamlParseMode.Property){ + Debug.WriteLine("CodeWriter: text for property"); + CreatePropertyText(((XamlTextNode)n).TextContent, ((XamlTextNode)n).finalType); + EndProperty(); + } else if (n is XamlTextNode && ((XamlTextNode)n).mode == XamlParseMode.DependencyProperty){ + Debug.WriteLine("CodeWriter: text for dependency property"); + CreateDependencyPropertyText(((XamlTextNode)n).TextContent, ((XamlTextNode)n).finalType); + EndDependencyProperty(); + } else if (n is XamlPropertyComplexEndNode) { + Debug.WriteLine("CodeWriter: end complex property"); + Debug.WriteLine("CodeWriter: final type is " + ((XamlPropertyComplexEndNode)n).finalType); + EndPropertyObject(((XamlPropertyComplexEndNode)n).finalType); + EndProperty(); + } else if (n is XamlLiteralContentNode) { + Debug.WriteLine("CodeWriter: literal content"); + CreateCode(((XamlLiteralContentNode)n).Content); + } else if (n is XamlElementEndNode) { + Debug.WriteLine("CodeWriter: end element"); + if (!((XamlElementEndNode)n).propertyObject) + EndObject(); + } else if (n is XamlDocumentEndNode) { + Debug.WriteLine("CodeWriter: end document"); + Finish(); + } else { + throw new Exception("Unknown node " + n.GetType()); + } + } + } + // pushes: a CodeVariableReferenceExpression to the present // instance @@ -91,7 +179,7 @@ namespace Mono.Windows.Serialization { type.Members.Add(constructor); ns.Types.Add(type); - objects.Add(new CodeThisReferenceExpression()); + push(new CodeThisReferenceExpression()); } // bottom of stack holds CodeVariableReferenceExpression @@ -133,11 +221,11 @@ namespace Mono.Windows.Serialization { } CodeVariableReferenceExpression varRef = new CodeVariableReferenceExpression(varName); CodeMethodInvokeExpression addChild = new CodeMethodInvokeExpression( - (CodeExpression)objects[objects.Count - 1], + (CodeExpression)peek(), "AddChild", varRef); constructor.Statements.Add(addChild); - objects.Add(varRef); + push(varRef); } // top of stack is a reference to an object @@ -146,9 +234,9 @@ namespace Mono.Windows.Serialization { { debug(); CodePropertyReferenceExpression prop = new CodePropertyReferenceExpression( - (CodeExpression)objects[objects.Count - 1], + (CodeExpression)peek(), property.Name); - objects.Add(prop); + push(prop); } // top of stack is a reference to an object @@ -157,9 +245,9 @@ namespace Mono.Windows.Serialization { { debug(); CodeEventReferenceExpression expr = new CodeEventReferenceExpression( - (CodeExpression)objects[objects.Count - 1], + (CodeExpression)peek(), evt.Name); - objects.Add(expr); + push(expr); } // top of stack is a reference to an object @@ -180,21 +268,19 @@ namespace Mono.Windows.Serialization { CodeMethodInvokeExpression call = new CodeMethodInvokeExpression( new CodeTypeReferenceExpression(attachedTo), "Set" + propertyName, - (CodeExpression)objects[objects.Count - 1], + (CodeExpression)peek(), new CodeVariableReferenceExpression(varName)); - objects.Add(call); - objects.Add(new CodeVariableReferenceExpression(varName)); + push(call); + push(new CodeVariableReferenceExpression(varName)); } // pops 2 items: the name of the property, and the object to attach to public void EndDependencyProperty() { debug(); - objects.RemoveAt(objects.Count - 1); // pop the variable name - we don't need it since it's already - // baked into the call - CodeExpression call = (CodeExpression)(objects[objects.Count - 1]); - objects.RemoveAt(objects.Count - 1); + pop(); // pop the variable name - we don't need it since it's already baked into the call + CodeExpression call = (CodeExpression)pop(); constructor.Statements.Add(call); } @@ -202,7 +288,7 @@ namespace Mono.Windows.Serialization { public void CreateObjectText(string text) { debug(); - CodeVariableReferenceExpression var = (CodeVariableReferenceExpression)objects[objects.Count - 1]; + CodeVariableReferenceExpression var = (CodeVariableReferenceExpression)peek(); CodeMethodInvokeExpression call = new CodeMethodInvokeExpression( var, "AddText", @@ -220,7 +306,7 @@ namespace Mono.Windows.Serialization { new CodeThisReferenceExpression(), functionName)); CodeAttachEventStatement attach = new CodeAttachEventStatement( - (CodeEventReferenceExpression)objects[objects.Count - 1], + (CodeEventReferenceExpression)peek(), expr); constructor.Statements.Add(attach); @@ -235,7 +321,7 @@ namespace Mono.Windows.Serialization { new CodeThisReferenceExpression(), functionName)); CodeAssignStatement assignment = new CodeAssignStatement( - (CodeExpression)objects[objects.Count - 1], + (CodeExpression)peek(), expr); constructor.Statements.Add(assignment); } @@ -269,7 +355,7 @@ namespace Mono.Windows.Serialization { expr)); } CodeAssignStatement assignment = new CodeAssignStatement( - (CodeExpression)objects[objects.Count - 1], + (CodeExpression)peek(), expr); constructor.Statements.Add(assignment); @@ -311,20 +397,18 @@ namespace Mono.Windows.Serialization { } CodeVariableReferenceExpression varRef = new CodeVariableReferenceExpression(varName); - objects.Add(type); - objects.Add(varRef); + push(type); + push(varRef); } public void EndPropertyObject(Type destType) { debug(); - CodeExpression varRef = (CodeExpression)objects[objects.Count - 1]; - objects.RemoveAt(objects.Count - 1); - Type sourceType = (Type)objects[objects.Count - 1]; - objects.RemoveAt(objects.Count - 1); + CodeExpression varRef = (CodeExpression)pop(); + Type sourceType = (Type)pop(); - Debug.WriteLine(destType + "->" + sourceType); + Debug.WriteLine("CodeWriter: " + destType + "->" + sourceType); CodeExpression expr; @@ -339,7 +423,7 @@ namespace Mono.Windows.Serialization { varRef, new CodeTypeOfExpression(destType))); CodeAssignStatement assignment = new CodeAssignStatement( - (CodeExpression)objects[objects.Count - 1], + (CodeExpression)peek(), expr); constructor.Statements.Add(assignment); } @@ -347,19 +431,19 @@ namespace Mono.Windows.Serialization { public void EndObject() { debug(); - objects.RemoveAt(objects.Count - 1); + pop(); } public void EndProperty() { debug(); - objects.RemoveAt(objects.Count - 1); + pop(); } public void EndEvent() { debug(); - objects.RemoveAt(objects.Count - 1); + pop(); } public void Finish() @@ -377,7 +461,28 @@ namespace Mono.Windows.Serialization { private void debug() { - Debug.WriteLine(new System.Diagnostics.StackTrace()); + Debug.WriteLine("CodeWriter: " + new System.Diagnostics.StackTrace()); + } + + private object pop() + { + object v = objects[objects.Count - 1]; + objects.RemoveAt(objects.Count - 1); + Debug.WriteLine("CodeWriter: POPPING"); + return v; + } + private void push(object v) + { + Debug.WriteLine("CodeWriter: PUSHING " + v); + objects.Add(v); + } + private object peek() + { + return peek(0); + } + private object peek(int i) + { + return objects[objects.Count - 1 - i]; } } } diff --git a/mcs/class/PresentationFramework/Mono.Windows.Serialization/ObjectWriter.cs b/mcs/class/PresentationFramework/Mono.Windows.Serialization/ObjectWriter.cs index f8c283cfbfc..c078cb0763e 100644 --- a/mcs/class/PresentationFramework/Mono.Windows.Serialization/ObjectWriter.cs +++ b/mcs/class/PresentationFramework/Mono.Windows.Serialization/ObjectWriter.cs @@ -33,42 +33,120 @@ using System.Collections; using System.CodeDom; using System.CodeDom.Compiler; using System.ComponentModel; +using System.Diagnostics; +using System.Windows; using System.Windows.Serialization; +using System.Xml; namespace Mono.Windows.Serialization { - public class ObjectWriter : IXamlWriter { + public class ObjectWriter { public object instance; ArrayList objects = new ArrayList(); + + public static object Parse(XmlTextReader reader) + { + ObjectWriter ow = new ObjectWriter(reader); + return ow.instance; + } + private ObjectWriter(XmlTextReader reader) + { + XamlParser p = new XamlParser(reader); + XamlNode n; + while (true) { + n = p.GetNextNode(); + if (n == null) + break; + Debug.WriteLine("ObjectWriter: INCOMING " + n.GetType()); + if (n is XamlDocumentStartNode) { + Debug.WriteLine("ObjectWriter: document begins"); + // do nothing + } else if (n is XamlElementStartNode && n.Depth == 0) { + Debug.WriteLine("ObjectWriter: element begins as top-level"); + CreateTopLevel(((XamlElementStartNode)n).ElementType, ((XamlElementStartNode)n).name); + } else if (n is XamlElementStartNode && peek() is PropertyInfo) { + Debug.WriteLine("ObjectWriter: element begins as property value"); + CreatePropertyObject(((XamlElementStartNode)n).ElementType, ((XamlElementStartNode)n).name); + } else if (n is XamlElementStartNode) { + Debug.WriteLine("ObjectWriter: element begins"); + CreateObject(((XamlElementStartNode)n).ElementType, ((XamlElementStartNode)n).name); + } else if (n is XamlPropertyNode && ((XamlPropertyNode)n).PropInfo != null) { + Debug.WriteLine("ObjectWriter: normal property begins"); + CreateProperty(((XamlPropertyNode)n).PropInfo); + } else if (n is XamlPropertyNode && ((XamlPropertyNode)n).DP != null) { + Debug.WriteLine("ObjectWriter: dependency property begins"); + DependencyProperty dp = ((XamlPropertyNode)n).DP; + Type typeAttachedTo = dp.OwnerType; + string propertyName = ((XamlPropertyNode)n).PropertyName; + + CreateDependencyProperty(typeAttachedTo, propertyName, dp.PropertyType); + } else if (n is XamlClrEventNode) { + Debug.WriteLine("ObjectWriter: event"); + CreateEvent((EventInfo)((XamlClrEventNode)n).EventMember); + CreateEventDelegate(((XamlClrEventNode)n).Value, ((EventInfo)((XamlClrEventNode)n).EventMember).EventHandlerType); + EndEvent(); + + } else if (n is XamlTextNode && ((XamlTextNode)n).mode == XamlParseMode.Object){ + Debug.WriteLine("ObjectWriter: text for object"); + CreateObjectText(((XamlTextNode)n).TextContent); + } else if (n is XamlTextNode && ((XamlTextNode)n).mode == XamlParseMode.Property){ + Debug.WriteLine("ObjectWriter: text for property"); + Debug.WriteLine("THINGTYPE = " + peek().GetType()); + CreatePropertyText(((XamlTextNode)n).TextContent, ((PropertyInfo)peek()).PropertyType); + EndProperty(); + } else if (n is XamlTextNode && ((XamlTextNode)n).mode == XamlParseMode.DependencyProperty){ + Debug.WriteLine("ObjectWriter: text for dependency property"); + string propertyName = (string)peek(); + Type attachedTo = (Type)peek(1); + CreateDependencyPropertyText(((XamlTextNode)n).TextContent, ((DependencyProperty)attachedTo.GetField(propertyName + "Property").GetValue(null)).PropertyType); + EndDependencyProperty(); + } else if (n is XamlPropertyComplexEndNode) { + Debug.WriteLine("ObjectWriter: end complex property"); + Debug.WriteLine("ObjectWriter: final type is " + ((XamlPropertyComplexEndNode)n).finalType); + EndPropertyObject(((XamlPropertyComplexEndNode)n).finalType); + EndProperty(); + } else if (n is XamlElementEndNode) { + Debug.WriteLine("ObjectWriter: end element"); + if (!((XamlElementEndNode)n).propertyObject) + EndObject(); + } else if (n is XamlDocumentEndNode) { + Debug.WriteLine("ObjectWriter: end document"); + Finish(); + } else { + throw new Exception("Unknown node " + n.GetType()); + } + } + } + public void CreateTopLevel(Type parent, string className) { instance = Activator.CreateInstance(parent); - objects.Add(instance); + push(instance); } public void CreateObject(Type type, string varName) { Object o = Activator.CreateInstance(type); - ((IAddChild)objects[objects.Count - 1]).AddChild(o); - objects.Add(o); + ((IAddChild)peek()).AddChild(o); + push(o); } public void CreateProperty(PropertyInfo property) { - objects.Add(property); + push(property); } // top of stack is a reference to an object // pushes a reference to the event public void CreateEvent(EventInfo evt) { - objects.Add(evt); + push(evt); } public void CreateDependencyProperty(Type attachedTo, string propertyName, Type propertyType) { - objects.Add(attachedTo); - objects.Add(propertyName); + push(attachedTo); + push(propertyName); } public void EndDependencyProperty() @@ -78,26 +156,26 @@ namespace Mono.Windows.Serialization { Type attachedTo = (Type)pop(); MethodInfo setter = attachedTo.GetMethod("Set" + propertyName); - setter.Invoke(null, new object[] { objects[objects.Count - 1], value}); + setter.Invoke(null, new object[] { peek(), value}); } public void CreateObjectText(string text) { - ((IAddChild)objects[objects.Count - 1]).AddText(text); + ((IAddChild)peek()).AddText(text); } // top of stack is reference to an event public void CreateEventDelegate(string functionName, Type eventDelegateType) { - EventInfo e = (EventInfo)objects[objects.Count-1]; - object o = objects[objects.Count-2]; + EventInfo e = (EventInfo)peek(); + object o = peek(1); e.AddEventHandler(o, Delegate.CreateDelegate(o.GetType(), o, functionName)); } // top of stack is reference to a property public void CreatePropertyDelegate(string functionName, Type propertyType) { - PropertyInfo p = (PropertyInfo)objects[objects.Count-1]; - object o = objects[objects.Count-2]; + PropertyInfo p = (PropertyInfo)peek(); + object o = peek(1); p.SetValue(o, Delegate.CreateDelegate(o.GetType(), o, functionName), null); } @@ -108,27 +186,28 @@ namespace Mono.Windows.Serialization { TypeConverter tc = TypeDescriptor.GetConverter(propertyType); value = tc.ConvertFromString(text); } - PropertyInfo p = (PropertyInfo)objects[objects.Count-1]; - object o = objects[objects.Count-2]; + PropertyInfo p = (PropertyInfo)peek(); + object o = peek(1); p.SetValue(o, value, null); } public void CreatePropertyObject(Type type, string name) { object value = Activator.CreateInstance(type); - objects.Add(value); + Debug.WriteLine("ObjectWriter CREATING PROPERTY OBJECT of type" + type); + push(value); } public void EndPropertyObject(Type destType) { - object value = objects[objects.Count - 1]; - objects.RemoveAt(objects.Count - 1); + object value = pop(); Type sourceType = value.GetType(); + Debug.WriteLine("ObjectWriter: EndPropertyObject has a " + value + value.GetType() + ", needs a " + destType); if (destType != sourceType && !sourceType.IsSubclassOf(destType)) { TypeConverter tc = TypeDescriptor.GetConverter(destType); value = tc.ConvertFrom(value); } - PropertyInfo p = (PropertyInfo)objects[objects.Count-1]; - object o = objects[objects.Count-2]; + PropertyInfo p = (PropertyInfo)peek(); + object o = peek(1); p.SetValue(o, value, null); } @@ -140,22 +219,22 @@ namespace Mono.Windows.Serialization { TypeConverter tc = TypeDescriptor.GetConverter(propertyType); value = tc.ConvertFromString(text); } - objects.Add(value); + push(value); } public void EndObject() { - objects.RemoveAt(objects.Count - 1); + pop(); } public void EndProperty() { - objects.RemoveAt(objects.Count - 1); + pop(); } public void EndEvent() { - objects.RemoveAt(objects.Count - 1); + pop(); } public void Finish() @@ -167,11 +246,25 @@ namespace Mono.Windows.Serialization { throw new NotImplementedException(); } + private object peek() + { + return peek(0); + } + private object peek(int i) + { + return objects[objects.Count - 1 - i]; + } private object pop() { object v = objects[objects.Count - 1]; objects.RemoveAt(objects.Count - 1); + Debug.WriteLine("ObjectWriter POPPING"); return v; } + private void push(object v) + { + Debug.WriteLine("ObjectWriter PUSHING " + v); + objects.Add(v); + } } } diff --git a/mcs/class/PresentationFramework/Mono.Windows.Serialization/XamlParser.cs b/mcs/class/PresentationFramework/Mono.Windows.Serialization/XamlParser.cs index b486bc66528..4a96b7e2482 100644 --- a/mcs/class/PresentationFramework/Mono.Windows.Serialization/XamlParser.cs +++ b/mcs/class/PresentationFramework/Mono.Windows.Serialization/XamlParser.cs @@ -40,8 +40,8 @@ namespace Mono.Windows.Serialization { public class XamlParser { public const string XAML_NAMESPACE = "http://schemas.microsoft.com/winfx/xaml/2005"; private Mapper mapper = new Mapper(new string[] { }); - private XmlReader reader; - private IXamlWriter writer; + private XmlTextReader reader; + private ArrayList nodeQueue = new ArrayList(); private enum CurrentType { Object, Property, @@ -56,32 +56,49 @@ namespace Mono.Windows.Serialization { private bool begun = false; - private ParserState currentState = null; + private ParserState currentState() { + if (oldStates.Count == 0) return null; + return (ParserState)oldStates[oldStates.Count - 1]; + } private ArrayList oldStates = new ArrayList(); + + int tempStateCount = 0; + private int getDepth() { + return oldStates.Count - tempStateCount; + } - public XamlParser(string filename, IXamlWriter writer) : this( - new XmlTextReader(filename), writer) + public XamlParser(string filename) : this( + new XmlTextReader(filename)) { } - public XamlParser(TextReader reader, IXamlWriter writer) : this( - new XmlTextReader(reader), writer) + public XamlParser(TextReader reader) : this( + new XmlTextReader(reader)) { } - public XamlParser(XmlReader reader, IXamlWriter writer) + public XamlParser(XmlTextReader reader) { this.reader = reader; - this.writer = writer; + } + + private XamlNode topNode() + { + return (XamlNode)nodeQueue[nodeQueue.Count - 1]; } - public void Parse() + public XamlNode GetNextNode() { + if (nodeQueue.Count != 0) { + XamlNode x = (XamlNode)nodeQueue[0]; + nodeQueue.RemoveAt(0); + return x; + } while (reader.Read()) { - Debug.WriteLine("NOW PARSING: " + reader.NodeType + "; " + reader.Name + "; " + reader.Value); + Debug.WriteLine("XamlParser: NOW PARSING: " + reader.NodeType + "; " + reader.Name + "; " + reader.Value); if (goneTooFar()) throw new Exception("Too far: " + reader.NodeType + ", " + reader.Name); - if (currentState != null && currentState.type == CurrentType.Code) + if (currentState() != null && currentState().type == CurrentType.Code) { processElementInCodeState(); continue; @@ -105,9 +122,14 @@ namespace Mono.Windows.Serialization { break; default: throw new Exception("Unknown element type " + reader.NodeType); - break; + } + if (nodeQueue.Count != 0) { + XamlNode x = (XamlNode)nodeQueue[0]; + nodeQueue.RemoveAt(0); + return x; } } + return null; } void processElementInCodeState() { @@ -118,14 +140,14 @@ namespace Mono.Windows.Serialization { } else if (reader.NodeType != XmlNodeType.CDATA && reader.NodeType != XmlNodeType.Text) { throw new Exception("Code element children must be either text or CDATA nodes."); } else { - currentState.obj = (string)currentState.obj + reader.Value; + currentState().obj = (string)currentState().obj + reader.Value; } } bool goneTooFar() { if (begun && - currentState == null && + currentState() == null && reader.NodeType != XmlNodeType.Whitespace && reader.NodeType != XmlNodeType.Comment) return true; @@ -162,14 +184,14 @@ namespace Mono.Windows.Serialization { // name before the dot. int dotPosition = reader.LocalName.IndexOf('.'); if (dotPosition < 0 || - currentState.type == CurrentType.Property) { + currentState().type == CurrentType.Property) { parseObjectElement(); return; } string beforeDot = reader.LocalName.Substring(0, dotPosition); string afterDot = reader.LocalName.Substring(dotPosition + 1); - // If we've got this far, then currentState.Type == Object - if (isNameOfAncestorClass(beforeDot, (Type)currentState.obj)) + // If we've got this far, then currentState().Type == Object + if (isNameOfAncestorClass(beforeDot, (Type)currentState().obj)) parseNormalPropertyElement(afterDot); else parseDependencyPropertyElement(beforeDot, afterDot); @@ -199,19 +221,25 @@ namespace Mono.Windows.Serialization { void parseText() { - switch (currentState.type) { + nodeQueue.Add(new XamlTextNode(reader.LineNumber, reader.LinePosition, getDepth(), reader.Value)); + switch (currentState().type) { case CurrentType.Object: case CurrentType.PropertyObject: abortIfNotAddChild("text"); - writer.CreateObjectText(reader.Value); + ((XamlTextNode)topNode()).setmode(XamlParseMode.Object); +// writer.CreateObjectText(reader.Value); break; case CurrentType.DependencyProperty: - DependencyProperty dp = (DependencyProperty)currentState.obj; - writer.CreateDependencyPropertyText(reader.Value, dp.PropertyType); + DependencyProperty dp = (DependencyProperty)currentState().obj; +// writer.CreateDependencyPropertyText(reader.Value, dp.PropertyType); + ((XamlTextNode)topNode()).setmode(XamlParseMode.DependencyProperty); + ((XamlTextNode)topNode()).setfinalType(dp.PropertyType); break; case CurrentType.Property: - PropertyInfo prop = (PropertyInfo)currentState.obj; - writer.CreatePropertyText(reader.Value, prop.PropertyType); + PropertyInfo prop = (PropertyInfo)currentState().obj; +// writer.CreatePropertyText(reader.Value, prop.PropertyType); + ((XamlTextNode)topNode()).setmode(XamlParseMode.Property); + ((XamlTextNode)topNode()).setfinalType(prop.PropertyType); break; default: throw new NotImplementedException(); @@ -220,26 +248,39 @@ namespace Mono.Windows.Serialization { void abortIfNotAddChild(string thing) { - if (!isAddChild((Type)currentState.obj)) + if (!isAddChild((Type)currentState().obj)) throw new Exception("Cannot add " + thing + " to instance of '" + - ((Type)currentState.obj) + + ((Type)currentState().obj) + "'."); } void parseNormalPropertyElement(string propertyName) { - // preconditions: currentState.Type == Object - Type currentType = (Type)currentState.obj; + // preconditions: currentState().Type == Object + Type currentType = (Type)currentState().obj; PropertyInfo prop = currentType.GetProperty(propertyName); if (prop == null) { throw new Exception("Property '" + propertyName + "' not found on '" + currentType.Name + "'."); } - push(CurrentType.Property, prop); - writer.CreateProperty(prop); +// writer.CreateProperty(prop); + nodeQueue.Add(new XamlPropertyNode( + reader.LineNumber, + reader.LinePosition, + getDepth(), + null, + currentType.Assembly.FullName, + currentType.AssemblyQualifiedName, + propertyName, + reader.Value, + reader.NamespaceURI, + BamlAttributeUsage.Default, + false)); + ((XamlPropertyNode)topNode()).setPropInfo(prop); + push(CurrentType.Property, prop); if (reader.HasAttributes) { throw new Exception("Property node should not have attributes."); @@ -249,14 +290,29 @@ namespace Mono.Windows.Serialization { void parseDependencyPropertyElement(string attachedTo, string propertyName) { - Type currentType = (Type)currentState.obj; + Type currentType = (Type)currentState().obj; ensureDependencyObject(currentType); Type typeAttachedTo = findTypeToAttachTo(attachedTo, propertyName); DependencyProperty dp = getDependencyProperty(typeAttachedTo, propertyName); - push(CurrentType.DependencyProperty, dp); - writer.CreateDependencyProperty(typeAttachedTo, propertyName, dp.PropertyType); +// writer.CreateDependencyProperty(typeAttachedTo, propertyName, dp.PropertyType); + nodeQueue.Add(new XamlPropertyNode( + reader.LineNumber, + reader.LinePosition, + getDepth(), + null, + currentType.Assembly.FullName, + currentType.AssemblyQualifiedName, + propertyName, + reader.Value, + reader.NamespaceURI, + BamlAttributeUsage.Default, + false)); + ((XamlPropertyNode)topNode()).setDP(dp); + + push(CurrentType.DependencyProperty, dp); + } bool isAddChild(Type t) { @@ -272,12 +328,14 @@ namespace Mono.Windows.Serialization { throw new Exception("Class '" + reader.Name + "' not found."); // whichever of these functions runs will push something - if (currentState == null) { + if (currentState() == null) { parseTopLevelObjectElement(parent); } else { parseChildObjectElement(parent); } + if (isEmpty) + tempStateCount ++; processObjectAttributes(); if (isEmpty) { @@ -302,10 +360,11 @@ namespace Mono.Windows.Serialization { if (name == null) name = reader.GetAttribute("Name", reader.NamespaceURI); - if (currentState.type == CurrentType.Object) { + Debug.WriteLine("XamlParser: parent is " + parent); + if (currentState().type == CurrentType.Object) { abortIfNotAddChild("object"); addChild(parent, name); - } else if (currentState.type == CurrentType.Property) { + } else if (currentState().type == CurrentType.Property) { addPropertyChild(parent, name); } else { throw new NotImplementedException(); @@ -329,34 +388,79 @@ namespace Mono.Windows.Serialization { void closeEmptyObjectElement() { - if (currentState.type == CurrentType.Object) { - writer.EndObject(); - } else if (currentState.type == CurrentType.PropertyObject) { - ParserState state = (ParserState)oldStates[oldStates.Count - 1]; - writer.EndPropertyObject(((PropertyInfo)state.obj).PropertyType); + if (currentState().type == CurrentType.Object) { + nodeQueue.Add(new XamlElementEndNode( + reader.LineNumber, + reader.LinePosition, + getDepth())); +// writer.EndObject(); + } else if (currentState().type == CurrentType.PropertyObject) { + nodeQueue.Add(new XamlElementEndNode( + reader.LineNumber, + reader.LinePosition, + getDepth())); + ((XamlElementEndNode)topNode()).setpropertyObject(true); + nodeQueue.Add(new XamlPropertyComplexEndNode( + reader.LineNumber, + reader.LinePosition, + getDepth())); + ((XamlPropertyComplexEndNode)topNode()).setfinalType((Type)currentState().obj); +// ParserState state = (ParserState)oldStates[oldStates.Count - 1]; +// writer.EndPropertyObject(((PropertyInfo)state.obj).PropertyType); } + tempStateCount --; pop(); } void createTopLevel(string parentName, string className) { Type t = Type.GetType(parentName); + nodeQueue.Add(new XamlDocumentStartNode(reader.LineNumber, reader.LinePosition, getDepth())); + nodeQueue.Add(new XamlElementStartNode( + reader.LineNumber, + reader.LinePosition, + getDepth(), + t.Assembly.FullName, + t.AssemblyQualifiedName, + t, + null)); + + ((XamlElementStartNode)topNode()).setname(className); - writer.CreateTopLevel(t, className); - currentState = new ParserState(); - currentState.type = CurrentType.Object; - currentState.obj = t; +// writer.CreateTopLevel(t, className); + push(CurrentType.Object, t); } void addChild(Type type, string objectName) { - writer.CreateObject(type, objectName); + nodeQueue.Add(new XamlElementStartNode( + reader.LineNumber, + reader.LinePosition, + getDepth(), + type.Assembly.FullName, + type.AssemblyQualifiedName, + type, + null)); + ((XamlElementStartNode)topNode()).setname(objectName); + +// writer.CreateObject(type, objectName); push(CurrentType.Object, type); } void addPropertyChild(Type type, string objectName) { - writer.CreatePropertyObject(type, objectName); +// writer.CreatePropertyObject(type, objectName); + nodeQueue.Add(new XamlElementStartNode( + reader.LineNumber, + reader.LinePosition, + getDepth(), + type.Assembly.FullName, + type.AssemblyQualifiedName, + type, + null)); + ((XamlElementStartNode)topNode()).setname(objectName); + ((XamlElementStartNode)topNode()).setpropertyObject(true); + push(CurrentType.PropertyObject, type); } @@ -366,21 +470,49 @@ namespace Mono.Windows.Serialization { void parseLocalPropertyAttribute() { string propertyName = reader.LocalName; - Type currentType = (Type)currentState.obj; + Type currentType = (Type)currentState().obj; PropertyInfo prop = currentType.GetProperty(propertyName); if (parsedAsEventProperty(currentType, propertyName)) return; if (prop == null) throw new Exception ("Property '" + propertyName + "' not found on '" + currentType.Name + "'."); - - writer.CreateProperty(prop); - - if (prop.PropertyType.IsSubclassOf(typeof(Delegate))) - writer.CreatePropertyDelegate(reader.Value, prop.PropertyType); - else - writer.CreatePropertyText(reader.Value, prop.PropertyType); - - writer.EndProperty(); + nodeQueue.Add(new XamlPropertyNode( + reader.LineNumber, + reader.LinePosition, + getDepth(), + null, + currentType.Assembly.FullName, + currentType.AssemblyQualifiedName, + propertyName, + reader.Value, + reader.NamespaceURI, + BamlAttributeUsage.Default, + false)); + ((XamlPropertyNode)nodeQueue[nodeQueue.Count - 1]).setPropInfo(prop); + + if (!prop.PropertyType.IsSubclassOf(typeof(Delegate))) { + + nodeQueue.Add(new XamlTextNode( + reader.LineNumber, + reader.LinePosition, + getDepth(), + reader.Value)); + + ((XamlTextNode)topNode()).setmode(XamlParseMode.Property); +// writer.CreatePropertyText(reader.Value, prop.PropertyType); + +// writer.EndProperty(); + ((XamlTextNode)topNode()).setfinalType(prop.PropertyType); + } else { +// writer.CreatePropertyDelegate(reader.Value, prop.PropertyType); + nodeQueue.Add(new XamlClrEventNode( + reader.LineNumber, + reader.LinePosition, + getDepth(), + propertyName, + prop, + reader.Value)); + } } bool parsedAsEventProperty(Type currentType, string eventName) @@ -388,9 +520,16 @@ namespace Mono.Windows.Serialization { EventInfo evt = currentType.GetEvent(eventName); if (evt == null) return false; - writer.CreateEvent(evt); - writer.CreateEventDelegate(reader.Value, evt.EventHandlerType); - writer.EndEvent(); + nodeQueue.Add(new XamlClrEventNode( + reader.LineNumber, + reader.LinePosition, + getDepth(), + eventName, + evt, + reader.Value)); +// writer.CreateEvent(evt); +// writer.CreateEventDelegate(reader.Value, evt.EventHandlerType); +// writer.EndEvent(); return true; } @@ -430,34 +569,84 @@ namespace Mono.Windows.Serialization { string attachedTo = reader.LocalName.Substring(0, index); string propertyName = reader.LocalName.Substring(index + 1); - Type currentType = (Type)currentState.obj; + Type currentType = (Type)currentState().obj; ensureDependencyObject(currentType); Type typeAttachedTo = findTypeToAttachTo(attachedTo, propertyName); DependencyProperty dp = getDependencyProperty(typeAttachedTo, propertyName); - writer.CreateDependencyProperty(typeAttachedTo, propertyName, dp.PropertyType); - writer.CreateDependencyPropertyText(reader.Value, dp.PropertyType); - writer.EndDependencyProperty(); + nodeQueue.Add(new XamlPropertyNode( + reader.LineNumber, + reader.LinePosition, + getDepth(), + null, + currentType.Assembly.FullName, + currentType.AssemblyQualifiedName, + propertyName, + reader.Value, + reader.NamespaceURI, + BamlAttributeUsage.Default, + false)); + ((XamlPropertyNode)topNode()).setDP(dp); + + nodeQueue.Add(new XamlTextNode(reader.LineNumber, reader.LinePosition, getDepth(), reader.Value)); + ((XamlTextNode)topNode()).setmode(XamlParseMode.DependencyProperty); + ((XamlTextNode)topNode()).setfinalType(dp.PropertyType); + +// writer.CreateDependencyProperty(typeAttachedTo, propertyName, dp.PropertyType); +// writer.CreateDependencyPropertyText(reader.Value, dp.PropertyType); +// writer.EndDependencyProperty(); } void parseEndElement() { - Debug.WriteLine("IN ENDELEMENT, SWITCHING ON " + currentState.type); - switch (currentState.type) { + Debug.WriteLine("XamlParser: IN ENDELEMENT, SWITCHING ON " + currentState().type); + switch (currentState().type) { case CurrentType.Code: - writer.CreateCode((string)currentState.obj); + nodeQueue.Add(new XamlLiteralContentNode( + reader.LineNumber, + reader.LinePosition, + getDepth(), + (string)currentState().obj)); +// writer.CreateCode((string)currentState().obj); break; case CurrentType.Object: - writer.EndObject(); + nodeQueue.Add(new XamlElementEndNode( + reader.LineNumber, + reader.LinePosition, + getDepth())); +// writer.EndObject(); break; case CurrentType.PropertyObject: - writer.EndPropertyObject((Type)currentState.obj); + nodeQueue.Add(new XamlElementEndNode( + reader.LineNumber, + reader.LinePosition, + getDepth())); + ((XamlElementEndNode)topNode()).setpropertyObject(true); + nodeQueue.Add(new XamlPropertyComplexEndNode( + reader.LineNumber, + reader.LinePosition, + getDepth())); + Debug.WriteLine("XamlParser: XXXXXXXX" + currentState().obj); + Debug.WriteLine("XamlParser: XXXXXXXX" + (currentState().obj is Type)); + ((XamlPropertyComplexEndNode)topNode()).setfinalType((Type)currentState().obj); + Debug.WriteLine("XamlParser: XXXXXXXX" + ((XamlPropertyComplexEndNode)topNode()).finalType); + Debug.WriteLine("TTTTTTTTT " + ((ParserState)oldStates[oldStates.Count - 1]).obj.GetType()); + Debug.WriteLine("TTTTTTTTT " + ((ParserState)oldStates[oldStates.Count - 1]).type); + Debug.WriteLine("TTTTTTTTT " + ((ParserState)oldStates[oldStates.Count - 2]).obj.GetType()); + Debug.WriteLine("TTTTTTTTT " + ((ParserState)oldStates[oldStates.Count - 2]).type); + Debug.WriteLine("TTTTTTTTT " + ((ParserState)oldStates[oldStates.Count - 3]).obj.GetType()); + Debug.WriteLine("TTTTTTTTT " + ((ParserState)oldStates[oldStates.Count - 3]).type); + Debug.WriteLine("TTTTTTTTT " + ((ParserState)oldStates[oldStates.Count - 4]).obj.GetType()); + Debug.WriteLine("TTTTTTTTT " + ((ParserState)oldStates[oldStates.Count - 4]).type); +// writer.EndPropertyObject((Type)currentState().obj); +// return; break; + // these next two happen automatically in the new model case CurrentType.Property: - writer.EndProperty(); +// writer.EndProperty(); break; case CurrentType.DependencyProperty: - writer.EndDependencyProperty(); +// writer.EndDependencyProperty(); break; } pop(); @@ -465,23 +654,26 @@ namespace Mono.Windows.Serialization { void pop() { - Debug.WriteLine("POPPING: " + currentState.type); - if (oldStates.Count == 0) { - currentState = null; - writer.Finish(); + Debug.WriteLine("XamlParser: POPPING: " + currentState().type); + // we are popping the last element + if (oldStates.Count == 1) { +// writer.Finish(); + nodeQueue.Add(new XamlDocumentEndNode( + reader.LineNumber, + reader.LinePosition, + getDepth())); return; } int lastIndex = oldStates.Count - 1; - currentState = (ParserState)oldStates[lastIndex]; oldStates.RemoveAt(lastIndex); } void push(CurrentType type, Object obj) { - Debug.WriteLine("PUSHING: " + type); - oldStates.Add(currentState); - currentState = new ParserState(); + Debug.WriteLine("XamlParser: PUSHING: " + oldStates.Count + " " + type); + ParserState currentState = new ParserState(); currentState.type = type; currentState.obj = obj; + oldStates.Add(currentState); } } } diff --git a/mcs/class/PresentationFramework/PresentationFramework.dll.sources b/mcs/class/PresentationFramework/PresentationFramework.dll.sources index aa60831d94a..796cdc5ace6 100644 --- a/mcs/class/PresentationFramework/PresentationFramework.dll.sources +++ b/mcs/class/PresentationFramework/PresentationFramework.dll.sources @@ -1,6 +1,9 @@ System.Windows.Serialization/IAddChild.cs System.Windows.Serialization/Mapper.cs System.Windows.Serialization/NamespaceMapEntry.cs +System.Windows.Serialization/XamlNodeType.cs +System.Windows.Serialization/XamlParseMode.cs +System.Windows.Serialization/BamlAttributeUsage.cs Mono.Windows.Serialization/CodeWriter.cs Mono.Windows.Serialization/ObjectWriter.cs Mono.Windows.Serialization/Exceptions.cs @@ -8,3 +11,38 @@ Mono.Windows.Serialization/XamlParser.cs Mono.Windows.Serialization/IXamlWriter.cs Assembly/AssemblyInfo.cs ../../build/common/Consts.cs +System.Windows.Serialization/XamlUnknownTagStartNode.cs +System.Windows.Serialization/XamlConstructorParametersEndNode.cs +System.Windows.Serialization/XamlEndAttributesNode.cs +System.Windows.Serialization/XamlDocumentStartNode.cs +System.Windows.Serialization/XamlTextNode.cs +System.Windows.Serialization/XamlDefAttributeNode.cs +System.Windows.Serialization/XamlRoutedEventNode.cs +System.Windows.Serialization/XamlNode.cs +System.Windows.Serialization/XamlPropertyComplexStartNode.cs +System.Windows.Serialization/XamlPropertyComplexEndNode.cs +System.Windows.Serialization/XamlPropertyIDictionaryEndNode.cs +System.Windows.Serialization/XamlUnknownAttributeNode.cs +System.Windows.Serialization/XamlPIMappingNode.cs +System.Windows.Serialization/XamlDocumentEndNode.cs +System.Windows.Serialization/XamlClrEventNode.cs +System.Windows.Serialization/XamlKeyElementStartNode.cs +System.Windows.Serialization/XamlPropertyArrayEndNode.cs +System.Windows.Serialization/XamlPropertyArrayStartNode.cs +System.Windows.Serialization/XamlElementEndNode.cs +System.Windows.Serialization/XamlElementStartNode.cs +System.Windows.Serialization/XamlLiteralContentNode.cs +System.Windows.Serialization/XamlDefTagNode.cs +System.Windows.Serialization/XamlConstructorParametersStartNode.cs +System.Windows.Serialization/XamlPropertyIDictionaryStartNode.cs +System.Windows.Serialization/XamlPropertyIListEndNode.cs +System.Windows.Serialization/XamlPropertyNode.cs +System.Windows.Serialization/XamlKeyElementEndNode.cs +System.Windows.Serialization/XamlAttributeNode.cs +System.Windows.Serialization/XamlPropertyIListStartNode.cs +System.Windows.Serialization/XamlPropertyWithTypeNode.cs +System.Windows.Serialization/XamlConstructorParameterTypeNode.cs +System.Windows.Serialization/XamlDefAttributeKeyTypeNode.cs +System.Windows.Serialization/XamlUnknownTagEndNode.cs +System.Windows.Serialization/XamlLanguageNode.cs + diff --git a/mcs/class/PresentationFramework/System.Windows.Serialization/data-classes-builder.pl b/mcs/class/PresentationFramework/System.Windows.Serialization/data-classes-builder.pl new file mode 100644 index 00000000000..d2ebd2e8b32 --- /dev/null +++ b/mcs/class/PresentationFramework/System.Windows.Serialization/data-classes-builder.pl @@ -0,0 +1,199 @@ +open FILE, "data-classes.txt"; + +%classes; + +while ($line = ) { + chop $line; + $properties = ""; + $magicprops = ""; + if (index($line, ":") == -1) { + $class = $line; + if (index($line, ";") != -1) { + $class = substr($line, 0, index($line, ";")); + $magicprops = substr($line, index($line, ";") + 2); + print "$class: $magicprops\n"; + } + } else { + $class = substr($line, 0, index($line, ":")); + $properties = substr($line, index($line, ":") + 2); + if (index($properties, ";") != -1) { + $magicprops = substr($properties, index($properties, ";") + 2); + $properties = substr($properties, 0, index($properties, ";")); + } + } + if ($line =~ m/Xaml[^(]+\(/) { + $parent = $class; + $parent =~ s/(Xaml[^(]+)\(([^)]+)\).*/\2/; + $clname = $class; + $clname =~ s/(Xaml[^(]+)\(([^)]+)\).*/\1/; + $class = $clname; + } else { + $parent = "XamlNode"; + } + $classes{$class} = { parent => $parent, + properties => $properties, + magicprops => $magicprops }; +} + +sub get_parent { + my $x = shift; + return $classes{$x}->{"parent"}; +} +sub get_properties { + my $x = shift; + return $classes{$x}->{"properties"}; +} +sub get_magic_properties { + my $x = shift; + return $classes{$x}->{"magicprops"}; +} + + +sub get_extended_params_list { + my $x = shift; + my $params = ""; + while ($x ne "XamlNode") { + $x = &get_parent($x); + $params = &get_properties($x) . ", " . $params; + $params =~ s/, $//; + } + $params =~ s/^XamlNodeType tokenType, //; + return $params; +} + +sub has_parent { + my $x = shift; + my $parent = shift; + while ($x ne "object") { + if ($x eq $parent) { + return 1; + } + $x = &get_parent($x); + } + return 0; +} + +for $class (keys %classes) { + print "$class.cs\n"; + open X, ">$class.cs"; + print X "// THIS FILE AUTOMATICALLY GENERATED BY data-classes-builder.pl\n"; + print X "// EDITING IS PROBABLY UNWISE\n"; + print X "namespace System.Windows.Serialization {\n"; + print X "using System;\n"; + print X "using System.Reflection;\n"; + print X "using System.Windows;\n"; + $parent = &get_parent($class); + + $props = &get_properties($class); + @propl = split /, /, $props; + + $eprops = &get_extended_params_list($class); + @epropl = split /, /, $eprops; + + $allprops = $eprops; + $allprops .= ", $props" unless ($props eq ""); + @allpropl = split /, /, $allprops; + my @allpropl2 = @allpropl; + for $prop (@allpropl2) { + $prop =~ s/^\+//; + } + $allprops = join ", ", @allpropl2; + + $mprops = &get_magic_properties($class); + @mpropl = split /, /, $mprops; + + $xamlnodetype = "$class"; + $xamlnodetype =~ s/^Xaml(.+)Node$/\1/; + $xamlnodetype = "XamlNodeType.$xamlnodetype"; + + print X "public class $class : " . $parent . " { \n"; + + # member variables + for $prop (@propl) { + next if $prop =~ m/^\+/; + print X "\tprivate $prop;\n"; + } + for $prop (@mpropl) { + next if $prop =~ m/^\+/; + $x = $prop; + $x =~ s/ / _/; + print X "\tprivate $x;\n"; + } + print X "\n\n"; + + # constructor + if ($class eq "XamlNode") { + print X "\tpublic $class($props)\n"; + print X "\t{\n"; + for $prop (@propl) { + $propname = substr($prop, index($prop, " ") + 1); + print X "\t\tthis.$propname = $propname;\n"; + } + print X "\t}\n"; + } else { + print X "\tpublic $class($allprops)\n"; + print X "\t\t: this("; + my @allpropnames; + push @allpropnames, $xamlnodetype; + for $prop (@allpropl) { + push @allpropnames, substr($prop, index($prop, " ") + 1); + } + print X (join ", ", @allpropnames); + print X ")\n\t{}\n\n\n"; + + print X "\tinternal $class(XamlNodeType type, $allprops)\n"; + + my @epropnamel; + for $prop (@epropl) { + push @epropnamel, substr($prop, index($prop, " ") + 1); + } + $epropnames = join ", ", @epropnamel; + print X "\t\t: base(type, $epropnames)\n"; + print X "\t{\n"; + for $prop (@propl) { + $propname = substr($prop, index($prop, " ") + 1); + if ($prop =~ m/^\+/) { + $func = substr($propname, 0, 1); + $func =~ tr/a-z/A-Z/; + $func = "set$func" . substr($propname, 1); + print X "\t\tthis.$func($propname);\n"; + } else { + print X "\t\tthis.$propname = $propname;\n"; + } + } + print X "\t}\n"; + } + + #property accessors + for $prop (@propl) { + $proptype = substr($prop, 0, index($prop, " ")); + $fieldname = substr($prop, index($prop, " ") + 1); + + $propname = substr($fieldname, 0, 1); + $propname =~ tr/a-z/A-Z/; + $propname .= substr($fieldname, 1); + + if ($proptype =~ m/^\+/) { + next; + } + + print X "\n\tpublic $proptype $propname {\n"; + print X "\t\tget { return $fieldname; }\n"; + print X "\t}\n"; + } + for $prop (@mpropl) { + $proptype = substr($prop, 0, index($prop, " ")); + $propname = substr($prop, index($prop, " ") + 1); + $fieldname = "_$propname"; + + + print X "\n\tpublic $proptype $propname {\n"; + print X "\t\tget { return $fieldname; }\n"; + print X "\t}\n"; + print X "\n\tinternal void set$propname($proptype v) {\n"; + print X "\t\t$fieldname = v;\n"; + print X "\t}\n"; + } + print X "}\n}\n\n"; + close X; +} diff --git a/mcs/class/PresentationFramework/System.Windows.Serialization/data-classes.txt b/mcs/class/PresentationFramework/System.Windows.Serialization/data-classes.txt new file mode 100644 index 00000000000..e9eaf80b239 --- /dev/null +++ b/mcs/class/PresentationFramework/System.Windows.Serialization/data-classes.txt @@ -0,0 +1,34 @@ +XamlAttributeNode; string Value +XamlClrEventNode(XamlAttributeNode): string eventName, MemberInfo eventMember, +string value +XamlConstructorParametersEndNode +XamlConstructorParametersStartNode +XamlConstructorParameterTypeNode: string valueTypeFullName, string valueAssemblyName, Type valueElementType +XamlDefAttributeKeyTypeNode(XamlAttributeNode): string assemblyName, string valueType +XamlDefAttributeNode(XamlAttributeNode): string name, +string value +XamlDefTagNode(XamlAttributeNode): bool isEmptyElement, System.Xml.XmlReader xmlReader, string defTagName +XamlDocumentEndNode +XamlDocumentStartNode +XamlElementStartNode: string assemblyName, string typeFullName, Type elementType, Type serializerType; string name, bool propertyObject +XamlElementEndNode; bool propertyObject +XamlEndAttributesNode: bool compact +XamlKeyElementEndNode(XamlElementEndNode) +XamlKeyElementStartNode(XamlElementStartNode) +XamlLanguageNode: string language +XamlLiteralContentNode: string content +XamlNode(object): XamlNodeType tokenType, int lineNumber, int linePosition, int depth +XamlPIMappingNode: string xmlNamespace, string clrNamespace, string assemblyName +XamlPropertyArrayEndNode +XamlPropertyArrayStartNode(XamlPropertyComplexStartNode) +XamlPropertyComplexEndNode; Type finalType +XamlPropertyComplexStartNode: Object propertyMember, string assemblyName, string typeFullName, string propertyName; PropertyInfo PropInfo, DependencyProperty DP, MethodInfo AttachedPropertySetter +XamlPropertyIDictionaryEndNode +XamlPropertyIDictionaryStartNode(XamlPropertyComplexStartNode) +XamlPropertyIListEndNode +XamlPropertyIListStartNode(XamlPropertyComplexStartNode) +XamlPropertyNode(XamlPropertyComplexStartNode): string value, string xmlNamespace, BamlAttributeUsage attributeUsage, bool complexAsSimple +XamlPropertyWithTypeNode(XamlPropertyComplexStartNode): String valueTypeFullName, string valueAssemblyFullName, Type valueElementType, string valueSerializerTypeFullName, string valueSerializerTypeAssemblyName, string xmlNamespace +XamlRoutedEventNode(XamlAttributeNode): System.Windows.RoutedEvent routedEvent, string assemblyName, string typeFullName, string routedEventName, +string value +XamlTextNode: string textContent; XamlParseMode mode, Type finalType +XamlUnknownAttributeNode(XamlAttributeNode): string xmlNamespace, string name, +string value +XamlUnknownTagEndNode +XamlUnknownTagStartNode(XamlAttributeNode): string xmlNamespace, +string value diff --git a/mcs/class/PresentationFramework/Test/CodeWriter.cs b/mcs/class/PresentationFramework/Test/CodeWriter.cs index a323db79809..1b08b87af9e 100644 --- a/mcs/class/PresentationFramework/Test/CodeWriter.cs +++ b/mcs/class/PresentationFramework/Test/CodeWriter.cs @@ -44,26 +44,23 @@ namespace MonoTests.System.Windows.Serialization [TestFixture] public class CodeWriterTest { - CodeWriter cw; - StringWriter w; + string code; [SetUp] public void GetReady() { - ICodeGenerator generator = (new Microsoft.CSharp.CSharpCodeProvider()).CreateGenerator(); - w = new StringWriter(); - cw = new CodeWriter(generator, w, false); } [TearDown] - public void Clean() {} + public void Clean() + { + code = null; + } [Test] public void TestTopLevel() { - cw.CreateTopLevel(typeof(ConsoleApp), null); - cw.EndObject(); - cw.Finish(); + code = ""; compare( "namespace DefaultNamespace {\n"+ " public class derivedConsoleApp : Xaml.TestVocab.Console.ConsoleApp {\n" + @@ -74,60 +71,30 @@ public class CodeWriterTest { ); } -#if NET_2_0 [Test] - public void TestPartialTopLevel() - { - // we duplicate the setup code here, with the one change that - // the third parameter (determining partialness) of CodeWriter's - // constructor is set to true - ICodeGenerator generator = (new Microsoft.CSharp.CSharpCodeProvider()).CreateGenerator(); - w = new StringWriter(); - cw = new CodeWriter(generator, w, true); - cw.CreateTopLevel(typeof(ConsoleApp), null); - cw.EndObject(); - cw.Finish(); - compare( - "namespace DefaultNamespace {\n"+ - " public partial class derivedConsoleApp : Xaml.TestVocab.Console.ConsoleApp {\n" + - " private derivedConsoleApp() {\n"+ - " }\n" + - " }\n" + - "}" - ); - } -#else +#if !NET_2_0 [ExpectedException(typeof(Exception), "Cannot create partial class")] - [Test] +#endif public void TestPartialTopLevel() { - // we duplicate the setup code here, with the one change that - // the third parameter (determining partialness) of CodeWriter's - // constructor is set to true - ICodeGenerator generator = (new Microsoft.CSharp.CSharpCodeProvider()).CreateGenerator(); - w = new StringWriter(); - cw = new CodeWriter(generator, w, true); - cw.CreateTopLevel(typeof(ConsoleApp), null); - cw.EndObject(); - cw.Finish(); + code = ""; compare( "namespace DefaultNamespace {\n"+ " public partial class derivedConsoleApp : Xaml.TestVocab.Console.ConsoleApp {\n" + " private derivedConsoleApp() {\n"+ " }\n" + " }\n" + - "}" + "}", + true ); } -#endif [Test] public void TestTopLevelWithClassName() { - cw.CreateTopLevel(typeof(ConsoleApp), "MyConsoleApp"); - cw.EndObject(); - cw.Finish(); + code = "\n"+ + ""; compare( "namespace DefaultNamespace {\n"+ " public class MyConsoleApp : Xaml.TestVocab.Console.ConsoleApp {\n" + @@ -141,9 +108,8 @@ public class CodeWriterTest { [Test] public void TestTopLevelWithClassNameAndNamespace() { - cw.CreateTopLevel(typeof(ConsoleApp), "Test.Thing.MyConsoleApp"); - cw.EndObject(); - cw.Finish(); + code = "\n"+ + ""; compare( "namespace Test.Thing {\n"+ " public class MyConsoleApp : Xaml.TestVocab.Console.ConsoleApp {\n" + @@ -157,11 +123,9 @@ public class CodeWriterTest { [Test] public void TestSimplestAddChild() { - cw.CreateTopLevel(typeof(ConsoleApp), null); - cw.CreateObject(typeof(ConsoleWriter), null); - cw.EndObject(); - cw.EndObject(); - cw.Finish(); + code = "\n"+ + "" + + ""; compare( "namespace DefaultNamespace {\n"+ " public class derivedConsoleApp : Xaml.TestVocab.Console.ConsoleApp {\n" + @@ -177,11 +141,9 @@ public class CodeWriterTest { [Test] public void TestSimplestAddChildWithInstanceName() { - cw.CreateTopLevel(typeof(ConsoleApp), null); - cw.CreateObject(typeof(ConsoleWriter), "XX"); - cw.EndObject(); - cw.EndObject(); - cw.Finish(); + code = "\n"+ + "" + + ""; compare( "namespace DefaultNamespace {\n"+ " public class derivedConsoleApp : Xaml.TestVocab.Console.ConsoleApp {\n" + @@ -198,12 +160,9 @@ public class CodeWriterTest { [Test] public void TestSimplestAddChildAndText() { - cw.CreateTopLevel(typeof(ConsoleApp), null); - cw.CreateObject(typeof(ConsoleWriter), null); - cw.CreateObjectText("Hello"); - cw.EndObject(); - cw.EndObject(); - cw.Finish(); + code = "\n"+ + "Hello" + + ""; compare( "namespace DefaultNamespace {\n"+ " public class derivedConsoleApp : Xaml.TestVocab.Console.ConsoleApp {\n" + @@ -220,14 +179,9 @@ public class CodeWriterTest { [Test] public void TestTextProperty() { - cw.CreateTopLevel(typeof(ConsoleApp), null); - cw.CreateObject(typeof(ConsoleWriter), null); - cw.CreateProperty(typeof(ConsoleWriter).GetProperty("Text")); - cw.CreatePropertyText("Hello", typeof(ConsoleValue)); - cw.EndProperty(); - cw.EndObject(); - cw.EndObject(); - cw.Finish(); + code = "\n"+ + "" + + ""; compare( "namespace DefaultNamespace {\n"+ " public class derivedConsoleApp : Xaml.TestVocab.Console.ConsoleApp {\n" + @@ -244,14 +198,9 @@ public class CodeWriterTest { [Test] public void TestDependencyProperty() { - cw.CreateTopLevel(typeof(ConsoleApp), null); - cw.CreateObject(typeof(ConsoleWriter), null); - cw.CreateDependencyProperty(typeof(ConsoleApp), "Repetitions", typeof(int)); - cw.CreateDependencyPropertyText("3", typeof(int)); - cw.EndDependencyProperty(); - cw.EndObject(); - cw.EndObject(); - cw.Finish(); + code = "\n"+ + "" + + ""; compare( "namespace DefaultNamespace {\n"+ " public class derivedConsoleApp : Xaml.TestVocab.Console.ConsoleApp {\n" + @@ -271,15 +220,11 @@ public class CodeWriterTest { [Test] public void TestObjectAsPropertyValue() { - cw.CreateTopLevel(typeof(ConsoleApp), null); - cw.CreateObject(typeof(ConsoleReader), null); - cw.CreateProperty(typeof(ConsoleReader).GetProperty("Prompt")); - cw.CreatePropertyObject(typeof(ConsoleWriter), null); - cw.EndPropertyObject(typeof(ConsoleWriter)); - cw.EndProperty(); - cw.EndObject(); - cw.EndObject(); - cw.Finish(); + code = "\n"+ + "\n" + + "\n" + + "\n" + + ""; compare( "namespace DefaultNamespace {\n"+ " public class derivedConsoleApp : Xaml.TestVocab.Console.ConsoleApp {\n" + @@ -298,15 +243,11 @@ public class CodeWriterTest { [Test] public void TestObjectAsPropertyValueWithSpecifiedName() { - cw.CreateTopLevel(typeof(ConsoleApp), null); - cw.CreateObject(typeof(ConsoleReader), null); - cw.CreateProperty(typeof(ConsoleReader).GetProperty("Prompt")); - cw.CreatePropertyObject(typeof(ConsoleWriter), "prompt"); - cw.EndPropertyObject(typeof(ConsoleWriter)); - cw.EndProperty(); - cw.EndObject(); - cw.EndObject(); - cw.Finish(); + code = "\n"+ + "\n" + + "\n" + + "\n" + + ""; compare( "namespace DefaultNamespace {\n"+ " public class derivedConsoleApp : Xaml.TestVocab.Console.ConsoleApp {\n" + @@ -326,12 +267,7 @@ public class CodeWriterTest { [Test] public void TestEvent() { - cw.CreateTopLevel(typeof(ConsoleApp), null); - cw.CreateEvent(typeof(ConsoleApp).GetEvent("SomethingHappened")); - cw.CreateEventDelegate("handleSomething", typeof(SomethingHappenedHandler)); - cw.EndEvent(); - cw.EndObject(); - cw.Finish(); + code = ""; compare( "namespace DefaultNamespace {\n"+ " public class derivedConsoleApp : Xaml.TestVocab.Console.ConsoleApp {\n" + @@ -346,14 +282,9 @@ public class CodeWriterTest { [Test] public void TestDelegateAsPropertyValue() { - cw.CreateTopLevel(typeof(ConsoleApp), null); - cw.CreateObject(typeof(ConsoleWriter), null); - cw.CreateProperty(typeof(ConsoleWriter).GetProperty("Filter")); - cw.CreatePropertyDelegate("filterfilter", typeof(Filter)); - cw.EndProperty(); - cw.EndObject(); - cw.EndObject(); - cw.Finish(); + code = "\n"+ + "\n"+ + ""; compare( "namespace DefaultNamespace {\n"+ " public class derivedConsoleApp : Xaml.TestVocab.Console.ConsoleApp {\n" + @@ -369,8 +300,15 @@ public class CodeWriterTest { private void compare(string expected) + { + compare(expected, false); + } + private void compare(string expected, bool isPartial) { int i, j; + ICodeGenerator generator = (new Microsoft.CSharp.CSharpCodeProvider()).CreateGenerator(); + string mapping = "\n"; + string w = CodeWriter.Parse(new XmlTextReader(new StringReader(mapping + code)), generator, isPartial); string[] actualLines = w.ToString().Split('\n'); for (i = 0; i < actualLines.Length; i++) { // set commented-out lines to null diff --git a/mcs/class/PresentationFramework/Test/ObjectWriter.cs b/mcs/class/PresentationFramework/Test/ObjectWriter.cs index aa2f0e80cd5..73618b8c251 100644 --- a/mcs/class/PresentationFramework/Test/ObjectWriter.cs +++ b/mcs/class/PresentationFramework/Test/ObjectWriter.cs @@ -44,23 +44,23 @@ namespace MonoTests.System.Windows.Serialization [TestFixture] public class ObjectWriterTest { - ObjectWriter ow; + string code; [SetUp] public void GetReady() { - ow = new ObjectWriter(); } [TearDown] - public void Clean() {} + public void Clean() + { + code = null; + } [Test] public void TestTopLevel() { - ow.CreateTopLevel(typeof(ConsoleApp), null); - ow.EndObject(); - ow.Finish(); + code = ""; ConsoleApp app = new ConsoleApp(); compare(app); } @@ -68,9 +68,8 @@ public class ObjectWriterTest { [Test] public void TestTopLevelWithClassName() { - ow.CreateTopLevel(typeof(ConsoleApp), "MyConsoleApp"); - ow.EndObject(); - ow.Finish(); + code = "\n"+ + ""; ConsoleApp app = new ConsoleApp(); compare(app); } @@ -78,9 +77,8 @@ public class ObjectWriterTest { [Test] public void TestTopLevelWithClassNameAndNamespace() { - ow.CreateTopLevel(typeof(ConsoleApp), "Test.Thing.MyConsoleApp"); - ow.EndObject(); - ow.Finish(); + code = "\n"+ + ""; ConsoleApp app = new ConsoleApp(); compare(app); } @@ -88,12 +86,10 @@ public class ObjectWriterTest { [Test] public void TestSimplestAddChild() { - ow.CreateTopLevel(typeof(ConsoleApp), null); - ow.CreateObject(typeof(ConsoleWriter), null); - ow.EndObject(); - ow.EndObject(); - ow.Finish(); + code = "\n"+ + "" + + ""; ConsoleApp app = new ConsoleApp(); ConsoleWriter writer = new ConsoleWriter(); app.AddChild(writer); @@ -104,11 +100,9 @@ public class ObjectWriterTest { [Test] public void TestSimplestAddChildWithInstanceName() { - ow.CreateTopLevel(typeof(ConsoleApp), null); - ow.CreateObject(typeof(ConsoleWriter), "XX"); - ow.EndObject(); - ow.EndObject(); - ow.Finish(); + code = "\n"+ + "" + + ""; ConsoleApp app = new ConsoleApp(); ConsoleWriter writer = new ConsoleWriter(); @@ -121,12 +115,9 @@ public class ObjectWriterTest { [Test] public void TestSimplestAddChildAndText() { - ow.CreateTopLevel(typeof(ConsoleApp), null); - ow.CreateObject(typeof(ConsoleWriter), null); - ow.CreateObjectText("Hello"); - ow.EndObject(); - ow.EndObject(); - ow.Finish(); + code = "\n"+ + "Hello" + + ""; ConsoleApp app = new ConsoleApp(); ConsoleWriter writer = new ConsoleWriter(); @@ -139,14 +130,9 @@ public class ObjectWriterTest { [Test] public void TestTextProperty() { - ow.CreateTopLevel(typeof(ConsoleApp), null); - ow.CreateObject(typeof(ConsoleWriter), null); - ow.CreateProperty(typeof(ConsoleWriter).GetProperty("Text")); - ow.CreatePropertyText("Hello", typeof(ConsoleValue)); - ow.EndProperty(); - ow.EndObject(); - ow.EndObject(); - ow.Finish(); + code = "\n"+ + "" + + ""; ConsoleApp app = new ConsoleApp(); ConsoleWriter writer = new ConsoleWriter(); @@ -159,14 +145,9 @@ public class ObjectWriterTest { [Test] public void TestDependencyProperty() { - ow.CreateTopLevel(typeof(ConsoleApp), null); - ow.CreateObject(typeof(ConsoleWriter), null); - ow.CreateDependencyProperty(typeof(ConsoleApp), "Repetitions", typeof(int)); - ow.CreateDependencyPropertyText("3", typeof(int)); - ow.EndDependencyProperty(); - ow.EndObject(); - ow.EndObject(); - ow.Finish(); + code = "\n"+ + "" + + ""; ConsoleApp app = new ConsoleApp(); ConsoleWriter writer = new ConsoleWriter(); @@ -179,15 +160,11 @@ public class ObjectWriterTest { [Test] public void TestObjectAsPropertyValue() { - ow.CreateTopLevel(typeof(ConsoleApp), null); - ow.CreateObject(typeof(ConsoleReader), null); - ow.CreateProperty(typeof(ConsoleReader).GetProperty("Prompt")); - ow.CreatePropertyObject(typeof(ConsoleWriter), null); - ow.EndPropertyObject(typeof(ConsoleWriter)); - ow.EndProperty(); - ow.EndObject(); - ow.EndObject(); - ow.Finish(); + code = "\n"+ + "\n" + + "\n" + + "\n" + + ""; ConsoleApp app = new ConsoleApp(); ConsoleReader reader = new ConsoleReader(); @@ -201,7 +178,9 @@ public class ObjectWriterTest { private void compare(object expected) { - Assert.AreEqual(expected, ow.instance); + string mapping = "\n"; + object o = ObjectWriter.Parse(new XmlTextReader(new StringReader(mapping + code))); + Assert.AreEqual(expected, o); } } diff --git a/mcs/class/PresentationFramework/Test/XamlParser.cs b/mcs/class/PresentationFramework/Test/XamlParser.cs index 79c81293ea4..d70bce4e17f 100644 --- a/mcs/class/PresentationFramework/Test/XamlParser.cs +++ b/mcs/class/PresentationFramework/Test/XamlParser.cs @@ -25,27 +25,6 @@ // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. // -// -// -// -// -// As you may be aware, testing a parser is something of a beastly job. The -// approach taken by these tests is to feed a file to XamlParser and see if it -// tells the code generator to do what you'd expect. This tests both the parsing -// and type-checking bits of XamlParser. -// -// The various Happening classes each represent methods on the IXamlWriter -// interface that XamlParser could call. The constructor of a Happening takes -// the same arguments as the IXamlWriter method it represents, and merely stashes -// those values in the suitable public fields. -// -// The ParserTester class takes a Xaml document and a list of Happenings, and -// handles comparison of the calls to ParserTester's methods to the expected -// sequence of Happenings. -// -// I think this strikes a tolerable balance between the need to keep the tests -// simple and the need to avoid writing 10 zillion lines of hard-to-follow test -// code. using NUnit.Framework; using System; @@ -54,6 +33,7 @@ using System.IO; using System.Xml; using System.Reflection; using System.Windows; +using System.Windows.Serialization; using Mono.Windows.Serialization; using Xaml.TestVocab.Console; @@ -61,7 +41,7 @@ namespace MonoTests.System.Windows.Serialization { [TestFixture] -public class XamlParserTest : Assertion { +public class XamlParserTest { const string MAPPING = "\n"; [SetUp] @@ -73,28 +53,44 @@ public class XamlParserTest : Assertion { [TearDown] public void Clean() {} + private void makeGoBang(string s) + { + XamlNode n; + XamlParser p = new XamlParser(new StringReader(s)); + do { + n = p.GetNextNode(); + } while (!(n is XamlDocumentEndNode)); + } + [Test] [ExpectedException(typeof(Exception), "Unknown processing instruction.")] public void TestIncorrectPIName() { string s = "\n"; - ParserTester pt = new ParserTester(s, - new CreateTopLevelHappening(typeof(ConsoleApp), null), - new EndObjectHappening(), - new FinishHappening()); - pt.Test(); - + makeGoBang(s); } [Test] public void TestTopLevel() { string s = ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), null), - new EndObjectHappening(), - new FinishHappening()); - pt.Test(); + XamlNode n; + XamlParser p = new XamlParser(new StringReader(MAPPING + s)); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlDocumentStartNode, "A1"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementStartNode, "B1"); + Assert.AreEqual(0, n.Depth, "B2"); + Assert.AreEqual(((XamlElementStartNode)n).ElementType, typeof(ConsoleApp), "B3"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementEndNode, "C1"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlDocumentEndNode, "D1"); + } [Test] @@ -102,11 +98,7 @@ public class XamlParserTest : Assertion { public void TestTopLevelWithIncorrectClassName() { string s = ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), null), - new EndObjectHappening(), - new FinishHappening()); - pt.Test(); + makeGoBang(MAPPING + s); } [Test] @@ -114,11 +106,8 @@ public class XamlParserTest : Assertion { public void TestTopLevelWithWrongEndingTag() { string s = ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), null), - new EndObjectHappening(), - new FinishHappening()); - pt.Test(); + makeGoBang(MAPPING + s); + } [Test] @@ -126,11 +115,8 @@ public class XamlParserTest : Assertion { public void TestTopLevelWithoutNamespace() { string s = ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), null), - new EndObjectHappening(), - new FinishHappening()); - pt.Test(); + makeGoBang(MAPPING + s); + } [Test] @@ -138,11 +124,23 @@ public class XamlParserTest : Assertion { { string s = "\n"+ ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), "nnn"), - new EndObjectHappening(), - new FinishHappening()); - pt.Test(); + XamlNode n; + XamlParser p = new XamlParser(new StringReader(MAPPING + s)); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlDocumentStartNode, "A1"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementStartNode, "B1"); + Assert.AreEqual(0, n.Depth, "B2"); + Assert.AreEqual("nnn", ((XamlElementStartNode)n).name, "B3"); + Assert.AreEqual(((XamlElementStartNode)n).ElementType, typeof(ConsoleApp), "B4"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementEndNode, "C1"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlDocumentEndNode, "D1"); } [Test] @@ -151,12 +149,7 @@ public class XamlParserTest : Assertion { { string s = "\n"+ ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), "nnn"), // this is a lie, actually we expect - // an exception just before this - new EndObjectHappening(), - new FinishHappening()); - pt.Test(); + makeGoBang(MAPPING + s); } [Test] @@ -165,13 +158,32 @@ public class XamlParserTest : Assertion { string s = "\n"+ "" + ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), null), - new CreateObjectHappening(typeof(ConsoleWriter), null), - new EndObjectHappening(), - new EndObjectHappening(), - new FinishHappening()); - pt.Test(); + + XamlNode n; + XamlParser p = new XamlParser(new StringReader(MAPPING + s)); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlDocumentStartNode); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementStartNode); + Assert.AreEqual(n.Depth, 0); + Assert.AreEqual(((XamlElementStartNode)n).ElementType, typeof(ConsoleApp)); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementStartNode); + Assert.AreEqual(n.Depth, 1); + Assert.AreEqual(((XamlElementStartNode)n).ElementType, typeof(ConsoleWriter)); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementEndNode); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementEndNode); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlDocumentEndNode); + } [Test] @@ -180,13 +192,33 @@ public class XamlParserTest : Assertion { string s = "\n"+ "" + ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), null), - new CreateObjectHappening(typeof(ConsoleWriter), "XXX"), - new EndObjectHappening(), - new EndObjectHappening(), - new FinishHappening()); - pt.Test(); + + XamlNode n; + XamlParser p = new XamlParser(new StringReader(MAPPING + s)); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlDocumentStartNode, "A1"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementStartNode, "B1"); + Assert.AreEqual(n.Depth, 0, "B2"); + Assert.AreEqual(((XamlElementStartNode)n).ElementType, typeof(ConsoleApp), "B3"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementStartNode, "C1"); + Assert.AreEqual(1, n.Depth, "C2"); + Assert.AreEqual("XXX", ((XamlElementStartNode)n).name, "C3"); + Assert.AreEqual(((XamlElementStartNode)n).ElementType, typeof(ConsoleWriter), "C4"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementEndNode, "D1"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementEndNode, "E1"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlDocumentEndNode, "F1"); + } @@ -197,13 +229,7 @@ public class XamlParserTest : Assertion { string s = "\n"+ "" + ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), null), - new CreateObjectHappening(typeof(ConsoleWriter), null), - new EndObjectHappening(), - new EndObjectHappening(), - new FinishHappening()); - pt.Test(); + makeGoBang(MAPPING + s); } [Test] @@ -213,13 +239,7 @@ public class XamlParserTest : Assertion { string s = "\n"+ "" + ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), null), - new CreateObjectHappening(typeof(ConsoleWriter), "abc"), - new EndObjectHappening(), - new EndObjectHappening(), - new FinishHappening()); - pt.Test(); + makeGoBang(MAPPING + s); } @@ -229,14 +249,36 @@ public class XamlParserTest : Assertion { string s = "\n"+ "Hello" + ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), null), - new CreateObjectHappening(typeof(ConsoleWriter), null), - new CreateObjectTextHappening("Hello"), - new EndObjectHappening(), - new EndObjectHappening(), - new FinishHappening()); - pt.Test(); + + XamlNode n; + XamlParser p = new XamlParser(new StringReader(MAPPING + s)); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlDocumentStartNode); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementStartNode); + Assert.AreEqual(n.Depth, 0); + Assert.AreEqual(((XamlElementStartNode)n).ElementType, typeof(ConsoleApp)); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementStartNode); + Assert.AreEqual(n.Depth, 1); + Assert.AreEqual(((XamlElementStartNode)n).ElementType, typeof(ConsoleWriter)); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlTextNode); + Assert.AreEqual(((XamlTextNode)n).TextContent, "Hello"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementEndNode); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementEndNode); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlDocumentEndNode); + } [Test] @@ -245,55 +287,72 @@ public class XamlParserTest : Assertion { string s = "\n"+ "" + ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), null), - new CreateObjectHappening(typeof(ConsoleWriter), null), - new CreatePropertyHappening(typeof(ConsoleWriter).GetProperty("Text")), - new CreatePropertyTextHappening("Hello", typeof(ConsoleValue)), - new EndPropertyHappening(), - new EndObjectHappening(), //ConsoleWriter - new EndObjectHappening(), //ConsoleApp - new FinishHappening()); - pt.Test(); + + XamlNode n; + XamlParser p = new XamlParser(new StringReader(MAPPING + s)); + + basicPropertyTestStream(p, 0); } [Test] - [ExpectedException(typeof(Exception), "Property 'Texxxt' not found on 'ConsoleWriter'.")] - public void TestTextPropertyWithIncorrectName() + public void TestTextPropertyAsElement() { string s = "\n"+ - "" + + "\n" + + "Hello\n" + + "\n" + ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), null), - new CreateObjectHappening(typeof(ConsoleWriter), null), - new CreatePropertyHappening(typeof(ConsoleWriter).GetProperty("Text")), - new CreatePropertyTextHappening("Hello", typeof(ConsoleValue)), - new EndPropertyHappening(), - new EndObjectHappening(), //ConsoleWriter - new EndObjectHappening(), //ConsoleApp - new FinishHappening()); - pt.Test(); + XamlParser p = new XamlParser(new StringReader(MAPPING + s)); + + basicPropertyTestStream(p, 1); + } + + + + private void basicPropertyTestStream(XamlParser p, int depthIncreaseForProperty) + { + XamlNode n; + n = p.GetNextNode(); + Assert.IsTrue(n is XamlDocumentStartNode, "A1"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementStartNode, "B1"); + Assert.AreEqual(0, n.Depth, "B2"); + Assert.AreEqual(((XamlElementStartNode)n).ElementType, typeof(ConsoleApp), "B3"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementStartNode, "C1"); + Assert.AreEqual(1, n.Depth, "C2"); + Assert.AreEqual(((XamlElementStartNode)n).ElementType, typeof(ConsoleWriter), "C3"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlPropertyNode, "D1"); + Assert.AreEqual(1 + depthIncreaseForProperty, n.Depth, "D2"); + Assert.AreEqual(((XamlPropertyNode)n).PropInfo, typeof(ConsoleWriter).GetProperty("Text"), "D3"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlTextNode, "E1"); + Assert.AreEqual(((XamlTextNode)n).TextContent, "Hello", "E2"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementEndNode, "F1"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementEndNode, "F2"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlDocumentEndNode, "F3"); + } [Test] - public void TestTextPropertyAsElement() + [ExpectedException(typeof(Exception), "Property 'Texxxt' not found on 'ConsoleWriter'.")] + public void TestTextPropertyWithIncorrectName() { string s = "\n"+ - "\n" + - "Hello\n" + - "\n" + + "" + ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), null), - new CreateObjectHappening(typeof(ConsoleWriter), null), - new CreatePropertyHappening(typeof(ConsoleWriter).GetProperty("Text")), - new CreatePropertyTextHappening("Hello", typeof(ConsoleValue)), - new EndPropertyHappening(), - new EndObjectHappening(), //ConsoleWriter - new EndObjectHappening(), //ConsoleApp - new FinishHappening()); - pt.Test(); + makeGoBang(MAPPING + s); } [Test] @@ -305,16 +364,7 @@ public class XamlParserTest : Assertion { "Hello\n"+ "\n" + ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), null), - new CreateObjectHappening(typeof(ConsoleWriter), null), - new CreatePropertyHappening(typeof(ConsoleWriter).GetProperty("Text")), - new CreatePropertyTextHappening("Hello", typeof(ConsoleValue)), - new EndPropertyHappening(), - new EndObjectHappening(), //ConsoleWriter - new EndObjectHappening(), //ConsoleApp - new FinishHappening()); - pt.Test(); + makeGoBang(MAPPING + s); } [Test] @@ -326,16 +376,7 @@ public class XamlParserTest : Assertion { "Hello\n" + "\n" + ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), null), - new CreateObjectHappening(typeof(ConsoleWriter), null), - new CreatePropertyHappening(typeof(ConsoleWriter).GetProperty("Text")), - new CreatePropertyTextHappening("Hello", typeof(ConsoleValue)), - new EndPropertyHappening(), - new EndObjectHappening(), //ConsoleWriter - new EndObjectHappening(), //ConsoleApp - new FinishHappening()); - pt.Test(); + makeGoBang(MAPPING + s); } [Test] @@ -344,16 +385,40 @@ public class XamlParserTest : Assertion { string s = "\n"+ "" + ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), null), - new CreateObjectHappening(typeof(ConsoleWriter), null), - new CreateDependencyPropertyHappening(typeof(ConsoleApp), "Repetitions", typeof(int)), - new CreateDependencyPropertyTextHappening("3", typeof(int)), - new EndDependencyPropertyHappening(), - new EndObjectHappening(), // ConsoleWriter - new EndObjectHappening(), // ConsoleApp - new FinishHappening()); - pt.Test(); + + XamlNode n; + XamlParser p = new XamlParser(new StringReader(MAPPING + s)); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlDocumentStartNode); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementStartNode); + Assert.AreEqual(n.Depth, 0); + Assert.AreEqual(((XamlElementStartNode)n).ElementType, typeof(ConsoleApp)); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementStartNode); + Assert.AreEqual(n.Depth, 1); + Assert.AreEqual(((XamlElementStartNode)n).ElementType, typeof(ConsoleWriter)); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlPropertyNode); + Assert.AreEqual(((XamlPropertyNode)n).DP, ConsoleApp.RepetitionsProperty); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlTextNode); + Assert.AreEqual(((XamlTextNode)n).TextContent, "3"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementEndNode); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementEndNode); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlDocumentEndNode); + } [Test] @@ -363,16 +428,7 @@ public class XamlParserTest : Assertion { string s = "\n"+ "" + ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), null), - new CreateObjectHappening(typeof(ConsoleValueString), null), - new CreateDependencyPropertyHappening(typeof(ConsoleApp), "Repetitions", typeof(int)), - new CreateDependencyPropertyTextHappening("3", typeof(int)), - new EndDependencyPropertyHappening(), - new EndObjectHappening(), // ConsoleWriter - new EndObjectHappening(), // ConsoleApp - new FinishHappening()); - pt.Test(); + makeGoBang(MAPPING + s); } [Test] @@ -382,16 +438,7 @@ public class XamlParserTest : Assertion { string s = "\n"+ "" + ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), null), - new CreateObjectHappening(typeof(ConsoleWriter), null), - new CreateDependencyPropertyHappening(typeof(ConsoleApp), "Repetitions", typeof(int)), - new CreateDependencyPropertyTextHappening("3", typeof(int)), - new EndDependencyPropertyHappening(), - new EndObjectHappening(), // ConsoleWriter - new EndObjectHappening(), // ConsoleApp - new FinishHappening()); - pt.Test(); + makeGoBang(MAPPING + s); } @@ -403,16 +450,41 @@ public class XamlParserTest : Assertion { "3\n" + "" + ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), null), - new CreateObjectHappening(typeof(ConsoleWriter), null), - new CreateDependencyPropertyHappening(typeof(ConsoleApp), "Repetitions", typeof(int)), - new CreateDependencyPropertyTextHappening("3", typeof(int)), - new EndDependencyPropertyHappening(), - new EndObjectHappening(), // ConsoleWriter - new EndObjectHappening(), // ConsoleApp - new FinishHappening()); - pt.Test(); + + XamlNode n; + XamlParser p = new XamlParser(new StringReader(MAPPING + s)); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlDocumentStartNode); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementStartNode); + Assert.AreEqual(n.Depth, 0); + Assert.AreEqual(((XamlElementStartNode)n).ElementType, typeof(ConsoleApp)); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementStartNode); + Assert.AreEqual(n.Depth, 1); + Assert.AreEqual(((XamlElementStartNode)n).ElementType, typeof(ConsoleWriter)); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlPropertyNode); + Assert.AreEqual(n.Depth, 2); + Assert.AreEqual(((XamlPropertyNode)n).DP, ConsoleApp.RepetitionsProperty); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlTextNode); + Assert.AreEqual(((XamlTextNode)n).TextContent, "3"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementEndNode); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementEndNode); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlDocumentEndNode); + } [Test] @@ -424,16 +496,7 @@ public class XamlParserTest : Assertion { "3\n" + "" + ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), null), - new CreateObjectHappening(typeof(ConsoleWriter), null), - new CreateDependencyPropertyHappening(typeof(ConsoleApp), "Repetitions", typeof(int)), - new CreateDependencyPropertyTextHappening("3", typeof(int)), - new EndDependencyPropertyHappening(), - new EndObjectHappening(), // ConsoleWriter - new EndObjectHappening(), // ConsoleApp - new FinishHappening()); - pt.Test(); + makeGoBang(MAPPING + s); } @@ -445,17 +508,46 @@ public class XamlParserTest : Assertion { "\n" + "\n" + ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), null), - new CreateObjectHappening(typeof(ConsoleReader), null), - new CreatePropertyHappening(typeof(ConsoleReader).GetProperty("Prompt")), - new CreatePropertyObjectHappening(typeof(ConsoleWriter), null), - new EndPropertyObjectHappening(typeof(ConsoleWriter)), - new EndPropertyHappening(), - new EndObjectHappening(), - new EndObjectHappening(), - new FinishHappening()); - pt.Test(); + XamlParser p = new XamlParser(new StringReader(MAPPING + s)); + XamlNode n; + n = p.GetNextNode(); + Assert.IsTrue(n is XamlDocumentStartNode, "A1"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementStartNode, "B1"); + Assert.AreEqual(n.Depth, 0, "B2"); + Assert.AreEqual(((XamlElementStartNode)n).ElementType, typeof(ConsoleApp), "B3"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementStartNode, "C1"); + Assert.AreEqual(1, n.Depth, "C2"); + Assert.AreEqual(((XamlElementStartNode)n).ElementType, typeof(ConsoleReader), "C3"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlPropertyNode, "D1"); + Assert.AreEqual(2, n.Depth, "D3"); + Assert.AreEqual(((XamlPropertyNode)n).PropInfo, typeof(ConsoleReader).GetProperty("Prompt"), "D2"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementStartNode, "E1" + n.GetType()); + Assert.AreEqual(3, n.Depth, "E2"); + Assert.AreEqual(((XamlElementStartNode)n).ElementType, typeof(ConsoleWriter), "E3"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementEndNode, "F1" + n.GetType()); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlPropertyComplexEndNode, "G1"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementEndNode, "H1"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementEndNode, "I1"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlDocumentEndNode, "J1"); + } [Test] @@ -467,15 +559,7 @@ public class XamlParserTest : Assertion { "" + "\n" + ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), null), - new CreateObjectHappening(typeof(ConsoleValueString), null), - new CreateObjectHappening(typeof(ConsoleWriter), null), - new EndObjectHappening(), - new EndObjectHappening(), - new EndObjectHappening(), - new FinishHappening()); - pt.Test(); + makeGoBang(MAPPING + s); } [Test] @@ -487,15 +571,7 @@ public class XamlParserTest : Assertion { "ABC" + "\n" + ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), null), - new CreateObjectHappening(typeof(ConsoleValueString), null), - new CreateObjectHappening(typeof(ConsoleWriter), null), - new EndObjectHappening(), - new EndObjectHappening(), - new EndObjectHappening(), - new FinishHappening()); - pt.Test(); + makeGoBang(MAPPING + s); } [Test] @@ -503,14 +579,26 @@ public class XamlParserTest : Assertion { { string s = "\n"+ ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), null), - new CreateEventHappening(typeof(ConsoleApp).GetEvent("SomethingHappened")), - new CreateEventDelegateHappening("handleSomething", typeof(SomethingHappenedHandler)), - new EndEventHappening(), - new EndObjectHappening(), - new FinishHappening()); - pt.Test(); + XamlParser p = new XamlParser(new StringReader(MAPPING + s)); + XamlNode n; + n = p.GetNextNode(); + Assert.IsTrue(n is XamlDocumentStartNode, "A1"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementStartNode, "B1"); + Assert.AreEqual(n.Depth, 0, "B2"); + Assert.AreEqual(((XamlElementStartNode)n).ElementType, typeof(ConsoleApp), "B3"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlClrEventNode, "C1"); + Assert.AreEqual(((XamlClrEventNode)n).EventMember, typeof(ConsoleApp).GetEvent("SomethingHappened"), "C2"); + + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementEndNode, "D1"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlDocumentEndNode, "E1"); } [Test] @@ -519,16 +607,40 @@ public class XamlParserTest : Assertion { string s = "\n"+ "\n"+ ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), null), - new CreateObjectHappening(typeof(ConsoleWriter), null), - new CreatePropertyHappening(typeof(ConsoleWriter).GetProperty("Filter")), - new CreatePropertyDelegateHappening("filterfilter", typeof(Filter)), - new EndPropertyHappening(), - new EndObjectHappening(), - new EndObjectHappening(), - new FinishHappening()); - pt.Test(); + XamlParser p = new XamlParser(new StringReader(MAPPING + s)); + XamlNode n; + n = p.GetNextNode(); + Assert.IsTrue(n is XamlDocumentStartNode, "A1"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementStartNode, "B1"); + Assert.AreEqual(n.Depth, 0, "B2"); + Assert.AreEqual(((XamlElementStartNode)n).ElementType, typeof(ConsoleApp), "B3"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementStartNode, "C1"); + Assert.AreEqual(n.Depth, 1, "C2"); + Assert.AreEqual(((XamlElementStartNode)n).ElementType, typeof(ConsoleWriter), "C3"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlPropertyNode, "D1"); + Assert.AreEqual(n.Depth, 1, "D2"); + Assert.AreEqual(((XamlPropertyNode)n).PropInfo, typeof(ConsoleWriter).GetProperty("Filter"), "D3"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlClrEventNode, "E1"); + Assert.AreEqual((MemberInfo)((XamlClrEventNode)n).EventMember, typeof(ConsoleWriter).GetProperty("Filter"), "E2"); + Assert.AreEqual(((XamlClrEventNode)n).Value, "filterfilter", "E3"); + + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementEndNode, "F1"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementEndNode, "G1"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlDocumentEndNode, "H1"); } [Test] @@ -537,12 +649,26 @@ public class XamlParserTest : Assertion { string s = "\n"+ " here there everywhere]]>\n"+ ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), null), - new CreateCodeHappening("Hi there here there everywhere"), - new EndObjectHappening(), - new FinishHappening()); - pt.Test(); + XamlParser p = new XamlParser(new StringReader(MAPPING + s)); + XamlNode n; + n = p.GetNextNode(); + Assert.IsTrue(n is XamlDocumentStartNode, "A1"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementStartNode, "B1"); + Assert.AreEqual(((XamlElementStartNode)n).ElementType, typeof(ConsoleApp), "B3"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlLiteralContentNode, "C1"); + Assert.AreEqual("Hi there here there everywhere", ((XamlLiteralContentNode)n).Content, "C2"); + + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlElementEndNode, "D1"); + + n = p.GetNextNode(); + Assert.IsTrue(n is XamlDocumentEndNode, "E1"); + } @@ -553,12 +679,7 @@ public class XamlParserTest : Assertion { string s = "\n"+ "Hi there here there everywhere\n"+ ""; - ParserTester pt = new ParserTester(MAPPING + s, - new CreateTopLevelHappening(typeof(ConsoleApp), null), - new CreateCodeHappening("Hi there here there everywhere"), - new EndObjectHappening(), - new FinishHappening()); - pt.Test(); + makeGoBang(MAPPING + s); } } @@ -730,11 +851,12 @@ class ParserTester : IXamlWriter { } public void Test() { - XamlParser p = new XamlParser(new StringReader(document), +/* XamlParser p = new XamlParser(new StringReader(document), this); p.Parse(); // if this fails, then we haven't consumed all the happenings - Assert.AreEqual(happenings.Length, c); + Assert.AreEqual(happenings.Length, c);*/ + Assert.IsTrue(false); } Happening getHappening() { -- cgit v1.2.3