private static void FinalizeNode(XamlNode node, XamlContext context, List <XamlNode> nodeStream, IXmlLineInfo lineInfo, string uri) { node.Line = lineInfo.LineNumber; node.Offset = lineInfo.LinePosition; node.Context = context; node.Uri = uri; nodeStream.Add(node); }
private static void HandleXmlNode(string uri, List <XamlNode> nodeStream, Stack <XamlNode> nodeStack, Stack <XamlContext> contextStack, XmlReader reader, IXmlLineInfo lineInfo) { switch (reader.NodeType) { case XmlNodeType.Element: { contextStack.Push(new XamlContext(contextStack.Peek())); // If the element contains a ".", it's a property. bool isProperty = reader.Name.Contains("."); if (!isProperty) { var start = new StartObject { ObjectTypeName = reader.LocalName, Prefix = reader.Prefix }; nodeStack.Push(start); FinalizeNode(start, contextStack.Peek(), nodeStream, lineInfo, uri); } else { var start = new StartMember { Name = reader.LocalName, Prefix = reader.Prefix }; nodeStack.Push(start); FinalizeNode(start, contextStack.Peek(), nodeStream, lineInfo, uri); } while (reader.MoveToNextAttribute()) { HandleXmlNode(uri, nodeStream, nodeStack, contextStack, reader, lineInfo); } if (reader.IsEmptyElement) { goto case XmlNodeType.EndElement; } } break; case XmlNodeType.Attribute: { if (reader.Prefix.Equals("xmlns")) { contextStack.Peek().UriMappings[reader.LocalName] = reader.Value; } else { var start = new StartMember { Name = reader.LocalName, Prefix = reader.Prefix }; var value = new Value { StringValue = reader.Value }; var end = new EndMember(); start.Nodes.Add(start); start.Nodes.Add(value); start.Nodes.Add(end); FinalizeNode(start, contextStack.Peek(), nodeStream, lineInfo, uri); FinalizeNode(value, contextStack.Peek(), nodeStream, lineInfo, uri); FinalizeNode(end, contextStack.Peek(), nodeStream, lineInfo, uri); } } break; case XmlNodeType.SignificantWhitespace: case XmlNodeType.Text: { var value = new Value { StringValue = reader.Value }; FinalizeNode(value, contextStack.Peek(), nodeStream, lineInfo, uri); } break; case XmlNodeType.EndElement: { int startIndex = nodeStream.Count; var startNode = nodeStack.Pop(); XamlNode end = null; switch (startNode.NodeType) { case NodeType.StartObject: end = new EndObject(); break; case NodeType.StartMember: end = new EndMember(); break; } if (end != null) { FinalizeNode(end, contextStack.Peek(), nodeStream, lineInfo, uri); } while (startIndex >= 0 && nodeStream[--startIndex] != startNode) { ; } startNode.Nodes.AddRange(nodeStream.Skip(startIndex)); contextStack.Pop(); } break; #region Ignored nodes case XmlNodeType.Whitespace: case XmlNodeType.Comment: case XmlNodeType.Document: case XmlNodeType.DocumentFragment: case XmlNodeType.DocumentType: break; case XmlNodeType.EntityReference: case XmlNodeType.EndEntity: case XmlNodeType.Entity: throw new NotSupportedException("Entities are not supported in XAML"); case XmlNodeType.Notation: throw new NotSupportedException("Notations are not supported in XAML"); case XmlNodeType.ProcessingInstruction: throw new NotSupportedException("Processing instructions are not supported in XAML"); case XmlNodeType.XmlDeclaration: throw new NotSupportedException("Xml Declarations are not supported in XAML"); case XmlNodeType.CDATA: throw new NotSupportedException("CDATA not yet supported"); #endregion } }