public void GetCommand_Should_Success(int surfaceRowsCount, int surfaceColumnsCount, int robotPositionRow, int robotPositionColumn, SurfaceDirection surfaceDirection, string commandsString, int expectedPositionRow, int expectedPositionColumn, SurfaceDirection expectedDirection, bool expectedIsLost) { SurfaceGrid _marsSurface = new SurfaceGrid(surfaceRowsCount + 1, surfaceColumnsCount + 1); MarsInvasionControlCenter controlCenter = new MarsInvasionControlCenter(_marsSurface); var position = new SurfacePosition(robotPositionRow, robotPositionColumn); var newRobot = controlCenter.AddNewRobot(position, surfaceDirection); if (!newRobot.IsLost) { var commandSet = RobotCommandSet.Create(_commandsFactory, commandsString); newRobot.ExecuteCommands(commandSet); PrintPosition(newRobot); } else { PrintPosition(newRobot); } Assert.AreEqual(expectedPositionRow, newRobot.Position.Row); Assert.AreEqual(expectedPositionColumn, newRobot.Position.Column); Assert.AreEqual(expectedDirection, newRobot.Direction); Assert.AreEqual(expectedIsLost, newRobot.IsLost); }
/// <summary> /// Gets the bicubicly interpolated modifier at given position. Called by the surface to get modifier height for each point. /// </summary> public float GetBicubicInterpolatedModifierAt(float row, float col, SurfacePosition sp) { int row1 = Mathf.FloorToInt(row); int col1 = Mathf.FloorToInt(col); float interX = row - row1; float interY = col - col1; float[][] array = new float[4][] { new float[4], new float[4], new float[4], new float[4] }; array[0][0] = GetModifierAt(row1 - 1, col1 - 1, sp); array[0][1] = GetModifierAt(row1 - 1, col1, sp); array[0][2] = GetModifierAt(row1 - 1, col1 + 1, sp); array[0][3] = GetModifierAt(row1 - 1, col1 + 2, sp); array[1][0] = GetModifierAt(row1, col1 - 1, sp); array[1][1] = GetModifierAt(row1, col1, sp); array[1][2] = GetModifierAt(row1, col1 + 1, sp); array[1][3] = GetModifierAt(row1, col1 + 2, sp); array[2][0] = GetModifierAt(row1 + 1, col1 - 1, sp); array[2][1] = GetModifierAt(row1 + 1, col1, sp); array[2][2] = GetModifierAt(row1 + 1, col1 + 1, sp); array[2][3] = GetModifierAt(row1 + 1, col1 + 2, sp); array[3][0] = GetModifierAt(row1 + 2, col1 - 1, sp); array[3][1] = GetModifierAt(row1 + 2, col1, sp); array[3][2] = GetModifierAt(row1 + 2, col1 + 1, sp); array[3][3] = GetModifierAt(row1 + 2, col1 + 2, sp); return(GetBiCubicValue(array, interX, interY)); }
/// <summary> /// Gets the nearest modifier at position /// </summary> public float GetModifierAt(int row, int col, SurfacePosition sp) { int x = row, y = col; SurfacePosition correctSP = GetCorrectSurfacePosition(ref x, ref y, sp); //if(x < 0 || x > modifierResolution-1 || y < 0 || y > modifierResolution-1) // Debug.Log("row: " + row + " col: " + col + " sp: " + sp + " | " + " x: " + x + " y: " + y + " correct:" + correctSP.ToString()); if (x < 0) { x = 0; } if (x > modifierResolution - 1) { x = modifierResolution - 1; } if (y < 0) { y = 0; } if (y > modifierResolution - 1) { y = modifierResolution - 1; } return(GetModifierArray(correctSP)[y * modifierResolution + x]); }
/// <summary> /// Single iteration generates one surface. To be used to show progress on the editor script /// </summary> public void CreateSurface(float x, float half, float y, float nx, float ny, SurfacePosition pos, int sx, int sy) { Vector3 start = Vector3.zero, end = Vector3.zero; Vector3 topRight = Vector3.zero, bottomLeft = Vector3.zero; switch (pos) { case SurfacePosition.TOP: start = new Vector3(x - half, half, y - half); end = new Vector3(nx - half, half, ny - half); topRight = new Vector3(nx - half, half, y - half); bottomLeft = new Vector3(x - half, half, ny - half); break; case SurfacePosition.FRONT: start = new Vector3(x - half, half - y, half); end = new Vector3(nx - half, half - ny, half); topRight = new Vector3(nx - half, half - y, half); bottomLeft = new Vector3(x - half, half - ny, half); break; case SurfacePosition.BOTTOM: start = new Vector3(x - half, -half, half - y); end = new Vector3(nx - half, -half, half - ny); topRight = new Vector3(nx - half, -half, half - y); bottomLeft = new Vector3(x - half, -half, half - ny); break; case SurfacePosition.BACK: start = new Vector3(half - x, half - y, -half); end = new Vector3(half - nx, half - ny, -half); topRight = new Vector3(half - nx, half - y, -half); bottomLeft = new Vector3(half - x, half - ny, -half); break; case SurfacePosition.LEFT: start = new Vector3(-half, half - y, -half + x); end = new Vector3(-half, half - ny, -half + nx); topRight = new Vector3(-half, half - y, -half + nx); bottomLeft = new Vector3(-half, half - ny, -half + x); break; case SurfacePosition.RIGHT: start = new Vector3(half, half - y, half - x); end = new Vector3(half, half - ny, half - nx); topRight = new Vector3(half, half - y, half - nx); bottomLeft = new Vector3(half, half - ny, half - x); break; } InstantiateSurface(id, start, end, topRight, bottomLeft, pos, sx, sy); id++; }
public LongRangeApproacherEngine(SurfacePosition position, IActionEngine prevEngine, IMovementClient client, string owner) { _client = client; _prevEngine = prevEngine; _position = position; _owner = owner; _attemptStart = DateTime.Now; }
public Robot(ISurfaceGrid marsSurface, SurfacePosition position, SurfaceDirection direction) { Position = position; Direction = direction; _marsSurface = marsSurface ?? throw new ArgumentNullException(nameof(marsSurface)); IsLost = !_marsSurface.IsValidPosition(position); }
public InfluencedDirEngine(IMovementClient actions, IScanner scanner, string owner, SurfacePosition position) { _actions = actions; _scanner = scanner; _owner = owner; _position = position; _lastScan = DateTime.Now; }
/// <summary> /// Add height value to surface with selected brush mode /// </summary> private void Add(SurfacePosition sp, Vector2 brushCenter, Vector2 position, Vector2 brushPosition, Color brushPixel) { // make sure position is in array range if (position.x < 0 || position.x > modifierResolution - 1 || position.y < 0 || position.y > modifierResolution - 1) { //Debug.Log("Planet tries to paint outside of array range"); return; } float[] modifier = GetModifierArray(sp); float value = modifier[(int)position.x + (int)position.y * modifierResolution]; float falloffValue = 1f; if (brushFalloff) { falloffValue = 1f - falloff.Evaluate(Vector2.Distance(brushCenter, brushPosition / modifierResolution) / (brushSize * 0.5f)); } float strength = brushStrength; if (useBrushTexture) { if (useBrushAlpha) { strength *= brushPixel.a; } else { strength *= brushPixel.grayscale; } } switch (brushMode) { case BrushMode.ADD: value += strength * falloffValue; break; case BrushMode.SUBSTRACT: value -= strength * falloffValue; break; case BrushMode.SET: value = Mathf.Lerp(value, brushSetValue, falloffValue * strength); break; } if (value > highLimit) { value = highLimit; } if (value < lowLimit) { value = lowLimit; } modifier[(int)position.x + (int)position.y * modifierResolution] = value; }
public ApproacherEngine(SurfacePosition position, IActionEngine prevEngine, IMovementClient client, string owner) { _position = position; _prevEngine = prevEngine; _client = client; _status = ApproachStatus.BREAKING; _owner = owner; _attemptStart = DateTime.Now; _next = null; }
private void CheckIfOtherMines(StatusUpdateModel model) { if (_next != null) { return; } var targets = model.GoldMines.Where(s => s.Owner != _owner && s != _position); if (targets.Count() > 0) { _next = targets.First(); } }
/// <summary> /// Gets the bilinearly interpolated modifier at given position. Called by the surface to get modifier height for each point. /// </summary> public float GetBilinearInterpolatedModifierAt(float row, float col, SurfacePosition sp) { int row1 = Mathf.FloorToInt(row); int col1 = Mathf.FloorToInt(col); float interX = row - row1; float interY = col - col1; float a = GetModifierAt(row1, col1, sp); float b = GetModifierAt(row1 + 1, col1, sp); float c = GetModifierAt(row1, col1 + 1, sp); float d = GetModifierAt(row1 + 1, col1 + 1, sp); return(Mathf.Lerp(Mathf.Lerp(a, b, interX), Mathf.Lerp(c, d, interX), interY)); }
private void FillMines() { if (!PopIfMessage("MINES")) { return; } ; var localMines = PopInt(); var mineList = new List <SurfacePosition>(); for (int i = 0; i < localMines; i++) { var pos = new SurfacePosition(PopString(), PopDouble(), PopDouble()); mineList.Add(pos); } _model.GoldMines = mineList; }
//Horizontal Rotation for a particular surface position private int Rotation(SurfacePosition s) { switch (s) { case SurfacePosition.Left: return(-90); case SurfacePosition.Right: return(90); case SurfacePosition.Back: return(180); default: return(0); } }
private void FillBombs() { if (!PopIfMessage("BOMBS")) { return; } ; //assuming it is {x} {y} var localBombs = PopInt(); var bombList = new List <SurfacePosition>(); for (int i = 0; i < localBombs; i++) { var pos = new SurfacePosition("--", PopDouble(), PopDouble()); bombList.Add(pos); } _model.Bombs = bombList; }
public void Execute(IRobot robot, ISurfaceGrid surfaceGrid) { var newPosition = new SurfacePosition(robot.Position.Row, robot.Position.Column); switch (robot.Direction) { case SurfaceDirection.Up: newPosition.Row++; break; case SurfaceDirection.Left: newPosition.Column--; break; case SurfaceDirection.Down: newPosition.Row--; break; case SurfaceDirection.Right: newPosition.Column++; break; default: throw new ArgumentException(nameof(robot.Direction), "Direction is not supported: " + robot.Direction); } if (!surfaceGrid.IsDeadScentMovement(robot.Position, robot.Direction)) { try { surfaceGrid.Move(robot.Position, robot.Direction); } finally { robot.SetPosition(newPosition); } } }
public void Robot_Not_Move_If_Scent_Exist() { SurfaceGrid _marsSurface = new SurfaceGrid(2, 2); MarsInvasionControlCenter controlCenter = new MarsInvasionControlCenter(_marsSurface); //First robot is being lost var position = new SurfacePosition(1, 1); var newRobot = controlCenter.AddNewRobot(position, SurfaceDirection.Up); var commandSet = RobotCommandSet.Create(_commandsFactory, "F"); newRobot.ExecuteCommands(commandSet); Assert.IsTrue(newRobot.IsLost); //Second robot is not lost newRobot = controlCenter.AddNewRobot(position, SurfaceDirection.Up); newRobot.ExecuteCommands(commandSet); Assert.IsFalse(newRobot.IsLost); Assert.AreEqual(1, newRobot.Position.Row); Assert.AreEqual(1, newRobot.Position.Column); }
public float[] GetModifierArray(SurfacePosition surfacePosition) { switch (surfacePosition) { case SurfacePosition.TOP: return(topModifier); case SurfacePosition.BOTTOM: return(bottomModifier); case SurfacePosition.LEFT: return(leftModifier); case SurfacePosition.RIGHT: return(rightModifier); case SurfacePosition.FRONT: return(frontModifier); case SurfacePosition.BACK: return(backModifier); } return(null); }
/// <summary> /// Determines the surface position relative to an entire chunk during point generation. /// </summary> /// <param name="current">The previously identified surface position.</param> /// <param name="surface">The surface position.</param> /// <param name="chunkOriginY">The Y origin of the chunk.</param> /// <returns>THe updated surface position.</returns> private SurfacePosition CheckSurfacePosition(SurfacePosition? current, float surface, int chunkOriginY) { if (current.HasValue && current.Value == SurfacePosition.Inside) { return current.Value; } else { int surfaceI = (int)System.Math.Floor(surface); SurfacePosition surfacePositionX; if (surfaceI < chunkOriginY) { surfacePositionX = SurfacePosition.Below; } else { if (surfaceI < chunkOriginY + Metrics.ChunkHeight) { surfacePositionX = SurfacePosition.Inside; } else { surfacePositionX = SurfacePosition.Above; } } if (current.HasValue && current.Value != surfacePositionX) { return SurfacePosition.Inside; } else { return surfacePositionX; } } }
public void SetPosition(SurfacePosition newPosition) { Position = newPosition; }
//Generate camera preview gizmo. private void OnDrawGizmos() { //Only draw if 2D mode. if (SceneView.currentDrawingSceneView != null && !SceneView.currentDrawingSceneView.in2DMode) { return; } if (EditorPrefs.HasKey("ImmersiveCameraScreenSize")) { screenSize = (ScreenSizes)EditorPrefs.GetInt("ImmersiveCameraScreenSize"); } if (EditorPrefs.HasKey("ImmersiveCameraLayout")) { layout = (SurfacePosition)EditorPrefs.GetInt("ImmersiveCameraLayout"); } //Check if camera settings have changed. if (_screenSize != screenSize || _layout != layout || _cagType != cagType) { _layout = layout; _screenSize = screenSize; _cagType = cagType; //Calculate new Surface Information rects = new List <Rect>(); var surfacePositions = GetSurfacesFromLayout(layout); var surfaceRects = GenerateSurfaceRectsInEditor(surfacePositions); GenerateSurfacesInfo(surfacePositions, surfaceRects); //Calculate new cameras size and position. for (int i = 0; i < walls.Count; i++) { var surface = walls[i]; Rect rect = new Rect(); rect.size = new Vector2(surface.aspectRatio, height * 2); if (cagType == CAGType.Interior) { rect.center = GetWallCameraPositionCAGI(surface); } else if (cagType == CAGType.Exterior) { rect.center = GetWallCameraPositionCAGE(surface); } rects.Add(rect); } } //Draw camera frustrums. float xPos = transform.position.x; float yPos = transform.position.y; var zPos = transform.position.z + mainCamera.farClipPlane; Gizmos.color = Color.white; for (int i = 0; i < rects.Count; i++) { var rect = rects[i]; Gizmos.DrawLine(new Vector3(xPos + rect.xMin, yPos + rect.yMax, zPos), new Vector3(xPos + rect.xMax, yPos + rect.yMax, zPos)); Gizmos.DrawLine(new Vector3(xPos + rect.xMin, yPos + rect.yMin, zPos), new Vector3(xPos + rect.xMax, yPos + rect.yMin, zPos)); Gizmos.DrawLine(new Vector3(xPos + rect.xMin, yPos + rect.yMin, zPos), new Vector3(xPos + rect.xMin, yPos + rect.yMax, zPos)); Gizmos.DrawLine(new Vector3(xPos + rect.xMax, yPos + rect.yMin, zPos), new Vector3(xPos + rect.xMax, yPos + rect.yMax, zPos)); } }
public SurfaceInfo(Rect rect, SurfacePosition position) { this.rect = rect; aspectRatio = rect.width / rect.height; this.position = position; }
public IRobot AddNewRobot(SurfacePosition position, SurfaceDirection direction) { return(new Robot(_marsSurface, position, direction)); }
/// <summary> /// Paints heights on the planet surface /// </summary> public void Paint(Surface surface, Vector2 pos) { int res = modifierResolution; float increment = 1f / res; int area = Mathf.RoundToInt(brushSize / increment); SurfacePosition sp = surface.surfacePosition; List <Surface> positions = new List <Surface>(); for (int y = -area / 2; y < area / 2; y++) { for (int x = -area / 2; x < area / 2; x++) { int xx = Mathf.RoundToInt((pos.x + x * increment) * res); int yy = Mathf.RoundToInt((pos.y + y * increment) * res); Vector2 brushPosition = new Vector2(xx, yy); Color pixel = Color.black; if (useBrushTexture && brushTexture != null) { pixel = brushTexture.GetPixelBilinear((x + area / 2f) / area, (y + area / 2f) / area); } // paint first to this position if known duplicate position (shared between surfaces) /*if(xx == 0 || xx == modifierResolution-1 || yy == 0 || yy == modifierResolution-1) { * if(!positions.Contains(sp)) * positions.Add(sp); * * Add(sp, pos, brushPosition, brushPosition, pixel); * }*/ SurfacePosition correctSP = GetCorrectSurfacePosition(ref xx, ref yy, sp); for (int i = 0; i < surfaces.Count; i++) { if (surfaces[i].surfacePosition == correctSP) { if (xx >= surfaces[i].modifierStartX && xx < surfaces[i].modifierStartX + surfaces[i].modifierResolution && yy >= surfaces[i].modifierStartY && yy < surfaces[i].modifierStartY + surfaces[i].modifierResolution) { if (!positions.Contains(surfaces[i])) { positions.Add(surfaces[i]); } break; } } } Vector2 newPos = new Vector2(xx, yy); Add(correctSP, pos, newPos, brushPosition, pixel); } } for (int i = 0; i < surfaces.Count; i++) { if (positions.Contains(surfaces[i])) { surfaces[i].GenerateMesh(meshResolution); } } positions.Clear(); }
/// <summary> /// Instantiates a surface and adds it to the list. Virtual so other planet types can override it to use different surfaces /// </summary> private void InstantiateSurface(int id, Vector3 start, Vector3 end, Vector3 topRight, Vector3 bottomLeft, SurfacePosition sp, int sx, int sy) { GameObject t = new GameObject("Surface" + id); t.transform.parent = this.transform; t.transform.position = transform.position; Surface surface = t.AddComponent <Surface>(); surface.Initialize(0, start, end, topRight, bottomLeft, this, sp, null, sx, sy); surface.GenerateMesh(meshResolution); surfaces.Add(surface); }
/*public Color[] GetColorArray(SurfacePosition surfacePosition) { * switch(surfacePosition) { * case SurfacePosition.TOP: * return topColor; * case SurfacePosition.BOTTOM: * return bottomColor; * case SurfacePosition.LEFT: * return leftColor; * case SurfacePosition.RIGHT: * return rightColor; * case SurfacePosition.FRONT: * return frontColor; * case SurfacePosition.BACK: * return backColor; * } * return null; * }*/ /// <summary> /// Returns the correct surface position when out of bounds of the current one /// </summary> public SurfacePosition GetCorrectSurfacePosition(ref int row, ref int col, SurfacePosition sp) { SurfacePosition correctSP = sp; switch (sp) { case SurfacePosition.TOP: if (row >= 0 && row < modifierResolution && col >= 0 && col < modifierResolution) { correctSP = SurfacePosition.TOP; } else if (row < 0) { correctSP = SurfacePosition.LEFT; int oldCol = col; col = Mathf.Abs(row + 1); row = oldCol; } else if (row >= modifierResolution) { correctSP = SurfacePosition.RIGHT; int oldCol = col; col = row - modifierResolution; row = (modifierResolution - 1) - oldCol; } else if (col < 0) { correctSP = SurfacePosition.BACK; col = Mathf.Abs(col + 1); row = (modifierResolution - 1) - row; } else if (col >= modifierResolution) { correctSP = SurfacePosition.FRONT; col -= modifierResolution; } break; case SurfacePosition.BOTTOM: if (row >= 0 && row < modifierResolution && col >= 0 && col < modifierResolution) { correctSP = SurfacePosition.BOTTOM; } else if (row < 0) { correctSP = SurfacePosition.LEFT; int oldCol = col; col = modifierResolution + row; row = (modifierResolution - 1) - oldCol; } else if (row >= modifierResolution) { correctSP = SurfacePosition.RIGHT; int oldCol = col; col = modifierResolution - (int)Mathf.Abs((modifierResolution - 1) - row); row = oldCol; } else if (col < 0) { correctSP = SurfacePosition.FRONT; col = modifierResolution + col; } else if (col >= modifierResolution) { correctSP = SurfacePosition.BACK; col = modifierResolution - (int)Mathf.Abs((modifierResolution - 1) - col); row = (modifierResolution - 1) - row; } break; case SurfacePosition.LEFT: if (row >= 0 && row < modifierResolution && col >= 0 && col < modifierResolution) { correctSP = SurfacePosition.LEFT; } else if (row < 0) { correctSP = SurfacePosition.BACK; row = modifierResolution + row; } else if (row >= modifierResolution) { correctSP = SurfacePosition.FRONT; row -= modifierResolution; } else if (col < 0) { correctSP = SurfacePosition.TOP; int oldRow = row; row = Mathf.Abs(col + 1); col = oldRow; } else if (col >= modifierResolution) { correctSP = SurfacePosition.BOTTOM; int oldRow = row; row = col - modifierResolution; col = (modifierResolution - 1) - oldRow; } break; case SurfacePosition.RIGHT: if (row >= 0 && row < modifierResolution && col >= 0 && col < modifierResolution) { correctSP = SurfacePosition.RIGHT; } else if (row < 0) { correctSP = SurfacePosition.FRONT; row = modifierResolution + row; } else if (row >= modifierResolution) { correctSP = SurfacePosition.BACK; row -= modifierResolution; } else if (col < 0) { correctSP = SurfacePosition.TOP; int oldRow = row; row = modifierResolution + col; col = (modifierResolution - 1) - oldRow; } else if (col >= modifierResolution) { correctSP = SurfacePosition.BOTTOM; int oldRow = row; row = modifierResolution - (int)Mathf.Abs((modifierResolution - 1) - col); col = oldRow; } break; case SurfacePosition.FRONT: if (row >= 0 && row < modifierResolution && col >= 0 && col < modifierResolution) { correctSP = SurfacePosition.FRONT; } else if (row < 0) { correctSP = SurfacePosition.LEFT; row = modifierResolution + row; } else if (row >= modifierResolution) { correctSP = SurfacePosition.RIGHT; row -= modifierResolution; } else if (col < 0) { correctSP = SurfacePosition.TOP; col = modifierResolution + col; } else if (col >= modifierResolution) { correctSP = SurfacePosition.BOTTOM; col -= modifierResolution; } break; case SurfacePosition.BACK: if (row >= 0 && row < modifierResolution && col >= 0 && col < modifierResolution) { correctSP = SurfacePosition.BACK; } else if (row < 0) { correctSP = SurfacePosition.RIGHT; row = modifierResolution + row; } else if (row >= modifierResolution) { correctSP = SurfacePosition.LEFT; row -= modifierResolution; } else if (col < 0) { correctSP = SurfacePosition.TOP; col = Mathf.Abs(col + 1); row = (modifierResolution - 1) - row; } else if (col >= modifierResolution) { correctSP = SurfacePosition.BOTTOM; col = modifierResolution - (int)Mathf.Abs((modifierResolution - 1) - col); row = modifierResolution - row; } break; } return(correctSP); }