Interfejs Media Enhancement API to działające na urządzeniu rozwiązanie oparte na sztucznej inteligencji, które zapewnia niskie opóźnienia i chroniące prywatność. Wykorzystuje akcelerację sprzętową, aby poprawiać jakość multimediów bez zwiększania rozmiaru pakietu APK. Więcej informacji znajdziesz w artykule Omówienie funkcji ulepszania multimediów.
Poniższy schemat architektury przedstawia cykl życia asynchronicznego trybu działania interfejsu Media Enhancement API. Ten tryb bezpośrednio łączy bufory sprzętowe, aby wyeliminować wąskie gardło wydajności związane z kopiowaniem nieskompresowanych klatek między buforami pamięci procesora i GPU.
Potok ulepszeń jest wdrażany w tych krokach:
Etap 1. Konfigurowanie sesji ulepszania
1. Udostępnij powierzchnię wejściową: aplikacja udostępnia platformie ulepszania uchwyt powierzchni wejściowej, aby uzyskać dostęp do klatek do przetworzenia.
2. Ustaw powierzchnię wyjściową: aplikacja udostępnia i wiąże cele renderowania (np. SurfaceView lub TextureView) bezpośrednio z platformą.
Etap 2. Utwórz klatkę wejściową.
3. Przygotuj podstawowe multimedia: aplikacja pobiera podstawowe nieskompresowane multimedia. Na przykład przez odczytanie pliku z dysku lokalnego.
4. Wstrzykiwanie danych klatki: aplikacja zapisuje surowe dane obrazu bezpośrednio w powiązanym potoku powierzchni wejściowej.
Etap 3. Przetwarzanie i ulepszanie
5. Wykonanie przetwarzania AI: framework przetwarza klatkę na GPU lub NPU urządzenia, stosując ulepszenia wynikające z uczenia maszynowego, takie jak mapowanie tonalne, usuwanie rozmycia czy skalowanie w górę.
6. Przekazywanie ulepszonej klatki: silnik przekazuje ulepszoną klatkę w pełnej rozdzielczości bezpośrednio do powiązanej powierzchni wyjściowej.
Etap 4. Wyświetlanie lub zapisywanie wyniku
7. Końcowe dane wyjściowe: aplikacja otrzymuje przetworzony bufor strumienia sprzętowego, aby renderować go w interfejsie lub zapisywać z powrotem w pamięci.
EnhancementSession to obiekt kontekstu o dużej wadze, który utrzymuje trwały potok pamięci GPU lub NPU. Przydziela dedykowaną pamięć RAM wideo (VRAM) i natywne uchwyty systemowe. Aby zapobiec poważnym wyciekom pamięci i potencjalnym OutOfMemoryErrorawariom, przestrzegaj tych zasad cyklu życia:
- Lenistwo w tworzeniu instancji: nie twórz sesji, dopóki użytkownik nie zainicjuje działania związanego z ulepszaniem.
- Strategiczne ponowne użycie: utrzymuj i ponownie używaj pojedynczej instancji sesji podczas przetwarzania strumieni lub klatek o identycznych konfiguracjach (wymiarach i włączonych opcjach).
- Zakończenie promptu: wywołuj
session.release()natychmiast po zakończeniu zadań wizualnych, aby zwolnić współdzielone zasoby sprzętowe.
Inicjowanie silnika ulepszania
Ta metoda przeprowadza dwuetapową weryfikację. Sprawdza, czy sprzęt urządzenia obsługuje akcelerację, a następnie upewnia się, że są obecne wymagane moduły uczenia maszynowego.
Uruchomienie tego kroku jako warunku wstępnego zapobiega błędom inicjowania w czasie działania, ponieważ sprawdza możliwości przed podjęciem przez aplikację próby przetworzenia multimediów.
class MediaSetupViewModel(application: Application) : AndroidViewModel(application) {
private val enhancementClient = Enhancement.getClient(application)
fun initializeEnhancementEngine() {
viewModelScope.launch {
try {
// 1. Verify hardware capability
val isSupported = enhancementClient.isDeviceSupportedAsync()
if (!isSupported) {
notifyUiDeviceIncompatible()
return@launch
}
// 2. Verify and download the Google Play services ML modules
val isInstalled = enhancementClient.isModuleInstalledAsync()
if (!isInstalled) {
notifyUiDownloadingModels()
enhancementClient.installModule().await()
}
notifyUiEngineReady()
} catch (e: Exception) {
// Handle potential errors during session creation or image
// processing.
handleInitializationError(e)
}
}
}
}
Wdrożenie: tryb powierzchniowy (powierzchnia wewnątrz, powierzchnia na zewnątrz)
Tryb wykonywania Surface (EnhancementMode.SURFACE) pozwala uniknąć obniżenia wydajności związanego z przenoszeniem ramek między buforami pamięci procesora i GPU. Zamiast tego biblioteka ulepszeń mapuje bezpośrednio surowe bufory sprzętowe, odczytując klatki z powierzchni wejściowej, przetwarzając je natywnie i przesyłając bezpośrednio na powierzchnię wyjściową.
Zrzuty powierzchni w jednej klatce
Ta metoda służy do efektywnego stosowania efektów do pojedynczej ramki obrazu dekodowanej sprzętowo.
// Provisions input Surface (for example, ImageReader) and output Surface (for
// example, SurfaceView)
val inputSurface: Surface = imageReader.surface
val outputSurface: Surface = surfaceView.holder.surface
// 1. Configure parameters for SURFACE mode
val surfaceOptions = EnhancementOptions(
imageReader.width,
imageReader.height,
EnhancementMode.SURFACE,
enableTonemap = true,
enableDeblurDenoise = true,
enableFaceDetection = false
).also {
// 2. Bind hardware surfaces
it.setInputSurface(inputSurface)
it.setOutputSurface(outputSurface)
}
// 3. Create the session to process the hardware frame
val singleFrameSession = enhancementClient.createSessionAsync(surfaceOptions, executor)
// The API processes the single frame. Upon completion, release the session.
singleFrameSession.release()