Skip to content

Revert "Migrate CameraX from SurfaceTexture to SurfaceProducer." #6838

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 3 commits into from
May 30, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions packages/camera/camera_android_camerax/CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,7 @@
## 0.6.5+5

* Reverts changes to support Impeller.

## 0.6.5+4

* [Supports Impeller](https://docs.flutter.dev/release/breaking-changes/android-surface-plugins).
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,9 @@
package io.flutter.plugins.camerax;

import android.app.Activity;
import android.graphics.SurfaceTexture;
import android.util.Size;
import android.view.Surface;
import androidx.annotation.NonNull;
import androidx.camera.core.CameraSelector;
import androidx.camera.core.ImageAnalysis;
Expand Down Expand Up @@ -49,6 +51,11 @@ public class CameraXProxy {
return new Preview.Builder();
}

/** Creates a {@link Surface} instance from the specified {@link SurfaceTexture}. */
public @NonNull Surface createSurface(@NonNull SurfaceTexture surfaceTexture) {
return new Surface(surfaceTexture);
}

/**
* Creates an instance of the {@link SystemServicesFlutterApiImpl}.
*
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@

package io.flutter.plugins.camerax;

import android.graphics.SurfaceTexture;
import android.util.Size;
import android.view.Surface;
import androidx.annotation.NonNull;
Expand All @@ -24,7 +25,7 @@ public class PreviewHostApiImpl implements PreviewHostApi {
private final TextureRegistry textureRegistry;

@VisibleForTesting public @NonNull CameraXProxy cameraXProxy = new CameraXProxy();
@VisibleForTesting public @Nullable TextureRegistry.SurfaceProducer flutterSurfaceProducer;
@VisibleForTesting public @Nullable TextureRegistry.SurfaceTextureEntry flutterSurfaceTexture;

public PreviewHostApiImpl(
@NonNull BinaryMessenger binaryMessenger,
Expand Down Expand Up @@ -61,11 +62,12 @@ public void create(
@Override
public @NonNull Long setSurfaceProvider(@NonNull Long identifier) {
Preview preview = getPreviewInstance(identifier);
flutterSurfaceProducer = textureRegistry.createSurfaceProducer();
Preview.SurfaceProvider surfaceProvider = createSurfaceProvider(flutterSurfaceProducer);
flutterSurfaceTexture = textureRegistry.createSurfaceTexture();
SurfaceTexture surfaceTexture = flutterSurfaceTexture.surfaceTexture();
Preview.SurfaceProvider surfaceProvider = createSurfaceProvider(surfaceTexture);
preview.setSurfaceProvider(surfaceProvider);

return flutterSurfaceProducer.id();
return flutterSurfaceTexture.id();
}

/**
Expand All @@ -74,13 +76,13 @@ public void create(
*/
@VisibleForTesting
public @NonNull Preview.SurfaceProvider createSurfaceProvider(
@NonNull TextureRegistry.SurfaceProducer surfaceProducer) {
@NonNull SurfaceTexture surfaceTexture) {
return new Preview.SurfaceProvider() {
@Override
public void onSurfaceRequested(@NonNull SurfaceRequest request) {
surfaceProducer.setSize(
surfaceTexture.setDefaultBufferSize(
request.getResolution().getWidth(), request.getResolution().getHeight());
Surface flutterSurface = surfaceProducer.getSurface();
Surface flutterSurface = cameraXProxy.createSurface(surfaceTexture);
request.provideSurface(
flutterSurface,
Executors.newSingleThreadExecutor(),
Expand Down Expand Up @@ -131,8 +133,8 @@ String getProvideSurfaceErrorDescription(int resultCode) {
*/
@Override
public void releaseFlutterSurfaceTexture() {
if (flutterSurfaceProducer != null) {
flutterSurfaceProducer.release();
if (flutterSurfaceTexture != null) {
flutterSurfaceTexture.release();
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;

import android.graphics.SurfaceTexture;
import android.util.Size;
import android.view.Surface;
import androidx.camera.core.Preview;
Expand Down Expand Up @@ -85,60 +86,59 @@ public void create_createsPreviewWithCorrectConfiguration() {
public void setSurfaceProviderTest_createsSurfaceProviderAndReturnsTextureEntryId() {
final PreviewHostApiImpl previewHostApi =
spy(new PreviewHostApiImpl(mockBinaryMessenger, testInstanceManager, mockTextureRegistry));
final TextureRegistry.SurfaceProducer mockSurfaceProducer =
mock(TextureRegistry.SurfaceProducer.class);
final TextureRegistry.SurfaceTextureEntry mockSurfaceTextureEntry =
mock(TextureRegistry.SurfaceTextureEntry.class);
final SurfaceTexture mockSurfaceTexture = mock(SurfaceTexture.class);
final Long previewIdentifier = 5L;
final Long surfaceProducerEntryId = 120L;
final Long surfaceTextureEntryId = 120L;

previewHostApi.cameraXProxy = mockCameraXProxy;
testInstanceManager.addDartCreatedInstance(mockPreview, previewIdentifier);

when(mockTextureRegistry.createSurfaceProducer()).thenReturn(mockSurfaceProducer);
when(mockSurfaceProducer.id()).thenReturn(surfaceProducerEntryId);
when(mockTextureRegistry.createSurfaceTexture()).thenReturn(mockSurfaceTextureEntry);
when(mockSurfaceTextureEntry.surfaceTexture()).thenReturn(mockSurfaceTexture);
when(mockSurfaceTextureEntry.id()).thenReturn(surfaceTextureEntryId);

final ArgumentCaptor<Preview.SurfaceProvider> surfaceProviderCaptor =
ArgumentCaptor.forClass(Preview.SurfaceProvider.class);
final ArgumentCaptor<Surface> surfaceCaptor = ArgumentCaptor.forClass(Surface.class);

// Test that surface provider was set and the surface texture ID was returned.
assertEquals(previewHostApi.setSurfaceProvider(previewIdentifier), surfaceProducerEntryId);
assertEquals(previewHostApi.setSurfaceProvider(previewIdentifier), surfaceTextureEntryId);
verify(mockPreview).setSurfaceProvider(surfaceProviderCaptor.capture());
verify(previewHostApi).createSurfaceProvider(mockSurfaceProducer);
verify(previewHostApi).createSurfaceProvider(mockSurfaceTexture);
}

@Test
public void createSurfaceProvider_createsExpectedPreviewSurfaceProvider() {
final PreviewHostApiImpl previewHostApi =
new PreviewHostApiImpl(mockBinaryMessenger, testInstanceManager, mockTextureRegistry);
final TextureRegistry.SurfaceProducer mockSurfaceProducer =
mock(TextureRegistry.SurfaceProducer.class);
final SurfaceTexture mockSurfaceTexture = mock(SurfaceTexture.class);
final Surface mockSurface = mock(Surface.class);
final SurfaceRequest mockSurfaceRequest = mock(SurfaceRequest.class);
final SurfaceRequest.Result mockSurfaceRequestResult = mock(SurfaceRequest.Result.class);
final SystemServicesFlutterApiImpl mockSystemServicesFlutterApi =
mock(SystemServicesFlutterApiImpl.class);
final int resolutionWidth = 200;
final int resolutionHeight = 500;
final Long surfaceProducerEntryId = 120L;

previewHostApi.cameraXProxy = mockCameraXProxy;
when(mockCameraXProxy.createSurface(mockSurfaceTexture)).thenReturn(mockSurface);
when(mockSurfaceRequest.getResolution())
.thenReturn(new Size(resolutionWidth, resolutionHeight));
when(mockCameraXProxy.createSystemServicesFlutterApiImpl(mockBinaryMessenger))
.thenReturn(mockSystemServicesFlutterApi);
when(mockTextureRegistry.createSurfaceProducer()).thenReturn(mockSurfaceProducer);
when(mockSurfaceProducer.id()).thenReturn(surfaceProducerEntryId);
when(mockSurfaceProducer.getSurface()).thenReturn(mockSurface);

final ArgumentCaptor<Surface> surfaceCaptor = ArgumentCaptor.forClass(Surface.class);
@SuppressWarnings("unchecked")
final ArgumentCaptor<Consumer<SurfaceRequest.Result>> consumerCaptor =
ArgumentCaptor.forClass(Consumer.class);

Preview.SurfaceProvider previewSurfaceProvider =
previewHostApi.createSurfaceProvider(mockSurfaceProducer);
previewHostApi.createSurfaceProvider(mockSurfaceTexture);
previewSurfaceProvider.onSurfaceRequested(mockSurfaceRequest);

verify(mockSurfaceProducer).setSize(resolutionWidth, resolutionHeight);
verify(mockSurfaceTexture).setDefaultBufferSize(resolutionWidth, resolutionHeight);
verify(mockSurfaceRequest)
.provideSurface(surfaceCaptor.capture(), any(Executor.class), consumerCaptor.capture());

Expand Down Expand Up @@ -189,13 +189,13 @@ public void createSurfaceProvider_createsExpectedPreviewSurfaceProvider() {
public void releaseFlutterSurfaceTexture_makesCallToReleaseFlutterSurfaceTexture() {
final PreviewHostApiImpl previewHostApi =
new PreviewHostApiImpl(mockBinaryMessenger, testInstanceManager, mockTextureRegistry);
final TextureRegistry.SurfaceProducer mockSurfaceProducer =
mock(TextureRegistry.SurfaceProducer.class);
final TextureRegistry.SurfaceTextureEntry mockSurfaceTextureEntry =
mock(TextureRegistry.SurfaceTextureEntry.class);

previewHostApi.flutterSurfaceProducer = mockSurfaceProducer;
previewHostApi.flutterSurfaceTexture = mockSurfaceTextureEntry;

previewHostApi.releaseFlutterSurfaceTexture();
verify(mockSurfaceProducer).release();
verify(mockSurfaceTextureEntry).release();
}

@Test
Expand Down
2 changes: 1 addition & 1 deletion packages/camera/camera_android_camerax/pubspec.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ name: camera_android_camerax
description: Android implementation of the camera plugin using the CameraX library.
repository: https://github.com/flutter/packages/tree/main/packages/camera/camera_android_camerax
issue_tracker: https://github.com/flutter/flutter/issues?q=is%3Aissue+is%3Aopen+label%3A%22p%3A+camera%22
version: 0.6.5+4
version: 0.6.5+5

environment:
sdk: ^3.4.0
Expand Down