11
11
import android .view .Surface ;
12
12
import io .flutter .view .TextureRegistry .ImageTextureEntry ;
13
13
14
- @ TargetApi (26 )
14
+ @ TargetApi (29 )
15
15
public class ImageReaderPlatformViewRenderTarget implements PlatformViewRenderTarget {
16
16
private ImageTextureEntry textureEntry ;
17
- private boolean mustRecreateImageReader = false ;
18
17
private ImageReader reader ;
19
18
private int bufferWidth = 0 ;
20
19
private int bufferHeight = 0 ;
21
20
private static final String TAG = "ImageReaderPlatformViewRenderTarget" ;
22
21
23
22
private void closeReader () {
24
23
if (this .reader != null ) {
24
+ // Push a null image, forcing the texture entry to close any cached images.
25
+ textureEntry .pushImage (null );
26
+ // Close the reader, which also closes any produced images.
25
27
this .reader .close ();
26
28
this .reader = null ;
27
29
}
28
30
}
29
31
30
- private void recreateImageReaderIfNeeded () {
31
- if (!mustRecreateImageReader ) {
32
- return ;
33
- }
34
- mustRecreateImageReader = false ;
35
- closeReader ();
36
- this .reader = createImageReader ();
37
- }
38
-
39
32
private final Handler onImageAvailableHandler = new Handler ();
40
33
private final ImageReader .OnImageAvailableListener onImageAvailableListener =
41
34
new ImageReader .OnImageAvailableListener () {
@@ -55,9 +48,12 @@ protected ImageReader createImageReader33() {
55
48
// Allow for double buffering.
56
49
builder .setMaxImages (3 );
57
50
// Use PRIVATE image format so that we can support video decoding.
58
- // TODO(johnmccutchan): Should we always use PRIVATE here? It may impact our ability
59
- // to read back texture data. If we don't always want to use it, how do we decide when
60
- // to use it or not? Perhaps PlatformViews can indicate if they may contain DRM'd content.
51
+ // TODO(johnmccutchan): Should we always use PRIVATE here? It may impact our
52
+ // ability to read back texture data. If we don't always want to use it, how do we
53
+ // decide when to use it or not? Perhaps PlatformViews can indicate if they may contain
54
+ // DRM'd content.
55
+ // I need to investigate how PRIVATE impacts our ability to take screenshots or capture
56
+ // the output of Flutter application.
61
57
builder .setImageFormat (ImageFormat .PRIVATE );
62
58
// Hint that consumed images will only be read by GPU.
63
59
builder .setUsage (HardwareBuffer .USAGE_GPU_SAMPLED_IMAGE );
@@ -68,29 +64,31 @@ protected ImageReader createImageReader33() {
68
64
69
65
@ TargetApi (29 )
70
66
protected ImageReader createImageReader29 () {
71
- return ImageReader .newInstance (
72
- bufferWidth , bufferHeight , ImageFormat .PRIVATE , 2 , HardwareBuffer .USAGE_GPU_SAMPLED_IMAGE );
73
- }
74
-
75
- @ TargetApi (26 )
76
- protected ImageReader createImageReader26 () {
77
- return ImageReader .newInstance (bufferWidth , bufferHeight , ImageFormat .PRIVATE , 2 );
67
+ final ImageReader reader =
68
+ ImageReader .newInstance (
69
+ bufferWidth ,
70
+ bufferHeight ,
71
+ ImageFormat .PRIVATE ,
72
+ 2 ,
73
+ HardwareBuffer .USAGE_GPU_SAMPLED_IMAGE );
74
+ reader .setOnImageAvailableListener (this .onImageAvailableListener , onImageAvailableHandler );
75
+ return reader ;
78
76
}
79
77
80
78
protected ImageReader createImageReader () {
81
79
if (Build .VERSION .SDK_INT >= 33 ) {
82
80
return createImageReader33 ();
83
81
} else if (Build .VERSION .SDK_INT >= 29 ) {
84
82
return createImageReader29 ();
85
- } else {
86
- return createImageReader26 ();
87
83
}
84
+ throw new UnsupportedOperationException (
85
+ "ImageReaderPlatformViewRenderTarget requires API version 29+" );
88
86
}
89
87
90
88
public ImageReaderPlatformViewRenderTarget (ImageTextureEntry textureEntry ) {
91
- if (Build .VERSION .SDK_INT < 26 ) {
89
+ if (Build .VERSION .SDK_INT < 29 ) {
92
90
throw new UnsupportedOperationException (
93
- "ImageReaderPlatformViewRenderTarget requires API version 26 +" );
91
+ "ImageReaderPlatformViewRenderTarget requires API version 29 +" );
94
92
}
95
93
this .textureEntry = textureEntry ;
96
94
}
@@ -127,17 +125,16 @@ public long getId() {
127
125
}
128
126
129
127
public void release () {
128
+ closeReader ();
130
129
// textureEntry has a finalizer attached.
131
130
textureEntry = null ;
132
- closeReader ();
133
131
}
134
132
135
133
public boolean isReleased () {
136
134
return this .textureEntry == null ;
137
135
}
138
136
139
137
public Surface getSurface () {
140
- recreateImageReaderIfNeeded ();
141
138
return this .reader .getSurface ();
142
139
}
143
140
}
0 commit comments