• 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.SurfaceControlProto.HASH_CODE;
26 import static android.view.SurfaceControlProto.LAYER_ID;
27 import static android.view.SurfaceControlProto.NAME;
28 
29 import android.Manifest;
30 import android.annotation.CallbackExecutor;
31 import android.annotation.DurationNanosLong;
32 import android.annotation.FlaggedApi;
33 import android.annotation.FloatRange;
34 import android.annotation.IntDef;
35 import android.annotation.IntRange;
36 import android.annotation.NonNull;
37 import android.annotation.Nullable;
38 import android.annotation.RequiresPermission;
39 import android.annotation.Size;
40 import android.annotation.SystemApi;
41 import android.annotation.TestApi;
42 import android.compat.annotation.UnsupportedAppUsage;
43 import android.graphics.ColorSpace;
44 import android.graphics.GraphicBuffer;
45 import android.graphics.Matrix;
46 import android.graphics.PixelFormat;
47 import android.graphics.Point;
48 import android.graphics.Rect;
49 import android.graphics.Region;
50 import android.gui.BorderSettings;
51 import android.gui.DropInputMode;
52 import android.gui.StalledTransactionInfo;
53 import android.gui.TrustedOverlay;
54 import android.hardware.DataSpace;
55 import android.hardware.DisplayLuts;
56 import android.hardware.HardwareBuffer;
57 import android.hardware.OverlayProperties;
58 import android.hardware.SyncFence;
59 import android.hardware.display.DeviceProductInfo;
60 import android.hardware.display.DisplayedContentSample;
61 import android.hardware.display.DisplayedContentSamplingAttributes;
62 import android.hardware.graphics.common.DisplayDecorationSupport;
63 import android.media.quality.PictureProfileHandle;
64 import android.opengl.EGLDisplay;
65 import android.opengl.EGLSync;
66 import android.os.Build;
67 import android.os.IBinder;
68 import android.os.Looper;
69 import android.os.Parcel;
70 import android.os.Parcelable;
71 import android.util.ArrayMap;
72 import android.util.Log;
73 import android.util.Slog;
74 import android.util.SparseIntArray;
75 import android.util.proto.ProtoOutputStream;
76 import android.view.Surface.OutOfResourcesException;
77 
78 import com.android.internal.annotations.GuardedBy;
79 import com.android.internal.util.Preconditions;
80 import com.android.window.flags.Flags;
81 
82 import dalvik.system.CloseGuard;
83 
84 import libcore.util.NativeAllocationRegistry;
85 
86 import java.io.Closeable;
87 import java.lang.annotation.Retention;
88 import java.lang.annotation.RetentionPolicy;
89 import java.lang.ref.WeakReference;
90 import java.nio.ByteBuffer;
91 import java.nio.ByteOrder;
92 import java.util.ArrayList;
93 import java.util.Arrays;
94 import java.util.List;
95 import java.util.Objects;
96 import java.util.concurrent.Executor;
97 import java.util.function.Consumer;
98 
99 /**
100  * Handle to an on-screen Surface managed by the system compositor. The SurfaceControl is
101  * a combination of a buffer source, and metadata about how to display the buffers.
102  * By constructing a {@link Surface} from this SurfaceControl you can submit buffers to be
103  * composited. Using {@link SurfaceControl.Transaction} you can manipulate various
104  * properties of how the buffer will be displayed on-screen. SurfaceControl's are
105  * arranged into a scene-graph like hierarchy, and as such any SurfaceControl may have
106  * a parent. Geometric properties like transform, crop, and Z-ordering will be inherited
107  * from the parent, as if the child were content in the parents buffer stream.
108  */
109 public final class SurfaceControl implements Parcelable {
110     private static final String TAG = "SurfaceControl";
111 
nativeCreate(SurfaceSession session, String name, int w, int h, int format, int flags, long parentObject, Parcel metadata)112     private static native long nativeCreate(SurfaceSession session, String name,
113             int w, int h, int format, int flags, long parentObject, Parcel metadata)
114             throws OutOfResourcesException;
nativeReadFromParcel(Parcel in)115     private static native long nativeReadFromParcel(Parcel in);
nativeCopyFromSurfaceControl(long nativeObject)116     private static native long nativeCopyFromSurfaceControl(long nativeObject);
nativeWriteToParcel(long nativeObject, Parcel out)117     private static native void nativeWriteToParcel(long nativeObject, Parcel out);
nativeGetNativeSurfaceControlFinalizer()118     private static native long nativeGetNativeSurfaceControlFinalizer();
nativeDisconnect(long nativeObject)119     private static native void nativeDisconnect(long nativeObject);
nativeUpdateDefaultBufferSize(long nativeObject, int width, int height)120     private static native void nativeUpdateDefaultBufferSize(long nativeObject, int width, int height);
121 
nativeMirrorSurface(long mirrorOfObject)122     private static native long nativeMirrorSurface(long mirrorOfObject);
nativeCreateTransaction()123     private static native long nativeCreateTransaction();
nativeGetNativeTransactionFinalizer()124     private static native long nativeGetNativeTransactionFinalizer();
nativeApplyTransaction(long transactionObj, boolean sync, boolean oneWay)125     private static native void nativeApplyTransaction(long transactionObj, boolean sync,
126             boolean oneWay);
nativeMergeTransaction(long transactionObj, long otherTransactionObj)127     private static native void nativeMergeTransaction(long transactionObj,
128             long otherTransactionObj);
nativeClearTransaction(long transactionObj)129     private static native void nativeClearTransaction(long transactionObj);
nativeSetAnimationTransaction(long transactionObj)130     private static native void nativeSetAnimationTransaction(long transactionObj);
nativeSetEarlyWakeupStart(long transactionObj)131     private static native void nativeSetEarlyWakeupStart(long transactionObj);
nativeSetEarlyWakeupEnd(long transactionObj)132     private static native void nativeSetEarlyWakeupEnd(long transactionObj);
nativeGetTransactionId(long transactionObj)133     private static native long nativeGetTransactionId(long transactionObj);
134 
nativeSetLayer(long transactionObj, long nativeObject, int zorder)135     private static native void nativeSetLayer(long transactionObj, long nativeObject, int zorder);
nativeSetRelativeLayer(long transactionObj, long nativeObject, long relativeToObject, int zorder)136     private static native void nativeSetRelativeLayer(long transactionObj, long nativeObject,
137             long relativeToObject, int zorder);
nativeSetPosition(long transactionObj, long nativeObject, float x, float y)138     private static native void nativeSetPosition(long transactionObj, long nativeObject,
139             float x, float y);
nativeSetScale(long transactionObj, long nativeObject, float x, float y)140     private static native void nativeSetScale(long transactionObj, long nativeObject,
141             float x, float y);
nativeSetTransparentRegionHint(long transactionObj, long nativeObject, Region region)142     private static native void nativeSetTransparentRegionHint(long transactionObj,
143             long nativeObject, Region region);
nativeSetAlpha(long transactionObj, long nativeObject, float alpha)144     private static native void nativeSetAlpha(long transactionObj, long nativeObject, float alpha);
nativeSetMatrix(long transactionObj, long nativeObject, float dsdx, float dtdx, float dtdy, float dsdy)145     private static native void nativeSetMatrix(long transactionObj, long nativeObject,
146             float dsdx, float dtdx,
147             float dtdy, float dsdy);
nativeSetColorTransform(long transactionObj, long nativeObject, float[] matrix, float[] translation)148     private static native void nativeSetColorTransform(long transactionObj, long nativeObject,
149             float[] matrix, float[] translation);
nativeSetColorSpaceAgnostic(long transactionObj, long nativeObject, boolean agnostic)150     private static native void nativeSetColorSpaceAgnostic(long transactionObj, long nativeObject,
151             boolean agnostic);
nativeSetGeometry(long transactionObj, long nativeObject, Rect sourceCrop, Rect dest, long orientation)152     private static native void nativeSetGeometry(long transactionObj, long nativeObject,
153             Rect sourceCrop, Rect dest, long orientation);
nativeSetColor(long transactionObj, long nativeObject, float[] color)154     private static native void nativeSetColor(long transactionObj, long nativeObject, float[] color);
nativeSetFlags(long transactionObj, long nativeObject, int flags, int mask)155     private static native void nativeSetFlags(long transactionObj, long nativeObject,
156             int flags, int mask);
nativeSetFrameRateSelectionPriority(long transactionObj, long nativeObject, int priority)157     private static native void nativeSetFrameRateSelectionPriority(long transactionObj,
158             long nativeObject, int priority);
nativeSetWindowCrop(long transactionObj, long nativeObject, int l, int t, int r, int b)159     private static native void nativeSetWindowCrop(long transactionObj, long nativeObject,
160             int l, int t, int r, int b);
nativeSetCrop(long transactionObj, long nativeObject, float l, float t, float r, float b)161     private static native void nativeSetCrop(long transactionObj, long nativeObject,
162             float l, float t, float r, float b);
nativeSetCornerRadius(long transactionObj, long nativeObject, float cornerRadius)163     private static native void nativeSetCornerRadius(long transactionObj, long nativeObject,
164             float cornerRadius);
nativeSetClientDrawnCornerRadius(long transactionObj, long nativeObject, float clientDrawnCornerRadius)165     private static native void nativeSetClientDrawnCornerRadius(long transactionObj,
166             long nativeObject, float clientDrawnCornerRadius);
nativeSetBackgroundBlurRadius(long transactionObj, long nativeObject, int blurRadius)167     private static native void nativeSetBackgroundBlurRadius(long transactionObj, long nativeObject,
168             int blurRadius);
nativeSetLayerStack(long transactionObj, long nativeObject, int layerStack)169     private static native void nativeSetLayerStack(long transactionObj, long nativeObject,
170             int layerStack);
nativeSetBlurRegions(long transactionObj, long nativeObj, float[][] regions, int length)171     private static native void nativeSetBlurRegions(long transactionObj, long nativeObj,
172             float[][] regions, int length);
nativeSetStretchEffect(long transactionObj, long nativeObj, float width, float height, float vecX, float vecY, float maxStretchAmountX, float maxStretchAmountY, float childRelativeLeft, float childRelativeTop, float childRelativeRight, float childRelativeBottom)173     private static native void nativeSetStretchEffect(long transactionObj, long nativeObj,
174             float width, float height, float vecX, float vecY,
175             float maxStretchAmountX, float maxStretchAmountY, float childRelativeLeft,
176             float childRelativeTop, float childRelativeRight, float childRelativeBottom);
nativeSetEdgeExtensionEffect(long transactionObj, long nativeObj, boolean leftEdge, boolean rightEdge, boolean topEdge, boolean bottomEdge)177     private static native void nativeSetEdgeExtensionEffect(long transactionObj, long nativeObj,
178                                                             boolean leftEdge, boolean rightEdge,
179                                                             boolean topEdge, boolean bottomEdge);
nativeSetTrustedOverlay(long transactionObj, long nativeObject, int isTrustedOverlay)180     private static native void nativeSetTrustedOverlay(long transactionObj, long nativeObject,
181             int isTrustedOverlay);
nativeSetDropInputMode( long transactionObj, long nativeObject, int flags)182     private static native void nativeSetDropInputMode(
183             long transactionObj, long nativeObject, int flags);
nativeSetCanOccludePresentation(long transactionObj, long nativeObject, boolean canOccludePresentation)184     private static native void nativeSetCanOccludePresentation(long transactionObj,
185             long nativeObject, boolean canOccludePresentation);
nativeSurfaceFlushJankData(long nativeSurfaceObject)186     private static native void nativeSurfaceFlushJankData(long nativeSurfaceObject);
nativeClearContentFrameStats(long nativeObject)187     private static native boolean nativeClearContentFrameStats(long nativeObject);
nativeGetContentFrameStats(long nativeObject, WindowContentFrameStats outStats)188     private static native boolean nativeGetContentFrameStats(long nativeObject, WindowContentFrameStats outStats);
nativeClearAnimationFrameStats()189     private static native boolean nativeClearAnimationFrameStats();
nativeGetAnimationFrameStats(WindowAnimationFrameStats outStats)190     private static native boolean nativeGetAnimationFrameStats(WindowAnimationFrameStats outStats);
191 
nativeSetDisplaySurface(long transactionObj, IBinder displayToken, long nativeSurfaceObject)192     private static native void nativeSetDisplaySurface(long transactionObj,
193             IBinder displayToken, long nativeSurfaceObject);
nativeSetDisplayLayerStack(long transactionObj, IBinder displayToken, int layerStack)194     private static native void nativeSetDisplayLayerStack(long transactionObj,
195             IBinder displayToken, int layerStack);
nativeSetDisplayFlags(long transactionObj, IBinder displayToken, int flags)196     private static native void nativeSetDisplayFlags(long transactionObj,
197             IBinder displayToken, int flags);
nativeSetDisplayProjection(long transactionObj, IBinder displayToken, int orientation, int l, int t, int r, int b, int L, int T, int R, int B)198     private static native void nativeSetDisplayProjection(long transactionObj,
199             IBinder displayToken, int orientation,
200             int l, int t, int r, int b,
201             int L, int T, int R, int B);
nativeSetDisplaySize(long transactionObj, IBinder displayToken, int width, int height)202     private static native void nativeSetDisplaySize(long transactionObj, IBinder displayToken,
203             int width, int height);
nativeGetStaticDisplayInfo(long displayId)204     private static native StaticDisplayInfo nativeGetStaticDisplayInfo(long displayId);
nativeGetDynamicDisplayInfo(long displayId)205     private static native DynamicDisplayInfo nativeGetDynamicDisplayInfo(long displayId);
206     private static native DisplayedContentSamplingAttributes
nativeGetDisplayedContentSamplingAttributes(IBinder displayToken)207             nativeGetDisplayedContentSamplingAttributes(IBinder displayToken);
nativeSetDisplayedContentSamplingEnabled(IBinder displayToken, boolean enable, int componentMask, int maxFrames)208     private static native boolean nativeSetDisplayedContentSamplingEnabled(IBinder displayToken,
209             boolean enable, int componentMask, int maxFrames);
nativeGetDisplayedContentSample( IBinder displayToken, long numFrames, long timestamp)210     private static native DisplayedContentSample nativeGetDisplayedContentSample(
211             IBinder displayToken, long numFrames, long timestamp);
nativeSetDesiredDisplayModeSpecs(IBinder displayToken, DesiredDisplayModeSpecs desiredDisplayModeSpecs)212     private static native boolean nativeSetDesiredDisplayModeSpecs(IBinder displayToken,
213             DesiredDisplayModeSpecs desiredDisplayModeSpecs);
214     private static native DesiredDisplayModeSpecs
nativeGetDesiredDisplayModeSpecs(IBinder displayToken)215             nativeGetDesiredDisplayModeSpecs(IBinder displayToken);
nativeGetDisplayNativePrimaries( IBinder displayToken)216     private static native DisplayPrimaries nativeGetDisplayNativePrimaries(
217             IBinder displayToken);
nativeGetCompositionDataspaces()218     private static native int[] nativeGetCompositionDataspaces();
nativeGetOverlaySupport()219     private static native OverlayProperties nativeGetOverlaySupport();
nativeSetActiveColorMode(IBinder displayToken, int colorMode)220     private static native boolean nativeSetActiveColorMode(IBinder displayToken,
221             int colorMode);
nativeGetBootDisplayModeSupport()222     private static native boolean nativeGetBootDisplayModeSupport();
nativeSetBootDisplayMode(IBinder displayToken, int displayMode)223     private static native void nativeSetBootDisplayMode(IBinder displayToken, int displayMode);
nativeClearBootDisplayMode(IBinder displayToken)224     private static native void nativeClearBootDisplayMode(IBinder displayToken);
nativeSetAutoLowLatencyMode(IBinder displayToken, boolean on)225     private static native void nativeSetAutoLowLatencyMode(IBinder displayToken, boolean on);
nativeSetGameContentType(IBinder displayToken, boolean on)226     private static native void nativeSetGameContentType(IBinder displayToken, boolean on);
nativeSetDisplayPowerMode( IBinder displayToken, int mode)227     private static native void nativeSetDisplayPowerMode(
228             IBinder displayToken, int mode);
nativeReparent(long transactionObj, long nativeObject, long newParentNativeObject)229     private static native void nativeReparent(long transactionObj, long nativeObject,
230             long newParentNativeObject);
nativeSetBuffer(long transactionObj, long nativeObject, HardwareBuffer buffer, long fencePtr, Consumer<SyncFence> releaseCallback)231     private static native void nativeSetBuffer(long transactionObj, long nativeObject,
232             HardwareBuffer buffer, long fencePtr, Consumer<SyncFence> releaseCallback);
nativeUnsetBuffer(long transactionObj, long nativeObject)233     private static native void nativeUnsetBuffer(long transactionObj, long nativeObject);
nativeSetBufferTransform(long transactionObj, long nativeObject, int transform)234     private static native void nativeSetBufferTransform(long transactionObj, long nativeObject,
235             int transform);
nativeSetDataSpace(long transactionObj, long nativeObject, @DataSpace.NamedDataSpace int dataSpace)236     private static native void nativeSetDataSpace(long transactionObj, long nativeObject,
237             @DataSpace.NamedDataSpace int dataSpace);
nativeSetExtendedRangeBrightness(long transactionObj, long nativeObject, float currentBufferRatio, float desiredRatio)238     private static native void nativeSetExtendedRangeBrightness(long transactionObj,
239             long nativeObject, float currentBufferRatio, float desiredRatio);
nativeSetDesiredHdrHeadroom(long transactionObj, long nativeObject, float desiredRatio)240     private static native void nativeSetDesiredHdrHeadroom(long transactionObj,
241             long nativeObject, float desiredRatio);
nativeSetCachingHint(long transactionObj, long nativeObject, int cachingHint)242     private static native void nativeSetCachingHint(long transactionObj,
243             long nativeObject, int cachingHint);
nativeSetDamageRegion(long transactionObj, long nativeObject, Region region)244     private static native void nativeSetDamageRegion(long transactionObj, long nativeObject,
245             Region region);
nativeSetDimmingEnabled(long transactionObj, long nativeObject, boolean dimmingEnabled)246     private static native void nativeSetDimmingEnabled(long transactionObj, long nativeObject,
247             boolean dimmingEnabled);
248 
nativeSetInputWindowInfo(long transactionObj, long nativeObject, InputWindowHandle handle)249     private static native void nativeSetInputWindowInfo(long transactionObj, long nativeObject,
250             InputWindowHandle handle);
251 
nativeGetProtectedContentSupport()252     private static native boolean nativeGetProtectedContentSupport();
nativeSetMetadata(long transactionObj, long nativeObject, int key, Parcel data)253     private static native void nativeSetMetadata(long transactionObj, long nativeObject, int key,
254             Parcel data);
nativeAddWindowInfosReportedListener(long transactionObj, Runnable listener)255     private static native void nativeAddWindowInfosReportedListener(long transactionObj,
256             Runnable listener);
nativeGetDisplayBrightnessSupport(IBinder displayToken)257     private static native boolean nativeGetDisplayBrightnessSupport(IBinder displayToken);
nativeSetDisplayBrightness(IBinder displayToken, float sdrBrightness, float sdrBrightnessNits, float displayBrightness, float displayBrightnessNits)258     private static native boolean nativeSetDisplayBrightness(IBinder displayToken,
259             float sdrBrightness, float sdrBrightnessNits, float displayBrightness,
260             float displayBrightnessNits);
nativeReadTransactionFromParcel(Parcel in)261     private static native long nativeReadTransactionFromParcel(Parcel in);
nativeWriteTransactionToParcel(long nativeObject, Parcel out)262     private static native void nativeWriteTransactionToParcel(long nativeObject, Parcel out);
nativeSetShadowRadius(long transactionObj, long nativeObject, float shadowRadius)263     private static native void nativeSetShadowRadius(long transactionObj, long nativeObject,
264             float shadowRadius);
265 
nativeSetBorderSettings(long transactionObj, long nativeObject, Parcel settings)266     private static native void nativeSetBorderSettings(long transactionObj, long nativeObject,
267             Parcel settings);
268 
nativeSetGlobalShadowSettings(@ize4) float[] ambientColor, @Size(4) float[] spotColor, float lightPosY, float lightPosZ, float lightRadius)269     private static native void nativeSetGlobalShadowSettings(@Size(4) float[] ambientColor,
270             @Size(4) float[] spotColor, float lightPosY, float lightPosZ, float lightRadius);
nativeGetDisplayDecorationSupport( IBinder displayToken)271     private static native DisplayDecorationSupport nativeGetDisplayDecorationSupport(
272             IBinder displayToken);
273 
nativeSetFrameRate(long transactionObj, long nativeObject, float frameRate, int compatibility, int changeFrameRateStrategy)274     private static native void nativeSetFrameRate(long transactionObj, long nativeObject,
275             float frameRate, int compatibility, int changeFrameRateStrategy);
nativeSetDefaultFrameRateCompatibility(long transactionObj, long nativeObject, int compatibility)276     private static native void nativeSetDefaultFrameRateCompatibility(long transactionObj,
277             long nativeObject, int compatibility);
nativeSetFrameRateCategory( long transactionObj, long nativeObject, int category, boolean smoothSwitchOnly)278     private static native void nativeSetFrameRateCategory(
279             long transactionObj, long nativeObject, int category, boolean smoothSwitchOnly);
nativeSetFrameRateSelectionStrategy( long transactionObj, long nativeObject, int strategy)280     private static native void nativeSetFrameRateSelectionStrategy(
281             long transactionObj, long nativeObject, int strategy);
nativeGetHandle(long nativeObject)282     private static native long nativeGetHandle(long nativeObject);
283 
nativeSetFixedTransformHint(long transactionObj, long nativeObject, int transformHint)284     private static native void nativeSetFixedTransformHint(long transactionObj, long nativeObject,
285             int transformHint);
nativeRemoveCurrentInputFocus(long nativeObject, int displayId)286     private static native void nativeRemoveCurrentInputFocus(long nativeObject, int displayId);
nativeSetFocusedWindow(long transactionObj, IBinder toToken, String windowName, int displayId)287     private static native void nativeSetFocusedWindow(long transactionObj, IBinder toToken,
288             String windowName, int displayId);
nativeSetFrameTimelineVsync(long transactionObj, long frameTimelineVsyncId)289     private static native void nativeSetFrameTimelineVsync(long transactionObj,
290             long frameTimelineVsyncId);
nativeCreateJankDataListenerWrapper( long surfaceControl, OnJankDataListener listener)291     private static native long nativeCreateJankDataListenerWrapper(
292             long surfaceControl, OnJankDataListener listener);
nativeGetJankDataListenerWrapperFinalizer()293     private static native long nativeGetJankDataListenerWrapperFinalizer();
nativeAddJankDataListener(long nativeListener)294     private static native void nativeAddJankDataListener(long nativeListener);
nativeFlushJankData(long nativeListener)295     private static native void nativeFlushJankData(long nativeListener);
nativeRemoveJankDataListener(long nativeListener, long afterVsync)296     private static native void nativeRemoveJankDataListener(long nativeListener, long afterVsync);
nativeGetGPUContextPriority()297     private static native int nativeGetGPUContextPriority();
nativeSetTransformHint(long nativeObject, @SurfaceControl.BufferTransform int transformHint)298     private static native void nativeSetTransformHint(long nativeObject,
299             @SurfaceControl.BufferTransform int transformHint);
nativeGetTransformHint(long nativeObject)300     private static native int nativeGetTransformHint(long nativeObject);
nativeGetLayerId(long nativeObject)301     private static native int nativeGetLayerId(long nativeObject);
nativeAddTransactionCommittedListener(long nativeObject, TransactionCommittedListener listener)302     private static native void nativeAddTransactionCommittedListener(long nativeObject,
303             TransactionCommittedListener listener);
nativeAddTransactionCompletedListener(long nativeObject, Consumer<TransactionStats> listener)304     private static native void nativeAddTransactionCompletedListener(long nativeObject,
305             Consumer<TransactionStats> listener);
nativeSanitize(long transactionObject, int pid, int uid)306     private static native void nativeSanitize(long transactionObject, int pid, int uid);
nativeSetDestinationFrame(long transactionObj, long nativeObject, int l, int t, int r, int b)307     private static native void nativeSetDestinationFrame(long transactionObj, long nativeObject,
308             int l, int t, int r, int b);
nativeSetDefaultApplyToken(IBinder token)309     private static native void nativeSetDefaultApplyToken(IBinder token);
nativeGetDefaultApplyToken()310     private static native IBinder nativeGetDefaultApplyToken();
nativeBootFinished()311     private static native boolean nativeBootFinished();
nativeCreateTpc(TrustedPresentationCallback callback)312     private static native long nativeCreateTpc(TrustedPresentationCallback callback);
getNativeTrustedPresentationCallbackFinalizer()313     private static native long getNativeTrustedPresentationCallbackFinalizer();
nativeSetTrustedPresentationCallback(long transactionObj, long nativeObject, long nativeTpc, TrustedPresentationThresholds thresholds)314     private static native void nativeSetTrustedPresentationCallback(long transactionObj,
315             long nativeObject, long nativeTpc, TrustedPresentationThresholds thresholds);
nativeClearTrustedPresentationCallback(long transactionObj, long nativeObject)316     private static native void nativeClearTrustedPresentationCallback(long transactionObj,
317             long nativeObject);
nativeGetStalledTransactionInfo(int pid)318     private static native StalledTransactionInfo nativeGetStalledTransactionInfo(int pid);
nativeSetDesiredPresentTimeNanos(long transactionObj, long desiredPresentTimeNanos)319     private static native void nativeSetDesiredPresentTimeNanos(long transactionObj,
320                                                                 long desiredPresentTimeNanos);
nativeNotifyShutdown()321     private static native void nativeNotifyShutdown();
nativeSetLuts(long transactionObj, long nativeObject, float[] buffers, int[] slots, int[] dimensions, int[] sizes, int[] samplingKeys)322     private static native void nativeSetLuts(long transactionObj, long nativeObject,
323             float[] buffers, int[] slots, int[] dimensions, int[] sizes, int[] samplingKeys);
nativeEnableDebugLogCallPoints(long transactionObj)324     private static native void nativeEnableDebugLogCallPoints(long transactionObj);
nativeGetMaxPictureProfiles()325     private static native int nativeGetMaxPictureProfiles();
nativeSetPictureProfileId(long transactionObj, long nativeObject, long pictureProfileId)326     private static native void nativeSetPictureProfileId(long transactionObj,
327             long nativeObject, long pictureProfileId);
nativeSetContentPriority(long transactionObj, long nativeObject, int priority)328     private static native void nativeSetContentPriority(long transactionObj, long nativeObject,
329             int priority);
330 
331     /**
332      * Transforms that can be applied to buffers as they are displayed to a window.
333      *
334      * Supported transforms are any combination of horizontal mirror, vertical mirror, and
335      * clock-wise 90 degree rotation, in that order. Rotations of 180 and 270 degrees are made up
336      * of those basic transforms.
337      * Mirrors {@code ANativeWindowTransform} definitions.
338      * @hide
339      */
340     @Retention(RetentionPolicy.SOURCE)
341     @IntDef(prefix = {"BUFFER_TRANSFORM_"},
342             value = {BUFFER_TRANSFORM_IDENTITY, BUFFER_TRANSFORM_MIRROR_HORIZONTAL,
343                     BUFFER_TRANSFORM_MIRROR_VERTICAL, BUFFER_TRANSFORM_ROTATE_90,
344                     BUFFER_TRANSFORM_ROTATE_180, BUFFER_TRANSFORM_ROTATE_270,
345                     BUFFER_TRANSFORM_MIRROR_HORIZONTAL | BUFFER_TRANSFORM_ROTATE_90,
346                     BUFFER_TRANSFORM_MIRROR_VERTICAL | BUFFER_TRANSFORM_ROTATE_90})
347     public @interface BufferTransform {
348     }
349 
350     /**
351      * Identity transform.
352      *
353      * These transforms that can be applied to buffers as they are displayed to a window.
354      * @see HardwareBuffer
355      *
356      * Supported transforms are any combination of horizontal mirror, vertical mirror, and
357      * clock-wise 90 degree rotation, in that order. Rotations of 180 and 270 degrees are
358      * made up of those basic transforms.
359      */
360     public static final int BUFFER_TRANSFORM_IDENTITY = 0x00;
361     /**
362      * Mirror horizontally. Can be combined with {@link #BUFFER_TRANSFORM_MIRROR_VERTICAL}
363      * and {@link #BUFFER_TRANSFORM_ROTATE_90}.
364      */
365     public static final int BUFFER_TRANSFORM_MIRROR_HORIZONTAL = 0x01;
366     /**
367      * Mirror vertically. Can be combined with {@link #BUFFER_TRANSFORM_MIRROR_HORIZONTAL}
368      * and {@link #BUFFER_TRANSFORM_ROTATE_90}.
369      */
370     public static final int BUFFER_TRANSFORM_MIRROR_VERTICAL = 0x02;
371     /**
372      * Rotate 90 degrees clock-wise. Can be combined with {@link
373      * #BUFFER_TRANSFORM_MIRROR_HORIZONTAL} and {@link #BUFFER_TRANSFORM_MIRROR_VERTICAL}.
374      */
375     public static final int BUFFER_TRANSFORM_ROTATE_90 = 0x04;
376     /**
377      * Rotate 180 degrees clock-wise. Cannot be combined with other transforms.
378      */
379     public static final int BUFFER_TRANSFORM_ROTATE_180 =
380             BUFFER_TRANSFORM_MIRROR_HORIZONTAL | BUFFER_TRANSFORM_MIRROR_VERTICAL;
381     /**
382      * Rotate 270 degrees clock-wise. Cannot be combined with other transforms.
383      */
384     public static final int BUFFER_TRANSFORM_ROTATE_270 =
385             BUFFER_TRANSFORM_ROTATE_180 | BUFFER_TRANSFORM_ROTATE_90;
386 
387     /**
388      * @hide
389      */
rotationToBufferTransform(@urface.Rotation int rotation)390     public static @BufferTransform int rotationToBufferTransform(@Surface.Rotation int rotation) {
391         switch (rotation) {
392             case Surface.ROTATION_0: return BUFFER_TRANSFORM_IDENTITY;
393             case Surface.ROTATION_90: return BUFFER_TRANSFORM_ROTATE_90;
394             case Surface.ROTATION_180: return BUFFER_TRANSFORM_ROTATE_180;
395             case Surface.ROTATION_270: return BUFFER_TRANSFORM_ROTATE_270;
396         }
397         Log.e(TAG, "Trying to convert unknown rotation=" + rotation);
398         return BUFFER_TRANSFORM_IDENTITY;
399     }
400 
401     @Nullable
402     @GuardedBy("mLock")
403     private ArrayList<OnReparentListener> mReparentListeners;
404 
405     /**
406      * Listener to observe surface reparenting.
407      *
408      * @hide
409      */
410     public interface OnReparentListener {
411 
412         /**
413          * Callback for reparenting surfaces.
414          *
415          * Important: You should only interact with the provided surface control
416          * only if you have a contract with its owner to avoid them closing it
417          * under you or vise versa.
418          *
419          * @param transaction The transaction that would commit reparenting.
420          * @param parent The future parent surface.
421          */
onReparent(@onNull Transaction transaction, @Nullable SurfaceControl parent)422         void onReparent(@NonNull Transaction transaction, @Nullable SurfaceControl parent);
423     }
424 
425     /**
426      * Jank information to be fed back via {@link OnJankDataListener}.
427      * <p>
428      * Apps may register a {@link OnJankDataListener} to get periodic batches of jank classification
429      * data from the (<a
430      * href="https://source.android.com/docs/core/graphics/surfaceflinger-windowmanagersystem">
431      * composer</a> regarding rendered frames. A frame is considered janky if it did not reach the
432      * display at the intended time, typically due to missing a rendering deadline. This API
433      * provides information that can be used to identify the root cause of the scheduling misses
434      * and provides overall frame scheduling statistics.
435      * <p>
436      * This API can be used in conjunction with the {@link FrameMetrics} API by associating jank
437      * classification data with {@link FrameMetrics} data via the frame VSync id.
438      */
439     @FlaggedApi(Flags.FLAG_JANK_API)
440     public static class JankData {
441 
442         /**
443          * Needs to be kept in sync with android_view_SurfaceControl.cpp's
444          * JankDataListenerWrapper::onJankDataAvailable.
445          * @hide
446          */
447         @IntDef(flag = true, value = {
448             JANK_NONE,
449             JANK_COMPOSER,
450             JANK_APPLICATION,
451             JANK_OTHER,
452         })
453         @Retention(RetentionPolicy.SOURCE)
454         public @interface JankType {}
455 
456         /**
457          * No jank detected, the frame was on time.
458          */
459         public static final int JANK_NONE = 0;
460 
461         /**
462          * Bitmask for jank due to deadlines missed by the composer.
463          */
464         public static final int JANK_COMPOSER = 1 << 0;
465 
466         /**
467          * Bitmask for jank due to deadlines missed by the application.
468          */
469         public static final int JANK_APPLICATION = 1 << 1;
470 
471         /**
472          * Bitmask for jank due to deadlines missed by other system components.
473          */
474         public static final int JANK_OTHER = 1 << 2;
475 
476         private final long mFrameVsyncId;
477         private final @JankType int mJankType;
478         private final @DurationNanosLong long mFrameIntervalNs;
479         private final @DurationNanosLong long mScheduledAppFrameTimeNs;
480         private final @DurationNanosLong long mActualAppFrameTimeNs;
481 
482         /**
483          * @hide
484          */
JankData(long frameVsyncId, @JankType int jankType, long frameIntervalNs, long scheduledAppFrameTimeNs, long actualAppFrameTimeNs)485         public JankData(long frameVsyncId, @JankType int jankType, long frameIntervalNs,
486                 long scheduledAppFrameTimeNs, long actualAppFrameTimeNs) {
487             mFrameVsyncId = frameVsyncId;
488             mJankType = jankType;
489             mFrameIntervalNs = frameIntervalNs;
490             mScheduledAppFrameTimeNs = scheduledAppFrameTimeNs;
491             mActualAppFrameTimeNs = actualAppFrameTimeNs;
492         }
493 
494         /**
495          * Returns the id of the frame for this jank classification.
496          *
497          * @see FrameMetrics#FRAME_TIMELINE_VSYNC_ID
498          * @see Choreographer.FrameTimeline#getVsyncId
499          * @see Transaction#setFrameTimeline
500          * @return the frame id
501          */
getVsyncId()502         public long getVsyncId() {
503             return mFrameVsyncId;
504         }
505 
506         /**
507          * Returns the bitmask indicating the types of jank observed.
508          *
509          * @return the jank type bitmask
510          */
getJankType()511         public @JankType int getJankType() {
512             return mJankType;
513         }
514 
515         /**
516          * Returns the time between frame VSyncs in nanoseconds.
517          *
518          * @return the frame interval in ns
519          * @hide
520          */
getFrameIntervalNanos()521         public @DurationNanosLong long getFrameIntervalNanos() {
522             return mFrameIntervalNs;
523         }
524 
525         /**
526          * Returns the duration in nanoseconds the application was scheduled to use to render this
527          * frame.
528          * <p>
529          * Note that this may be higher than the frame interval to allow for CPU/GPU
530          * parallelization of work.
531          *
532          * @return scheduled app time in ns
533          */
getScheduledAppFrameTimeNanos()534         public @DurationNanosLong long getScheduledAppFrameTimeNanos() {
535             return mScheduledAppFrameTimeNs;
536         }
537 
538         /**
539          * Returns the actual time in nanoseconds taken by the application to render this frame.
540          *
541          * @return the actual app time in ns
542          */
getActualAppFrameTimeNanos()543         public @DurationNanosLong long getActualAppFrameTimeNanos() {
544             return mActualAppFrameTimeNs;
545         }
546 
547         @Override
toString()548         public String toString() {
549             return "JankData{vsync=" + mFrameVsyncId
550                     + ", jankType=0x" + Integer.toHexString(mJankType)
551                     + ", frameInterval=" + mFrameIntervalNs + "ns"
552                     + ", scheduledAppTime=" + mScheduledAppFrameTimeNs + "ns"
553                     + ", actualAppTime=" + mActualAppFrameTimeNs + "ns}";
554         }
555     }
556 
557     /**
558      * Listener interface to be informed about SurfaceFlinger's jank classification for a specific
559      * surface.
560      *
561      * @see JankData
562      * @see #addOnJankDataListener
563      */
564     @FlaggedApi(Flags.FLAG_JANK_API)
565     public interface OnJankDataListener {
566         /**
567          * Called when new jank classifications are available. The listener is invoked out of band
568          * of the rendered frames with jank classification data for a batch of frames.
569          */
onJankDataAvailable(@onNull List<JankData> jankData)570         void onJankDataAvailable(@NonNull List<JankData> jankData);
571 
572     }
573 
574     /**
575      * Handle to a registered {@link OnJankDatalistener}.
576      */
577     @FlaggedApi(Flags.FLAG_JANK_API)
578     public static class OnJankDataListenerRegistration {
579         /** @hide */
580         public static final OnJankDataListenerRegistration NONE =
581                 new OnJankDataListenerRegistration() {
582                     @Override
583                     public void flush() {}
584 
585                     @Override
586                     public void removeAfter(long afterVsync) {}
587 
588                     @Override
589                     public void release() {}
590                 };
591 
592         private final long mNativeObject;
593 
594         private static final NativeAllocationRegistry sRegistry =
595                 NativeAllocationRegistry.createMalloced(
596                        OnJankDataListenerRegistration.class.getClassLoader(),
597                        nativeGetJankDataListenerWrapperFinalizer());
598 
599         private final Runnable mFreeNativeResources;
600         private boolean mRemoved = false;
601         private OnJankDataListener mListener;
602 
OnJankDataListenerRegistration()603         private OnJankDataListenerRegistration() {
604             mNativeObject = 0;
605             mFreeNativeResources = () -> {};
606         }
607 
OnJankDataListenerRegistration(SurfaceControl surface, OnJankDataListener listener)608         OnJankDataListenerRegistration(SurfaceControl surface, OnJankDataListener listener) {
609             mNativeObject = nativeCreateJankDataListenerWrapper(surface.mNativeObject, listener);
610             mFreeNativeResources = (mNativeObject == 0) ? () -> {} :
611                     sRegistry.registerNativeAllocation(this, mNativeObject);
612             // Make sure the listener doesn't get GCed as long as the registration is alive.
613             mListener = listener;
614         }
615 
616         /**
617          * Request a flush of any pending jank classification data.
618          * <p>
619          * May cause the registered listener to be invoked inband. Since jank is tracked by the
620          * system compositor by surface, flushing the data on one listener, will also cause other
621          * listeners on the same surface to receive jank classification data.
622          */
flush()623         public void flush() {
624             nativeFlushJankData(mNativeObject);
625         }
626 
627         /**
628          * Schedule the removal of the registered listener after the frame with the provided id.
629          * <p>
630          * Because jank classification is only possible after frames have been displayed, the
631          * callbacks are always delayed. To ensure receipt of all jank classification data, an
632          * application can schedule the removal to happen no sooner than after the data for the
633          * frame with the provided id has been provided.
634          * <p>
635          * Use a value &lt;= 0 for afterVsync to remove the listener immediately, ensuring no future
636          * callbacks.
637          *
638          * @param afterVsync the id of the Vsync after which to remove the listener
639          */
removeAfter(long afterVsync)640         public void removeAfter(long afterVsync) {
641             mRemoved = true;
642             nativeRemoveJankDataListener(mNativeObject, afterVsync);
643         }
644 
645         /**
646          * Free the native resources associated with the listener registration.
647          * @hide
648          */
release()649         public void release() {
650             if (!mRemoved) {
651                 removeAfter(0);
652             }
653             mListener = null;
654             mFreeNativeResources.run();
655         }
656     }
657 
658     private final CloseGuard mCloseGuard = CloseGuard.get();
659     private String mName;
660     private String mCallsite;
661 
662      /**
663      * Note: do not rename, this field is used by native code.
664      * @hide
665      */
666     public long mNativeObject;
667     private long mNativeHandle;
668 
669     private final Object mChoreographerLock = new Object();
670     @GuardedBy("mChoreographerLock")
671     private Choreographer mChoreographer;
672 
673     // TODO: Move width/height to native and fix locking through out.
674     private final Object mLock = new Object();
675     @GuardedBy("mLock")
676     private int mWidth;
677     @GuardedBy("mLock")
678     private int mHeight;
679 
680     private TrustedPresentationCallback mTrustedPresentationCallback;
681 
682     private WeakReference<View> mLocalOwnerView;
683 
684     // A throwable with the stack filled when this SurfaceControl is released (only if
685     // sDebugUsageAfterRelease) is enabled
686     private Throwable mReleaseStack = null;
687 
688     // Triggers the stack to be saved when any SurfaceControl in this process is released, which can
689     // be dumped as additional context
690     private static volatile boolean sDebugUsageAfterRelease = false;
691 
692     private static final NativeAllocationRegistry sRegistry =
693             NativeAllocationRegistry.createMalloced(SurfaceControl.class.getClassLoader(),
694                     nativeGetNativeSurfaceControlFinalizer());
695 
696     private Runnable mFreeNativeResources;
697 
698     /**
699      * Adds a reparenting listener.
700      *
701      * @param listener The listener.
702      * @return Whether listener was added.
703      *
704      * @hide
705      */
addOnReparentListener(@onNull OnReparentListener listener)706     public boolean addOnReparentListener(@NonNull OnReparentListener listener) {
707         synchronized (mLock) {
708             if (mReparentListeners == null) {
709                 mReparentListeners = new ArrayList<>(1);
710             }
711             return mReparentListeners.add(listener);
712         }
713     }
714 
715     /**
716      * Removes a reparenting listener.
717      *
718      * @param listener The listener.
719      * @return Whether listener was removed.
720      *
721      * @hide
722      */
removeOnReparentListener(@onNull OnReparentListener listener)723     public boolean removeOnReparentListener(@NonNull OnReparentListener listener) {
724         synchronized (mLock) {
725             final boolean removed = mReparentListeners.remove(listener);
726             if (mReparentListeners.isEmpty()) {
727                 mReparentListeners = null;
728             }
729             return removed;
730         }
731     }
732 
733     /* flags used in constructor (keep in sync with ISurfaceComposerClient.h) */
734 
735     /**
736      * Surface creation flag: Surface is created hidden
737      * @hide
738      */
739     @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553)
740     public static final int HIDDEN = 0x00000004;
741 
742     /**
743      * Surface creation flag: Skip this layer and its children when taking a screenshot. This
744      * also includes mirroring and screen recording, so the layers with flag SKIP_SCREENSHOT
745      * will not be included on non primary displays.
746      * @hide
747      */
748     public static final int SKIP_SCREENSHOT = 0x00000040;
749 
750     /**
751      * Surface creation flag: Special measures will be taken to disallow the surface's content to
752      * be copied. In particular, screenshots and secondary, non-secure displays will render black
753      * content instead of the surface content.
754      *
755      * @see com.android.server.display.DisplayControl#createDisplay(String, boolean)
756      * @hide
757      */
758     public static final int SECURE = 0x00000080;
759 
760 
761     /**
762      * Queue up BufferStateLayer buffers instead of dropping the oldest buffer when this flag is
763      * set. This blocks the client until all the buffers have been presented. If the buffers
764      * have presentation timestamps, then we may drop buffers.
765      * @hide
766      */
767     public static final int ENABLE_BACKPRESSURE = 0x00000100;
768 
769     /**
770      * Buffers from this SurfaceControl should be considered display decorations.
771      *
772      * If the hardware has optimizations for display decorations (e.g. rounded corners, camera
773      * cutouts, etc), it should use them for this layer.
774      * @hide
775      */
776     public static final int DISPLAY_DECORATION = 0x00000200;
777 
778     /**
779      * Ignore any destination frame set on the layer. This is used when the buffer scaling mode
780      * is freeze and the destination frame is applied asynchronously with the buffer submission.
781      * This is needed to maintain compatibility for SurfaceView scaling behavior.
782      * See SurfaceView scaling behavior for more details.
783      * @hide
784      */
785     public static final int IGNORE_DESTINATION_FRAME = 0x00000400;
786 
787     /**
788      * Special casing for layer that is a refresh rate indicator
789      * @hide
790      */
791     public static final int LAYER_IS_REFRESH_RATE_INDICATOR = 0x00000800;
792 
793     /**
794      * Sets a property on this layer indicating that its visible region should be considered when
795      * computing TrustedPresentation Thresholds
796      * @hide
797      */
798     public static final int CAN_OCCLUDE_PRESENTATION = 0x00001000;
799 
800     /**
801      * Indicates that the SurfaceControl should recover from buffer stuffing when
802      * possible. This is the case when the SurfaceControl is a ViewRootImpl.
803      * @hide
804      */
805     public static final int RECOVERABLE_FROM_BUFFER_STUFFING = 0x00002000;
806 
807     /**
808      * Surface creation flag: Creates a surface where color components are interpreted
809      * as "non pre-multiplied" by their alpha channel. Of course this flag is
810      * meaningless for surfaces without an alpha channel. By default
811      * surfaces are pre-multiplied, which means that each color component is
812      * already multiplied by its alpha value. In this case the blending
813      * equation used is:
814      * <p>
815      *    <code>DEST = SRC + DEST * (1-SRC_ALPHA)</code>
816      * <p>
817      * By contrast, non pre-multiplied surfaces use the following equation:
818      * <p>
819      *    <code>DEST = SRC * SRC_ALPHA * DEST * (1-SRC_ALPHA)</code>
820      * <p>
821      * pre-multiplied surfaces must always be used if transparent pixels are
822      * composited on top of each-other into the surface. A pre-multiplied
823      * surface can never lower the value of the alpha component of a given
824      * pixel.
825      * <p>
826      * In some rare situations, a non pre-multiplied surface is preferable.
827      * @hide
828      */
829     public static final int NON_PREMULTIPLIED = 0x00000100;
830 
831     /**
832      * Surface creation flag: Indicates that the surface must be considered opaque,
833      * even if its pixel format contains an alpha channel. This can be useful if an
834      * application needs full RGBA 8888 support for instance but will
835      * still draw every pixel opaque.
836      * <p>
837      * This flag is ignored if setAlpha() is used to make the surface non-opaque.
838      * Combined effects are (assuming a buffer format with an alpha channel):
839      * <ul>
840      * <li>OPAQUE + alpha(1.0) == opaque composition
841      * <li>OPAQUE + alpha(0.x) == blended composition
842      * <li>!OPAQUE + alpha(1.0) == blended composition
843      * <li>!OPAQUE + alpha(0.x) == blended composition
844      * </ul>
845      * If the underlying buffer lacks an alpha channel, the OPAQUE flag is effectively
846      * set automatically.
847      * @hide
848      */
849     public static final int OPAQUE = 0x00000400;
850 
851     /**
852      * Surface creation flag: Application requires a hardware-protected path to an
853      * external display sink. If a hardware-protected path is not available,
854      * then this surface will not be displayed on the external sink.
855      *
856      * @hide
857      */
858     public static final int PROTECTED_APP = 0x00000800;
859 
860     // 0x1000 is reserved for an independent DRM protected flag in framework
861 
862     /**
863      * Surface creation flag: Window represents a cursor glyph.
864      * @hide
865      */
866     public static final int CURSOR_WINDOW = 0x00002000;
867 
868     /**
869      * Surface creation flag: Indicates the effect layer will not have a color fill on
870      * creation.
871      *
872      * @hide
873      */
874     public static final int NO_COLOR_FILL = 0x00004000;
875 
876     /**
877      * Surface creation flag: Creates a normal surface.
878      * This is the default.
879      *
880      * @hide
881      */
882     public static final int FX_SURFACE_NORMAL   = 0x00000000;
883 
884     /**
885      * Surface creation flag: Creates a effect surface which
886      * represents a solid color and or shadows.
887      *
888      * @hide
889      */
890     public static final int FX_SURFACE_EFFECT = 0x00020000;
891 
892     /**
893      * Surface creation flag: Creates a container surface.
894      * This surface will have no buffers and will only be used
895      * as a container for other surfaces, or for its InputInfo.
896      * @hide
897      */
898     public static final int FX_SURFACE_CONTAINER = 0x00080000;
899 
900     /**
901      * @hide
902      */
903     public static final int FX_SURFACE_BLAST = 0x00040000;
904 
905     /**
906      * Mask used for FX values above.
907      *
908      * @hide
909      */
910     public static final int FX_SURFACE_MASK = 0x000F0000;
911 
912     /* flags used with setFlags() (keep in sync with ISurfaceComposer.h) */
913 
914     /**
915      * Surface flag: Hide the surface.
916      * Equivalent to calling hide().
917      * Updates the value set during Surface creation (see {@link #HIDDEN}).
918      */
919     private static final int SURFACE_HIDDEN = 0x01;
920 
921     /**
922      * Surface flag: composite without blending when possible.
923      * Updates the value set during Surface creation (see {@link #OPAQUE}).
924      */
925     private static final int SURFACE_OPAQUE = 0x02;
926 
927     /* flags used with setDisplayFlags() (keep in sync with DisplayDevice.h) */
928 
929     /**
930      * DisplayDevice flag: This display's transform is sent to inputflinger and used for input
931      * dispatch. This flag is used to disambiguate displays which share a layerstack.
932      * @hide
933      */
934     public static final int DISPLAY_RECEIVES_INPUT = 0x01;
935 
936     // Display power modes.
937     /**
938      * Display power mode off: used while blanking the screen.
939      * Use only with {@link SurfaceControl#setDisplayPowerMode}.
940      * @hide
941      */
942     public static final int POWER_MODE_OFF = 0;
943 
944     /**
945      * Display power mode doze: used while putting the screen into low power mode.
946      * Use only with {@link SurfaceControl#setDisplayPowerMode}.
947      * @hide
948      */
949     public static final int POWER_MODE_DOZE = 1;
950 
951     /**
952      * Display power mode normal: used while unblanking the screen.
953      * Use only with {@link SurfaceControl#setDisplayPowerMode}.
954      * @hide
955      */
956     public static final int POWER_MODE_NORMAL = 2;
957 
958     /**
959      * Display power mode doze: used while putting the screen into a suspended
960      * low power mode.  Use only with {@link SurfaceControl#setDisplayPowerMode}.
961      * @hide
962      */
963     public static final int POWER_MODE_DOZE_SUSPEND = 3;
964 
965     /**
966      * Display power mode on: used while putting the screen into a suspended
967      * full power mode.  Use only with {@link SurfaceControl#setDisplayPowerMode}.
968      * @hide
969      */
970     public static final int POWER_MODE_ON_SUSPEND = 4;
971 
972     /**
973      * Hint that this SurfaceControl should not participate in layer caching within SurfaceFlinger.
974      *
975      * A system layer may request that a layer does not participate in caching when there are known
976      * quality limitations when caching via the compositor's GPU path.
977      * Use only with {@link SurfaceControl.Transaction#setCachingHint}.
978      * @hide
979      */
980     public static final int CACHING_DISABLED = 0;
981 
982     /**
983      * Hint that this SurfaceControl should participate in layer caching within SurfaceFlinger.
984      *
985      * Use only with {@link SurfaceControl.Transaction#setCachingHint}.
986      * @hide
987      */
988     public static final int CACHING_ENABLED = 1;
989 
990     /** @hide */
991     @IntDef(flag = true, value = {CACHING_DISABLED, CACHING_ENABLED})
992     @Retention(RetentionPolicy.SOURCE)
993     public @interface CachingHint {}
994 
assignNativeObject(long nativeObject, String callsite)995     private void assignNativeObject(long nativeObject, String callsite) {
996         if (mNativeObject != 0) {
997             release();
998         }
999         if (nativeObject != 0) {
1000             mFreeNativeResources =
1001                     sRegistry.registerNativeAllocation(this, nativeObject);
1002         }
1003         mNativeObject = nativeObject;
1004         mNativeHandle = mNativeObject != 0 ? nativeGetHandle(nativeObject) : 0;
1005         if (sDebugUsageAfterRelease && mNativeObject == 0) {
1006             mReleaseStack = new Throwable("Assigned invalid nativeObject");
1007         } else {
1008             mReleaseStack = null;
1009         }
1010         setUnreleasedWarningCallSite(callsite);
1011         if (nativeObject != 0) {
1012             // Only add valid surface controls to the registry. This is called at the end of this
1013             // method since its information is dumped if the process threshold is reached.
1014             SurfaceControlRegistry.getProcessInstance().add(this);
1015         }
1016     }
1017 
1018     /**
1019      * @hide
1020      */
copyFrom(@onNull SurfaceControl other, String callsite)1021     public void copyFrom(@NonNull SurfaceControl other, String callsite) {
1022         mName = other.mName;
1023         mWidth = other.mWidth;
1024         mHeight = other.mHeight;
1025         mLocalOwnerView = other.mLocalOwnerView;
1026         assignNativeObject(nativeCopyFromSurfaceControl(other.mNativeObject), callsite);
1027     }
1028 
1029     /**
1030      * owner UID.
1031      * @hide
1032      */
1033     public static final int METADATA_OWNER_UID = 1;
1034 
1035     /**
1036      * Window type as per {@link WindowManager.LayoutParams}.
1037      * @hide
1038      */
1039     public static final int METADATA_WINDOW_TYPE = 2;
1040 
1041     /**
1042      * Task id to allow association between surfaces and task.
1043      * @hide
1044      */
1045     public static final int METADATA_TASK_ID = 3;
1046 
1047     /**
1048      * The style of mouse cursor and hotspot.
1049      * @hide
1050      */
1051     public static final int METADATA_MOUSE_CURSOR = 4;
1052 
1053     /**
1054      * Accessibility ID to allow association between surfaces and accessibility tree.
1055      * @hide
1056      */
1057     public static final int METADATA_ACCESSIBILITY_ID = 5;
1058 
1059     /**
1060      * owner PID.
1061      * @hide
1062      */
1063     public static final int METADATA_OWNER_PID = 6;
1064 
1065     /**
1066      * game mode for the layer - used for metrics
1067      * @hide
1068      */
1069     public static final int METADATA_GAME_MODE = 8;
1070 
1071     /** @hide */
1072     @Retention(RetentionPolicy.SOURCE)
1073     @IntDef(prefix = {"FRAME_RATE_SELECTION_STRATEGY_"},
1074             value = {FRAME_RATE_SELECTION_STRATEGY_PROPAGATE,
1075                     FRAME_RATE_SELECTION_STRATEGY_OVERRIDE_CHILDREN,
1076                     FRAME_RATE_SELECTION_STRATEGY_SELF})
1077     public @interface FrameRateSelectionStrategy {}
1078 
1079     // From window.h. Keep these in sync.
1080     /**
1081      * Default value. The layer uses its own frame rate specifications, assuming it has any
1082      * specifications, instead of its parent's. If it does not have its own frame rate
1083      * specifications, it will try to use its parent's. It will propagate its specifications to any
1084      * descendants that do not have their own.
1085      *
1086      * However, {@link #FRAME_RATE_SELECTION_STRATEGY_OVERRIDE_CHILDREN} on an ancestor layer
1087      * supersedes this behavior, meaning that this layer will inherit frame rate specifications
1088      * regardless of whether it has its own.
1089      * @hide
1090      */
1091     public static final int FRAME_RATE_SELECTION_STRATEGY_PROPAGATE = 0;
1092 
1093     /**
1094      * The layer's frame rate specifications will propagate to and override those of its descendant
1095      * layers.
1096      *
1097      * The layer itself has the {@link #FRAME_RATE_SELECTION_STRATEGY_PROPAGATE} behavior.
1098      * Thus, ancestor layer that also has the strategy
1099      * {@link #FRAME_RATE_SELECTION_STRATEGY_OVERRIDE_CHILDREN} will override this layer's
1100      * frame rate specifications.
1101      * @hide
1102      */
1103     public static final int FRAME_RATE_SELECTION_STRATEGY_OVERRIDE_CHILDREN = 1;
1104 
1105     /**
1106      * The layer's frame rate specifications will not propagate to its descendant
1107      * layers, even if the descendant layer has no frame rate specifications.
1108      * However, {@link #FRAME_RATE_SELECTION_STRATEGY_OVERRIDE_CHILDREN} on an ancestor
1109      * layer supersedes this behavior.
1110      * @hide
1111      */
1112     public static final int FRAME_RATE_SELECTION_STRATEGY_SELF = 2;
1113 
1114     /**
1115      * Builder class for {@link SurfaceControl} objects.
1116      *
1117      * By default the surface will be hidden, and have "unset" bounds, meaning it can
1118      * be as large as the bounds of its parent if a buffer or child so requires.
1119      *
1120      * It is necessary to set at least a name via {@link Builder#setName}
1121      */
1122     public static class Builder {
1123         private SurfaceSession mSession;
1124         private int mFlags = HIDDEN;
1125         private int mWidth;
1126         private int mHeight;
1127         private int mFormat = PixelFormat.OPAQUE;
1128         private String mName;
1129         private WeakReference<View> mLocalOwnerView;
1130         private SurfaceControl mParent;
1131         private SparseIntArray mMetadata;
1132         private String mCallsite = "SurfaceControl.Builder";
1133 
1134         /**
1135          * Begin building a SurfaceControl with a given {@link SurfaceSession}.
1136          *
1137          * @param session The {@link SurfaceSession} with which to eventually construct the surface.
1138          * @hide
1139          */
Builder(SurfaceSession session)1140         public Builder(SurfaceSession session) {
1141             mSession = session;
1142         }
1143 
1144         /**
1145          * Begin building a SurfaceControl.
1146          */
Builder()1147         public Builder() {
1148         }
1149 
1150         /**
1151          * Construct a new {@link SurfaceControl} with the set parameters. The builder
1152          * remains valid.
1153          */
1154         @NonNull
build()1155         public SurfaceControl build() {
1156             if (mWidth < 0 || mHeight < 0) {
1157                 throw new IllegalStateException(
1158                         "width and height must be positive or unset");
1159             }
1160             if ((mWidth > 0 || mHeight > 0) && (isEffectLayer() || isContainerLayer())) {
1161                 throw new IllegalStateException(
1162                         "Only buffer layers can set a valid buffer size.");
1163             }
1164 
1165             if (mName == null) {
1166                 Log.w(TAG, "Missing name for SurfaceControl", new Throwable());
1167             }
1168 
1169             if ((mFlags & FX_SURFACE_MASK) == FX_SURFACE_NORMAL) {
1170                 setBLASTLayer();
1171             }
1172 
1173             return new SurfaceControl(
1174                     mSession, mName, mWidth, mHeight, mFormat, mFlags, mParent, mMetadata,
1175                     mLocalOwnerView, mCallsite);
1176         }
1177 
1178         /**
1179          * Set a debugging-name for the SurfaceControl.
1180          *
1181          * @param name A name to identify the Surface in debugging.
1182          */
1183         @NonNull
setName(@onNull String name)1184         public Builder setName(@NonNull String name) {
1185             mName = name;
1186             return this;
1187         }
1188 
1189         /**
1190          * Set the local owner view for the surface. This view is only
1191          * valid in the same process and is not transferred in an IPC.
1192          *
1193          * Note: This is used for cases where we want to know the view
1194          * that manages the surface control while intercepting reparenting.
1195          * A specific example is InlineContentView which exposes is surface
1196          * control for reparenting as a way to implement clipping of several
1197          * InlineContentView instances within a certain area.
1198          *
1199          * @param view The owner view.
1200          * @return This builder.
1201          *
1202          * @hide
1203          */
1204         @NonNull
setLocalOwnerView(@onNull View view)1205         public Builder setLocalOwnerView(@NonNull View view) {
1206             mLocalOwnerView = new WeakReference<>(view);
1207             return this;
1208         }
1209 
1210         /**
1211          * Set the initial size of the controlled surface's buffers in pixels.
1212          *
1213          * @param width The buffer width in pixels.
1214          * @param height The buffer height in pixels.
1215          */
1216         @NonNull
setBufferSize(@ntRangefrom = 0) int width, @IntRange(from = 0) int height)1217         public Builder setBufferSize(@IntRange(from = 0) int width,
1218                 @IntRange(from = 0) int height) {
1219             if (width < 0 || height < 0) {
1220                 throw new IllegalArgumentException(
1221                         "width and height must be positive");
1222             }
1223             mWidth = width;
1224             mHeight = height;
1225             // set this as a buffer layer since we are specifying a buffer size.
1226             return setFlags(FX_SURFACE_NORMAL, FX_SURFACE_MASK);
1227         }
1228 
unsetBufferSize()1229         private void unsetBufferSize() {
1230             mWidth = 0;
1231             mHeight = 0;
1232         }
1233 
1234         /**
1235          * Set the pixel format of the controlled surface's buffers, using constants from
1236          * {@link android.graphics.PixelFormat}.
1237          */
1238         @NonNull
setFormat(@ixelFormat.Format int format)1239         public Builder setFormat(@PixelFormat.Format int format) {
1240             mFormat = format;
1241             return this;
1242         }
1243 
1244         /**
1245          * Specify if the app requires a hardware-protected path to
1246          * an external display sync. If protected content is enabled, but
1247          * such a path is not available, then the controlled Surface will
1248          * not be displayed.
1249          *
1250          * @param protectedContent Whether to require a protected sink.
1251          * @hide
1252          */
1253         @NonNull
setProtected(boolean protectedContent)1254         public Builder setProtected(boolean protectedContent) {
1255             if (protectedContent) {
1256                 mFlags |= PROTECTED_APP;
1257             } else {
1258                 mFlags &= ~PROTECTED_APP;
1259             }
1260             return this;
1261         }
1262 
1263         /**
1264          * Specify whether the Surface contains secure content. If true, the system
1265          * will prevent the surfaces content from being copied by another process. In
1266          * particular screenshots and VNC servers will be disabled. This is however
1267          * not a complete prevention of readback as {@link #setProtected}.
1268          * @hide
1269          */
1270         @NonNull
setSecure(boolean secure)1271         public Builder setSecure(boolean secure) {
1272             if (secure) {
1273                 mFlags |= SECURE;
1274             } else {
1275                 mFlags &= ~SECURE;
1276             }
1277             return this;
1278         }
1279 
1280         /**
1281          * Indicates whether the surface must be considered opaque,
1282          * even if its pixel format is set to translucent. This can be useful if an
1283          * application needs full RGBA 8888 support for instance but will
1284          * still draw every pixel opaque.
1285          * <p>
1286          * This flag only determines whether opacity will be sampled from the alpha channel.
1287          * Plane-alpha from calls to setAlpha() can still result in blended composition
1288          * regardless of the opaque setting.
1289          *
1290          * Combined effects are (assuming a buffer format with an alpha channel):
1291          * <ul>
1292          * <li>OPAQUE + alpha(1.0) == opaque composition
1293          * <li>OPAQUE + alpha(0.x) == blended composition
1294          * <li>OPAQUE + alpha(0.0) == no composition
1295          * <li>!OPAQUE + alpha(1.0) == blended composition
1296          * <li>!OPAQUE + alpha(0.x) == blended composition
1297          * <li>!OPAQUE + alpha(0.0) == no composition
1298          * </ul>
1299          * If the underlying buffer lacks an alpha channel, it is as if setOpaque(true)
1300          * were set automatically.
1301          * @param opaque Whether the Surface is OPAQUE.
1302          */
1303         @NonNull
setOpaque(boolean opaque)1304         public Builder setOpaque(boolean opaque) {
1305             if (opaque) {
1306                 mFlags |= OPAQUE;
1307             } else {
1308                 mFlags &= ~OPAQUE;
1309             }
1310             return this;
1311         }
1312 
1313         /**
1314          * Set the initial visibility for the SurfaceControl.
1315          *
1316          * @param hidden Whether the Surface is initially HIDDEN.
1317          */
1318         @NonNull
setHidden(boolean hidden)1319         public Builder setHidden(boolean hidden) {
1320             if (hidden) {
1321                 mFlags |= HIDDEN;
1322             } else {
1323                 mFlags &= ~HIDDEN;
1324             }
1325             return this;
1326         }
1327 
1328         /**
1329          * Set a parent surface for our new SurfaceControl.
1330          *
1331          * Child surfaces are constrained to the onscreen region of their parent.
1332          * Furthermore they stack relatively in Z order, and inherit the transformation
1333          * of the parent.
1334          *
1335          * @param parent The parent control.
1336          */
1337         @NonNull
setParent(@ullable SurfaceControl parent)1338         public Builder setParent(@Nullable SurfaceControl parent) {
1339             mParent = parent;
1340             return this;
1341         }
1342 
1343         /**
1344          * Sets a metadata int.
1345          *
1346          * @param key metadata key
1347          * @param data associated data
1348          * @hide
1349          */
setMetadata(int key, int data)1350         public Builder setMetadata(int key, int data) {
1351             if (mMetadata == null) {
1352                 mMetadata = new SparseIntArray();
1353             }
1354             mMetadata.put(key, data);
1355             return this;
1356         }
1357 
1358         /**
1359          * Indicate whether an 'EffectLayer' is to be constructed.
1360          *
1361          * An effect layer behaves like a container layer by default but it can support
1362          * color fill, shadows and/or blur. These layers will not have an associated buffer.
1363          * When created, this layer has no effects set and will be transparent but the caller
1364          * can render an effect by calling:
1365          *  - {@link Transaction#setColor(SurfaceControl, float[])}
1366          *  - {@link Transaction#setBackgroundBlurRadius(SurfaceControl, int)}
1367          *  - {@link Transaction#setShadowRadius(SurfaceControl, float)}
1368          *
1369          * @hide
1370          */
setEffectLayer()1371         public Builder setEffectLayer() {
1372             mFlags |= NO_COLOR_FILL;
1373             unsetBufferSize();
1374             return setFlags(FX_SURFACE_EFFECT, FX_SURFACE_MASK);
1375         }
1376 
1377         /**
1378          * A convenience function to create an effect layer with a default color fill
1379          * applied to it. Currently that color is black.
1380          *
1381          * @hide
1382          */
setColorLayer()1383         public Builder setColorLayer() {
1384             unsetBufferSize();
1385             return setFlags(FX_SURFACE_EFFECT, FX_SURFACE_MASK);
1386         }
1387 
isEffectLayer()1388         private boolean isEffectLayer() {
1389             return  (mFlags & FX_SURFACE_EFFECT) == FX_SURFACE_EFFECT;
1390         }
1391 
1392         /**
1393          * @hide
1394          */
setBLASTLayer()1395         public Builder setBLASTLayer() {
1396             return setFlags(FX_SURFACE_BLAST, FX_SURFACE_MASK);
1397         }
1398 
1399         /**
1400          * Indicates whether a 'ContainerLayer' is to be constructed.
1401          *
1402          * Container layers will not be rendered in any fashion and instead are used
1403          * as a parent of renderable layers.
1404          *
1405          * @hide
1406          */
setContainerLayer()1407         public Builder setContainerLayer() {
1408             unsetBufferSize();
1409             return setFlags(FX_SURFACE_CONTAINER, FX_SURFACE_MASK);
1410         }
1411 
isContainerLayer()1412         private boolean isContainerLayer() {
1413             return  (mFlags & FX_SURFACE_CONTAINER) == FX_SURFACE_CONTAINER;
1414         }
1415 
1416         /**
1417          * Set 'Surface creation flags' such as {@link #HIDDEN}, {@link #SECURE}.
1418          *
1419          * TODO: Finish conversion to individual builder methods?
1420          * @param flags The combined flags
1421          * @hide
1422          */
setFlags(int flags)1423         public Builder setFlags(int flags) {
1424             mFlags = flags;
1425             return this;
1426         }
1427 
1428         /**
1429          * Sets the callsite this SurfaceControl is constructed from.
1430          *
1431          * @param callsite String uniquely identifying callsite that created this object. Used for
1432          *                 leakage tracking.
1433          * @hide
1434          */
setCallsite(String callsite)1435         public Builder setCallsite(String callsite) {
1436             mCallsite = callsite;
1437             return this;
1438         }
1439 
setFlags(int flags, int mask)1440         private Builder setFlags(int flags, int mask) {
1441             mFlags = (mFlags & ~mask) | flags;
1442             return this;
1443         }
1444     }
1445 
1446     /**
1447      * Create a surface with a name.
1448      * <p>
1449      * The surface creation flags specify what kind of surface to create and
1450      * certain options such as whether the surface can be assumed to be opaque
1451      * and whether it should be initially hidden.  Surfaces should always be
1452      * created with the {@link #HIDDEN} flag set to ensure that they are not
1453      * made visible prematurely before all of the surface's properties have been
1454      * configured.
1455      * <p>
1456      * Good practice is to first create the surface with the {@link #HIDDEN} flag
1457      * specified, open a transaction, set the surface layer, layer stack, alpha,
1458      * and position, call {@link Transaction#show(SurfaceControl)} if appropriate, and close the
1459      * transaction.
1460      * <p>
1461      * Bounds of the surface is determined by its crop and its buffer size. If the
1462      * surface has no buffer or crop, the surface is boundless and only constrained
1463      * by the size of its parent bounds.
1464      *
1465      * @param session  The surface session.
1466      * @param name     The surface name, must not be null.
1467      * @param w        The surface initial width.
1468      * @param h        The surface initial height.
1469      * @param flags    The surface creation flags.
1470      * @param metadata Initial metadata.
1471      * @param callsite String uniquely identifying callsite that created this object. Used for
1472      *                 leakage tracking.
1473      * @throws throws OutOfResourcesException If the SurfaceControl cannot be created.
1474      */
SurfaceControl(SurfaceSession session, String name, int w, int h, int format, int flags, SurfaceControl parent, SparseIntArray metadata, WeakReference<View> localOwnerView, String callsite)1475     private SurfaceControl(SurfaceSession session, String name, int w, int h, int format, int flags,
1476             SurfaceControl parent, SparseIntArray metadata, WeakReference<View> localOwnerView,
1477             String callsite)
1478                     throws OutOfResourcesException, IllegalArgumentException {
1479         if (name == null) {
1480             throw new IllegalArgumentException("name must not be null");
1481         }
1482 
1483         mName = name;
1484         mWidth = w;
1485         mHeight = h;
1486         mLocalOwnerView = localOwnerView;
1487         Parcel metaParcel = Parcel.obtain();
1488         long nativeObject = 0;
1489         try {
1490             if (metadata != null && metadata.size() > 0) {
1491                 metaParcel.writeInt(metadata.size());
1492                 for (int i = 0; i < metadata.size(); ++i) {
1493                     metaParcel.writeInt(metadata.keyAt(i));
1494                     metaParcel.writeByteArray(
1495                             ByteBuffer.allocate(4).order(ByteOrder.nativeOrder())
1496                                     .putInt(metadata.valueAt(i)).array());
1497                 }
1498                 metaParcel.setDataPosition(0);
1499             }
1500             nativeObject = nativeCreate(session, name, w, h, format, flags,
1501                     parent != null ? parent.mNativeObject : 0, metaParcel);
1502         } finally {
1503             metaParcel.recycle();
1504         }
1505         if (nativeObject == 0) {
1506             throw new OutOfResourcesException(
1507                     "Couldn't allocate SurfaceControl native object");
1508         }
1509         assignNativeObject(nativeObject, callsite);
1510     }
1511 
1512     /**
1513      * Copy constructor. Creates a new native object pointing to the same surface as {@code other}.
1514      *
1515      * @param other The object to copy the surface from.
1516      * @param callsite String uniquely identifying callsite that created this object. Used for
1517      *                 leakage tracking.
1518      * @hide
1519      */
1520     @TestApi
SurfaceControl(@onNull SurfaceControl other, @NonNull String callsite)1521     public SurfaceControl(@NonNull SurfaceControl other, @NonNull String callsite) {
1522         copyFrom(other, callsite);
1523     }
1524 
SurfaceControl(Parcel in)1525     private SurfaceControl(Parcel in) {
1526         readFromParcel(in);
1527     }
1528 
1529     /**
1530      * Note: Most callers should use {@link SurfaceControl.Builder} or one of the other constructors
1531      *       to build an instance of a SurfaceControl. This constructor is mainly used for
1532      *       unparceling and passing into an AIDL call as an out parameter.
1533      * @hide
1534      */
SurfaceControl()1535     public SurfaceControl() {
1536     }
1537 
readFromParcel(Parcel in)1538     public void readFromParcel(Parcel in) {
1539         if (in == null) {
1540             throw new IllegalArgumentException("source must not be null");
1541         }
1542 
1543         mName = in.readString8();
1544         mWidth = in.readInt();
1545         mHeight = in.readInt();
1546 
1547         long object = 0;
1548         if (in.readInt() != 0) {
1549             object = nativeReadFromParcel(in);
1550         }
1551         assignNativeObject(object, "readFromParcel");
1552     }
1553 
1554     @Override
describeContents()1555     public int describeContents() {
1556         return 0;
1557     }
1558 
1559     @Override
writeToParcel(Parcel dest, int flags)1560     public void writeToParcel(Parcel dest, int flags) {
1561         if (sDebugUsageAfterRelease) {
1562             checkNotReleased();
1563         }
1564         dest.writeString8(mName);
1565         dest.writeInt(mWidth);
1566         dest.writeInt(mHeight);
1567         if (mNativeObject == 0) {
1568             dest.writeInt(0);
1569         } else {
1570             dest.writeInt(1);
1571         }
1572         nativeWriteToParcel(mNativeObject, dest);
1573 
1574         if ((flags & Parcelable.PARCELABLE_WRITE_RETURN_VALUE) != 0) {
1575             release();
1576         }
1577     }
1578 
1579     /**
1580      * Enables additional debug logs to track usage-after-release of all SurfaceControls in this
1581      * process.
1582      * @hide
1583      */
setDebugUsageAfterRelease(boolean debug)1584     public static void setDebugUsageAfterRelease(boolean debug) {
1585         if (!Build.isDebuggable()) {
1586             return;
1587         }
1588         sDebugUsageAfterRelease = debug;
1589     }
1590 
1591     /**
1592      * Provides more information to show about the source of this SurfaceControl if it is finalized
1593      * without being released. This is primarily intended for callers to update the call site after
1594      * receiving a SurfaceControl from another process, which would otherwise get a generic default
1595      * call site.
1596      * @hide
1597      */
setUnreleasedWarningCallSite(@onNull String callsite)1598     public void setUnreleasedWarningCallSite(@NonNull String callsite) {
1599         if (!isValid()) {
1600             return;
1601         }
1602         mCloseGuard.openWithCallSite("release", callsite);
1603         mCallsite = callsite;
1604     }
1605 
1606     /**
1607      * Returns the last provided call site when this SurfaceControl was created.
1608      * @hide
1609      */
getCallsite()1610     @Nullable String getCallsite() {
1611         return mCallsite;
1612     }
1613 
1614     /**
1615      * Returns the name of this SurfaceControl, mainly for debugging purposes.
1616      * @hide
1617      */
getName()1618     @NonNull String getName() {
1619         return mName;
1620     }
1621 
1622     /**
1623      * Checks whether two {@link SurfaceControl} objects represent the same surface.
1624      *
1625      * @param other The other object to check
1626      * @return {@code true} if these two {@link SurfaceControl} objects represent the same surface.
1627      * @hide
1628      */
1629     @TestApi
isSameSurface(@onNull SurfaceControl other)1630     public boolean isSameSurface(@NonNull SurfaceControl other) {
1631         return other.mNativeHandle == mNativeHandle;
1632     }
1633 
1634     /**
1635      * When called for the first time a new instance of the {@link Choreographer} is created
1636      * with a {@link android.os.Looper} of the current thread. Every subsequent call will return
1637      * the same instance of the Choreographer.
1638      *
1639      * @see #getChoreographer(Looper) to create Choreographer with a different
1640      * looper than current thread looper.
1641      *
1642      * @hide
1643      */
1644     @TestApi
getChoreographer()1645     public @NonNull Choreographer getChoreographer() {
1646         checkNotReleased();
1647         synchronized (mChoreographerLock) {
1648             if (mChoreographer == null) {
1649                 return getChoreographer(Looper.myLooper());
1650             }
1651             return mChoreographer;
1652         }
1653     }
1654 
1655     /**
1656      * When called for the first time a new instance of the {@link Choreographer} is created with
1657      * the sourced {@link android.os.Looper}. Every subsequent call will return the same
1658      * instance of the Choreographer.
1659      *
1660      * @see #getChoreographer()
1661      *
1662      * @throws IllegalStateException when a {@link Choreographer} instance exists with a different
1663      * looper than sourced.
1664      * @param looper the choreographer is attached on this looper.
1665      *
1666      * @hide
1667      */
1668     @TestApi
getChoreographer(@onNull Looper looper)1669     public @NonNull Choreographer getChoreographer(@NonNull Looper looper) {
1670         checkNotReleased();
1671         synchronized (mChoreographerLock) {
1672             if (mChoreographer == null) {
1673                 mChoreographer = Choreographer.getInstanceForSurfaceControl(mNativeHandle, looper);
1674             } else if (!mChoreographer.isTheLooperSame(looper)) {
1675                 throw new IllegalStateException(
1676                         "Choreographer already exists with a different looper");
1677             }
1678             return mChoreographer;
1679         }
1680     }
1681 
1682     /**
1683      * Returns true if {@link Choreographer} is present otherwise false.
1684      * To check the validity use {@link #isValid} on the SurfaceControl, a valid SurfaceControl with
1685      * choreographer will have the valid Choreographer.
1686      *
1687      * @hide
1688      */
1689     @TestApi
1690     @UnsupportedAppUsage
hasChoreographer()1691     public boolean hasChoreographer() {
1692         synchronized (mChoreographerLock) {
1693             return mChoreographer != null;
1694         }
1695     }
1696 
1697     /**
1698      * Write to a protocol buffer output stream. Protocol buffer message definition is at {@link
1699      * android.view.SurfaceControlProto}.
1700      *
1701      * @param proto Stream to write the SurfaceControl object to.
1702      * @param fieldId Field Id of the SurfaceControl as defined in the parent message.
1703      * @hide
1704      */
dumpDebug(ProtoOutputStream proto, long fieldId)1705     public void dumpDebug(ProtoOutputStream proto, long fieldId) {
1706         final long token = proto.start(fieldId);
1707         proto.write(HASH_CODE, System.identityHashCode(this));
1708         proto.write(NAME, mName);
1709         proto.write(LAYER_ID, getLayerId());
1710         proto.end(token);
1711     }
1712 
1713     public static final @android.annotation.NonNull Creator<SurfaceControl> CREATOR
1714             = new Creator<SurfaceControl>() {
1715         public SurfaceControl createFromParcel(Parcel in) {
1716             return new SurfaceControl(in);
1717         }
1718 
1719         public SurfaceControl[] newArray(int size) {
1720             return new SurfaceControl[size];
1721         }
1722     };
1723 
1724     /**
1725      * @hide
1726      */
1727     @Override
finalize()1728     protected void finalize() throws Throwable {
1729         try {
1730             if (mCloseGuard != null) {
1731                 mCloseGuard.warnIfOpen();
1732             }
1733             SurfaceControlRegistry.getProcessInstance().remove(this);
1734         } finally {
1735             super.finalize();
1736         }
1737     }
1738 
1739     /**
1740      * Release the local reference to the server-side surface. The surface
1741      * may continue to exist on-screen as long as its parent continues
1742      * to exist. To explicitly remove a surface from the screen use
1743      * {@link Transaction#reparent} with a null-parent. After release,
1744      * {@link #isValid} will return false and other methods will throw
1745      * an exception.
1746      *
1747      * Always call release() when you're done with a SurfaceControl.
1748      */
release()1749     public void release() {
1750         if (mNativeObject != 0) {
1751             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
1752                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
1753                         "release", null, this, null);
1754             }
1755             mFreeNativeResources.run();
1756             mNativeObject = 0;
1757             mNativeHandle = 0;
1758             if (sDebugUsageAfterRelease) {
1759                 mReleaseStack = new Throwable("Released");
1760             }
1761             mCloseGuard.close();
1762             synchronized (mChoreographerLock) {
1763                 if (mChoreographer != null) {
1764                     mChoreographer.invalidate();
1765                     mChoreographer = null;
1766                 }
1767             }
1768             SurfaceControlRegistry.getProcessInstance().remove(this);
1769         }
1770     }
1771 
1772     /**
1773      * Disconnect any client still connected to the surface.
1774      * @hide
1775      */
disconnect()1776     public void disconnect() {
1777         if (mNativeObject != 0) {
1778             nativeDisconnect(mNativeObject);
1779         }
1780     }
1781 
checkNotReleased()1782     private void checkNotReleased() {
1783         if (mNativeObject == 0) {
1784             if (mReleaseStack != null) {
1785                 throw new IllegalStateException("Invalid usage after release of " + this,
1786                         mReleaseStack);
1787             } else {
1788                 throw new NullPointerException("mNativeObject of " + this
1789                         + " is null. Have you called release() already?");
1790             }
1791         }
1792     }
1793 
1794     /**
1795      * Check whether this instance points to a valid layer with the system-compositor. For
1796      * example this may be false if construction failed, or the layer was released
1797      * ({@link #release}).
1798      *
1799      * @return Whether this SurfaceControl is valid.
1800      */
isValid()1801     public boolean isValid() {
1802         return mNativeObject != 0;
1803     }
1804 
1805     /** start a transaction
1806      * @hide
1807      * @deprecated Use regular Transaction instead.
1808      */
1809     @Deprecated
1810     @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.VANILLA_ICE_CREAM,
1811             publicAlternatives = "Use {@code SurfaceControl.Transaction} instead",
1812             trackingBug = 247078497)
openTransaction()1813     public static void openTransaction() {
1814         // TODO(b/247078497): It was used for global transaction (all usages are removed).
1815         //  Keep the method declaration to avoid breaking reference from legacy access.
1816     }
1817 
1818     /** end a transaction
1819      * @hide
1820      * @deprecated Use regular Transaction instead.
1821      */
1822     @Deprecated
1823     @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.VANILLA_ICE_CREAM,
1824             publicAlternatives = "Use {@code SurfaceControl.Transaction} instead",
1825             trackingBug = 247078497)
closeTransaction()1826     public static void closeTransaction() {
1827         // TODO(b/247078497): It was used for global transaction (all usages are removed).
1828         //  Keep the method declaration to avoid breaking reference from legacy access.
1829     }
1830 
1831     /**
1832      * @hide
1833      */
clearContentFrameStats()1834     public boolean clearContentFrameStats() {
1835         checkNotReleased();
1836         return nativeClearContentFrameStats(mNativeObject);
1837     }
1838 
1839     /**
1840      * @hide
1841      */
getContentFrameStats(WindowContentFrameStats outStats)1842     public boolean getContentFrameStats(WindowContentFrameStats outStats) {
1843         checkNotReleased();
1844         return nativeGetContentFrameStats(mNativeObject, outStats);
1845     }
1846 
1847     /**
1848      * @hide
1849      */
clearAnimationFrameStats()1850     public static boolean clearAnimationFrameStats() {
1851         return nativeClearAnimationFrameStats();
1852     }
1853 
1854     /**
1855      * @hide
1856      */
getAnimationFrameStats(WindowAnimationFrameStats outStats)1857     public static boolean getAnimationFrameStats(WindowAnimationFrameStats outStats) {
1858         return nativeGetAnimationFrameStats(outStats);
1859     }
1860 
1861     /**
1862      * @hide
1863      */
getWidth()1864     public int getWidth() {
1865         synchronized (mLock) {
1866             return mWidth;
1867         }
1868     }
1869 
1870     /**
1871      * @hide
1872      */
getHeight()1873     public int getHeight() {
1874         synchronized (mLock) {
1875             return mHeight;
1876         }
1877     }
1878 
1879     /**
1880      * Gets the local view that owns this surface.
1881      *
1882      * @return The owner view.
1883      *
1884      * @hide
1885      */
getLocalOwnerView()1886     public @Nullable View getLocalOwnerView() {
1887         return (mLocalOwnerView != null) ? mLocalOwnerView.get() : null;
1888     }
1889 
1890     @Override
toString()1891     public String toString() {
1892         return "Surface(name=" + mName + ")/@0x" +
1893                 Integer.toHexString(System.identityHashCode(this));
1894     }
1895 
1896     /**
1897      * Immutable information about physical display.
1898      *
1899      * @hide
1900      */
1901     public static final class StaticDisplayInfo {
1902         public boolean isInternal;
1903         public float density;
1904         public boolean secure;
1905         public DeviceProductInfo deviceProductInfo;
1906         public @Surface.Rotation int installOrientation;
1907 
1908         @Override
toString()1909         public String toString() {
1910             return "StaticDisplayInfo{isInternal=" + isInternal
1911                     + ", density=" + density
1912                     + ", secure=" + secure
1913                     + ", deviceProductInfo=" + deviceProductInfo
1914                     + ", installOrientation=" + installOrientation + "}";
1915         }
1916 
1917         @Override
equals(@ullable Object o)1918         public boolean equals(@Nullable Object o) {
1919             if (this == o) return true;
1920             if (o == null || getClass() != o.getClass()) return false;
1921             StaticDisplayInfo that = (StaticDisplayInfo) o;
1922             return isInternal == that.isInternal
1923                     && density == that.density
1924                     && secure == that.secure
1925                     && Objects.equals(deviceProductInfo, that.deviceProductInfo)
1926                     && installOrientation == that.installOrientation;
1927         }
1928 
1929         @Override
hashCode()1930         public int hashCode() {
1931             return Objects.hash(isInternal, density, secure, deviceProductInfo, installOrientation);
1932         }
1933     }
1934 
1935     /**
1936      * Dynamic information about physical display.
1937      *
1938      * @hide
1939      */
1940     public static final class DynamicDisplayInfo {
1941         public DisplayMode[] supportedDisplayModes;
1942         public int activeDisplayModeId;
1943         public float renderFrameRate;
1944         public boolean hasArrSupport;
1945         public FrameRateCategoryRate frameRateCategoryRate;
1946         public float[] supportedRefreshRates;
1947 
1948         public int[] supportedColorModes;
1949         public int activeColorMode;
1950 
1951         public Display.HdrCapabilities hdrCapabilities;
1952 
1953         public boolean autoLowLatencyModeSupported;
1954         public boolean gameContentTypeSupported;
1955 
1956         public int preferredBootDisplayMode;
1957 
1958         @Override
toString()1959         public String toString() {
1960             return "DynamicDisplayInfo{"
1961                     + "supportedDisplayModes=" + Arrays.toString(supportedDisplayModes)
1962                     + ", activeDisplayModeId=" + activeDisplayModeId
1963                     + ", renderFrameRate=" + renderFrameRate
1964                     + ", hasArrSupport=" + hasArrSupport
1965                     + ", frameRateCategoryRate=" + frameRateCategoryRate
1966                     + ", supportedRefreshRates=" + Arrays.toString(supportedRefreshRates)
1967                     + ", supportedColorModes=" + Arrays.toString(supportedColorModes)
1968                     + ", activeColorMode=" + activeColorMode
1969                     + ", hdrCapabilities=" + hdrCapabilities
1970                     + ", autoLowLatencyModeSupported=" + autoLowLatencyModeSupported
1971                     + ", gameContentTypeSupported" + gameContentTypeSupported
1972                     + ", preferredBootDisplayMode" + preferredBootDisplayMode + "}";
1973         }
1974 
1975         @Override
equals(@ullable Object o)1976         public boolean equals(@Nullable Object o) {
1977             if (this == o) return true;
1978             if (o == null || getClass() != o.getClass()) return false;
1979             DynamicDisplayInfo that = (DynamicDisplayInfo) o;
1980             return Arrays.equals(supportedDisplayModes, that.supportedDisplayModes)
1981                 && activeDisplayModeId == that.activeDisplayModeId
1982                 && renderFrameRate == that.renderFrameRate
1983                 && Arrays.equals(supportedColorModes, that.supportedColorModes)
1984                 && activeColorMode == that.activeColorMode
1985                 && Objects.equals(hdrCapabilities, that.hdrCapabilities)
1986                 && preferredBootDisplayMode == that.preferredBootDisplayMode
1987                 && hasArrSupport == that.hasArrSupport
1988                 && Objects.equals(frameRateCategoryRate, that.frameRateCategoryRate)
1989                 && Arrays.equals(supportedRefreshRates, that.supportedRefreshRates);
1990         }
1991 
1992         @Override
hashCode()1993         public int hashCode() {
1994             return Objects.hash(Arrays.hashCode(supportedDisplayModes), activeDisplayModeId,
1995                     renderFrameRate, activeColorMode, hdrCapabilities, hasArrSupport,
1996                     frameRateCategoryRate, Arrays.hashCode(supportedRefreshRates));
1997         }
1998     }
1999 
2000     /**
2001      * Configuration supported by physical display.
2002      *
2003      * @hide
2004      */
2005     public static final class DisplayMode {
2006         public int id;
2007         public int width;
2008         public int height;
2009         public float xDpi;
2010         public float yDpi;
2011 
2012         // Some modes have peak refresh rate lower than the panel vsync rate.
2013         public float peakRefreshRate;
2014         // Fixed rate of vsync deadlines for the panel.
2015         // This can be higher then the peak refresh rate for some panel technologies
2016         // See: VrrConfig.aidl
2017         public float vsyncRate;
2018         public long appVsyncOffsetNanos;
2019         public long presentationDeadlineNanos;
2020         public int[] supportedHdrTypes;
2021 
2022         /**
2023          * The config group ID this config is associated to.
2024          * Configs in the same group are similar from vendor's perspective and switching between
2025          * configs within the same group can be done seamlessly in most cases.
2026          * @see: android.hardware.graphics.composer@2.4::IComposerClient::Attribute::CONFIG_GROUP
2027          */
2028         public int group;
2029 
2030         @Override
toString()2031         public String toString() {
2032             return "DisplayMode{id=" + id
2033                     + ", width=" + width
2034                     + ", height=" + height
2035                     + ", xDpi=" + xDpi
2036                     + ", yDpi=" + yDpi
2037                     + ", peakRefreshRate=" + peakRefreshRate
2038                     + ", vsyncRate=" + vsyncRate
2039                     + ", appVsyncOffsetNanos=" + appVsyncOffsetNanos
2040                     + ", presentationDeadlineNanos=" + presentationDeadlineNanos
2041                     + ", supportedHdrTypes=" + Arrays.toString(supportedHdrTypes)
2042                     + ", group=" + group + "}";
2043         }
2044 
2045         @Override
equals(Object o)2046         public boolean equals(Object o) {
2047             if (this == o) return true;
2048             if (o == null || getClass() != o.getClass()) return false;
2049             DisplayMode that = (DisplayMode) o;
2050             return id == that.id
2051                     && width == that.width
2052                     && height == that.height
2053                     && Float.compare(that.xDpi, xDpi) == 0
2054                     && Float.compare(that.yDpi, yDpi) == 0
2055                     && Float.compare(that.peakRefreshRate, peakRefreshRate) == 0
2056                     && Float.compare(that.vsyncRate, vsyncRate) == 0
2057                     && appVsyncOffsetNanos == that.appVsyncOffsetNanos
2058                     && presentationDeadlineNanos == that.presentationDeadlineNanos
2059                     && Arrays.equals(supportedHdrTypes, that.supportedHdrTypes)
2060                     && group == that.group;
2061         }
2062 
2063         @Override
hashCode()2064         public int hashCode() {
2065             return Objects.hash(id, width, height, xDpi, yDpi, peakRefreshRate, vsyncRate,
2066                     appVsyncOffsetNanos, presentationDeadlineNanos, group,
2067                     Arrays.hashCode(supportedHdrTypes));
2068         }
2069     }
2070 
2071     /**
2072      * @hide
2073      */
setDisplayPowerMode(IBinder displayToken, int mode)2074     public static void setDisplayPowerMode(IBinder displayToken, int mode) {
2075         if (displayToken == null) {
2076             throw new IllegalArgumentException("displayToken must not be null");
2077         }
2078         nativeSetDisplayPowerMode(displayToken, mode);
2079     }
2080 
2081     /**
2082      * @hide
2083      */
getStaticDisplayInfo(long displayId)2084     public static StaticDisplayInfo getStaticDisplayInfo(long displayId) {
2085         return nativeGetStaticDisplayInfo(displayId);
2086     }
2087 
2088     /**
2089      * @hide
2090      */
getDynamicDisplayInfo(long displayId)2091     public static DynamicDisplayInfo getDynamicDisplayInfo(long displayId) {
2092         return nativeGetDynamicDisplayInfo(displayId);
2093     }
2094 
2095     /**
2096      * @hide
2097      */
getDisplayedContentSamplingAttributes( IBinder displayToken)2098     public static DisplayedContentSamplingAttributes getDisplayedContentSamplingAttributes(
2099             IBinder displayToken) {
2100         if (displayToken == null) {
2101             throw new IllegalArgumentException("displayToken must not be null");
2102         }
2103         return nativeGetDisplayedContentSamplingAttributes(displayToken);
2104     }
2105 
2106     /**
2107      * @hide
2108      */
setDisplayedContentSamplingEnabled( IBinder displayToken, boolean enable, int componentMask, int maxFrames)2109     public static boolean setDisplayedContentSamplingEnabled(
2110             IBinder displayToken, boolean enable, int componentMask, int maxFrames) {
2111         if (displayToken == null) {
2112             throw new IllegalArgumentException("displayToken must not be null");
2113         }
2114         final int maxColorComponents = 4;
2115         if ((componentMask >> maxColorComponents) != 0) {
2116             throw new IllegalArgumentException("invalid componentMask when enabling sampling");
2117         }
2118         return nativeSetDisplayedContentSamplingEnabled(
2119                 displayToken, enable, componentMask, maxFrames);
2120     }
2121 
2122     /**
2123      * @hide
2124      */
getDisplayedContentSample( IBinder displayToken, long maxFrames, long timestamp)2125     public static DisplayedContentSample getDisplayedContentSample(
2126             IBinder displayToken, long maxFrames, long timestamp) {
2127         if (displayToken == null) {
2128             throw new IllegalArgumentException("displayToken must not be null");
2129         }
2130         return nativeGetDisplayedContentSample(displayToken, maxFrames, timestamp);
2131     }
2132 
2133     /**
2134      * Information about the min and max refresh rate DM would like to set the display to.
2135      * @hide
2136      */
2137     public static final class RefreshRateRange implements Parcelable {
2138         public static final String TAG = "RefreshRateRange";
2139 
2140         // The tolerance within which we consider something approximately equals.
2141         public static final float FLOAT_TOLERANCE = 0.01f;
2142 
2143         /**
2144          * The lowest desired refresh rate.
2145          */
2146         public float min;
2147 
2148         /**
2149          * The highest desired refresh rate.
2150          */
2151         public float max;
2152 
RefreshRateRange()2153         public RefreshRateRange() {}
2154 
RefreshRateRange(float min, float max)2155         public RefreshRateRange(float min, float max) {
2156             if (min < 0 || max < 0 || min > max + FLOAT_TOLERANCE) {
2157                 Slog.e(TAG, "Wrong values for min and max when initializing RefreshRateRange : "
2158                         + min + " " + max);
2159                 this.min = this.max = 0;
2160                 return;
2161             }
2162             if (min > max) {
2163                 // Min and max are within epsilon of each other, but in the wrong order.
2164                 float t = min;
2165                 min = max;
2166                 max = t;
2167             }
2168             this.min = min;
2169             this.max = max;
2170         }
2171 
2172         /**
2173          * Checks whether the two objects have the same values.
2174          */
2175         @Override
equals(Object other)2176         public boolean equals(Object other) {
2177             if (other == this) {
2178                 return true;
2179             }
2180 
2181             if (!(other instanceof RefreshRateRange)) {
2182                 return false;
2183             }
2184 
2185             RefreshRateRange refreshRateRange = (RefreshRateRange) other;
2186             return (min == refreshRateRange.min && max == refreshRateRange.max);
2187         }
2188 
2189         @Override
hashCode()2190         public int hashCode() {
2191             return Objects.hash(min, max);
2192         }
2193 
2194         @Override
toString()2195         public String toString() {
2196             return "(" + min + " " + max + ")";
2197         }
2198 
2199         /**
2200          * Copies the supplied object's values to this object.
2201          */
copyFrom(RefreshRateRange other)2202         public void copyFrom(RefreshRateRange other) {
2203             this.min = other.min;
2204             this.max = other.max;
2205         }
2206 
2207         /**
2208          * Writes the RefreshRateRange to parce
2209          *
2210          * @param dest parcel to write the transaction to
2211          */
2212         @Override
writeToParcel(@onNull Parcel dest, @WriteFlags int flags)2213         public void writeToParcel(@NonNull Parcel dest, @WriteFlags int flags) {
2214             dest.writeFloat(min);
2215             dest.writeFloat(max);
2216         }
2217 
2218         @Override
describeContents()2219         public int describeContents() {
2220             return 0;
2221         }
2222 
2223         public static final @NonNull Creator<RefreshRateRange> CREATOR =
2224                 new Creator<RefreshRateRange>() {
2225                     @Override
2226                     public RefreshRateRange createFromParcel(Parcel in) {
2227                         return new RefreshRateRange(in.readFloat(), in.readFloat());
2228                     }
2229 
2230                     @Override
2231                     public RefreshRateRange[] newArray(int size) {
2232                         return new RefreshRateRange[size];
2233                     }
2234                 };
2235     }
2236 
2237     /**
2238      * Information about the ranges of refresh rates for the display physical refresh rates and the
2239      * render frame rate DM would like to set the policy to.
2240      * @hide
2241      */
2242     public static final class RefreshRateRanges {
2243         public static final String TAG = "RefreshRateRanges";
2244 
2245         /**
2246          *  The range of refresh rates that the display should run at.
2247          */
2248         public final RefreshRateRange physical;
2249 
2250         /**
2251          *  The range of refresh rates that apps should render at.
2252          */
2253         public final RefreshRateRange render;
2254 
RefreshRateRanges()2255         public RefreshRateRanges() {
2256             physical = new RefreshRateRange();
2257             render = new RefreshRateRange();
2258         }
2259 
RefreshRateRanges(RefreshRateRange physical, RefreshRateRange render)2260         public RefreshRateRanges(RefreshRateRange physical, RefreshRateRange render) {
2261             this.physical = new RefreshRateRange(physical.min, physical.max);
2262             this.render = new RefreshRateRange(render.min, render.max);
2263         }
2264 
2265         /**
2266          * Checks whether the two objects have the same values.
2267          */
2268         @Override
equals(Object other)2269         public boolean equals(Object other) {
2270             if (other == this) {
2271                 return true;
2272             }
2273 
2274             if (!(other instanceof RefreshRateRanges)) {
2275                 return false;
2276             }
2277 
2278             RefreshRateRanges rates = (RefreshRateRanges) other;
2279             return physical.equals(rates.physical) && render.equals(
2280                     rates.render);
2281         }
2282 
2283         @Override
hashCode()2284         public int hashCode() {
2285             return Objects.hash(physical, render);
2286         }
2287 
2288         @Override
toString()2289         public String toString() {
2290             return "physical: " + physical + " render:  " + render;
2291         }
2292 
2293         /**
2294          * Copies the supplied object's values to this object.
2295          */
copyFrom(RefreshRateRanges other)2296         public void copyFrom(RefreshRateRanges other) {
2297             this.physical.copyFrom(other.physical);
2298             this.render.copyFrom(other.render);
2299         }
2300     }
2301 
2302     /**
2303      * Contains information of the idle time of the screen after which the refresh rate is to be
2304      * reduced.
2305      *
2306      * @hide
2307      */
2308     public static final class IdleScreenRefreshRateConfig {
2309         /**
2310          *  The time(in ms) after which the refresh rate is to be reduced. Defaults to -1, which
2311          *  means no timeout has been configured for the current conditions
2312          */
2313         public int timeoutMillis;
2314 
IdleScreenRefreshRateConfig()2315         public IdleScreenRefreshRateConfig() {
2316             timeoutMillis = -1;
2317         }
2318 
IdleScreenRefreshRateConfig(int timeoutMillis)2319         public IdleScreenRefreshRateConfig(int timeoutMillis) {
2320             this.timeoutMillis = timeoutMillis;
2321         }
2322 
2323         /**
2324          * Checks whether the two objects have the same values.
2325          */
2326         @Override
equals(Object other)2327         public boolean equals(Object other) {
2328             if (other == this) {
2329                 return true;
2330             }
2331 
2332             if (!(other instanceof IdleScreenRefreshRateConfig) || other == null) {
2333                 return false;
2334             }
2335 
2336             IdleScreenRefreshRateConfig
2337                     idleScreenRefreshRateConfig = (IdleScreenRefreshRateConfig) other;
2338             return timeoutMillis == idleScreenRefreshRateConfig.timeoutMillis;
2339         }
2340 
2341         @Override
hashCode()2342         public int hashCode() {
2343             return Objects.hash(timeoutMillis);
2344         }
2345 
2346         @Override
toString()2347         public String toString() {
2348             return "timeoutMillis: " + timeoutMillis;
2349         }
2350 
2351         /**
2352          * Copies the supplied object's values to this object.
2353          */
copyFrom(IdleScreenRefreshRateConfig other)2354         public void copyFrom(IdleScreenRefreshRateConfig other) {
2355             if (other != null) {
2356                 this.timeoutMillis = other.timeoutMillis;
2357             }
2358         }
2359     }
2360 
2361 
2362     /**
2363      * Contains information about desired display configuration.
2364      *
2365      * @hide
2366      */
2367     public static final class DesiredDisplayModeSpecs {
2368         public int defaultMode;
2369         /**
2370          * If true this will allow switching between modes in different display configuration
2371          * groups. This way the user may see visual interruptions when the display mode changes.
2372          */
2373         public boolean allowGroupSwitching;
2374 
2375         /**
2376          * The primary physical and render refresh rate ranges represent display manager's general
2377          * guidance on the display configs surface flinger will consider when switching refresh
2378          * rates and scheduling the frame rate. Unless surface flinger has a specific reason to do
2379          * otherwise, it will stay within this range.
2380          */
2381         public final RefreshRateRanges primaryRanges;
2382 
2383         /**
2384          * The app request physical and render refresh rate ranges allow surface flinger to consider
2385          * more display configs when switching refresh rates. Although surface flinger will
2386          * generally stay within the primary range, specific considerations, such as layer frame
2387          * rate settings specified via the setFrameRate() api, may cause surface flinger to go
2388          * outside the primary range. Surface flinger never goes outside the app request range.
2389          * The app request range will be greater than or equal to the primary refresh rate range,
2390          * never smaller.
2391          */
2392         public final RefreshRateRanges appRequestRanges;
2393 
2394         /**
2395          * Represents the idle time of the screen after which the associated display's refresh rate
2396          * is to be reduced to preserve power
2397          * Defaults to null, meaning that the device is not configured to have a timeout.
2398          * Timeout value of -1 refers that the current conditions require no timeout
2399          */
2400         @Nullable
2401         public IdleScreenRefreshRateConfig idleScreenRefreshRateConfig;
2402 
DesiredDisplayModeSpecs()2403         public DesiredDisplayModeSpecs() {
2404             this.primaryRanges = new RefreshRateRanges();
2405             this.appRequestRanges = new RefreshRateRanges();
2406         }
2407 
DesiredDisplayModeSpecs(DesiredDisplayModeSpecs other)2408         public DesiredDisplayModeSpecs(DesiredDisplayModeSpecs other) {
2409             this.primaryRanges = new RefreshRateRanges();
2410             this.appRequestRanges = new RefreshRateRanges();
2411             copyFrom(other);
2412         }
2413 
DesiredDisplayModeSpecs(int defaultMode, boolean allowGroupSwitching, RefreshRateRanges primaryRanges, RefreshRateRanges appRequestRanges, @Nullable IdleScreenRefreshRateConfig idleScreenRefreshRateConfig)2414         public DesiredDisplayModeSpecs(int defaultMode, boolean allowGroupSwitching,
2415                 RefreshRateRanges primaryRanges, RefreshRateRanges appRequestRanges,
2416                 @Nullable IdleScreenRefreshRateConfig idleScreenRefreshRateConfig) {
2417             this.defaultMode = defaultMode;
2418             this.allowGroupSwitching = allowGroupSwitching;
2419             this.primaryRanges =
2420                     new RefreshRateRanges(primaryRanges.physical, primaryRanges.render);
2421             this.appRequestRanges =
2422                     new RefreshRateRanges(appRequestRanges.physical, appRequestRanges.render);
2423             this.idleScreenRefreshRateConfig =
2424                     (idleScreenRefreshRateConfig == null) ? null : new IdleScreenRefreshRateConfig(
2425                             idleScreenRefreshRateConfig.timeoutMillis);
2426         }
2427 
2428         @Override
equals(@ullable Object o)2429         public boolean equals(@Nullable Object o) {
2430             return o instanceof DesiredDisplayModeSpecs && equals((DesiredDisplayModeSpecs) o);
2431         }
2432 
2433         /**
2434          * Tests for equality.
2435          */
equals(DesiredDisplayModeSpecs other)2436         public boolean equals(DesiredDisplayModeSpecs other) {
2437             return other != null && defaultMode == other.defaultMode
2438                     && allowGroupSwitching == other.allowGroupSwitching
2439                     && primaryRanges.equals(other.primaryRanges)
2440                     && appRequestRanges.equals(other.appRequestRanges)
2441                     && Objects.equals(
2442                     idleScreenRefreshRateConfig, other.idleScreenRefreshRateConfig);
2443         }
2444 
2445         @Override
hashCode()2446         public int hashCode() {
2447             return 0; // don't care
2448         }
2449 
2450         /**
2451          * Copies the supplied object's values to this object.
2452          */
copyFrom(DesiredDisplayModeSpecs other)2453         public void copyFrom(DesiredDisplayModeSpecs other) {
2454             defaultMode = other.defaultMode;
2455             allowGroupSwitching = other.allowGroupSwitching;
2456             primaryRanges.copyFrom(other.primaryRanges);
2457             appRequestRanges.copyFrom(other.appRequestRanges);
2458             copyIdleScreenRefreshRateConfig(other.idleScreenRefreshRateConfig);
2459         }
2460 
2461         @Override
toString()2462         public String toString() {
2463             return "defaultMode=" + defaultMode
2464                     + " allowGroupSwitching=" + allowGroupSwitching
2465                     + " primaryRanges=" + primaryRanges
2466                     + " appRequestRanges=" + appRequestRanges
2467                     + " idleScreenRefreshRate=" + String.valueOf(idleScreenRefreshRateConfig);
2468         }
2469 
copyIdleScreenRefreshRateConfig(IdleScreenRefreshRateConfig other)2470         private void copyIdleScreenRefreshRateConfig(IdleScreenRefreshRateConfig other) {
2471             if (idleScreenRefreshRateConfig == null) {
2472                 if (other != null) {
2473                     idleScreenRefreshRateConfig =
2474                             new IdleScreenRefreshRateConfig(other.timeoutMillis);
2475                 }
2476             } else if (other == null) {
2477                 idleScreenRefreshRateConfig = null;
2478             } else {
2479                 idleScreenRefreshRateConfig.copyFrom(other);
2480             }
2481         }
2482     }
2483 
2484     /**
2485      * @hide
2486      */
setDesiredDisplayModeSpecs(IBinder displayToken, DesiredDisplayModeSpecs desiredDisplayModeSpecs)2487     public static boolean setDesiredDisplayModeSpecs(IBinder displayToken,
2488             DesiredDisplayModeSpecs desiredDisplayModeSpecs) {
2489         if (displayToken == null) {
2490             throw new IllegalArgumentException("displayToken must not be null");
2491         }
2492         if (desiredDisplayModeSpecs == null) {
2493             throw new IllegalArgumentException("desiredDisplayModeSpecs must not be null");
2494         }
2495         if (desiredDisplayModeSpecs.defaultMode < 0) {
2496             throw new IllegalArgumentException("defaultMode must be non-negative");
2497         }
2498 
2499         return nativeSetDesiredDisplayModeSpecs(displayToken, desiredDisplayModeSpecs);
2500     }
2501 
2502     /**
2503      * @hide
2504      */
getDesiredDisplayModeSpecs( IBinder displayToken)2505     public static DesiredDisplayModeSpecs getDesiredDisplayModeSpecs(
2506             IBinder displayToken) {
2507         if (displayToken == null) {
2508             throw new IllegalArgumentException("displayToken must not be null");
2509         }
2510 
2511         return nativeGetDesiredDisplayModeSpecs(displayToken);
2512     }
2513 
2514     /**
2515      * Color coordinates in CIE1931 XYZ color space
2516      *
2517      * @hide
2518      */
2519     public static final class CieXyz {
2520         /**
2521          * @hide
2522          */
2523         public float X;
2524 
2525         /**
2526          * @hide
2527          */
2528         public float Y;
2529 
2530         /**
2531          * @hide
2532          */
2533         public float Z;
2534     }
2535 
2536     /**
2537      * Contains a display's color primaries
2538      *
2539      * @hide
2540      */
2541     public static final class DisplayPrimaries {
2542         /**
2543          * @hide
2544          */
2545         public CieXyz red;
2546 
2547         /**
2548          * @hide
2549          */
2550         public CieXyz green;
2551 
2552         /**
2553          * @hide
2554          */
2555         public CieXyz blue;
2556 
2557         /**
2558          * @hide
2559          */
2560         public CieXyz white;
2561 
2562         /**
2563          * @hide
2564          */
DisplayPrimaries()2565         public DisplayPrimaries() {
2566         }
2567     }
2568 
2569     /**
2570      * @hide
2571      */
getDisplayNativePrimaries( IBinder displayToken)2572     public static DisplayPrimaries getDisplayNativePrimaries(
2573             IBinder displayToken) {
2574         if (displayToken == null) {
2575             throw new IllegalArgumentException("displayToken must not be null");
2576         }
2577 
2578         return nativeGetDisplayNativePrimaries(displayToken);
2579     }
2580 
2581     /**
2582      * @hide
2583      */
setActiveColorMode(IBinder displayToken, int colorMode)2584     public static boolean setActiveColorMode(IBinder displayToken, int colorMode) {
2585         if (displayToken == null) {
2586             throw new IllegalArgumentException("displayToken must not be null");
2587         }
2588         return nativeSetActiveColorMode(displayToken, colorMode);
2589     }
2590 
2591     /**
2592      * Returns an array of color spaces with 2 elements. The first color space is the
2593      * default color space and second one is wide color gamut color space.
2594      * @hide
2595      */
getCompositionColorSpaces()2596     public static ColorSpace[] getCompositionColorSpaces() {
2597         int[] dataspaces = nativeGetCompositionDataspaces();
2598         ColorSpace srgb = ColorSpace.get(ColorSpace.Named.SRGB);
2599         ColorSpace[] colorSpaces = { srgb, srgb };
2600         if (dataspaces != null && dataspaces.length == 2) {
2601             for (int i = 0; i < 2; ++i) {
2602                 ColorSpace cs = ColorSpace.getFromDataSpace(dataspaces[i]);
2603                 if (cs != null) {
2604                     colorSpaces[i] = cs;
2605                 }
2606             }
2607         }
2608         return colorSpaces;
2609     }
2610 
2611     /**
2612      * @return the overlay properties of the device
2613      * @hide
2614      */
getOverlaySupport()2615     public static OverlayProperties getOverlaySupport() {
2616         return nativeGetOverlaySupport();
2617     }
2618 
2619     /**
2620      * @hide
2621      */
getBootDisplayModeSupport()2622     public static boolean getBootDisplayModeSupport() {
2623         return nativeGetBootDisplayModeSupport();
2624     }
2625 
2626     /** There is no associated getter for this method.  When this is set, the display is expected
2627      * to start up in this mode next time the device reboots.
2628      * @hide
2629      */
setBootDisplayMode(IBinder displayToken, int displayModeId)2630     public static void setBootDisplayMode(IBinder displayToken, int displayModeId) {
2631         if (displayToken == null) {
2632             throw new IllegalArgumentException("displayToken must not be null");
2633         }
2634 
2635         nativeSetBootDisplayMode(displayToken, displayModeId);
2636     }
2637 
2638     /**
2639      * @hide
2640      */
clearBootDisplayMode(IBinder displayToken)2641     public static void clearBootDisplayMode(IBinder displayToken) {
2642         if (displayToken == null) {
2643             throw new IllegalArgumentException("displayToken must not be null");
2644         }
2645 
2646         nativeClearBootDisplayMode(displayToken);
2647     }
2648 
2649     /**
2650      * @hide
2651      */
setAutoLowLatencyMode(IBinder displayToken, boolean on)2652     public static void setAutoLowLatencyMode(IBinder displayToken, boolean on) {
2653         if (displayToken == null) {
2654             throw new IllegalArgumentException("displayToken must not be null");
2655         }
2656 
2657         nativeSetAutoLowLatencyMode(displayToken, on);
2658     }
2659 
2660     /**
2661      * @hide
2662      */
setGameContentType(IBinder displayToken, boolean on)2663     public static void setGameContentType(IBinder displayToken, boolean on) {
2664         if (displayToken == null) {
2665             throw new IllegalArgumentException("displayToken must not be null");
2666         }
2667 
2668         nativeSetGameContentType(displayToken, on);
2669     }
2670 
2671     /**
2672      * Returns whether protected content is supported in GPU composition.
2673      * @hide
2674      */
getProtectedContentSupport()2675     public static boolean getProtectedContentSupport() {
2676         return nativeGetProtectedContentSupport();
2677     }
2678 
2679     /**
2680      * Returns whether brightness operations are supported on a display.
2681      *
2682      * @param displayToken
2683      *      The token for the display.
2684      *
2685      * @return Whether brightness operations are supported on the display.
2686      *
2687      * @hide
2688      */
getDisplayBrightnessSupport(IBinder displayToken)2689     public static boolean getDisplayBrightnessSupport(IBinder displayToken) {
2690         return nativeGetDisplayBrightnessSupport(displayToken);
2691     }
2692 
2693     /**
2694      * Sets the brightness of a display.
2695      *
2696      * @param displayToken
2697      *      The token for the display whose brightness is set.
2698      * @param brightness
2699      *      A number between 0.0f (minimum brightness) and 1.0f (maximum brightness), or -1.0f to
2700      *      turn the backlight off.
2701      *
2702      * @return Whether the method succeeded or not.
2703      *
2704      * @throws IllegalArgumentException if:
2705      *      - displayToken is null;
2706      *      - brightness is NaN or greater than 1.0f.
2707      *
2708      * @hide
2709      */
setDisplayBrightness(IBinder displayToken, float brightness)2710     public static boolean setDisplayBrightness(IBinder displayToken, float brightness) {
2711         return setDisplayBrightness(displayToken, brightness, -1, brightness, -1);
2712     }
2713 
2714     /**
2715      * Sets the brightness of a display.
2716      *
2717      * @param displayToken
2718      *      The token for the display whose brightness is set.
2719      * @param sdrBrightness
2720      *      A number between 0.0f (minimum brightness) and 1.0f (maximum brightness), or -1.0f to
2721      *      turn the backlight off. Specifies the desired brightness of SDR content.
2722      * @param sdrBrightnessNits
2723      *      The value of sdrBrightness converted to calibrated nits. -1 if this isn't available.
2724      * @param displayBrightness
2725      *     A number between 0.0f (minimum brightness) and 1.0f (maximum brightness), or
2726      *     -1.0f to turn the backlight off. Specifies the desired brightness of the display itself,
2727      *     used directly for HDR content.
2728      * @param displayBrightnessNits
2729      *      The value of displayBrightness converted to calibrated nits. -1 if this isn't
2730      *      available.
2731      *
2732      * @return Whether the method succeeded or not.
2733      *
2734      * @throws IllegalArgumentException if:
2735      *      - displayToken is null;
2736      *      - brightness is NaN or greater than 1.0f.
2737      *
2738      * @hide
2739      */
setDisplayBrightness(IBinder displayToken, float sdrBrightness, float sdrBrightnessNits, float displayBrightness, float displayBrightnessNits)2740     public static boolean setDisplayBrightness(IBinder displayToken, float sdrBrightness,
2741             float sdrBrightnessNits, float displayBrightness, float displayBrightnessNits) {
2742         Objects.requireNonNull(displayToken);
2743         if (Float.isNaN(displayBrightness) || displayBrightness > 1.0f
2744                 || (displayBrightness < 0.0f && displayBrightness != -1.0f)) {
2745             throw new IllegalArgumentException("displayBrightness must be a number between 0.0f "
2746                     + " and 1.0f, or -1 to turn the backlight off: " + displayBrightness);
2747         }
2748         if (Float.isNaN(sdrBrightness) || sdrBrightness > 1.0f
2749                 || (sdrBrightness < 0.0f && sdrBrightness != -1.0f)) {
2750             throw new IllegalArgumentException("sdrBrightness must be a number between 0.0f "
2751                     + "and 1.0f, or -1 to turn the backlight off: " + sdrBrightness);
2752         }
2753         return nativeSetDisplayBrightness(displayToken, sdrBrightness, sdrBrightnessNits,
2754                 displayBrightness, displayBrightnessNits);
2755     }
2756 
2757     /**
2758      * Creates a mirrored hierarchy for the mirrorOf {@link SurfaceControl}
2759      *
2760      * Real Hierarchy    Mirror
2761      *                     SC (value that's returned)
2762      *                      |
2763      *      A               A'
2764      *      |               |
2765      *      B               B'
2766      *
2767      * @param mirrorOf The root of the hierarchy that should be mirrored.
2768      * @return A SurfaceControl that's the parent of the root of the mirrored hierarchy.
2769      *
2770      * @hide
2771      */
mirrorSurface(SurfaceControl mirrorOf)2772     public static SurfaceControl mirrorSurface(SurfaceControl mirrorOf) {
2773         long nativeObj = nativeMirrorSurface(mirrorOf.mNativeObject);
2774         SurfaceControl sc = new SurfaceControl();
2775         sc.mName = mirrorOf.mName + " (mirror)";
2776         sc.assignNativeObject(nativeObj, "mirrorSurface");
2777         return sc;
2778     }
2779 
validateColorArg(@ize4) float[] color)2780     private static void validateColorArg(@Size(4) float[] color) {
2781         final String msg = "Color must be specified as a float array with"
2782                 + " four values to represent r, g, b, a in range [0..1]";
2783         if (color.length != 4) {
2784             throw new IllegalArgumentException(msg);
2785         }
2786         for (float c:color) {
2787             if ((c < 0.f) || (c > 1.f)) {
2788                 throw new IllegalArgumentException(msg);
2789             }
2790         }
2791     }
2792 
2793     /**
2794      * Sets the global configuration for all the shadows drawn by SurfaceFlinger. Shadow follows
2795      * material design guidelines.
2796      *
2797      * @param ambientColor Color applied to the ambient shadow. The alpha is premultiplied. A
2798      *                     float array with four values to represent r, g, b, a in range [0..1]
2799      * @param spotColor Color applied to the spot shadow. The alpha is premultiplied. The position
2800      *                  of the spot shadow depends on the light position. A float array with
2801      *                  four values to represent r, g, b, a in range [0..1]
2802      * @param lightPosY Y axis position of the light used to cast the spot shadow in pixels.
2803      * @param lightPosZ Z axis position of the light used to cast the spot shadow in pixels. The X
2804      *                  axis position is set to the display width / 2.
2805      * @param lightRadius Radius of the light casting the shadow in pixels.
2806      *[
2807      * @hide
2808      */
setGlobalShadowSettings(@ize4) float[] ambientColor, @Size(4) float[] spotColor, float lightPosY, float lightPosZ, float lightRadius)2809     public static void setGlobalShadowSettings(@Size(4) float[] ambientColor,
2810             @Size(4) float[] spotColor, float lightPosY, float lightPosZ, float lightRadius) {
2811         validateColorArg(ambientColor);
2812         validateColorArg(spotColor);
2813         nativeSetGlobalShadowSettings(ambientColor, spotColor, lightPosY, lightPosZ, lightRadius);
2814     }
2815 
2816     /**
2817      * Returns whether/how a display supports DISPLAY_DECORATION.
2818      *
2819      * @param displayToken
2820      *      The token for the display.
2821      *
2822      * @return A class describing how the display supports DISPLAY_DECORATION or null if it does
2823      * not.
2824      *
2825      * TODO (b/218524164): Move this out of SurfaceControl.
2826      * @hide
2827      */
getDisplayDecorationSupport(IBinder displayToken)2828     public static DisplayDecorationSupport getDisplayDecorationSupport(IBinder displayToken) {
2829         return nativeGetDisplayDecorationSupport(displayToken);
2830     }
2831 
2832     /**
2833      * Adds a callback to be informed about SF's jank classification for this surface.
2834      * @hide
2835      */
2836     @NonNull
addOnJankDataListener( @onNull OnJankDataListener listener)2837     public OnJankDataListenerRegistration addOnJankDataListener(
2838             @NonNull OnJankDataListener listener) {
2839         return new OnJankDataListenerRegistration(this, listener);
2840     }
2841 
2842     /**
2843      * Return GPU Context priority that is set in SurfaceFlinger's Render Engine.
2844      * @hide
2845      */
getGPUContextPriority()2846     public static int getGPUContextPriority() {
2847         return nativeGetGPUContextPriority();
2848     }
2849 
2850     /**
2851      * Lets surfaceFlinger know the boot procedure is completed.
2852      * @hide
2853      */
bootFinished()2854     public static boolean bootFinished() {
2855         return nativeBootFinished();
2856     }
2857 
2858     /**
2859      * Retrieve the maximum number of concurrent picture profiles allowed across all displays.
2860      *
2861      * A picture profile is assigned to a layer via:
2862      * <ul>
2863      *     <li>Picture processing via {@link MediaCodec.KEY_PICTURE_PROFILE}</li>
2864      *     <li>Picture processing via {@link SurfaceControl.Transaction#setPictureProfileHandle}
2865      *     </li>
2866      * </ul>
2867      *
2868      * If the maximum number is exceeded, some layers will not receive profiles based on:
2869      * <ul>
2870      *     <li>The content priority assigned by the app</li>
2871      *     <li>The system-determined priority of the app owning the layer</li>
2872      * </ul>
2873      *
2874      * @see MediaCodec.KEY_PICTURE_PROFILE
2875      * @see SurfaceControl.Transaction#setPictureProfileHandle
2876      * @see SurfaceControl.Transaction#setContentPriority
2877      *
2878      * @hide
2879      */
2880     @IntRange(from = 0)
getMaxPictureProfiles()2881     public static int getMaxPictureProfiles() {
2882         return nativeGetMaxPictureProfiles();
2883     }
2884 
2885     /**
2886      * Interface to handle request to
2887      * {@link SurfaceControl.Transaction#addTransactionCommittedListener(Executor, TransactionCommittedListener)}
2888      */
2889     public interface TransactionCommittedListener {
2890         /**
2891          * Invoked when the transaction has been committed in SurfaceFlinger.
2892          */
onTransactionCommitted()2893         void onTransactionCommitted();
2894     }
2895 
2896     /**
2897      * Transaction stats given to the listener registered in
2898      * {@link SurfaceControl.Transaction#addTransactionCompletedListener}
2899      */
2900     @FlaggedApi(Flags.FLAG_SDK_DESIRED_PRESENT_TIME)
2901     public static final class TransactionStats {
2902         private long mLatchTimeNanos;
2903         private SyncFence mSyncFence;
2904 
2905         // called from native
TransactionStats(long latchTimeNanos, long presentFencePtr)2906         private TransactionStats(long latchTimeNanos, long presentFencePtr) {
2907             mLatchTimeNanos = latchTimeNanos;
2908             mSyncFence = new SyncFence(presentFencePtr);
2909         }
2910 
2911         /**
2912          * Close the TransactionStats. Called by the framework when the listener returns.
2913          * @hide
2914          */
close()2915         public void close() {
2916             mSyncFence.close();
2917         }
2918 
2919         /**
2920          * Returns the timestamp (in CLOCK_MONOTONIC) of when the frame was latched by the
2921          * framework and queued for presentation.
2922          */
2923         @FlaggedApi(Flags.FLAG_SDK_DESIRED_PRESENT_TIME)
getLatchTimeNanos()2924         public long getLatchTimeNanos() {
2925             return mLatchTimeNanos;
2926         }
2927 
2928         /**
2929          * Returns a new SyncFence that signals when the transaction has been presented.
2930          * The caller takes ownership of the fence and is responsible for closing
2931          * it by calling {@link SyncFence#close}.
2932          * If a device does not support present fences, an empty fence will be returned.
2933          */
2934         @FlaggedApi(Flags.FLAG_SDK_DESIRED_PRESENT_TIME)
getPresentFence()2935         public @NonNull SyncFence getPresentFence() {
2936             return new SyncFence(mSyncFence);
2937         }
2938     };
2939 
2940     /**
2941      * Threshold values that are sent with
2942      * {@link Transaction#setTrustedPresentationCallback(SurfaceControl,
2943      * TrustedPresentationThresholds, Executor, Consumer)}
2944      *
2945      * @deprecated Use {@link android.window.TrustedPresentationThresholds} instead.
2946      */
2947     @Deprecated
2948     public static final class TrustedPresentationThresholds {
2949         private final float mMinAlpha;
2950         private final float mMinFractionRendered;
2951         private final int mStabilityRequirementMs;
2952 
2953         /**
2954          * Creates a TrustedPresentationThresholds that's used when calling
2955          * {@link Transaction#setTrustedPresentationCallback(SurfaceControl,
2956          * TrustedPresentationThresholds, Executor, Consumer)}
2957          *
2958          * @param minAlpha               The min alpha the {@link SurfaceControl} is required to
2959          *                               have to be considered inside the threshold.
2960          * @param minFractionRendered    The min fraction of the SurfaceControl that was presented
2961          *                               to the user to be considered inside the threshold.
2962          * @param stabilityRequirementMs The time in milliseconds required for the
2963          *                               {@link SurfaceControl} to be in the threshold.
2964          * @throws IllegalArgumentException If threshold values are invalid.
2965          */
TrustedPresentationThresholds( @loatRangefrom = 0f, fromInclusive = false, to = 1f) float minAlpha, @FloatRange(from = 0f, fromInclusive = false, to = 1f) float minFractionRendered, @IntRange(from = 1) int stabilityRequirementMs)2966         public TrustedPresentationThresholds(
2967                 @FloatRange(from = 0f, fromInclusive = false, to = 1f) float minAlpha,
2968                 @FloatRange(from = 0f, fromInclusive = false, to = 1f) float minFractionRendered,
2969                 @IntRange(from = 1) int stabilityRequirementMs) {
2970             mMinAlpha = minAlpha;
2971             mMinFractionRendered = minFractionRendered;
2972             mStabilityRequirementMs = stabilityRequirementMs;
2973 
2974             checkValid();
2975         }
2976 
checkValid()2977         private void checkValid() {
2978             if (mMinAlpha <= 0 || mMinFractionRendered <= 0 || mStabilityRequirementMs < 1) {
2979                 throw new IllegalArgumentException(
2980                         "TrustedPresentationThresholds values are invalid");
2981             }
2982         }
2983     }
2984 
2985     /**
2986      * Register a TrustedPresentationCallback for a particular SurfaceControl so it can be notified
2987      * when the specified Threshold has been crossed.
2988      *
2989      * @hide
2990      */
2991     public abstract static class TrustedPresentationCallback {
2992         private final long mNativeObject;
2993 
2994         private static final NativeAllocationRegistry sRegistry =
2995                 NativeAllocationRegistry.createMalloced(
2996                         TrustedPresentationCallback.class.getClassLoader(),
2997                         getNativeTrustedPresentationCallbackFinalizer());
2998 
2999         private final Runnable mFreeNativeResources;
3000 
TrustedPresentationCallback()3001         private TrustedPresentationCallback() {
3002             mNativeObject = nativeCreateTpc(this);
3003             mFreeNativeResources = sRegistry.registerNativeAllocation(this, mNativeObject);
3004         }
3005 
3006         /**
3007          * Invoked when the SurfaceControl that this TrustedPresentationCallback was registered for
3008          * enters or exits the threshold bounds.
3009          *
3010          * @param inTrustedPresentationState true when the SurfaceControl entered the
3011          *                                   presentation state, false when it has left.
3012          */
onTrustedPresentationChanged(boolean inTrustedPresentationState)3013         public abstract void onTrustedPresentationChanged(boolean inTrustedPresentationState);
3014     }
3015 
3016     /**
3017      * An atomic set of changes to a set of SurfaceControl.
3018      */
3019     public static class Transaction implements Closeable, Parcelable {
3020         /**
3021          * @hide
3022          */
3023         public static final NativeAllocationRegistry sRegistry = new NativeAllocationRegistry(
3024                 Transaction.class.getClassLoader(),
3025                 nativeGetNativeTransactionFinalizer(), 512);
3026         /**
3027          * @hide
3028          */
3029         public long mNativeObject;
3030 
3031         private final ArrayMap<SurfaceControl, Point> mResizedSurfaces = new ArrayMap<>();
3032         private final ArrayMap<SurfaceControl, SurfaceControl> mReparentedSurfaces =
3033                  new ArrayMap<>();
3034         // Only non-null if the SurfaceControlRegistry is enabled. This list tracks the set of calls
3035         // made through this transaction object, and is dumped (and cleared) when the transaction is
3036         // later applied.
3037         @Nullable
3038         ArrayList<String> mCalls;
3039 
3040         Runnable mFreeNativeResources;
3041         private static final float[] INVALID_COLOR = {-1, -1, -1};
3042 
3043         /**
3044          * @hide
3045          */
checkPreconditions(SurfaceControl sc)3046         protected void checkPreconditions(SurfaceControl sc) {
3047             sc.checkNotReleased();
3048         }
3049 
3050         /**
3051          * Open a new transaction object. The transaction may be filed with commands to
3052          * manipulate {@link SurfaceControl} instances, and then applied atomically with
3053          * {@link #apply}. Eventually the user should invoke {@link #close}, when the object
3054          * is no longer required. Note however that re-using a transaction after a call to apply
3055          * is allowed as a convenience.
3056          */
Transaction()3057         public Transaction() {
3058             this(nativeCreateTransaction());
3059         }
3060 
Transaction(long nativeObject)3061         private Transaction(long nativeObject) {
3062             mNativeObject = nativeObject;
3063             mFreeNativeResources = sRegistry.registerNativeAllocation(this, mNativeObject);
3064             setUpForSurfaceControlRegistry();
3065         }
3066 
Transaction(Parcel in)3067         private Transaction(Parcel in) {
3068             readFromParcel(in);
3069             setUpForSurfaceControlRegistry();
3070         }
3071 
3072         /**
3073          * Sets up this transaction for the SurfaceControlRegistry.
3074          */
setUpForSurfaceControlRegistry()3075         private void setUpForSurfaceControlRegistry() {
3076             if (!SurfaceControlRegistry.sCallStackDebuggingInitialized) {
3077                 SurfaceControlRegistry.initializeCallStackDebugging();
3078             }
3079             mCalls = SurfaceControlRegistry.sLogAllTxCallsOnApply
3080                     ? new ArrayList<>()
3081                     : null;
3082             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
3083                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
3084                         "ctor", this, null, null);
3085             }
3086         }
3087 
3088         /**
3089          * Changes the default ApplyToken.
3090          *
3091          * ApplyToken is used to determine the order in which Transactions are applied.
3092          * Transactions applied with the same ApplyToken will be applied in the order
3093          * they were queued in SurfaceFlinger. Transactions are sent via binder so the
3094          * caller should be aware of the order in which binder calls are executed in
3095          * SurfaceFlinger. This along with the ApplyToken will determine the order
3096          * in which Transactions are applied. Transactions with different apply tokens
3097          * will be applied in arbitrary order regardless of when they were queued in
3098          * SurfaceFlinger.
3099          *
3100          * Caller must keep track of the previous ApplyToken if they want to restore it.
3101          *
3102          * Note each buffer producer should have its own ApplyToken in order to ensure
3103          * that Transactions are not delayed by Transactions from other buffer producers.
3104          *
3105          * @hide
3106          */
setDefaultApplyToken(IBinder token)3107         public static void setDefaultApplyToken(IBinder token) {
3108             nativeSetDefaultApplyToken(token);
3109         }
3110 
3111         /**
3112          * Returns the default ApplyToken.
3113          *
3114          * @hide
3115          */
getDefaultApplyToken()3116         public static IBinder getDefaultApplyToken() {
3117             return nativeGetDefaultApplyToken();
3118         }
3119 
3120         /**
3121          * Apply the transaction, clearing its state, and making it usable
3122          * as a new transaction.
3123          *
3124          * This method will also increment the transaction ID for debugging purposes.
3125          */
apply()3126         public void apply() {
3127             apply(/*sync*/ false);
3128         }
3129 
3130         /**
3131          * Applies the transaction as a one way binder call. This transaction will be applied out
3132          * of order with other transactions that are applied synchronously. This method is not
3133          * safe. It should only be used when the order does not matter.
3134          *
3135          * @hide
3136          */
applyAsyncUnsafe()3137         public void applyAsyncUnsafe() {
3138             apply(/*sync*/ false, /*oneWay*/ true);
3139         }
3140 
3141 
3142         /**
3143          * Clear the transaction object, without applying it. The transction ID is preserved.
3144          *
3145          * @hide
3146          */
clear()3147         public void clear() {
3148             mResizedSurfaces.clear();
3149             mReparentedSurfaces.clear();
3150             if (mNativeObject != 0) {
3151                 nativeClearTransaction(mNativeObject);
3152             }
3153             if (mCalls != null) {
3154                 mCalls.clear();
3155             }
3156         }
3157 
3158         /**
3159          * Release the native transaction object, without applying it.
3160          */
3161         @Override
close()3162         public void close() {
3163             mResizedSurfaces.clear();
3164             mReparentedSurfaces.clear();
3165             mFreeNativeResources.run();
3166             mNativeObject = 0;
3167             if (mCalls != null) {
3168                 mCalls.clear();
3169             }
3170         }
3171 
3172         /**
3173          * Jankier version of apply. Avoid use (b/28068298).
3174          * @hide
3175          */
apply(boolean sync)3176         public void apply(boolean sync) {
3177             apply(sync, /*oneWay*/ false);
3178         }
3179 
apply(boolean sync, boolean oneWay)3180         private void apply(boolean sync, boolean oneWay) {
3181             applyResizedSurfaces();
3182             notifyReparentedSurfaces();
3183 
3184             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
3185                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
3186                         SurfaceControlRegistry.APPLY, this, null, null);
3187             }
3188             if (mCalls != null) {
3189                 mCalls.clear();
3190             }
3191             nativeApplyTransaction(mNativeObject, sync, oneWay);
3192         }
3193 
3194         /**
3195          * @hide
3196          */
applyResizedSurfaces()3197         protected void applyResizedSurfaces() {
3198             for (int i = mResizedSurfaces.size() - 1; i >= 0; i--) {
3199                 final Point size = mResizedSurfaces.valueAt(i);
3200                 final SurfaceControl surfaceControl = mResizedSurfaces.keyAt(i);
3201                 synchronized (surfaceControl.mLock) {
3202                     surfaceControl.resize(size.x, size.y);
3203                 }
3204             }
3205             mResizedSurfaces.clear();
3206         }
3207 
3208         /**
3209          * @hide
3210          */
notifyReparentedSurfaces()3211         protected void notifyReparentedSurfaces() {
3212             final int reparentCount = mReparentedSurfaces.size();
3213             for (int i = reparentCount - 1; i >= 0; i--) {
3214                 final SurfaceControl child = mReparentedSurfaces.keyAt(i);
3215                 synchronized (child.mLock) {
3216                     final int listenerCount = (child.mReparentListeners != null)
3217                             ? child.mReparentListeners.size() : 0;
3218                     for (int j = 0; j < listenerCount; j++) {
3219                         final OnReparentListener listener = child.mReparentListeners.get(j);
3220                         listener.onReparent(this, mReparentedSurfaces.valueAt(i));
3221                     }
3222                     mReparentedSurfaces.removeAt(i);
3223                 }
3224             }
3225         }
3226 
3227         /**
3228          * Toggle the visibility of a given Layer and it's sub-tree.
3229          *
3230          * @param sc The SurfaceControl for which to set the visibility
3231          * @param visible The new visibility
3232          * @return This transaction object.
3233          */
3234         @NonNull
setVisibility(@onNull SurfaceControl sc, boolean visible)3235         public Transaction setVisibility(@NonNull SurfaceControl sc, boolean visible) {
3236             checkPreconditions(sc);
3237             if (visible) {
3238                 return show(sc);
3239             } else {
3240                 return hide(sc);
3241             }
3242         }
3243 
3244         /**
3245          * This information is passed to SurfaceFlinger to decide which window should have a
3246          * priority when deciding about the refresh rate of the display. All windows have the
3247          * lowest priority by default.
3248          * @hide
3249          */
3250         @NonNull
setFrameRateSelectionPriority(@onNull SurfaceControl sc, int priority)3251         public Transaction setFrameRateSelectionPriority(@NonNull SurfaceControl sc, int priority) {
3252             checkPreconditions(sc);
3253             nativeSetFrameRateSelectionPriority(mNativeObject, sc.mNativeObject, priority);
3254             return this;
3255         }
3256 
3257         /**
3258          * Request that a given surface and it's sub-tree be shown.
3259          *
3260          * @param sc The surface to show.
3261          * @return This transaction.
3262          * @hide
3263          */
3264         @UnsupportedAppUsage
show(SurfaceControl sc)3265         public Transaction show(SurfaceControl sc) {
3266             checkPreconditions(sc);
3267             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
3268                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
3269                         "show", this, sc, null);
3270             }
3271             nativeSetFlags(mNativeObject, sc.mNativeObject, 0, SURFACE_HIDDEN);
3272             return this;
3273         }
3274 
3275         /**
3276          * Request that a given surface and it's sub-tree be hidden.
3277          *
3278          * @param sc The surface to hidden.
3279          * @return This transaction.
3280          * @hide
3281          */
3282         @UnsupportedAppUsage
hide(SurfaceControl sc)3283         public Transaction hide(SurfaceControl sc) {
3284             checkPreconditions(sc);
3285             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
3286                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
3287                         "hide", this, sc, null);
3288             }
3289             nativeSetFlags(mNativeObject, sc.mNativeObject, SURFACE_HIDDEN, SURFACE_HIDDEN);
3290             return this;
3291         }
3292 
3293         /**
3294          * Sets the SurfaceControl to the specified position relative to the parent
3295          * SurfaceControl
3296          *
3297          * @param sc The SurfaceControl to change position
3298          * @param x the X position
3299          * @param y the Y position
3300          * @return this transaction
3301          */
3302         @NonNull
setPosition(@onNull SurfaceControl sc, float x, float y)3303         public Transaction setPosition(@NonNull SurfaceControl sc, float x, float y) {
3304             checkPreconditions(sc);
3305             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
3306                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
3307                         "setPosition", this, sc, "x=" + x + " y=" + y);
3308             }
3309             nativeSetPosition(mNativeObject, sc.mNativeObject, x, y);
3310             return this;
3311         }
3312 
3313         /**
3314          * Sets the SurfaceControl to the specified scale with (0, 0) as the center point
3315          * of the scale.
3316          *
3317          * @param sc The SurfaceControl to change scale
3318          * @param scaleX the X scale
3319          * @param scaleY the Y scale
3320          * @return this transaction
3321          */
3322         @NonNull
setScale(@onNull SurfaceControl sc, float scaleX, float scaleY)3323         public Transaction setScale(@NonNull SurfaceControl sc, float scaleX, float scaleY) {
3324             checkPreconditions(sc);
3325             Preconditions.checkArgument(scaleX >= 0, "Negative value passed in for scaleX");
3326             Preconditions.checkArgument(scaleY >= 0, "Negative value passed in for scaleY");
3327             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
3328                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
3329                         "setScale", this, sc, "sx=" + scaleX + " sy=" + scaleY);
3330             }
3331             nativeSetScale(mNativeObject, sc.mNativeObject, scaleX, scaleY);
3332             return this;
3333         }
3334 
3335         /**
3336          * Set the default buffer size for the SurfaceControl, if there is a
3337          * {@link Surface} associated with the control, then
3338          * this will be the default size for buffers dequeued from it.
3339          * @param sc The surface to set the buffer size for.
3340          * @param w The default width
3341          * @param h The default height
3342          * @return This Transaction
3343          */
3344         @NonNull
setBufferSize(@onNull SurfaceControl sc, @IntRange(from = 0) int w, @IntRange(from = 0) int h)3345         public Transaction setBufferSize(@NonNull SurfaceControl sc,
3346                 @IntRange(from = 0) int w, @IntRange(from = 0) int h) {
3347             checkPreconditions(sc);
3348             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
3349                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
3350                         "setBufferSize", this, sc, "w=" + w + " h=" + h);
3351             }
3352             mResizedSurfaces.put(sc, new Point(w, h));
3353             return this;
3354         }
3355 
3356         /**
3357          * Provide the graphic producer a transform hint if the layer and its children are
3358          * in an orientation different from the display's orientation. The caller is responsible
3359          * for clearing this transform hint if the layer is no longer in a fixed orientation.
3360          *
3361          * The transform hint is used to prevent allocating a buffer of different size when a
3362          * layer is rotated. The producer can choose to consume the hint and allocate the buffer
3363          * with the same size.
3364          *
3365          * @return This Transaction.
3366          * @hide
3367          */
3368         @NonNull
setFixedTransformHint(@onNull SurfaceControl sc, @Surface.Rotation int transformHint)3369         public Transaction setFixedTransformHint(@NonNull SurfaceControl sc,
3370                        @Surface.Rotation int transformHint) {
3371             checkPreconditions(sc);
3372             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
3373                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
3374                         "setFixedTransformHint", this, sc, "hint=" + transformHint);
3375             }
3376             nativeSetFixedTransformHint(mNativeObject, sc.mNativeObject, transformHint);
3377             return this;
3378         }
3379 
3380         /**
3381          * Clearing any transform hint if set on this layer.
3382          *
3383          * @return This Transaction.
3384          * @hide
3385          */
3386         @NonNull
unsetFixedTransformHint(@onNull SurfaceControl sc)3387         public Transaction unsetFixedTransformHint(@NonNull SurfaceControl sc) {
3388             checkPreconditions(sc);
3389             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
3390                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
3391                         "unsetFixedTransformHint", this, sc, null);
3392             }
3393             nativeSetFixedTransformHint(mNativeObject, sc.mNativeObject, -1/* INVALID_ROTATION */);
3394             return this;
3395         }
3396 
3397         /**
3398          * Set the Z-order for a given SurfaceControl, relative to it's siblings.
3399          * If two siblings share the same Z order the ordering is undefined. Surfaces
3400          * with a negative Z will be placed below the parent surface.
3401          *
3402          * Calling setLayer after setRelativeLayer will reset the relative layer
3403          * in the same transaction.
3404          *
3405          * @param sc The SurfaceControl to set the Z order on
3406          * @param z The Z-order
3407          * @return This Transaction.
3408          */
3409         @NonNull
setLayer(@onNull SurfaceControl sc, @IntRange(from = Integer.MIN_VALUE, to = Integer.MAX_VALUE) int z)3410         public Transaction setLayer(@NonNull SurfaceControl sc,
3411                 @IntRange(from = Integer.MIN_VALUE, to = Integer.MAX_VALUE) int z) {
3412             checkPreconditions(sc);
3413             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
3414                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
3415                         "setLayer", this, sc, "z=" + z);
3416             }
3417             nativeSetLayer(mNativeObject, sc.mNativeObject, z);
3418             return this;
3419         }
3420 
3421         /**
3422          * Set the Z-order for a given SurfaceControl, relative to the specified SurfaceControl.
3423          * The SurfaceControl with a negative z will be placed below the relativeTo
3424          * SurfaceControl and the SurfaceControl with a positive z will be placed above the
3425          * relativeTo SurfaceControl.
3426          *
3427          * Calling setLayer will reset the relative layer. Calling setRelativeLayer after setLayer
3428          * will override the setLayer call.
3429          *
3430          * If a layer is set to be relative to a layer that is destroyed, the layer will be
3431          * offscreen until setLayer is called or setRelativeLayer is called with a valid
3432          * SurfaceControl.
3433          *
3434          * @param sc The SurfaceControl to set the Z order on
3435          * @param relativeTo The SurfaceControl to set the Z order relative to
3436          * @param z The Z-order
3437          * @return This Transaction.
3438          * @hide
3439          */
setRelativeLayer(SurfaceControl sc, SurfaceControl relativeTo, int z)3440         public Transaction setRelativeLayer(SurfaceControl sc, SurfaceControl relativeTo, int z) {
3441             checkPreconditions(sc);
3442             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
3443                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
3444                         "setRelativeLayer", this, sc, "relTo=" + relativeTo + " z=" + z);
3445             }
3446             nativeSetRelativeLayer(mNativeObject, sc.mNativeObject, relativeTo.mNativeObject, z);
3447             return this;
3448         }
3449 
3450         /**
3451          * The hint from the buffer producer as to what portion of the layer is
3452          * transparent.
3453          *
3454          * @hide
3455          */
setTransparentRegionHint(SurfaceControl sc, Region transparentRegion)3456         public Transaction setTransparentRegionHint(SurfaceControl sc, Region transparentRegion) {
3457             checkPreconditions(sc);
3458             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
3459                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
3460                         "unsetFixedTransformHint", this, sc, "region=" + transparentRegion);
3461             }
3462             nativeSetTransparentRegionHint(mNativeObject,
3463                     sc.mNativeObject, transparentRegion);
3464             return this;
3465         }
3466 
3467         /**
3468          * Set the alpha for a given surface. If the alpha is non-zero the SurfaceControl
3469          * will be blended with the Surfaces under it according to the specified ratio.
3470          *
3471          * @param sc The given SurfaceControl.
3472          * @param alpha The alpha to set.
3473          */
3474         @NonNull
setAlpha(@onNull SurfaceControl sc, @FloatRange(from = 0.0, to = 1.0) float alpha)3475         public Transaction setAlpha(@NonNull SurfaceControl sc,
3476                 @FloatRange(from = 0.0, to = 1.0) float alpha) {
3477             checkPreconditions(sc);
3478             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
3479                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
3480                         "setAlpha", this, sc, "alpha=" + alpha);
3481             }
3482             nativeSetAlpha(mNativeObject, sc.mNativeObject, alpha);
3483             return this;
3484         }
3485 
3486         /**
3487          * Sets the input channel for a given SurfaceControl. The position and order of the
3488          * SurfaceControl in conjunction with the touchable region in the InputWindowHandle
3489          * determines the hit region.
3490          *
3491          * @hide
3492          */
setInputWindowInfo(SurfaceControl sc, InputWindowHandle handle)3493         public Transaction setInputWindowInfo(SurfaceControl sc, InputWindowHandle handle) {
3494             checkPreconditions(sc);
3495             nativeSetInputWindowInfo(mNativeObject, sc.mNativeObject, handle);
3496             return this;
3497         }
3498 
3499         /**
3500          * Adds a callback that is called after WindowInfosListeners from the systems server are
3501          * complete. This is primarily used to ensure that InputDispatcher::setInputWindowsLocked
3502          * has been called before running the added callback.
3503          *
3504          * @hide
3505          */
addWindowInfosReportedListener(@onNull Runnable listener)3506         public Transaction addWindowInfosReportedListener(@NonNull Runnable listener) {
3507             nativeAddWindowInfosReportedListener(mNativeObject, listener);
3508             return this;
3509         }
3510 
3511         /**
3512          * Specify how the buffer associated with this Surface is mapped in to the
3513          * parent coordinate space. The source frame will be scaled to fit the destination
3514          * frame, after being rotated according to the orientation parameter.
3515          *
3516          * @param sc The SurfaceControl to specify the geometry of
3517          * @param sourceCrop The source rectangle in buffer space. Or null for the entire buffer.
3518          * @param destFrame The destination rectangle in parent space. Or null for the source frame.
3519          * @param orientation The buffer rotation
3520          * @return This transaction object.
3521          * @deprecated Use {@link #setCrop(SurfaceControl, Rect)},
3522          * {@link #setBufferTransform(SurfaceControl, int)},
3523          * {@link #setPosition(SurfaceControl, float, float)} and
3524          * {@link #setScale(SurfaceControl, float, float)} instead.
3525          */
3526         @NonNull
setGeometry(@onNull SurfaceControl sc, @Nullable Rect sourceCrop, @Nullable Rect destFrame, @Surface.Rotation int orientation)3527         public Transaction setGeometry(@NonNull SurfaceControl sc, @Nullable Rect sourceCrop,
3528                 @Nullable Rect destFrame, @Surface.Rotation int orientation) {
3529             checkPreconditions(sc);
3530             nativeSetGeometry(mNativeObject, sc.mNativeObject, sourceCrop, destFrame, orientation);
3531             return this;
3532         }
3533 
3534         /**
3535          * @hide
3536          */
3537         @UnsupportedAppUsage
setMatrix(SurfaceControl sc, float dsdx, float dtdx, float dtdy, float dsdy)3538         public Transaction setMatrix(SurfaceControl sc,
3539                 float dsdx, float dtdx, float dtdy, float dsdy) {
3540             checkPreconditions(sc);
3541             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
3542                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
3543                         "setMatrix", this, sc,
3544                         "dsdx=" + dsdx + " dtdx=" + dtdx + " dtdy=" + dtdy + " dsdy=" + dsdy);
3545             }
3546             nativeSetMatrix(mNativeObject, sc.mNativeObject,
3547                     dsdx, dtdx, dtdy, dsdy);
3548             return this;
3549         }
3550 
3551         /**
3552          * Sets the transform and position of a {@link SurfaceControl} from a 3x3 transformation
3553          * matrix.
3554          *
3555          * @param sc     SurfaceControl to set matrix of
3556          * @param matrix The matrix to apply.
3557          * @param float9 An array of 9 floats to be used to extract the values from the matrix.
3558          * @hide
3559          */
3560         @UnsupportedAppUsage
setMatrix(SurfaceControl sc, Matrix matrix, float[] float9)3561         public Transaction setMatrix(SurfaceControl sc, Matrix matrix, float[] float9) {
3562             matrix.getValues(float9);
3563             setMatrix(sc, float9[MSCALE_X], float9[MSKEW_Y],
3564                     float9[MSKEW_X], float9[MSCALE_Y]);
3565             setPosition(sc, float9[MTRANS_X], float9[MTRANS_Y]);
3566             return this;
3567         }
3568 
3569         /**
3570          * Sets the color transform for the Surface.
3571          *
3572          * @param sc          SurfaceControl to set color transform of
3573          * @param matrix      A float array with 9 values represents a 3x3 transform matrix
3574          * @param translation A float array with 3 values represents a translation vector
3575          * @hide
3576          */
setColorTransform(SurfaceControl sc, @Size(9) float[] matrix, @Size(3) float[] translation)3577         public Transaction setColorTransform(SurfaceControl sc, @Size(9) float[] matrix,
3578                 @Size(3) float[] translation) {
3579             checkPreconditions(sc);
3580             nativeSetColorTransform(mNativeObject, sc.mNativeObject, matrix, translation);
3581             return this;
3582         }
3583 
3584         /**
3585          * Sets the Surface to be color space agnostic. If a surface is color space agnostic,
3586          * the color can be interpreted in any color space.
3587          * @param agnostic A boolean to indicate whether the surface is color space agnostic
3588          * @hide
3589          */
setColorSpaceAgnostic(SurfaceControl sc, boolean agnostic)3590         public Transaction setColorSpaceAgnostic(SurfaceControl sc, boolean agnostic) {
3591             checkPreconditions(sc);
3592             nativeSetColorSpaceAgnostic(mNativeObject, sc.mNativeObject, agnostic);
3593             return this;
3594         }
3595 
3596         /**
3597          * Bounds the surface and its children to the bounds specified. Size of the surface will be
3598          * ignored and only the crop and buffer size will be used to determine the bounds of the
3599          * surface. If no crop is specified and the surface has no buffer, the surface bounds is
3600          * only constrained by the size of its parent bounds.
3601          *
3602          * To unset the crop, pass in an invalid Rect (0, 0, -1, -1)
3603          *
3604          * @param sc   SurfaceControl to set crop of.
3605          * @param crop Bounds of the crop to apply.
3606          * @hide
3607          * @deprecated Use {@link #setCrop(SurfaceControl, Rect)} instead.
3608          */
3609         @Deprecated
3610         @UnsupportedAppUsage
setWindowCrop(SurfaceControl sc, Rect crop)3611         public Transaction setWindowCrop(SurfaceControl sc, Rect crop) {
3612             checkPreconditions(sc);
3613             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
3614                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
3615                         "setWindowCrop", this, sc, "crop=" + crop);
3616             }
3617             if (crop != null) {
3618                 nativeSetWindowCrop(mNativeObject, sc.mNativeObject,
3619                         crop.left, crop.top, crop.right, crop.bottom);
3620             } else {
3621                 nativeSetWindowCrop(mNativeObject, sc.mNativeObject, 0, 0, 0, 0);
3622             }
3623 
3624             return this;
3625         }
3626 
3627         /**
3628          * Bounds the surface and its children to the bounds specified. Size of the surface will be
3629          * ignored and only the crop and buffer size will be used to determine the bounds of the
3630          * surface. If no crop is specified and the surface has no buffer, the surface bounds is
3631          * only constrained by the size of its parent bounds.
3632          *
3633          * To unset the crop, pass in an invalid Rect (0, 0, -1, -1)
3634          *
3635          * @param sc   SurfaceControl to set crop of.
3636          * @param crop Bounds of the crop to apply.
3637          * @return this This transaction for chaining
3638          */
setCrop(@onNull SurfaceControl sc, @Nullable Rect crop)3639         public @NonNull Transaction setCrop(@NonNull SurfaceControl sc, @Nullable Rect crop) {
3640             checkPreconditions(sc);
3641             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
3642                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
3643                         "setCrop", this, sc, "crop=" + crop);
3644             }
3645             if (crop != null) {
3646                 Preconditions.checkArgument(crop.isValid(), "Crop " + crop
3647                         + " isn't valid");
3648                 nativeSetWindowCrop(mNativeObject, sc.mNativeObject,
3649                         crop.left, crop.top, crop.right, crop.bottom);
3650             } else {
3651                 nativeSetWindowCrop(mNativeObject, sc.mNativeObject, 0, 0, 0, 0);
3652             }
3653 
3654             return this;
3655         }
3656 
3657         /**
3658          * Same as {@link Transaction#setWindowCrop(SurfaceControl, Rect)} but sets the crop rect
3659          * top left at 0, 0.
3660          *
3661          * @param sc     SurfaceControl to set crop of.
3662          * @param width  width of crop rect
3663          * @param height height of crop rect
3664          * @hide
3665          */
setWindowCrop(SurfaceControl sc, int width, int height)3666         public Transaction setWindowCrop(SurfaceControl sc, int width, int height) {
3667             checkPreconditions(sc);
3668             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
3669                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
3670                         "setWindowCrop", this, sc, "w=" + width + " h=" + height);
3671             }
3672             nativeSetWindowCrop(mNativeObject, sc.mNativeObject, 0, 0, width, height);
3673             return this;
3674         }
3675 
3676         /**
3677          * Bounds the surface and its children to the bounds specified. Size of the surface will be
3678          * ignored and only the crop and buffer size will be used to determine the bounds of the
3679          * surface. If no crop is specified and the surface has no buffer, the surface bounds is
3680          * only constrained by the size of its parent bounds.
3681          *
3682          * To unset the crop, pass in an invalid Rect (0, 0, -1, -1)
3683          *
3684          * @param sc   SurfaceControl to set crop of.
3685          * @param crop Bounds of the crop to apply.
3686          * @return this This transaction for chaining
3687          * @hide
3688          */
setCrop(@onNull SurfaceControl sc, float left, float top, float right, float bottom)3689         public @NonNull Transaction setCrop(@NonNull SurfaceControl sc, float left, float top,
3690                 float right, float bottom) {
3691             checkPreconditions(sc);
3692             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
3693                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
3694                         "setCrop", this, sc, "crop={" + top + ", " + left + ", " +
3695                         bottom + ", " + right + "}");
3696             }
3697             nativeSetCrop(mNativeObject, sc.mNativeObject, left, top, right, bottom);
3698             return this;
3699         }
3700 
3701         /**
3702          * Sets the corner radius of a {@link SurfaceControl}. This corner radius is applied to the
3703          * SurfaceControl and its children. The API expects a crop to be set on the SurfaceControl
3704          * to ensure that the corner radius is applied to the correct region. If the crop does not
3705          * intersect with the SurfaceControl's visible content, the corner radius will not be
3706          * applied.
3707          *
3708          * @param sc SurfaceControl
3709          * @param cornerRadius Corner radius in pixels.
3710          * @return Itself.
3711          * @hide
3712          */
3713         @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553)
setCornerRadius(SurfaceControl sc, float cornerRadius)3714         public Transaction setCornerRadius(SurfaceControl sc, float cornerRadius) {
3715             checkPreconditions(sc);
3716             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
3717                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
3718                         "setCornerRadius", this, sc, "cornerRadius=" + cornerRadius);
3719             }
3720             nativeSetCornerRadius(mNativeObject, sc.mNativeObject, cornerRadius);
3721 
3722             return this;
3723         }
3724 
3725 
3726         /**
3727          * Disables corner radius of a {@link SurfaceControl}. When the radius set by
3728          * {@link Transaction#setCornerRadius(SurfaceControl, float)} is equal to
3729          * clientDrawnCornerRadius the corner radius drawn by SurfaceFlinger is disabled.
3730          *
3731          * @param sc SurfaceControl
3732          * @param clientDrawnCornerRadius Corner radius drawn by the client
3733          * @return Itself.
3734          * @hide
3735          */
3736         @NonNull
setClientDrawnCornerRadius(@onNull SurfaceControl sc, float clientDrawnCornerRadius)3737         public Transaction setClientDrawnCornerRadius(@NonNull SurfaceControl sc,
3738                                                             float clientDrawnCornerRadius) {
3739             checkPreconditions(sc);
3740             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
3741                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
3742                         "setClientDrawnCornerRadius", this, sc, "clientDrawnCornerRadius="
3743                         + clientDrawnCornerRadius);
3744             }
3745             if (Flags.ignoreCornerRadiusAndShadows()) {
3746                 nativeSetClientDrawnCornerRadius(mNativeObject, sc.mNativeObject,
3747                                                                 clientDrawnCornerRadius);
3748             } else {
3749                 Log.w(TAG, "setClientDrawnCornerRadius was called but"
3750                             + "ignore_corner_radius_and_shadows flag is disabled");
3751             }
3752 
3753             return this;
3754         }
3755 
3756         /**
3757          * Sets the background blur radius of the {@link SurfaceControl}.
3758          *
3759          * @param sc SurfaceControl.
3760          * @param radius Blur radius in pixels.
3761          * @return itself.
3762          * @hide
3763          */
setBackgroundBlurRadius(SurfaceControl sc, int radius)3764         public Transaction setBackgroundBlurRadius(SurfaceControl sc, int radius) {
3765             checkPreconditions(sc);
3766             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
3767                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
3768                         "setBackgroundBlurRadius", this, sc, "radius=" + radius);
3769             }
3770             nativeSetBackgroundBlurRadius(mNativeObject, sc.mNativeObject, radius);
3771             return this;
3772         }
3773 
3774         /**
3775          * Specify what regions should be blurred on the {@link SurfaceControl}.
3776          *
3777          * @param sc SurfaceControl.
3778          * @param regions List of regions that will have blurs.
3779          * @return itself.
3780          * @see BlurRegion#toFloatArray()
3781          * @hide
3782          */
setBlurRegions(SurfaceControl sc, float[][] regions)3783         public Transaction setBlurRegions(SurfaceControl sc, float[][] regions) {
3784             checkPreconditions(sc);
3785             nativeSetBlurRegions(mNativeObject, sc.mNativeObject, regions, regions.length);
3786             return this;
3787         }
3788 
3789         /**
3790          * @hide
3791          */
setStretchEffect(SurfaceControl sc, float width, float height, float vecX, float vecY, float maxStretchAmountX, float maxStretchAmountY, float childRelativeLeft, float childRelativeTop, float childRelativeRight, float childRelativeBottom)3792         public Transaction setStretchEffect(SurfaceControl sc, float width, float height,
3793                 float vecX, float vecY, float maxStretchAmountX,
3794                 float maxStretchAmountY, float childRelativeLeft, float childRelativeTop, float childRelativeRight,
3795                 float childRelativeBottom) {
3796             checkPreconditions(sc);
3797             nativeSetStretchEffect(mNativeObject, sc.mNativeObject, width, height,
3798                     vecX, vecY, maxStretchAmountX, maxStretchAmountY, childRelativeLeft, childRelativeTop,
3799                     childRelativeRight, childRelativeBottom);
3800             return this;
3801         }
3802 
3803         /**
3804          * @hide
3805          */
setEdgeExtensionEffect(SurfaceControl sc, int edge)3806         public Transaction setEdgeExtensionEffect(SurfaceControl sc, int edge) {
3807             checkPreconditions(sc);
3808 
3809             nativeSetEdgeExtensionEffect(
3810                     mNativeObject, sc.mNativeObject,
3811                     (edge & WindowInsets.Side.LEFT) != 0, (edge & WindowInsets.Side.RIGHT) != 0,
3812                     (edge & WindowInsets.Side.TOP) != 0, (edge & WindowInsets.Side.BOTTOM) != 0);
3813             return this;
3814         }
3815 
3816         /**
3817          * Associates a layer with a display. The layer will be drawn on the display with the
3818          * specified layer stack. If the layer is not a root layer, this call has no effect.
3819          *
3820          * @hide
3821          */
3822         @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.O)
setLayerStack(SurfaceControl sc, int layerStack)3823         public Transaction setLayerStack(SurfaceControl sc, int layerStack) {
3824             checkPreconditions(sc);
3825             nativeSetLayerStack(mNativeObject, sc.mNativeObject, layerStack);
3826             return this;
3827         }
3828 
3829         /**
3830          * Re-parents a given layer to a new parent. Children inherit transform (position, scaling)
3831          * crop, visibility, and Z-ordering from their parents, as if the children were pixels within the
3832          * parent Surface.
3833          *
3834          * @param sc The SurfaceControl to reparent
3835          * @param newParent The new parent for the given control.
3836          * @return This Transaction
3837          */
3838         @NonNull
reparent(@onNull SurfaceControl sc, @Nullable SurfaceControl newParent)3839         public Transaction reparent(@NonNull SurfaceControl sc,
3840                 @Nullable SurfaceControl newParent) {
3841             checkPreconditions(sc);
3842             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
3843                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
3844                         "reparent", this, sc, "newParent=" + newParent);
3845             }
3846             long otherObject = 0;
3847             if (newParent != null) {
3848                 newParent.checkNotReleased();
3849                 otherObject = newParent.mNativeObject;
3850             }
3851             nativeReparent(mNativeObject, sc.mNativeObject, otherObject);
3852             mReparentedSurfaces.put(sc, newParent);
3853             return this;
3854         }
3855 
3856         /**
3857          * Fills the surface with the specified color.
3858          *
3859          * @param color A float array with three values to represent r, g, b in range [0..1]. An
3860          * invalid color will remove the color fill.
3861          * @hide
3862          */
3863         @UnsupportedAppUsage
setColor(SurfaceControl sc, @Size(3) float[] color)3864         public Transaction setColor(SurfaceControl sc, @Size(3) float[] color) {
3865             checkPreconditions(sc);
3866             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
3867                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
3868                         "setColor", this, sc,
3869                         "r=" + color[0] + " g=" + color[1] + " b=" + color[2]);
3870             }
3871             nativeSetColor(mNativeObject, sc.mNativeObject, color);
3872             return this;
3873         }
3874 
3875         /**
3876          * Removes color fill.
3877          *
3878          * @hide
3879          */
unsetColor(SurfaceControl sc)3880         public Transaction unsetColor(SurfaceControl sc) {
3881             checkPreconditions(sc);
3882             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
3883                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
3884                         "unsetColor", this, sc, null);
3885             }
3886             nativeSetColor(mNativeObject, sc.mNativeObject, INVALID_COLOR);
3887             return this;
3888         }
3889 
3890         /**
3891          * Sets the security of the surface.  Setting the flag is equivalent to creating the
3892          * Surface with the {@link #SECURE} flag.
3893          * @hide
3894          */
setSecure(SurfaceControl sc, boolean isSecure)3895         public Transaction setSecure(SurfaceControl sc, boolean isSecure) {
3896             checkPreconditions(sc);
3897             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
3898                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
3899                         "setSecure", this, sc, "secure=" + isSecure);
3900             }
3901             if (isSecure) {
3902                 nativeSetFlags(mNativeObject, sc.mNativeObject, SECURE, SECURE);
3903             } else {
3904                 nativeSetFlags(mNativeObject, sc.mNativeObject, 0, SECURE);
3905             }
3906             return this;
3907         }
3908 
3909         /**
3910          * Sets whether the surface should take advantage of display decoration optimizations.
3911          * @hide
3912          */
setDisplayDecoration(SurfaceControl sc, boolean displayDecoration)3913         public Transaction setDisplayDecoration(SurfaceControl sc, boolean displayDecoration) {
3914             checkPreconditions(sc);
3915             if (displayDecoration) {
3916                 nativeSetFlags(mNativeObject, sc.mNativeObject, DISPLAY_DECORATION,
3917                         DISPLAY_DECORATION);
3918             } else {
3919                 nativeSetFlags(mNativeObject, sc.mNativeObject, 0, DISPLAY_DECORATION);
3920             }
3921             return this;
3922         }
3923 
3924         /**
3925          * Indicates whether the surface must be considered opaque, even if its pixel format is
3926          * set to translucent. This can be useful if an application needs full RGBA 8888 support
3927          * for instance but will still draw every pixel opaque.
3928          * <p>
3929          * This flag only determines whether opacity will be sampled from the alpha channel.
3930          * Plane-alpha from calls to setAlpha() can still result in blended composition
3931          * regardless of the opaque setting.
3932          *
3933          * Combined effects are (assuming a buffer format with an alpha channel):
3934          * <ul>
3935          * <li>OPAQUE + alpha(1.0) == opaque composition
3936          * <li>OPAQUE + alpha(0.x) == blended composition
3937          * <li>OPAQUE + alpha(0.0) == no composition
3938          * <li>!OPAQUE + alpha(1.0) == blended composition
3939          * <li>!OPAQUE + alpha(0.x) == blended composition
3940          * <li>!OPAQUE + alpha(0.0) == no composition
3941          * </ul>
3942          * If the underlying buffer lacks an alpha channel, it is as if setOpaque(true)
3943          * were set automatically.
3944          *
3945          * @see Builder#setOpaque(boolean)
3946          *
3947          * @param sc The SurfaceControl to update
3948          * @param isOpaque true if the buffer's alpha should be ignored, false otherwise
3949          * @return this
3950          */
3951         @NonNull
setOpaque(@onNull SurfaceControl sc, boolean isOpaque)3952         public Transaction setOpaque(@NonNull SurfaceControl sc, boolean isOpaque) {
3953             checkPreconditions(sc);
3954             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
3955                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
3956                         "setOpaque", this, sc, "opaque=" + isOpaque);
3957             }
3958             if (isOpaque) {
3959                 nativeSetFlags(mNativeObject, sc.mNativeObject, SURFACE_OPAQUE, SURFACE_OPAQUE);
3960             } else {
3961                 nativeSetFlags(mNativeObject, sc.mNativeObject, 0, SURFACE_OPAQUE);
3962             }
3963             return this;
3964         }
3965 
3966         /**
3967          * Sets the surface to render contents of the display to.
3968          *
3969          * @hide
3970          */
setDisplaySurface(IBinder displayToken, Surface surface)3971         public Transaction setDisplaySurface(IBinder displayToken, Surface surface) {
3972             if (displayToken == null) {
3973                 throw new IllegalArgumentException("displayToken must not be null");
3974             }
3975 
3976             if (surface != null) {
3977                 synchronized (surface.mLock) {
3978                     nativeSetDisplaySurface(mNativeObject, displayToken, surface.mNativeObject);
3979                 }
3980             } else {
3981                 nativeSetDisplaySurface(mNativeObject, displayToken, 0);
3982             }
3983             return this;
3984         }
3985 
3986         /**
3987          * Sets the layer stack of the display.
3988          *
3989          * All layers with the same layer stack will be drawn on this display.
3990          * @hide
3991          */
setDisplayLayerStack(IBinder displayToken, int layerStack)3992         public Transaction setDisplayLayerStack(IBinder displayToken, int layerStack) {
3993             if (displayToken == null) {
3994                 throw new IllegalArgumentException("displayToken must not be null");
3995             }
3996             nativeSetDisplayLayerStack(mNativeObject, displayToken, layerStack);
3997             return this;
3998         }
3999 
4000         /**
4001          * @hide
4002          */
setDisplayFlags(IBinder displayToken, int flags)4003         public Transaction setDisplayFlags(IBinder displayToken, int flags) {
4004             if (displayToken == null) {
4005                 throw new IllegalArgumentException("displayToken must not be null");
4006             }
4007             nativeSetDisplayFlags(mNativeObject, displayToken, flags);
4008             return this;
4009         }
4010 
4011         /**
4012          * @hide
4013          */
setDisplayProjection(IBinder displayToken, int orientation, Rect layerStackRect, Rect displayRect)4014         public Transaction setDisplayProjection(IBinder displayToken,
4015                 int orientation, Rect layerStackRect, Rect displayRect) {
4016             if (displayToken == null) {
4017                 throw new IllegalArgumentException("displayToken must not be null");
4018             }
4019             if (layerStackRect == null) {
4020                 throw new IllegalArgumentException("layerStackRect must not be null");
4021             }
4022             if (displayRect == null) {
4023                 throw new IllegalArgumentException("displayRect must not be null");
4024             }
4025             nativeSetDisplayProjection(mNativeObject, displayToken, orientation,
4026                     layerStackRect.left, layerStackRect.top, layerStackRect.right, layerStackRect.bottom,
4027                     displayRect.left, displayRect.top, displayRect.right, displayRect.bottom);
4028             return this;
4029         }
4030 
4031         /**
4032          * @hide
4033          */
setDisplaySize(IBinder displayToken, int width, int height)4034         public Transaction setDisplaySize(IBinder displayToken, int width, int height) {
4035             if (displayToken == null) {
4036                 throw new IllegalArgumentException("displayToken must not be null");
4037             }
4038             if (width <= 0 || height <= 0) {
4039                 throw new IllegalArgumentException("width and height must be positive");
4040             }
4041 
4042             nativeSetDisplaySize(mNativeObject, displayToken, width, height);
4043             return this;
4044         }
4045 
4046         /** flag the transaction as an animation
4047          * @hide
4048          */
setAnimationTransaction()4049         public Transaction setAnimationTransaction() {
4050             nativeSetAnimationTransaction(mNativeObject);
4051             return this;
4052         }
4053 
4054          /**
4055           * Provides a hint to SurfaceFlinger to change its offset so that SurfaceFlinger wakes up
4056           * earlier to compose surfaces. The caller should use this as a hint to SurfaceFlinger
4057           * when the scene is complex enough to use GPU composition. The hint will remain active
4058           * until until the client calls {@link Transaction#setEarlyWakeupEnd}.
4059           *
4060           * @hide
4061           */
4062         @RequiresPermission(Manifest.permission.WAKEUP_SURFACE_FLINGER)
setEarlyWakeupStart()4063         public Transaction setEarlyWakeupStart() {
4064             nativeSetEarlyWakeupStart(mNativeObject);
4065             return this;
4066         }
4067 
4068         /**
4069          * Removes the early wake up hint set by {@link Transaction#setEarlyWakeupStart}.
4070          *
4071          * @hide
4072          */
4073         @RequiresPermission(Manifest.permission.WAKEUP_SURFACE_FLINGER)
setEarlyWakeupEnd()4074         public Transaction setEarlyWakeupEnd() {
4075             nativeSetEarlyWakeupEnd(mNativeObject);
4076             return this;
4077         }
4078 
4079         /**
4080          * @hide
4081          * @return The transaction's current id.
4082          *         The id changed every time the transaction is applied.
4083          */
getId()4084         public long getId() {
4085             return nativeGetTransactionId(mNativeObject);
4086         }
4087 
4088         /**
4089          * Sets an arbitrary piece of metadata on the surface. This is a helper for int data.
4090          * @hide
4091          */
setMetadata(SurfaceControl sc, int key, int data)4092         public Transaction setMetadata(SurfaceControl sc, int key, int data) {
4093             Parcel parcel = Parcel.obtain();
4094             parcel.writeInt(data);
4095             try {
4096                 setMetadata(sc, key, parcel);
4097             } finally {
4098                 parcel.recycle();
4099             }
4100             return this;
4101         }
4102 
4103         /**
4104          * Sets an arbitrary piece of metadata on the surface.
4105          * @hide
4106          */
setMetadata(SurfaceControl sc, int key, Parcel data)4107         public Transaction setMetadata(SurfaceControl sc, int key, Parcel data) {
4108             checkPreconditions(sc);
4109             nativeSetMetadata(mNativeObject, sc.mNativeObject, key, data);
4110             return this;
4111         }
4112 
4113          /**
4114           * Draws shadows of length {@code shadowRadius} around the surface {@link SurfaceControl}.
4115           * If the length is 0.0f then the shadows will not be drawn.
4116           *
4117           * Shadows are drawn around the screen bounds, these are the post transformed cropped
4118           * bounds. They can draw over their parent bounds and will be occluded by layers with a
4119           * higher z-order. The shadows will respect the surface's corner radius if the
4120           * rounded corner bounds (transformed source bounds) are within the screen bounds.
4121           *
4122           * A shadow will only be drawn on buffer and color layers. If the radius is applied on a
4123           * container layer, it will be passed down the hierarchy to be applied on buffer and color
4124           * layers but not its children. A scenario where this is useful is when SystemUI animates
4125           * a task by controlling a leash to it, can draw a shadow around the app surface by
4126           * setting a shadow on the leash. This is similar to how rounded corners are set.
4127           *
4128           * @hide
4129           */
setShadowRadius(SurfaceControl sc, float shadowRadius)4130         public Transaction setShadowRadius(SurfaceControl sc, float shadowRadius) {
4131             checkPreconditions(sc);
4132             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
4133                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
4134                         "setShadowRadius", this, sc, "radius=" + shadowRadius);
4135             }
4136             nativeSetShadowRadius(mNativeObject, sc.mNativeObject, shadowRadius);
4137             return this;
4138         }
4139 
4140         /**
4141          * Sets the outline settings on this SurfaceControl. If a shadow radius is set,
4142          * the outline will be drawn after the shadow and before any buffers.
4143          * The outline will be drawn on the border (outside) of the rounded rectangle
4144          * that is used for shadow casting. I.e. for an opaque layer,
4145          * the outline begins where shadow is visible.
4146          *
4147          * @hide
4148          */
setBorderSettings(SurfaceControl sc, @NonNull BorderSettings settings)4149         public Transaction setBorderSettings(SurfaceControl sc,
4150                 @NonNull BorderSettings settings) {
4151             checkPreconditions(sc);
4152             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
4153                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
4154                         "setBorderSettings", this, sc, "settings=" + settings);
4155             }
4156 
4157             if (!Flags.enableBorderSettings()) {
4158                 Log.w(TAG, "setBorderSettings was called but"
4159                             + "enable_border_settings flag is disabled");
4160                 return this;
4161             }
4162 
4163             Parcel settingsParcel = Parcel.obtain();
4164             settings.writeToParcel(settingsParcel, 0);
4165             settingsParcel.setDataPosition(0);
4166             nativeSetBorderSettings(mNativeObject, sc.mNativeObject, settingsParcel);
4167             return this;
4168         }
4169 
4170         /**
4171          * Sets the intended frame rate for this surface. Any switching of refresh rates is
4172          * most probably going to be seamless.
4173          *
4174          * @see #setFrameRate(SurfaceControl, float, int, int)
4175          */
4176         @NonNull
setFrameRate(@onNull SurfaceControl sc, @FloatRange(from = 0.0) float frameRate, @Surface.FrameRateCompatibility int compatibility)4177         public Transaction setFrameRate(@NonNull SurfaceControl sc,
4178                 @FloatRange(from = 0.0) float frameRate,
4179                 @Surface.FrameRateCompatibility int compatibility) {
4180             return setFrameRate(sc, frameRate, compatibility,
4181                     Surface.CHANGE_FRAME_RATE_ONLY_IF_SEAMLESS);
4182         }
4183 
4184         /**
4185          * Sets the intended frame rate for the surface {@link SurfaceControl}.
4186          * <p>
4187          * On devices that are capable of running the display at different refresh rates, the system
4188          * may choose a display refresh rate to better match this surface's frame rate. Usage of
4189          * this API won't directly affect the application's frame production pipeline. However,
4190          * because the system may change the display refresh rate, calls to this function may result
4191          * in changes to Choreographer callback timings, and changes to the time interval at which
4192          * the system releases buffers back to the application.
4193          * <p>
4194          * Note that this only has an effect for surfaces presented on the display. If this
4195          * surface is consumed by something other than the system compositor, e.g. a media
4196          * codec, this call has no effect.
4197          *
4198          * @param sc The SurfaceControl to specify the frame rate of.
4199          * @param frameRate The intended frame rate for this surface, in frames per second. 0 is a
4200          *                  special value that indicates the app will accept the system's choice for
4201          *                  the display frame rate, which is the default behavior if this function
4202          *                  isn't called. The <code>frameRate</code> param does <em>not</em> need
4203          *                  to be a valid refresh rate for this device's display - e.g., it's fine
4204          *                  to pass 30fps to a device that can only run the display at 60fps.
4205          * @param compatibility The frame rate compatibility of this surface. The compatibility
4206          *                      value may influence the system's choice of display frame rate.
4207          *                      This parameter is ignored when <code>frameRate</code> is 0.
4208          * @param changeFrameRateStrategy Whether display refresh rate transitions caused by this
4209          *                                surface should be seamless. A seamless transition is one
4210          *                                that doesn't have any visual interruptions, such as a
4211          *                                black screen for a second or two. This parameter is
4212          *                                ignored when <code>frameRate</code> is 0.
4213          * @return This transaction object.
4214          *
4215          * @see #clearFrameRate(SurfaceControl)
4216          */
4217         @NonNull
setFrameRate(@onNull SurfaceControl sc, @FloatRange(from = 0.0) float frameRate, @Surface.FrameRateCompatibility int compatibility, @Surface.ChangeFrameRateStrategy int changeFrameRateStrategy)4218         public Transaction setFrameRate(@NonNull SurfaceControl sc,
4219                 @FloatRange(from = 0.0) float frameRate,
4220                 @Surface.FrameRateCompatibility int compatibility,
4221                 @Surface.ChangeFrameRateStrategy int changeFrameRateStrategy) {
4222             checkPreconditions(sc);
4223             nativeSetFrameRate(mNativeObject, sc.mNativeObject, frameRate, compatibility,
4224                     changeFrameRateStrategy);
4225             return this;
4226         }
4227 
4228         /**
4229          * Sets the intended frame rate for the surface {@link SurfaceControl}.
4230          *
4231          * <p>On devices that are capable of running the display at different frame rates,
4232          * the system may choose a display refresh rate to better match this surface's frame
4233          * rate. Usage of this API won't introduce frame rate throttling, or affect other
4234          * aspects of the application's frame production pipeline. However, because the system
4235          * may change the display refresh rate, calls to this function may result in changes
4236          * to {@link Choreographer} callback timings, and changes to the time interval at which the
4237          * system releases buffers back to the application.</p>
4238          *
4239          * <p>Note that this only has an effect for surfaces presented on the display. If this
4240          * surface is consumed by something other than the system compositor, e.g. a media
4241          * codec, this call has no effect.</p>
4242          *
4243          * @param sc The SurfaceControl to specify the frame rate of.
4244          * @param frameRateParams The parameters describing the intended frame rate of this surface.
4245          *         Refer to {@link Surface.FrameRateParams} for details.
4246          * @return This transaction object.
4247          *
4248          * @see #clearFrameRate(SurfaceControl)
4249          */
4250         @NonNull
4251         @FlaggedApi(com.android.graphics.surfaceflinger.flags.Flags
4252                         .FLAG_ARR_SURFACECONTROL_SETFRAMERATE_API)
setFrameRate(@onNull SurfaceControl sc, @NonNull Surface.FrameRateParams frameRateParams)4253         public Transaction setFrameRate(@NonNull SurfaceControl sc,
4254                 @NonNull Surface.FrameRateParams frameRateParams) {
4255             checkPreconditions(sc);
4256 
4257             if (com.android.graphics.surfaceflinger.flags.Flags.arrSetframerateApi()) {
4258                 // TODO(b/362798998): Logic currently incomplete: it uses fixed source rate over the
4259                 // desired min/max rates. Fix when plumbing is upgraded.
4260                 int compatibility = frameRateParams.getFixedSourceRate() == 0
4261                         ? Surface.FRAME_RATE_COMPATIBILITY_DEFAULT
4262                         : Surface.FRAME_RATE_COMPATIBILITY_FIXED_SOURCE;
4263                 float frameRate = compatibility == Surface.FRAME_RATE_COMPATIBILITY_DEFAULT
4264                         ? frameRateParams.getDesiredMinRate()
4265                         : frameRateParams.getFixedSourceRate();
4266                 nativeSetFrameRate(mNativeObject, sc.mNativeObject, frameRate, compatibility,
4267                         frameRateParams.getChangeFrameRateStrategy());
4268             } else {
4269                 Log.w(TAG, "setFrameRate was called but flag arr_setframerate_api is disabled");
4270             }
4271             return this;
4272         }
4273 
4274         /**
4275          * Clears the frame rate which was set for the surface {@link SurfaceControl}.
4276          *
4277          * <p>This is equivalent to calling {@link #setFrameRate(SurfaceControl, float, int, int)}
4278          * using {@code 0} for {@code frameRate}.
4279          * <p>
4280          * Note that this only has an effect for surfaces presented on the display. If this
4281          * surface is consumed by something other than the system compositor, e.g. a media
4282          * codec, this call has no effect.
4283          *
4284          * @param sc The SurfaceControl to clear the frame rate of.
4285          * @return This transaction object.
4286          *
4287          * @see #setFrameRate(SurfaceControl, float, int)
4288          */
4289         @NonNull
clearFrameRate(@onNull SurfaceControl sc)4290         public Transaction clearFrameRate(@NonNull SurfaceControl sc) {
4291             checkPreconditions(sc);
4292             nativeSetFrameRate(mNativeObject, sc.mNativeObject, 0.0f,
4293                     Surface.FRAME_RATE_COMPATIBILITY_DEFAULT,
4294                     Surface.CHANGE_FRAME_RATE_ALWAYS);
4295             return this;
4296         }
4297 
4298         /**
4299          * Sets the default frame rate compatibility for the surface {@link SurfaceControl}
4300          *
4301          * @param sc The SurfaceControl to specify the frame rate of.
4302          * @param compatibility The frame rate compatibility of this surface. The compatibility
4303          *               value may influence the system's choice of display frame rate.
4304          *
4305          * @return This transaction object.
4306          *
4307          * @hide
4308          */
4309         @NonNull
setDefaultFrameRateCompatibility(@onNull SurfaceControl sc, @Surface.FrameRateCompatibility int compatibility)4310         public Transaction setDefaultFrameRateCompatibility(@NonNull SurfaceControl sc,
4311                 @Surface.FrameRateCompatibility int compatibility) {
4312             checkPreconditions(sc);
4313             nativeSetDefaultFrameRateCompatibility(mNativeObject, sc.mNativeObject, compatibility);
4314             return this;
4315         }
4316 
4317         /**
4318          * Sets the frame rate category for the {@link SurfaceControl}.
4319          *
4320          * This helps instruct the system on choosing a display refresh rate based on the surface's
4321          * chosen category, which is a device-specific range of frame rates.
4322          * {@link #setFrameRateCategory} should be used by components such as animations that do not
4323          * require an exact frame rate, but has an opinion on an approximate desirable frame rate.
4324          * The values of {@code category} gives example use cases for which category to choose.
4325          *
4326          * To instead specify an exact frame rate, use
4327          * {@link #setFrameRate(SurfaceControl, float, int, int)}, which is more suitable for
4328          * content that knows specifically which frame rate is optimal.
4329          * Although not a common use case, {@link #setFrameRateCategory} and {@link #setFrameRate}
4330          * can be called together, with both calls potentially influencing the display refresh rate.
4331          * For example, considering only one {@link SurfaceControl}: if {@link #setFrameRate}'s
4332          * value is 24 and {@link #setFrameRateCategory}'s value is
4333          * {@link Surface#FRAME_RATE_CATEGORY_HIGH}, defined to be the range [90,120] fps for an
4334          * example device, then the best refresh rate for the SurfaceControl should be 120 fps.
4335          * This is because 120 fps is a multiple of 24 fps, and 120 fps is in the specified
4336          * category's range.
4337          *
4338          * @param sc The SurfaceControl to specify the frame rate category of.
4339          * @param category The frame rate category of this surface. The category value may influence
4340          * the system's choice of display frame rate.
4341          * @param smoothSwitchOnly Set to {@code true} to indicate the display frame rate should not
4342          * change if changing it would cause jank. Else {@code false}.
4343          * This parameter is ignored when {@code category} is
4344          * {@link Surface#FRAME_RATE_CATEGORY_DEFAULT}.
4345          *
4346          * @return This transaction object.
4347          *
4348          * @see #setFrameRate(SurfaceControl, float, int, int)
4349          *
4350          * @hide
4351          */
4352         @NonNull
setFrameRateCategory(@onNull SurfaceControl sc, @Surface.FrameRateCategory int category, boolean smoothSwitchOnly)4353         public Transaction setFrameRateCategory(@NonNull SurfaceControl sc,
4354                 @Surface.FrameRateCategory int category, boolean smoothSwitchOnly) {
4355             checkPreconditions(sc);
4356             nativeSetFrameRateCategory(mNativeObject, sc.mNativeObject, category, smoothSwitchOnly);
4357             return this;
4358         }
4359 
4360         /**
4361          * Sets the frame rate selection strategy for the {@link SurfaceControl}.
4362          *
4363          * This instructs the system on how to choose a display refresh rate, following the
4364          * strategy for the layer's frame rate specifications relative to other layers'.
4365          *
4366          * @param sc The SurfaceControl to specify the frame rate category of.
4367          * @param strategy The frame rate selection strategy.
4368          *
4369          * @return This transaction object.
4370          *
4371          * @see #setFrameRate(SurfaceControl, float, int, int)
4372          * @see #setFrameRateCategory(SurfaceControl, int)
4373          * @see #setDefaultFrameRateCompatibility(SurfaceControl, int)
4374          *
4375          * @hide
4376          */
4377         @NonNull
setFrameRateSelectionStrategy( @onNull SurfaceControl sc, @FrameRateSelectionStrategy int strategy)4378         public Transaction setFrameRateSelectionStrategy(
4379                 @NonNull SurfaceControl sc, @FrameRateSelectionStrategy int strategy) {
4380             checkPreconditions(sc);
4381             nativeSetFrameRateSelectionStrategy(mNativeObject, sc.mNativeObject, strategy);
4382             return this;
4383         }
4384 
4385         /**
4386          * Sets focus on the window identified by the input {@code token} if the window is focusable
4387          * otherwise the request is dropped.
4388          *
4389          * If the window is not visible, the request will be queued until the window becomes
4390          * visible or the request is overrriden by another request. The currently focused window
4391          * will lose focus immediately. This is to send the newly focused window any focus
4392          * dispatched events that occur while it is completing its first draw.
4393          *
4394          * @hide
4395          */
setFocusedWindow(@onNull IBinder token, String windowName, int displayId)4396         public Transaction setFocusedWindow(@NonNull IBinder token, String windowName,
4397                 int displayId) {
4398             nativeSetFocusedWindow(mNativeObject, token, windowName, displayId);
4399             return this;
4400         }
4401 
4402         /**
4403          * Removes the input focus from the current window which is having the input focus. Should
4404          * only be called when the current focused app is not responding and the current focused
4405          * window is not beloged to the current focused app.
4406          * @hide
4407          */
removeCurrentInputFocus(int displayId)4408         public Transaction removeCurrentInputFocus(int displayId) {
4409             nativeRemoveCurrentInputFocus(mNativeObject, displayId);
4410             return this;
4411         }
4412 
4413         /**
4414          * Adds or removes the flag SKIP_SCREENSHOT of the surface.  Setting the flag is equivalent
4415          * to creating the Surface with the {@link #SKIP_SCREENSHOT} flag.
4416          *
4417          * @hide
4418          */
setSkipScreenshot(SurfaceControl sc, boolean skipScrenshot)4419         public Transaction setSkipScreenshot(SurfaceControl sc, boolean skipScrenshot) {
4420             checkPreconditions(sc);
4421             if (skipScrenshot) {
4422                 nativeSetFlags(mNativeObject, sc.mNativeObject, SKIP_SCREENSHOT, SKIP_SCREENSHOT);
4423             } else {
4424                 nativeSetFlags(mNativeObject, sc.mNativeObject, 0, SKIP_SCREENSHOT);
4425             }
4426             return this;
4427         }
4428 
4429         /**
4430          * Set a buffer for a SurfaceControl. This can only be used for SurfaceControls that were
4431          * created as type {@link #FX_SURFACE_BLAST}
4432          *
4433          * @hide
4434          * @deprecated Use {@link #setBuffer(SurfaceControl, HardwareBuffer)} instead
4435          */
4436         @Deprecated
setBuffer(SurfaceControl sc, GraphicBuffer buffer)4437         public Transaction setBuffer(SurfaceControl sc, GraphicBuffer buffer) {
4438             return setBuffer(sc, HardwareBuffer.createFromGraphicBuffer(buffer));
4439         }
4440 
4441         /**
4442          * Updates the HardwareBuffer displayed for the SurfaceControl.
4443          *
4444          * Note that the buffer must be allocated with {@link HardwareBuffer#USAGE_COMPOSER_OVERLAY}
4445          * as well as {@link HardwareBuffer#USAGE_GPU_SAMPLED_IMAGE} as the surface control might
4446          * be composited using either an overlay or using the GPU.
4447          *
4448          * @param sc The SurfaceControl to update
4449          * @param buffer The buffer to be displayed
4450          * @return this
4451          */
setBuffer(@onNull SurfaceControl sc, @Nullable HardwareBuffer buffer)4452         public @NonNull Transaction setBuffer(@NonNull SurfaceControl sc,
4453                 @Nullable HardwareBuffer buffer) {
4454             return setBuffer(sc, buffer, null);
4455         }
4456 
4457         /**
4458          * Unsets the buffer for the SurfaceControl in the current Transaction. This will not clear
4459          * the buffer being rendered, but resets the buffer state in the Transaction only. The call
4460          * will also invoke the release callback.
4461          *
4462          * Note, this call is different from passing a null buffer to
4463          * {@link SurfaceControl.Transaction#setBuffer} which will release the last displayed
4464          * buffer.
4465          *
4466          * @hide
4467          */
unsetBuffer(SurfaceControl sc)4468         public Transaction unsetBuffer(SurfaceControl sc) {
4469             nativeUnsetBuffer(mNativeObject, sc.mNativeObject);
4470             return this;
4471         }
4472 
4473         /**
4474          * Updates the HardwareBuffer displayed for the SurfaceControl.
4475          *
4476          * Note that the buffer must be allocated with {@link HardwareBuffer#USAGE_COMPOSER_OVERLAY}
4477          * as well as {@link HardwareBuffer#USAGE_GPU_SAMPLED_IMAGE} as the surface control might
4478          * be composited using either an overlay or using the GPU.
4479          *
4480          * A presentation fence may be passed to improve performance by allowing the buffer
4481          * to complete rendering while it is waiting for the transaction to be applied.
4482          * For example, if the buffer is being produced by rendering with OpenGL ES then
4483          * a fence created with
4484          * {@link android.opengl.EGLExt#eglDupNativeFenceFDANDROID(EGLDisplay, EGLSync)} can be
4485          * used to allow the GPU rendering to be concurrent with the transaction. The compositor
4486          * will wait for the fence to be signaled before the buffer is displayed. If multiple
4487          * buffers are set as part of the same transaction, the presentation fences of all of them
4488          * must signal before any buffer is displayed. That is, the entire transaction is delayed
4489          * until all presentation fences have signaled, ensuring the transaction remains consistent.
4490          *
4491          * @param sc The SurfaceControl to update
4492          * @param buffer The buffer to be displayed. Pass in a null buffer to release the last
4493          * displayed buffer.
4494          * @param fence The presentation fence. If null or invalid, this is equivalent to
4495          *              {@link #setBuffer(SurfaceControl, HardwareBuffer)}
4496          * @return this
4497          */
setBuffer(@onNull SurfaceControl sc, @Nullable HardwareBuffer buffer, @Nullable SyncFence fence)4498         public @NonNull Transaction setBuffer(@NonNull SurfaceControl sc,
4499                 @Nullable HardwareBuffer buffer, @Nullable SyncFence fence) {
4500             return setBuffer(sc, buffer, fence, null);
4501         }
4502 
4503         /**
4504          * Updates the HardwareBuffer displayed for the SurfaceControl.
4505          *
4506          * Note that the buffer must be allocated with {@link HardwareBuffer#USAGE_COMPOSER_OVERLAY}
4507          * as well as {@link HardwareBuffer#USAGE_GPU_SAMPLED_IMAGE} as the surface control might
4508          * be composited using either an overlay or using the GPU.
4509          *
4510          * A presentation fence may be passed to improve performance by allowing the buffer
4511          * to complete rendering while it is waiting for the transaction to be applied.
4512          * For example, if the buffer is being produced by rendering with OpenGL ES then
4513          * a fence created with
4514          * {@link android.opengl.EGLExt#eglDupNativeFenceFDANDROID(EGLDisplay, EGLSync)} can be
4515          * used to allow the GPU rendering to be concurrent with the transaction. The compositor
4516          * will wait for the fence to be signaled before the buffer is displayed. If multiple
4517          * buffers are set as part of the same transaction, the presentation fences of all of them
4518          * must signal before any buffer is displayed. That is, the entire transaction is delayed
4519          * until all presentation fences have signaled, ensuring the transaction remains consistent.
4520          *
4521          * A releaseCallback may be passed to know when the buffer is safe to be reused. This
4522          * is recommended when attempting to render continuously using SurfaceControl transactions
4523          * instead of through {@link Surface}, as it provides a safe & reliable way to know when
4524          * a buffer can be re-used. The callback will be invoked with a {@link SyncFence} which,
4525          * if {@link SyncFence#isValid() valid}, must be waited on prior to using the buffer. This
4526          * can either be done directly with {@link SyncFence#awaitForever()} or it may be done
4527          * indirectly such as passing it as a release fence to
4528          * {@link android.media.Image#setFence(SyncFence)} when using
4529          * {@link android.media.ImageReader}.
4530          *
4531          * @param sc The SurfaceControl to update
4532          * @param buffer The buffer to be displayed
4533          * @param fence The presentation fence. If null or invalid, this is equivalent to
4534          *              {@link #setBuffer(SurfaceControl, HardwareBuffer)}
4535          * @param releaseCallback The callback to invoke when the buffer being set has been released
4536          *                        by a later transaction. That is, the point at which it is safe
4537          *                        to re-use the buffer.
4538          * @return this
4539          */
setBuffer(@onNull SurfaceControl sc, @Nullable HardwareBuffer buffer, @Nullable SyncFence fence, @Nullable Consumer<SyncFence> releaseCallback)4540         public @NonNull Transaction setBuffer(@NonNull SurfaceControl sc,
4541                 @Nullable HardwareBuffer buffer, @Nullable SyncFence fence,
4542                 @Nullable Consumer<SyncFence> releaseCallback) {
4543             checkPreconditions(sc);
4544             if (fence != null) {
4545                 synchronized (fence.getLock()) {
4546                     nativeSetBuffer(mNativeObject, sc.mNativeObject, buffer,
4547                             fence.getNativeFence(), releaseCallback);
4548                 }
4549             } else {
4550                 nativeSetBuffer(mNativeObject, sc.mNativeObject, buffer, 0, releaseCallback);
4551             }
4552             return this;
4553         }
4554 
4555 
4556         /**
4557          * Sets the buffer transform that should be applied to the current buffer.
4558          *
4559          * This can be used in combination with
4560          * {@link AttachedSurfaceControl#addOnBufferTransformHintChangedListener(AttachedSurfaceControl.OnBufferTransformHintChangedListener)}
4561          * to pre-rotate the buffer for the current display orientation. This can
4562          * improve the performance of displaying the associated buffer.
4563          *
4564          * @param sc The SurfaceControl to update
4565          * @param transform The transform to apply to the buffer.
4566          * @return this
4567          */
setBufferTransform(@onNull SurfaceControl sc, @SurfaceControl.BufferTransform int transform)4568         public @NonNull Transaction setBufferTransform(@NonNull SurfaceControl sc,
4569                 @SurfaceControl.BufferTransform int transform) {
4570             checkPreconditions(sc);
4571             nativeSetBufferTransform(mNativeObject, sc.mNativeObject, transform);
4572             return this;
4573         }
4574 
4575         /**
4576          * Updates the region for the content on this surface updated in this transaction. The
4577          * damage region is the area of the buffer that has changed since the previously
4578          * sent buffer. This can be used to reduce the amount of recomposition that needs
4579          * to happen when only a small region of the buffer is being updated, such as for
4580          * a small blinking cursor or a loading indicator.
4581          *
4582          * @param sc The SurfaceControl on which to set the damage region
4583          * @param region The region to set. If null, the entire buffer is assumed dirty. This is
4584          *               equivalent to not setting a damage region at all.
4585          */
setDamageRegion(@onNull SurfaceControl sc, @Nullable Region region)4586         public @NonNull Transaction setDamageRegion(@NonNull SurfaceControl sc,
4587                 @Nullable Region region) {
4588             nativeSetDamageRegion(mNativeObject, sc.mNativeObject, region);
4589             return this;
4590         }
4591 
4592         /**
4593          * Set if the layer can be dimmed.
4594          *
4595          * <p>Dimming is to adjust brightness of the layer.
4596          * Default value is {@code true}, which means the layer can be dimmed.
4597          * Disabling dimming means the brightness of the layer can not be changed, i.e.,
4598          * keep the white point for the layer same as the display brightness.</p>
4599          *
4600          * @param sc The SurfaceControl on which to enable or disable dimming.
4601          * @param dimmingEnabled The dimming flag.
4602          * @return this.
4603          *
4604          * @hide
4605          */
setDimmingEnabled(@onNull SurfaceControl sc, boolean dimmingEnabled)4606         public @NonNull Transaction setDimmingEnabled(@NonNull SurfaceControl sc,
4607                 boolean dimmingEnabled) {
4608             checkPreconditions(sc);
4609             nativeSetDimmingEnabled(mNativeObject, sc.mNativeObject, dimmingEnabled);
4610             return this;
4611         }
4612 
4613         /**
4614          * Set the color space for the SurfaceControl. The supported color spaces are SRGB
4615          * and Display P3, other color spaces will be treated as SRGB. This can only be used for
4616          * SurfaceControls that were created as type {@link #FX_SURFACE_BLAST}
4617          *
4618          * @hide
4619          * @deprecated use {@link #setDataSpace(SurfaceControl, long)} instead
4620          */
4621         @Deprecated
setColorSpace(SurfaceControl sc, ColorSpace colorSpace)4622         public Transaction setColorSpace(SurfaceControl sc, ColorSpace colorSpace) {
4623             checkPreconditions(sc);
4624             if (colorSpace.getId() == ColorSpace.Named.DISPLAY_P3.ordinal()) {
4625                 setDataSpace(sc, DataSpace.DATASPACE_DISPLAY_P3);
4626             } else {
4627                 setDataSpace(sc, DataSpace.DATASPACE_SRGB);
4628             }
4629             return this;
4630         }
4631 
4632         /**
4633          * Set the dataspace for the SurfaceControl. This will control how the buffer
4634          * set with {@link #setBuffer(SurfaceControl, HardwareBuffer)} is displayed.
4635          *
4636          * @param sc The SurfaceControl to update
4637          * @param dataspace The dataspace to set it to
4638          * @return this
4639          */
setDataSpace(@onNull SurfaceControl sc, @DataSpace.NamedDataSpace int dataspace)4640         public @NonNull Transaction setDataSpace(@NonNull SurfaceControl sc,
4641                 @DataSpace.NamedDataSpace int dataspace) {
4642             checkPreconditions(sc);
4643             nativeSetDataSpace(mNativeObject, sc.mNativeObject, dataspace);
4644             return this;
4645         }
4646 
4647         /**
4648          * Sets the desired extended range brightness for the layer. This only applies for layers
4649          * whose dataspace has RANGE_EXTENDED.
4650          *
4651          * @param sc The layer whose extended range brightness is being specified
4652          * @param currentBufferRatio The current HDR/SDR ratio of the current buffer. For example
4653          *                           if the buffer was rendered with a target SDR whitepoint of
4654          *                           100 nits and a max display brightness of 200 nits, this should
4655          *                           be set to 2.0f.
4656          *
4657          *                           <p>Default value is 1.0f.
4658          *
4659          *                           <p>Transfer functions that encode their own brightness ranges,
4660          *                           such as HLG or PQ, should also set this to 1.0f and instead
4661          *                           communicate extended content brightness information via
4662          *                           metadata such as CTA861_3 or SMPTE2086.
4663          *
4664          *                           <p>Must be finite && >= 1.0f
4665          *
4666          * @param desiredRatio The desired HDR/SDR ratio. This can be used to communicate the max
4667          *                     desired brightness range. This is similar to the "max luminance"
4668          *                     value in other HDR metadata formats, but represented as a ratio of
4669          *                     the target SDR whitepoint to the max display brightness. The system
4670          *                     may not be able to, or may choose not to, deliver the
4671          *                     requested range.
4672          *
4673          *                     <p>While requesting a large desired ratio will result in the most
4674          *                     dynamic range, voluntarily reducing the requested range can help
4675          *                     improve battery life as well as can improve quality by ensuring
4676          *                     greater bit depth is allocated to the luminance range in use.
4677          *
4678          *                     <p>Default value is 1.0f and indicates that extended range brightness
4679          *                     is not being used, so the resulting SDR or HDR behavior will be
4680          *                     determined entirely by the dataspace being used (ie, typically SDR
4681          *                     however PQ or HLG transfer functions will still result in HDR)
4682          *
4683          *                     <p>Must be finite && >= 1.0f
4684          * @return this
4685          **/
setExtendedRangeBrightness(@onNull SurfaceControl sc, float currentBufferRatio, float desiredRatio)4686         public @NonNull Transaction setExtendedRangeBrightness(@NonNull SurfaceControl sc,
4687                 float currentBufferRatio, float desiredRatio) {
4688             checkPreconditions(sc);
4689             if (!Float.isFinite(currentBufferRatio) || currentBufferRatio < 1.0f) {
4690                 throw new IllegalArgumentException(
4691                         "currentBufferRatio must be finite && >= 1.0f; got " + currentBufferRatio);
4692             }
4693             if (!Float.isFinite(desiredRatio) || desiredRatio < 1.0f) {
4694                 throw new IllegalArgumentException(
4695                         "desiredRatio must be finite && >= 1.0f; got " + desiredRatio);
4696             }
4697             nativeSetExtendedRangeBrightness(mNativeObject, sc.mNativeObject, currentBufferRatio,
4698                     desiredRatio);
4699             return this;
4700         }
4701 
4702         /**
4703          * Sets the desired HDR headroom for the layer.
4704          *
4705          * <p>Prefer using this API over {@link #setExtendedRangeBrightness} for formats that
4706          *. conform to HDR video standards like HLG or HDR10 which do not communicate a HDR/SDR
4707          * ratio as part of generating the buffer.
4708          *
4709          * @param sc The layer whose desired HDR headroom is being specified
4710          *
4711          * @param desiredRatio The desired HDR/SDR ratio. This can be used to communicate the max
4712          *                     desired brightness range. This is similar to the "max luminance"
4713          *                     value in other HDR metadata formats, but represented as a ratio of
4714          *                     the target SDR whitepoint to the max display brightness. The system
4715          *                     may not be able to, or may choose not to, deliver the
4716          *                     requested range.
4717          *
4718          *                     <p>Default value is 0.0f and indicates that the system will choose
4719          *                     the best headroom for this surface control's content. Typically,
4720          *                     this means that HLG/PQ encoded content will be displayed with some
4721          *                     HDR headroom greater than 1.0.
4722          *
4723          *                     <p>When called after {@link #setExtendedRangeBrightness}, the
4724          *                     desiredHeadroom will override the desiredRatio provided by
4725          *                     {@link #setExtendedRangeBrightness}. Conversely, when called
4726          *                     before {@link #setExtendedRangeBrightness}, the desiredRatio provided
4727          *                     by {@link #setExtendedRangeBrightness} will override the
4728          *                     desiredHeadroom.
4729          *
4730          *                     <p>Must be finite && >= 1.0f or 0.0f.
4731          * @return this
4732          * @see #setExtendedRangeBrightness
4733          **/
4734         @FlaggedApi(com.android.graphics.hwui.flags.Flags.FLAG_LIMITED_HDR)
setDesiredHdrHeadroom(@onNull SurfaceControl sc, @FloatRange(from = 0.0f) float desiredRatio)4735         public @NonNull Transaction setDesiredHdrHeadroom(@NonNull SurfaceControl sc,
4736                 @FloatRange(from = 0.0f) float desiredRatio) {
4737             checkPreconditions(sc);
4738             if (!Float.isFinite(desiredRatio) || (desiredRatio != 0 && desiredRatio < 1.0f)) {
4739                 throw new IllegalArgumentException(
4740                         "desiredRatio must be finite && >= 1.0f or 0; got " + desiredRatio);
4741             }
4742             nativeSetDesiredHdrHeadroom(mNativeObject, sc.mNativeObject, desiredRatio);
4743             return this;
4744         }
4745 
4746         /**
4747          * Sets the Luts for the layer.
4748          *
4749          * <p> The function also allows to clear previously applied lut(s). To do this,
4750          * set the displayluts to be either {@code nullptr} or
4751          * an empty {@link android.hardware.DisplayLuts} instance.
4752          *
4753          * @param sc The SurfaceControl to update
4754          *
4755          * @param displayLuts The selected Lut(s)
4756          *
4757          * @return this
4758          * @see DisplayLuts
4759          */
4760         @FlaggedApi(android.hardware.flags.Flags.FLAG_LUTS_API)
setLuts(@onNull SurfaceControl sc, @Nullable DisplayLuts displayLuts)4761         public @NonNull Transaction setLuts(@NonNull SurfaceControl sc,
4762                 @Nullable DisplayLuts displayLuts) {
4763             checkPreconditions(sc);
4764             if (displayLuts != null && displayLuts.valid()) {
4765                 nativeSetLuts(mNativeObject, sc.mNativeObject, displayLuts.getLutBuffers(),
4766                         displayLuts.getOffsets(), displayLuts.getLutDimensions(),
4767                         displayLuts.getLutSizes(), displayLuts.getLutSamplingKeys());
4768             } else {
4769                 nativeSetLuts(mNativeObject, sc.mNativeObject, null, null, null, null, null);
4770             }
4771             return this;
4772         }
4773 
4774         /**
4775          * Sets the desired picture profile handle for a layer.
4776          * <p>
4777          * A handle, retrieved from {@link MediaQualityManager#getProfileHandles}, which
4778          * refers a set of parameters that are used to configure picture processing that is applied
4779          * to all subsequent buffers to enhance the quality of their contents (e.g. gamma, color
4780          * temperature, hue, saturation, etc.).
4781          * <p>
4782          * Setting a handle does not guarantee access to limited picture processing. The content
4783          * priority for the  as well as the prominance of app to the current user experience plays a
4784          * role in which layer(s) get access to the limited picture processing resources. A maximum
4785          * number of {@link MediaQualityManager.getMaxPictureProfiles} can be applied at any given
4786          * point in time.
4787          *
4788          * @param sc The SurfaceControl of the layer that should be updated
4789          * @param handle The picture profile handle which refers to the set of desired parameters
4790          *
4791          * @see MediaQualityManager#getMaxPictureProfiles
4792          * @see MediaQualityManager#getProfileHandles
4793          * @see MediaCodec.KEY_PICTURE_PROFILE
4794          * @see SurfaceControl.Transaction#setContentPriority
4795          *
4796          * @hide
4797          */
4798         @FlaggedApi(android.media.tv.flags.Flags.FLAG_APPLY_PICTURE_PROFILES)
4799         @SystemApi
setPictureProfileHandle(@onNull SurfaceControl sc, @NonNull PictureProfileHandle handle)4800         public @NonNull Transaction setPictureProfileHandle(@NonNull SurfaceControl sc,
4801                                                             @NonNull PictureProfileHandle handle) {
4802             checkPreconditions(sc);
4803 
4804             nativeSetPictureProfileId(mNativeObject, sc.mNativeObject, handle.getId());
4805             return this;
4806         }
4807 
4808         /**
4809          * Sets the importance the layer's contents has to the app's user experience.
4810          * <p>
4811          * When a two layers within the same app are competing for a limited rendering resource,
4812          * the layer with the highest priority will gets access to the resource.
4813          * <p>
4814          * Resources managed by this priority:
4815          * <ul>
4816          *     <li>Picture processing via {@link MediaCodec.KEY_PICTURE_PROFILE}</li>
4817          *     <li>Picture processing via {@link SurfaceControl.Transaction#setPictureProfileHandle}
4818          *     </li>
4819          * </ul>
4820          *
4821          * @param sc The SurfaceControl of the layer that should be updated
4822          * @param priority The priority this layer should have with respect to other layers in the
4823          *                 app. The default priority is zero.
4824          *
4825          * @see MediaQualityManager#getMaxPictureProfiles
4826          * @see MediaCodec.KEY_PICTURE_PROFILE
4827          * @see SurfaceControl.Transaction#setPictureProfileHandle
4828          */
4829         @FlaggedApi(android.media.tv.flags.Flags.FLAG_APPLY_PICTURE_PROFILES)
setContentPriority(@onNull SurfaceControl sc, int priority)4830         public @NonNull Transaction setContentPriority(@NonNull SurfaceControl sc,
4831                                                        int priority) {
4832             checkPreconditions(sc);
4833 
4834             nativeSetContentPriority(mNativeObject, sc.mNativeObject, priority);
4835             return this;
4836         }
4837 
4838         /**
4839          * Sets the caching hint for the layer. By default, the caching hint is
4840          * {@link CACHING_ENABLED}.
4841          *
4842          * @param sc The SurfaceControl to update
4843          * @param cachingHint The caching hint to apply to the SurfaceControl. The CachingHint is
4844          *                    not applied to any children of this SurfaceControl.
4845          * @return this
4846          * @hide
4847          */
setCachingHint( @onNull SurfaceControl sc, @CachingHint int cachingHint)4848         public @NonNull Transaction setCachingHint(
4849                 @NonNull SurfaceControl sc, @CachingHint int cachingHint) {
4850             checkPreconditions(sc);
4851             nativeSetCachingHint(mNativeObject, sc.mNativeObject, cachingHint);
4852             return this;
4853         }
4854 
4855         /**
4856          * @see Transaction#setTrustedOverlay(SurfaceControl, int)
4857          * @hide
4858          */
setTrustedOverlay(SurfaceControl sc, boolean isTrustedOverlay)4859         public Transaction setTrustedOverlay(SurfaceControl sc, boolean isTrustedOverlay) {
4860             return setTrustedOverlay(sc,
4861                     isTrustedOverlay ? TrustedOverlay.ENABLED : TrustedOverlay.UNSET);
4862         }
4863 
4864         /**
4865          * Trusted overlay state prevents SurfaceControl from being considered as obscuring for
4866          * input occlusion detection purposes. The caller must hold the
4867          * ACCESS_SURFACE_FLINGER permission. See {@code TrustedOverlay}.
4868          * <p>
4869          * Arguments:
4870          * {@code TrustedOverlay.UNSET} - The default value, SurfaceControl will inherit the state
4871          * from its parents. If the parent state is also {@code TrustedOverlay.UNSET}, the layer
4872          * will be considered as untrusted.
4873          * <p>
4874          * {@code TrustedOverlay.DISABLED} - Treats this SurfaceControl and all its children as an
4875          * untrusted overlay. This will override any state set by its parent SurfaceControl.
4876          * <p>
4877          * {@code TrustedOverlay.ENABLED} - Treats this SurfaceControl and all its children as a
4878          * trusted overlay unless the child SurfaceControl explicitly disables its trusted state
4879          * via {@code TrustedOverlay.DISABLED}.
4880          * <p>
4881          * @hide
4882          */
setTrustedOverlay(SurfaceControl sc, @TrustedOverlay int trustedOverlay)4883         public Transaction setTrustedOverlay(SurfaceControl sc,
4884                                              @TrustedOverlay int trustedOverlay) {
4885             checkPreconditions(sc);
4886             nativeSetTrustedOverlay(mNativeObject, sc.mNativeObject, trustedOverlay);
4887             return this;
4888         }
4889 
4890         /**
4891          * Sets the input event drop mode on this SurfaceControl and its children. The caller must
4892          * hold the ACCESS_SURFACE_FLINGER permission. See {@code InputEventDropMode}.
4893          * @hide
4894          */
setDropInputMode(SurfaceControl sc, @DropInputMode int mode)4895         public Transaction setDropInputMode(SurfaceControl sc, @DropInputMode int mode) {
4896             checkPreconditions(sc);
4897             nativeSetDropInputMode(mNativeObject, sc.mNativeObject, mode);
4898             return this;
4899         }
4900 
4901         /**
4902          * Sets a property on this SurfaceControl and all its children indicating that the visible
4903          * region of this SurfaceControl should be considered when computing TrustedPresentation
4904          * Thresholds.
4905          * <p>
4906          * API Guidance:
4907          * The goal of this API is to identify windows that can be used to occlude content on
4908          * another window. This includes windows controlled by the user or the system. If the window
4909          * is transient, like Toast or notification shade, the window should not set this flag since
4910          * the user or the app cannot use the window to occlude content in a persistent manner. All
4911          * apps should have this flag set.
4912          * <p>
4913          * The caller must hold the ACCESS_SURFACE_FLINGER permission.
4914          * @hide
4915          */
setCanOccludePresentation(SurfaceControl sc, boolean canOccludePresentation)4916         public Transaction setCanOccludePresentation(SurfaceControl sc,
4917                 boolean canOccludePresentation) {
4918             checkPreconditions(sc);
4919             final int value = (canOccludePresentation) ? CAN_OCCLUDE_PRESENTATION : 0;
4920             nativeSetFlags(mNativeObject, sc.mNativeObject, value, CAN_OCCLUDE_PRESENTATION);
4921             return this;
4922         }
4923 
4924         /**
4925          * Sends a flush jank data transaction for the given surface.
4926          * @hide
4927          */
sendSurfaceFlushJankData(SurfaceControl sc)4928         public static void sendSurfaceFlushJankData(SurfaceControl sc) {
4929             sc.checkNotReleased();
4930             nativeSurfaceFlushJankData(sc.mNativeObject);
4931         }
4932 
4933         /**
4934          * @hide
4935          */
sanitize(int pid, int uid)4936         public void sanitize(int pid, int uid) {
4937             nativeSanitize(mNativeObject, pid, uid);
4938         }
4939 
4940         /**
4941          * @hide
4942          */
setDestinationFrame(SurfaceControl sc, @NonNull Rect destinationFrame)4943         public Transaction setDestinationFrame(SurfaceControl sc, @NonNull Rect destinationFrame) {
4944             checkPreconditions(sc);
4945             nativeSetDestinationFrame(mNativeObject, sc.mNativeObject,
4946                     destinationFrame.left, destinationFrame.top, destinationFrame.right,
4947                     destinationFrame.bottom);
4948             return this;
4949         }
4950 
4951         /**
4952          * @hide
4953          */
setDestinationFrame(SurfaceControl sc, int width, int height)4954         public Transaction setDestinationFrame(SurfaceControl sc, int width, int height) {
4955             checkPreconditions(sc);
4956             nativeSetDestinationFrame(mNativeObject, sc.mNativeObject, 0, 0, width, height);
4957             return this;
4958         }
4959 
4960         /**
4961          * Merge the other transaction into this transaction, clearing the
4962          * other transaction as if it had been applied.
4963          *
4964          * @param other The transaction to merge in to this one.
4965          * @return This transaction.
4966          */
4967         @NonNull
merge(@onNull Transaction other)4968         public Transaction merge(@NonNull Transaction other) {
4969             if (this == other) {
4970                 return this;
4971             }
4972             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
4973                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
4974                         "merge", this, null, "otherTx=" + other.getId());
4975                 if (mCalls != null) {
4976                     if (other.mCalls != null) {
4977                         mCalls.addAll(other.mCalls);
4978                         other.mCalls.clear();
4979                     }
4980                 }
4981             }
4982             mResizedSurfaces.putAll(other.mResizedSurfaces);
4983             other.mResizedSurfaces.clear();
4984             mReparentedSurfaces.putAll(other.mReparentedSurfaces);
4985             other.mReparentedSurfaces.clear();
4986             nativeMergeTransaction(mNativeObject, other.mNativeObject);
4987             return this;
4988         }
4989 
4990         /**
4991          * This is called when BlastBufferQueue.mergeWithNextTransaction() is called from java, and
4992          * for the purposes of logging that path.
4993          */
onMergeWithNextTransaction(CharSequence windowName)4994         void onMergeWithNextTransaction(CharSequence windowName) {
4995             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
4996                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
4997                         "merge", this, null, "window=" + windowName);
4998                 if (mCalls != null) {
4999                     mCalls.clear();
5000                 }
5001                 nativeEnableDebugLogCallPoints(mNativeObject);
5002             }
5003         }
5004 
5005         /**
5006          * Equivalent to reparent with a null parent, in that it removes
5007          * the SurfaceControl from the scene, but it also releases
5008          * the local resources (by calling {@link SurfaceControl#release})
5009          * after this method returns, {@link SurfaceControl#isValid} will return
5010          * false for the argument.
5011          *
5012          * @param sc The surface to remove and release.
5013          * @return This transaction
5014          * @hide
5015          */
5016         @NonNull
remove(@onNull SurfaceControl sc)5017         public Transaction remove(@NonNull SurfaceControl sc) {
5018             reparent(sc, null);
5019             sc.release();
5020             return this;
5021         }
5022 
5023         /**
5024          * Sets the frame timeline to use in SurfaceFlinger.
5025          *
5026          * A frame timeline should be chosen based on the frame deadline the application
5027          * can meet when rendering the frame and the application's desired presentation time.
5028          * By setting a frame timeline, SurfaceFlinger tries to present the frame at the
5029          * corresponding expected presentation time.
5030          *
5031          * To receive frame timelines, a callback must be posted to Choreographer using
5032          * {@link Choreographer#postVsyncCallback} The vsyncId can then be extracted from the
5033          * {@link Choreographer.FrameTimeline#getVsyncId}.
5034          *
5035          * @param vsyncId The vsync ID received from Choreographer, setting the frame's
5036          *                presentation target to the corresponding expected presentation time
5037          *                and deadline from the frame to be rendered. A stale or invalid value
5038          *                will be ignored.
5039          *
5040          */
5041         @FlaggedApi(Flags.FLAG_SDK_DESIRED_PRESENT_TIME)
5042         @NonNull
setFrameTimeline(long vsyncId)5043         public Transaction setFrameTimeline(long vsyncId) {
5044             if (!Flags.sdkDesiredPresentTime()) {
5045                 Log.w(TAG, "addTransactionCompletedListener was called but flag is disabled");
5046                 return this;
5047             }
5048             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
5049                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
5050                         "setFrameTimeline", this, null, "vsyncId=" + vsyncId);
5051             }
5052             nativeSetFrameTimelineVsync(mNativeObject, vsyncId);
5053             return this;
5054         }
5055 
5056         /** @hide */
5057         @NonNull
setFrameTimelineVsync(long frameTimelineVsyncId)5058         public Transaction setFrameTimelineVsync(long frameTimelineVsyncId) {
5059             if (SurfaceControlRegistry.sCallStackDebuggingEnabled) {
5060                 SurfaceControlRegistry.getProcessInstance().checkCallStackDebugging(
5061                         "setFrameTimelineVsync", this, null, "frameTimelineVsyncId="
5062                                 + frameTimelineVsyncId);
5063             }
5064             nativeSetFrameTimelineVsync(mNativeObject, frameTimelineVsyncId);
5065             return this;
5066         }
5067 
5068         /**
5069          * Request to add a {@link TransactionCommittedListener}.
5070          *
5071          * The callback is invoked when transaction is applied and the updates are ready to be
5072          * presented. This callback does not mean buffers have been released! It simply means that
5073          * any new transactions applied will not overwrite the transaction for which we are
5074          * receiving a callback and instead will be included in the next frame. If you are trying
5075          * to avoid dropping frames (overwriting transactions), and unable to use timestamps (Which
5076          * provide a more efficient solution), then this method provides a method to pace your
5077          * transaction application.
5078          * The listener is invoked once the transaction is applied, and never again. Multiple
5079          * listeners can be added to the same transaction, however the order the listeners will
5080          * be called is not guaranteed.
5081          *
5082          * @param executor The executor that the callback should be invoked on.
5083          * @param listener The callback that will be invoked when the transaction has been
5084          *                 committed.
5085          */
5086         @NonNull
addTransactionCommittedListener( @onNull @allbackExecutor Executor executor, @NonNull TransactionCommittedListener listener)5087         public Transaction addTransactionCommittedListener(
5088                 @NonNull @CallbackExecutor Executor executor,
5089                 @NonNull TransactionCommittedListener listener) {
5090             TransactionCommittedListener listenerInner =
5091                     () -> executor.execute(listener::onTransactionCommitted);
5092             nativeAddTransactionCommittedListener(mNativeObject, listenerInner);
5093             return this;
5094         }
5095 
5096         /**
5097          * Request to add a TransactionCompletedListener.
5098          *
5099          * The listener is invoked when transaction is presented, and never again. Multiple
5100          * listeners can be added to the same transaction, however the order the listeners will
5101          * be called is not guaranteed.
5102          *
5103          * @param executor The executor that the callback should be invoked on.
5104          * @param listener The callback that will be invoked when the transaction has been
5105          *                 completed.
5106          */
5107         @FlaggedApi(Flags.FLAG_SDK_DESIRED_PRESENT_TIME)
5108         @NonNull
addTransactionCompletedListener( @onNull @allbackExecutor Executor executor, @NonNull Consumer<TransactionStats> listener)5109         public Transaction addTransactionCompletedListener(
5110                 @NonNull @CallbackExecutor Executor executor,
5111                 @NonNull Consumer<TransactionStats> listener) {
5112 
5113             if (!Flags.sdkDesiredPresentTime()) {
5114                 Log.w(TAG, "addTransactionCompletedListener was called but flag is disabled");
5115                 return this;
5116             }
5117             Consumer<TransactionStats> listenerInner = stats -> executor.execute(
5118                                     () -> listener.andThen(TransactionStats::close).accept(stats));
5119             nativeAddTransactionCompletedListener(mNativeObject, listenerInner);
5120             return this;
5121         }
5122 
5123         /**
5124          * Sets a callback to receive feedback about the presentation of a {@link SurfaceControl}.
5125          * When the {@link SurfaceControl} is presented according to the passed in
5126          * {@link TrustedPresentationThresholds}, it is said to "enter the state", and receives the
5127          * callback with {@code true}. When the conditions fall out of thresholds, it is then
5128          * said to leave the state.
5129          * <p>
5130          * There are a few simple thresholds:
5131          * <ul>
5132          *    <li>minAlpha: Lower bound on computed alpha</li>
5133          *    <li>minFractionRendered: Lower bounds on fraction of pixels that were rendered</li>
5134          *    <li>stabilityThresholdMs: A time that alpha and fraction rendered must remain within
5135          *    bounds before we can "enter the state" </li>
5136          * </ul>
5137          * <p>
5138          * The fraction of pixels rendered is a computation based on scale, crop
5139          * and occlusion. The calculation may be somewhat counterintuitive, so we
5140          * can work through an example. Imagine we have a SurfaceControl with a 100x100 buffer
5141          * which is occluded by (10x100) pixels on the left, and cropped by (100x10) pixels
5142          * on the top. Furthermore imagine this SurfaceControl is scaled by 0.9 in both dimensions.
5143          * (c=crop,o=occluded,b=both,x=none)
5144          *
5145          * <blockquote>
5146          * <table>
5147          *   <caption></caption>
5148          *   <tr><td>b</td><td>c</td><td>c</td><td>c</td></tr>
5149          *   <tr><td>o</td><td>x</td><td>x</td><td>x</td></tr>
5150          *   <tr><td>o</td><td>x</td><td>x</td><td>x</td></tr>
5151          *   <tr><td>o</td><td>x</td><td>x</td><td>x</td></tr>
5152          * </table>
5153          * </blockquote>
5154          * <p>
5155          * We first start by computing fr=xscale*yscale=0.9*0.9=0.81, indicating
5156          * that "81%" of the pixels were rendered. This corresponds to what was 100
5157          * pixels being displayed in 81 pixels. This is somewhat of an abuse of
5158          * language, as the information of merged pixels isn't totally lost, but
5159          * we err on the conservative side.
5160          * <p>
5161          * We then repeat a similar process for the crop and covered regions and
5162          * accumulate the results: fr = fr * (fractionNotCropped) * (fractionNotCovered)
5163          * So for this example we would get 0.9*0.9*0.9*0.9=0.65...
5164          * <p>
5165          * Notice that this is not completely accurate, as we have double counted
5166          * the region marked as b. However we only wanted a "lower bound" and so it
5167          * is ok to err in this direction. Selection of the threshold will ultimately
5168          * be somewhat arbitrary, and so there are some somewhat arbitrary decisions in
5169          * this API as well.
5170          * <p>
5171          *
5172          * @param sc         The {@link SurfaceControl} to set the callback on
5173          * @param thresholds The {@link TrustedPresentationThresholds} that will specify when the to
5174          *                   invoke the callback.
5175          * @param executor   The {@link Executor} where the callback will be invoked on.
5176          * @param listener   The {@link Consumer} that will receive the callbacks when entered or
5177          *                   exited the threshold.
5178          * @return This transaction
5179          * @see TrustedPresentationThresholds
5180          * @deprecated Use
5181          * {@link WindowManager#registerTrustedPresentationListener(IBinder,
5182          * android.window.TrustedPresentationThresholds, Executor, Consumer)} instead.
5183          */
5184         @Deprecated
5185         @NonNull
setTrustedPresentationCallback(@onNull SurfaceControl sc, @NonNull TrustedPresentationThresholds thresholds, @NonNull Executor executor, @NonNull Consumer<Boolean> listener)5186         public Transaction setTrustedPresentationCallback(@NonNull SurfaceControl sc,
5187                 @NonNull TrustedPresentationThresholds thresholds, @NonNull Executor executor,
5188                 @NonNull Consumer<Boolean> listener) {
5189             checkPreconditions(sc);
5190             TrustedPresentationCallback tpc = new TrustedPresentationCallback() {
5191                 @Override
5192                 public void onTrustedPresentationChanged(boolean inTrustedPresentationState) {
5193                     executor.execute(
5194                             () -> listener.accept(inTrustedPresentationState));
5195                 }
5196             };
5197 
5198             if (sc.mTrustedPresentationCallback != null) {
5199                 sc.mTrustedPresentationCallback.mFreeNativeResources.run();
5200             }
5201 
5202             nativeSetTrustedPresentationCallback(mNativeObject, sc.mNativeObject,
5203                     tpc.mNativeObject, thresholds);
5204             sc.mTrustedPresentationCallback = tpc;
5205             return this;
5206         }
5207 
5208         /**
5209          * Clears the callback for a specific {@link SurfaceControl}
5210          *
5211          * @param sc The SurfaceControl that the callback should be cleared from
5212          * @return This transaction
5213          * @deprecated Use {@link WindowManager#unregisterTrustedPresentationListener(Consumer)}
5214          * instead.
5215          */
5216         @Deprecated
5217         @NonNull
clearTrustedPresentationCallback(@onNull SurfaceControl sc)5218         public Transaction clearTrustedPresentationCallback(@NonNull SurfaceControl sc) {
5219             checkPreconditions(sc);
5220             nativeClearTrustedPresentationCallback(mNativeObject, sc.mNativeObject);
5221             if (sc.mTrustedPresentationCallback != null) {
5222                 sc.mTrustedPresentationCallback.mFreeNativeResources.run();
5223                 sc.mTrustedPresentationCallback = null;
5224             }
5225             return this;
5226         }
5227 
5228         /**
5229          * Specifies a desiredPresentTimeNanos for the transaction. The framework will try to
5230          * present the transaction at or after the time specified.
5231          *
5232          * Transactions will not be presented until all of their acquire fences have signaled even
5233          * if the app requests an earlier present time.
5234          *
5235          * If an earlier transaction has a desired present time of x, and a later transaction has
5236          * a desired present time that is before x, the later transaction will not preempt the
5237          * earlier transaction.
5238          *
5239          * @param desiredPresentTimeNanos The desired time (in CLOCK_MONOTONIC) for the transaction.
5240          * @return This transaction
5241          */
5242         @FlaggedApi(Flags.FLAG_SDK_DESIRED_PRESENT_TIME)
5243         @NonNull
setDesiredPresentTimeNanos(long desiredPresentTimeNanos)5244         public Transaction setDesiredPresentTimeNanos(long desiredPresentTimeNanos) {
5245             if (!Flags.sdkDesiredPresentTime()) {
5246                 Log.w(TAG, "addTransactionCompletedListener was called but flag is disabled");
5247                 return this;
5248             }
5249             nativeSetDesiredPresentTimeNanos(mNativeObject, desiredPresentTimeNanos);
5250             return this;
5251         }
5252 
5253         /**
5254          * Specifies that the SurfaceControl is a buffer producer that should recover from buffer
5255          * stuffing, meaning that the SurfaceControl is a ViewRootImpl.
5256          *
5257          * @hide
5258          */
5259         @NonNull
setRecoverableFromBufferStuffing(@onNull SurfaceControl sc)5260         public Transaction setRecoverableFromBufferStuffing(@NonNull SurfaceControl sc) {
5261             checkPreconditions(sc);
5262             nativeSetFlags(mNativeObject, sc.mNativeObject, RECOVERABLE_FROM_BUFFER_STUFFING,
5263                     RECOVERABLE_FROM_BUFFER_STUFFING);
5264             return this;
5265         }
5266 
5267         /**
5268          * Writes the transaction to parcel, clearing the transaction as if it had been applied so
5269          * it can be used to store future transactions. It's the responsibility of the parcel
5270          * reader to apply the original transaction.
5271          *
5272          * @param dest parcel to write the transaction to
5273          * @param flags
5274          */
5275         @Override
writeToParcel(@onNull Parcel dest, @WriteFlags int flags)5276         public void writeToParcel(@NonNull Parcel dest, @WriteFlags int flags) {
5277             if (mNativeObject == 0) {
5278                 dest.writeInt(0);
5279                 return;
5280             }
5281 
5282             dest.writeInt(1);
5283             nativeWriteTransactionToParcel(mNativeObject, dest);
5284             if ((flags & Parcelable.PARCELABLE_WRITE_RETURN_VALUE) != 0) {
5285                 nativeClearTransaction(mNativeObject);
5286             }
5287         }
5288 
readFromParcel(Parcel in)5289         private void readFromParcel(Parcel in) {
5290             mNativeObject = 0;
5291             if (in.readInt() != 0) {
5292                 mNativeObject = nativeReadTransactionFromParcel(in);
5293                 mFreeNativeResources = sRegistry.registerNativeAllocation(this, mNativeObject);
5294             }
5295         }
5296 
5297         @Override
describeContents()5298         public int describeContents() {
5299             return 0;
5300         }
5301 
5302         public static final @NonNull Creator<Transaction> CREATOR = new Creator<Transaction>() {
5303                     @Override
5304                     public Transaction createFromParcel(Parcel in) {
5305                         return new Transaction(in);
5306                     }
5307                     @Override
5308                     public Transaction[] newArray(int size) {
5309                         return new Transaction[size];
5310                     }
5311                 };
5312     }
5313 
5314     /**
5315      * A debugging utility subclass of SurfaceControl.Transaction. At construction
5316      * you can pass in a monitor object, and all the other methods will throw an exception
5317      * if the monitor is not held when they are called.
5318      * @hide
5319      */
5320     public static class LockDebuggingTransaction extends SurfaceControl.Transaction {
5321         Object mMonitor;
5322 
LockDebuggingTransaction(Object o)5323         public LockDebuggingTransaction(Object o) {
5324             mMonitor = o;
5325         }
5326 
5327         @Override
checkPreconditions(SurfaceControl sc)5328         protected void checkPreconditions(SurfaceControl sc) {
5329             super.checkPreconditions(sc);
5330             if (!Thread.holdsLock(mMonitor)) {
5331                 throw new RuntimeException(
5332                         "Unlocked access to synchronized SurfaceControl.Transaction");
5333             }
5334         }
5335     }
5336 
5337     /**
5338      * @hide
5339      */
resize(int w, int h)5340     public void resize(int w, int h) {
5341         mWidth = w;
5342         mHeight = h;
5343         nativeUpdateDefaultBufferSize(mNativeObject, w, h);
5344     }
5345 
5346     /**
5347      * @hide
5348      */
getTransformHint()5349     public @SurfaceControl.BufferTransform int getTransformHint() {
5350         checkNotReleased();
5351         return nativeGetTransformHint(mNativeObject);
5352     }
5353 
5354     /**
5355      * Update the transform hint of current SurfaceControl. Only affect if type is
5356      * {@link #FX_SURFACE_BLAST}
5357      *
5358      * The transform hint is used to prevent allocating a buffer of different size when a
5359      * layer is rotated. The producer can choose to consume the hint and allocate the buffer
5360      * with the same size.
5361      * @hide
5362      */
setTransformHint(@urfaceControl.BufferTransform int transformHint)5363     public void setTransformHint(@SurfaceControl.BufferTransform int transformHint) {
5364         nativeSetTransformHint(mNativeObject, transformHint);
5365     }
5366 
5367     /**
5368      * @hide
5369      */
getLayerId()5370     public int getLayerId() {
5371         if (mNativeObject != 0) {
5372             return nativeGetLayerId(mNativeObject);
5373         }
5374 
5375         return -1;
5376     }
5377 
5378     // Called by native
invokeReleaseCallback(Consumer<SyncFence> callback, long nativeFencePtr)5379     private static void invokeReleaseCallback(Consumer<SyncFence> callback, long nativeFencePtr) {
5380         SyncFence fence = new SyncFence(nativeFencePtr);
5381         callback.accept(fence);
5382     }
5383 
5384     /**
5385      * @hide
5386      */
getStalledTransactionInfo(int pid)5387     public static StalledTransactionInfo getStalledTransactionInfo(int pid) {
5388         return nativeGetStalledTransactionInfo(pid);
5389     }
5390 
5391     /**
5392      * Notify the SurfaceFlinger to capture transaction traces when shutdown.
5393      * @hide
5394      */
notifyShutdown()5395     public static void notifyShutdown() {
5396         nativeNotifyShutdown();
5397     }
5398 }
5399