Exemplo n.º 1
0
        static int Run(RunOptions options)
        {
            CheckFileList(options.files, ALLOWED_EXTENSIONS);

            // Create the object that handles callbacks
            var impl = new ConsoleRunnerImplementation(waitForLines: options.waitForInput);

            // load the default variables we got on the command line
            foreach (var variable in options.variables)
            {
                var entry = variable.Split(new char[] { '=' }, StringSplitOptions.RemoveEmptyEntries);

                float value;
                // If there aren't two parts to this or the second part isn't a float, fail
                if (entry.Length != 2 || float.TryParse(entry[1], out value) == false)
                {
                    Warn(string.Format(CultureInfo.CurrentCulture, "Skipping invalid variable {0}", variable));
                    continue;
                }
                var name = entry[0];

                impl.SetNumber(name, value);
            }

            if (options.automaticallySelectFirstOption == true)
            {
                impl.autoSelectFirstOption = true;
            }

            Dialogue dialogue = CreateDialogue(options, impl);

            // Run the conversation

            for (int run = 0; run < options.runTimes; run++)
            {
                foreach (var step in dialogue.Run(options.startNode))
                {
                    // It can be one of three types: a line to show, options
                    // to present to the user, or an internal command to run

                    if (step is Dialogue.LineResult)
                    {
                        var lineResult = step as Dialogue.LineResult;
                        impl.RunLine(lineResult.line);
                    }
                    else if (step is Dialogue.OptionSetResult)
                    {
                        var optionsResult = step as Dialogue.OptionSetResult;
                        impl.RunOptions(optionsResult.options, optionsResult.setSelectedOptionDelegate);
                    }
                    else if (step is Dialogue.CommandResult)
                    {
                        var commandResult = step as Dialogue.CommandResult;
                        impl.RunCommand(commandResult.command.text);
                    }
                }
                impl.DialogueComplete();
            }
            return(0);
        }
Exemplo n.º 2
0
        public static void Main(string[] args)
        {
            if (args.Length == 0)
            {
                ShowHelpAndExit();
            }
            bool   showTokens            = false;
            bool   showParseTree         = false;
            bool   waitForLines          = false;
            string onlyConsiderNode      = null;
            bool   showDebugging         = false;
            int    runTimes              = 1;
            bool   compileToBytecodeOnly = false;

            var    inputFiles = new List <string> ();
            string startNode  = Dialogue.DEFAULT_START;

            string[] allowedExtensions = { ".node", ".json" };

            var defaultVariables = new Dictionary <string, float> ();

            foreach (var arg in args)
            {
                // Handle 'start' parameter
                if (arg.IndexOf("-s=") != -1)
                {
                    var startArray = arg.Split(new char[] { '=' });
                    if (startArray.Length != 2)
                    {
                        ShowHelpAndExit();
                    }
                    else
                    {
                        startNode = startArray [1];
                        continue;
                    }
                }

                // Handle variable input
                if (arg.IndexOf("-v") != -1)
                {
                    var variable      = arg.Substring(2);
                    var variableArray = variable.Split(new char[] { '=' });
                    if (variableArray.Length != 2)
                    {
                        ShowHelpAndExit();
                    }
                    else
                    {
                        var varName  = "$" + variableArray [0];
                        var varValue = float.Parse(variableArray [1]);
                        defaultVariables [varName] = varValue;
                        continue;
                    }
                }

                // Handle 'only this node' parameter
                if (arg.IndexOf("-o=") != -1)
                {
                    var startArray = arg.Split(new char[] { '=' });
                    if (startArray.Length != 2)
                    {
                        ShowHelpAndExit();
                    }
                    else
                    {
                        onlyConsiderNode = startArray [1];
                        continue;
                    }
                }

                // Handle 'run times' parameter
                if (arg.IndexOf("-r=") != -1)
                {
                    var argArray = arg.Split('=');
                    if (argArray.Length != 2)
                    {
                        ShowHelpAndExit();
                    }
                    else
                    {
                        runTimes = int.Parse(argArray [1]);
                        continue;
                    }
                }


                switch (arg)
                {
                case "-t":
                    showTokens    = true;
                    showDebugging = true;
                    break;

                case "-p":
                    showParseTree = true;
                    showDebugging = true;
                    break;

                case "-w":
                    waitForLines = true;
                    break;

                case "-d":
                    showDebugging = true;
                    break;

                case "-c":
                    compileToBytecodeOnly = true;
                    break;

                case "-h":
                    ShowHelpAndExit();
                    break;

                default:

                    // only allow one file
                    if (inputFiles.Count > 0)
                    {
                        Console.Error.WriteLine("Error: Too many files specified.");
                        Environment.Exit(1);
                    }

                    var extension = System.IO.Path.GetExtension(arg);
                    if (Array.IndexOf(allowedExtensions, extension) != -1)
                    {
                        inputFiles.Add(arg);
                    }
                    break;
                }
            }

            if (inputFiles.Count == 0)
            {
                Console.Error.WriteLine("Error: No files specified.");
                Environment.Exit(1);
            }

            // Create the object that handles callbacks
            var impl = new ConsoleRunnerImplementation(waitForLines: waitForLines);

            // load the default variables we got on the command line
            foreach (var variable in defaultVariables)
            {
                impl.SetNumber(variable.Key, variable.Value);
            }

            // Load nodes
            var dialogue = new Dialogue(impl);


            // Add some methods for testing
            dialogue.library.RegisterFunction("add_three_operands", 3, delegate(Value[] parameters) {
                var f1 = parameters[0].AsNumber;
                var f2 = parameters[1].AsNumber;
                var f3 = parameters[2].AsNumber;

                return(f1 + f2 + f3);
            });

            dialogue.library.RegisterFunction("last_value", -1, delegate(Value[] parameters) {
                // return the last value
                return(parameters[parameters.Length - 1]);
            });

            dialogue.library.RegisterFunction("is_even", 1, delegate(Value[] parameters) {
                return((int)parameters[0].AsNumber % 2 == 0);
            });

            // Register the "assert" function, which stops execution if its parameter evaluates to false
            dialogue.library.RegisterFunction("assert", 1, delegate(Value[] parameters) {
                if (parameters[0].AsBool == false)
                {
                    // TODO: Include file, node and line number
                    dialogue.LogErrorMessage("ASSERTION FAILED");
                    Environment.Exit(1);
                }
            });


            // Register a function to let test scripts register how many
            // options they expect to send
            dialogue.library.RegisterFunction("prepare_for_options", 2, delegate(Value[] parameters) {
                impl.numberOfExpectedOptions = (int)parameters [0].AsNumber;
                impl.autoSelectOptionNumber  = (int)parameters[1].AsNumber;
            });

            dialogue.library.RegisterFunction("expect_line", 1, delegate(Value[] parameters) {
                impl.expectedNextLine = parameters[0].AsString;
            });

            dialogue.library.RegisterFunction("expect_command", 1, delegate(Value[] parameters) {
                impl.expectedNextCommand = parameters[0].AsString;
            });

            // If debugging is enabled, log debug messages; otherwise, ignore them
            if (showDebugging)
            {
                dialogue.LogDebugMessage = delegate(string message) {
                    Console.WriteLine("Debug: " + message);
                };
            }
            else
            {
                dialogue.LogDebugMessage = delegate(string message) {};
            }

            dialogue.LogErrorMessage = delegate(string message) {
                Console.WriteLine("ERROR: " + message);
            };

            dialogue.LoadFile(inputFiles [0], showTokens, showParseTree, onlyConsiderNode);

            if (compileToBytecodeOnly)
            {
                var result = dialogue.Compile();
                Console.WriteLine(result);
            }

            // Only run the program when we're not emitting debug output of some kind
            var runProgram =
                showTokens == false &&
                showParseTree == false &&
                compileToBytecodeOnly == false;

            if (runProgram)
            {
                // Run the conversation

                for (int run = 0; run < runTimes; run++)
                {
                    foreach (var step in dialogue.Run(startNode))
                    {
                        // It can be one of three types: a line to show, options
                        // to present to the user, or an internal command to run

                        if (step is Dialogue.LineResult)
                        {
                            var lineResult = step as Dialogue.LineResult;
                            impl.RunLine(lineResult.line);
                        }
                        else if (step is Dialogue.OptionSetResult)
                        {
                            var optionsResult = step as Dialogue.OptionSetResult;
                            impl.RunOptions(optionsResult.options, optionsResult.setSelectedOptionDelegate);
                        }
                        else if (step is Dialogue.CommandResult)
                        {
                            var commandResult = step as Dialogue.CommandResult;
                            impl.RunCommand(commandResult.command.text);
                        }
                    }
                    impl.DialogueComplete();
                }
            }
        }
Exemplo n.º 3
0
        static internal Dialogue CreateDialogue(ExecutionOptions options, ConsoleRunnerImplementation impl)
        {
            // Load nodes
            var dialogue = new Dialogue(impl);

            // Add some methods for testing
            dialogue.library.RegisterFunction("add_three_operands", 3, delegate(Value[] parameters)
            {
                return(parameters[0] + parameters[1] + parameters[2]);
            });

            dialogue.library.RegisterFunction("last_value", -1, delegate(Value[] parameters)
            {
                // return the last value
                return(parameters[parameters.Length - 1]);
            });

            dialogue.library.RegisterFunction("is_even", 1, delegate(Value[] parameters)
            {
                return((int)parameters[0].AsNumber % 2 == 0);
            });

            // Register the "assert" function, which stops execution if its parameter evaluates to false
            dialogue.library.RegisterFunction("assert", -1, delegate(Value[] parameters)
            {
                if (parameters[0].AsBool == false)
                {
                    // TODO: Include file, node and line number
                    if (parameters.Length > 1 && parameters[1].AsBool)
                    {
                        dialogue.LogErrorMessage("ASSERTION FAILED: " + parameters[1].AsString);
                    }
                    else
                    {
                        dialogue.LogErrorMessage("ASSERTION FAILED");
                    }
                    Environment.Exit(1);
                }
            });


            // Register a function to let test scripts register how many
            // options they expect to send
            dialogue.library.RegisterFunction("prepare_for_options", 2, delegate(Value[] parameters)
            {
                impl.numberOfExpectedOptions = (int)parameters[0].AsNumber;
                impl.autoSelectOptionNumber  = (int)parameters[1].AsNumber;
            });

            dialogue.library.RegisterFunction("expect_line", 1, delegate(Value[] parameters)
            {
                impl.expectedNextLine = parameters[0].AsString;
            });

            dialogue.library.RegisterFunction("expect_command", 1, delegate(Value[] parameters)
            {
                impl.expectedNextCommand = parameters[0].AsString;
            });

            // If debugging is enabled, log debug messages; otherwise, ignore them
            if (options.showDebuggingInfo)
            {
                dialogue.LogDebugMessage = delegate(string message)
                {
                    Note(message);
                };
            }
            else
            {
                dialogue.LogDebugMessage = delegate(string message) { };
            }

            dialogue.LogErrorMessage = delegate(string message)
            {
                Warn("Yarn Error: " + message);
            };

            foreach (var file in options.files)
            {
                try
                {
                    dialogue.LoadFile(file, false, false, options.onlyConsiderNode);
                }
                catch (Yarn.ParseException e)
                {
                    Warn(e.Message);
                }
            }

            // Load string table
            if (options.stringTable != null)
            {
                var parsedTable = new Dictionary <string, string>();

                using (var reader = new System.IO.StreamReader(options.stringTable))
                {
                    using (var csvReader = new CsvReader(reader))
                    {
                        if (csvReader.ReadHeader() == false)
                        {
                            Error(string.Format(CultureInfo.CurrentCulture, "{0} is not a valid string table", options.stringTable));
                        }

                        foreach (var row in csvReader.GetRecords <LocalisedLine>())
                        {
                            parsedTable[row.LineCode] = row.LineText;
                        }
                    }
                }

                dialogue.AddStringTable(parsedTable);
            }

            return(dialogue);
        }
Exemplo n.º 4
0
        public static void Main(string[] args)
        {
            if (args.Length == 0) {
                ShowHelpAndExit ();
            }
            bool showTokens = false;
            bool showParseTree = false;
            bool waitForLines = false;
            string onlyConsiderNode = null;
            bool showDebugging = false;
            int runTimes = 1;

            var inputFiles = new List<string> ();
            string startNode = Dialogue.DEFAULT_START;

            string[] allowedExtensions = {".node", ".json" };

            var defaultVariables = new Dictionary<string,float> ();

            foreach (var arg in args) {

                // Handle 'start' parameter
                if (arg.IndexOf("-s=") != -1) {
                    var startArray = arg.Split (new char[]{ '=' });
                    if (startArray.Length != 2) {
                        ShowHelpAndExit ();
                    } else {
                        startNode = startArray [1];
                        continue;
                    }
                }

                // Handle variable input
                if (arg.IndexOf("-v") != -1) {
                    var variable = arg.Substring (2);
                    var variableArray = variable.Split (new char[]{ '=' });
                    if (variableArray.Length != 2) {
                        ShowHelpAndExit ();
                    } else {
                        var varName = "$" + variableArray [0];
                        var varValue = float.Parse (variableArray [1]);
                        defaultVariables [varName] = varValue;
                        continue;
                    }

                }

                // Handle 'only this node' parameter
                if (arg.IndexOf("-o=") != -1) {
                    var startArray = arg.Split (new char[]{ '=' });
                    if (startArray.Length != 2) {
                        ShowHelpAndExit ();
                    } else {
                        onlyConsiderNode = startArray [1];
                        continue;
                    }
                }

                // Handle 'run times' parameter
                if (arg.IndexOf("-r=") != -1) {
                    var argArray = arg.Split ('=');
                    if (argArray.Length != 2) {
                        ShowHelpAndExit ();
                    } else {
                        runTimes = int.Parse (argArray [1]);
                        continue;
                    }

                }

                switch (arg) {
                case "-t":
                    showTokens = true;
                    showDebugging = true;
                    break;
                case "-p":
                    showParseTree = true;
                    showDebugging = true;
                    break;
                case "-w":
                    waitForLines = true;
                    break;
                case "-d":
                    showDebugging = true;
                    break;
                case "-h":
                    ShowHelpAndExit ();
                    break;
                default:

                    // only allow one file
                    if (inputFiles.Count > 0) {
                        Console.Error.WriteLine ("Error: Too many files specified.");
                        Environment.Exit (1);
                    }

                    var extension = System.IO.Path.GetExtension (arg);
                    if (Array.IndexOf(allowedExtensions, extension) != -1) {
                        inputFiles.Add (arg);
                    }
                    break;
                }
            }

            if (inputFiles.Count == 0) {
                Console.Error.WriteLine ("Error: No files specified.");
                Environment.Exit (1);
            }

            // Create the object that handles callbacks
            var impl = new ConsoleRunnerImplementation (waitForLines:waitForLines);

            // load the default variables we got on the command line
            foreach (var variable in defaultVariables) {

                impl.SetNumber (variable.Key, variable.Value);
            }

            // Load nodes
            var dialogue = new Dialogue(impl);

            // Add some methods for testing
            dialogue.library.RegisterFunction ("add_three_operands", 3, delegate(Value[] parameters) {
                var f1 = parameters[0].AsNumber;
                var f2 = parameters[1].AsNumber;
                var f3 = parameters[2].AsNumber;

                return f1+f2+f3;
            });

            dialogue.library.RegisterFunction ("last_value", -1, delegate(Value[] parameters) {
                // return the last value
                return parameters[parameters.Length-1];
            });

            dialogue.library.RegisterFunction ("is_even", 1, delegate(Value[] parameters) {
                return (int)parameters[0].AsNumber % 2 == 0;
            });

            // If debugging is enabled, log debug messages; otherwise, ignore them
            if (showDebugging) {
                dialogue.LogDebugMessage = delegate(string message) {
                    Console.WriteLine ("Debug: " + message);
                };
            } else {
                dialogue.LogDebugMessage = delegate(string message) {};
            }

            dialogue.LogErrorMessage = delegate(string message) {
                Console.WriteLine ("ERROR: " + message);
            };

            dialogue.LoadFile (inputFiles [0],showTokens, showParseTree, onlyConsiderNode);

            if (showTokens == false && showParseTree == false) {
                // Run the conversation

                for (int run = 0; run < runTimes; run++) {
                    foreach (var step in dialogue.Run (startNode)) {

                        // It can be one of three types: a line to show, options
                        // to present to the user, or an internal command to run

                        if (step is Dialogue.LineResult) {
                            var lineResult = step as Dialogue.LineResult;
                            impl.RunLine (lineResult.line);
                        } else if (step is Dialogue.OptionSetResult) {
                            var optionsResult = step as Dialogue.OptionSetResult;
                            impl.RunOptions (optionsResult.options, optionsResult.setSelectedOptionDelegate);
                        } else if (step is Dialogue.CommandResult) {
                            var commandResult = step as Dialogue.CommandResult;
                            impl.RunCommand (commandResult.command.text);
                        }
                    }
                    impl.DialogueComplete ();
                }

            }
        }
Exemplo n.º 5
0
        public static void Main(string[] args)
        {
            if (args.Length == 0) {
                ShowHelpAndExit ();
            }

            bool showTokens = false;
            bool showParseTree = false;
            bool waitForLines = false;
            string onlyConsiderNode = null;
            bool showDebugging = false;
            int runTimes = 1;
            bool compileToBytecodeOnly = false;
            bool verifyOnly = false;
            bool autoSelectFirstOption = false;
            bool analyseOnly = false;

            var inputFiles = new List<string> ();
            string startNode = Dialogue.DEFAULT_START;

            string[] allowedExtensions = {".node", ".json" };

            var defaultVariables = new Dictionary<string,float> ();

            foreach (var arg in args) {

                // Handle 'start' parameter
                if (arg.IndexOf("-s=") != -1) {
                    var startArray = arg.Split (new char[]{ '=' });
                    if (startArray.Length != 2) {
                        ShowHelpAndExit ();
                    } else {
                        startNode = startArray [1];
                        continue;
                    }
                }

                // Handle variable input
                if (arg.IndexOf("-v") != -1) {
                    var variable = arg.Substring (2);
                    var variableArray = variable.Split (new char[]{ '=' });
                    if (variableArray.Length != 2) {
                        ShowHelpAndExit ();
                    } else {
                        var varName = "$" + variableArray [0];
                        var varValue = float.Parse (variableArray [1]);
                        defaultVariables [varName] = varValue;
                        continue;
                    }

                }

                // Handle 'only this node' parameter
                if (arg.IndexOf("-o=") != -1) {
                    var startArray = arg.Split (new char[]{ '=' });
                    if (startArray.Length != 2) {
                        ShowHelpAndExit ();
                    } else {
                        onlyConsiderNode = startArray [1];
                        continue;
                    }
                }

                // Handle 'run times' parameter
                if (arg.IndexOf("-r=") != -1) {
                    var argArray = arg.Split ('=');
                    if (argArray.Length != 2) {
                        ShowHelpAndExit ();
                    } else {
                        runTimes = int.Parse (argArray [1]);
                        continue;
                    }

                }

                switch (arg) {
                case "-V":
                    verifyOnly = true;
                    break;
                case "-t":
                    showTokens = true;
                    showDebugging = true;
                    break;
                case "-p":
                    showParseTree = true;
                    showDebugging = true;
                    break;
                case "-w":
                    waitForLines = true;
                    break;
                case "-d":
                    showDebugging = true;
                    break;
                case "-c":
                    compileToBytecodeOnly = true;
                    break;
                case "-1":
                    autoSelectFirstOption = true;
                    break;
                case "-h":
                    ShowHelpAndExit ();
                    break;
                case "-a":
                    analyseOnly = true;
                    break;
                default:

                    // only allow one file
                    if (inputFiles.Count > 0) {
                        Console.Error.WriteLine ("Error: Too many files specified.");
                        Environment.Exit (1);
                    }

                    var extension = System.IO.Path.GetExtension (arg);
                    if (Array.IndexOf(allowedExtensions, extension) != -1) {
                        inputFiles.Add (arg);
                    }
                    break;
                }
            }

            if (inputFiles.Count == 0) {
                Console.Error.WriteLine ("Error: No files specified.");
                Environment.Exit (1);
            }

            // Create the object that handles callbacks
            var impl = new ConsoleRunnerImplementation (waitForLines:waitForLines);

            // load the default variables we got on the command line
            foreach (var variable in defaultVariables) {

                impl.SetNumber (variable.Key, variable.Value);
            }

            // Load nodes
            var dialogue = new Dialogue(impl);

            // Add some methods for testing
            dialogue.library.RegisterFunction ("add_three_operands", 3, delegate(Value[] parameters) {
                return parameters[0]+parameters[1]+parameters[2];
            });

            dialogue.library.RegisterFunction ("last_value", -1, delegate(Value[] parameters) {
                // return the last value
                return parameters[parameters.Length-1];
            });

            dialogue.library.RegisterFunction ("is_even", 1, delegate(Value[] parameters) {
                return (int)parameters[0].AsNumber % 2 == 0;
            });

            // Register the "assert" function, which stops execution if its parameter evaluates to false
            dialogue.library.RegisterFunction ("assert", -1, delegate(Value[] parameters) {
                if (parameters[0].AsBool == false) {

                    // TODO: Include file, node and line number
                    if( parameters.Length > 1 && parameters[1].AsBool ) {
                        dialogue.LogErrorMessage ("ASSERTION FAILED: " + parameters[1].AsString);
                    } else {
                        dialogue.LogErrorMessage ("ASSERTION FAILED");
                    }
                    Environment.Exit(1);
                }
            });

            // Register a function to let test scripts register how many
            // options they expect to send
            dialogue.library.RegisterFunction ("prepare_for_options", 2, delegate(Value[] parameters) {
                impl.numberOfExpectedOptions = (int)parameters [0].AsNumber;
                impl.autoSelectOptionNumber = (int)parameters[1].AsNumber;
            });

            dialogue.library.RegisterFunction ("expect_line", 1, delegate(Value[] parameters) {
                impl.expectedNextLine = parameters[0].AsString;
            });

            dialogue.library.RegisterFunction ("expect_command", 1, delegate(Value[] parameters) {
                impl.expectedNextCommand = parameters[0].AsString;
            });

            if (autoSelectFirstOption == true) {
                impl.autoSelectFirstOption = true;
            }

            // If debugging is enabled, log debug messages; otherwise, ignore them
            if (showDebugging) {
                dialogue.LogDebugMessage = delegate(string message) {
                    Console.WriteLine ("Debug: " + message);
                };
            } else {
                dialogue.LogDebugMessage = delegate(string message) {};
            }

            dialogue.LogErrorMessage = delegate(string message) {
                Console.WriteLine ("ERROR: " + message);
            };

            if (verifyOnly) {
                try {
                    dialogue.LoadFile (inputFiles [0],showTokens, showParseTree, onlyConsiderNode);
                } catch (Exception e) {
                    Console.WriteLine ("Error: " + e.Message);
                }
                return;
            }

            dialogue.LoadFile (inputFiles [0],showTokens, showParseTree, onlyConsiderNode);

            if (compileToBytecodeOnly) {
                var result = dialogue.GetByteCode ();
                Console.WriteLine (result);
                return;
            }

            if (analyseOnly) {

                var context = new Yarn.Analysis.Context ();

                dialogue.Analyse (context);

                foreach (var diagnosis in context.FinishAnalysis()) {
                    Console.WriteLine (diagnosis.ToString(showSeverity:true));
                }
                return;
            }

            // Only run the program when we're not emitting debug output of some kind
            var runProgram =
                showTokens == false &&
                showParseTree == false &&
                compileToBytecodeOnly == false &&
                analyseOnly == false;

            if (runProgram) {
                // Run the conversation

                for (int run = 0; run < runTimes; run++) {
                    foreach (var step in dialogue.Run (startNode)) {

                        // It can be one of three types: a line to show, options
                        // to present to the user, or an internal command to run

                        if (step is Dialogue.LineResult) {
                            var lineResult = step as Dialogue.LineResult;
                            impl.RunLine (lineResult.line);
                        } else if (step is Dialogue.OptionSetResult) {
                            var optionsResult = step as Dialogue.OptionSetResult;
                            impl.RunOptions (optionsResult.options, optionsResult.setSelectedOptionDelegate);
                        } else if (step is Dialogue.CommandResult) {
                            var commandResult = step as Dialogue.CommandResult;
                            impl.RunCommand (commandResult.command.text);
                        }
                    }
                    impl.DialogueComplete ();
                }

            }
        }