예제 #1
0
        /// <summary>
        /// Create <see cref="NewFolding"/>s for the specified document.
        /// </summary>
        public IEnumerable<NewFolding> CreateNewFoldings(TextDocument document, XmlReader reader, out int firstErrorOffset)
        {
            Stack<XmlFoldStart> stack = new Stack<XmlFoldStart>();
            List<NewFolding> foldMarkers = new List<NewFolding>();
            try {
                while (reader.Read()) {
                    switch (reader.NodeType) {
                        case XmlNodeType.Element:
                            if (!reader.IsEmptyElement) {
                                XmlFoldStart newFoldStart = CreateElementFoldStart(document, reader);
                                stack.Push(newFoldStart);
                            }
                            break;

                        case XmlNodeType.EndElement:
                            XmlFoldStart foldStart = stack.Pop();
                            CreateElementFold(document, foldMarkers, reader, foldStart);
                            break;

                        case XmlNodeType.Comment:
                            CreateCommentFold(document, foldMarkers, reader);
                            break;
                    }
                }
                firstErrorOffset = -1;
            } catch (XmlException ex) {
                // ignore errors at invalid positions (prevent ArgumentOutOfRangeException)
                if (ex.LineNumber >= 1 && ex.LineNumber <= document.LineCount)
                    firstErrorOffset = document.GetOffset(ex.LineNumber, ex.LinePosition);
                else
                    firstErrorOffset = 0;
            }
            foldMarkers.Sort((a,b) => a.StartOffset.CompareTo(b.StartOffset));
            return foldMarkers;
        }
예제 #2
0
 static int GetOffset(TextDocument document, XmlReader reader)
 {
     IXmlLineInfo info = reader as IXmlLineInfo;
     if (info != null && info.HasLineInfo()) {
         return document.GetOffset(info.LineNumber, info.LinePosition);
     } else {
         throw new ArgumentException("XmlReader does not have positioning information.");
     }
 }
예제 #3
0
        /// <summary>
        /// Creates an XmlFoldStart for the start tag of an element.
        /// </summary>
        XmlFoldStart CreateElementFoldStart(TextDocument document, XmlReader reader)
        {
            // Take off 1 from the offset returned
            // from the xml since it points to the start
            // of the element name and not the beginning
            // tag.
            //XmlFoldStart newFoldStart = new XmlFoldStart(reader.Prefix, reader.LocalName, reader.LineNumber - 1, reader.LinePosition - 2);
            XmlFoldStart newFoldStart = new XmlFoldStart();

            IXmlLineInfo lineInfo = (IXmlLineInfo)reader;
            newFoldStart.StartLine = lineInfo.LineNumber;
            newFoldStart.StartOffset = document.GetOffset(newFoldStart.StartLine, lineInfo.LinePosition - 1);

            if (this.ShowAttributesWhenFolded && reader.HasAttributes) {
                newFoldStart.Name = String.Concat("<", reader.Name, " ", GetAttributeFoldText(reader), ">");
            } else {
                newFoldStart.Name = String.Concat("<", reader.Name, ">");
            }

            return newFoldStart;
        }
예제 #4
0
 /// <summary>
 /// Create an element fold if the start and end tag are on
 /// different lines.
 /// </summary>
 static void CreateElementFold(TextDocument document, List<NewFolding> foldMarkers, XmlReader reader, XmlFoldStart foldStart)
 {
     IXmlLineInfo lineInfo = (IXmlLineInfo)reader;
     int endLine = lineInfo.LineNumber;
     if (endLine > foldStart.StartLine) {
         int endCol = lineInfo.LinePosition + reader.Name.Length + 1;
         foldStart.EndOffset = document.GetOffset(endLine, endCol);
         foldMarkers.Add(foldStart);
     }
 }