I want to make a app for detecting location and user’s view angle, and I need to get Magnetic North. But it seems that I haven’t got any permission about compass sensor just by Input.compass.enabled = true. Can anyone find a problem in my code or tell me why I can’t fix this issue?
Here’s my code
public class LocationManager : MonoBehaviour
{
public float Latitude { get; private set; }
public float Longitude { get; private set; }
public float compassHeading { get; private set; }
public RectTransform compassNeedle; //
public Button updateButton; //
void Start()
{
Debug.Log("LocationManager.cs Start() is called.");
//
StartCoroutine(StartLocationService());
//Activate compass sensor
StartCoroutine(WaitForCompassEnabled());
//
Input.gyro.enabled = true;
// call UpdateNorth when button clicked
updateButton.onClick.AddListener(UpdateNorth);
// Set North 1st time
UpdateNorth();
}
IEnumerator StartLocationService()
{
//
if (!Input.location.isEnabledByUser)
{
Debug.Log("Location service is disabled.");
yield break;
}
//
Input.location.Start();
//
int maxWait = 20;
while (Input.location.status == LocationServiceStatus.Initializing && maxWait > 0)
{
yield return new WaitForSeconds(1);
maxWait--;
}
//
if (maxWait <= 0)
{
Debug.Log("Location service timed out.");
yield break;
}
//
if (Input.location.status == LocationServiceStatus.Failed)
{
Debug.Log("Unable to determine device location.");
yield break;
}
}
IEnumerator WaitForCompassEnabled()
{
// Try activating compass sensor
Input.compass.enabled = true;
Debug.Log("Attempting to enable compass...");
yield return new WaitForSeconds(1.0f);
int maxWait = 20;
// Wait until compass.enabled is true
while (!Input.compass.enabled && maxWait >= 0)
{
Debug.Log("Compass not enabled yet. Retrying...");
yield return new WaitForSeconds(1.0f); // Duration: 1s
Input.compass.enabled = true; // retry
maxWait--;
}
if (Input.compass.enabled)
Debug.Log("Compass is now enabled!");
else
Debug.Log("Compass is not available");
}
void UpdateLocationData()
{
if (Input.location.status == LocationServiceStatus.Running)
{
Latitude = Input.location.lastData.latitude;
Longitude = Input.location.lastData.longitude;
}
else
{
Debug.Log("Location service stopped.");
}
}
void Update()
{
UpdateLocationData();
float gyroHeading = -Input.gyro.attitude.eulerAngles.y;
float combinedHeading = Mathf.Lerp(compassHeading, gyroHeading, 0.5f);
//
if (compassNeedle == null)
{
Debug.LogError("Fail to load Compass Object");
return;
}
//
compassNeedle.localRotation = Quaternion.Euler(0, 0, -combinedHeading);
}
void UpdateNorth()
{
//
compassHeading = Input.compass.trueHeading;
Debug.Log("Updated Heading: " + compassHeading.ToString());
}
}
P.S. I can get my longitude and latitude normally, so it doesn’t seem to have a matter in Input.location.
- When it comes to gyro sensor, I found there’s an issue not only with the compass, but also with the gyro sensor. Maybe it’s related to compatibility or authority for higher levels.