- Home /
[Solved]Make Object face correct direction
Hi,
I'm sure this is elementary for the wizards reading this, but I've searched and searched and I just can't implement it with my set up. I have a 2D game, with an isometric camera. I have a cube with only 1 side textured facing the camera. The cube is hit (its a golf ball) and flies off in a random direction depending on the wind strength - but it always faces up, even if the ball is curving off to the west, so I wanted it to check the direction it was flying in and face that and update each frame during flight.
This is my code so far:
#pragma strict
internal var ballHeight : float;
var power : float = 100.0;
var height : float = 80.0;
var windx : float;
var windy : float;
var windSpeed : float;
function Update () {
if (Input.GetButtonUp("Fire1")){
hitball();
}
rigidbody.AddForce(Vector3.right * windSpeed, ForceMode.Acceleration);
//change size of sprite on height
ballHeight = transform.position.z;
transform.localScale = Vector3(ballHeight / 3 + 2,ballHeight / 3 + 2,ballHeight / 3 + 2);
//change rotation to match direction (add if statement to be above height of 10 else look straight)
transform.rotation = Quaternion.LookRotation(rigidbody.velocity);
}
function hitball() {
windSpeed = Random.Range(-15.0, 15.0);
rigidbody.AddForce(Vector3(windx,power,height + windy));
}
It almost works, but it spins the cube so that the isometric camera can no longer see it. This is a top down golf game, but I have set the gravity on Z so that the golf hole is actually 'stood' up in the scene.
I must have tried about 10 different bits of code 'tweaked' alas getting nowhere, and I'm sure this is such a SIMPLE thing - that I'm just to new to understand.
Any help appreciated.
Korpers.
Answer by robertbu · Aug 27, 2013 at 03:53 PM
It may be a simple thing to fix, but I'm having a heck of a time visualizing how everything is put together, so I'm unclear about what is causing the problem. Let me give you two things to try. If they don't work, then you'll need to give me a more detailed description of how everything is put together. Things such as which face of the cube is textured and how the ball moves in the 2D space.
1) Look rotation takes an optional second parameter for the up vector. By default it is Vector3.up. You can try specifying other axes for this second parameter.
2) Look rotation assumes you want the positive 'Z' direction of the object is the one you want facing the specified vector. If the issue is that the 'textured' face of the ball faces the wrong direction if the ball is facing the direction of movement then you can combine rotations. Insert on line 26:
transform.rotation = transform.rotation * Quaternion.Euler(90,0,0);
Where 'Quaternion.Euler(90,0,0)' is a placeholder for some rotation specific to your game.
Apologies Robert, yes it does sound a bit skew whiff. I'll try and explain again.
It is a 2D game of golf. Top down birds eye view. However, I have (stupidly or correctly, I'm not sure) - set it up as a traditional side scroller. So the camera looks forwards and the terrain (it is not a terrain object, it is simply a cube with my golf hole layout graphics on it) is in front of the camera faceing upwards. So the Tee off area is at the bottom of the screen and the green is at the top.
I have changed the gravity from Y -9 in the global physics menu - to Z -9, so that when the ball is hit it travels up and towards the screen, and then the gravity pulls it back to the golf hole.
The golf 'ball' is just a cube with a sprite attached to it. I only use the cube as an invisible collision detector. The sprite faces the camera at all times and must only rotate on the Z axis, absolutely not the Y or X as it then rotates away from the camera and goes a skew perspective.
I have a script on the ball that gives it a forwards momentum with a slight deviation left or right depending on the wind strength. The cube does fly in the correct direction, but it never rotates on the Z axis which of course looks wrong.
I have tried both your suggestions and neither have worked - though they ARE turning the cube at least. I also tried putting the '90' on the Quaternion.Euler in all three axis - none worked correctly.
Is this a bit more clear - I know whats co$$anonymous$$g.....you're going to tell me to lay it flat like a table aren't you?
What do you reckon? Thanks again for your help.
This information helps. I'm still unclear about the natural orientation of the plane (i.e.) where it faces with a rotation of (0,0,0), the natural orientation of the cube, and what direction on the plane do you want to aim to the direction the ball is moving. I assume the plane is a child of the cube. Note you could just have a plane with a box collider ins$$anonymous$$d of having two objects.
I see two approaches to the problem. Without the information above, I cannot give you specific code. The first is to adjust the point used to calculate the rotation. Depending on how you are using it, you would set the 'y' to either 0 or to the transform.position.y of the plane. Let me assume the plane is on the back of the cube, and that forward is the local Vector3.right. This might do what you are looking to do:
var v = rigidbody.velocity;
v.y = 0;
if (v != Vector3.zero) {
var q = Quaternion.FromToRotation(transform.right, v);
transform.rotation = q * transform.rotation;
}
Assu$$anonymous$$g the plane is a child of the cube, the other solution is to just rotate the child so that it is always facing up regardless of the angle of the cube. You may want to do this in LateUpdate():
var q = Quaternion.FromToRotation(transform.up, Vector3.up);
transform.rotation = q * transform.rotation;
Hi robert, I have since rotated the entire scene so that now the golf course is lying nice and horizontal - and the gravity is set back to the Y axis. So everything is quite normal now - not sure why I did it the other way - I think I read it was a correct set up for a 2D game, but that game happened to be a platformer!
All normal now anyway - will your script still work in it's current format?
Also - to answer your queries above: the 'plane' is the golf course and is simply a large cube - the 'ball' is also a cube (albeit a much smaller one) and is not a parent / child of the 'plane' (golf course), they are separate entities.
With a rotation of 0,0,0 on BOTH objects - they are both now lying horizontally flat. With the golf ball waiting to have add.force applied to it to then fire off down the course plane on the Z axis.
I have a random wind modifier that is applied on striking the ball that adds a little X value to the ball (positive or negative) meaning the ball veers left or right. When this happens I want the ball cube to rotate on it's Y axis to face the direction it is veering towards.
I hope that clears it up - sorry for flipping my scene about and making a confusing mess out of what seems to be a simple issue!
Ok Robert, I implemented your code in the comments here and it worked a treat (after I put my axis and gravity all back in the right direction).
Thanks for helping me with this. I'm sure I'll be back when I hit my next brick wall.
Answer by Partel-Lang · Aug 28, 2013 at 06:51 AM
You dont need all this Quaternion madness.
You can just directly set an axis of your golf ball to whatever direction you need:
transform.right = rigidbody.velocity;
transform.forward = Vector3.forward;
This would keep the local X axis directed at the velocity and always make sure the local Z axis is directed towards world Z that is the direction to your camera.
Cheers, Pärtel
Thanks Pärtel, - this would be wonderfully simple if I knew how to implement it. I have tried putting it in the update function - but I can't see anywhere in your lines that talks about the rotation of the object?
Those two line are rotating the object. The first line rotates the object so that it's right (red) axis faces towards the direction of the velocity, the second line rotates the object so that it's forward (blue) axis faces the global blue axis. You need to place it inside the Update() function and remove any other line that is rotating the object.
@Partel - I forget that you can assign the transform directions. This would have been a simple solution. Since I did not get a clear idea of his setup, it is unclear that the exact recipe you've listed would work, but in concept it is much simpler. +1.