Guide du développeur Augmented Images pour le NDK Android

Découvrez comment utiliser les images augmentées dans vos propres applications.

Prérequis

Avant de continuer, assurez-vous de bien comprendre les concepts fondamentaux de la RA et de savoir configurer une session ARCore.

Créer une base de données d'images

Créez un ArAugmentedImageDatabase pour stocker les images de référence. Vous avez le choix entre deux méthodes:

  • Créer une base de données vide
ArAugmentedImageDatabase* ar_augmented_image_database = NULL;
ArAugmentedImageDatabase_create(ar_session, &ar_augmented_image_database);
  • Lire à partir d'un fichier de base de données d'images. Reportez-vous à l'[application exemple C AugmentedImage] pour util::LoadFileFromAssetManager.
std::string database_buffer;
util::LoadFileFromAssetManager(asset_manager_, "sample_database.imgdb",
                               &database_buffer);
uint8_t* raw_buffer = reinterpret_cast<uint8_t*>(&database_buffer.front());

ArAugmentedImageDatabase* ar_augmented_image_database = NULL;
const ArStatus status = ArAugmentedImageDatabase_deserialize(
    ar_session, raw_buffer, database_buffer.size(),
    &ar_augmented_image_database);

Vous pouvez créer des fichiers de base de données à l'aide de l'outil Image ou en appelant ArAugmentedImageDatabase_serialize().

Ajouter des images à la base de données

Cette étape est facultative si les images de référence souhaitées ont déjà été chargées à partir du fichier de base de données. Pour ajouter une image au moment de l'exécution, appelez ArAugmentedImageDatabase_addImage(), comme illustré ci-dessous. Consultez l'augmented_image_c pour connaître les fonctions de l'espace de noms util.

int32_t width, height, stride, index;
uint8_t* image_pixel_buffer = nullptr;
constexpr const char kSampleImageName[] = "default.jpg";
bool load_image_result = util::LoadImageFromAssetManager(
    kSampleImageName, &width, &height, &stride, &image_pixel_buffer);

uint8_t* grayscale_buffer = nullptr;
util::ConvertRgbaToGrayscale(image_pixel_buffer, width, height, stride,
                             &grayscale_buffer);

int32_t grayscale_stride = stride / 4;
const ArStatus status = ArAugmentedImageDatabase_addImage(
    ar_session_, ar_augmented_image_database, kSampleImageName,
    grayscale_buffer, width, height, grayscale_stride, &index);

// If the physical size of the image is known, you can instead use
//     ArStatus ArAugmentedImageDatabase_addImageWithPhysicalSize
// This will improve the initial detection speed. ARCore will still actively
// estimate the physical size of the image as it is viewed from multiple
// viewpoints.

delete[] image_pixel_buffer;
delete[] grayscale_buffer;

Les valeurs index et name sont utilisées ultérieurement pour identifier l'image de référence détectée.

Activer le suivi des images

Configurez votre session ARCore pour suivre les images en enregistrant la base de données d'images:

ArConfig_setAugmentedImageDatabase(ar_session_, ar_config,
                                   ar_augmented_image_database);
const ArStatus status = ArSession_configure(ar_session_, ar_config);

Pendant la session, ARCore utilise les points d'intérêt de l'image de la caméra pour les faire correspondre à ceux de la base de données d'images.

Rechercher des images augmentées dans une session RA

Pour obtenir les images correspondantes, interrogez les ArAugmentedImage mis à jour dans votre boucle de mise à jour de frame.

// Update loop, in onDrawFrame
ArTrackableList* updated_image_list = nullptr;
ArTrackableList_create(ar_session_, &updated_image_list);
ArFrame_getUpdatedTrackables(
    ar_session_, ar_frame_, AR_TRACKABLE_AUGMENTED_IMAGE, updated_image_list);

int32_t image_list_size;
ArTrackableList_getSize(ar_session_, updated_image_list, &image_list_size);

for (int i = 0; i < image_list_size; ++i) {
  ArTrackable* ar_trackable = nullptr;
  ArTrackableList_acquireItem(ar_session_, updated_image_list, i,
                              &ar_trackable);
  ArAugmentedImage* image = ArAsAugmentedImage(ar_trackable);

  ArTrackingState tracking_state;
  ArTrackable_getTrackingState(ar_session_, ar_trackable, &tracking_state);

  int image_index;
  ArAugmentedImage_getIndex(ar_session_, image, &image_index);

  if (tracking_state == AR_TRACKING_STATE_TRACKING) {
    util::ScopedArPose scopedArPose(ar_session_);
    ArAugmentedImage_getCenterPose(ar_session_, image,
                                   scopedArPose.GetArPose());

    ArAnchor* image_anchor = nullptr;
    const ArStatus status = ArTrackable_acquireNewAnchor(
        ar_session_, ar_trackable, scopedArPose.GetArPose(), &image_anchor);

    // For example, you can now render content at the image anchor, choosing
    // content based on the image index (or name).
  }
}

Prise en charge de différents cas d'utilisation

Lorsque ARCore détecte une image étendue, il crée un Trackable pour cette image étendue et définit ArTrackingState sur TRACKING et ArAugmentedImageTrackingMethod sur FULL_TRACKING. Lorsque l'image suivie sort du champ de vision de la caméra, ARCore continue de définir ArTrackingState sur TRACKING, mais remplace ArAugmentedImageTrackingMethod par LAST_KNOWN_POSE tout en continuant de fournir l'orientation et la position de l'image.

Votre application doit utiliser l'état et la méthode de suivi différemment en fonction du cas d'utilisation prévu.

  • Images fixes La plupart des cas d'utilisation impliquant des images fixes (c'est-à-dire qui ne doivent pas bouger) peuvent simplement utiliser ArTrackingState pour déterminer si l'image a été détectée et si son emplacement est connu. ArAugmentedImageTrackingMethod peut être ignoré.

  • Déplacer des images Si votre application doit suivre une image en mouvement, utilisez à la fois ArTrackingState et ArAugmentedImageTrackingMethod pour déterminer si l'image a été détectée et si sa position est connue.

Cas d'utilisation Image fixe Image animée
Exemple Un poster accroché au mur Annonce sur le flanc d'un bus
La pose peut être considérée comme valide lorsque :
ArTrackingState == TRACKING ArTrackingState == TRACKING
et
ArAugmentedImageTrackingMethod == FULL_TRACKING