Reputation: 11
I'm making an endless runner like game where very in mechanics to android IronMan game. The player will be flying straight along the course and will be able to move left, right, up and down. I managed to split the screen in to 9 even sections and implement a little control system that recognizes where the player is and where he want's to move and if he/she is allowed to move there and I managed to get the player to move to desired location on the screen but instead of gradually travelling from one point to another the Game object just snaps from one position to another. Please find below my code for moving in one direction:
public class PlayerControl : MonoBehaviour
{
// Declare Control Input
public KeyCode moveL;
public KeyCode moveR;
public KeyCode moveU;
public KeyCode moveD;
// Set movement distance
private float verticalIncrement = 3.0f;
private float horizontalIncrement = 5.0f;
// Set initial internal position of the craft
private int laneNum = 1;
private int rowNum = 1;
// Declare player Game object
GameObject spaceCraft;
// Set input lock
bool pressLockOn = false;
// Use this for initialization
void Start()
{
spaceCraft = GameObject.FindGameObjectWithTag("Player");
}
// Update is called once per frame
void Update()
{
if (Input.GetKeyDown(moveR))
{
if (laneNum < 2)
{
// Retrieve craft current position coordinates
float craftPositionX = spaceCraft.transform.localPosition.x;
float craftPositionY = spaceCraft.transform.localPosition.y;
// Save craft's desired position coordinates as string for comparison
string newCraftPositionString = (craftPositionX + horizontalIncrement) + "" + craftPositionY;
// Declare target box position coordinates for comparison
string targetPositionString = null;
// Find desired target box based on player's location and button pressed
for (int i = 0; i < Initialization.positionCubesArray.Length; i++)
{
for (int j = 0; j < Initialization.positionCubesArray[i].Length; j++)
{
// Declare temp GameObject to store desired target box
GameObject target = Initialization.positionCubesArray[i][j];
// Retrieve target box location coordinates
float boxPosX = target.GetComponent<Transform>().localPosition.x;
float boxPosY = target.GetComponent<Transform>().localPosition.y;
// Save target box's coordinates as string for comparison
boxPositionString = boxPosX + "" + boxPosY;
// Check if craft's desired position matches found target
if (newCraftPositionString.Equals(targetPositionString))
{
// Set input lock on
pressLockOn = true;
// Move player's craft to desired location
spaceCraft.transform.localPosition = Vector3.Lerp(spaceCraft.transform.localPosition, target.transform.localPosition, 1f);
// Start coroutine to delay input lock for half a second
StartCoroutine(stopTime(0.5f));
// Check if craft traveled to desired location
if ((craftPositionX + "" + craftPositionY).Equals(newCraftPositionString) )
{
// Update internal position of the craft
laneNum++;
}
}
}
}
}
}
...
}
IEnumerator stopTime(float amount)
{
yield return new WaitForSeconds(amount);
pressLockOn = false;
}
I've also tried with another approach following this tutorial:
https://www.youtube.com/watch?v=Zb7Th_H7bvw
But it wouldn't work either and wouldn't move my player at all as the journey fraction would always equal to 0. I also tried exporting the moving object logic out of the loop but with no effect either. Please find below updated code:
// Update is called once per frame
void Update()
{
if (Input.GetKeyDown(moveR))
{
if (laneNum < 2)
{
// Declare target Dame object
GameObject target;
// Retrieve craft position coordinates
float craftPositionX = spaceCraft.transform.localPosition.x;
float craftPositionY = spaceCraft.transform.localPosition.y;
// Retrieve desired craft's postiotn
string newCraftPositionString = (craftPositionX + horizontalIncrement) + "" + craftPositionY;
// Declare target box string for comparison
string boxPositionString = null;
// Declare initial temp i and j to export target game object from the loops
int tempI = 0;
int tempJ = 0;
// Search for target game objects in 2D array
for (int i = 0; i < Initialization.positionCubesArray.Length; i++)
{
// Setup found target flag
bool foundTarget = false;
for (int j = 0; j < Initialization.positionCubesArray[i].Length; j++)
{
// Retrieve each target's coordinates
float boxPosX = Initialization.positionCubesArray[i][j].GetComponent<Transform>().localPosition.x;
float boxPosY = Initialization.positionCubesArray[i][j].GetComponent<Transform>().localPosition.y;
// Target coordinates string for comparison
boxPositionString = boxPosX + "" + boxPosY;
// Check if target's coordinates matches desired location's coordinates
if (newCraftPositionString.Equals(boxPositionString))
{
// Set temp i and j to export found target out off the loop
tempI = i;
tempJ = j;
print("Found Target\n " + tempI + " " + tempJ);
print("Target Postion: " + boxPositionString);
// Set found target flag to true
foundTarget = true;
// Break inner loop
break;
}
}
// Break outter loop
if (foundTarget)
{
break;
}
}
print("New Crafft Position: " + newCraftPositionString + "\nTarget Position: " + boxPositionString);
// Again chack if target's coordinates matches desired location's coordinates
if (newCraftPositionString.Equals(boxPositionString))
{
// Retrieve found target from 2D array with temp i and j found in 2D for-loop
target = Initialization.positionCubesArray[tempI][tempJ];
// Set input lock on
pressLockOn = true;
float startTime = Time.time;
float totalDistance = Vector3.Distance(spaceCraft.transform.localPosition, target.transform.localPosition);
float currentDuration = Time.time - startTime;
float journeyFraction = currentDuration / totalDistance;
print("Start time: " + startTime + " | Total Distance: " + totalDistance
+ "\nCurrent Duration: " + currentDuration + " | Journey fraction: " + journeyFraction);
spaceCraft.transform.localPosition = Vector3.Lerp(spaceCraft.transform.localPosition, target.transform.localPosition, journeyFraction);
// Start coroutine to delay input lock
StartCoroutine(stopTime(0.5f));
// Update internal craft coordinates
if ((craftPositionX + "" + craftPositionY).Equals(newCraftPositionString))
{
laneNum++;
}
}
}
}
I've also tried moving startTime variable to Start method and currentDuration time to the start of the update method like in the tutorial and my player would move but not into desired position, it would only move very slightly but never reach the target and it would crash the whole moving "system".
Upvotes: 0
Views: 1615
Reputation: 11
Ok, I fixed it and it's working. The code is a lot more clear now as well. The issue had to do with fact that I was pressing the button and the position was only being updated once. The code responsible for calling the Lerp
method wasn't being called in the update method anymore.
Upvotes: 1
Reputation: 15151
Lerp
will interpolate two values via a factor. Per example, if you Lerp
between 0 to 20 with a factor of 0.5 the result will be 10, by 0 will be 0, by 1 will be 20 and so on.
Why I say that? Because in your code you just Lerp
with a factor of 1.0f, that will just return the final value.
If you want a smooth interpolation you must "travel" from 0 to 1 on the factor at the desired speed.
Upvotes: 2