public static IEnumerable <Point> GetNeighbors(this Point source) { foreach (Dir8 dir in EightDirections.Enumerate(true, false, false)) { yield return(source.PointInDir(dir)); } }
private void ScanInternal() { while (frontier.Count > 0) { Point current = frontier.Dequeue(); foreach (Dir8 dir in EightDirections.Enumerate(true, false, false)) { Point neighbor = current.PointInDir(dir); if (!neighbor.ExistsOnMap()) { continue; } int neighborCost = GetCellCost(neighbor); if (neighborCost < 0) { if (this[neighbor] == Unexplored) { this[neighbor] = Blocked; } } else { int totalCost = this[current] + neighborCost; if (this[neighbor] > totalCost) { this[neighbor] = totalCost; frontier.Enqueue(neighbor, totalCost); } } } } }
//Performs Shield ability //NOTE: Also need to pass in bool if that's how I'm gonna handle animationss public void Shield(ref PlayerState playerState) { switch (shieldState) { case ShieldState.Setup: //Activate shield collider here playerFaceDirection = orientationSystem.DetermineDirectionFromVector(moveInfo.GetLastMove()); ActivateCorrespondingCollider(playerFaceDirection); //Debug.Log (playerFaceDirection); //Play animation animator.Play("Shield State"); shieldState = ShieldState.Shielding; break; case ShieldState.Shielding: //NOTE: if strafing, play strafe animation Strafe(); //If player is shielding, stay in this state; else, exit state if (isShielding()) { //Stay in this state } else { DeactivateCorrespondingCollider(playerFaceDirection); shieldState = ShieldState.Setup; playerState = PlayerState.Default; return; } //Check for Grab, Dodge, or (maybe) Jump inputs //Grab if (Input.GetButtonDown("AttackPS4")) { //shieldColliderUp.enabled = false; //Switch to grab state } else if (Input.GetButtonDown("SprintPS4")) { //Check if there's any movement if (playerMoving) { //Switch to DodgeRoll state DeactivateCorrespondingCollider(playerFaceDirection); shieldState = ShieldState.Setup; playerState = PlayerState.DodgeRolling; } } break; } } //Shield
public static IEnumerable <Point> Scan(Point source, Func <Point, bool> condition, SourceOption sourceOption = SourceOption.AlwaysIncludeSource) { List <Point> frontier = new List <Point>(); HashSet <Point> visited = new HashSet <Point> { source }; switch (sourceOption) { case SourceOption.AlwaysIncludeSource: yield return(source); break; case SourceOption.ConditionallyIncludeSource: case SourceOption.StopScanOnSourceFailure: if (condition.Invoke(source)) { yield return(source); } else if (sourceOption == SourceOption.StopScanOnSourceFailure) { yield break; } break; } frontier.Add(source); while (frontier.Count > 0) { Point current = frontier[frontier.Count - 1]; frontier.RemoveAt(frontier.Count - 1); foreach (Dir8 dir in EightDirections.Enumerate(true, false, false)) { Point neighbor = current.PointInDir(dir); if (!neighbor.ExistsBetweenMapEdges()) { continue; } if (visited.Contains(neighbor)) { continue; } if (condition.Invoke(neighbor)) { yield return(neighbor); frontier.Add(neighbor); visited.Add(neighbor); } } } }
//===============HELPER FUNCTIONS THAT DO THE MOVING======================= //NOTE: "acceleration" is useless now that I'm using raw input //Handles player movement from user input private void MovePlayer() { //Get player input float moveHorizontal = (Input.GetAxisRaw("Horizontal")) * acceleration; float moveVertical = (Input.GetAxisRaw("Vertical")) * acceleration; Sprint(ref moveHorizontal, ref moveVertical); //Move the Player according to raw input //if (moveHorizontal > 0.5f || moveHorizontal < -0.5f || moveVertical > 0.5f || moveVertical < -0.5f) { if (moveHorizontal > 0f || moveHorizontal < -0f || moveVertical > 0f || moveVertical < -0f) { //To make sure diagonal movement isn't faster Vector2 moveDir = new Vector2(moveHorizontal, moveVertical); if (moveDir.magnitude > 1f) { moveDir.Normalize(); moveHorizontal = moveDir.x; moveVertical = moveDir.y; } //Move player Mathf.Clamp(moveVertical, -1f, 1f); Mathf.Clamp(moveHorizontal, -1f, 1f); playerBody.velocity = new Vector2(moveHorizontal * moveSpeed, moveVertical * moveSpeed); playerMoving = true; //Update variables that contain info about movement lastMove = new Vector2(moveHorizontal, moveVertical); playerOrientation = orientationSystem.DetermineDirectionFromVector(lastMove); } else { playerMoving = false; } //Stop the player from moving when velocity is 0 if ((moveHorizontal < 0.1f && moveHorizontal > -0.1f) || (moveVertical < 0.1F && moveVertical > -0.1f)) { playerBody.velocity = new Vector2(moveHorizontal * moveSpeed, moveVertical * moveSpeed); } }
/* Might add these at some point -- these are the ones that would allow partial rescans by resetting values starting at the changed cell(s). * 1) Search outward from the given changed cell(s) as long as you can keep jumping to a cell with HIGHER total cost. This set of cells represents * all the cells which might have been influenced by the changed cell(s). * 2) Note where this search stopped: Each of the cells adjacent to this set (but not part of it) will be the frontier for the rescan. * 3) Reset the value of each cell in this set to Unexplored. * 3) Rescan the map from the frontier. * (If any of the changed cells could be sources, that needs to be handled too.) * public void Rescan(Point changedCell){ } * public void Rescan(IEnumerable<Point> changedCells){ }*/ private void RescanInternal() // Differs from ScanInternal in how it uses the frontier { while (frontier.Count > 0) { Point current = frontier.Dequeue(); foreach (Dir8 dir in EightDirections.Enumerate(true, false, false)) { Point neighbor = current.PointInDir(dir); if (!neighbor.ExistsOnMap()) { continue; } if (this[neighbor] == Blocked) { continue; } int neighborCost = GetCellCost(neighbor); if (neighborCost < 0) { if (this[neighbor] == Unexplored) { frontier.TryRemove(neighbor); // (Not sure this can happen on a rescan if done correctly) this[neighbor] = Blocked; } } else { int totalCost = this[current] + neighborCost; if (this[neighbor] > totalCost) { // Remove them before changing sort values, so the sort doesn't break: if (this[neighbor] != Unexplored) { frontier.TryRemove(neighbor); } this[neighbor] = totalCost; frontier.Enqueue(neighbor, totalCost); } } } } }
/// <summary> /// Takes in one of the eight directions a unit in the game can /// be facing (EightDirections) and returns the vector of approx. magnitude /// 1 that would correspond to that direction passed in. /// </summary> /// <returns>The orientation vector.</returns> /// <param name="orientation">Orientation.</param> public Vector2 GetOrientationVector(EightDirections orientation) { Vector2 dir = Vector2.zero; switch (orientation) { case EightDirections.North: dir = Vector2.up; break; case EightDirections.NorthEast: dir = new Vector2(.707f, .707f); break; case EightDirections.East: dir = Vector2.right; break; case EightDirections.SouthEast: dir = new Vector2(.707f, -.707f); break; case EightDirections.South: dir = Vector2.down; break; case EightDirections.SouthWest: dir = new Vector2(-.707f, -.707f); break; case EightDirections.West: dir = Vector2.left; break; case EightDirections.NorthWest: dir = new Vector2(-.707f, .707f); break; } return(dir); }
//Deactivates collider corresponding to the direction // the player is facing private void DeactivateCorrespondingCollider(EightDirections dir) { switch (dir) { case EightDirections.North: //.Log ("NORTH COLLIDER"); shieldColliderUp.enabled = false; break; case EightDirections.NorthEast: break; case EightDirections.East: //Debug.Log ("EAST COLLIDER"); shieldColliderRight.enabled = false; break; case EightDirections.SouthEast: break; case EightDirections.South: shieldColliderDown.enabled = false; break; case EightDirections.SouthWest: break; case EightDirections.West: shieldColliderLeft.enabled = false; break; case EightDirections.NorthWest: break; } }
//Activates collider corresponding to the direction // the player is facing //NOTE: Writing 2 functions for enabling and disabling // instead of just flipping the value just to be safe private void ActivateCorrespondingCollider(EightDirections dir) { switch (dir) { case EightDirections.North: shieldColliderUp.enabled = true; break; case EightDirections.NorthEast: break; case EightDirections.East: shieldColliderRight.enabled = true; break; case EightDirections.SouthEast: break; case EightDirections.South: shieldColliderDown.enabled = true; break; case EightDirections.SouthWest: break; case EightDirections.West: shieldColliderLeft.enabled = true; break; case EightDirections.NorthWest: break; } }
//To be used by other classes when they update the last move (like Attacks) public void UpdateLastMove(Vector2 newLastMove) { lastMove = newLastMove; playerOrientation = orientationSystem.DetermineDirectionFromVector(lastMove); }