public void Break(bool silent = false) { if (!silent && !allowControlCBreak) { return; } // grab the full stack and tuck it away for future reference ValList stack = M1API.StackList(interpreter.vm); // also find the first non-null entry, to display right away SourceLoc loc = null; if (interpreter.vm != null) { foreach (var stackLoc in interpreter.vm.GetStack()) { loc = stackLoc; if (loc != null) { break; } } } interpreter.Stop(); console.AbortInput(); console.keyBuffer.Clear(); if (!silent) { string msg = "BREAK"; if (loc != null) { msg += " at "; if (loc.context != null) { msg += loc.context + " "; } msg += "line " + loc.lineNum; } textDisplay.Print(msg + "\n"); //Debug.Log("printed: " + msg); } ValMap globals = interpreter.vm.globalContext.variables; interpreter.Reset(); interpreter.REPL(""); // (forces creation of a VM) interpreter.vm.globalContext.variables = globals; globals.SetElem(M1API._stackAtBreak, stack); AddGlobals(); //Debug.Log("Rebuilt VM and restored " + globals.Count + " globals"); }
public void UpdateScriptFromSelf() { if (positionMap == null) { positionMap = new ValMap(); } positionMap.SetElem(xStr, new ValNumber(transform.position.x)); positionMap.SetElem(yStr, new ValNumber(transform.position.y)); interpreter.SetGlobalValue("position", positionMap); if (actualMap == null) { actualMap = new ValMap(); } actualMap.SetElem(headingStr, new ValNumber(Mathf.Round(reindeer.curAngle))); actualMap.SetElem(speedStr, new ValNumber(Mathf.Round(reindeer.curSpeed / reindeer.maxSpeed * 100f))); interpreter.SetGlobalValue("actual", actualMap); interpreter.SetGlobalValue("energy", new ValNumber(Mathf.Round(reindeer.energy))); interpreter.SetGlobalValue("health", new ValNumber(reindeer.health)); interpreter.SetGlobalValue("deerCount", GetDeerCount()); interpreter.SetGlobalValue("heading", new ValNumber(Mathf.Round(reindeer.targetAngle))); }
static void AddIntrinsics() { if (intrinsicsAdded) { return; // already done! } intrinsicsAdded = true; Intrinsic f; // look // finds the closest enemy within a narrow angle of our current heading, // and returns a map with: distance, direction, heading, speed, energy, health. f = Intrinsic.Create("look"); f.code = (context, partialResult) => { ReindeerScript rs = context.interpreter.hostData as ReindeerScript; Vector2 here = rs.transform.position; Vector2 forward = rs.transform.right; Reindeer reindeer = rs.reindeer; ValMap result = null; float resultDist = 0; foreach (Reindeer deer in rs.game.deer) { if (deer == reindeer) { continue; } if (!deer.gameObject.activeSelf) { continue; } Vector2 dvec = (Vector2)deer.transform.position - here; float ang = Vector2.Angle(dvec, forward); if (ang < 5) { float dist = dvec.magnitude; if (result == null || dist < resultDist) { float direction = Mathf.Atan2(dvec.y, dvec.x) * Mathf.Rad2Deg; if (result == null) { result = ValMap.Create(); } resultDist = dist; // On second thought, not including direction, as this makes // aiming *too* precise. //result.SetElem(directionStr, new ValNumber(direction)); result.SetElem(distanceStr, ValNumber.Create(Mathf.Round(dist))); result.SetElem(headingStr, ValNumber.Create(deer.curAngle)); result.SetElem(speedStr, ValNumber.Create(deer.curSpeed)); result.SetElem(energyStr, ValNumber.Create(Mathf.Round(deer.energy))); result.SetElem(healthStr, ValNumber.Create(deer.health)); } } } return(new Intrinsic.Result(result)); }; // throw(energy=20) // fires a snowball in our current heading; returns 1 if success, 0 if failed. f = Intrinsic.Create("throw"); f.AddParam("energy", ValNumber.Create(20)); f.code = (context, partialResult) => { ReindeerScript rs = context.interpreter.hostData as ReindeerScript; Reindeer reindeer = rs.reindeer; float eCost = (float)context.GetVar("energy").DoubleValue(); if (reindeer.ThrowSnowball(eCost)) { return(new Intrinsic.Result(ValNumber.one)); } return(new Intrinsic.Result(ValNumber.zero)); }; // drop(energy=20, delay=5) // drops a meadow mine; returns 1 if success, 0 if failed f = Intrinsic.Create("drop"); f.AddParam("energy", ValNumber.Create(20)); f.AddParam("delay", ValNumber.Create(5)); f.code = (context, partialResult) => { ReindeerScript rs = context.interpreter.hostData as ReindeerScript; Reindeer reindeer = rs.reindeer; float eCost = (float)context.GetVar("energy").DoubleValue(); float delay = (float)context.GetVar("delay").DoubleValue(); if (reindeer.LayMine(eCost, delay)) { return(new Intrinsic.Result(ValNumber.one)); } return(new Intrinsic.Result(ValNumber.zero)); }; }