针对 Android NDK 的增强图像开发者指南

了解如何在您自己的应用中使用增强图像。

前提条件

请务必先了解基本的 AR 概念以及如何配置 ARCore 会话,然后再继续操作。

创建图像数据库

创建 ArAugmentedImageDatabase 来存储参考图片。您可以通过以下两种方式:

  • 创建空数据库
ArAugmentedImageDatabase* ar_augmented_image_database = NULL;
ArAugmentedImageDatabase_create(ar_session, &ar_augmented_image_database);
  • 从图像数据库文件读取。如需详细了解增强图像C 示例应用] 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);

您可以使用图片工具或调用 ArAugmentedImageDatabase_serialize() 来创建数据库文件。

向数据库添加图片

如果您已从数据库文件加载了所需的参考图片,则此步骤是可选的。如需在运行时添加图片,请调用 ArAugmentedImageDatabase_addImage(),如下所示。 如需了解 util 命名空间中的函数,请参阅 augmented_image_c 示例应用

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;

我们稍后会使用 indexname 值来标识检测到了哪些参考图片。

启用图片跟踪

通过注册图像数据库,配置 ARCore 会话以跟踪图像:

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

在会话期间,ARCore 使用相机图像中的特征点与图像数据库中的特征点进行匹配。

在 AR 会话中查找增强图像

要获取匹配的图片,请在帧更新循环中轮询更新的 ArAugmentedImage

// 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).
  }
}

支持不同的用例

当 ARCore 检测到增强图像时,会为该增强图像创建一个 Trackable,并将 ArTrackingState 设置为 TRACKINGArAugmentedImageTrackingMethod更改为 FULL_TRACKING。当跟踪的图片移出相机视图时,ARCore 会继续将 ArTrackingState 设置为 TRACKING,但会更改 ArAugmentedImageTrackingMethodLAST_KNOWN_POSE,同时继续提供图片的方向和位置。

您的应用应根据预期用例以不同的方式使用跟踪状态和跟踪方法。

  • 固定图片。涉及已固定(即预计不会移动)图片的大多数用例都可以直接使用 ArTrackingState 来确定是否检测到了图片,以及图片的位置是否已知。可以忽略 ArAugmentedImageTrackingMethod

  • 移动图片。如果您的应用需要跟踪移动图片,请使用 ArTrackingStateArAugmentedImageTrackingMethod 确定是否检测到了图片,以及图片的位置是否已知。

用例 固定图片 移动图片
示例 墙上挂着的海报 公交车旁边的广告
在以下情况下,可以将姿势
有效:
ArTrackingState == TRACKING ArTrackingState == TRACKING

ArAugmentedImageTrackingMethod == FULL_TRACKING