Ejemplo n.º 1
0
        String IMarkupFormatter.OpenTag(IElement element, Boolean selfClosing)
        {
            var temp = StringBuilderPool.Obtain();

            temp.Append(Symbols.LessThan);

            if (!String.IsNullOrEmpty(element.Prefix))
            {
                temp.Append(element.Prefix).Append(Symbols.Colon);
            }

            temp.Append(element.LocalName);

            foreach (var attribute in element.Attributes)
            {
                temp.Append(" ").Append(Instance.Attribute(attribute));
            }

            temp.Append(Symbols.GreaterThan);
            return(temp.ToPool());
        }
Ejemplo n.º 2
0
        String IStyleFormatter.Sheet(IEnumerable <IStyleFormattable> rules)
        {
            var sb  = StringBuilderPool.Obtain();
            var sep = Environment.NewLine;

            using (var writer = new StringWriter(sb))
            {
                foreach (var rule in rules)
                {
                    rule.ToCss(writer, this);
                    writer.Write(sep);
                }

                if (sb.Length > 0)
                {
                    sb.Remove(sb.Length - sep.Length, sep.Length);
                }
            }

            return(sb.ToPool());
        }
Ejemplo n.º 3
0
        String IStyleFormatter.BlockDeclarations(IEnumerable <IStyleFormattable> declarations)
        {
            var sb = StringBuilderPool.Obtain().Append(Symbols.CurlyBracketOpen);

            using (var writer = new StringWriter(sb))
            {
                foreach (var declaration in declarations)
                {
                    writer.Write(Symbols.Space);
                    declaration.ToCss(writer, this);
                    writer.Write(Symbols.Semicolon);
                }

                if (sb.Length > 1)
                {
                    sb.Remove(sb.Length - 1, 1);
                }
            }

            return(sb.Append(Symbols.Space).Append(Symbols.CurlyBracketClose).ToPool());
        }
Ejemplo n.º 4
0
        protected void PEReference(Char c, Boolean use = true)
        {
            var buffer = StringBuilderPool.Obtain();

            if (c.IsXmlNameStart())
            {
                do
                {
                    buffer.Append(c);
                    c = _stream.Next;
                }while (c.IsXmlName());

                var temp = buffer.ToPool();

                if (c == Symbols.Semicolon)
                {
                    var p = _container.GetParameter(temp);

                    if (p != null)
                    {
                        if (use)
                        {
                            _stream.Push(temp, p.NodeValue);
                            return;
                        }
                        else
                        {
                            throw new DomException(DomError.InvalidAccess);
                        }
                    }
                }
            }

            if (use)
            {
                throw new DomException(DomError.InvalidAccess);
            }

            StringBuffer.Append(Symbols.Percent).Append(buffer.ToString());
        }
Ejemplo n.º 5
0
        /// <summary>
        /// Escapes the given text by replacing special characters with their
        /// XHTML entity (amp, nbsp as numeric value, lt, and gt).
        /// </summary>
        /// <param name="content">The string to alter.</param>
        /// <returns>The altered string.</returns>
        public static String EscapeText(String content)
        {
            var temp = StringBuilderPool.Obtain();

            for (var i = 0; i < content.Length; i++)
            {
                switch (content[i])
                {
                case Symbols.Ampersand: temp.Append("&amp;"); break;

                case Symbols.NoBreakSpace: temp.Append("&#160;"); break;

                case Symbols.GreaterThan: temp.Append("&gt;"); break;

                case Symbols.LessThan: temp.Append("&lt;"); break;

                default: temp.Append(content[i]); break;
                }
            }

            return(temp.ToPool());
        }
Ejemplo n.º 6
0
        private Boolean ParseSchemeData(String input, Int32 index, Int32 length)
        {
            var buffer = StringBuilderPool.Obtain();

            while (index < length)
            {
                var c = input[index];

                if (c == Symbols.QuestionMark)
                {
                    _schemeData = buffer.ToPool();
                    return(ParseQuery(input, index + 1, length));
                }
                else if (c == Symbols.Num)
                {
                    _schemeData = buffer.ToPool();
                    return(ParseFragment(input, index + 1, length));
                }
                else if (c == Symbols.Percent && index + 2 < length && input[index + 1].IsHex() && input[index + 2].IsHex())
                {
                    buffer.Append(input[index++]);
                    buffer.Append(input[index++]);
                    buffer.Append(input[index]);
                }
                else if (c.IsInRange(0x20, 0x7e))
                {
                    buffer.Append(c);
                }
                else if (c != Symbols.Tab && c != Symbols.LineFeed && c != Symbols.CarriageReturn)
                {
                    index += Utf8PercentEncode(buffer, input, index);
                }

                index++;
            }

            _schemeData = buffer.ToPool();
            return(true);
        }
Ejemplo n.º 7
0
        public override String ToString()
        {
            var sb     = default(StringBuilder);
            var offset = Start;
            var dest   = End;

            if (Head is IText startText)
            {
                if (Head == Tail)
                {
                    return(startText.Substring(offset, dest - offset));
                }
                else
                {
                    sb ??= StringBuilderPool.Obtain();

                    sb.Append(startText.Substring(offset, startText.Length - offset));
                }
            }

            sb ??= StringBuilderPool.Obtain();

            var nodes = CommonAncestor.Descendents <IText>();

            foreach (var node in nodes)
            {
                if (IsStartBefore(node, 0) && IsEndAfter(node, node.Length))
                {
                    sb.Append(node.Text);
                }
            }

            if (Tail is IText endText)
            {
                sb.Append(endText.Substring(0, dest));
            }

            return(sb.ToPool());
        }
Ejemplo n.º 8
0
        public static String Escape(String str)
        {
            if (str.Length != 1 || str[0] != Symbols.Minus)
            {
                var sb = StringBuilderPool.Obtain();

                for (var i = 0; i < str.Length; i++)
                {
                    var ch = str[i];

                    if (ch == Symbols.Null)
                    {
                        ch = Symbols.Replacement;
                    }
                    else if (ch == 0x7f ||
                             (ch.IsInRange(0x01, 0x1f)) ||
                             (ch.IsDigit() && (i == 0 || (i == 1 && str[0] == Symbols.Minus))))
                    {
                        sb.Append(Symbols.ReverseSolidus);
                        sb.Append(ch.ToHex());
                        sb.Append(Symbols.Space);
                        continue;
                    }
                    else if (ch < 0x80 &&
                             !ch.IsOneOf(Symbols.Minus, Symbols.Underscore) &&
                             !ch.IsAlphanumericAscii())
                    {
                        sb.Append(Symbols.ReverseSolidus);
                    }

                    sb.Append(ch);
                }

                return(sb.ToPool());
            }

            return(@"\-");
        }
Ejemplo n.º 9
0
        public static String Join(this ICssValue[] values, String separator)
        {
            var buffer   = StringBuilderPool.Obtain();
            var previous = false;

            for (var i = 0; i < values.Length; i++)
            {
                var str = values[i]?.CssText;

                if (!String.IsNullOrEmpty(str))
                {
                    if (previous)
                    {
                        buffer.Append(separator);
                    }

                    buffer.Append(str);
                    previous = true;
                }
            }

            return(buffer.ToPool());
        }
        String IStyleFormatter.Sheet(IEnumerable <IStyleFormattable> rules)
        {
            var sb  = StringBuilderPool.Obtain();
            var sep = _newLineString + _newLineString;

            using (var writer = new StringWriter(sb))
            {
                foreach (var rule in rules)
                {
                    rule.ToCss(writer, this);
                    writer.Write(sep);
                }
            }

            var pos = sb.Length - sep.Length;

            if (pos > 0)
            {
                sb.Remove(pos, sep.Length);
            }

            return(sb.ToPool());
        }
        String IStyleFormatter.BlockRules(IEnumerable <IStyleFormattable> rules)
        {
            var sb  = StringBuilderPool.Obtain();
            var ind = String.Concat(Enumerable.Repeat(_intendString, _intends));
            var sep = _newLineString + ind;

            sb.Append('{').Append(' ');
            ++_intends;

            using (var writer = new StringWriter(sb))
            {
                foreach (var rule in rules)
                {
                    writer.Write(sep);
                    writer.Write(_intendString);
                    rule.ToCss(writer, this);
                    writer.Write(sep);
                }
            }

            --_intends;
            return(sb.Append('}').ToPool());
        }
Ejemplo n.º 12
0
        public void StringBuilderDropsOneWithLeastCapacity()
        {
            StringBuilderPool.MaxCount = 4;
            var sb1 = StringBuilderPool.Obtain();
            var sb2 = StringBuilderPool.Obtain();
            var sb3 = StringBuilderPool.Obtain();
            var sb4 = StringBuilderPool.Obtain();
            var sb5 = StringBuilderPool.Obtain();

            sb1.Capacity = 1024;
            sb1.ToPool();
            sb2.Capacity = 512;
            sb2.ToPool();
            sb3.Capacity = 2048;
            sb3.ToPool();
            sb4.Capacity = 8192;
            sb4.ToPool();
            sb5.Capacity = 16384;
            sb5.ToPool();
            Assert.AreEqual(16384, StringBuilderPool.Obtain().Capacity);
            Assert.AreEqual(8192, StringBuilderPool.Obtain().Capacity);
            Assert.AreEqual(2048, StringBuilderPool.Obtain().Capacity);
            Assert.AreEqual(1024, StringBuilderPool.Obtain().Capacity);
        }
Ejemplo n.º 13
0
        public override string OpenTag(IElement element, bool selfClosing)
        {
            var stringBuilder = StringBuilderPool.Obtain();

            stringBuilder.Append('<');
            if (!string.IsNullOrEmpty(element.Prefix))
            {
                stringBuilder.Append(element.Prefix).Append(':');
            }
            stringBuilder.Append(element.LocalName);
            foreach (IAttr attribute in element.Attributes)
            {
                stringBuilder.Append(' ').Append(Attribute(attribute));
            }

            // DON'T FORGET TO APPEND A SLASH FOR SELF CLOSING TAG.
            if (selfClosing)
            {
                stringBuilder.Append('/');
            }

            stringBuilder.Append('>');
            return(stringBuilder.ToPool());
        }
        public static String Join <T>(this IEnumerable <T> values, String separator)
            where T : ICssValue
        {
            var buffer   = StringBuilderPool.Obtain();
            var previous = false;

            foreach (var value in values)
            {
                var str = value?.CssText;

                if (!String.IsNullOrEmpty(str))
                {
                    if (previous)
                    {
                        buffer.Append(separator);
                    }

                    buffer.Append(str);
                    previous = true;
                }
            }

            return(buffer.ToPool());
        }
Ejemplo n.º 15
0
        String IMarkupFormatter.Attribute(IAttr attribute)
        {
            var value = attribute.Value;
            var temp  = StringBuilderPool.Obtain();

            temp.Append(attribute.Name);
            temp.Append(Symbols.Equality).Append(Symbols.DoubleQuote);

            for (var i = 0; i < value.Length; i++)
            {
                switch (value[i])
                {
                case Symbols.Ampersand: temp.Append("&amp;"); break;

                case Symbols.LessThan: temp.Append("&lt;"); break;

                case Symbols.DoubleQuote: temp.Append("&quot;"); break;

                default: temp.Append(value[i]); break;
                }
            }

            return(temp.Append(Symbols.DoubleQuote).ToPool());
        }
Ejemplo n.º 16
0
        public void StringBuilderDoesNotRebuildIfLeastOneIsAdded()
        {
            StringBuilderPool.MaxCount = 4;
            var sb1 = StringBuilderPool.Obtain();
            var sb2 = StringBuilderPool.Obtain();
            var sb3 = StringBuilderPool.Obtain();
            var sb4 = StringBuilderPool.Obtain();
            var sb5 = StringBuilderPool.Obtain();

            sb1.Capacity = 1024;
            sb1.ToPool();
            sb2.Capacity = 2048;
            sb2.ToPool();
            sb3.Capacity = 4096;
            sb3.ToPool();
            sb4.Capacity = 8192;
            sb4.ToPool();
            sb5.Capacity = 512;
            sb5.ToPool();
            Assert.AreEqual(8192, StringBuilderPool.Obtain().Capacity);
            Assert.AreEqual(4096, StringBuilderPool.Obtain().Capacity);
            Assert.AreEqual(2048, StringBuilderPool.Obtain().Capacity);
            Assert.AreEqual(1024, StringBuilderPool.Obtain().Capacity);
        }
Ejemplo n.º 17
0
        public void StringBuilderPreservesOrderWhenRebuilding()
        {
            StringBuilderPool.MaxCount = 4;
            var sb0 = StringBuilderPool.Obtain();
            var sb1 = StringBuilderPool.Obtain();
            var sb2 = StringBuilderPool.Obtain();
            var sb3 = StringBuilderPool.Obtain();
            var sb4 = StringBuilderPool.Obtain();

            sb0.Capacity = 512;
            sb0.ToPool();
            sb1.Capacity = 1024;
            sb1.ToPool();
            sb2.Capacity = 2048;
            sb2.ToPool();
            sb3.Capacity = 4096;
            sb3.ToPool();
            sb4.Capacity = 8192;
            sb4.ToPool();
            Assert.AreEqual(8192, StringBuilderPool.Obtain().Capacity);
            Assert.AreEqual(4096, StringBuilderPool.Obtain().Capacity);
            Assert.AreEqual(2048, StringBuilderPool.Obtain().Capacity);
            Assert.AreEqual(1024, StringBuilderPool.Obtain().Capacity);
        }
Ejemplo n.º 18
0
        private static UrlReference Unquoted(StringSource source)
        {
            var buffer  = StringBuilderPool.Obtain();
            var current = source.Current;

            while (true)
            {
                if (current.IsSpaceCharacter())
                {
                    return(End(source, buffer));
                }
                else if (current.IsOneOf(Symbols.RoundBracketClose, Symbols.EndOfFile))
                {
                    source.Next();
                    return(new UrlReference(buffer.ToPool()));
                }
                else if (current.IsOneOf(Symbols.DoubleQuote, Symbols.SingleQuote, Symbols.RoundBracketOpen) || current.IsNonPrintable())
                {
                    return(Bad(source, buffer));
                }
                else if (current != Symbols.ReverseSolidus)
                {
                    buffer.Append(current);
                }
                else if (source.IsValidEscape())
                {
                    buffer.Append(source.ConsumeEscape());
                }
                else
                {
                    return(Bad(source, buffer));
                }

                current = source.Next();
            }
        }
Ejemplo n.º 19
0
        /// <summary>
        /// Escapes the given string using CSS escaping rules.
        /// </summary>
        /// <param name="text">The text to escape.</param>
        /// <returns>The escaped text.</returns>
        public static String Escape(String text)
        {
            if (!String.IsNullOrEmpty(text))
            {
                var length        = text.Length;
                var index         = -1;
                var result        = StringBuilderPool.Obtain();
                var firstCodeUnit = (Int32)text[0];

                while (++index < length)
                {
                    var codeUnit = (Int32)text[index];
                    // Note: there’s no need to special-case astral symbols, surrogate
                    // pairs, or lone surrogates.

                    // If the character is NULL (U+0000), then the REPLACEMENT CHARACTER // (U+FFFD).
                    if (codeUnit == 0x0000)
                    {
                        result.Append('\uFFFD');
                        continue;
                    }

                    if (
                        // If the character is in the range [\1-\1F] (U+0001 to U+001F) or is
                        // U+007F, […]
                        (codeUnit >= 0x0001 && codeUnit <= 0x001F) || codeUnit == 0x007F ||
                        // If the character is the first character and is in the range [0-9]
                        // (U+0030 to U+0039), […]
                        (index == 0 && codeUnit >= 0x0030 && codeUnit <= 0x0039) ||
                        // If the character is the second character and is in the range [0-9]
                        // (U+0030 to U+0039) and the first character is a `-` (U+002D), […]
                        (
                            index == 1 &&
                            codeUnit >= 0x0030 && codeUnit <= 0x0039 &&
                            firstCodeUnit == 0x002D
                        )
                        )
                    {
                        // https://drafts.csswg.org/cssom/#escape-a-character-as-code-point
                        result.Append('\\').Append(codeUnit.ToString("X")).Append(' ');
                        continue;
                    }

                    // If the character is the first character and is a `-` (U+002D), and there is no second character, […]
                    if (index == 0 && length == 1 && codeUnit == 0x002D)
                    {
                        result.Append('\\').Append(text[index]);
                        continue;
                    }

                    // If the character is not handled by one of the above rules and is
                    // greater than or equal to U+0080, is `-` (U+002D) or `_` (U+005F), or
                    // is in one of the ranges [0-9] (U+0030 to U+0039), [A-Z] (U+0041 to
                    // U+005A), or [a-z] (U+0061 to U+007A), […]
                    if (
                        codeUnit >= 0x0080 ||
                        codeUnit == 0x002D ||
                        codeUnit == 0x005F ||
                        codeUnit >= 0x0030 && codeUnit <= 0x0039 ||
                        codeUnit >= 0x0041 && codeUnit <= 0x005A ||
                        codeUnit >= 0x0061 && codeUnit <= 0x007A
                        )
                    {
                        // the character itself
                        result.Append(text[index]);
                        continue;
                    }

                    // Otherwise, the escaped character.
                    // https://drafts.csswg.org/cssom/#escape-a-character
                    result.Append('\\').Append(Char.ConvertFromUtf32(text[index]));
                }

                return(result.ToPool());
            }

            return(text);
        }
Ejemplo n.º 20
0
        private Boolean ParsePath(String input, Int32 index, Int32 length, Boolean onlyPath = false)
        {
            var init = index;

            if (index < length && (input[index] == Symbols.Solidus || input[index] == Symbols.ReverseSolidus))
            {
                index++;
            }

            var paths = new List <String>();

            if (!onlyPath && !String.IsNullOrEmpty(_path) && index - init == 0)
            {
                var split = _path.Split(Symbols.Solidus);

                if (split.Length > 1)
                {
                    paths.AddRange(split);
                    paths.RemoveAt(split.Length - 1);
                }
            }

            var originalCount = paths.Count;
            var buffer        = StringBuilderPool.Obtain();

            while (index <= length)
            {
                var c        = index == length ? Symbols.EndOfFile : input[index];
                var breakNow = !onlyPath && (c == Symbols.Num || c == Symbols.QuestionMark);

                if (c == Symbols.EndOfFile || c == Symbols.Solidus || c == Symbols.ReverseSolidus || breakNow)
                {
                    var path  = buffer.ToString();
                    var close = false;
                    buffer.Clear();

                    if (path.Isi(CurrentDirectoryAlternative))
                    {
                        path = CurrentDirectory;
                    }
                    else if (path.Isi(UpperDirectoryAlternatives[0]) ||
                             path.Isi(UpperDirectoryAlternatives[1]) ||
                             path.Isi(UpperDirectoryAlternatives[2]))
                    {
                        path = UpperDirectory;
                    }

                    if (path.Is(UpperDirectory))
                    {
                        if (paths.Count > 0)
                        {
                            paths.RemoveAt(paths.Count - 1);
                        }

                        close = true;
                    }
                    else if (!path.Is(CurrentDirectory))
                    {
                        if (_scheme.Is(ProtocolNames.File) &&
                            paths.Count == originalCount &&
                            path.Length == 2 &&
                            path[0].IsLetter() &&
                            path[1] == Symbols.Pipe)
                        {
                            path = path.Replace(Symbols.Pipe, Symbols.Colon);
                            paths.Clear();
                        }

                        paths.Add(path);
                    }
                    else
                    {
                        close = true;
                    }

                    if (close && c != Symbols.Solidus && c != Symbols.ReverseSolidus)
                    {
                        paths.Add(String.Empty);
                    }

                    if (breakNow)
                    {
                        break;
                    }
                }
                else if (c == Symbols.Percent &&
                         index + 2 < length &&
                         input[index + 1].IsHex() &&
                         input[index + 2].IsHex())
                {
                    buffer.Append(input[index++]);
                    buffer.Append(input[index++]);
                    buffer.Append(input[index]);
                }
                else if (c == Symbols.Tab || c == Symbols.LineFeed || c == Symbols.CarriageReturn)
                {
                    // Parse Error
                }
                else if (c.IsNormalPathCharacter())
                {
                    buffer.Append(c);
                }
                else
                {
                    index += Utf8PercentEncode(buffer, input, index);
                }

                index++;
            }

            buffer.ToPool();
            _path = String.Join("/", paths);

            if (index < length)
            {
                if (input[index] == Symbols.QuestionMark)
                {
                    return(ParseQuery(input, index + 1, length));
                }

                return(ParseFragment(input, index + 1, length));
            }

            return(true);
        }