protected override void UpdateTargetDirection(Driver.Sensors sensors, Driver.Actuators actuators) { // Read player input. float turningInput = Input.GetAxis("Turning"); if (turningInput == 0) { // If the input was just released, square to 90 degrees. if (lastTurningInput != 0) { CardinalDirection cardinalDirection = DirectionHelpers.GetCardinalDirectionForVector(sensors.transform.forward); actuators.targetDirection = DirectionHelpers.cardinalDirectionVectors[cardinalDirection]; // Reset turning input time for next time. turningInputNonZeroTime = 0; } } else { // If the input was just changed, change lane. if (turningInput < 0 && lastTurningInput >= 0) { // We want to go left, but if our current target was to go right, just return to current lane. if (actuators.targetLane > sensors.carTracker.currentLane) { actuators.targetLane = sensors.carTracker.currentLane; } else { actuators.targetLane = Math.Max(sensors.carTracker.currentLane - 1, 0); } } else if (turningInput > 0 && lastTurningInput <= 0) { // We want to go right, but if our current target was to go left, just return to current lane. if (actuators.targetLane < sensors.carTracker.currentLane) { actuators.targetLane = sensors.carTracker.currentLane; } else { actuators.targetLane = Math.Min(sensors.carTracker.currentLane + 1, sensors.carTracker.representativeStreet.lanesCount + 1); } } // If turning has been active enough time, change target direction. turningInputNonZeroTime += Time.deltaTime; if (turningInputNonZeroTime > laneChangeOnlyDuration) { float rotationAngleDegrees = turningInput * maxAngleChangeDifferenceDegrees * Mathf.Sign(sensors.car.speed); Quaternion rotation = Quaternion.Euler(0, rotationAngleDegrees, 0); actuators.targetDirection = rotation * sensors.transform.forward; } } lastTurningInput = turningInput; }
public static CardinalDirection GetCardinalDirection(this Vector3 vector) { return(DirectionHelpers.GetCardinalDirectionForVector(vector)); }
protected virtual void UpdateTargetDirection(Driver.Sensors sensors, Driver.Actuators actuators) { float turningInput = Input.GetAxis("Turning"); bool performTurn = false; if (Input.GetButtonDown("Turning")) { // See if the turn button is down. if (Input.GetButton("Turn")) { // We want to make a turn. performTurn = true; } else { // Turn button is not down, so do a lane switch. if (turningInput < 0) { // We want to go left, but if our current target was to go right, just return to current lane. if (actuators.targetLane > sensors.carTracker.currentLane) { actuators.targetLane = sensors.carTracker.currentLane; } else { actuators.targetLane = Math.Max(sensors.carTracker.currentLane - 1, 0); } } else { // We want to go right, but if our current target was to go left, just return to current lane. if (actuators.targetLane < sensors.carTracker.currentLane) { actuators.targetLane = sensors.carTracker.currentLane; } else { actuators.targetLane = Math.Min(sensors.carTracker.currentLane + 1, sensors.carTracker.representativeStreet.lanesCount + 1); } } } } // If turn button is pressed and we have a direction, we should turn. if (Input.GetButtonDown("Turn") && turningInput != 0) { performTurn = true; } // Perform the turn if controls dictated it. if (performTurn) { // When going backwards, turning needs to be reversed. if (sensors.car.speed < 0) { turningInput *= -1; } // Determine to which side we're currently turning. Vector3 forward = sensors.car.transform.forward; Quaternion currentTargetDelta = Quaternion.FromToRotation(forward, actuators.targetDirection); // Use delta angle to wrap the angle to -180..180 range. float currentTargetDeltaAngle = Mathf.DeltaAngle(0, currentTargetDelta.eulerAngles.y); Vector3 newDirection; if (turningInput < 0) { // We want to go left, but if our current target was to go right, just return to current direction. if (currentTargetDeltaAngle > 45) { newDirection = forward; } else { newDirection = Quaternion.Euler(0, -90, 0) * forward; } } else { // We want to go right, but if our current target was to go left, just return to current direction. if (currentTargetDeltaAngle < -45) { newDirection = forward; } else { newDirection = Quaternion.Euler(0, 90, 0) * forward; } } // Square rotation to 90 degrees. CardinalDirection cardinalDirection = DirectionHelpers.GetCardinalDirectionForVector(newDirection); actuators.targetDirection = DirectionHelpers.cardinalDirectionVectors[cardinalDirection]; } }