package lib.turtle; // Check usage of NativeStringTools // here https://api.haxe.org/lua/NativeStringTools.html // and here http://lua-users.org/wiki/StringLibraryTutorial import kernel.turtle.Types.TurtleSlot; import kernel.turtle.Turtle; import lua.NativeStringTools; using tink.CoreApi; /** Save a set of turtle instructions to a string and execute them. **/ class TurtleInstructionParser { public function new() {} public function encode(instructions:Array):String { var s = ""; var times = 0; var lastInstruction:TurtleInstruction = null; for (inst in instructions) { if (inst == lastInstruction) { times++; continue; } if (lastInstruction != null) { var encoded = encodeInstruction(lastInstruction); s = s + '${times + 1}$encoded'; } times = 0; lastInstruction = inst; } var encoded = encodeInstruction(lastInstruction); s = s + '${times + 1}$encoded'; return s; } private function encodeInstruction(inst:TurtleInstruction):String { for (k => v in cmdMap) { if (v == inst) { return k; } } switch inst { case Select(slot): return "m" + encodeSlot(slot); default: return ""; } return ""; } private function encodeSlot(slot:TurtleSlot):String { return String.fromCharCode(slot + 97); } public function parse(instructionsString:String):Array { var rtn:Array = []; var mfunc = NativeStringTools.gmatch(instructionsString, "%d+%D+"); while (true) { var found = mfunc(); if (found == null) { break; } var times = Std.parseInt(NativeStringTools.match(found, "%d+")); var command = NativeStringTools.match(found, "%D+"); var cmd = cmdMap.get(command); if (cmd != null) { rtn = rtn.concat([for (i in 0...times) cmd]); } switch command.charAt(0) { case "m": // select var slot = parseSlot(command.charAt(1)); rtn = rtn.concat([for (i in 0...times) Select(slot)]); } } return rtn; } private static function parseSlot(slot:String):TurtleSlot { var slot = slot.charCodeAt(0) - 97; if (slot < 0 || slot > Turtle.MAX_SLOTS) { // TODO: better error handling throw new Error("Invalid slot: " + slot); } return slot; } private var cmdMap:Map = [ "a" => Forward, "b" => Back, "c" => TurnLeft, "d" => TurnRight, "e" => Up, "f" => Down, "g" => Dig(Front), "h" => Dig(Up), "i" => Dig(Down), "j" => Place(Front), "k" => Place(Up), "l" => Place(Down), ]; }