- Home /
iOS Gyroscope in Unity 4
Hi everyone, I am in the process of porting my Unity 3.5 game to Unity 4, and can't get the gyroscope to work. Here is my (well, the FOV2GO teams) code:
* URL: http://diy.mxrlab.com/ * Please direct any bugs/comments/suggestions to hoberman@usc.edu.
* Stereoskopix FOV2GO for Unity Copyright (c) 2011-12 Perry Hoberman & MxR Lab. All rights reserved.
*/
/* Gyroscope-controlled camera for iPhone & Android revised 5.12.12
* Usage: Attach this script to main camera.
* Note: Unity Remote does not currently support gyroscope.
* This script uses three techniques to get the correct orientation out of the gyroscope attitude:
1. creates a parent transform (camParent) and rotates it with eulerAngles
2. for Android (Samsung Galaxy Nexus) only: remaps gyro.Attitude quaternion values from xyzw to wxyz (quatMap)
3. multiplies attitude quaternion by quaternion quatMult
* Also creates a grandparent (camGrandparent) which can be rotated to change heading
* This node allows an arbitrary heading to be added to the gyroscope reading
so that the virtual camera can be facing any direction in the scene, no matter which way the phone is actually facing
* Option for direct touch input - horizontal swipe controls heading (leave OFF if using s3dRotateHeading.js)
* Note: As of Unity 3.5.2: for correct operation, in Player Settings, Default Rotation has to be set to Auto Rotation
* So this script checks (once per second) if screen orientation has changed while running
*/
#pragma strict
static var gyroBool : boolean = false;
private var gyro : Gyroscope;
private var compass : Compass;
private var quatMult : Quaternion;
private var quatMap : Quaternion;
private var prevScreenOrientation: ScreenOrientation;
// camera grandparent node to rotate heading
private var camParent: GameObject;
private var camGrandparent : GameObject;
public var heading : float = 0;
public var Pitch : float = 0;
public var setZeroToNorth : boolean = true;
// mouse/touch input
public var touchRotatesHeading : boolean;
private var headingAtTouchStart : float;
private var pitchAtTouchStart : float;
private var mouseStartPoint: Vector2;
private var screenSize : Vector2;
@script AddComponentMenu ("stereoskopix/s3d Gyro Cam")
function Awake() {
// find the current parent of the camera's transform
var currentParent = transform.parent;
// instantiate a new transform
camParent = new GameObject ("camParent");
// match the transform to the camera position
camParent.transform.position = transform.position;
// make the new transform the parent of the camera transform
transform.parent = camParent.transform;
// instantiate a new transform
camGrandparent = new GameObject ("camGrandParent");
// match the transform to the camera position
camGrandparent.transform.position = transform.position;
// make the new transform the grandparent of the camera transform
camParent.transform.parent = camGrandparent.transform;
// make the original parent the great grandparent of the camera transform
camGrandparent.transform.parent = currentParent;
// check whether device supports gyroscope
#if UNITY_3_4
gyroBool = Input.isGyroAvailable;
#endif
#if UNITY_3_5
gyroBool = SystemInfo.supportsGyroscope;
#endif
if (gyroBool) {
prevScreenOrientation = Screen.orientation;
gyro = Input.gyro;
gyro.enabled = true;
if (setZeroToNorth) {
compass = Input.compass;
compass.enabled = true;
}
fixScreenOrientation();
}
Screen.sleepTimeout = SleepTimeout.NeverSleep;
}
function Start() {
if (gyroBool) {
if (setZeroToNorth) {
turnToFaceNorth();
}
}
screenSize.x = Screen.width;
screenSize.y = Screen.height;
#if (UNITY_IPHONE || UNITY_ANDROID) && ! UNITY_EDITOR
InvokeRepeating("checkAutoRotation",1.0,1.0);
#endif
}
function turnToFaceNorth() {
yield WaitForSeconds(1);
heading = Input.compass.magneticHeading;
}
function Update () {
camGrandparent.transform.localEulerAngles.y = heading;
if (gyroBool) {
#if UNITY_IPHONE
quatMap = gyro.attitude;
#endif
#if UNITY_ANDROID
quatMap = Quaternion(gyro.attitude.w,gyro.attitude.x,gyro.attitude.y,gyro.attitude.z);
#endif
transform.localRotation = quatMap * quatMult;
}
if (touchRotatesHeading) {
GetTouchMouseInput();
}
camGrandparent.transform.localEulerAngles.y = heading;
// only update pitch if in Unity Editor (on device, pitch is handled by gyroscope)
#if UNITY_EDITOR
transform.localEulerAngles.x = Pitch;
#endif
}
function checkAutoRotation() {
// check if Screen.orientation has changed
if (prevScreenOrientation != Screen.orientation) {
// fix gyroscope orientation settings
fixScreenOrientation();
// also need to fix camera aspect
fixCameraAspect();
}
prevScreenOrientation = Screen.orientation;
}
function fixCameraAspect() {
var theCamera : s3dCamera;
yield WaitForSeconds(1);
theCamera = GetComponent(s3dCamera);
if (!theCamera.useStereoShader) {
if (theCamera) theCamera.fixCameraAspect();
}
}
function fixScreenOrientation() {
#if UNITY_IPHONE
camParent.transform.eulerAngles = Vector3(90,90,0);
if (Screen.orientation == ScreenOrientation.LandscapeLeft) {
quatMult = Quaternion(0,0,0.7071,0.7071);
} else if (Screen.orientation == ScreenOrientation.LandscapeRight) {
quatMult = Quaternion(0,0,-0.7071,0.7071);
} else if (Screen.orientation == ScreenOrientation.Portrait) {
quatMult = Quaternion(0,0,1,0);
} else if (Screen.orientation == ScreenOrientation.PortraitUpsideDown) {
quatMult = Quaternion(0,0,0,1);
}
#endif
#if UNITY_ANDROID
camParent.transform.eulerAngles = Vector3(-90,0,0);
if (Screen.orientation == ScreenOrientation.LandscapeLeft) {
quatMult = Quaternion(0,0,0.7071,-0.7071);
} else if (Screen.orientation == ScreenOrientation.LandscapeRight) {
quatMult = Quaternion(0,0,-0.7071,-0.7071);
} else if (Screen.orientation == ScreenOrientation.Portrait) {
quatMult = Quaternion(0,0,0,1);
} else if (Screen.orientation == ScreenOrientation.PortraitUpsideDown) {
quatMult = Quaternion(0,0,1,0);
}
#endif
}
function GetTouchMouseInput() {
if(Input.GetMouseButtonDown(0)) {
mouseStartPoint = Input.mousePosition;
headingAtTouchStart = heading;
#if UNITY_EDITOR
pitchAtTouchStart = Pitch;
#endif
} else if (Input.GetMouseButton(0)) {
var delta : Vector2;
var mousePos = Input.mousePosition;
delta.x = (mousePos.x - mouseStartPoint.x)/screenSize.x;
heading = (headingAtTouchStart+delta.x*100);
heading = heading%360;
#if UNITY_EDITOR
delta.y = (mousePos.y - mouseStartPoint.y)/screenSize.y;
Pitch = (pitchAtTouchStart+delta.y*-100);
Pitch = Mathf.Clamp(Pitch%360, -60, 60);
#endif
}
}
Any tips on getting this to work in Unity 4? Thanks!
I have the same problem with Unity4. Has anyone found a solution?
Answer by siberman · Nov 27, 2012 at 11:37 PM
Get rid of the #if UNITY_3_5 #endif around this in the Awake function.
#if UNITY_3_5
gyroBool = SystemInfo.supportsGyroscope;
#endif
Answer by peterept · Dec 10, 2012 at 04:10 AM
Does it work as exptected though? For me the screen is rotated 90 degrees around. has Unity changed the gyro orientation in Unity 4 ?
Answer by mkielczyk · Apr 19, 2013 at 07:58 AM
Looks like in Unity 4 gyro attitude has orientation fix applied, at least on android, so just get rid of the quatMult part and it should work fine.
Apparently in Unity 4.2 they removed the gyro attitude orientation fix again?? So, iOS gyro is working as in Unity 3.x? Can anybody confirm this?
What I did to work around these issues was I added GUI buttons to multiply quaternions (rotation) based on euler angles (I think the syntax is Quaternion.euler(xx,yy,zz) to be multiplied before and after the gyroscope readings.
So put twelve buttons on your screen: incrementing and decrementing the quaternion.euler(x,y,z) for x, y, and z by 90 degrees for the rotation applied to the rotation before and after the gyroscope readings.
The answer for me was a (90,90,0) Quaternion.euler multiplied to the gyro readings before and a Quaternion(0,0,1,0) to be multiplied after.
With Quaternions, order of multiplication matters. That hard lesson cost me days of my life.
@ paver
your solution solved my problem. I was altering the quaternion xyzw with all kinds of results. But when I used the quaternion.euler(90,90,0) * input.gyro.attitude it fixed everything in Unity4
THAN$$anonymous$$S !!!!! :)
Your answer
![](https://koobas.hobune.stream/wayback/20220613082859im_/https://answers.unity.com/themes/thub/images/avi.jpg)
Follow this Question
Related Questions
gyroscope or accelrometer?? 1 Answer
How to show permission dialog in Unity for IOS? 0 Answers
Sensor Fusion of Accelerometer and Gyroscope 0 Answers
Android Gyro explanation? 2 Answers
Are there any plans to support apfs(OSX 10.13) in unity 4.x? 0 Answers