• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2013 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package android.view;
18 
19 import static android.graphics.Matrix.MSCALE_X;
20 import static android.graphics.Matrix.MSCALE_Y;
21 import static android.graphics.Matrix.MSKEW_X;
22 import static android.graphics.Matrix.MSKEW_Y;
23 import static android.graphics.Matrix.MTRANS_X;
24 import static android.graphics.Matrix.MTRANS_Y;
25 import static android.view.Surface.ROTATION_270;
26 import static android.view.Surface.ROTATION_90;
27 import static android.view.SurfaceControlProto.HASH_CODE;
28 import static android.view.SurfaceControlProto.NAME;
29 
30 import android.annotation.Size;
31 import android.graphics.Bitmap;
32 import android.graphics.GraphicBuffer;
33 import android.graphics.Matrix;
34 import android.graphics.PixelFormat;
35 import android.graphics.Point;
36 import android.graphics.Rect;
37 import android.graphics.Region;
38 import android.os.IBinder;
39 import android.os.Parcel;
40 import android.os.Parcelable;
41 import android.os.Process;
42 import android.os.UserHandle;
43 import android.util.ArrayMap;
44 import android.util.Log;
45 import android.util.proto.ProtoOutputStream;
46 import android.view.Surface.OutOfResourcesException;
47 
48 import com.android.internal.annotations.GuardedBy;
49 
50 import dalvik.system.CloseGuard;
51 
52 import libcore.util.NativeAllocationRegistry;
53 
54 import java.io.Closeable;
55 
56 /**
57  * SurfaceControl
58  *  @hide
59  */
60 public class SurfaceControl implements Parcelable {
61     private static final String TAG = "SurfaceControl";
62 
nativeCreate(SurfaceSession session, String name, int w, int h, int format, int flags, long parentObject, int windowType, int ownerUid)63     private static native long nativeCreate(SurfaceSession session, String name,
64             int w, int h, int format, int flags, long parentObject, int windowType, int ownerUid)
65             throws OutOfResourcesException;
nativeReadFromParcel(Parcel in)66     private static native long nativeReadFromParcel(Parcel in);
nativeWriteToParcel(long nativeObject, Parcel out)67     private static native void nativeWriteToParcel(long nativeObject, Parcel out);
nativeRelease(long nativeObject)68     private static native void nativeRelease(long nativeObject);
nativeDestroy(long nativeObject)69     private static native void nativeDestroy(long nativeObject);
nativeDisconnect(long nativeObject)70     private static native void nativeDisconnect(long nativeObject);
71 
nativeScreenshot(IBinder displayToken, Rect sourceCrop, int width, int height, int minLayer, int maxLayer, boolean allLayers, boolean useIdentityTransform, int rotation)72     private static native Bitmap nativeScreenshot(IBinder displayToken,
73             Rect sourceCrop, int width, int height, int minLayer, int maxLayer,
74             boolean allLayers, boolean useIdentityTransform, int rotation);
nativeScreenshotToBuffer(IBinder displayToken, Rect sourceCrop, int width, int height, int minLayer, int maxLayer, boolean allLayers, boolean useIdentityTransform, int rotation, boolean captureSecureLayers)75     private static native GraphicBuffer nativeScreenshotToBuffer(IBinder displayToken,
76             Rect sourceCrop, int width, int height, int minLayer, int maxLayer,
77             boolean allLayers, boolean useIdentityTransform, int rotation,
78             boolean captureSecureLayers);
nativeScreenshot(IBinder displayToken, Surface consumer, Rect sourceCrop, int width, int height, int minLayer, int maxLayer, boolean allLayers, boolean useIdentityTransform)79     private static native void nativeScreenshot(IBinder displayToken, Surface consumer,
80             Rect sourceCrop, int width, int height, int minLayer, int maxLayer,
81             boolean allLayers, boolean useIdentityTransform);
nativeCaptureLayers(IBinder layerHandleToken, Rect sourceCrop, float frameScale)82     private static native GraphicBuffer nativeCaptureLayers(IBinder layerHandleToken,
83             Rect sourceCrop, float frameScale);
84 
nativeCreateTransaction()85     private static native long nativeCreateTransaction();
nativeGetNativeTransactionFinalizer()86     private static native long nativeGetNativeTransactionFinalizer();
nativeApplyTransaction(long transactionObj, boolean sync)87     private static native void nativeApplyTransaction(long transactionObj, boolean sync);
nativeMergeTransaction(long transactionObj, long otherTransactionObj)88     private static native void nativeMergeTransaction(long transactionObj,
89             long otherTransactionObj);
nativeSetAnimationTransaction(long transactionObj)90     private static native void nativeSetAnimationTransaction(long transactionObj);
nativeSetEarlyWakeup(long transactionObj)91     private static native void nativeSetEarlyWakeup(long transactionObj);
92 
nativeSetLayer(long transactionObj, long nativeObject, int zorder)93     private static native void nativeSetLayer(long transactionObj, long nativeObject, int zorder);
nativeSetRelativeLayer(long transactionObj, long nativeObject, IBinder relativeTo, int zorder)94     private static native void nativeSetRelativeLayer(long transactionObj, long nativeObject,
95             IBinder relativeTo, int zorder);
nativeSetPosition(long transactionObj, long nativeObject, float x, float y)96     private static native void nativeSetPosition(long transactionObj, long nativeObject,
97             float x, float y);
nativeSetGeometryAppliesWithResize(long transactionObj, long nativeObject)98     private static native void nativeSetGeometryAppliesWithResize(long transactionObj,
99             long nativeObject);
nativeSetSize(long transactionObj, long nativeObject, int w, int h)100     private static native void nativeSetSize(long transactionObj, long nativeObject, int w, int h);
nativeSetTransparentRegionHint(long transactionObj, long nativeObject, Region region)101     private static native void nativeSetTransparentRegionHint(long transactionObj,
102             long nativeObject, Region region);
nativeSetAlpha(long transactionObj, long nativeObject, float alpha)103     private static native void nativeSetAlpha(long transactionObj, long nativeObject, float alpha);
nativeSetMatrix(long transactionObj, long nativeObject, float dsdx, float dtdx, float dtdy, float dsdy)104     private static native void nativeSetMatrix(long transactionObj, long nativeObject,
105             float dsdx, float dtdx,
106             float dtdy, float dsdy);
nativeSetColor(long transactionObj, long nativeObject, float[] color)107     private static native void nativeSetColor(long transactionObj, long nativeObject, float[] color);
nativeSetFlags(long transactionObj, long nativeObject, int flags, int mask)108     private static native void nativeSetFlags(long transactionObj, long nativeObject,
109             int flags, int mask);
nativeSetWindowCrop(long transactionObj, long nativeObject, int l, int t, int r, int b)110     private static native void nativeSetWindowCrop(long transactionObj, long nativeObject,
111             int l, int t, int r, int b);
nativeSetFinalCrop(long transactionObj, long nativeObject, int l, int t, int r, int b)112     private static native void nativeSetFinalCrop(long transactionObj, long nativeObject,
113             int l, int t, int r, int b);
nativeSetLayerStack(long transactionObj, long nativeObject, int layerStack)114     private static native void nativeSetLayerStack(long transactionObj, long nativeObject,
115             int layerStack);
116 
nativeClearContentFrameStats(long nativeObject)117     private static native boolean nativeClearContentFrameStats(long nativeObject);
nativeGetContentFrameStats(long nativeObject, WindowContentFrameStats outStats)118     private static native boolean nativeGetContentFrameStats(long nativeObject, WindowContentFrameStats outStats);
nativeClearAnimationFrameStats()119     private static native boolean nativeClearAnimationFrameStats();
nativeGetAnimationFrameStats(WindowAnimationFrameStats outStats)120     private static native boolean nativeGetAnimationFrameStats(WindowAnimationFrameStats outStats);
121 
nativeGetBuiltInDisplay(int physicalDisplayId)122     private static native IBinder nativeGetBuiltInDisplay(int physicalDisplayId);
nativeCreateDisplay(String name, boolean secure)123     private static native IBinder nativeCreateDisplay(String name, boolean secure);
nativeDestroyDisplay(IBinder displayToken)124     private static native void nativeDestroyDisplay(IBinder displayToken);
nativeSetDisplaySurface(long transactionObj, IBinder displayToken, long nativeSurfaceObject)125     private static native void nativeSetDisplaySurface(long transactionObj,
126             IBinder displayToken, long nativeSurfaceObject);
nativeSetDisplayLayerStack(long transactionObj, IBinder displayToken, int layerStack)127     private static native void nativeSetDisplayLayerStack(long transactionObj,
128             IBinder displayToken, int layerStack);
nativeSetDisplayProjection(long transactionObj, IBinder displayToken, int orientation, int l, int t, int r, int b, int L, int T, int R, int B)129     private static native void nativeSetDisplayProjection(long transactionObj,
130             IBinder displayToken, int orientation,
131             int l, int t, int r, int b,
132             int L, int T, int R, int B);
nativeSetDisplaySize(long transactionObj, IBinder displayToken, int width, int height)133     private static native void nativeSetDisplaySize(long transactionObj, IBinder displayToken,
134             int width, int height);
nativeGetDisplayConfigs( IBinder displayToken)135     private static native SurfaceControl.PhysicalDisplayInfo[] nativeGetDisplayConfigs(
136             IBinder displayToken);
nativeGetActiveConfig(IBinder displayToken)137     private static native int nativeGetActiveConfig(IBinder displayToken);
nativeSetActiveConfig(IBinder displayToken, int id)138     private static native boolean nativeSetActiveConfig(IBinder displayToken, int id);
nativeGetDisplayColorModes(IBinder displayToken)139     private static native int[] nativeGetDisplayColorModes(IBinder displayToken);
nativeGetActiveColorMode(IBinder displayToken)140     private static native int nativeGetActiveColorMode(IBinder displayToken);
nativeSetActiveColorMode(IBinder displayToken, int colorMode)141     private static native boolean nativeSetActiveColorMode(IBinder displayToken,
142             int colorMode);
nativeSetDisplayPowerMode( IBinder displayToken, int mode)143     private static native void nativeSetDisplayPowerMode(
144             IBinder displayToken, int mode);
nativeDeferTransactionUntil(long transactionObj, long nativeObject, IBinder handle, long frame)145     private static native void nativeDeferTransactionUntil(long transactionObj, long nativeObject,
146             IBinder handle, long frame);
nativeDeferTransactionUntilSurface(long transactionObj, long nativeObject, long surfaceObject, long frame)147     private static native void nativeDeferTransactionUntilSurface(long transactionObj,
148             long nativeObject,
149             long surfaceObject, long frame);
nativeReparentChildren(long transactionObj, long nativeObject, IBinder handle)150     private static native void nativeReparentChildren(long transactionObj, long nativeObject,
151             IBinder handle);
nativeReparent(long transactionObj, long nativeObject, IBinder parentHandle)152     private static native void nativeReparent(long transactionObj, long nativeObject,
153             IBinder parentHandle);
nativeSeverChildren(long transactionObj, long nativeObject)154     private static native void nativeSeverChildren(long transactionObj, long nativeObject);
nativeSetOverrideScalingMode(long transactionObj, long nativeObject, int scalingMode)155     private static native void nativeSetOverrideScalingMode(long transactionObj, long nativeObject,
156             int scalingMode);
nativeDestroy(long transactionObj, long nativeObject)157     private static native void nativeDestroy(long transactionObj, long nativeObject);
nativeGetHandle(long nativeObject)158     private static native IBinder nativeGetHandle(long nativeObject);
nativeGetTransformToDisplayInverse(long nativeObject)159     private static native boolean nativeGetTransformToDisplayInverse(long nativeObject);
160 
nativeGetHdrCapabilities(IBinder displayToken)161     private static native Display.HdrCapabilities nativeGetHdrCapabilities(IBinder displayToken);
162 
163 
164     private final CloseGuard mCloseGuard = CloseGuard.get();
165     private final String mName;
166     long mNativeObject; // package visibility only for Surface.java access
167 
168     // TODO: Move this to native.
169     private final Object mSizeLock = new Object();
170     @GuardedBy("mSizeLock")
171     private int mWidth;
172     @GuardedBy("mSizeLock")
173     private int mHeight;
174 
175     static Transaction sGlobalTransaction;
176     static long sTransactionNestCount = 0;
177 
178     /* flags used in constructor (keep in sync with ISurfaceComposerClient.h) */
179 
180     /**
181      * Surface creation flag: Surface is created hidden
182      */
183     public static final int HIDDEN = 0x00000004;
184 
185     /**
186      * Surface creation flag: The surface contains secure content, special
187      * measures will be taken to disallow the surface's content to be copied
188      * from another process. In particular, screenshots and VNC servers will
189      * be disabled, but other measures can take place, for instance the
190      * surface might not be hardware accelerated.
191      *
192      */
193     public static final int SECURE = 0x00000080;
194 
195     /**
196      * Surface creation flag: Creates a surface where color components are interpreted
197      * as "non pre-multiplied" by their alpha channel. Of course this flag is
198      * meaningless for surfaces without an alpha channel. By default
199      * surfaces are pre-multiplied, which means that each color component is
200      * already multiplied by its alpha value. In this case the blending
201      * equation used is:
202      * <p>
203      *    <code>DEST = SRC + DEST * (1-SRC_ALPHA)</code>
204      * <p>
205      * By contrast, non pre-multiplied surfaces use the following equation:
206      * <p>
207      *    <code>DEST = SRC * SRC_ALPHA * DEST * (1-SRC_ALPHA)</code>
208      * <p>
209      * pre-multiplied surfaces must always be used if transparent pixels are
210      * composited on top of each-other into the surface. A pre-multiplied
211      * surface can never lower the value of the alpha component of a given
212      * pixel.
213      * <p>
214      * In some rare situations, a non pre-multiplied surface is preferable.
215      *
216      */
217     public static final int NON_PREMULTIPLIED = 0x00000100;
218 
219     /**
220      * Surface creation flag: Indicates that the surface must be considered opaque,
221      * even if its pixel format contains an alpha channel. This can be useful if an
222      * application needs full RGBA 8888 support for instance but will
223      * still draw every pixel opaque.
224      * <p>
225      * This flag is ignored if setAlpha() is used to make the surface non-opaque.
226      * Combined effects are (assuming a buffer format with an alpha channel):
227      * <ul>
228      * <li>OPAQUE + alpha(1.0) == opaque composition
229      * <li>OPAQUE + alpha(0.x) == blended composition
230      * <li>!OPAQUE + alpha(1.0) == blended composition
231      * <li>!OPAQUE + alpha(0.x) == blended composition
232      * </ul>
233      * If the underlying buffer lacks an alpha channel, the OPAQUE flag is effectively
234      * set automatically.
235      */
236     public static final int OPAQUE = 0x00000400;
237 
238     /**
239      * Surface creation flag: Application requires a hardware-protected path to an
240      * external display sink. If a hardware-protected path is not available,
241      * then this surface will not be displayed on the external sink.
242      *
243      */
244     public static final int PROTECTED_APP = 0x00000800;
245 
246     // 0x1000 is reserved for an independent DRM protected flag in framework
247 
248     /**
249      * Surface creation flag: Window represents a cursor glyph.
250      */
251     public static final int CURSOR_WINDOW = 0x00002000;
252 
253     /**
254      * Surface creation flag: Creates a normal surface.
255      * This is the default.
256      *
257      */
258     public static final int FX_SURFACE_NORMAL   = 0x00000000;
259 
260     /**
261      * Surface creation flag: Creates a Dim surface.
262      * Everything behind this surface is dimmed by the amount specified
263      * in {@link #setAlpha}.  It is an error to lock a Dim surface, since it
264      * doesn't have a backing store.
265      *
266      */
267     public static final int FX_SURFACE_DIM = 0x00020000;
268 
269     /**
270      * Mask used for FX values above.
271      *
272      */
273     public static final int FX_SURFACE_MASK = 0x000F0000;
274 
275     /* flags used with setFlags() (keep in sync with ISurfaceComposer.h) */
276 
277     /**
278      * Surface flag: Hide the surface.
279      * Equivalent to calling hide().
280      * Updates the value set during Surface creation (see {@link #HIDDEN}).
281      */
282     private static final int SURFACE_HIDDEN = 0x01;
283 
284     /**
285      * Surface flag: composite without blending when possible.
286      * Updates the value set during Surface creation (see {@link #OPAQUE}).
287      */
288     private static final int SURFACE_OPAQUE = 0x02;
289 
290 
291     /* built-in physical display ids (keep in sync with ISurfaceComposer.h)
292      * these are different from the logical display ids used elsewhere in the framework */
293 
294     /**
295      * Built-in physical display id: Main display.
296      * Use only with {@link SurfaceControl#getBuiltInDisplay(int)}.
297      */
298     public static final int BUILT_IN_DISPLAY_ID_MAIN = 0;
299 
300     /**
301      * Built-in physical display id: Attached HDMI display.
302      * Use only with {@link SurfaceControl#getBuiltInDisplay(int)}.
303      */
304     public static final int BUILT_IN_DISPLAY_ID_HDMI = 1;
305 
306     /* Display power modes * /
307 
308     /**
309      * Display power mode off: used while blanking the screen.
310      * Use only with {@link SurfaceControl#setDisplayPowerMode}.
311      */
312     public static final int POWER_MODE_OFF = 0;
313 
314     /**
315      * Display power mode doze: used while putting the screen into low power mode.
316      * Use only with {@link SurfaceControl#setDisplayPowerMode}.
317      */
318     public static final int POWER_MODE_DOZE = 1;
319 
320     /**
321      * Display power mode normal: used while unblanking the screen.
322      * Use only with {@link SurfaceControl#setDisplayPowerMode}.
323      */
324     public static final int POWER_MODE_NORMAL = 2;
325 
326     /**
327      * Display power mode doze: used while putting the screen into a suspended
328      * low power mode.  Use only with {@link SurfaceControl#setDisplayPowerMode}.
329      */
330     public static final int POWER_MODE_DOZE_SUSPEND = 3;
331 
332     /**
333      * Display power mode on: used while putting the screen into a suspended
334      * full power mode.  Use only with {@link SurfaceControl#setDisplayPowerMode}.
335      */
336     public static final int POWER_MODE_ON_SUSPEND = 4;
337 
338     /**
339      * A value for windowType used to indicate that the window should be omitted from screenshots
340      * and display mirroring. A temporary workaround until we express such things with
341      * the hierarchy.
342      * TODO: b/64227542
343      * @hide
344      */
345     public static final int WINDOW_TYPE_DONT_SCREENSHOT = 441731;
346 
347     /**
348      * Builder class for {@link SurfaceControl} objects.
349      */
350     public static class Builder {
351         private SurfaceSession mSession;
352         private int mFlags = HIDDEN;
353         private int mWidth;
354         private int mHeight;
355         private int mFormat = PixelFormat.OPAQUE;
356         private String mName;
357         private SurfaceControl mParent;
358         private int mWindowType = -1;
359         private int mOwnerUid = -1;
360 
361         /**
362          * Begin building a SurfaceControl with a given {@link SurfaceSession}.
363          *
364          * @param session The {@link SurfaceSession} with which to eventually construct the surface.
365          */
Builder(SurfaceSession session)366         public Builder(SurfaceSession session) {
367             mSession = session;
368         }
369 
370         /**
371          * Construct a new {@link SurfaceControl} with the set parameters.
372          */
build()373         public SurfaceControl build() {
374             if (mWidth <= 0 || mHeight <= 0) {
375                 throw new IllegalArgumentException(
376                         "width and height must be set");
377             }
378             return new SurfaceControl(mSession, mName, mWidth, mHeight, mFormat,
379                     mFlags, mParent, mWindowType, mOwnerUid);
380         }
381 
382         /**
383          * Set a debugging-name for the SurfaceControl.
384          *
385          * @param name A name to identify the Surface in debugging.
386          */
setName(String name)387         public Builder setName(String name) {
388             mName = name;
389             return this;
390         }
391 
392         /**
393          * Set the initial size of the controlled surface's buffers in pixels.
394          *
395          * @param width The buffer width in pixels.
396          * @param height The buffer height in pixels.
397          */
setSize(int width, int height)398         public Builder setSize(int width, int height) {
399             if (width <= 0 || height <= 0) {
400                 throw new IllegalArgumentException(
401                         "width and height must be positive");
402             }
403             mWidth = width;
404             mHeight = height;
405             return this;
406         }
407 
408         /**
409          * Set the pixel format of the controlled surface's buffers, using constants from
410          * {@link android.graphics.PixelFormat}.
411          */
setFormat(@ixelFormat.Format int format)412         public Builder setFormat(@PixelFormat.Format int format) {
413             mFormat = format;
414             return this;
415         }
416 
417         /**
418          * Specify if the app requires a hardware-protected path to
419          * an external display sync. If protected content is enabled, but
420          * such a path is not available, then the controlled Surface will
421          * not be displayed.
422          *
423          * @param protectedContent Whether to require a protected sink.
424          */
setProtected(boolean protectedContent)425         public Builder setProtected(boolean protectedContent) {
426             if (protectedContent) {
427                 mFlags |= PROTECTED_APP;
428             } else {
429                 mFlags &= ~PROTECTED_APP;
430             }
431             return this;
432         }
433 
434         /**
435          * Specify whether the Surface contains secure content. If true, the system
436          * will prevent the surfaces content from being copied by another process. In
437          * particular screenshots and VNC servers will be disabled. This is however
438          * not a complete prevention of readback as {@link #setProtected}.
439          */
setSecure(boolean secure)440         public Builder setSecure(boolean secure) {
441             if (secure) {
442                 mFlags |= SECURE;
443             } else {
444                 mFlags &= ~SECURE;
445             }
446             return this;
447         }
448 
449         /**
450          * Indicates whether the surface must be considered opaque,
451          * even if its pixel format is set to translucent. This can be useful if an
452          * application needs full RGBA 8888 support for instance but will
453          * still draw every pixel opaque.
454          * <p>
455          * This flag only determines whether opacity will be sampled from the alpha channel.
456          * Plane-alpha from calls to setAlpha() can still result in blended composition
457          * regardless of the opaque setting.
458          *
459          * Combined effects are (assuming a buffer format with an alpha channel):
460          * <ul>
461          * <li>OPAQUE + alpha(1.0) == opaque composition
462          * <li>OPAQUE + alpha(0.x) == blended composition
463          * <li>OPAQUE + alpha(0.0) == no composition
464          * <li>!OPAQUE + alpha(1.0) == blended composition
465          * <li>!OPAQUE + alpha(0.x) == blended composition
466          * <li>!OPAQUE + alpha(0.0) == no composition
467          * </ul>
468          * If the underlying buffer lacks an alpha channel, it is as if setOpaque(true)
469          * were set automatically.
470          * @param opaque Whether the Surface is OPAQUE.
471          */
setOpaque(boolean opaque)472         public Builder setOpaque(boolean opaque) {
473             if (opaque) {
474                 mFlags |= OPAQUE;
475             } else {
476                 mFlags &= ~OPAQUE;
477             }
478             return this;
479         }
480 
481         /**
482          * Set a parent surface for our new SurfaceControl.
483          *
484          * Child surfaces are constrained to the onscreen region of their parent.
485          * Furthermore they stack relatively in Z order, and inherit the transformation
486          * of the parent.
487          *
488          * @param parent The parent control.
489          */
setParent(SurfaceControl parent)490         public Builder setParent(SurfaceControl parent) {
491             mParent = parent;
492             return this;
493         }
494 
495         /**
496          * Set surface metadata.
497          *
498          * Currently these are window-types as per {@link WindowManager.LayoutParams} and
499          * owner UIDs. Child surfaces inherit their parents
500          * metadata so only the WindowManager needs to set this on root Surfaces.
501          *
502          * @param windowType A window-type
503          * @param ownerUid UID of the window owner.
504          */
setMetadata(int windowType, int ownerUid)505         public Builder setMetadata(int windowType, int ownerUid) {
506             if (UserHandle.getAppId(Process.myUid()) != Process.SYSTEM_UID) {
507                 throw new UnsupportedOperationException(
508                         "It only makes sense to set Surface metadata from the WindowManager");
509             }
510             mWindowType = windowType;
511             mOwnerUid = ownerUid;
512             return this;
513         }
514 
515         /**
516          * Indicate whether a 'ColorLayer' is to be constructed.
517          *
518          * Color layers will not have an associated BufferQueue and will instead always render a
519          * solid color (that is, solid before plane alpha). Currently that color is black.
520          *
521          * @param isColorLayer Whether to create a color layer.
522          */
setColorLayer(boolean isColorLayer)523         public Builder setColorLayer(boolean isColorLayer) {
524             if (isColorLayer) {
525                 mFlags |= FX_SURFACE_DIM;
526             } else {
527                 mFlags &= ~FX_SURFACE_DIM;
528             }
529             return this;
530         }
531 
532         /**
533          * Set 'Surface creation flags' such as {@link HIDDEN}, {@link SECURE}.
534          *
535          * TODO: Finish conversion to individual builder methods?
536          * @param flags The combined flags
537          */
setFlags(int flags)538         public Builder setFlags(int flags) {
539             mFlags = flags;
540             return this;
541         }
542     }
543 
544     /**
545      * Create a surface with a name.
546      * <p>
547      * The surface creation flags specify what kind of surface to create and
548      * certain options such as whether the surface can be assumed to be opaque
549      * and whether it should be initially hidden.  Surfaces should always be
550      * created with the {@link #HIDDEN} flag set to ensure that they are not
551      * made visible prematurely before all of the surface's properties have been
552      * configured.
553      * <p>
554      * Good practice is to first create the surface with the {@link #HIDDEN} flag
555      * specified, open a transaction, set the surface layer, layer stack, alpha,
556      * and position, call {@link #show} if appropriate, and close the transaction.
557      *
558      * @param session The surface session, must not be null.
559      * @param name The surface name, must not be null.
560      * @param w The surface initial width.
561      * @param h The surface initial height.
562      * @param flags The surface creation flags.  Should always include {@link #HIDDEN}
563      * in the creation flags.
564      * @param windowType The type of the window as specified in WindowManager.java.
565      * @param ownerUid A unique per-app ID.
566      *
567      * @throws throws OutOfResourcesException If the SurfaceControl cannot be created.
568      */
SurfaceControl(SurfaceSession session, String name, int w, int h, int format, int flags, SurfaceControl parent, int windowType, int ownerUid)569     private SurfaceControl(SurfaceSession session, String name, int w, int h, int format, int flags,
570             SurfaceControl parent, int windowType, int ownerUid)
571                     throws OutOfResourcesException, IllegalArgumentException {
572         if (session == null) {
573             throw new IllegalArgumentException("session must not be null");
574         }
575         if (name == null) {
576             throw new IllegalArgumentException("name must not be null");
577         }
578 
579         if ((flags & SurfaceControl.HIDDEN) == 0) {
580             Log.w(TAG, "Surfaces should always be created with the HIDDEN flag set "
581                     + "to ensure that they are not made visible prematurely before "
582                     + "all of the surface's properties have been configured.  "
583                     + "Set the other properties and make the surface visible within "
584                     + "a transaction.  New surface name: " + name,
585                     new Throwable());
586         }
587 
588         mName = name;
589         mWidth = w;
590         mHeight = h;
591         mNativeObject = nativeCreate(session, name, w, h, format, flags,
592             parent != null ? parent.mNativeObject : 0, windowType, ownerUid);
593         if (mNativeObject == 0) {
594             throw new OutOfResourcesException(
595                     "Couldn't allocate SurfaceControl native object");
596         }
597 
598         mCloseGuard.open("release");
599     }
600 
601     // This is a transfer constructor, useful for transferring a live SurfaceControl native
602     // object to another Java wrapper which could have some different behavior, e.g.
603     // event logging.
SurfaceControl(SurfaceControl other)604     public SurfaceControl(SurfaceControl other) {
605         mName = other.mName;
606         mWidth = other.mWidth;
607         mHeight = other.mHeight;
608         mNativeObject = other.mNativeObject;
609         other.mCloseGuard.close();
610         other.mNativeObject = 0;
611         mCloseGuard.open("release");
612     }
613 
SurfaceControl(Parcel in)614     private SurfaceControl(Parcel in) {
615         mName = in.readString();
616         mWidth = in.readInt();
617         mHeight = in.readInt();
618         mNativeObject = nativeReadFromParcel(in);
619         if (mNativeObject == 0) {
620             throw new IllegalArgumentException("Couldn't read SurfaceControl from parcel=" + in);
621         }
622         mCloseGuard.open("release");
623     }
624 
625     @Override
describeContents()626     public int describeContents() {
627         return 0;
628     }
629 
630     @Override
writeToParcel(Parcel dest, int flags)631     public void writeToParcel(Parcel dest, int flags) {
632         dest.writeString(mName);
633         dest.writeInt(mWidth);
634         dest.writeInt(mHeight);
635         nativeWriteToParcel(mNativeObject, dest);
636     }
637 
638     /**
639      * Write to a protocol buffer output stream. Protocol buffer message definition is at {@link
640      * android.view.SurfaceControlProto}.
641      *
642      * @param proto Stream to write the SurfaceControl object to.
643      * @param fieldId Field Id of the SurfaceControl as defined in the parent message.
644      * @hide
645      */
writeToProto(ProtoOutputStream proto, long fieldId)646     public void writeToProto(ProtoOutputStream proto, long fieldId) {
647         final long token = proto.start(fieldId);
648         proto.write(HASH_CODE, System.identityHashCode(this));
649         proto.write(NAME, mName);
650         proto.end(token);
651     }
652 
653     public static final Creator<SurfaceControl> CREATOR
654             = new Creator<SurfaceControl>() {
655         public SurfaceControl createFromParcel(Parcel in) {
656             return new SurfaceControl(in);
657         }
658 
659         public SurfaceControl[] newArray(int size) {
660             return new SurfaceControl[size];
661         }
662     };
663 
664     @Override
finalize()665     protected void finalize() throws Throwable {
666         try {
667             if (mCloseGuard != null) {
668                 mCloseGuard.warnIfOpen();
669             }
670             if (mNativeObject != 0) {
671                 nativeRelease(mNativeObject);
672             }
673         } finally {
674             super.finalize();
675         }
676     }
677 
678     /**
679      * Release the local reference to the server-side surface.
680      * Always call release() when you're done with a Surface.
681      * This will make the surface invalid.
682      */
release()683     public void release() {
684         if (mNativeObject != 0) {
685             nativeRelease(mNativeObject);
686             mNativeObject = 0;
687         }
688         mCloseGuard.close();
689     }
690 
691     /**
692      * Free all server-side state associated with this surface and
693      * release this object's reference.  This method can only be
694      * called from the process that created the service.
695      */
destroy()696     public void destroy() {
697         if (mNativeObject != 0) {
698             nativeDestroy(mNativeObject);
699             mNativeObject = 0;
700         }
701         mCloseGuard.close();
702     }
703 
704     /**
705      * Disconnect any client still connected to the surface.
706      */
disconnect()707     public void disconnect() {
708         if (mNativeObject != 0) {
709             nativeDisconnect(mNativeObject);
710         }
711     }
712 
checkNotReleased()713     private void checkNotReleased() {
714         if (mNativeObject == 0) throw new NullPointerException(
715                 "mNativeObject is null. Have you called release() already?");
716     }
717 
718     /*
719      * set surface parameters.
720      * needs to be inside open/closeTransaction block
721      */
722 
723     /** start a transaction */
openTransaction()724     public static void openTransaction() {
725         synchronized (SurfaceControl.class) {
726             if (sGlobalTransaction == null) {
727                 sGlobalTransaction = new Transaction();
728             }
729             synchronized(SurfaceControl.class) {
730                 sTransactionNestCount++;
731             }
732         }
733     }
734 
closeTransaction(boolean sync)735     private static void closeTransaction(boolean sync) {
736         synchronized(SurfaceControl.class) {
737             if (sTransactionNestCount == 0) {
738                 Log.e(TAG, "Call to SurfaceControl.closeTransaction without matching openTransaction");
739             } else if (--sTransactionNestCount > 0) {
740                 return;
741             }
742             sGlobalTransaction.apply(sync);
743         }
744     }
745 
746     /**
747      * Merge the supplied transaction in to the deprecated "global" transaction.
748      * This clears the supplied transaction in an identical fashion to {@link Transaction#merge}.
749      * <p>
750      * This is a utility for interop with legacy-code and will go away with the Global Transaction.
751      */
752     @Deprecated
mergeToGlobalTransaction(Transaction t)753     public static void mergeToGlobalTransaction(Transaction t) {
754         synchronized(SurfaceControl.class) {
755             sGlobalTransaction.merge(t);
756         }
757     }
758 
759     /** end a transaction */
closeTransaction()760     public static void closeTransaction() {
761         closeTransaction(false);
762     }
763 
closeTransactionSync()764     public static void closeTransactionSync() {
765         closeTransaction(true);
766     }
767 
deferTransactionUntil(IBinder handle, long frame)768     public void deferTransactionUntil(IBinder handle, long frame) {
769         synchronized(SurfaceControl.class) {
770             sGlobalTransaction.deferTransactionUntil(this, handle, frame);
771         }
772     }
773 
deferTransactionUntil(Surface barrier, long frame)774     public void deferTransactionUntil(Surface barrier, long frame) {
775         synchronized(SurfaceControl.class) {
776             sGlobalTransaction.deferTransactionUntilSurface(this, barrier, frame);
777         }
778     }
779 
reparentChildren(IBinder newParentHandle)780     public void reparentChildren(IBinder newParentHandle) {
781         synchronized(SurfaceControl.class) {
782             sGlobalTransaction.reparentChildren(this, newParentHandle);
783         }
784     }
785 
reparent(IBinder newParentHandle)786     public void reparent(IBinder newParentHandle) {
787         synchronized(SurfaceControl.class) {
788             sGlobalTransaction.reparent(this, newParentHandle);
789         }
790     }
791 
detachChildren()792     public void detachChildren() {
793         synchronized(SurfaceControl.class) {
794             sGlobalTransaction.detachChildren(this);
795         }
796     }
797 
setOverrideScalingMode(int scalingMode)798     public void setOverrideScalingMode(int scalingMode) {
799         checkNotReleased();
800         synchronized(SurfaceControl.class) {
801             sGlobalTransaction.setOverrideScalingMode(this, scalingMode);
802         }
803     }
804 
getHandle()805     public IBinder getHandle() {
806         return nativeGetHandle(mNativeObject);
807     }
808 
setAnimationTransaction()809     public static void setAnimationTransaction() {
810         synchronized (SurfaceControl.class) {
811             sGlobalTransaction.setAnimationTransaction();
812         }
813     }
814 
setLayer(int zorder)815     public void setLayer(int zorder) {
816         checkNotReleased();
817         synchronized(SurfaceControl.class) {
818             sGlobalTransaction.setLayer(this, zorder);
819         }
820     }
821 
setRelativeLayer(SurfaceControl relativeTo, int zorder)822     public void setRelativeLayer(SurfaceControl relativeTo, int zorder) {
823         checkNotReleased();
824         synchronized(SurfaceControl.class) {
825             sGlobalTransaction.setRelativeLayer(this, relativeTo, zorder);
826         }
827     }
828 
setPosition(float x, float y)829     public void setPosition(float x, float y) {
830         checkNotReleased();
831         synchronized(SurfaceControl.class) {
832             sGlobalTransaction.setPosition(this, x, y);
833         }
834     }
835 
setGeometryAppliesWithResize()836     public void setGeometryAppliesWithResize() {
837         checkNotReleased();
838         synchronized(SurfaceControl.class) {
839             sGlobalTransaction.setGeometryAppliesWithResize(this);
840         }
841     }
842 
setSize(int w, int h)843     public void setSize(int w, int h) {
844         checkNotReleased();
845         synchronized(SurfaceControl.class) {
846             sGlobalTransaction.setSize(this, w, h);
847         }
848     }
849 
hide()850     public void hide() {
851         checkNotReleased();
852         synchronized(SurfaceControl.class) {
853             sGlobalTransaction.hide(this);
854         }
855     }
856 
show()857     public void show() {
858         checkNotReleased();
859         synchronized(SurfaceControl.class) {
860             sGlobalTransaction.show(this);
861         }
862     }
863 
setTransparentRegionHint(Region region)864     public void setTransparentRegionHint(Region region) {
865         checkNotReleased();
866         synchronized(SurfaceControl.class) {
867             sGlobalTransaction.setTransparentRegionHint(this, region);
868         }
869     }
870 
clearContentFrameStats()871     public boolean clearContentFrameStats() {
872         checkNotReleased();
873         return nativeClearContentFrameStats(mNativeObject);
874     }
875 
getContentFrameStats(WindowContentFrameStats outStats)876     public boolean getContentFrameStats(WindowContentFrameStats outStats) {
877         checkNotReleased();
878         return nativeGetContentFrameStats(mNativeObject, outStats);
879     }
880 
clearAnimationFrameStats()881     public static boolean clearAnimationFrameStats() {
882         return nativeClearAnimationFrameStats();
883     }
884 
getAnimationFrameStats(WindowAnimationFrameStats outStats)885     public static boolean getAnimationFrameStats(WindowAnimationFrameStats outStats) {
886         return nativeGetAnimationFrameStats(outStats);
887     }
888 
setAlpha(float alpha)889     public void setAlpha(float alpha) {
890         checkNotReleased();
891         synchronized(SurfaceControl.class) {
892             sGlobalTransaction.setAlpha(this, alpha);
893         }
894     }
895 
setColor(@ize3) float[] color)896     public void setColor(@Size(3) float[] color) {
897         checkNotReleased();
898         synchronized (SurfaceControl.class) {
899             sGlobalTransaction.setColor(this, color);
900         }
901     }
902 
setMatrix(float dsdx, float dtdx, float dtdy, float dsdy)903     public void setMatrix(float dsdx, float dtdx, float dtdy, float dsdy) {
904         checkNotReleased();
905         synchronized(SurfaceControl.class) {
906             sGlobalTransaction.setMatrix(this, dsdx, dtdx, dtdy, dsdy);
907         }
908     }
909 
910     /**
911      * Sets the transform and position of a {@link SurfaceControl} from a 3x3 transformation matrix.
912      *
913      * @param matrix The matrix to apply.
914      * @param float9 An array of 9 floats to be used to extract the values from the matrix.
915      */
setMatrix(Matrix matrix, float[] float9)916     public void setMatrix(Matrix matrix, float[] float9) {
917         checkNotReleased();
918         matrix.getValues(float9);
919         synchronized (SurfaceControl.class) {
920             sGlobalTransaction.setMatrix(this, float9[MSCALE_X], float9[MSKEW_Y],
921                     float9[MSKEW_X], float9[MSCALE_Y]);
922             sGlobalTransaction.setPosition(this, float9[MTRANS_X], float9[MTRANS_Y]);
923         }
924     }
925 
setWindowCrop(Rect crop)926     public void setWindowCrop(Rect crop) {
927         checkNotReleased();
928         synchronized (SurfaceControl.class) {
929             sGlobalTransaction.setWindowCrop(this, crop);
930         }
931     }
932 
setFinalCrop(Rect crop)933     public void setFinalCrop(Rect crop) {
934         checkNotReleased();
935         synchronized (SurfaceControl.class) {
936             sGlobalTransaction.setFinalCrop(this, crop);
937         }
938     }
939 
setLayerStack(int layerStack)940     public void setLayerStack(int layerStack) {
941         checkNotReleased();
942         synchronized(SurfaceControl.class) {
943             sGlobalTransaction.setLayerStack(this, layerStack);
944         }
945     }
946 
setOpaque(boolean isOpaque)947     public void setOpaque(boolean isOpaque) {
948         checkNotReleased();
949 
950         synchronized (SurfaceControl.class) {
951             sGlobalTransaction.setOpaque(this, isOpaque);
952         }
953     }
954 
setSecure(boolean isSecure)955     public void setSecure(boolean isSecure) {
956         checkNotReleased();
957 
958         synchronized (SurfaceControl.class) {
959             sGlobalTransaction.setSecure(this, isSecure);
960         }
961     }
962 
getWidth()963     public int getWidth() {
964         synchronized (mSizeLock) {
965             return mWidth;
966         }
967     }
968 
getHeight()969     public int getHeight() {
970         synchronized (mSizeLock) {
971             return mHeight;
972         }
973     }
974 
975     @Override
toString()976     public String toString() {
977         return "Surface(name=" + mName + ")/@0x" +
978                 Integer.toHexString(System.identityHashCode(this));
979     }
980 
981     /*
982      * set display parameters.
983      * needs to be inside open/closeTransaction block
984      */
985 
986     /**
987      * Describes the properties of a physical display known to surface flinger.
988      */
989     public static final class PhysicalDisplayInfo {
990         public int width;
991         public int height;
992         public float refreshRate;
993         public float density;
994         public float xDpi;
995         public float yDpi;
996         public boolean secure;
997         public long appVsyncOffsetNanos;
998         public long presentationDeadlineNanos;
999 
PhysicalDisplayInfo()1000         public PhysicalDisplayInfo() {
1001         }
1002 
PhysicalDisplayInfo(PhysicalDisplayInfo other)1003         public PhysicalDisplayInfo(PhysicalDisplayInfo other) {
1004             copyFrom(other);
1005         }
1006 
1007         @Override
equals(Object o)1008         public boolean equals(Object o) {
1009             return o instanceof PhysicalDisplayInfo && equals((PhysicalDisplayInfo)o);
1010         }
1011 
equals(PhysicalDisplayInfo other)1012         public boolean equals(PhysicalDisplayInfo other) {
1013             return other != null
1014                     && width == other.width
1015                     && height == other.height
1016                     && refreshRate == other.refreshRate
1017                     && density == other.density
1018                     && xDpi == other.xDpi
1019                     && yDpi == other.yDpi
1020                     && secure == other.secure
1021                     && appVsyncOffsetNanos == other.appVsyncOffsetNanos
1022                     && presentationDeadlineNanos == other.presentationDeadlineNanos;
1023         }
1024 
1025         @Override
hashCode()1026         public int hashCode() {
1027             return 0; // don't care
1028         }
1029 
copyFrom(PhysicalDisplayInfo other)1030         public void copyFrom(PhysicalDisplayInfo other) {
1031             width = other.width;
1032             height = other.height;
1033             refreshRate = other.refreshRate;
1034             density = other.density;
1035             xDpi = other.xDpi;
1036             yDpi = other.yDpi;
1037             secure = other.secure;
1038             appVsyncOffsetNanos = other.appVsyncOffsetNanos;
1039             presentationDeadlineNanos = other.presentationDeadlineNanos;
1040         }
1041 
1042         // For debugging purposes
1043         @Override
toString()1044         public String toString() {
1045             return "PhysicalDisplayInfo{" + width + " x " + height + ", " + refreshRate + " fps, "
1046                     + "density " + density + ", " + xDpi + " x " + yDpi + " dpi, secure " + secure
1047                     + ", appVsyncOffset " + appVsyncOffsetNanos
1048                     + ", bufferDeadline " + presentationDeadlineNanos + "}";
1049         }
1050     }
1051 
setDisplayPowerMode(IBinder displayToken, int mode)1052     public static void setDisplayPowerMode(IBinder displayToken, int mode) {
1053         if (displayToken == null) {
1054             throw new IllegalArgumentException("displayToken must not be null");
1055         }
1056         nativeSetDisplayPowerMode(displayToken, mode);
1057     }
1058 
getDisplayConfigs(IBinder displayToken)1059     public static SurfaceControl.PhysicalDisplayInfo[] getDisplayConfigs(IBinder displayToken) {
1060         if (displayToken == null) {
1061             throw new IllegalArgumentException("displayToken must not be null");
1062         }
1063         return nativeGetDisplayConfigs(displayToken);
1064     }
1065 
getActiveConfig(IBinder displayToken)1066     public static int getActiveConfig(IBinder displayToken) {
1067         if (displayToken == null) {
1068             throw new IllegalArgumentException("displayToken must not be null");
1069         }
1070         return nativeGetActiveConfig(displayToken);
1071     }
1072 
setActiveConfig(IBinder displayToken, int id)1073     public static boolean setActiveConfig(IBinder displayToken, int id) {
1074         if (displayToken == null) {
1075             throw new IllegalArgumentException("displayToken must not be null");
1076         }
1077         return nativeSetActiveConfig(displayToken, id);
1078     }
1079 
getDisplayColorModes(IBinder displayToken)1080     public static int[] getDisplayColorModes(IBinder displayToken) {
1081         if (displayToken == null) {
1082             throw new IllegalArgumentException("displayToken must not be null");
1083         }
1084         return nativeGetDisplayColorModes(displayToken);
1085     }
1086 
getActiveColorMode(IBinder displayToken)1087     public static int getActiveColorMode(IBinder displayToken) {
1088         if (displayToken == null) {
1089             throw new IllegalArgumentException("displayToken must not be null");
1090         }
1091         return nativeGetActiveColorMode(displayToken);
1092     }
1093 
setActiveColorMode(IBinder displayToken, int colorMode)1094     public static boolean setActiveColorMode(IBinder displayToken, int colorMode) {
1095         if (displayToken == null) {
1096             throw new IllegalArgumentException("displayToken must not be null");
1097         }
1098         return nativeSetActiveColorMode(displayToken, colorMode);
1099     }
1100 
setDisplayProjection(IBinder displayToken, int orientation, Rect layerStackRect, Rect displayRect)1101     public static void setDisplayProjection(IBinder displayToken,
1102             int orientation, Rect layerStackRect, Rect displayRect) {
1103         synchronized (SurfaceControl.class) {
1104             sGlobalTransaction.setDisplayProjection(displayToken, orientation,
1105                     layerStackRect, displayRect);
1106         }
1107     }
1108 
setDisplayLayerStack(IBinder displayToken, int layerStack)1109     public static void setDisplayLayerStack(IBinder displayToken, int layerStack) {
1110         synchronized (SurfaceControl.class) {
1111             sGlobalTransaction.setDisplayLayerStack(displayToken, layerStack);
1112         }
1113     }
1114 
setDisplaySurface(IBinder displayToken, Surface surface)1115     public static void setDisplaySurface(IBinder displayToken, Surface surface) {
1116         synchronized (SurfaceControl.class) {
1117             sGlobalTransaction.setDisplaySurface(displayToken, surface);
1118         }
1119     }
1120 
setDisplaySize(IBinder displayToken, int width, int height)1121     public static void setDisplaySize(IBinder displayToken, int width, int height) {
1122         synchronized (SurfaceControl.class) {
1123             sGlobalTransaction.setDisplaySize(displayToken, width, height);
1124         }
1125     }
1126 
getHdrCapabilities(IBinder displayToken)1127     public static Display.HdrCapabilities getHdrCapabilities(IBinder displayToken) {
1128         if (displayToken == null) {
1129             throw new IllegalArgumentException("displayToken must not be null");
1130         }
1131         return nativeGetHdrCapabilities(displayToken);
1132     }
1133 
createDisplay(String name, boolean secure)1134     public static IBinder createDisplay(String name, boolean secure) {
1135         if (name == null) {
1136             throw new IllegalArgumentException("name must not be null");
1137         }
1138         return nativeCreateDisplay(name, secure);
1139     }
1140 
destroyDisplay(IBinder displayToken)1141     public static void destroyDisplay(IBinder displayToken) {
1142         if (displayToken == null) {
1143             throw new IllegalArgumentException("displayToken must not be null");
1144         }
1145         nativeDestroyDisplay(displayToken);
1146     }
1147 
getBuiltInDisplay(int builtInDisplayId)1148     public static IBinder getBuiltInDisplay(int builtInDisplayId) {
1149         return nativeGetBuiltInDisplay(builtInDisplayId);
1150     }
1151 
1152     /**
1153      * Copy the current screen contents into the provided {@link Surface}
1154      *
1155      * @param display The display to take the screenshot of.
1156      * @param consumer The {@link Surface} to take the screenshot into.
1157      * @param width The desired width of the returned bitmap; the raw
1158      * screen will be scaled down to this size.
1159      * @param height The desired height of the returned bitmap; the raw
1160      * screen will be scaled down to this size.
1161      * @param minLayer The lowest (bottom-most Z order) surface layer to
1162      * include in the screenshot.
1163      * @param maxLayer The highest (top-most Z order) surface layer to
1164      * include in the screenshot.
1165      * @param useIdentityTransform Replace whatever transformation (rotation,
1166      * scaling, translation) the surface layers are currently using with the
1167      * identity transformation while taking the screenshot.
1168      */
screenshot(IBinder display, Surface consumer, int width, int height, int minLayer, int maxLayer, boolean useIdentityTransform)1169     public static void screenshot(IBinder display, Surface consumer,
1170             int width, int height, int minLayer, int maxLayer,
1171             boolean useIdentityTransform) {
1172         screenshot(display, consumer, new Rect(), width, height, minLayer, maxLayer,
1173                 false, useIdentityTransform);
1174     }
1175 
1176     /**
1177      * Copy the current screen contents into the provided {@link Surface}
1178      *
1179      * @param display The display to take the screenshot of.
1180      * @param consumer The {@link Surface} to take the screenshot into.
1181      * @param width The desired width of the returned bitmap; the raw
1182      * screen will be scaled down to this size.
1183      * @param height The desired height of the returned bitmap; the raw
1184      * screen will be scaled down to this size.
1185      */
screenshot(IBinder display, Surface consumer, int width, int height)1186     public static void screenshot(IBinder display, Surface consumer,
1187             int width, int height) {
1188         screenshot(display, consumer, new Rect(), width, height, 0, 0, true, false);
1189     }
1190 
1191     /**
1192      * Copy the current screen contents into the provided {@link Surface}
1193      *
1194      * @param display The display to take the screenshot of.
1195      * @param consumer The {@link Surface} to take the screenshot into.
1196      */
screenshot(IBinder display, Surface consumer)1197     public static void screenshot(IBinder display, Surface consumer) {
1198         screenshot(display, consumer, new Rect(), 0, 0, 0, 0, true, false);
1199     }
1200 
1201     /**
1202      * Copy the current screen contents into a hardware bitmap and return it.
1203      * Note: If you want to modify the Bitmap in software, you will need to copy the Bitmap into
1204      * a software Bitmap using {@link Bitmap#copy(Bitmap.Config, boolean)}
1205      *
1206      * CAVEAT: Versions of screenshot that return a {@link Bitmap} can
1207      * be extremely slow; avoid use unless absolutely necessary; prefer
1208      * the versions that use a {@link Surface} instead, such as
1209      * {@link SurfaceControl#screenshot(IBinder, Surface)}.
1210      *
1211      * @param sourceCrop The portion of the screen to capture into the Bitmap;
1212      * caller may pass in 'new Rect()' if no cropping is desired.
1213      * @param width The desired width of the returned bitmap; the raw
1214      * screen will be scaled down to this size.
1215      * @param height The desired height of the returned bitmap; the raw
1216      * screen will be scaled down to this size.
1217      * @param minLayer The lowest (bottom-most Z order) surface layer to
1218      * include in the screenshot.
1219      * @param maxLayer The highest (top-most Z order) surface layer to
1220      * include in the screenshot.
1221      * @param useIdentityTransform Replace whatever transformation (rotation,
1222      * scaling, translation) the surface layers are currently using with the
1223      * identity transformation while taking the screenshot.
1224      * @param rotation Apply a custom clockwise rotation to the screenshot, i.e.
1225      * Surface.ROTATION_0,90,180,270. Surfaceflinger will always take
1226      * screenshots in its native portrait orientation by default, so this is
1227      * useful for returning screenshots that are independent of device
1228      * orientation.
1229      * @return Returns a hardware Bitmap containing the screen contents, or null
1230      * if an error occurs. Make sure to call Bitmap.recycle() as soon as
1231      * possible, once its content is not needed anymore.
1232      */
screenshot(Rect sourceCrop, int width, int height, int minLayer, int maxLayer, boolean useIdentityTransform, int rotation)1233     public static Bitmap screenshot(Rect sourceCrop, int width, int height,
1234             int minLayer, int maxLayer, boolean useIdentityTransform,
1235             int rotation) {
1236         // TODO: should take the display as a parameter
1237         IBinder displayToken = SurfaceControl.getBuiltInDisplay(
1238                 SurfaceControl.BUILT_IN_DISPLAY_ID_MAIN);
1239         return nativeScreenshot(displayToken, sourceCrop, width, height,
1240                 minLayer, maxLayer, false, useIdentityTransform, rotation);
1241     }
1242 
1243     /**
1244      * Like {@link SurfaceControl#screenshot(Rect, int, int, int, int, boolean, int)}
1245      * but returns a GraphicBuffer.
1246      */
screenshotToBuffer(Rect sourceCrop, int width, int height, int minLayer, int maxLayer, boolean useIdentityTransform, int rotation)1247     public static GraphicBuffer screenshotToBuffer(Rect sourceCrop, int width, int height,
1248             int minLayer, int maxLayer, boolean useIdentityTransform,
1249             int rotation) {
1250         IBinder displayToken = SurfaceControl.getBuiltInDisplay(
1251                 SurfaceControl.BUILT_IN_DISPLAY_ID_MAIN);
1252         return nativeScreenshotToBuffer(displayToken, sourceCrop, width, height,
1253                 minLayer, maxLayer, false, useIdentityTransform, rotation,
1254                 false /* captureSecureLayers */);
1255     }
1256 
1257     /**
1258      * Like screenshotToBuffer, but if the caller is AID_SYSTEM, allows
1259      * for the capture of secure layers. This is used for the screen rotation
1260      * animation where the system server takes screenshots but does
1261      * not persist them or allow them to leave the server. However in other
1262      * cases in the system server, we mostly want to omit secure layers
1263      * like when we take a screenshot on behalf of the assistant.
1264      *
1265      * @hide
1266      */
screenshotToBufferWithSecureLayersUnsafe(Rect sourceCrop, int width, int height, int minLayer, int maxLayer, boolean useIdentityTransform, int rotation)1267     public static GraphicBuffer screenshotToBufferWithSecureLayersUnsafe(Rect sourceCrop,
1268             int width, int height, int minLayer, int maxLayer, boolean useIdentityTransform,
1269             int rotation) {
1270         IBinder displayToken = SurfaceControl.getBuiltInDisplay(
1271                 SurfaceControl.BUILT_IN_DISPLAY_ID_MAIN);
1272         return nativeScreenshotToBuffer(displayToken, sourceCrop, width, height,
1273                 minLayer, maxLayer, false, useIdentityTransform, rotation,
1274                 true /* captureSecureLayers */);
1275     }
1276 
1277     /**
1278      * Like {@link SurfaceControl#screenshot(Rect, int, int, int, int, boolean, int)} but
1279      * includes all Surfaces in the screenshot. This will also update the orientation so it
1280      * sends the correct coordinates to SF based on the rotation value.
1281      *
1282      * @param sourceCrop The portion of the screen to capture into the Bitmap;
1283      * caller may pass in 'new Rect()' if no cropping is desired.
1284      * @param width The desired width of the returned bitmap; the raw
1285      * screen will be scaled down to this size.
1286      * @param height The desired height of the returned bitmap; the raw
1287      * screen will be scaled down to this size.
1288      * @param rotation Apply a custom clockwise rotation to the screenshot, i.e.
1289      * Surface.ROTATION_0,90,180,270. Surfaceflinger will always take
1290      * screenshots in its native portrait orientation by default, so this is
1291      * useful for returning screenshots that are independent of device
1292      * orientation.
1293      * @return Returns a Bitmap containing the screen contents, or null
1294      * if an error occurs. Make sure to call Bitmap.recycle() as soon as
1295      * possible, once its content is not needed anymore.
1296      */
screenshot(Rect sourceCrop, int width, int height, int rotation)1297     public static Bitmap screenshot(Rect sourceCrop, int width, int height, int rotation) {
1298         // TODO: should take the display as a parameter
1299         IBinder displayToken = SurfaceControl.getBuiltInDisplay(
1300                 SurfaceControl.BUILT_IN_DISPLAY_ID_MAIN);
1301         if (rotation == ROTATION_90 || rotation == ROTATION_270) {
1302             rotation = (rotation == ROTATION_90) ? ROTATION_270 : ROTATION_90;
1303         }
1304 
1305         SurfaceControl.rotateCropForSF(sourceCrop, rotation);
1306         return nativeScreenshot(displayToken, sourceCrop, width, height, 0, 0, true,
1307                 false, rotation);
1308     }
1309 
screenshot(IBinder display, Surface consumer, Rect sourceCrop, int width, int height, int minLayer, int maxLayer, boolean allLayers, boolean useIdentityTransform)1310     private static void screenshot(IBinder display, Surface consumer, Rect sourceCrop,
1311             int width, int height, int minLayer, int maxLayer, boolean allLayers,
1312             boolean useIdentityTransform) {
1313         if (display == null) {
1314             throw new IllegalArgumentException("displayToken must not be null");
1315         }
1316         if (consumer == null) {
1317             throw new IllegalArgumentException("consumer must not be null");
1318         }
1319         nativeScreenshot(display, consumer, sourceCrop, width, height,
1320                 minLayer, maxLayer, allLayers, useIdentityTransform);
1321     }
1322 
rotateCropForSF(Rect crop, int rot)1323     private static void rotateCropForSF(Rect crop, int rot) {
1324         if (rot == Surface.ROTATION_90 || rot == Surface.ROTATION_270) {
1325             int tmp = crop.top;
1326             crop.top = crop.left;
1327             crop.left = tmp;
1328             tmp = crop.right;
1329             crop.right = crop.bottom;
1330             crop.bottom = tmp;
1331         }
1332     }
1333 
1334     /**
1335      * Captures a layer and its children and returns a {@link GraphicBuffer} with the content.
1336      *
1337      * @param layerHandleToken The root layer to capture.
1338      * @param sourceCrop       The portion of the root surface to capture; caller may pass in 'new
1339      *                         Rect()' or null if no cropping is desired.
1340      * @param frameScale       The desired scale of the returned buffer; the raw
1341      *                         screen will be scaled up/down.
1342      *
1343      * @return Returns a GraphicBuffer that contains the layer capture.
1344      */
captureLayers(IBinder layerHandleToken, Rect sourceCrop, float frameScale)1345     public static GraphicBuffer captureLayers(IBinder layerHandleToken, Rect sourceCrop,
1346             float frameScale) {
1347         return nativeCaptureLayers(layerHandleToken, sourceCrop, frameScale);
1348     }
1349 
1350     public static class Transaction implements Closeable {
1351         public static final NativeAllocationRegistry sRegistry = new NativeAllocationRegistry(
1352                 Transaction.class.getClassLoader(),
1353                 nativeGetNativeTransactionFinalizer(), 512);
1354         private long mNativeObject;
1355 
1356         private final ArrayMap<SurfaceControl, Point> mResizedSurfaces = new ArrayMap<>();
1357         Runnable mFreeNativeResources;
1358 
Transaction()1359         public Transaction() {
1360             mNativeObject = nativeCreateTransaction();
1361             mFreeNativeResources
1362                 = sRegistry.registerNativeAllocation(this, mNativeObject);
1363         }
1364 
1365         /**
1366          * Apply the transaction, clearing it's state, and making it usable
1367          * as a new transaction.
1368          */
apply()1369         public void apply() {
1370             apply(false);
1371         }
1372 
1373         /**
1374          * Close the transaction, if the transaction was not already applied this will cancel the
1375          * transaction.
1376          */
1377         @Override
close()1378         public void close() {
1379             mFreeNativeResources.run();
1380             mNativeObject = 0;
1381         }
1382 
1383         /**
1384          * Jankier version of apply. Avoid use (b/28068298).
1385          */
apply(boolean sync)1386         public void apply(boolean sync) {
1387             applyResizedSurfaces();
1388             nativeApplyTransaction(mNativeObject, sync);
1389         }
1390 
applyResizedSurfaces()1391         private void applyResizedSurfaces() {
1392             for (int i = mResizedSurfaces.size() - 1; i >= 0; i--) {
1393                 final Point size = mResizedSurfaces.valueAt(i);
1394                 final SurfaceControl surfaceControl = mResizedSurfaces.keyAt(i);
1395                 synchronized (surfaceControl.mSizeLock) {
1396                     surfaceControl.mWidth = size.x;
1397                     surfaceControl.mHeight = size.y;
1398                 }
1399             }
1400             mResizedSurfaces.clear();
1401         }
1402 
show(SurfaceControl sc)1403         public Transaction show(SurfaceControl sc) {
1404             sc.checkNotReleased();
1405             nativeSetFlags(mNativeObject, sc.mNativeObject, 0, SURFACE_HIDDEN);
1406             return this;
1407         }
1408 
hide(SurfaceControl sc)1409         public Transaction hide(SurfaceControl sc) {
1410             sc.checkNotReleased();
1411             nativeSetFlags(mNativeObject, sc.mNativeObject, SURFACE_HIDDEN, SURFACE_HIDDEN);
1412             return this;
1413         }
1414 
setPosition(SurfaceControl sc, float x, float y)1415         public Transaction setPosition(SurfaceControl sc, float x, float y) {
1416             sc.checkNotReleased();
1417             nativeSetPosition(mNativeObject, sc.mNativeObject, x, y);
1418             return this;
1419         }
1420 
setSize(SurfaceControl sc, int w, int h)1421         public Transaction setSize(SurfaceControl sc, int w, int h) {
1422             sc.checkNotReleased();
1423             mResizedSurfaces.put(sc, new Point(w, h));
1424             nativeSetSize(mNativeObject, sc.mNativeObject, w, h);
1425             return this;
1426         }
1427 
setLayer(SurfaceControl sc, int z)1428         public Transaction setLayer(SurfaceControl sc, int z) {
1429             sc.checkNotReleased();
1430             nativeSetLayer(mNativeObject, sc.mNativeObject, z);
1431             return this;
1432         }
1433 
setRelativeLayer(SurfaceControl sc, SurfaceControl relativeTo, int z)1434         public Transaction setRelativeLayer(SurfaceControl sc, SurfaceControl relativeTo, int z) {
1435             sc.checkNotReleased();
1436             nativeSetRelativeLayer(mNativeObject, sc.mNativeObject,
1437                     relativeTo.getHandle(), z);
1438             return this;
1439         }
1440 
setTransparentRegionHint(SurfaceControl sc, Region transparentRegion)1441         public Transaction setTransparentRegionHint(SurfaceControl sc, Region transparentRegion) {
1442             sc.checkNotReleased();
1443             nativeSetTransparentRegionHint(mNativeObject,
1444                     sc.mNativeObject, transparentRegion);
1445             return this;
1446         }
1447 
setAlpha(SurfaceControl sc, float alpha)1448         public Transaction setAlpha(SurfaceControl sc, float alpha) {
1449             sc.checkNotReleased();
1450             nativeSetAlpha(mNativeObject, sc.mNativeObject, alpha);
1451             return this;
1452         }
1453 
setMatrix(SurfaceControl sc, float dsdx, float dtdx, float dtdy, float dsdy)1454         public Transaction setMatrix(SurfaceControl sc,
1455                 float dsdx, float dtdx, float dtdy, float dsdy) {
1456             sc.checkNotReleased();
1457             nativeSetMatrix(mNativeObject, sc.mNativeObject,
1458                     dsdx, dtdx, dtdy, dsdy);
1459             return this;
1460         }
1461 
setMatrix(SurfaceControl sc, Matrix matrix, float[] float9)1462         public Transaction setMatrix(SurfaceControl sc, Matrix matrix, float[] float9) {
1463             matrix.getValues(float9);
1464             setMatrix(sc, float9[MSCALE_X], float9[MSKEW_Y],
1465                     float9[MSKEW_X], float9[MSCALE_Y]);
1466             setPosition(sc, float9[MTRANS_X], float9[MTRANS_Y]);
1467             return this;
1468         }
1469 
setWindowCrop(SurfaceControl sc, Rect crop)1470         public Transaction setWindowCrop(SurfaceControl sc, Rect crop) {
1471             sc.checkNotReleased();
1472             if (crop != null) {
1473                 nativeSetWindowCrop(mNativeObject, sc.mNativeObject,
1474                         crop.left, crop.top, crop.right, crop.bottom);
1475             } else {
1476                 nativeSetWindowCrop(mNativeObject, sc.mNativeObject, 0, 0, 0, 0);
1477             }
1478 
1479             return this;
1480         }
1481 
setFinalCrop(SurfaceControl sc, Rect crop)1482         public Transaction setFinalCrop(SurfaceControl sc, Rect crop) {
1483             sc.checkNotReleased();
1484             if (crop != null) {
1485                 nativeSetFinalCrop(mNativeObject, sc.mNativeObject,
1486                         crop.left, crop.top, crop.right, crop.bottom);
1487             } else {
1488                 nativeSetFinalCrop(mNativeObject, sc.mNativeObject, 0, 0, 0, 0);
1489             }
1490 
1491             return this;
1492         }
1493 
setLayerStack(SurfaceControl sc, int layerStack)1494         public Transaction setLayerStack(SurfaceControl sc, int layerStack) {
1495             sc.checkNotReleased();
1496             nativeSetLayerStack(mNativeObject, sc.mNativeObject, layerStack);
1497             return this;
1498         }
1499 
deferTransactionUntil(SurfaceControl sc, IBinder handle, long frameNumber)1500         public Transaction deferTransactionUntil(SurfaceControl sc, IBinder handle,
1501                 long frameNumber) {
1502             if (frameNumber < 0) {
1503                 return this;
1504             }
1505             sc.checkNotReleased();
1506             nativeDeferTransactionUntil(mNativeObject, sc.mNativeObject, handle, frameNumber);
1507             return this;
1508         }
1509 
deferTransactionUntilSurface(SurfaceControl sc, Surface barrierSurface, long frameNumber)1510         public Transaction deferTransactionUntilSurface(SurfaceControl sc, Surface barrierSurface,
1511                 long frameNumber) {
1512             if (frameNumber < 0) {
1513                 return this;
1514             }
1515             sc.checkNotReleased();
1516             nativeDeferTransactionUntilSurface(mNativeObject, sc.mNativeObject,
1517                     barrierSurface.mNativeObject, frameNumber);
1518             return this;
1519         }
1520 
reparentChildren(SurfaceControl sc, IBinder newParentHandle)1521         public Transaction reparentChildren(SurfaceControl sc, IBinder newParentHandle) {
1522             sc.checkNotReleased();
1523             nativeReparentChildren(mNativeObject, sc.mNativeObject, newParentHandle);
1524             return this;
1525         }
1526 
1527         /** Re-parents a specific child layer to a new parent */
reparent(SurfaceControl sc, IBinder newParentHandle)1528         public Transaction reparent(SurfaceControl sc, IBinder newParentHandle) {
1529             sc.checkNotReleased();
1530             nativeReparent(mNativeObject, sc.mNativeObject,
1531                     newParentHandle);
1532             return this;
1533         }
1534 
detachChildren(SurfaceControl sc)1535         public Transaction detachChildren(SurfaceControl sc) {
1536             sc.checkNotReleased();
1537             nativeSeverChildren(mNativeObject, sc.mNativeObject);
1538             return this;
1539         }
1540 
setOverrideScalingMode(SurfaceControl sc, int overrideScalingMode)1541         public Transaction setOverrideScalingMode(SurfaceControl sc, int overrideScalingMode) {
1542             sc.checkNotReleased();
1543             nativeSetOverrideScalingMode(mNativeObject, sc.mNativeObject,
1544                     overrideScalingMode);
1545             return this;
1546         }
1547 
1548         /**
1549          * Sets a color for the Surface.
1550          * @param color A float array with three values to represent r, g, b in range [0..1]
1551          */
setColor(SurfaceControl sc, @Size(3) float[] color)1552         public Transaction setColor(SurfaceControl sc, @Size(3) float[] color) {
1553             sc.checkNotReleased();
1554             nativeSetColor(mNativeObject, sc.mNativeObject, color);
1555             return this;
1556         }
1557 
1558         /**
1559          * If the buffer size changes in this transaction, position and crop updates specified
1560          * in this transaction will not complete until a buffer of the new size
1561          * arrives. As transform matrix and size are already frozen in this fashion,
1562          * this enables totally freezing the surface until the resize has completed
1563          * (at which point the geometry influencing aspects of this transaction will then occur)
1564          */
setGeometryAppliesWithResize(SurfaceControl sc)1565         public Transaction setGeometryAppliesWithResize(SurfaceControl sc) {
1566             sc.checkNotReleased();
1567             nativeSetGeometryAppliesWithResize(mNativeObject, sc.mNativeObject);
1568             return this;
1569         }
1570 
1571         /**
1572          * Sets the security of the surface.  Setting the flag is equivalent to creating the
1573          * Surface with the {@link #SECURE} flag.
1574          */
setSecure(SurfaceControl sc, boolean isSecure)1575         public Transaction setSecure(SurfaceControl sc, boolean isSecure) {
1576             sc.checkNotReleased();
1577             if (isSecure) {
1578                 nativeSetFlags(mNativeObject, sc.mNativeObject, SECURE, SECURE);
1579             } else {
1580                 nativeSetFlags(mNativeObject, sc.mNativeObject, 0, SECURE);
1581             }
1582             return this;
1583         }
1584 
1585         /**
1586          * Sets the opacity of the surface.  Setting the flag is equivalent to creating the
1587          * Surface with the {@link #OPAQUE} flag.
1588          */
setOpaque(SurfaceControl sc, boolean isOpaque)1589         public Transaction setOpaque(SurfaceControl sc, boolean isOpaque) {
1590             sc.checkNotReleased();
1591             if (isOpaque) {
1592                 nativeSetFlags(mNativeObject, sc.mNativeObject, SURFACE_OPAQUE, SURFACE_OPAQUE);
1593             } else {
1594                 nativeSetFlags(mNativeObject, sc.mNativeObject, 0, SURFACE_OPAQUE);
1595             }
1596             return this;
1597         }
1598 
1599         /**
1600          * Same as {@link #destroy()} except this is invoked in a transaction instead of
1601          * immediately.
1602          */
destroy(SurfaceControl sc)1603         public Transaction destroy(SurfaceControl sc) {
1604             sc.checkNotReleased();
1605 
1606             /**
1607              * Perhaps it's safer to transfer the close guard to the Transaction
1608              * but then we have a whole wonky scenario regarding merging, multiple
1609              * close-guards per transaction etc...the whole scenario is kind of wonky
1610              * and it seems really we'd like to just be able to call release here
1611              * but the WindowManager has some code that looks like
1612              * --- destroyInTransaction(a)
1613              * --- reparentChildrenInTransaction(a)
1614              * so we need to ensure the SC remains valid until the transaction
1615              * is applied.
1616              */
1617             sc.mCloseGuard.close();
1618 
1619             nativeDestroy(mNativeObject, sc.mNativeObject);
1620             return this;
1621         }
1622 
setDisplaySurface(IBinder displayToken, Surface surface)1623         public Transaction setDisplaySurface(IBinder displayToken, Surface surface) {
1624             if (displayToken == null) {
1625                 throw new IllegalArgumentException("displayToken must not be null");
1626             }
1627 
1628             if (surface != null) {
1629                 synchronized (surface.mLock) {
1630                     nativeSetDisplaySurface(mNativeObject, displayToken, surface.mNativeObject);
1631                 }
1632             } else {
1633                 nativeSetDisplaySurface(mNativeObject, displayToken, 0);
1634             }
1635             return this;
1636         }
1637 
setDisplayLayerStack(IBinder displayToken, int layerStack)1638         public Transaction setDisplayLayerStack(IBinder displayToken, int layerStack) {
1639             if (displayToken == null) {
1640                 throw new IllegalArgumentException("displayToken must not be null");
1641             }
1642             nativeSetDisplayLayerStack(mNativeObject, displayToken, layerStack);
1643             return this;
1644         }
1645 
setDisplayProjection(IBinder displayToken, int orientation, Rect layerStackRect, Rect displayRect)1646         public Transaction setDisplayProjection(IBinder displayToken,
1647                 int orientation, Rect layerStackRect, Rect displayRect) {
1648             if (displayToken == null) {
1649                 throw new IllegalArgumentException("displayToken must not be null");
1650             }
1651             if (layerStackRect == null) {
1652                 throw new IllegalArgumentException("layerStackRect must not be null");
1653             }
1654             if (displayRect == null) {
1655                 throw new IllegalArgumentException("displayRect must not be null");
1656             }
1657             nativeSetDisplayProjection(mNativeObject, displayToken, orientation,
1658                     layerStackRect.left, layerStackRect.top, layerStackRect.right, layerStackRect.bottom,
1659                     displayRect.left, displayRect.top, displayRect.right, displayRect.bottom);
1660             return this;
1661         }
1662 
setDisplaySize(IBinder displayToken, int width, int height)1663         public Transaction setDisplaySize(IBinder displayToken, int width, int height) {
1664             if (displayToken == null) {
1665                 throw new IllegalArgumentException("displayToken must not be null");
1666             }
1667             if (width <= 0 || height <= 0) {
1668                 throw new IllegalArgumentException("width and height must be positive");
1669             }
1670 
1671             nativeSetDisplaySize(mNativeObject, displayToken, width, height);
1672             return this;
1673         }
1674 
1675         /** flag the transaction as an animation */
setAnimationTransaction()1676         public Transaction setAnimationTransaction() {
1677             nativeSetAnimationTransaction(mNativeObject);
1678             return this;
1679         }
1680 
1681         /**
1682          * Indicate that SurfaceFlinger should wake up earlier than usual as a result of this
1683          * transaction. This should be used when the caller thinks that the scene is complex enough
1684          * that it's likely to hit GL composition, and thus, SurfaceFlinger needs to more time in
1685          * order not to miss frame deadlines.
1686          * <p>
1687          * Corresponds to setting ISurfaceComposer::eEarlyWakeup
1688          */
setEarlyWakeup()1689         public Transaction setEarlyWakeup() {
1690             nativeSetEarlyWakeup(mNativeObject);
1691             return this;
1692         }
1693 
1694         /**
1695          * Merge the other transaction into this transaction, clearing the
1696          * other transaction as if it had been applied.
1697          */
merge(Transaction other)1698         public Transaction merge(Transaction other) {
1699             mResizedSurfaces.putAll(other.mResizedSurfaces);
1700             other.mResizedSurfaces.clear();
1701             nativeMergeTransaction(mNativeObject, other.mNativeObject);
1702             return this;
1703         }
1704     }
1705 }
1706