- Home /
Link Input.acceleration to camera
I am building a tilt type game based on the Roller Ball tutorial. I have a camera which "smooth" follows the ball. My problem is tilting of the phone is linked to the stage not the camera. If the camera rotates 180 around the ball the tilt controls are opposite, tilt left and the ball moves to the right. The tilt doesn't update with the camera. This makes control of the ball imposable.
How can I have the tilting linked to the camera view and not the scene.
Here is the code
public var force:float = 1.0; public var simulateAccelerometer:boolean = false;
function FixedUpdate () {
print camera.transform.rotation();
var dir : Vector3 = Vector3.zero;
if (simulateAccelerometer) { // using joystick input instead of iPhone accelerometer dir.x = Input.GetAxis("Horizontal"); dir.z = Input.GetAxis("Vertical"); } else { // we assume that device is held parallel to the ground // and Home button is in the right hand
// remap device acceleration axis to game coordinates
// 1) XY plane of the device is mapped onto XZ plane
// 2) rotated 90 degrees around Y axis
dir.x = -Input.acceleration.y;
dir.z = Input.acceleration.x;
// clamp acceleration vector to unit sphere
if (dir.sqrMagnitude > 1)
dir.Normalize();
}
rigidbody.AddForce(dir * force); }
Thanks
Answer by Statement · Apr 04, 2011 at 01:12 PM
Try to transform the input direction relative to the camera:
dir = Camera.main.transform.TransformDirection(dir);
rigidbody.AddForce(dir * force);
Alternatively if you want to ignore any height slope:
var lookAt = transform.position - Camera.main.transform.position; lookAt.y = 0;
var rotation = Quaternion.LookRotation(lookAt); rigidbody.AddForce(rotation dir force);
// Complete test script that I successfully tested with. var force = 5.0f; function FixedUpdate () { var dir : Vector3 = Vector3.zero; dir.x = Input.GetAxis("Horizontal"); dir.z = Input.GetAxis("Vertical");
var lookAt = transform.position - Camera.main.transform.position;
lookAt.y = 0;
var rotation = Quaternion.LookRotation(lookAt);
rigidbody.AddForce(rotation * dir * force);
}
Answer by McBuff · Mar 22, 2011 at 12:56 PM
So you have ported the tilting over to the unity scene? Then you're halfway there.
Right now your tilt is registered in World coordinates ( the coordinates relative to (0,0,0) of your scene).
I assume you know what is causing your problem so yo need to know how the phone is tilted relative to the camera.
That means you need to convert the tilt of the phone from being relative to the scene to being relative to your camera ( local coordinates).
This might seem complex but it's actually pretty easy to implement.
First, get yourself the transform component of your camera.
get the transform's WorldToLocal Matrix. ( no worries, you don't need to understand how it works ). Then multiply your tilt VECTOR with the matrix.
You'll end up with something like this.
Transform cameraTransform; //todo: get camera transform Vector3 dir = Vector3.zero; dir.x = -Input.acceleration.y; dir.z = Input.acceleration.x;
Matrix4x4 worldToLocal = cameraTransform.worldToLocalMatrix; Vector3 localTilt = worldToLocal.MultiplyVector(dir);
localtilt will now contain a tilt value that is relative to your camera position & angle.
Hope this helps!
Thanks for this, but I am getting an error on these lines: "Assets/Scripts/Controller2.js(30,18): UCE0001: ';' expected. Insert a semicolon at the end. on these two lines: $$anonymous$$atrix4x4 worldToLocal = cameraTransform.worldToLocal$$anonymous$$atrix; and Vector3 localTilt = worldToLocal.$$anonymous$$ultiplyVector(dir); Richard 0 secs ago
That's because it is C# code $$anonymous$$cBuff posted.
If you make a complete script for device.it really helpful for us. Thanks