@@ -0,0 +1,2505 @@
+package org.parboiled.examples.doublequotedstring;%0A%0Aimport org.parboiled.BaseParser;%0Aimport org.parboiled.Parboiled;%0Aimport org.parboiled.Rule;%0Aimport org.parboiled.annotations.BuildParseTree;%0Aimport org.parboiled.errors.ErrorUtils;%0Aimport org.parboiled.parserunners.TracingParseRunner;%0Aimport org.parboiled.support.ParseTreeUtils;%0Aimport org.parboiled.support.ParsingResult;%0A%0Aimport java.util.Scanner;%0A%0A/**%0A * A simple, double quoted string matching grammar%0A *%0A * %3Cp%3EThis will match inputs such as:%3C/p%3E%0A *%0A * %3Cul%3E%0A *     %3Cli%3E%7B@code %22hello world%22%7D;%3C/li%3E%0A *     %3Cli%3E%7B@code %22hello %5C%22world%5C%22%22%7D;%3C/li%3E%0A *     %3Cli%3E%7B@code %22%22%7D;%3C/li%3E%0A *     %3Cli%3E%7B@code %22%5C%22%22%7D%3C/li%3E%0A * %3C/ul%3E%0A *%0A * %3Cp%3Eand so on.%3C/p%3E%0A *%0A * %3Cp%3EThis parser builds the parse tree (the class is annotated using %7B@link%0A * BuildParseTree%7D) and uses a %7B@link TracingParseRunner%7D so that you can see%0A * the parsing process in action.%3C/p%3E%0A *%0A * %3Cp%3EThis parser uses the %7B@code normal* (special normal*)*%7D pattern, often%0A * used in regexes to %22unroll the loop%22. In this case:%3C/p%3E%0A *%0A * %3Cul%3E%0A *     %3Cli%3E%7B@code normal%7D is everything but a backslash or a double quote,%3C/li%3E%0A *     %3Cli%3E%7B@code special%7D is the character sequence %7B@code '%5C', '%22'%7D.%3C/li%3E%0A * %3C/ul%3E%0A */%0A@BuildParseTree%0Apublic class DoubleQuotedString%0A    extends BaseParser%3CVoid%3E%0A%7B%0A    Rule Normal()%0A    %7B%0A        return NoneOf(%22%5C%5C%5C%22%22);%0A    %7D%0A%0A    Rule Special()%0A    %7B%0A        return String(%22%5C%5C%5C%22%22);%0A    %7D%0A%0A    Rule NSN()%0A    %7B%0A        return Sequence(%0A            ZeroOrMore(Normal()),%0A            ZeroOrMore(Special(), ZeroOrMore(Normal()))%0A        );%0A    %7D%0A%0A    Rule DoubleQuotedString()%0A    %7B%0A        return Sequence('%22', NSN(), '%22', EOI);%0A    %7D%0A%0A    public static void main(final String... args)%0A    %7B%0A        final DoubleQuotedString parser%0A            = Parboiled.createParser(DoubleQuotedString.class);%0A%0A        final Scanner scanner = new Scanner(System.in);%0A        ParsingResult%3C?%3E result;%0A        String line;%0A%0A        while (true) %7B%0A            System.out.print(%22Enter a value to test (empty to quit): %22);%0A            line = scanner.nextLine();%0A            if (line.isEmpty())%0A                break;%0A            result = new TracingParseRunner(parser.DoubleQuotedString())%0A                .run(line);%0A            if (result.hasErrors()) %7B%0A                System.out.println(%22Invalid input!%22);%0A                System.out.println(ErrorUtils.printParseErrors(result));%0A            %7D else %7B%0A                System.out.println(ParseTreeUtils.printNodeTree(result));%0A            %7D%0A        %7D%0A    %7D%0A%7D%0A

Add a simple double quoted string parser