Compare commits

..

6 Commits

Author SHA1 Message Date
aca39ea46f added turtleInstructionParser 2022-04-13 21:40:57 +02:00
b40e293d6e added turtle executer 2022-04-13 21:40:45 +02:00
dffb493d4f added turtle instruction set 2022-04-13 21:40:33 +02:00
a5c023c78a added item class 2022-04-13 21:40:19 +02:00
82939e53cc improved turtle kernel 2022-04-13 21:39:59 +02:00
96c6595846 make turtle slot 0 based in kernel 2022-04-12 01:02:04 +02:00
5 changed files with 228 additions and 9 deletions

View File

@@ -6,6 +6,7 @@ using tink.CoreApi;
class Turtle {
public static var instance:Turtle;
public static final MAX_SLOTS:Int = 16;
@:allow(kernel.Init)
private function new() {
@@ -109,7 +110,7 @@ class Turtle {
public function selectSlot(slot:TurtleSlot):Outcome<Noise, Noise> {
// TODO: slot in bounds?
var r = cc.Turtle.select(slot);
var r = cc.Turtle.select(slot + 1);
return (r) ? Outcome.Success(null) : Outcome.Failure("Slot out of bounds");
}
@@ -117,13 +118,13 @@ class Turtle {
public function getItemCount(?slot:TurtleSlot):Int {
// TODO: slot in bounds?
return cc.Turtle.getItemCount(slot);
return cc.Turtle.getItemCount(slot + 1);
}
public function getItemSpace(?slot:TurtleSlot):Int {
// TODO: slot in bounds?
return cc.Turtle.getItemSpace(slot);
return cc.Turtle.getItemSpace(slot + 1);
}
public function detect(dir:InteractDirections):Bool {
@@ -196,16 +197,17 @@ class Turtle {
}
public function compareSlot(otherSlot:TurtleSlot):Bool {
return cc.Turtle.compareTo(otherSlot);
return cc.Turtle.compareTo(otherSlot + 1);
}
public function transferToSlot(to:TurtleSlot, ?count:Int):Outcome<Noise, Noise> {
var r = cc.Turtle.transferTo(to, count);
public function transfer(from:TurtleSlot, to:TurtleSlot, ?count:Int):Outcome<Noise, Noise> {
this.selectSlot(from);
var r = cc.Turtle.transferTo(to + 1, count);
return r ? Outcome.Success(null) : Outcome.Failure(null);
}
public function getSelectedSlot():TurtleSlot {
return cc.Turtle.getSelectedSlot();
return cc.Turtle.getSelectedSlot() - 1;
}
public function getFuelLimit():Int {
@@ -245,7 +247,7 @@ class Turtle {
}
public function getItemDetail(?detailed:Bool = false, ?slot:TurtleSlot):Option<ItemInspect> {
var r = cc.Turtle.getItemDetail(slot); // FIXME: can take detailed as flag. Has to be fixed upstream
var r = cc.Turtle.getItemDetail(slot + 1); // FIXME: can take detailed as flag. Has to be fixed upstream
if (r == null) {
return None;

23
src/lib/Item.hx Normal file
View File

@@ -0,0 +1,23 @@
package lib;
/**
Represents an item in the game.
**/
abstract Item(String) to String {
public inline function new(name: String) {
// Check if the name is valid. in the format `mod:item_name` e.g. `minecraft:apple`
// TODO: implement
// make sure to not use regex
this = name;
}
@:from(String)
public static function fromString(s: String) {
return new Item(s);
}
function getBase(): String {
return this.split(":")[0];
}
}

View File

@@ -0,0 +1,51 @@
package lib.turtle;
import kernel.turtle.Turtle;
using tink.CoreApi;
class TurtleExecuter {
private var instructions:Array<TurtleInstruction>;
public function new(instructions:Array<TurtleInstruction>) {
this.instructions = instructions;
}
public function execute() {
for (inst in instructions){
executeInst(inst);
}
}
private function executeInst(instruction: TurtleInstruction): Outcome<Noise,String> {
switch instruction {
case Forward:
return Turtle.instance.forward();
case Back:
return Turtle.instance.back();
case Up:
return Turtle.instance.up();
case Down:
return Turtle.instance.down();
case TurnLeft:
return Turtle.instance.turnLeft();
case TurnRight:
return Turtle.instance.turnRight();
case Dig(dir):
return Turtle.instance.dig(dir);
case Place(dir):
return Turtle.instance.place(dir);
case PlacseSign(dir, text):
return Turtle.instance.placeSign(dir, text);
case Select(slot):
var r = Turtle.instance.selectSlot(slot);
if (r.isSuccess()) {
return Outcome.Success(null);
} else {
return Outcome.Failure("Failed to select slot");
}
}
return Outcome.Failure("Unknown instruction: " + instruction);
}
}

View File

@@ -0,0 +1,17 @@
package lib.turtle;
import kernel.turtle.Types.InteractDirections;
import kernel.turtle.Types.TurtleSlot;
enum TurtleInstruction {
Forward;
Back;
Up;
Down;
TurnLeft;
TurnRight;
Dig(dir: InteractDirections);
Place(dir: InteractDirections);
PlacseSign(dir: InteractDirections, text: String);
Select(slot: TurtleSlot);
}

View File

@@ -0,0 +1,126 @@
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<TurtleInstruction>): 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<TurtleInstruction> {
var rtn: Array<TurtleInstruction> = [];
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<String,TurtleInstruction> = [
"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),
];
}