Validate Device Requirements

This document describes how to check a device for AR support and update software.

Device requirements

AR relies on expensive computer vision algorithms to work, and so not every device will be able to maintain a quality experience. Older devices might not have a high enough quality CPU, GPU, or camera. The device requirements are listed in the Runtime Requirements section of System Requirements.

In addition, ARDK depends on shared libraries like ARCore or ARKit. Even if a device’s hardware supports AR, it also needs to have those libraries installed and be able to run them.

Validating requirements

ARDK is able to manage checking these requirements for you. ARWorldTrackingConfigurationFactory.CheckCapabilityAndSupport will let you know if the device supports AR, and whether the necessary software is up to date.

CapabilityChecker

The CapabilityChecker is a Manager for asynchronously determining if ARDK can run on the device surfacing the result. On Android devices, that process includes attempting to update ARCore if needed.

Installing ARCore

For Android, Google Play Services for AR (ARCore) needs to both be linked into your app and installed through the Play store. ARDK already links ARCore so all there is to do is make sure ARCore is installed. In ARDK there is an API to direct the end user to the Play store to install/update ARCore if it isn’t already up to date. If ARWorldTrackingConfigurationFactory.CheckCapabilityAndSupport indicates that an Android device’s software is supported but out of date, ARCoreInstaller.RequestInstallARCore can be called to prompt the user to install/update it.

The user will be shown a popup explaining what is happening and that they need to update ARCore. Then they’ll be taken to the Play store where they can start the update, and once it’s done they’ll be returned to your app.

On iOS, calling this method will do nothing except return ARCoreInstaller.InstallResult.Installed. Best practice would still be to not call it on iOS but there would be no major problem if it was called.

Note

If you are targeting Android 11 / API 30 and higher, you may need to configure your Unity build to support queries for the version of ARCore installed. See “Building for Android 11 (API level 30) and higher” in Building for Android for more details.

Arguments

The first argument, shouldPromptUserToUpdate, determines whether it is being called to send the user to the Play store, or to check the results of a previous request.

The second argument, installBehavior, determines whether the user is allowed to cancel out of the prompt and return to your app before going to the Play store. If this is Optional they’ll be allowed to cancel, if it is Required they won’t be. Note that it is always possible for the user to decline the installation and return, even you pass Required.

The third argument, messageType, determines the text that will be shown to the user to explain what is happening. If it is Application or Feature, they’ll be told that the application or feature requires ARCore, respectively. If it is UserAlreadyInformed, the user won’t be given any explaination.

Walkthrough

A step-by-step walkthrough of the process might look like this:

  1. Check the AR compatibility and support of the user’s device with ARWorldTrackingConfigurationFactory.CheckCapabilityAndSupport.

    using Niantic.ARDK.AR.Configuration;
    
    public class ValidateDeviceRequirements: MonoBehaviour
    {
      public void CheckARSupport()
      {
        ARWorldTrackingConfigurationFactory.CheckCapabilityAndSupport
        (
          HandleCapabilityAndSupport
        );
      }
    
      private void HandleCapabilityAndSupport(ARHardwareCapability hardwareCapability, ARSoftwareSupport softwareSupport)
      {
        // ...
      }
  2. If the result of ARWorldTrackingConfigurationFactory.CheckCapabilityAndSupport indicates the hardware is supported, but the software needs an update, then call InstallARCore(), defined in the next step.

    private void HandleCapabilityAndSupport(ARHardwareCapability hardwareCapability, ARSoftwareSupport softwareSupport)
    {
      if (hardwareCapability == ARHardwareCapability.Capable && softwareSupport == ARSoftwareSupport.SupportedNeedsUpdate)
      {
        InstallARCore();
      }
      else
      {
        // Handle other cases...
      }
    }
    
    private void InstallARCore()
    {
      // ...
    }
  3. In InstallARCore(), use ARCoreInstaller.RequestInstallARCore(true, ...) to send the user to the Play store to install ARCore.

    private bool _havePromptedTheUserToInstallARCore = false;
    
    private void InstallARCore()
    {
      var installationResult = ARCoreInstaller.RequestInstallARCore
      (
        true,
        ARCoreInstaller.InstallBehavior.Optional,
        ARCoreInstaller.InstallMessageType.Application
      );
    
      if (installationResult == ARCoreInstaller.InstallResult.PromptingUserToUpdate)
      {
        _havePromptedTheUserToInstallARCore = true;
      }
      else
      {
        // Handle the failure...
      }
    }
  4. Unity pauses the game’s activity, so OnApplicationPause will be called on any MonoBehaviours with pauseStatus = true.

  5. The user can then install ARCore, hit cancel, or navigate away from the Play store and back to your app.

  6. The game’s activity then resumes, so OnApplicationPause will be called on any MonoBehaviours with pauseStatus = false.

  7. ARCoreInstaller.RequestInstallARCore(false, ...) will now indicate whether ARCore is now installed or not.

    public void OnApplicationPause(bool pauseStatus)
    {
      if (!pauseStatus && _havePromptedTheUserToInstallARCore)
      {
        var installationResult = ARCoreInstaller.RequestInstallARCore
        (
          true,
          ARCoreInstaller.InstallBehavior.Optional,
          ARCoreInstaller.InstallMessageType.Application
        );
        _havePromptedTheUserToInstallARCore = false;
    
        if (installationResult == ARCoreInstaller.InstallResult.Installed)
        {
          // Handle successfully installing ARCore...
        }
        else
        {
          // Handle the failure...
        }
      }
    }

Sample code

Here is an example combining the above snippet code into one helper class, to show how they all interact.

using Niantic.ARDK.AR.Configuration;

public class ValidateDeviceRequirements: MonoBehaviour
{
  private void NotSupported()
  {
    // Handle a lack of AR support.
  }

  private void Supported()
  {
    // Handle AR support.
  }

  // A public method that will eventually call either Supported or NotSupported.
  public void CheckARSupport()
  {
    ARWorldTrackingConfigurationFactory.CheckCapabilityAndSupport
    (
      HandleCapabilityAndSupport
    );
  }

  private void HandleCapabilityAndSupport(ARHardwareCapability hardwareCapability, ARSoftwareSupport softwareSupport)
  {
    // Based on the hardwareCapability and softwareSupport values, AR is supported, not supported, or support is dependent on the result of installing ARCore
    if (hardwareCapability != ARHardwareCapability.Capable)
    {
      NotSupported();
    }
    else if (softwareSupport == ARSoftwareSupport.NotSupported)
    {
      NotSupported();
    }
    else if (softwareSupport == ARSoftwareSupport.SupportedNeedsUpdate)
    {
      #if UNITY_IOS
        NotSupported();
      #elif UNITY_ANDROID
        InstallARCore();
      #endif
    }
    else
    {
      Supported();
    }
  }

  private bool _havePromptedTheUserToInstallARCore = false;

  // Send the user to install ARCore. This can either fail immediately, or send them to the Play store.
  private void InstallARCore()
  {
    var installationResult = ARCoreInstaller.RequestInstallARCore
    (
      true,
      ARCoreInstaller.InstallBehavior.Optional,
      ARCoreInstaller.InstallMessageType.Application
    );

    if (installationResult == ARCoreInstaller.InstallResult.PromptingUserToUpdate)
    {
      _havePromptedTheUserToInstallARCore = true;
    }
    else
    {
      NotSupported();
    }
  }

  public void OnApplicationPause(bool pauseStatus)
  {
    if (!pauseStatus && _havePromptedTheUserToInstallARCore)
    {
      // The user is returning to the Unity Activity for the first time since they were sent to the Play store, so check the result of the installation request.
      var installationResult = ARCoreInstaller.RequestInstallARCore
      (
        true,
        ARCoreInstaller.InstallBehavior.Optional,
        ARCoreInstaller.InstallMessageType.Application
      );
      _havePromptedTheUserToInstallARCore = false;

      if (installationResult == ARCoreInstaller.InstallResult.Installed)
      {
        Supported();
      }
      else
      {
        NotSupported();
      }
    }
  }