mirror of
https://github.com/plexusorg/Plex-FAWE.git
synced 2024-12-23 09:47:38 +00:00
Improve CachedMask a bit - no need to unwrap/wrap blockvectors, allow extents to be parsed
(cherry picked from commit 41c0ea98f16ecbfadced41e4be277ad6ceda6b1a)
This commit is contained in:
parent
f5d6d4079a
commit
b6b6ba7265
@ -40,17 +40,17 @@ public class AdjacentAnyMask extends AbstractMask implements ResettableMask {
|
|||||||
int x = v.getBlockX();
|
int x = v.getBlockX();
|
||||||
int y = v.getBlockY();
|
int y = v.getBlockY();
|
||||||
int z = v.getBlockZ();
|
int z = v.getBlockZ();
|
||||||
if (mask.test(x + 1, y, z)) {
|
if (mask.test(mutable.setComponents(x + 1, y, z))) {
|
||||||
return mutable.setComponents(1, 0, 0);
|
return mutable.setComponents(1, 0, 0);
|
||||||
} else if (mask.test(x - 1, y, z)) {
|
} else if (mask.test(mutable.setComponents(x - 1, y, z))) {
|
||||||
return mutable.setComponents(-1, 0, 0);
|
return mutable.setComponents(-1, 0, 0);
|
||||||
} else if (mask.test(x, y, z + 1)) {
|
} else if (mask.test(mutable.setComponents(x, y, z + 1))) {
|
||||||
return mutable.setComponents(0, 0, 1);
|
return mutable.setComponents(0, 0, 1);
|
||||||
} else if (mask.test(x, y, z - 1)) {
|
} else if (mask.test(mutable.setComponents(x, y, z - 1))) {
|
||||||
return mutable.setComponents(0, 0, -1);
|
return mutable.setComponents(0, 0, -1);
|
||||||
} else if (y < maxY && mask.test(x, y + 1, z)) {
|
} else if (y < maxY && mask.test(mutable.setComponents(x, y + 1, z))) {
|
||||||
return mutable.setComponents(0, 1, 0);
|
return mutable.setComponents(0, 1, 0);
|
||||||
} else if (y > minY && mask.test(x, y - 1, z)) {
|
} else if (y > minY && mask.test(mutable.setComponents(x, y - 1, z))) {
|
||||||
return mutable.setComponents(0, -1, 0);
|
return mutable.setComponents(0, -1, 0);
|
||||||
} else {
|
} else {
|
||||||
return null;
|
return null;
|
||||||
|
@ -1,6 +1,8 @@
|
|||||||
package com.fastasyncworldedit.core.function.mask;
|
package com.fastasyncworldedit.core.function.mask;
|
||||||
|
|
||||||
|
import com.fastasyncworldedit.core.math.MutableBlockVector3;
|
||||||
import com.sk89q.worldedit.extent.Extent;
|
import com.sk89q.worldedit.extent.Extent;
|
||||||
|
import com.sk89q.worldedit.function.mask.AbstractExtentMask;
|
||||||
import com.sk89q.worldedit.function.mask.Mask;
|
import com.sk89q.worldedit.function.mask.Mask;
|
||||||
import com.sk89q.worldedit.function.mask.SolidBlockMask;
|
import com.sk89q.worldedit.function.mask.SolidBlockMask;
|
||||||
import com.sk89q.worldedit.math.BlockVector3;
|
import com.sk89q.worldedit.math.BlockVector3;
|
||||||
@ -9,8 +11,8 @@ import java.util.Arrays;
|
|||||||
|
|
||||||
public class AngleMask extends SolidBlockMask implements ResettableMask {
|
public class AngleMask extends SolidBlockMask implements ResettableMask {
|
||||||
|
|
||||||
public static double ADJACENT_MOD = 0.5;
|
protected static double ADJACENT_MOD = 0.5;
|
||||||
public static double DIAGONAL_MOD = 1 / Math.sqrt(8);
|
protected static double DIAGONAL_MOD = 1 / Math.sqrt(8);
|
||||||
|
|
||||||
protected final CachedMask mask;
|
protected final CachedMask mask;
|
||||||
protected final double max;
|
protected final double max;
|
||||||
@ -20,6 +22,13 @@ public class AngleMask extends SolidBlockMask implements ResettableMask {
|
|||||||
protected final int maxY;
|
protected final int maxY;
|
||||||
protected final int minY;
|
protected final int minY;
|
||||||
protected final int distance;
|
protected final int distance;
|
||||||
|
protected transient int cacheBotX = Integer.MIN_VALUE;
|
||||||
|
protected transient int cacheBotZ = Integer.MIN_VALUE;
|
||||||
|
protected transient byte[] cacheHeights;
|
||||||
|
protected transient int lastY;
|
||||||
|
protected transient int lastX = Integer.MIN_VALUE;
|
||||||
|
protected transient int lastZ = Integer.MIN_VALUE;
|
||||||
|
protected transient boolean lastValue;
|
||||||
|
|
||||||
public AngleMask(Extent extent, double min, double max, boolean overlay, int distance) {
|
public AngleMask(Extent extent, double min, double max, boolean overlay, int distance) {
|
||||||
super(extent);
|
super(extent);
|
||||||
@ -39,26 +48,13 @@ public class AngleMask extends SolidBlockMask implements ResettableMask {
|
|||||||
cacheBotZ = Integer.MIN_VALUE;
|
cacheBotZ = Integer.MIN_VALUE;
|
||||||
lastX = Integer.MIN_VALUE;
|
lastX = Integer.MIN_VALUE;
|
||||||
lastY = Integer.MIN_VALUE;
|
lastY = Integer.MIN_VALUE;
|
||||||
|
lastZ = Integer.MIN_VALUE;
|
||||||
if (cacheHeights != null) {
|
if (cacheHeights != null) {
|
||||||
Arrays.fill(cacheHeights, (byte) 0);
|
Arrays.fill(cacheHeights, (byte) 0);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
protected transient int cacheCenZ;
|
protected int getHeight(Extent extent, int x, int y, int z) {
|
||||||
protected transient int cacheBotX = Integer.MIN_VALUE;
|
|
||||||
protected transient int cacheBotZ = Integer.MIN_VALUE;
|
|
||||||
protected transient int cacheCenterZ;
|
|
||||||
|
|
||||||
protected transient byte[] cacheHeights;
|
|
||||||
|
|
||||||
protected transient int lastY;
|
|
||||||
protected transient int lastX = Integer.MIN_VALUE;
|
|
||||||
protected transient int lastZ = Integer.MIN_VALUE;
|
|
||||||
protected transient boolean foundY;
|
|
||||||
protected transient boolean lastValue;
|
|
||||||
|
|
||||||
public int getHeight(Extent extent, int x, int y, int z) {
|
|
||||||
// return extent.getNearestSurfaceTerrainBlock(x, z, y, 0, maxY);
|
|
||||||
int rx = x - cacheBotX + 16;
|
int rx = x - cacheBotX + 16;
|
||||||
int rz = z - cacheBotZ + 16;
|
int rz = z - cacheBotZ + 16;
|
||||||
int index;
|
int index;
|
||||||
@ -85,7 +81,6 @@ public class AngleMask extends SolidBlockMask implements ResettableMask {
|
|||||||
|
|
||||||
protected boolean testSlope(Extent extent, int x, int y, int z) {
|
protected boolean testSlope(Extent extent, int x, int y, int z) {
|
||||||
double slope;
|
double slope;
|
||||||
boolean aboveMin;
|
|
||||||
lastY = y;
|
lastY = y;
|
||||||
slope =
|
slope =
|
||||||
Math.abs(getHeight(extent, x + distance, y, z) - getHeight(extent, x - distance, y, z))
|
Math.abs(getHeight(extent, x + distance, y, z) - getHeight(extent, x - distance, y, z))
|
||||||
@ -122,26 +117,26 @@ public class AngleMask extends SolidBlockMask implements ResettableMask {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean adjacentAir(BlockVector3 v) {
|
private boolean adjacentAir(Extent extent, MutableBlockVector3 mutable) {
|
||||||
int x = v.getBlockX();
|
int x = mutable.getBlockX();
|
||||||
int y = v.getBlockY();
|
int y = mutable.getBlockY();
|
||||||
int z = v.getBlockZ();
|
int z = mutable.getBlockZ();
|
||||||
if (!mask.test(x + 1, y, z)) {
|
if (!mask.test(extent, mutable.setComponents(x + 1, y, z))) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
if (!mask.test(x - 1, y, z)) {
|
if (!mask.test(extent, mutable.setComponents(x - 1, y, z))) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
if (!mask.test(x, y, z + 1)) {
|
if (!mask.test(extent, mutable.setComponents(x, y, z + 1))) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
if (!mask.test(x, y, z - 1)) {
|
if (!mask.test(extent, mutable.setComponents(x, y, z - 1))) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
if (y < maxY && !mask.test(x, y + 1, z)) {
|
if (y != maxY && !mask.test(extent, mutable.setComponents(x, y + 1, z))) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
return y > minY && !mask.test(x, y - 1, z);
|
return y != minY && !mask.test(extent, mutable.setComponents(x, y - 1, z));
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -151,21 +146,23 @@ public class AngleMask extends SolidBlockMask implements ResettableMask {
|
|||||||
int z = vector.getBlockZ();
|
int z = vector.getBlockZ();
|
||||||
|
|
||||||
if ((lastX == (lastX = x) & lastZ == (lastZ = z))) {
|
if ((lastX == (lastX = x) & lastZ == (lastZ = z))) {
|
||||||
int height = getHeight(getExtent(), x, y, z);
|
int height = getHeight(extent, x, y, z);
|
||||||
if (y <= height) {
|
if (y <= height) {
|
||||||
return overlay ? (lastValue && y == height) : lastValue;
|
return overlay ? (lastValue && y == height) : lastValue;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!mask.test(x, y, z)) {
|
MutableBlockVector3 mutable = new MutableBlockVector3(x, y, z);
|
||||||
|
|
||||||
|
if (!mask.test(extent, mutable)) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
if (overlay) {
|
if (overlay) {
|
||||||
if (y < maxY && !adjacentAir(vector)) {
|
if (y < maxY && !adjacentAir(extent, mutable)) {
|
||||||
return lastValue = false;
|
return lastValue = false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return testSlope(getExtent(), x, y, z);
|
return testSlope(extent, x, y, z);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -1,20 +1,22 @@
|
|||||||
package com.fastasyncworldedit.core.function.mask;
|
package com.fastasyncworldedit.core.function.mask;
|
||||||
|
|
||||||
import com.fastasyncworldedit.core.math.LocalBlockVectorSet;
|
import com.fastasyncworldedit.core.math.LocalBlockVectorSet;
|
||||||
import com.fastasyncworldedit.core.math.MutableBlockVector3;
|
import com.sk89q.worldedit.extent.Extent;
|
||||||
|
import com.sk89q.worldedit.function.mask.AbstractExtentMask;
|
||||||
import com.sk89q.worldedit.function.mask.Mask;
|
import com.sk89q.worldedit.function.mask.Mask;
|
||||||
import com.sk89q.worldedit.math.BlockVector3;
|
import com.sk89q.worldedit.math.BlockVector3;
|
||||||
|
|
||||||
|
import javax.annotation.Nullable;
|
||||||
|
|
||||||
public class CachedMask extends AbstractDelegateMask implements ResettableMask {
|
public class CachedMask extends AbstractDelegateMask implements ResettableMask {
|
||||||
|
|
||||||
private transient MutableBlockVector3 mutable = new MutableBlockVector3();
|
private final boolean hasExtent;
|
||||||
private transient LocalBlockVectorSet cache_checked = new LocalBlockVectorSet();
|
private transient LocalBlockVectorSet cache_checked = new LocalBlockVectorSet();
|
||||||
private transient LocalBlockVectorSet cache_results = new LocalBlockVectorSet();
|
private transient LocalBlockVectorSet cache_results = new LocalBlockVectorSet();
|
||||||
|
|
||||||
public CachedMask(Mask mask) {
|
public CachedMask(Mask mask) {
|
||||||
super(mask);
|
super(mask);
|
||||||
cache_checked.setOffset(Integer.MIN_VALUE, Integer.MIN_VALUE);
|
hasExtent = mask instanceof AbstractExtentMask;
|
||||||
cache_results.setOffset(Integer.MIN_VALUE, Integer.MIN_VALUE);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static CachedMask cache(Mask mask) {
|
public static CachedMask cache(Mask mask) {
|
||||||
@ -26,7 +28,6 @@ public class CachedMask extends AbstractDelegateMask implements ResettableMask {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void reset() {
|
public void reset() {
|
||||||
mutable = new MutableBlockVector3();
|
|
||||||
cache_checked = new LocalBlockVectorSet();
|
cache_checked = new LocalBlockVectorSet();
|
||||||
cache_results = new LocalBlockVectorSet();
|
cache_results = new LocalBlockVectorSet();
|
||||||
resetCache();
|
resetCache();
|
||||||
@ -35,35 +36,55 @@ public class CachedMask extends AbstractDelegateMask implements ResettableMask {
|
|||||||
private void resetCache() {
|
private void resetCache() {
|
||||||
cache_checked.clear();
|
cache_checked.clear();
|
||||||
cache_results.clear();
|
cache_results.clear();
|
||||||
cache_checked.setOffset(Integer.MIN_VALUE, Integer.MIN_VALUE);
|
|
||||||
cache_results.setOffset(Integer.MIN_VALUE, Integer.MIN_VALUE);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean test(BlockVector3 vector) {
|
public boolean test(BlockVector3 vector) {
|
||||||
return test(vector.getBlockX(), vector.getBlockY(), vector.getBlockZ());
|
int x = vector.getX();
|
||||||
}
|
int y = vector.getY();
|
||||||
|
int z = vector.getZ();
|
||||||
public boolean test(int x, int y, int z) {
|
|
||||||
try {
|
try {
|
||||||
boolean check = cache_checked.add(x, y, z);
|
boolean check = cache_checked.add(x, y, z);
|
||||||
if (!check) {
|
if (!check) {
|
||||||
return cache_results.contains(x, y, z);
|
return cache_results.contains(x, y, z);
|
||||||
}
|
}
|
||||||
boolean result = getMask().test(mutable.setComponents(x, y, z));
|
boolean result = getMask().test(vector);
|
||||||
if (result) {
|
if (result) {
|
||||||
cache_results.add(x, y, z);
|
cache_results.add(x, y, z);
|
||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
} catch (UnsupportedOperationException ignored) {
|
} catch (UnsupportedOperationException ignored) {
|
||||||
boolean result = getMask().test(mutable.setComponents(x, y, z));
|
boolean result = getMask().test(vector);
|
||||||
// Assume that the mask won't be given y outside the world range
|
resetCache();
|
||||||
// if (y < 0 || y > 255) {
|
cache_checked.add(x, y, z);
|
||||||
// return result;
|
if (result) {
|
||||||
//}
|
cache_results.add(x, y, z);
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean test(@Nullable Extent extent, BlockVector3 vector) {
|
||||||
|
if (!hasExtent || !(extent instanceof AbstractExtentMask)) {
|
||||||
|
return test(vector);
|
||||||
|
}
|
||||||
|
int x = vector.getX();
|
||||||
|
int y = vector.getY();
|
||||||
|
int z = vector.getZ();
|
||||||
|
AbstractExtentMask mask = (AbstractExtentMask) getMask();
|
||||||
|
try {
|
||||||
|
boolean check = cache_checked.add(x, y, z);
|
||||||
|
if (!check) {
|
||||||
|
return cache_results.contains(x, y, z);
|
||||||
|
}
|
||||||
|
boolean result = mask.test(extent, vector);
|
||||||
|
if (result) {
|
||||||
|
cache_results.add(x, y, z);
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
} catch (UnsupportedOperationException ignored) {
|
||||||
|
boolean result = mask.test(extent, vector);
|
||||||
resetCache();
|
resetCache();
|
||||||
cache_checked.setOffset(x, z);
|
|
||||||
cache_results.setOffset(x, z);
|
|
||||||
cache_checked.add(x, y, z);
|
cache_checked.add(x, y, z);
|
||||||
if (result) {
|
if (result) {
|
||||||
cache_results.add(x, y, z);
|
cache_results.add(x, y, z);
|
||||||
|
@ -21,7 +21,7 @@ public class SurfaceMask extends AdjacentAnyMask {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean test(BlockVector3 v) {
|
public boolean test(BlockVector3 v) {
|
||||||
return !getParentMask().test(v.getBlockX(), v.getBlockY(), v.getBlockZ()) && super.test(v);
|
return !getParentMask().test(v) && super.test(v);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
Loading…
Reference in New Issue
Block a user