'Unity AR Rotate Scene to match reference point

How to Match a reference point in 2 different AR scenes by position and rotation?

Here are some details about my project: I have 2 scenes: "new scan" and "load scan". In the "new scan" scene I instantiate a 3d cube and make all the other points relative to it. This is my reference point. Then I instantiate some more points and finally save all the data to the device (my phone). Next, in "load scan" I load the scene again and instantiate the cube in the exact same world position. For now, I managed to set the right position for each point but the axis is rotated because I start the scene from a different real-world location and different phone rotation. Based on the cubes which are instantiated in the same place, I need to match the rotation and the position of the scene so the points will appear in the same relative position as the first cube.

Note: one can assume that the cube will instantiate with the user standing in the same direction as the desired position. But Do NOT assume that the user starts the "load scan" scene in the same direction as the "new scan" scene (which effect the whole scene rotation).

Here is a visualization of the problem: Image of New Scan:

new scan elements

Image of Load Scan:

Load Scan after instantiating the cube

Thanks



Solution 1:[1]

If you want to make sure that the cube will appear in the same position/rotation in every AR session you have several options:

  • Use an Image marker
  • Use ARWorldMap (iOS exclusive)
  • Use a Cloud Tracking solution (google cloud anchors / Azure spatial anchors)

Of course you can also try to make the user place the cube correctly themselves, or redesign your app to work without these restrictions.

Solution 2:[2]

So I've found a solution but this is not the ultimate solution:

First, make a class with public static parameter so we can pass it through other scripts and scenes. Something like that:

public static class SceneStage 
{
   public static int ResetScene = 0;
}

Now, every time the camera turns on, check the SceneStage.ResetScene state. If value == 0 don't do anything, otherwise ask the user to stand facing the desire direction and then press a button, which call the function ResetScene:

private void ResetScene(int _scene)
{
    var xrManagerSettings = UnityEngine.XR.Management.XRGeneralSettings.Instance.Manager;
    xrManagerSettings.DeinitializeLoader();
    SceneManager.LoadScene(_scene); // reload current scene
    xrManagerSettings.InitializeLoaderSync();
}

Here I send the scene build index to the function with:

ResetScene(SceneManager.GetActiveScene().buildIndex);

So basically, the flow is like that: for the first time we open the scene (when SceneStage.ResetScene = 1) -> change the value to 0, and reset the scene. The second time don't do anything, but when we leave the scene set the value back to 1 so the next scene will reset too (because the ARPose driver still tracking the environment).

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1
Solution 2 David Shandor