AStarBase class

Пакет: com.hypixel.hytale.server.npc.navigation

Файл: com/hypixel/hytale/server/npc/navigation/AStarBase.java

Поля (100)

МодификаторыТипИмя
final HytaleLogger LOGGER
UNSTARTED, ABORTED, COMPUTING, ACCOMPLISHED, TERMINATED, TERMINATED_OPEN_NODE_LIMIT_EXCEEDED, TERMINATED_TOTAL_NODE_LIMIT_EXCEEDED
break
break
AStarNode var1
AStarNode var1
long var10
int var10
float var10
int var10
var10
long var11
long var12
double var12
long var13
long var14
double var14
long var16
double var16
long var18
double var18
double var2
long var2
int var2
double var20
long var20
Vector3d var22
AStarNode var22
int var23
int var23
int var24
var24
Vector3d var25
long var26
Vector3d var28
var28
AStarNode var28
AStarNode var29
int var3
Vector3d var30
Vector3d var30
Vector3d var31
double var32
double var34
AStarNode var4
ObjectIterator var4
double var4
long var4
int var4
long var4
int var4
Vector3d var42
var42
var42
double var47
float var5
var5
AStarNode var5
ObjectIterator var5
float var5
float var5
float var5
AStarNode var5
var5
Vector3d var51
double var53
int var54
double var56
double var58
int var6
AStarNode var6
var6
float var6
var6
double var6
float var6
long var6
float var6
long var6
AStarNode var7
AStarNode var7
AStarNode var7
var7
AStarNode var7
AStarNode var7
var7
long var8
Vector3d var8
float var8
AStarNode var8
int var8
AStarNode var8
AStarNode var8
var8
AStarNode[] var9
float var9
AStarNode var9
float var9
int var9
long var9

Методы (87)

МодификаторыВозвратСигнатура
abstract return new AStarDebugBasereturn new AStarDebugBase(this, var1)
abstract throw new IllegalStateExceptionthrow new IllegalStateException("Can't find inverse search direction")
abstract throw new IllegalStateExceptionthrow new IllegalStateException("Can't find correct number of normals")
Progress Progress()
private boolean abandonCyclicPathboolean abandonCyclicPath(@Nonnull AStarNode var1, int var2)
protected long addOffsetToIndexlong addOffsetToIndex(long var1, long var3, long var5, long var7)
protected void addOpenNodevoid addOpenNode(@Nonnull AStarNode var1, int var2, @Nonnull Vector3d var3, long var4, float var6, MotionController var7)
protected void addOpenNodevoid addOpenNode(@Nonnull AStarNode var1, long var2)
protected void addOrUpdateNodevoid addOrUpdateNode(@Nonnull AStarNode var1, int var2, @Nonnull Vector3d var3, @Nonnull MotionController var4, @Nonnull ComponentAccessor<EntityStore> var5)
protected void addStartNodevoid addStartNode(Vector3d var1, @Nonnull Vector3d var2, @Nonnull MotionController var3)
public float buildFurthestPathfloat buildFurthestPath()
public float buildLongestPathfloat buildLongestPath()
protected boolean buildPathboolean buildPath(@Nullable AStarNode var1)
public void clearPathvoid clearPath()
public AStarBase.Progress computePathAStarBase.Progress computePath(@Nonnull Ref<EntityStore> var1, @Nonnull MotionController var2, @Nonnull ProbeMoveData var3, int var4, @Nonnull ComponentAccessor<EntityStore> var5)
for for(double var25 = -1.0; var25 <= 1.0; var25++)
for for(double var27 = -1.0; var27 <= 1.0; var27++)
for for(double var29 = -1.0; var29 <= 1.0; var29++)
for for(int var48 = 0; var48 < this.inverseSearchDirections.length; var48++)
for for(int var49 = 0; var49 < this.searchDirections.length - 1; var49++)
for for(int var26 = var49 + 1; var26 < this.searchDirections.length; var26++)
for for(int var50 = 0; var50 < this.searchDirections.length; var50++)
for for(int var57 = 0; var57 < this.searchDirections.length; var57++)
for for(double var46 = this.projectedX ? 0.0 : 0.5; var46 >= 0.0; var46 -= 0.5)
for for(double var52 = this.projectedY ? 0.0 : 0.5; var52 >= 0.0; var52 -= 0.5)
for for(double var55 = this.projectedZ ? 0.0 : 0.5; var55 >= 0.0; var55 -= 0.5)
for for(double var36 = var47; var36 <= var53; var36 += 0.5)
for for(double var38 = var56; var38 <= var58; var38 += 0.5)
for for(double var40 = var32; var40 <= var34; var40 += 0.5)
for for(int var11 = 0; var11 < var10; var11++)
for for(int var24 = var23; var24 < var23 + this.normalsPerDirection; var24++)
public AStarEvaluator getEvaluatorAStarEvaluator getEvaluator()
public int getIterationsint getIterations()
public int getLengthint getLength()
public int getOpenCountint getOpenCount()
public AStarBase.Progress getProgressAStarBase.Progress getProgress()
public long getStartPositionIndexlong getStartPositionIndex()
if if(!this.projectedX || var25 == 0.0)
if if(!this.projectedY || var27 == 0.0)
if if(this.inverseSearchDirections[var49] == -1)
if if(this.inverseSearchDirections[var49] == -1)
if if(this.is2D)
if if(var24 == var54)
if if(var24 != var54)
if if(var42 != null)
if if(var42 != null)
if if(var42 != null)
if if(this.progress != AStarBase.Progress.COMPUTING)
if if(var9[var11] == null)
if if(var20 != -1L)
if if(var22 != null)
if if(this.is2D)
if if(var28 != null)
if if(var29 != null)
if if(this.path != null)
if if(var4 == null)
if if(this.path != null)
if if(var5 == null)
if if(var6 != -1L && var6 != var1.positionIndex)
if if(var8 == null)
if if(var6 < 0.0F)
if if(var1 == null)
if if(this.optimizedBuildPath)
if if(++var3 > var2)
if if(++var3 > var2)
static long indexFromXYZlong indexFromXYZ(long var0, long var2, long var4)
abstract return indexFromXYZreturn indexFromXYZ(var2, var4, var6)
abstract return indexFromXYZreturn indexFromXYZ(var9, var11, var13)
public AStarBase.Progress initComputePathAStarBase.Progress initComputePath(@Nonnull Ref<EntityStore> var1, @Nonnull Vector3d var2, AStarEvaluator var3, @Nonnull MotionController var4, @Nonnull ProbeMoveData var5, @Nonnull AStarNodePoolProvider var6, @Nonnull ComponentAccessor<EntityStore> var7)
public boolean isComputingboolean isComputing()
protected float measureWalkCostfloat measureWalkCost(Vector3d var1, Vector3d var2, @Nonnull MotionController var3)
protected long positionToIndexlong positionToIndex(@Nonnull Vector3d var1)
public void setCanMoveDiagonalvoid setCanMoveDiagonal(boolean var1)
public void setMaxPathLengthvoid setMaxPathLength(int var1)
public void setOpenNodesLimitvoid setOpenNodesLimit(int var1)
public void setOptimizedBuildPathvoid setOptimizedBuildPath(boolean var1)
protected AStarBase.Progress setProgressAStarBase.Progress setProgress(AStarBase.Progress var1)
public void setStartPositionvoid setStartPosition(@Nonnull Vector3d var1)
public void setTotalNodesLimitvoid setTotalNodesLimit(int var1)
protected void updateNodevoid updateNode(@Nonnull AStarNode var1, int var2, @Nonnull AStarNode var3, @Nonnull MotionController var4)
protected void updateNodeCostvoid updateNodeCost(@Nonnull AStarNode var1, int var2, @Nonnull AStarNode var3, float var4)
while while(var8 != null)
static int xFromIndexint xFromIndex(long var0)
static int yFromIndexint yFromIndex(long var0)
static int zFromIndexint zFromIndex(long var0)
abstract return zFromIndexreturn zFromIndex(var0 >> 11)
abstract return zFromIndexreturn zFromIndex(var0 >> 22)

Исходный код

Показать/скрыть
class="kw">package com.hypixel.hytale.server.npc.navigation;

class="kw">import com.hypixel.hytale.component.ComponentAccessor;
class="kw">import com.hypixel.hytale.component.Ref;
class="kw">import com.hypixel.hytale.function.function.BiToFloatFunction;
class="kw">import com.hypixel.hytale.function.function.ToFloatFunction;
class="kw">import com.hypixel.hytale.function.predicate.BiFloatPredicate;
class="kw">import com.hypixel.hytale.logger.HytaleLogger;
class="kw">import com.hypixel.hytale.math.util.MathUtil;
class="kw">import com.hypixel.hytale.server.core.universe.world.storage.EntityStore;
class="kw">import com.hypixel.hytale.server.npc.movement.constraints.RelaxedConstraint;
class="kw">import com.hypixel.hytale.server.npc.movement.controllers.MotionController;
class="kw">import com.hypixel.hytale.server.npc.movement.controllers.ProbeMoveData;
class="kw">import it.unimi.dsi.fastutil.longs.Long2ObjectMap;
class="kw">import it.unimi.dsi.fastutil.longs.Long2ObjectMaps;
class="kw">import it.unimi.dsi.fastutil.longs.Long2ObjectOpenHashMap;
class="kw">import it.unimi.dsi.fastutil.longs.Long2ObjectMap.Entry;
class="kw">import it.unimi.dsi.fastutil.objects.ObjectArrayList;
class="kw">import it.unimi.dsi.fastutil.objects.ObjectIterator;
class="kw">import java.util.EnumSet;
class="kw">import java.util.List;
class="kw">import java.util.concurrent.TimeUnit;
class="kw">import java.util.logging.Level;
class="kw">import javax.annotation.Nonnull;
class="kw">import javax.annotation.Nullable;
class="kw">import org.joml.Vector3d;

class="kw">public class AStarBase {
   class="kw">private class="kw">static class="kw">final HytaleLogger LOGGER = HytaleLogger.forEnclosingClass();
   class="kw">public class="kw">static class="kw">final double FULL_STEP_THRESHOLD = 0.9999999;
   class="kw">public class="kw">static class="kw">final double REQUIRED_TARGET_DISTANCE = 9.999999994736442E-8;
   class="kw">public class="kw">static class="kw">final double HALF_STEP_THRESHOLD = 0.49999995;
   class="kw">public class="kw">static class="kw">final double ON_GRID_THRESHOLD = 0.01;
   class="kw">protected class="kw">static class="kw">final int INDEX_FRACTIONAL_BITS = 1;
   class="kw">protected class="kw">static class="kw">final int POSITION_BITS = 11;
   class="kw">protected class="kw">static class="kw">final int POSITION_OFFSET = 1024;
   class="kw">protected class="kw">static class="kw">final int POSITION_MASK = 2047;
   class="kw">protected int maxPathLength = 200;
   class="kw">protected int openNodesLimit = 80;
   class="kw">protected int totalNodesLimit = 400;
   class="kw">protected boolean canMoveDiagonal = true;
   class="kw">protected boolean optimizedBuildPath = true;
   class="kw">protected EnumSet<RelaxedConstraint> relaxedConstraints = EnumSet.noneOf(RelaxedConstraint.class);
   class="kw">protected class="kw">final Vector3d startPosition = new Vector3d();
   class="kw">protected AStarEvaluator evaluator;
   class="kw">protected double positionToIndexOffsetX;
   class="kw">protected double positionToIndexOffsetY;
   class="kw">protected double positionToIndexOffsetZ;
   class="kw">protected long indexToPositionOffsetX;
   class="kw">protected long indexToPositionOffsetY;
   class="kw">protected long indexToPositionOffsetZ;
   class="kw">protected long startPositionIndex;
   class="kw">protected boolean is2D;
   class="kw">protected boolean projectedX;
   class="kw">protected boolean projectedY;
   class="kw">protected boolean projectedZ;
   class="kw">protected class="kw">final Vector3d searchDirectionsWorldNormal = new Vector3d();
   class="kw">protected boolean searchDirectionIsDiagonalMoves;
   class="kw">protected boolean searchDirectionIs2D;
   class="kw">protected Vector3d[] searchDirections;
   class="kw">protected double[] searchDirectionDistances;
   class="kw">protected int[] inverseSearchDirections;
   class="kw">protected int normalsPerDirection;
   class="kw">protected int[] normalDirections;
   class="kw">protected AStarNodePool nodePool;
   class="kw">protected class="kw">final List<AStarNode> openNodes = new ObjectArrayList();
   class="kw">protected class="kw">final Long2ObjectMap<AStarNode> visitedBlocks = new Long2ObjectOpenHashMap();
   class="kw">protected int iterations;
   @Nullable
   class="kw">protected AStarNode path;
   class="kw">protected AStarBase.Progress progress;
   class="kw">protected class="kw">final Vector3d pathEnd = new Vector3d();
   class="kw">protected class="kw">final Vector3d tempPositionVector = new Vector3d();
   class="kw">protected class="kw">final Vector3d tempDirectionVector = new Vector3d();

   class="kw">public AStarBase() {
   }

   class="kw">public void setCanMoveDiagonal(boolean var1) {
      this.canMoveDiagonal = var1;
   }

   class="kw">public void setMaxPathLength(int var1) {
      this.maxPathLength = var1;
   }

   class="kw">public void setOpenNodesLimit(int var1) {
      this.openNodesLimit = var1;
   }

   class="kw">public void setTotalNodesLimit(int var1) {
      this.totalNodesLimit = var1;
   }

   class="kw">public void setStartPosition(@Nonnull Vector3d var1) {
      this.startPosition.set(var1);
   }

   @Nonnull
   class="kw">public Vector3d getStartPosition() {
      class="kw">return this.startPosition;
   }

   class="kw">public void setOptimizedBuildPath(boolean var1) {
      this.optimizedBuildPath = var1;
   }

   class="kw">public AStarEvaluator getEvaluator() {
      class="kw">return this.evaluator;
   }

   @Nonnull
   class="kw">public List<AStarNode> getOpenNodes() {
      class="kw">return this.openNodes;
   }

   class="kw">public int getOpenCount() {
      class="kw">return this.openNodes.size();
   }

   @Nonnull
   class="kw">public Long2ObjectMap<AStarNode> getVisitedBlocks() {
      class="kw">return this.visitedBlocks;
   }

   class="kw">public long getStartPositionIndex() {
      class="kw">return this.startPositionIndex;
   }

   @Nullable
   class="kw">public AStarNode getPath() {
      class="kw">return this.path;
   }

   @Nullable
   class="kw">public Vector3d getPosition() {
      class="kw">return this.path != null ? this.path.getPosition() : null;
   }

   class="kw">public int getLength() {
      class="kw">return this.path != null ? this.path.getLength() : 0;
   }

   class="kw">public int getIterations() {
      class="kw">return this.iterations;
   }

   @Nullable
   class="kw">public Vector3d getEndPosition() {
      class="kw">return this.path != null ? this.pathEnd : null;
   }

   class="kw">public void clearPath() {
      this.path = null;
      if (!this.visitedBlocks.isEmpty()) {
         Long2ObjectMaps.fastForEach(this.visitedBlocks, var1 -> this.nodePool.deallocate((AStarNode)var1.getValue()));
         this.visitedBlocks.clear();
      }

      this.openNodes.clear();
      this.setProgress(AStarBase.Progress.UNSTARTED);
   }

   class="kw">public AStarBase.Progress initComputePath(
      @Nonnull Ref<EntityStore> var1,
      @Nonnull Vector3d var2,
      AStarEvaluator var3,
      @Nonnull MotionController var4,
      @Nonnull ProbeMoveData var5,
      @Nonnull AStarNodePoolProvider var6,
      @Nonnull ComponentAccessor<EntityStore> var7
   ) {
      this.clearPath();
      this.iterations = 0;
      this.evaluator = var3;
      this.startPosition.set(var2);
      this.relaxedConstraints.clear();
      this.relaxedConstraints.addAll(var5.getRelaxedConstraints());
      long var8 = MathUtil.fastFloor(this.startPosition.x);
      long var10 = MathUtil.fastFloor(this.startPosition.y);
      long var12 = MathUtil.fastFloor(this.startPosition.z);
      long var14 = 2L * var8;
      long var16 = 2L * var10;
      long var18 = 2L * var12;
      double var20 = -1023.25;
      this.positionToIndexOffsetX = var14 + var20;
      this.positionToIndexOffsetY = var16 + var20;
      this.positionToIndexOffsetZ = var18 + var20;
      this.indexToPositionOffsetX = var14 + 1L - 1024L;
      this.indexToPositionOffsetY = var16 + 1L - 1024L;
      this.indexToPositionOffsetZ = var18 + 1L - 1024L;
      this.startPositionIndex = this.positionToIndex(this.startPosition);
      Vector3d var22 = var4.getComponentSelector();
      this.is2D = var4.is2D();
      this.projectedX = this.is2D && var22.x == 0.0;
      this.projectedY = this.is2D && var22.y == 0.0;
      this.projectedZ = this.is2D && var22.z == 0.0;
      if (this.searchDirections == null
         || this.searchDirectionIs2D != this.is2D
         || this.searchDirectionIsDiagonalMoves != this.canMoveDiagonal
         || !this.searchDirectionsWorldNormal.equals(var4.getWorldNormal())) {
         this.searchDirectionIsDiagonalMoves = this.canMoveDiagonal;
         this.searchDirectionIs2D = this.is2D;
         this.searchDirectionsWorldNormal.set(var4.getWorldNormal());
         int var23 = this.is2D ? (this.canMoveDiagonal ? 8 : 4) : (this.canMoveDiagonal ? 26 : 6);
         this.searchDirections = new Vector3d[var23];
         this.searchDirectionDistances = new double[var23];
         int var24 = 0;

         for (double var25 = -1.0; var25 <= 1.0; var25++) {
            if (!this.projectedX || var25 == 0.0) {
               for (double var27 = -1.0; var27 <= 1.0; var27++) {
                  if (!this.projectedY || var27 == 0.0) {
                     for (double var29 = -1.0; var29 <= 1.0; var29++) {
                        if ((!this.projectedZ || var29 == 0.0) && (var25 != 0.0 || var27 != 0.0 || var29 != 0.0)) {
                           Vector3d var31 = new Vector3d(var25, var27, var29);
                           this.searchDirections[var24] = var31;
                           this.searchDirectionDistances[var24] = var31.length();
                           var24++;
                        }
                     }
                  }
               }
            }
         }

         this.inverseSearchDirections = new int[var23];

         for (int var48 = 0; var48 < this.inverseSearchDirections.length; var48++) {
            this.inverseSearchDirections[var48] = -1;
         }

         for (int var49 = 0; var49 < this.searchDirections.length - 1; var49++) {
            if (this.inverseSearchDirections[var49] == -1) {
               this.tempDirectionVector.set(this.searchDirections[var49]).negate();

               for (int var26 = var49 + 1; var26 < this.searchDirections.length; var26++) {
                  if (this.searchDirections[var26].equals(this.tempDirectionVector, 0.0)) {
                     this.inverseSearchDirections[var49] = var26;
                     this.inverseSearchDirections[var26] = var49;
                     break;
                  }
               }

               if (this.inverseSearchDirections[var49] == -1) {
                  throw new IllegalStateException("Can't find inverse search direction");
               }
            }
         }

         if (this.is2D) {
            this.normalsPerDirection = 1;
            this.normalDirections = new int[this.normalsPerDirection * var23];
            var24 = 0;

            for (int var50 = 0; var50 < this.searchDirections.length; var50++) {
               Vector3d var51 = this.searchDirections[var50];
               int var54 = var24 + this.normalsPerDirection;
               Vector3d var28 = null;

               for (int var57 = 0; var57 < this.searchDirections.length; var57++) {
                  Vector3d var30 = this.searchDirections[var57];
                  if (var50 != var57 && var51.dot(var30) == 0.0 && (var28 == null || var28.dot(var30) == 0.0)) {
                     this.normalDirections[var24++] = var57;
                     if (var24 == var54) {
                        break;
                     }

                     var28 = var30;
                  }
               }

               if (var24 != var54) {
                  throw new IllegalStateException("Can't find correct number of normals");
               }
            }
         }

         this.nodePool = var6.getPool(var23);
      }

      var5.setSaveSegments(false);
      this.tempPositionVector.set(this.projectedX ? var2.x : var8 + 0.5, this.projectedY ? var2.y : var10 + 0.5, this.projectedZ ? var2.z : var12 + 0.5);
      Vector3d var42 = this.canAdvance(var1, this.startPosition, this.tempPositionVector, var4, var5, var7);
      if (var42 != null) {
         this.addStartNode(this.startPosition, var42, var4);
         var5.setSaveSegments(true);
         class="kw">return this.setProgress(AStarBase.Progress.COMPUTING);
      }

      this.tempPositionVector.x = this.projectedX ? var2.x : MathUtil.fastFloor(2.0 * var2.x) / 2.0;
      this.tempPositionVector.y = this.projectedY ? var2.y : MathUtil.fastFloor(2.0 * var2.y) / 2.0;
      this.tempPositionVector.z = this.projectedZ ? var2.z : MathUtil.fastFloor(2.0 * var2.z) / 2.0;

      for (double var46 = this.projectedX ? 0.0 : 0.5; var46 >= 0.0; var46 -= 0.5) {
         for (double var52 = this.projectedY ? 0.0 : 0.5; var52 >= 0.0; var52 -= 0.5) {
            for (double var55 = this.projectedZ ? 0.0 : 0.5; var55 >= 0.0; var55 -= 0.5) {
               this.tempDirectionVector.set(var46, var52, var55).add(this.tempPositionVector);
               var42 = this.canAdvance(var1, this.startPosition, this.tempDirectionVector, var4, var5, var7);
               if (var42 != null) {
                  this.addStartNode(this.startPosition, var42, var4);
               }
            }
         }
      }

      if (this.openNodes.isEmpty()) {
         double var47 = this.tempPositionVector.x + (this.projectedX ? 0 : -1);
         double var53 = this.tempPositionVector.x + (this.projectedX ? 0 : 1);
         double var56 = this.tempPositionVector.y + (this.projectedY ? 0 : -1);
         double var58 = this.tempPositionVector.y + (this.projectedY ? 0 : 1);
         double var32 = this.tempPositionVector.z + (this.projectedZ ? 0 : -1);
         double var34 = this.tempPositionVector.z + (this.projectedZ ? 0 : 1);

         for (double var36 = var47; var36 <= var53; var36 += 0.5) {
            for (double var38 = var56; var38 <= var58; var38 += 0.5) {
               for (double var40 = var32; var40 <= var34; var40 += 0.5) {
                  this.tempDirectionVector.set(var36, var38, var40);
                  var42 = this.canAdvance(var1, this.startPosition, this.tempDirectionVector, var4, var5, var7);
                  if (var42 != null) {
                     this.addStartNode(this.startPosition, var42, var4);
                  }
               }
            }
         }
      }

      var5.setSaveSegments(true);
      class="kw">return this.setProgress(this.openNodes.isEmpty() ? AStarBase.Progress.ABORTED : AStarBase.Progress.COMPUTING);
   }

   class="kw">public AStarBase.Progress computePath(
      @Nonnull Ref<EntityStore> var1, @Nonnull MotionController var2, @Nonnull ProbeMoveData var3, int var4, @Nonnull ComponentAccessor<EntityStore> var5
   ) {
      if (this.progress != AStarBase.Progress.COMPUTING) {
         class="kw">return this.progress;
      }

      var3.setRelaxedConstraints(this.relaxedConstraints);

      while (!this.openNodes.isEmpty() && var4-- > 0) {
         int var6 = this.openNodes.size() - 1;
         AStarNode var7 = this.openNodes.get(var6);
         var7.close();
         if (this.evaluator.isGoalReached(var1, this, var7, var2, var5)) {
            class="kw">return this.setProgress(this.buildPath(var7) ? AStarBase.Progress.ACCOMPLISHED : AStarBase.Progress.ABORTED);
         }

         this.openNodes.remove(var6);
         this.iterations++;
         if (var7.getLength() < this.maxPathLength) {
            Vector3d var8 = var7.getPosition();
            AStarNode[] var9 = var7.getSuccessors();
            int var10 = this.searchDirections.length;

            label94:
            for (int var11 = 0; var11 < var10; var11++) {
               if (var9[var11] == null) {
                  double var12 = this.searchDirectionDistances[var11];
                  var3.setPosition(var8).setDirection(this.searchDirections[var11]);
                  double var14 = var2.probeMove(var1, var3, var5);
                  double var16 = var12 * 0.49999995;
                  if (!(var14 < var16)) {
                     double var18 = var12 * 0.5;
                     var3.computePosition(var18, var3.targetPosition);
                     long var20 = this.positionToIndex(var3.targetPosition);
                     if (var20 != -1L) {
                        AStarNode var22 = (AStarNode)this.visitedBlocks.get(var20);
                        if (var22 != null) {
                           this.updateNode(var7, var11, var22, var2);
                        } else {
                           if (this.is2D) {
                              int var23 = var11 * this.normalsPerDirection;

                              for (int var24 = var23; var24 < var23 + this.normalsPerDirection; var24++) {
                                 Vector3d var25 = this.searchDirections[this.normalDirections[var24]];
                                 long var26 = this.addOffsetToIndex(var20, (long)var25.x, (long)var25.y, (long)var25.z);
                                 AStarNode var28 = (AStarNode)this.visitedBlocks.get(var26);
                                 if (var28 != null) {
                                    AStarNode var29 = var28.getSuccessor(this.inverseSearchDirections[var24]);
                                    if (var29 != null) {
                                       class="kw">continue label94;
                                    }
                                 }
                              }
                           }

                           Vector3d var30 = var14 >= var12 * 0.9999999 ? var3.probePosition : var3.targetPosition;
                           this.addOrUpdateNode(var7, var11, var30, var2, var5);
                        }
                     }
                  }
               }
            }

            if (this.openNodesLimit > 0 && this.openNodes.size() >= this.openNodesLimit) {
               class="kw">return this.setProgress(AStarBase.Progress.TERMINATED_OPEN_NODE_LIMIT_EXCEEDED);
            }

            if (this.totalNodesLimit > 0 && this.visitedBlocks.size() >= this.totalNodesLimit) {
               class="kw">return this.setProgress(AStarBase.Progress.TERMINATED_TOTAL_NODE_LIMIT_EXCEEDED);
            }
         }
      }

      class="kw">return this.setProgress(this.openNodes.isEmpty() ? AStarBase.Progress.TERMINATED : AStarBase.Progress.COMPUTING);
   }

   class="kw">public AStarBase.Progress getProgress() {
      class="kw">return this.progress;
   }

   class="kw">public boolean isComputing() {
      class="kw">return this.progress == AStarBase.Progress.COMPUTING;
   }

   class="kw">public float buildLongestPath() {
      AStarNode var1 = this.buildBestPath(AStarNode::getTravelCost, (var0, var1x) -> var1x > var0, 0.0F);
      class="kw">return var1 == null ? 0.0F : var1.getTravelCost();
   }

   class="kw">public float buildFurthestPath() {
      AStarNode var1 = this.buildBestPath(var1x -> (float)var1x.getPosition().distanceSquared(this.startPosition), (var0, var1x) -> var1x > var0, 0.0F);
      class="kw">return var1 == null ? 0.0F : var1.getTravelCost();
   }

   @Nullable
   class="kw">public AStarNode buildBestPath(@Nonnull ToFloatFunction<AStarNode> var1, @Nonnull BiFloatPredicate var2, float var3) {
      if (this.path != null) {
         class="kw">return null;
      } else {
         AStarNode var4 = this.findBestVisitedNode(var1, var2, var3);
         if (var4 == null) {
            class="kw">return null;
         } else {
            class="kw">return this.buildPath(var4) ? var4 : null;
         }
      }
   }

   @Nullable
   class="kw">public AStarNode findBestVisitedNode(@Nonnull ToFloatFunction<AStarNode> var1, @Nonnull BiFloatPredicate var2, float var3) {
      if (this.visitedBlocks.isEmpty()) {
         class="kw">return null;
      }

      ObjectIterator var4 = Long2ObjectMaps.fastIterator(this.visitedBlocks);
      float var5 = var3;
      AStarNode var6 = null;

      while (var4.hasNext()) {
         AStarNode var7 = (AStarNode)((Entry)var4.next()).getValue();
         float var8 = var1.applyAsFloat(var7);
         if (var2.test(var5, var8)) {
            var5 = var8;
            var6 = var7;
         }
      }

      class="kw">return var6;
   }

   @Nullable
   class="kw">public <T> AStarNode buildBestPath(@Nonnull BiToFloatFunction<AStarNode, T> var1, @Nonnull BiFloatPredicate var2, float var3, T var4) {
      if (this.path != null) {
         class="kw">return null;
      } else {
         AStarNode var5 = this.findBestVisitedNode(var1, var2, var3, var4);
         if (var5 == null) {
            class="kw">return null;
         } else {
            class="kw">return this.buildPath(var5) ? var5 : null;
         }
      }
   }

   @Nullable
   class="kw">public <T> AStarNode findBestVisitedNode(@Nonnull BiToFloatFunction<AStarNode, T> var1, @Nonnull BiFloatPredicate var2, float var3, T var4) {
      if (this.visitedBlocks.isEmpty()) {
         class="kw">return null;
      }

      ObjectIterator var5 = Long2ObjectMaps.fastIterator(this.visitedBlocks);
      float var6 = var3;
      AStarNode var7 = null;

      while (var5.hasNext()) {
         AStarNode var8 = (AStarNode)((Entry)var5.next()).getValue();
         float var9 = var1.applyAsFloat(var8, var4);
         if (var2.test(var6, var9)) {
            var6 = var9;
            var7 = var8;
         }
      }

      class="kw">return var7;
   }

   @Nonnull
   class="kw">public AStarDebugBase createDebugHelper(@Nonnull HytaleLogger var1) {
      class="kw">return new AStarDebugBase(this, var1);
   }

   class="kw">public class="kw">static long indexFromXYZ(long var0, long var2, long var4) {
      class="kw">return var0 >= 0L && var0 <= 2047L && var2 >= 0L && var2 <= 2047L && var4 >= 0L && var4 <= 2047L ? (var0 << 22) + (var2 << 11) + var4 : -1L;
   }

   class="kw">public class="kw">static int zFromIndex(long var0) {
      class="kw">return (int)(var0 & 2047L);
   }

   class="kw">public class="kw">static int yFromIndex(long var0) {
      class="kw">return zFromIndex(var0 >> 11);
   }

   class="kw">public class="kw">static int xFromIndex(long var0) {
      class="kw">return zFromIndex(var0 >> 22);
   }

   @Nonnull
   class="kw">public class="kw">static String positionIndexToString(long var0) {
      double var2 = (xFromIndex(var0) - 1024) * 0.5 + 0.5;
      double var4 = (yFromIndex(var0) - 1024) * 0.5 + 0.5;
      double var6 = (zFromIndex(var0) - 1024) * 0.5 + 0.5;
      class="kw">return "[" + var2 + "/" + var4 + "/" + var6 + "]";
   }

   class="kw">protected AStarBase.Progress setProgress(AStarBase.Progress var1) {
      this.progress = var1;
      class="kw">return this.progress;
   }

   @Nullable
   class="kw">protected Vector3d canAdvance(
      @Nonnull Ref<EntityStore> var1,
      @Nonnull Vector3d var2,
      @Nonnull Vector3d var3,
      @Nonnull MotionController var4,
      @Nonnull ProbeMoveData var5,
      @Nonnull ComponentAccessor<EntityStore> var6
   ) {
      var5.setPosition(var2).setTargetPosition(var3);
      class="kw">return var5.canAdvance(var1, var4, 0.9999999, var6) ? var5.probePosition : null;
   }

   class="kw">protected void addStartNode(Vector3d var1, @Nonnull Vector3d var2, @Nonnull MotionController var3) {
      long var4 = this.positionToIndex(var2);
      float var6 = this.measureWalkCost(var1, var2, var3);
      AStarNode var7 = this.nodePool.allocate().initAsStartNode(var2, var4, var6, this.evaluator.estimateToGoal(this, var2, var3));
      this.addOpenNode(var7, var4);
   }

   class="kw">protected void addOpenNode(@Nonnull AStarNode var1, int var2, @Nonnull Vector3d var3, long var4, float var6, MotionController var7) {
      int var8 = this.inverseSearchDirections[var2];
      AStarNode var9 = this.nodePool.allocate().initWithPredecessor(var1, var2, var3, var4, var8, var6, this.evaluator.estimateToGoal(this, var3, var7));
      this.addOpenNode(var9, var4);
   }

   class="kw">protected void addOpenNode(@Nonnull AStarNode var1, long var2) {
      int var4 = this.openNodes.size() - 1;
      float var5 = var1.getTotalCost();

      while (var4 >= 0 && this.openNodes.get(var4).getTotalCost() < var5) {
         var4--;
      }

      this.openNodes.add(var4 + 1, var1);
      this.visitedBlocks.put(var2, var1);
   }

   class="kw">protected void updateNode(@Nonnull AStarNode var1, int var2, @Nonnull AStarNode var3, @Nonnull MotionController var4) {
      if (!var3.isInvalid()) {
         float var5 = this.measureWalkCost(var1.getPosition(), var3.getPosition(), var4);
         this.updateNodeCost(var1, var2, var3, var5);
      }
   }

   class="kw">protected void addOrUpdateNode(
      @Nonnull AStarNode var1, int var2, @Nonnull Vector3d var3, @Nonnull MotionController var4, @Nonnull ComponentAccessor<EntityStore> var5
   ) {
      long var6 = this.positionToIndex(var3);
      if (var6 != -1L && var6 != var1.positionIndex) {
         AStarNode var8 = (AStarNode)this.visitedBlocks.get(var6);
         if (var8 == null) {
            if (!var4.isValidPosition(var3, var5)) {
               this.visitedBlocks.put(var6, this.nodePool.allocate().initAsInvalid(var3, this.positionToIndex(var3)));
            } else {
               float var10 = var1.getTravelCost() + this.measureWalkCost(var1.getPosition(), var3, var4);
               this.addOpenNode(var1, var2, var3, var6, var10, var4);
            }
         } else if (!var8.isInvalid()) {
            float var9 = this.measureWalkCost(var1.getPosition(), var3, var4);
            this.updateNodeCost(var1, var2, var8, var9);
         }
      }
   }

   class="kw">protected void updateNodeCost(@Nonnull AStarNode var1, int var2, @Nonnull AStarNode var3, float var4) {
      float var5 = var1.getTravelCost() + var4;
      float var6 = var5 - var3.getTravelCost();
      if (var6 < 0.0F) {
         var3.adjustOptimalPath(var1, var6, var2);
         var1.setSuccessor(var2, var3, this.inverseSearchDirections[var2], var4);
      } else {
         var1.successors[var2] = AStarNode.ENTRY_NODE_TAG;
         var3.successors[this.inverseSearchDirections[var2]] = AStarNode.ENTRY_NODE_TAG;
      }
   }

   class="kw">protected long positionToIndex(@Nonnull Vector3d var1) {
      long var2 = MathUtil.fastFloor(var1.x * 2.0 - this.positionToIndexOffsetX);
      long var4 = MathUtil.fastFloor(var1.y * 2.0 - this.positionToIndexOffsetY);
      long var6 = MathUtil.fastFloor(var1.z * 2.0 - this.positionToIndexOffsetZ);
      class="kw">return indexFromXYZ(var2, var4, var6);
   }

   class="kw">protected float measureWalkCost(Vector3d var1, Vector3d var2, @Nonnull MotionController var3) {
      class="kw">return (float)var3.waypointDistance(var1, var2);
   }

   class="kw">protected boolean buildPath(@Nullable AStarNode var1) {
      if (var1 == null) {
         this.path = null;
         class="kw">return false;
      }

      this.pathEnd.set(var1.getPosition());
      int var2 = this.visitedBlocks.size();
      int var3 = 0;
      if (this.optimizedBuildPath) {
         AStarNode var8 = var1;
         int var9 = 1;
         int var10 = -1;
         AStarNode var7 = null;

         while (var8 != null) {
            if (++var3 > var2) {
               class="kw">return this.abandonCyclicPath(var1, var2);
            }

            var8.setNextNode(var7, var9);
            if (var8.getPredecessorDirection() != var10) {
               var10 = var8.getPredecessorDirection();
               var7 = var8;
               var9++;
            }

            this.path = var8;
            var8 = var8.getPredecessor();
         }

         class="kw">return true;
      } else {
         int var4 = 0;
         AStarNode var5 = null;

         for (AStarNode var6 = var1; var6 != null; var6 = var6.getPredecessor()) {
            if (++var3 > var2) {
               class="kw">return this.abandonCyclicPath(var1, var2);
            }

            var6.setNextNode(var5, ++var4);
            this.path = var6;
            var5 = var6;
         }

         class="kw">return true;
      }
   }

   class="kw">private boolean abandonCyclicPath(@Nonnull AStarNode var1, int var2) {
      this.path = null;
      ((HytaleLogger.Api)LOGGER.at(Level.WARNING).atMostEvery(1, TimeUnit.MINUTES))
         .log("Discarding path ending at %s: its predecessor chain exceeded the %d nodes visited by the search, so it is cyclic", var1.getPosition(), var2);
      class="kw">return false;
   }

   class="kw">protected long addOffsetToIndex(long var1, long var3, long var5, long var7) {
      long var9 = xFromIndex(var1) + var3;
      long var11 = yFromIndex(var1) + var5;
      long var13 = zFromIndex(var1) + var7;
      class="kw">return indexFromXYZ(var9, var11, var13);
   }

   class="kw">public enum Progress {
      UNSTARTED,
      ABORTED,
      COMPUTING,
      ACCOMPLISHED,
      TERMINATED,
      TERMINATED_OPEN_NODE_LIMIT_EXCEEDED,
      TERMINATED_TOTAL_NODE_LIMIT_EXCEEDED;

      Progress() {
      }
   }
}