Object sense support / Bugfixes

This commit is contained in:
Anuken
2020-09-09 19:02:40 -04:00
parent c03e3f56aa
commit 5259969384
14 changed files with 101 additions and 23 deletions

View File

@@ -1,8 +1,8 @@
package mindustry.logic;
public enum ConditionOp{
equal("==", (a, b) -> Math.abs(a - b) < 0.000001),
notEqual("not", (a, b) -> Math.abs(a - b) >= 0.000001),
equal("==", (a, b) -> Math.abs(a - b) < 0.000001, (a, b) -> a == b),
notEqual("not", (a, b) -> Math.abs(a - b) >= 0.000001, (a, b) -> a != b),
lessThan("<", (a, b) -> a < b),
lessThanEq("<=", (a, b) -> a <= b),
greaterThan(">", (a, b) -> a > b),
@@ -10,12 +10,18 @@ public enum ConditionOp{
public static final ConditionOp[] all = values();
public final CondObjOpLambda objFunction;
public final CondOpLambda function;
public final String symbol;
ConditionOp(String symbol, CondOpLambda function){
this(symbol, function, null);
}
ConditionOp(String symbol, CondOpLambda function, CondObjOpLambda objFunction){
this.symbol = symbol;
this.function = function;
this.objFunction = objFunction;
}
@Override
@@ -23,6 +29,10 @@ public enum ConditionOp{
return symbol;
}
interface CondObjOpLambda{
boolean get(Object a, Object b);
}
interface CondOpLambda{
boolean get(double a, double b);
}

View File

@@ -25,6 +25,7 @@ public enum LAccess{
shootY,
shooting,
team,
type,
//values with parameters are considered controllable
enabled("to"), //"to" is standard for single parameter access

View File

@@ -8,6 +8,7 @@ import mindustry.gen.*;
import mindustry.logic.LExecutor.*;
import mindustry.logic.LStatements.*;
import mindustry.type.*;
import mindustry.world.*;
/** "Compiles" a sequence of statements into instructions. */
public class LAssembler{
@@ -38,6 +39,12 @@ public class LAssembler{
putConst("@" + liquid.name, liquid);
}
for(Block block : Vars.content.blocks()){
if(block.synthetic()){
putConst("@" + block.name, block);
}
}
//store sensor constants
for(LAccess sensor : LAccess.all){

View File

@@ -255,18 +255,22 @@ public class LExecutor{
Object target = exec.obj(from);
Object sense = exec.obj(type);
double output = 0;
if(target instanceof Senseable){
Senseable se = (Senseable)target;
if(sense instanceof Content){
output = ((Senseable)target).sense(((Content)sense));
exec.setnum(to, se.sense(((Content)sense)));
}else if(sense instanceof LAccess){
output = ((Senseable)target).sense(((LAccess)sense));
Object objOut = se.senseObject((LAccess)sense);
if(objOut == Senseable.noSensed){
//numeric output
exec.setnum(to, se.sense((LAccess)sense));
}else{
//object output
exec.setobj(to, objOut);
}
}
}
exec.setnum(to, output);
}
}
@@ -399,7 +403,17 @@ public class LExecutor{
if(op.unary){
exec.setnum(dest, op.function1.get(exec.num(a)));
}else{
exec.setnum(dest, op.function2.get(exec.num(a), exec.num(b)));
Var va = exec.vars[a];
Var vb = exec.vars[b];
if(op.objFunction2 != null && (va.isobj || vb.isobj)){
//use object function if provided, and one of the variables is an object
exec.setnum(dest, op.objFunction2.get(exec.obj(a), exec.obj(b)));
}else{
//otherwise use the numeric function
exec.setnum(dest, op.function2.get(exec.num(a), exec.num(b)));
}
}
}
}
@@ -554,8 +568,21 @@ public class LExecutor{
@Override
public void run(LExecutor exec){
if(address != -1 && op.function.get(exec.num(value), exec.num(compare))){
exec.vars[varCounter].numval = address;
if(address != -1){
Var va = exec.vars[value];
Var vb = exec.vars[compare];
boolean cmp = false;
if(op.objFunction != null && (va.isobj || vb.isobj)){
//use object function if provided, and one of the variables is an object
cmp = op.objFunction.get(exec.obj(value), exec.obj(compare));
}else{
cmp = op.function.get(exec.num(value), exec.num(compare));
}
if(cmp){
exec.vars[varCounter].numval = address;
}
}
}
}

View File

@@ -8,8 +8,8 @@ public enum LogicOp{
mul("*", (a, b) -> a * b),
div("/", (a, b) -> a / b),
mod("%", (a, b) -> a % b),
equal("==", (a, b) -> Math.abs(a - b) < 0.000001 ? 1 : 0),
notEqual("not", (a, b) -> Math.abs(a - b) < 0.000001 ? 0 : 1),
equal("==", (a, b) -> Math.abs(a - b) < 0.000001 ? 1 : 0, (a, b) -> a == b ? 1 : 0),
notEqual("not", (a, b) -> Math.abs(a - b) < 0.000001 ? 0 : 1, (a, b) -> a != b ? 1 : 0),
lessThan("<", (a, b) -> a < b ? 1 : 0),
lessThanEq("<=", (a, b) -> a <= b ? 1 : 0),
greaterThan(">", (a, b) -> a > b ? 1 : 0),
@@ -41,16 +41,22 @@ public enum LogicOp{
public static final LogicOp[] all = values();
public final OpObjLambda2 objFunction2;
public final OpLambda2 function2;
public final OpLambda1 function1;
public final boolean unary;
public final String symbol;
LogicOp(String symbol, OpLambda2 function){
this(symbol, function, null);
}
LogicOp(String symbol, OpLambda2 function, OpObjLambda2 objFunction){
this.symbol = symbol;
this.function2 = function;
this.function1 = null;
this.unary = false;
this.objFunction2 = objFunction;
}
LogicOp(String symbol, OpLambda1 function){
@@ -58,6 +64,7 @@ public enum LogicOp{
this.function1 = function;
this.function2 = null;
this.unary = true;
this.objFunction2 = null;
}
@Override
@@ -65,6 +72,10 @@ public enum LogicOp{
return symbol;
}
interface OpObjLambda2{
double get(Object a, Object b);
}
interface OpLambda2{
double get(double a, double b);
}

View File

@@ -3,6 +3,12 @@ package mindustry.logic;
import mindustry.ctype.*;
public interface Senseable{
Object noSensed = new Object();
double sense(LAccess sensor);
double sense(Content content);
default Object senseObject(LAccess sensor){
return noSensed;
}
}