public Line <FiringDistance> this[int x, int y, Direction outwardDirection, EdgeOffset edgeOffset = EdgeOffset.Centre] { get { return(this[new Point((short)x, (short)y), outwardDirection, edgeOffset]); } }
// TODO: Cache these offsets public static Point GetOffsetToPointOnTankEdge(Direction edge, EdgeOffset edgeOffset) { Point offsetToCentreOfEdge = Constants.TANK_EXTENT_OFFSET * edge.GetOffset(); Direction perpendicular = Direction.NONE; int multiplier = 1; switch (edgeOffset) { case EdgeOffset.Centre: return(offsetToCentreOfEdge); case EdgeOffset.OffCentreAntiClockwise: perpendicular = edge.AntiClockwise(); break; case EdgeOffset.OffCentreClockwise: perpendicular = edge.Clockwise(); break; case EdgeOffset.CornerAntiClockwise: perpendicular = edge.AntiClockwise(); multiplier = 2; break; case EdgeOffset.CornerClockwise: perpendicular = edge.Clockwise(); multiplier = 2; break; } return(offsetToCentreOfEdge + multiplier * perpendicular.GetOffset()); }
private void AddNextFiringLineNodesToQueueForMovementDirAndEdgeOffset( TwoValuedCircularBuffer <Node> bfsQueue, Direction movementDir, EdgeOffset edgeOffset, FiringLineSummary firingLineSummary, int distanceToAdd) { Line <FiringDistance> firingLine = firingLineSummary.FiringLine; int nextFiringLineIndex; for (nextFiringLineIndex = firingLineSummary.IndexOfNextFiringLinePoint; nextFiringLineIndex < firingLine.Length; nextFiringLineIndex++) { if (nextFiringLineIndex == -1) { return; } FiringDistance firingDist = firingLine[nextFiringLineIndex]; int nextEdgeWeighting = firingDist.TicksTillTargetShot - 1; // This distance is the edge weight in the graph. // The -1 is because we need to compensate for the weight 1 edge added from // the tank's position + direction on the firing line, to the firing line node. if (nextEdgeWeighting > distanceToAdd) { firingLineSummary.NextEdgeWeighting = nextEdgeWeighting; firingLineSummary.IndexOfNextFiringLinePoint = nextFiringLineIndex; return; } if (!TurnCalculationCache.CellMatrix[firingDist.StartingTankPosition].IsValid) { firingLineSummary.NextEdgeWeighting = Constants.UNREACHABLE_DISTANCE; firingLineSummary.IndexOfNextFiringLinePoint = -1; return; } Node firingLineNode = new Node(ActionType.FiringLine, movementDir, firingDist.StartingTankPosition, (byte)nextFiringLineIndex, edgeOffset); bfsQueue.Add(firingLineNode, nextEdgeWeighting); } if (nextFiringLineIndex == firingLine.Length) { firingLineSummary.NextEdgeWeighting = Constants.UNREACHABLE_DISTANCE; firingLineSummary.IndexOfNextFiringLinePoint = -1; } }
public Node(ActionType actionType, Direction dir, int x, int y, byte firingLineIndex = 0, EdgeOffset edgeOffset = EdgeOffset.Centre) : this() { MobilityId = (byte)x | ((byte)y << YBitShift) | ((byte)dir << DirBitShift) | ((byte)actionType << ActionTypeBitShift) | ((byte)edgeOffset << EdgeOffsetBitShift) | (firingLineIndex << FiringLineIndexBitShift); /* Slows down algorithm too much... * Debug.Assert(ActionType == actionType, "ActionType wrong"); * Debug.Assert(Dir == dir, "Dir wrong"); * Debug.Assert(X == x, "X wrong"); * Debug.Assert(Y == y, "Y wrong"); * Debug.Assert(FiringLineIndex == firingLineIndex, "FiringLineIndex wrong"); * Debug.Assert(EdgeOffset == edgeOffset, "EdgeOffset wrong"); */ }
public static Point GetPointOnTankEdge(int centreX, int centreY, Direction edge, EdgeOffset edgeOffset) { return(GetPointOnTankEdge(new Point((short)centreX, (short)centreY), edge, edgeOffset)); }
public static Point GetPointOnTankEdge(Point centreOfTank, Direction edge, EdgeOffset edgeOffset) { return(centreOfTank + GetOffsetToPointOnTankEdge(edge, edgeOffset)); }
public Node(ActionType actionType, MobileState mobileState, byte firingLineIndex = 0, EdgeOffset edgeOffset = EdgeOffset.Centre) : this(actionType, mobileState.Dir, mobileState.Pos, firingLineIndex, edgeOffset) { }
public Node(ActionType actionType, Direction dir, Point pos, byte firingLineIndex = 0, EdgeOffset edgeOffset = EdgeOffset.Centre) : this(actionType, dir, pos.X, pos.Y, firingLineIndex, edgeOffset) { }
public Line <FiringDistance> this[Point targetPoint, Direction outwardDirection, EdgeOffset edgeOffset = EdgeOffset.Centre] { get { Debug.Assert((int)edgeOffset < FiringLineArraySize, "An unsupported edge offset has been requested of a firing line matrix"); Line <FiringDistance>[] firingLinesByEdgeOffset = directionalMatrixOfFiringLinesByEdgeOffset[outwardDirection, targetPoint]; if (firingLinesByEdgeOffset == null) { firingLinesByEdgeOffset = new Line <FiringDistance> [FiringLineArraySize]; } Line <FiringDistance> firingLine = firingLinesByEdgeOffset[(int)edgeOffset]; if (firingLine == null) { Cell targetCell; switch (ExtentType) { case ElementExtentType.TankBody: targetCell = TurnCalcationCache.TankLocationMatrix[targetPoint] .CellsOnEdgeByDirectionAndEdgeOffset[(int)outwardDirection, (int)edgeOffset]; break; default: // case ElementExtentType.Point: targetCell = TurnCalcationCache.CellMatrix[targetPoint]; break; } firingLine = FiringDistanceCalculator.GetFiringDistancesToPoint( targetCell, outwardDirection.GetOpposite() /*movement direction*/, TurnCalcationCache, GameStateCalculationCache); } return(firingLine); } }