رمزگشای تصویر

‫NDK ImageDecoder API یک API استاندارد برای برنامه‌های Android C/C++‎ ارائه می‌دهد تا تصاویر را مستقیماً رمزگشایی کنند. توسعه‌دهندگان نرم‌افزار دیگر نیازی به استفاده از Java API (ازطریق JNI) یا کتابخانه‌های رمزگشایی تصویر شخص ثالث ندارند. این میانای برنامه‌سازی کاربردی، همراه با توابع کدبندی در واحد Bitmap، موارد زیر را فعال می‌کند:

  • برنامه‌ها و کتابخانه‌های بومی می‌توانند کوچک‌تر باشند زیرا دیگر لازم نیست کتابخانه‌های رمزگشایی خودشان را پیوند دهند.
  • برنامه‌ها و کتابخانه‌ها به‌طور خودکار از به‌روزرسانی‌های امنیتی پلاتفرم برای کتابخانه‌های رمزگشایی بهره‌مند می‌شوند.
  • برنامه‌ها می‌توانند تصاویر را مستقیماً در حافظه‌ای که ارائه می‌دهند رمزگشایی کنند. سپس برنامه‌ها می‌توانند داده‌های تصویر را پس‌پردازش کنند (درصورت تمایل) و آن را به OpenGL یا کد طراحی خود منتقل کنند.

این صفحه نحوه استفاده از API برای رمزگشایی تصویر را شرح می‌دهد.

دردسترس بودن و قابلیت

ImageDecoder API در برنامه‌هایی که Android 11 (سطح میانای برنامه‌سازی کاربردی ۳۰) یا بالاتر را هدف قرار می‌دهند دردسترس است. پیاده‌سازی در فایل‌های زیر قرار دارد:

  • imagedecoder.h برای کدگشا
  • bitmap.h برای کدبند
  • libjnigraphics.so

این میانای برنامه‌سازی کاربردی از قالب‌های تصویر زیر پشتیبانی می‌کند:

  • JPEG
  • PNG
  • GIF
  • WebP : قالب WebP
  • BMP

  • عرضه اولیه سکه (ICO)

  • WBMP

  • HEIF

  • نگاتیوهای دیجیتال (ازطریق DNG SDK)

برای پوشش دادن همه موارد استفاده از تصاویر خام رمزگشایی‌شده، این API اشیاء سطح بالاتر مانند اشیاء ساخته‌شده روی تصاویر رمزگشایی‌شده در چارچوب Java را ارائه نمی‌دهد، ازجمله:

  • Drawable شیء.
  • NinePatch: اگر در تصویر کدگذاری‌شده وجود داشته باشد، تکه‌های NinePatch نادیده گرفته می‌شود.
  • تراکم نقشه بیتی: AImageDecoder هیچ‌گونه تنظیم خودکار اندازه براساس تراکم صفحه‌نمایش انجام نمی‌دهد، اما امکان رمزگشایی به اندازه متفاوت را ازطریق AImageDecoder_setTargetSize() فراهم می‌کند.
  • پویانمایی‌ها: فقط اولین فریم فایل WebP یا گیف پویانمایی‌شده را رمزگشایی می‌کند.

رمزگشایی تصویر

رمزگشایی با نوعی ورودی که نشان‌دهنده تصویر رمزگذاری‌شده است شروع می‌شود. AImageDecoder انواع مختلفی از ورودی را می‌پذیرد:

  • AAsset (در زیر نشان داده شده است)
  • توصیف‌گر فایل
  • حائل

کد زیر نحوه باز کردن تصویر Asset از فایل، رمزگشایی آن، و سپس دور انداختن صحیح رمزگشا و دارایی را نشان می‌دهد. برای دیدن نمونه‌ای از پرداخت تصویر رمزگشایی‌شده، نمونه قوری را ببینید.

AAssetManager* nativeManager = AAssetManager_fromJava(env, jAssets);
const char* file = // Filename
AAsset* asset = AAssetManager_open(nativeManager, file, AASSET_MODE_STREAMING);
AImageDecoder* decoder;
int result = AImageDecoder_createFromAAsset(asset, &decoder);
if (result != ANDROID_IMAGE_DECODER_SUCCESS) {
  // An error occurred, and the file could not be decoded.
}

const AImageDecoderHeaderInfo* info = AImageDecoder_getHeaderInfo(decoder);
int32_t width = AImageDecoderHeaderInfo_getWidth(info);
int32_t height = AImageDecoderHeaderInfo_getHeight(info);
AndroidBitmapFormat format =
       (AndroidBitmapFormat) AImageDecoderHeaderInfo_getAndroidBitmapFormat(info);
size_t stride = AImageDecoder_getMinimumStride(decoder);  // Image decoder does not
                                                          // use padding by default
size_t size = height * stride;
void* pixels = malloc(size);

result = AImageDecoder_decodeImage(decoder, pixels, stride, size);
if (result != ANDROID_IMAGE_DECODER_SUCCESS) {
  // An error occurred, and the file could not be decoded.
}

// We’re done with the decoder, so now it’s safe to delete it.
AImageDecoder_delete(decoder);

// The decoder is no longer accessing the AAsset, so it is safe to
// close it.
AAsset_close(asset);

// Draw the pixels somewhere

// Free the pixels when done drawing with them
free(pixels);