Esempio n. 1
0
        /// <summary>
        /// Override Read in order to search for strippable whitespace, to concatenate adjacent text nodes, and to
        /// resolve entities.
        /// </summary>
        public override bool Read()
        {
            string?ws = null;

            // Clear text value
            _val = null;

            while (base.Read())
            {
                switch (base.NodeType)
                {
                case XmlNodeType.Element:
                    // Push boolean indicating whether whitespace children of this element should be stripped
                    if (!base.IsEmptyElement)
                    {
                        _stkStrip.PushBit(_shouldStrip);

                        // Strip if rules say we should and we're not within the scope of xml:space="preserve"
                        _shouldStrip = _wsRules.ShouldStripSpace(base.LocalName, base.NamespaceURI) && (base.XmlSpace != XmlSpace.Preserve);
                    }
                    break;

                case XmlNodeType.EndElement:
                    // Restore parent shouldStrip setting
                    _shouldStrip = _stkStrip.PopBit();
                    break;

                case XmlNodeType.Text:
                case XmlNodeType.CDATA:
                    // If preserving adjacent text, don't perform any further checks
                    if (_preserveAdjacent)
                    {
                        return(true);
                    }

                    if (_shouldStrip)
                    {
                        // Reader may report whitespace as Text or CDATA
                        if (XmlCharType.IsOnlyWhitespace(base.Value))
                        {
                            goto case XmlNodeType.Whitespace;
                        }

                        // If whitespace was cached, then prepend it to text or CDATA value
                        if (ws != null)
                        {
                            _val = string.Concat(ws, base.Value);
                        }

                        // Preserve adjacent whitespace
                        _preserveAdjacent = true;
                        return(true);
                    }
                    break;

                case XmlNodeType.Whitespace:
                case XmlNodeType.SignificantWhitespace:
                    // If preserving adjacent text, don't perform any further checks
                    if (_preserveAdjacent)
                    {
                        return(true);
                    }

                    if (_shouldStrip)
                    {
                        // Save whitespace until it can be determined whether it will be stripped
                        ws = ws == null ?
                             base.Value :
                             string.Concat(ws, base.Value);

                        // Read next event
                        continue;
                    }
                    break;

                case XmlNodeType.EndEntity:
                    // Read next event
                    continue;
                }

                // No longer preserve adjacent space
                _preserveAdjacent = false;
                return(true);
            }

            return(false);
        }