I'm assuming you are using two different cameras (as you probably should).
If so, then the script below should work for what you want.
Attach this script to the player (or any gameobject that is always active in your scene). Then be sure to assign the cameras to the script from the inspector.
When you are switching cameras, particularly from the other cam to the first-person cam, the FirstPersonCam script is already active so it is going to react to mouse movements immediately. It has to be deactivated, then slerp, then activated when the interpolation is completed. Also, when the script is deactivated, the angles need to be reset so it transitions to a clean state looking straight ahead.
SwitchCamera.cs
using UnityEngine;
using System.Collections.Generic;
public class SwitchCamera : MonoBehaviour {
public float slerpDuration = 1.0f;
private float slerpTime = 0.0f;
public List<Camera> cameras;
private bool interpolating = false;
private Vector3 oldPosition;
private Quaternion oldRotation;
private Vector3 newPosition;
private Quaternion newRotation;
void OnEnable() {
if ((cameras == null) || (cameras.Count < 2)) {
Debug.LogError("At least two cameras must be added to the 'cameras' list.");
}
}
void Update() {
if (!interpolating && Input.GetMouseButtonUp(1)) {
Camera oldCamera = Camera.main;
Camera newCamera;
int next = cameras.IndexOf(oldCamera);
if (++next >= cameras.Count) { next = 0; }
newCamera = cameras[next];
oldCamera.enabled = false;
newCamera.enabled = true;
EnableFirstPersonCam(false);
oldPosition = oldCamera.transform.position;
oldRotation = oldCamera.transform.rotation;
newPosition = newCamera.transform.position;
newRotation = newCamera.transform.rotation;
newCamera.transform.position = oldCamera.transform.position;
newCamera.transform.rotation = oldCamera.transform.rotation;
interpolating = true;
slerpTime = 0.0f;
} else if (interpolating) {
if (slerpTime < slerpDuration) {
slerpTime += Time.deltaTime;
Camera.main.transform.position = Vector3.Slerp(oldPosition, newPosition, slerpTime);
Camera.main.transform.rotation = Quaternion.Slerp(oldRotation, newRotation, slerpTime);
} else {
interpolating = false;
EnableFirstPersonCam(true);
}
}
}
private void EnableFirstPersonCam(bool enabled) {
FirstPersonCam fpc = Camera.main.GetComponent<FirstPersonCam>();
if (fpc != null) { fpc.enabled = enabled; }
}
}
I also had to add an OnDisable event to the FirstPersonCam script.
(I changed the code a bit, but other than the OnDisable() and the addition of support for Roll), it is the same. Roll is not actually used, since the roll speed is 0.0f;
FirstPersonCam.cs
using UnityEngine;
using System.Collections;
public class FirstPersonCam : MonoBehaviour {
public Vector3 defaultAngles = new Vector3(0.0f, 0.0f, 0.0f); // pitch, yaw, roll in degrees (euler)
public Vector3 rotationSpeed = new Vector3(-2.0f, +2.0f, +0.0f); // pitch, yaw, roll (degrees per update)
private Vector3 currentAngles;
void OnDisable() {
currentAngles = defaultAngles;
transform.eulerAngles = currentAngles;
}
// Update is called once per frame
void Update () {
currentAngles.x += rotationSpeed.x * Input.GetAxis("Mouse Y"); // pitch
currentAngles.y += rotationSpeed.y * Input.GetAxis("Mouse X"); // yaw
currentAngles.z += rotationSpeed.z * Input.GetAxis("Mouse ScrollWheel"); // roll
transform.eulerAngles = currentAngles;
}
}
PS. The SwitchCamera script actually cycles between all cameras in the list, so if you have more than 2, it will transition to the next camera in the list.