- Home /
Camera that sits behind player
Hi Everyone,
I'm trying to find a way to have a camera follow the player but sit behind them whilst able to rotate with the player. Dragon Age style camera wouldn't be too far from the mark..
So far, I've tried lookAt style scripts with no Avail.. They automatically try and pin to the top even with a Vector3 offset, if I use transfom.position = target.position instead of LookAt it snaps to the player and won't rotate with the player around the world. Attaching the camera with a click to move player end's in a continuous spin. I've tried pretty much most of the scripts out of the Unit Script Wiki bank.
public Transform target;
public Vector3 destination;
public Vector3 offset = new Vector3 (0,0,0);
Camera.main.transform.position = target.position + offset;
The above seems to be a good starting point, I now need to get it to rotate with the player. Whilst making sure the camera continues to sit behind the player.
I cannot figure out what you are asking for here. It sounds like it is what you get if you take the camera, place it behind the character, and make the camera a child of the character. It is helpful when you make a video game reference to find a video that displays the behavior and list the video and a time offset within the video.
Here is some code that is equivalent to setting the camera behind the character and making the camera a child:
Camera.main.transform.position = transform.position - transform.forward * dist;
Camera.main.transform.LookAt(transform);
Where 'dist' is the following distance.
Thanks Rob, that script caused the camera to fly off the plane:
Here is what I'm talking about link text
Assu$$anonymous$$g 'transform' is the transform of the player, and your player is walking around on the XZ plane, I see no way the above code could cause the camera to fly off the plane. Check to see what other scripts you might have that are impacting the camera position.
Watching the video was confusing. Sometimes the camera followed the player from the back. Sometimes it did not. Sometimes the camera rotated up for an overhead view. As a guess I would say that there is a script that wants to follow the player, but it also allows the player to rotate the camera around the player. When the player is manipulating the camera it stays where the player puts it. Once the controls are released, the camera returns to "home position" (i.e. from the back). But this is only a guess.
In order to get some feedback, if you haven't already, I'd like you to try the standard smooth follow script. You can get it by:
Assets>Import Package>Scripts
It will be one of the scripts that is imported. It attaches to the camera, and with the camera selected in the hierarchy you must drag and drop your target onto 'target' in the script. $$anonymous$$ake sure any other scripts that are manipulating the camera are disabled or removed.
There has to be some way to do it
The problem is that I have no idea what 'it' is. $$anonymous$$aking the camera a child, my couple of lines above, and the smooth follow script all do some form of what you describe. If they are working but are not what you want, then we need a better description of what you want to do, and you can use the behavior of these scripts to compare and contrast. If they are not working, then maybe you should experiment apart from your app first to figure things out, and then work to integrate the technology. For example:
Create a new scene
Create a plane
Create a capsule on the plane
Add a CC to the capsule
Add a script to the capsule to drive the CC. The one in the reference in for CharacterController.$$anonymous$$ove().
Add the SmoothFollow script to camera
$$anonymous$$ake the character a target
Take it out for a test run.
Answer by shavais · Oct 13, 2013 at 12:06 AM
Are you trying to do a mouse orbit? Such that you can right click, and drag the camera up and down, and left and right around the character, while it'll stay looking at the character? Maybe something like this would work:
Parent the camera to the player, so it's position is relative to the player.
Put a script on the camera that has distance, hAngle (horizontal), and vAngle (vertical) float variables.
In that script, in Update(), set the transform position based on those variables, and update the forward vector so that it points that the player.
In that script, in OnGUI() look at the event and if it is a mouse event, get the mouse position, and subtract off the previously sampled position (if it wasn't 0,0), and increase or decrease your angle variables accordingly. (Don't forget that the angles are in radians, not that that really matters in this situation.)
If your character is walking on the X,Z plane, so that increasing Y is "up", then try this:
in Update() ..
// position the camera at a certain distance, horizontal angle and vertical angle from the player
transform.position = distance * (new Vector3(
Mathf.Cos(hAngle),
Mathf.Sin(vAngle),
Mathf.Sin(hAngle)
));
// make the camara look directly at the player
transform.forward = player.transform.position - transform.position;
Actually come to think of it, if the player is the camera's parent, and the position of the camera is relative to the player, the player should always be at 0,0,0 in the camera's reference frame, so you might have to set the forward vector to -1 * transform.position.normalized. That is,
transform.forward = -1 * transform.position.normalized;
That should make the camera point at 0,0,0 in its reference frame, which I would think would be where the player is, if the player is the parent of the camera.
Your solution doesn't work. It places my camera miles away from my player and the controls are fudgy... :(
Thundersoul:
What value did you use for distance? If the camera has the player's avatar as its parent in the scene, it should move and rotate with the avatar as though it were part of the avatar. If it doesn't, something's fishy.
But I'm not sure fixing the camera onto the avatar is desirable, actually -
I think if I were to do this today, I would not make the camera part of the avatar, ins$$anonymous$$d I would give it a world position that was near the avatar and point it at a spot that was a configurable distance over the avatar's head, and then orbit the camera around that spot when the player right clicked and dragged the mouse (the exact math for which would take some iterative tweaking to get right, for sure), and then make it sort of get dragged around by the avatar as the avatar moved around. The update would (if the player wasn't right clicking and dragging) move the camera directly toward a spot that was another configurable distance above avatar's head or directly away from that spot in order to maintain a fixed distance from the avatar while still being above it. The effect should cause it to fairly quickly swing behind and above the avatar as they move forward. I might end up putting a bit of adjusting math in based on the angle of the player's motion (around the vertical axis relative to one of the horizontal ones) in order to sort of optimize that swing. If the player is moving backwards, I might move it with the same movement vector as the avatar so it would move with the avatar without swinging in front it. (And I might do that if the player was clicking and dragging, too, so the swinging affect would not compete with the orbiting being done for the mouse.)
Sometimes when I attempt a solution that should definitely work in theory, I have trouble getting it to work in Unity the way I'd expect it to, and I have trouble explaining why, until I find some little bug in my code or some configuration flag or switch that affects the physics engine or the way things are being rendered that I had no idea existed. Like any good, living SD$$anonymous$$, Unity is kind of a moving target.
(And then of course there are those way-too-frequent times when some little bug in my code lasts for days or weeks or months and makes me $$anonymous$$r my hair and lose my will to live until I finally find it and then I feel like something far, far stupider than a moron and I want to shoot myself. I was stuck for the last four days, for example, because of what turned out to be a @#$% typo. I think other developers must be light years smarter than I am if they manage to do it for long without committing suicide.)
I'm a bit puzzled on the OnGUI part. i got the void function there but i'm not too sure how to do the rest. Help?
Answer by $$anonymous$$ · Oct 12, 2013 at 11:51 PM
I'm nearly there, attach camera to main player.. Found a script that I modified extensively to figure out exactly what I need out of the quaternion rotations:
Just need to clamp certain angles and maybe add a zoom.. When making a game start from 0.0.0!! Causes a nightmare otherwise.
public Transform target;
float x = 0.0f;
float y = 0.0f;
public float walkDistance;
public bool camButtonDown;
public float runDistance;
public float height;
public float xSpeed = 250.0f;
public float ySpeed = 120.0f;
// Use this for initialization
void Start () {
var player = GameObject.FindWithTag("Player");
target = player.transform;
//Vector3 angles = transform.eulerAngles;
//x = angles.y;
//y = angles.x;
}
// Update is called once per frame
void Update () {
if(Input.GetMouseButtonDown(1)) { //Use the Input Manager to make this user selectable button
camButtonDown = true;
}
if(Input.GetMouseButtonUp(1)) {
camButtonDown = false;
}
}
void LateUpdate(){
if(camButtonDown) {
x += Input.GetAxis("Mouse X") * xSpeed * 0.02f;
y -= Input.GetAxis("Mouse Y") * ySpeed * 0.02f;
// y = ClamAngle(y, yMinLimit, yMaxLimit);
Quaternion rotation = Quaternion.Euler(y, x, 0);
target.rotation = rotation;
}
else {
target.position = new Vector3(target.position.x, target.position.y + height, target.position.z - walkDistance);
target.LookAt(target);
x = 0;
y = 0;
}
}
}
Your answer
Follow this Question
Related Questions
Runescape Camera Rotation? 0 Answers
Replicate rotation of Camera 1 Answer
Camera following Pivot not working 1 Answer
Camera following/looking at aircraft 1 Answer
How to freeze rotation of the camera 1 Answer