diff --git a/src/main/java/carpet/script/CarpetExpression.java b/src/main/java/carpet/script/CarpetExpression.java
index 8083c2d7..6af69768 100644
--- a/src/main/java/carpet/script/CarpetExpression.java
+++ b/src/main/java/carpet/script/CarpetExpression.java
@@ -365,6 +365,23 @@ public class CarpetExpression
* block(0,0,0) == block('bedrock') => 1
* block('hopper[facing=north]{Items:[{Slot:1b,id:"minecraft:slime_ball",Count:16b}]}') => hopper
*
+ *
Retrieving a block with block function has also a side-effect of evaluating its current state and data.
+ * so if you use it later it will reflect block state and data of the block that was when block was called, rather than
+ * when it was used. Block values passed in various places like scan functions, etc, are not fully evaluated
+ * unless its properties are needed. This means that if the block at the location changes before its queried in the program
+ * this might result in getting the later state, which might not be desired. Consider the following example:
+ *
+ * set(10,10,10,'stone');
+ * scan(10,10,10,0,0,0, b = _);
+ * set(10,10,10,'air');
+ * print(b); // 'air', block was remembered 'lazily', and evaluated by `print`, when it was already set to air
+ *
+ * set(10,10,10,'stone');
+ * scan(10,10,10,0,0,0, b = block(_));
+ * set(10,10,10,'air');
+ * print(b); // 'stone', block was evaluated 'eagerly' but call to `block`
+ *
+ *
* World Manipulation
* All the functions below can be used with block value, queried with coord triple, or 3-long list.
* All pos in the functions referenced below refer to either method of passing block position
@@ -669,7 +686,10 @@ public class CarpetExpression
{
throw new InternalExpressionException("Block requires at least one parameter");
}
- Value retval = BlockValue.fromParams(cc, lv, 0, true).block;
+ BlockValue retval = BlockValue.fromParams(cc, lv, 0, true).block;
+ // fixing block state and data
+ retval.getBlockState();
+ retval.getData();
return (c_, t_) -> retval;
});
@@ -2086,7 +2106,8 @@ public class CarpetExpression
c.setVariable("_z", (c_, t_) -> new NumericValue(zFinal).bindTo("_z"));
Value blockValue = BlockValue.fromCoords(((CarpetContext)c), xFinal,yFinal,zFinal).bindTo("_");
c.setVariable( "_", (cc_, t_c) -> blockValue);
- if (expr.evalValue(c, Context.BOOLEAN).getBoolean())
+ Value result = expr.evalValue(c, t);
+ if (t != Context.VOID && result.getBoolean())
{
sCount += 1;
}
@@ -2138,7 +2159,8 @@ public class CarpetExpression
c.setVariable("_z", (c_, t_) -> new NumericValue(zFinal).bindTo("_z"));
Value blockValue = BlockValue.fromCoords(((CarpetContext)c), xFinal,yFinal,zFinal).bindTo("_");
c.setVariable( "_", (cc_, t_c) -> blockValue);
- if (expr.evalValue(c, Context.BOOLEAN).getBoolean())
+ Value result = expr.evalValue(c, t);
+ if (t != Context.VOID && result.getBoolean())
{
sCount += 1;
}
diff --git a/src/main/java/carpet/script/Expression.java b/src/main/java/carpet/script/Expression.java
index a0019457..14608707 100644
--- a/src/main/java/carpet/script/Expression.java
+++ b/src/main/java/carpet/script/Expression.java
@@ -994,8 +994,9 @@ public class Expression implements Cloneable
addLazyBinaryOperator(";",precedence.get("nextop;"), true, (c, t, lv1, lv2) ->
{
- Value v1 = lv1.evalValue(c, Context.VOID);
- return lv2;
+ lv1.evalValue(c, Context.VOID);
+ Value v2 = lv2.evalValue(c, t);
+ return (cc, tt) -> v2;
});
//assigns const procedure to the lhs, returning its previous value
@@ -1053,13 +1054,13 @@ public class Expression implements Cloneable
if (lv.get(i).evalValue(c, Context.BOOLEAN).getBoolean())
{
//int iFinal = i;
- Value ret = lv.get(i+1).evalValue(c);
+ Value ret = lv.get(i+1).evalValue(c, t);
return (cc, tt) -> ret;
}
}
if (lv.size()%2 == 1)
{
- Value ret = lv.get(lv.size() - 1).evalValue(c);
+ Value ret = lv.get(lv.size() - 1).evalValue(c, t);
return (cc, tt) -> ret;
}
return (cc, tt) -> Value.NULL;
@@ -1746,7 +1747,7 @@ public class Expression implements Cloneable
c.setVariable("_",(cc, tt) -> new NumericValue(0).bindTo("_"));
while (i new NumericValue(seriously).bindTo("_"));
@@ -1777,8 +1778,8 @@ public class Expression implements Cloneable
{
long whyYouAsk = i;
c.setVariable("_", (cc, tt) -> new NumericValue(whyYouAsk).bindTo("_"));
- lastOne = expr.evalValue(c);
- if (cond != null && cond.evalValue(c).getBoolean())
+ lastOne = expr.evalValue(c, t);
+ if (cond != null && cond.evalValue(c, Context.BOOLEAN).getBoolean())
break;
}
//revering scope
@@ -1817,7 +1818,7 @@ public class Expression implements Cloneable
c.setVariable("_", (cc, tt) -> next);
c.setVariable("_i", (cc, tt) -> new NumericValue(doYouReally).bindTo("_i"));
result.add(expr.evalValue(c));
- if (cond != null && cond.evalValue(c).getBoolean())
+ if (cond != null && cond.evalValue(c, Context.BOOLEAN).getBoolean())
{
next.boundVariable = var;
break;
@@ -1861,9 +1862,9 @@ public class Expression implements Cloneable
int seriously = i;
c.setVariable("_", (cc, tt) -> next);
c.setVariable("_i", (cc, tt) -> new NumericValue(seriously).bindTo("_i"));
- if(expr.evalValue(c).getBoolean())
+ if(expr.evalValue(c, Context.BOOLEAN).getBoolean())
result.add(next);
- if (cond != null && cond.evalValue(c).getBoolean())
+ if (cond != null && cond.evalValue(c, Context.BOOLEAN).getBoolean())
{
next.boundVariable = var;
break;
@@ -1901,7 +1902,7 @@ public class Expression implements Cloneable
int seriously = i;
c.setVariable("_", (cc, tt) -> next);
c.setVariable("_i", (cc, tt) -> new NumericValue(seriously).bindTo("_i"));
- if(expr.evalValue(c).getBoolean())
+ if(expr.evalValue(c, Context.BOOLEAN).getBoolean())
{
result = next;
next.boundVariable = var;
@@ -1939,7 +1940,7 @@ public class Expression implements Cloneable
int seriously = i;
c.setVariable("_", (cc, tt) -> next);
c.setVariable("_i", (cc, tt) -> new NumericValue(seriously).bindTo("_i"));
- if(!expr.evalValue(c).getBoolean())
+ if(!expr.evalValue(c, Context.BOOLEAN).getBoolean())
{
result = LazyValue.FALSE;
next.boundVariable = var;
@@ -1983,9 +1984,10 @@ public class Expression implements Cloneable
int seriously = i;
c.setVariable("_", (cc, tt) -> next);
c.setVariable("_i", (cc, tt) -> new NumericValue(seriously).bindTo("_i"));
- if(expr.evalValue(c).getBoolean())
+ Value result = expr.evalValue(c, t);
+ if(t != Context.VOID && result.getBoolean())
successCount++;
- if (cond != null && cond.evalValue(c).getBoolean())
+ if (cond != null && cond.evalValue(c, Context.BOOLEAN).getBoolean())
{
next.boundVariable = var;
break;
@@ -2033,7 +2035,7 @@ public class Expression implements Cloneable
Value promiseWontChangeYou = acc;
c.setVariable("_a", (cc, tt) -> promiseWontChangeYou.bindTo("_a"));
c.setVariable("_", (cc, tt) -> next);
- acc = expr.evalValue(c);
+ acc = expr.evalValue(c, t);
next.boundVariable = var;
}
//reverting scope
diff --git a/src/main/java/carpet/script/LazyValue.java b/src/main/java/carpet/script/LazyValue.java
index 8a7d8f43..1cfb32a3 100644
--- a/src/main/java/carpet/script/LazyValue.java
+++ b/src/main/java/carpet/script/LazyValue.java
@@ -19,6 +19,6 @@ public interface LazyValue
Value evalValue(Context c, Integer type);
default Value evalValue(Context c){
- return evalValue(c, 0);
+ return evalValue(c, Context.NONE);
}
}
diff --git a/src/main/java/carpet/script/value/BlockValue.java b/src/main/java/carpet/script/value/BlockValue.java
index 6c32aebc..5a193f41 100644
--- a/src/main/java/carpet/script/value/BlockValue.java
+++ b/src/main/java/carpet/script/value/BlockValue.java
@@ -144,8 +144,6 @@ public class BlockValue extends Value
}
if (v1 instanceof BlockValue)
{
- ((BlockValue) v1).getBlockState();
- ((BlockValue) v1).getData();
return new LocatorResult(((BlockValue) v1), 1+offset);
}
if (v1 instanceof ListValue)
@@ -256,7 +254,7 @@ public class BlockValue extends Value
@Override
public Value clone()
{
- return new BlockValue(blockState, world, pos);
+ return new BlockValue(blockState, world, pos, data);
}
@Override
diff --git a/src/main/java/carpet/script/value/Value.java b/src/main/java/carpet/script/value/Value.java
index 4b529c6a..8faf4c15 100644
--- a/src/main/java/carpet/script/value/Value.java
+++ b/src/main/java/carpet/script/value/Value.java
@@ -48,6 +48,7 @@ public abstract class Value implements Comparable, Cloneable
{
// should not happen
e.printStackTrace();
+ throw new InternalExpressionException("Variable of type "+getTypeString()+" is not cloneable. Tell gnembon about it, this shoudn't happen");
}
copy.boundVariable = var;
return copy;