先日、Instagram で夜間モードを使用して暗い場所でも美しい写真を撮影できるようになったことをお知らせしました。この機能は、複数の露出を組み合わせて高品質の静止画像を撮影する時間がある静止画像に最適です。しかし、写真と写真の間に起こる瞬間はどうでしょうか?ユーザーは、シャッター ボタンを押す瞬間だけでなく、カメラを操作する必要があります。また、プレビューを使用してシーンを構成したり、QR コードをスキャンしたりすることもできます。
今回は、リアルタイムのカメラ ストリームを明るくするために設計された強力な機能である Low Light Boost(LLB)について詳しく説明します。夜間モードでは静止した状態での撮影が必要ですが、Low Light Boost はライブ プレビューと動画撮影で瞬時に機能します。LLB は、利用可能な光に基づいて必要な明るさを自動的に調整するため、あらゆる環境に最適化されています。
最近のアップデートにより、LLB を使用して Instagram ユーザーは完璧なショットを撮影できるようになりました。また、既存の夜間モードの実装により、ユーザーが 1 年以上前から楽しんでいる高画質の低照度写真が撮影できます。
リアルタイムの明るさが重要な理由
夜間モードは最終的な画質の向上を目的としていますが、ローライト ブーストは暗い場所での使いやすさとインタラクティビティを目的としています。もう 1 つ考慮すべき重要な要素は、LLB と夜間モードは非常にうまく連携しますが、それぞれ単独で使用できることです。これらのユースケースの一部でわかるように、夜間モードの写真が必要ない場合でも、LLB には独自の価値があります。LLB がユーザー エクスペリエンスを向上させる仕組みは次のとおりです。
- フレーミングとキャプチャの改善: 薄暗いシーンでは、標準のカメラ プレビューは真っ黒になることがあります。LLB はビューファインダーを明るくし、ユーザーがシャッター ボタンを押す前に、実際にフレーミングしているものを確認できるようにします。このエクスペリエンスでは、夜間モードを使用して暗い場所で撮影した写真の品質を最大限に高めることも、LLB を使用して「見たまま」の写真を撮影することもできます。
- 信頼性の高いスキャン: QR コードはどこにでもありますが、暗いレストランや屋内駐車場でスキャンするのは難しいことがよくあります。カメラフィードが大幅に明るくなるため、スキャン アルゴリズムは非常に暗い環境でも QR コードを確実に検出してデコードできます。
- インタラクションの強化: ライブ動画のインタラクション(AI アシスタントやビデオ通話など)を含むアプリの場合、LLB は認識可能な情報の量を増やし、コンピュータ ビジョン モデルが十分なデータで動作できるようにします。
Instagram の違い
Android 版 Instagram アプリのエンジニアリング チームは、ユーザーに最先端のカメラ エクスペリエンスを提供するため、常に努力を重ねています。上の例では、Google Pixel 10 Pro で LLB がどれほど効果を発揮しているかを確認できます。
ユーザー エクスペリエンスにどのような違いが生じるかは、容易に想像できます。キャプチャしている内容を確認できない場合、ユーザーがキャプチャを中止する可能性が高くなります。
実装の選択
ローライト ブーストを実装して、幅広いデバイスで最高のユーザー エクスペリエンスを提供するには、次の 2 つの方法があります。
- ローライト ブースト AE モード: ハードウェア レイヤの自動露出モードです。画像信号処理装置(ISP)パイプラインを直接調整するため、最高の品質とパフォーマンスを実現します。必ず最初に確認してください。
- Google 低照度ブースト: デバイスが AE モードをサポートしていない場合は、Google Play 開発者サービスが提供するこのソフトウェア ベースのソリューションにフォールバックできます。カメラ ストリームに後処理を適用して明るくします。オールソフトウェア ソリューションであるため、より多くのデバイスで利用できます。この実装により、LLB を搭載したデバイスを増やせます。
ローライト ブースト AE モード(ハードウェア)
メカニズム:
このモードは、Android 15 以降を搭載するデバイスでサポートされており、OEM が HAL でサポートを実装している必要があります(現在は Google Pixel 10 デバイスで利用可能です)。カメラの画像信号処理装置(ISP)と直接統合されています。CaptureRequest.CONTROL_AE_MODE を CameraMetadata.CONTROL_AE_MODE_ON_LOW_LIGHT_BOOST_BRIGHTNESS_PRIORITY に設定すると、カメラ システムが制御を引き継ぎます。
動作:
HAL/ISP はシーンを分析し、センサーと処理のパラメータを調整します。多くの場合、露出時間を長くして画像を明るくします。露出時間を延長することで、デジタル センサーのゲイン(ISO)を上げることなく、センサーがより多くの光情報を取得できるため、信号対雑音比(SNR)が大幅に改善されたフレームが得られます。
メリット:
専用のハードウェア パスウェイを活用するため、画質と電力効率が向上する可能性があります。
トレードオフ:
センサーが光を取り込むのに時間がかかるため、非常に暗い場所ではフレームレートが低下する可能性があります。非常に暗い場所では、フレームレートが 10 FPS まで低下することがあります。
Google ローライト ブースト(Google Play 開発サービス経由のソフトウェア)
メカニズム:
このソリューションは、Google Play 開発者サービスを介してオプション モジュールとして配信され、カメラ ストリームに後処理を適用します。HDRNet と呼ばれる高度なリアルタイム画像補正技術を使用しています。
Google HDRNet:
このディープ ラーニング モデルは、低解像度で画像を分析し、コンパクトなパラメータ セット(バイラテラル グリッド)を予測します。このグリッドは、GPU でのフル解像度画像の効率的で空間的に変化するエンハンスメントをガイドします。このモデルは、暗い場所での画像の明るさと画質を向上させるようにトレーニングされています。顔の視認性に重点が置かれています。
プロセス オーケストレーション:
HDRNet モデルとその付随するロジックは、ローライト ブースト プロセッサによってオーケストレーションされます。以下が該当します。
-
シーン分析:
カメラのメタデータ(センサー感度、露出時間など)と画像コンテンツを使用して、実際のシーンの明るさを推定するカスタム計算ツール。この分析により、ブーストレベルが決定されます。 -
HDRNet 処理:
HDRNet モデルを適用してフレームを明るくします。使用されるモデルは、低照度シーン向けに調整され、リアルタイム パフォーマンス向けに最適化されています。 -
ブレンディング:
元のフレームと HDRNet 処理済みのフレームがブレンドされます。適用されるブレンドの量は、シーンの明るさ計算ツールによって動的に制御され、ブーストされた状態とブーストされていない状態の間でスムーズな切り替えが保証されます。
利点:
特定の HAL サポートを必要とせず、幅広いデバイス(現在は Samsung S22 Ultra、S23 Ultra、S24 Ultra、S25 Ultra、Google Pixel 6 ~ Google Pixel 9 をサポート)で動作します。ポストプロセス エフェクトであるため、カメラのフレームレートを維持します。
トレードオフ:
後処理メソッドとして、品質はセンサーから配信されるフレームに含まれる情報によって制限されます。センサーレベルで極端な暗さによって失われた詳細を復元することはできません。
ハードウェアとソフトウェアの両方のパスウェイを提供することで、Low Light Boost は Android エコシステム全体で低照度カメラのパフォーマンスを向上させるスケーラブルなソリューションを提供します。デベロッパーは、利用可能な場合は AE モードを優先し、Google ローライト ブーストを堅牢なフォールバックとして使用する必要があります。
アプリでのローライト ブーストの実装
次に、両方の LLB サービスを実装する方法について説明します。アプリで CameraX と Camera2 のどちらを使用している場合でも、以下を実装できます。最適な結果を得るには、ステップ 1 とステップ 2 の両方を実装することをおすすめします。
ステップ 1: ローライト ブースト AE モード
Android 15 以降を搭載した一部のデバイスで利用可能な LLB AE モードは、特定の自動露出(AE)モードとして機能します。
1. 利用可能かどうかを確認する
まず、カメラ デバイスが LLB AE モードをサポートしているかどうかを確認します。
val cameraInfo = cameraProvider.getCameraInfo(cameraSelector) val isLlbSupported = cameraInfo.isLowLightBoostSupported
2. モードを有効にする
サポートされている場合は、CameraX の CameraControl オブジェクトを使用して LLB AE モードを有効にできます。
// After setting up your camera, use the CameraInfo object to enable LLB AE Mode.
camera = cameraProvider.bindToLifecycle(...)
if (isLlbSupported) {
try {
// The .await() extension suspends the coroutine until the
// ListenableFuture completes. If the operation fails, it throws
// an exception which we catch below.
camera?.cameraControl.enableLowLightBoostAsync(true).await()
} catch (e: IllegalStateException) {
Log.e(TAG, "Failed to enable low light boost: not available on this device or with the current camera configuration", e)
} catch (e: CameraControl.OperationCanceledException) {
Log.e(TAG, "Failed to enable low light boost: camera is closed or value has changed", e)
}
}
3. 状態をモニタリングする
モードをリクエストしたからといって、現在「ブースト」されているとは限りません。システムは、シーンが実際に暗い場合にのみブーストを有効にします。Observer を設定して、UI を更新したり(月アイコンを表示するなど)、拡張関数 asFlow() を使用して Flow に変換したりできます。
if (isLlbSupported) {
camera?.cameraInfo.lowLightBoostState.asFlow().collectLatest { state ->
// Update UI accordingly
updateMoonIcon(state == LowLightBoostState.ACTIVE)
}
}
ローライト ブースト AE モードについてのガイドの全文はこちらをご覧ください。
ステップ 2: Google ローライト ブースト
ハードウェア AE モードをサポートしていないデバイスの場合、Google 低照度ブーストは強力なフォールバックとして機能します。LowLightBoostSession を使用して、ストリームをインターセプトして明るくします。
1. 依存関係を追加する
この機能は Google Play 開発者サービスを通じて提供されます。
implementation("com.google.android.gms:play-services-camera-low-light-boost:16.0.1-beta06")
// Add coroutines-play-services to simplify Task APIs
implementation("org.jetbrains.kotlinx:kotlinx-coroutines-play-services:1.10.2")
2. クライアントを初期化する
カメラを起動する前に、LowLightBoostClient を使用して、モジュールがインストールされ、デバイスがサポートされていることを確認します。
val llbClient = LowLightBoost.getClient(context)
// Check support and install if necessary
val isSupported = llbClient.isCameraSupported(cameraId).await()
val isInstalled = llbClient.isModuleInstalled().await()
if (isSupported && !isInstalled) {
// Trigger installation
llbClient.installModule(installCallback).await()
}
3. LLB セッションを作成する
Google LLB は各フレームを処理するため、ディスプレイ Surface を LowLightBoostSession に渡す必要があります。すると、明るさ調整が適用された Surface が返されます。Camera2 アプリの場合、結果の Surface を CaptureRequest.Builder.addTarget() で追加できます。CameraX の場合、この処理パイプラインは CameraEffect クラスに最適です。このクラスでは、SurfaceProcessor でエフェクトを適用し、このコードで示されているように、SurfaceProvider でプレビューに戻すことができます。
// With a SurfaceOutput from SurfaceProcessor.onSurfaceOutput() and a
// SurfaceRequest from Preview.SurfaceProvider.onSurfaceRequested(),
// create a LLB Session.
suspend fun createLlbSession(surfaceRequest: SurfaceRequest, outputSurfaceForLlb: Surface) {
// 1. Create the LLB Session configuration
val options = LowLightBoostOptions(
outputSurfaceForLlb,
cameraId,
surfaceRequest.resolution.width,
surfaceRequest.resolution.height,
true // Start enabled
)
// 2. Create the session.
val llbSession = llbClient.createSession(options, callback).await()
// 3. Get the surface to use.
val llbInputSurface = llbSession.getCameraSurface()
// 4. Provide the surface to the CameraX Preview UseCase.
surfaceRequest.provideSurface(llbInputSurface, executor, resultListener)
// 5. Set the scene detector callback to monitor how much boost is being applied.
val onSceneBrightnessChanged = object : SceneDetectorCallback {
override fun onSceneBrightnessChanged(
session: LowLightBoostSession,
boostStrength: Float
) {
// Monitor the boostStrength from 0 (no boosting) to 1 (maximum boosting)
}
}
llbSession.setSceneDetectorCallback(onSceneBrightnessChanged, null)
}
4. メタデータを渡す
このアルゴリズムが機能するには、カメラの自動露出状態を分析する必要があります。キャプチャ結果を LLB セッションに渡す必要があります。CameraX では、Camera2Interop.Extender.setSessionCaptureCallback() を使用して Preview.Builder を拡張することで、これを行うことができます。
Camera2Interop.Extender(previewBuilder).setSessionCaptureCallback(
object : CameraCaptureSession.CaptureCallback() {
override fun onCaptureCompleted(
session: CameraCaptureSession,
request: CaptureRequest,
result: TotalCaptureResult
) {
super.onCaptureCompleted(session, request, result)
llbSession?.processCaptureResult(result)
}
}
)
クライアントとセッションの詳細な実装手順については、 Google Low Light Boost ガイドをご覧ください。
次の手順
これらの 2 つのオプションを実装することで、照明条件に関係なく、ユーザーがはっきりと見ることができ、確実にスキャンして効果的に操作できるようになります。
これらの機能が完全な本番環境対応のコードベースでどのように動作するかについては、GitHub の Jetpack カメラアプリをご覧ください。LLB AE モードと Google LLB の両方を実装しており、独自の統合の参考になります。
続きを読む
-
プロダクト ニュース
Android Studio Panda 4 が安定版となり、本番環境で使用できる準備が整いました。このリリースでは、プランニング モードや次の編集の予測などが導入され、高品質の Android アプリをこれまで以上に簡単に作成できるようになりました。
Matt Dyor • 所要時間: 5 分
-
プロダクト ニュース
Android デベロッパーで、革新的な AI 機能をアプリに実装したいとお考えの場合は、最近リリースされた強力な新機能をご利用ください。
Thomas Ezan • 所要時間: 3 分
-
プロダクト ニュース
Android 17 はベータ版 4 に到達しました。これはこのリリース サイクルの最後の予定ベータ版であり、アプリの互換性とプラットフォームの安定性にとって重要なマイルストーンです。
Daniel Galpin • 所要時間: 4 分
メールを受け取る
Android 開発に関する最新の分析情報を毎週メールでお届けします。