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.view.WindowManager.LayoutParams.INVALID_WINDOW_TYPE; 20 21 import android.graphics.Bitmap; 22 import android.graphics.GraphicBuffer; 23 import android.graphics.Rect; 24 import android.graphics.Region; 25 import android.os.Binder; 26 import android.os.IBinder; 27 import android.util.Log; 28 import android.view.Surface.OutOfResourcesException; 29 30 import dalvik.system.CloseGuard; 31 32 /** 33 * SurfaceControl 34 * @hide 35 */ 36 public class SurfaceControl { 37 private static final String TAG = "SurfaceControl"; 38 nativeCreate(SurfaceSession session, String name, int w, int h, int format, int flags, long parentObject, int windowType, int ownerUid)39 private static native long nativeCreate(SurfaceSession session, String name, 40 int w, int h, int format, int flags, long parentObject, int windowType, int ownerUid) 41 throws OutOfResourcesException; nativeRelease(long nativeObject)42 private static native void nativeRelease(long nativeObject); nativeDestroy(long nativeObject)43 private static native void nativeDestroy(long nativeObject); nativeDisconnect(long nativeObject)44 private static native void nativeDisconnect(long nativeObject); 45 nativeScreenshot(IBinder displayToken, Rect sourceCrop, int width, int height, int minLayer, int maxLayer, boolean allLayers, boolean useIdentityTransform, int rotation)46 private static native Bitmap nativeScreenshot(IBinder displayToken, 47 Rect sourceCrop, int width, int height, int minLayer, int maxLayer, 48 boolean allLayers, boolean useIdentityTransform, int rotation); nativeScreenshotToBuffer(IBinder displayToken, Rect sourceCrop, int width, int height, int minLayer, int maxLayer, boolean allLayers, boolean useIdentityTransform, int rotation)49 private static native GraphicBuffer nativeScreenshotToBuffer(IBinder displayToken, 50 Rect sourceCrop, int width, int height, int minLayer, int maxLayer, 51 boolean allLayers, boolean useIdentityTransform, int rotation); nativeScreenshot(IBinder displayToken, Surface consumer, Rect sourceCrop, int width, int height, int minLayer, int maxLayer, boolean allLayers, boolean useIdentityTransform)52 private static native void nativeScreenshot(IBinder displayToken, Surface consumer, 53 Rect sourceCrop, int width, int height, int minLayer, int maxLayer, 54 boolean allLayers, boolean useIdentityTransform); 55 nativeOpenTransaction()56 private static native void nativeOpenTransaction(); nativeCloseTransaction(boolean sync)57 private static native void nativeCloseTransaction(boolean sync); nativeSetAnimationTransaction()58 private static native void nativeSetAnimationTransaction(); 59 nativeSetLayer(long nativeObject, int zorder)60 private static native void nativeSetLayer(long nativeObject, int zorder); nativeSetRelativeLayer(long nativeObject, IBinder relativeTo, int zorder)61 private static native void nativeSetRelativeLayer(long nativeObject, IBinder relativeTo, 62 int zorder); nativeSetPosition(long nativeObject, float x, float y)63 private static native void nativeSetPosition(long nativeObject, float x, float y); nativeSetGeometryAppliesWithResize(long nativeObject)64 private static native void nativeSetGeometryAppliesWithResize(long nativeObject); nativeSetSize(long nativeObject, int w, int h)65 private static native void nativeSetSize(long nativeObject, int w, int h); nativeSetTransparentRegionHint(long nativeObject, Region region)66 private static native void nativeSetTransparentRegionHint(long nativeObject, Region region); nativeSetAlpha(long nativeObject, float alpha)67 private static native void nativeSetAlpha(long nativeObject, float alpha); nativeSetMatrix(long nativeObject, float dsdx, float dtdx, float dsdy, float dtdy)68 private static native void nativeSetMatrix(long nativeObject, float dsdx, float dtdx, float dsdy, float dtdy); nativeSetFlags(long nativeObject, int flags, int mask)69 private static native void nativeSetFlags(long nativeObject, int flags, int mask); nativeSetWindowCrop(long nativeObject, int l, int t, int r, int b)70 private static native void nativeSetWindowCrop(long nativeObject, int l, int t, int r, int b); nativeSetFinalCrop(long nativeObject, int l, int t, int r, int b)71 private static native void nativeSetFinalCrop(long nativeObject, int l, int t, int r, int b); nativeSetLayerStack(long nativeObject, int layerStack)72 private static native void nativeSetLayerStack(long nativeObject, int layerStack); 73 nativeClearContentFrameStats(long nativeObject)74 private static native boolean nativeClearContentFrameStats(long nativeObject); nativeGetContentFrameStats(long nativeObject, WindowContentFrameStats outStats)75 private static native boolean nativeGetContentFrameStats(long nativeObject, WindowContentFrameStats outStats); nativeClearAnimationFrameStats()76 private static native boolean nativeClearAnimationFrameStats(); nativeGetAnimationFrameStats(WindowAnimationFrameStats outStats)77 private static native boolean nativeGetAnimationFrameStats(WindowAnimationFrameStats outStats); 78 nativeGetBuiltInDisplay(int physicalDisplayId)79 private static native IBinder nativeGetBuiltInDisplay(int physicalDisplayId); nativeCreateDisplay(String name, boolean secure)80 private static native IBinder nativeCreateDisplay(String name, boolean secure); nativeDestroyDisplay(IBinder displayToken)81 private static native void nativeDestroyDisplay(IBinder displayToken); nativeSetDisplaySurface( IBinder displayToken, long nativeSurfaceObject)82 private static native void nativeSetDisplaySurface( 83 IBinder displayToken, long nativeSurfaceObject); nativeSetDisplayLayerStack( IBinder displayToken, int layerStack)84 private static native void nativeSetDisplayLayerStack( 85 IBinder displayToken, int layerStack); nativeSetDisplayProjection( IBinder displayToken, int orientation, int l, int t, int r, int b, int L, int T, int R, int B)86 private static native void nativeSetDisplayProjection( 87 IBinder displayToken, int orientation, 88 int l, int t, int r, int b, 89 int L, int T, int R, int B); nativeSetDisplaySize(IBinder displayToken, int width, int height)90 private static native void nativeSetDisplaySize(IBinder displayToken, int width, int height); nativeGetDisplayConfigs( IBinder displayToken)91 private static native SurfaceControl.PhysicalDisplayInfo[] nativeGetDisplayConfigs( 92 IBinder displayToken); nativeGetActiveConfig(IBinder displayToken)93 private static native int nativeGetActiveConfig(IBinder displayToken); nativeSetActiveConfig(IBinder displayToken, int id)94 private static native boolean nativeSetActiveConfig(IBinder displayToken, int id); nativeGetDisplayColorModes(IBinder displayToken)95 private static native int[] nativeGetDisplayColorModes(IBinder displayToken); nativeGetActiveColorMode(IBinder displayToken)96 private static native int nativeGetActiveColorMode(IBinder displayToken); nativeSetActiveColorMode(IBinder displayToken, int colorMode)97 private static native boolean nativeSetActiveColorMode(IBinder displayToken, 98 int colorMode); nativeSetDisplayPowerMode( IBinder displayToken, int mode)99 private static native void nativeSetDisplayPowerMode( 100 IBinder displayToken, int mode); nativeDeferTransactionUntil(long nativeObject, IBinder handle, long frame)101 private static native void nativeDeferTransactionUntil(long nativeObject, 102 IBinder handle, long frame); nativeDeferTransactionUntilSurface(long nativeObject, long surfaceObject, long frame)103 private static native void nativeDeferTransactionUntilSurface(long nativeObject, 104 long surfaceObject, long frame); nativeReparentChildren(long nativeObject, IBinder handle)105 private static native void nativeReparentChildren(long nativeObject, 106 IBinder handle); nativeSeverChildren(long nativeObject)107 private static native void nativeSeverChildren(long nativeObject); nativeSetOverrideScalingMode(long nativeObject, int scalingMode)108 private static native void nativeSetOverrideScalingMode(long nativeObject, 109 int scalingMode); nativeGetHandle(long nativeObject)110 private static native IBinder nativeGetHandle(long nativeObject); nativeGetTransformToDisplayInverse(long nativeObject)111 private static native boolean nativeGetTransformToDisplayInverse(long nativeObject); 112 nativeGetHdrCapabilities(IBinder displayToken)113 private static native Display.HdrCapabilities nativeGetHdrCapabilities(IBinder displayToken); 114 115 116 private final CloseGuard mCloseGuard = CloseGuard.get(); 117 private final String mName; 118 long mNativeObject; // package visibility only for Surface.java access 119 120 /* flags used in constructor (keep in sync with ISurfaceComposerClient.h) */ 121 122 /** 123 * Surface creation flag: Surface is created hidden 124 */ 125 public static final int HIDDEN = 0x00000004; 126 127 /** 128 * Surface creation flag: The surface contains secure content, special 129 * measures will be taken to disallow the surface's content to be copied 130 * from another process. In particular, screenshots and VNC servers will 131 * be disabled, but other measures can take place, for instance the 132 * surface might not be hardware accelerated. 133 * 134 */ 135 public static final int SECURE = 0x00000080; 136 137 /** 138 * Surface creation flag: Creates a surface where color components are interpreted 139 * as "non pre-multiplied" by their alpha channel. Of course this flag is 140 * meaningless for surfaces without an alpha channel. By default 141 * surfaces are pre-multiplied, which means that each color component is 142 * already multiplied by its alpha value. In this case the blending 143 * equation used is: 144 * <p> 145 * <code>DEST = SRC + DEST * (1-SRC_ALPHA)</code> 146 * <p> 147 * By contrast, non pre-multiplied surfaces use the following equation: 148 * <p> 149 * <code>DEST = SRC * SRC_ALPHA * DEST * (1-SRC_ALPHA)</code> 150 * <p> 151 * pre-multiplied surfaces must always be used if transparent pixels are 152 * composited on top of each-other into the surface. A pre-multiplied 153 * surface can never lower the value of the alpha component of a given 154 * pixel. 155 * <p> 156 * In some rare situations, a non pre-multiplied surface is preferable. 157 * 158 */ 159 public static final int NON_PREMULTIPLIED = 0x00000100; 160 161 /** 162 * Surface creation flag: Indicates that the surface must be considered opaque, 163 * even if its pixel format is set to translucent. This can be useful if an 164 * application needs full RGBA 8888 support for instance but will 165 * still draw every pixel opaque. 166 * <p> 167 * This flag is ignored if setAlpha() is used to make the surface non-opaque. 168 * Combined effects are (assuming a buffer format with an alpha channel): 169 * <ul> 170 * <li>OPAQUE + alpha(1.0) == opaque composition 171 * <li>OPAQUE + alpha(0.x) == blended composition 172 * <li>!OPAQUE + alpha(1.0) == blended composition 173 * <li>!OPAQUE + alpha(0.x) == blended composition 174 * </ul> 175 * If the underlying buffer lacks an alpha channel, the OPAQUE flag is effectively 176 * set automatically. 177 */ 178 public static final int OPAQUE = 0x00000400; 179 180 /** 181 * Surface creation flag: Application requires a hardware-protected path to an 182 * external display sink. If a hardware-protected path is not available, 183 * then this surface will not be displayed on the external sink. 184 * 185 */ 186 public static final int PROTECTED_APP = 0x00000800; 187 188 // 0x1000 is reserved for an independent DRM protected flag in framework 189 190 /** 191 * Surface creation flag: Window represents a cursor glyph. 192 */ 193 public static final int CURSOR_WINDOW = 0x00002000; 194 195 /** 196 * Surface creation flag: Creates a normal surface. 197 * This is the default. 198 * 199 */ 200 public static final int FX_SURFACE_NORMAL = 0x00000000; 201 202 /** 203 * Surface creation flag: Creates a Dim surface. 204 * Everything behind this surface is dimmed by the amount specified 205 * in {@link #setAlpha}. It is an error to lock a Dim surface, since it 206 * doesn't have a backing store. 207 * 208 */ 209 public static final int FX_SURFACE_DIM = 0x00020000; 210 211 /** 212 * Mask used for FX values above. 213 * 214 */ 215 public static final int FX_SURFACE_MASK = 0x000F0000; 216 217 /* flags used with setFlags() (keep in sync with ISurfaceComposer.h) */ 218 219 /** 220 * Surface flag: Hide the surface. 221 * Equivalent to calling hide(). 222 * Updates the value set during Surface creation (see {@link #HIDDEN}). 223 */ 224 private static final int SURFACE_HIDDEN = 0x01; 225 226 /** 227 * Surface flag: composite without blending when possible. 228 * Updates the value set during Surface creation (see {@link #OPAQUE}). 229 */ 230 private static final int SURFACE_OPAQUE = 0x02; 231 232 233 /* built-in physical display ids (keep in sync with ISurfaceComposer.h) 234 * these are different from the logical display ids used elsewhere in the framework */ 235 236 /** 237 * Built-in physical display id: Main display. 238 * Use only with {@link SurfaceControl#getBuiltInDisplay(int)}. 239 */ 240 public static final int BUILT_IN_DISPLAY_ID_MAIN = 0; 241 242 /** 243 * Built-in physical display id: Attached HDMI display. 244 * Use only with {@link SurfaceControl#getBuiltInDisplay(int)}. 245 */ 246 public static final int BUILT_IN_DISPLAY_ID_HDMI = 1; 247 248 /* Display power modes * / 249 250 /** 251 * Display power mode off: used while blanking the screen. 252 * Use only with {@link SurfaceControl#setDisplayPowerMode}. 253 */ 254 public static final int POWER_MODE_OFF = 0; 255 256 /** 257 * Display power mode doze: used while putting the screen into low power mode. 258 * Use only with {@link SurfaceControl#setDisplayPowerMode}. 259 */ 260 public static final int POWER_MODE_DOZE = 1; 261 262 /** 263 * Display power mode normal: used while unblanking the screen. 264 * Use only with {@link SurfaceControl#setDisplayPowerMode}. 265 */ 266 public static final int POWER_MODE_NORMAL = 2; 267 268 /** 269 * Display power mode doze: used while putting the screen into a suspended 270 * low power mode. Use only with {@link SurfaceControl#setDisplayPowerMode}. 271 */ 272 public static final int POWER_MODE_DOZE_SUSPEND = 3; 273 274 /** 275 * Create a surface with a name. 276 * <p> 277 * The surface creation flags specify what kind of surface to create and 278 * certain options such as whether the surface can be assumed to be opaque 279 * and whether it should be initially hidden. Surfaces should always be 280 * created with the {@link #HIDDEN} flag set to ensure that they are not 281 * made visible prematurely before all of the surface's properties have been 282 * configured. 283 * <p> 284 * Good practice is to first create the surface with the {@link #HIDDEN} flag 285 * specified, open a transaction, set the surface layer, layer stack, alpha, 286 * and position, call {@link #show} if appropriate, and close the transaction. 287 * 288 * @param session The surface session, must not be null. 289 * @param name The surface name, must not be null. 290 * @param w The surface initial width. 291 * @param h The surface initial height. 292 * @param flags The surface creation flags. Should always include {@link #HIDDEN} 293 * in the creation flags. 294 * @param windowType The type of the window as specified in WindowManager.java. 295 * @param ownerUid A unique per-app ID. 296 * 297 * @throws throws OutOfResourcesException If the SurfaceControl cannot be created. 298 */ SurfaceControl(SurfaceSession session, String name, int w, int h, int format, int flags, int windowType, int ownerUid)299 public SurfaceControl(SurfaceSession session, 300 String name, int w, int h, int format, int flags, int windowType, int ownerUid) 301 throws OutOfResourcesException { 302 this(session, name, w, h, format, flags, null, windowType, ownerUid); 303 } 304 SurfaceControl(SurfaceSession session, String name, int w, int h, int format, int flags)305 public SurfaceControl(SurfaceSession session, 306 String name, int w, int h, int format, int flags) 307 throws OutOfResourcesException { 308 this(session, name, w, h, format, flags, null, INVALID_WINDOW_TYPE, Binder.getCallingUid()); 309 } 310 SurfaceControl(SurfaceSession session, String name, int w, int h, int format, int flags, SurfaceControl parent, int windowType, int ownerUid)311 public SurfaceControl(SurfaceSession session, String name, int w, int h, int format, int flags, 312 SurfaceControl parent, int windowType, int ownerUid) 313 throws OutOfResourcesException { 314 if (session == null) { 315 throw new IllegalArgumentException("session must not be null"); 316 } 317 if (name == null) { 318 throw new IllegalArgumentException("name must not be null"); 319 } 320 321 if ((flags & SurfaceControl.HIDDEN) == 0) { 322 Log.w(TAG, "Surfaces should always be created with the HIDDEN flag set " 323 + "to ensure that they are not made visible prematurely before " 324 + "all of the surface's properties have been configured. " 325 + "Set the other properties and make the surface visible within " 326 + "a transaction. New surface name: " + name, 327 new Throwable()); 328 } 329 330 mName = name; 331 mNativeObject = nativeCreate(session, name, w, h, format, flags, 332 parent != null ? parent.mNativeObject : 0, windowType, ownerUid); 333 if (mNativeObject == 0) { 334 throw new OutOfResourcesException( 335 "Couldn't allocate SurfaceControl native object"); 336 } 337 338 mCloseGuard.open("release"); 339 } 340 341 // This is a transfer constructor, useful for transferring a live SurfaceControl native 342 // object to another Java wrapper which could have some different behavior, e.g. 343 // event logging. SurfaceControl(SurfaceControl other)344 public SurfaceControl(SurfaceControl other) { 345 mName = other.mName; 346 mNativeObject = other.mNativeObject; 347 other.mCloseGuard.close(); 348 other.mNativeObject = 0; 349 mCloseGuard.open("release"); 350 } 351 352 @Override finalize()353 protected void finalize() throws Throwable { 354 try { 355 if (mCloseGuard != null) { 356 mCloseGuard.warnIfOpen(); 357 } 358 if (mNativeObject != 0) { 359 nativeRelease(mNativeObject); 360 } 361 } finally { 362 super.finalize(); 363 } 364 } 365 366 @Override toString()367 public String toString() { 368 return "Surface(name=" + mName + ")"; 369 } 370 371 /** 372 * Release the local reference to the server-side surface. 373 * Always call release() when you're done with a Surface. 374 * This will make the surface invalid. 375 */ release()376 public void release() { 377 if (mNativeObject != 0) { 378 nativeRelease(mNativeObject); 379 mNativeObject = 0; 380 } 381 mCloseGuard.close(); 382 } 383 384 /** 385 * Free all server-side state associated with this surface and 386 * release this object's reference. This method can only be 387 * called from the process that created the service. 388 */ destroy()389 public void destroy() { 390 if (mNativeObject != 0) { 391 nativeDestroy(mNativeObject); 392 mNativeObject = 0; 393 } 394 mCloseGuard.close(); 395 } 396 397 /** 398 * Disconnect any client still connected to the surface. 399 */ disconnect()400 public void disconnect() { 401 if (mNativeObject != 0) { 402 nativeDisconnect(mNativeObject); 403 } 404 } 405 checkNotReleased()406 private void checkNotReleased() { 407 if (mNativeObject == 0) throw new NullPointerException( 408 "mNativeObject is null. Have you called release() already?"); 409 } 410 411 /* 412 * set surface parameters. 413 * needs to be inside open/closeTransaction block 414 */ 415 416 /** start a transaction */ openTransaction()417 public static void openTransaction() { 418 nativeOpenTransaction(); 419 } 420 421 /** end a transaction */ closeTransaction()422 public static void closeTransaction() { 423 nativeCloseTransaction(false); 424 } 425 closeTransactionSync()426 public static void closeTransactionSync() { 427 nativeCloseTransaction(true); 428 } 429 deferTransactionUntil(IBinder handle, long frame)430 public void deferTransactionUntil(IBinder handle, long frame) { 431 if (frame > 0) { 432 nativeDeferTransactionUntil(mNativeObject, handle, frame); 433 } 434 } 435 deferTransactionUntil(Surface barrier, long frame)436 public void deferTransactionUntil(Surface barrier, long frame) { 437 if (frame > 0) { 438 nativeDeferTransactionUntilSurface(mNativeObject, barrier.mNativeObject, frame); 439 } 440 } 441 reparentChildren(IBinder newParentHandle)442 public void reparentChildren(IBinder newParentHandle) { 443 nativeReparentChildren(mNativeObject, newParentHandle); 444 } 445 detachChildren()446 public void detachChildren() { 447 nativeSeverChildren(mNativeObject); 448 } 449 setOverrideScalingMode(int scalingMode)450 public void setOverrideScalingMode(int scalingMode) { 451 checkNotReleased(); 452 nativeSetOverrideScalingMode(mNativeObject, scalingMode); 453 } 454 getHandle()455 public IBinder getHandle() { 456 return nativeGetHandle(mNativeObject); 457 } 458 459 /** flag the transaction as an animation */ setAnimationTransaction()460 public static void setAnimationTransaction() { 461 nativeSetAnimationTransaction(); 462 } 463 setLayer(int zorder)464 public void setLayer(int zorder) { 465 checkNotReleased(); 466 nativeSetLayer(mNativeObject, zorder); 467 } 468 setRelativeLayer(IBinder relativeTo, int zorder)469 public void setRelativeLayer(IBinder relativeTo, int zorder) { 470 checkNotReleased(); 471 nativeSetRelativeLayer(mNativeObject, relativeTo, zorder); 472 } 473 setPosition(float x, float y)474 public void setPosition(float x, float y) { 475 checkNotReleased(); 476 nativeSetPosition(mNativeObject, x, y); 477 } 478 479 /** 480 * If the buffer size changes in this transaction, position and crop updates specified 481 * in this transaction will not complete until a buffer of the new size 482 * arrives. As transform matrix and size are already frozen in this fashion, 483 * this enables totally freezing the surface until the resize has completed 484 * (at which point the geometry influencing aspects of this transaction will then occur) 485 */ setGeometryAppliesWithResize()486 public void setGeometryAppliesWithResize() { 487 checkNotReleased(); 488 nativeSetGeometryAppliesWithResize(mNativeObject); 489 } 490 setSize(int w, int h)491 public void setSize(int w, int h) { 492 checkNotReleased(); 493 nativeSetSize(mNativeObject, w, h); 494 } 495 hide()496 public void hide() { 497 checkNotReleased(); 498 nativeSetFlags(mNativeObject, SURFACE_HIDDEN, SURFACE_HIDDEN); 499 } 500 show()501 public void show() { 502 checkNotReleased(); 503 nativeSetFlags(mNativeObject, 0, SURFACE_HIDDEN); 504 } 505 setTransparentRegionHint(Region region)506 public void setTransparentRegionHint(Region region) { 507 checkNotReleased(); 508 nativeSetTransparentRegionHint(mNativeObject, region); 509 } 510 clearContentFrameStats()511 public boolean clearContentFrameStats() { 512 checkNotReleased(); 513 return nativeClearContentFrameStats(mNativeObject); 514 } 515 getContentFrameStats(WindowContentFrameStats outStats)516 public boolean getContentFrameStats(WindowContentFrameStats outStats) { 517 checkNotReleased(); 518 return nativeGetContentFrameStats(mNativeObject, outStats); 519 } 520 clearAnimationFrameStats()521 public static boolean clearAnimationFrameStats() { 522 return nativeClearAnimationFrameStats(); 523 } 524 getAnimationFrameStats(WindowAnimationFrameStats outStats)525 public static boolean getAnimationFrameStats(WindowAnimationFrameStats outStats) { 526 return nativeGetAnimationFrameStats(outStats); 527 } 528 529 /** 530 * Sets an alpha value for the entire Surface. This value is combined with the 531 * per-pixel alpha. It may be used with opaque Surfaces. 532 */ setAlpha(float alpha)533 public void setAlpha(float alpha) { 534 checkNotReleased(); 535 nativeSetAlpha(mNativeObject, alpha); 536 } 537 setMatrix(float dsdx, float dtdx, float dtdy, float dsdy)538 public void setMatrix(float dsdx, float dtdx, float dtdy, float dsdy) { 539 checkNotReleased(); 540 nativeSetMatrix(mNativeObject, dsdx, dtdx, dtdy, dsdy); 541 } 542 setWindowCrop(Rect crop)543 public void setWindowCrop(Rect crop) { 544 checkNotReleased(); 545 if (crop != null) { 546 nativeSetWindowCrop(mNativeObject, 547 crop.left, crop.top, crop.right, crop.bottom); 548 } else { 549 nativeSetWindowCrop(mNativeObject, 0, 0, 0, 0); 550 } 551 } 552 setFinalCrop(Rect crop)553 public void setFinalCrop(Rect crop) { 554 checkNotReleased(); 555 if (crop != null) { 556 nativeSetFinalCrop(mNativeObject, 557 crop.left, crop.top, crop.right, crop.bottom); 558 } else { 559 nativeSetFinalCrop(mNativeObject, 0, 0, 0, 0); 560 } 561 } 562 setLayerStack(int layerStack)563 public void setLayerStack(int layerStack) { 564 checkNotReleased(); 565 nativeSetLayerStack(mNativeObject, layerStack); 566 } 567 568 /** 569 * Sets the opacity of the surface. Setting the flag is equivalent to creating the 570 * Surface with the {@link #OPAQUE} flag. 571 */ setOpaque(boolean isOpaque)572 public void setOpaque(boolean isOpaque) { 573 checkNotReleased(); 574 if (isOpaque) { 575 nativeSetFlags(mNativeObject, SURFACE_OPAQUE, SURFACE_OPAQUE); 576 } else { 577 nativeSetFlags(mNativeObject, 0, SURFACE_OPAQUE); 578 } 579 } 580 581 /** 582 * Sets the security of the surface. Setting the flag is equivalent to creating the 583 * Surface with the {@link #SECURE} flag. 584 */ setSecure(boolean isSecure)585 public void setSecure(boolean isSecure) { 586 checkNotReleased(); 587 if (isSecure) { 588 nativeSetFlags(mNativeObject, SECURE, SECURE); 589 } else { 590 nativeSetFlags(mNativeObject, 0, SECURE); 591 } 592 } 593 594 /* 595 * set display parameters. 596 * needs to be inside open/closeTransaction block 597 */ 598 599 /** 600 * Describes the properties of a physical display known to surface flinger. 601 */ 602 public static final class PhysicalDisplayInfo { 603 public int width; 604 public int height; 605 public float refreshRate; 606 public float density; 607 public float xDpi; 608 public float yDpi; 609 public boolean secure; 610 public long appVsyncOffsetNanos; 611 public long presentationDeadlineNanos; 612 PhysicalDisplayInfo()613 public PhysicalDisplayInfo() { 614 } 615 PhysicalDisplayInfo(PhysicalDisplayInfo other)616 public PhysicalDisplayInfo(PhysicalDisplayInfo other) { 617 copyFrom(other); 618 } 619 620 @Override equals(Object o)621 public boolean equals(Object o) { 622 return o instanceof PhysicalDisplayInfo && equals((PhysicalDisplayInfo)o); 623 } 624 equals(PhysicalDisplayInfo other)625 public boolean equals(PhysicalDisplayInfo other) { 626 return other != null 627 && width == other.width 628 && height == other.height 629 && refreshRate == other.refreshRate 630 && density == other.density 631 && xDpi == other.xDpi 632 && yDpi == other.yDpi 633 && secure == other.secure 634 && appVsyncOffsetNanos == other.appVsyncOffsetNanos 635 && presentationDeadlineNanos == other.presentationDeadlineNanos; 636 } 637 638 @Override hashCode()639 public int hashCode() { 640 return 0; // don't care 641 } 642 copyFrom(PhysicalDisplayInfo other)643 public void copyFrom(PhysicalDisplayInfo other) { 644 width = other.width; 645 height = other.height; 646 refreshRate = other.refreshRate; 647 density = other.density; 648 xDpi = other.xDpi; 649 yDpi = other.yDpi; 650 secure = other.secure; 651 appVsyncOffsetNanos = other.appVsyncOffsetNanos; 652 presentationDeadlineNanos = other.presentationDeadlineNanos; 653 } 654 655 // For debugging purposes 656 @Override toString()657 public String toString() { 658 return "PhysicalDisplayInfo{" + width + " x " + height + ", " + refreshRate + " fps, " 659 + "density " + density + ", " + xDpi + " x " + yDpi + " dpi, secure " + secure 660 + ", appVsyncOffset " + appVsyncOffsetNanos 661 + ", bufferDeadline " + presentationDeadlineNanos + "}"; 662 } 663 } 664 setDisplayPowerMode(IBinder displayToken, int mode)665 public static void setDisplayPowerMode(IBinder displayToken, int mode) { 666 if (displayToken == null) { 667 throw new IllegalArgumentException("displayToken must not be null"); 668 } 669 nativeSetDisplayPowerMode(displayToken, mode); 670 } 671 getDisplayConfigs(IBinder displayToken)672 public static SurfaceControl.PhysicalDisplayInfo[] getDisplayConfigs(IBinder displayToken) { 673 if (displayToken == null) { 674 throw new IllegalArgumentException("displayToken must not be null"); 675 } 676 return nativeGetDisplayConfigs(displayToken); 677 } 678 getActiveConfig(IBinder displayToken)679 public static int getActiveConfig(IBinder displayToken) { 680 if (displayToken == null) { 681 throw new IllegalArgumentException("displayToken must not be null"); 682 } 683 return nativeGetActiveConfig(displayToken); 684 } 685 setActiveConfig(IBinder displayToken, int id)686 public static boolean setActiveConfig(IBinder displayToken, int id) { 687 if (displayToken == null) { 688 throw new IllegalArgumentException("displayToken must not be null"); 689 } 690 return nativeSetActiveConfig(displayToken, id); 691 } 692 getDisplayColorModes(IBinder displayToken)693 public static int[] getDisplayColorModes(IBinder displayToken) { 694 if (displayToken == null) { 695 throw new IllegalArgumentException("displayToken must not be null"); 696 } 697 return nativeGetDisplayColorModes(displayToken); 698 } 699 getActiveColorMode(IBinder displayToken)700 public static int getActiveColorMode(IBinder displayToken) { 701 if (displayToken == null) { 702 throw new IllegalArgumentException("displayToken must not be null"); 703 } 704 return nativeGetActiveColorMode(displayToken); 705 } 706 setActiveColorMode(IBinder displayToken, int colorMode)707 public static boolean setActiveColorMode(IBinder displayToken, int colorMode) { 708 if (displayToken == null) { 709 throw new IllegalArgumentException("displayToken must not be null"); 710 } 711 return nativeSetActiveColorMode(displayToken, colorMode); 712 } 713 setDisplayProjection(IBinder displayToken, int orientation, Rect layerStackRect, Rect displayRect)714 public static void setDisplayProjection(IBinder displayToken, 715 int orientation, Rect layerStackRect, Rect displayRect) { 716 if (displayToken == null) { 717 throw new IllegalArgumentException("displayToken must not be null"); 718 } 719 if (layerStackRect == null) { 720 throw new IllegalArgumentException("layerStackRect must not be null"); 721 } 722 if (displayRect == null) { 723 throw new IllegalArgumentException("displayRect must not be null"); 724 } 725 nativeSetDisplayProjection(displayToken, orientation, 726 layerStackRect.left, layerStackRect.top, layerStackRect.right, layerStackRect.bottom, 727 displayRect.left, displayRect.top, displayRect.right, displayRect.bottom); 728 } 729 setDisplayLayerStack(IBinder displayToken, int layerStack)730 public static void setDisplayLayerStack(IBinder displayToken, int layerStack) { 731 if (displayToken == null) { 732 throw new IllegalArgumentException("displayToken must not be null"); 733 } 734 nativeSetDisplayLayerStack(displayToken, layerStack); 735 } 736 setDisplaySurface(IBinder displayToken, Surface surface)737 public static void setDisplaySurface(IBinder displayToken, Surface surface) { 738 if (displayToken == null) { 739 throw new IllegalArgumentException("displayToken must not be null"); 740 } 741 742 if (surface != null) { 743 synchronized (surface.mLock) { 744 nativeSetDisplaySurface(displayToken, surface.mNativeObject); 745 } 746 } else { 747 nativeSetDisplaySurface(displayToken, 0); 748 } 749 } 750 setDisplaySize(IBinder displayToken, int width, int height)751 public static void setDisplaySize(IBinder displayToken, int width, int height) { 752 if (displayToken == null) { 753 throw new IllegalArgumentException("displayToken must not be null"); 754 } 755 if (width <= 0 || height <= 0) { 756 throw new IllegalArgumentException("width and height must be positive"); 757 } 758 759 nativeSetDisplaySize(displayToken, width, height); 760 } 761 getHdrCapabilities(IBinder displayToken)762 public static Display.HdrCapabilities getHdrCapabilities(IBinder displayToken) { 763 if (displayToken == null) { 764 throw new IllegalArgumentException("displayToken must not be null"); 765 } 766 return nativeGetHdrCapabilities(displayToken); 767 } 768 createDisplay(String name, boolean secure)769 public static IBinder createDisplay(String name, boolean secure) { 770 if (name == null) { 771 throw new IllegalArgumentException("name must not be null"); 772 } 773 return nativeCreateDisplay(name, secure); 774 } 775 destroyDisplay(IBinder displayToken)776 public static void destroyDisplay(IBinder displayToken) { 777 if (displayToken == null) { 778 throw new IllegalArgumentException("displayToken must not be null"); 779 } 780 nativeDestroyDisplay(displayToken); 781 } 782 getBuiltInDisplay(int builtInDisplayId)783 public static IBinder getBuiltInDisplay(int builtInDisplayId) { 784 return nativeGetBuiltInDisplay(builtInDisplayId); 785 } 786 787 /** 788 * Copy the current screen contents into the provided {@link Surface} 789 * 790 * @param display The display to take the screenshot of. 791 * @param consumer The {@link Surface} to take the screenshot into. 792 * @param width The desired width of the returned bitmap; the raw 793 * screen will be scaled down to this size. 794 * @param height The desired height of the returned bitmap; the raw 795 * screen will be scaled down to this size. 796 * @param minLayer The lowest (bottom-most Z order) surface layer to 797 * include in the screenshot. 798 * @param maxLayer The highest (top-most Z order) surface layer to 799 * include in the screenshot. 800 * @param useIdentityTransform Replace whatever transformation (rotation, 801 * scaling, translation) the surface layers are currently using with the 802 * identity transformation while taking the screenshot. 803 */ screenshot(IBinder display, Surface consumer, int width, int height, int minLayer, int maxLayer, boolean useIdentityTransform)804 public static void screenshot(IBinder display, Surface consumer, 805 int width, int height, int minLayer, int maxLayer, 806 boolean useIdentityTransform) { 807 screenshot(display, consumer, new Rect(), width, height, minLayer, maxLayer, 808 false, useIdentityTransform); 809 } 810 811 /** 812 * Copy the current screen contents into the provided {@link Surface} 813 * 814 * @param display The display to take the screenshot of. 815 * @param consumer The {@link Surface} to take the screenshot into. 816 * @param width The desired width of the returned bitmap; the raw 817 * screen will be scaled down to this size. 818 * @param height The desired height of the returned bitmap; the raw 819 * screen will be scaled down to this size. 820 */ screenshot(IBinder display, Surface consumer, int width, int height)821 public static void screenshot(IBinder display, Surface consumer, 822 int width, int height) { 823 screenshot(display, consumer, new Rect(), width, height, 0, 0, true, false); 824 } 825 826 /** 827 * Copy the current screen contents into the provided {@link Surface} 828 * 829 * @param display The display to take the screenshot of. 830 * @param consumer The {@link Surface} to take the screenshot into. 831 */ screenshot(IBinder display, Surface consumer)832 public static void screenshot(IBinder display, Surface consumer) { 833 screenshot(display, consumer, new Rect(), 0, 0, 0, 0, true, false); 834 } 835 836 /** 837 * Copy the current screen contents into a bitmap and return it. 838 * 839 * CAVEAT: Versions of screenshot that return a {@link Bitmap} can 840 * be extremely slow; avoid use unless absolutely necessary; prefer 841 * the versions that use a {@link Surface} instead, such as 842 * {@link SurfaceControl#screenshot(IBinder, Surface)}. 843 * 844 * @param sourceCrop The portion of the screen to capture into the Bitmap; 845 * caller may pass in 'new Rect()' if no cropping is desired. 846 * @param width The desired width of the returned bitmap; the raw 847 * screen will be scaled down to this size. 848 * @param height The desired height of the returned bitmap; the raw 849 * screen will be scaled down to this size. 850 * @param minLayer The lowest (bottom-most Z order) surface layer to 851 * include in the screenshot. 852 * @param maxLayer The highest (top-most Z order) surface layer to 853 * include in the screenshot. 854 * @param useIdentityTransform Replace whatever transformation (rotation, 855 * scaling, translation) the surface layers are currently using with the 856 * identity transformation while taking the screenshot. 857 * @param rotation Apply a custom clockwise rotation to the screenshot, i.e. 858 * Surface.ROTATION_0,90,180,270. Surfaceflinger will always take 859 * screenshots in its native portrait orientation by default, so this is 860 * useful for returning screenshots that are independent of device 861 * orientation. 862 * @return Returns a Bitmap containing the screen contents, or null 863 * if an error occurs. Make sure to call Bitmap.recycle() as soon as 864 * possible, once its content is not needed anymore. 865 */ screenshot(Rect sourceCrop, int width, int height, int minLayer, int maxLayer, boolean useIdentityTransform, int rotation)866 public static Bitmap screenshot(Rect sourceCrop, int width, int height, 867 int minLayer, int maxLayer, boolean useIdentityTransform, 868 int rotation) { 869 // TODO: should take the display as a parameter 870 IBinder displayToken = SurfaceControl.getBuiltInDisplay( 871 SurfaceControl.BUILT_IN_DISPLAY_ID_MAIN); 872 return nativeScreenshot(displayToken, sourceCrop, width, height, 873 minLayer, maxLayer, false, useIdentityTransform, rotation); 874 } 875 876 /** 877 * Like {@link SurfaceControl#screenshot(Rect, int, int, int, int, boolean, int)} 878 * but returns a GraphicBuffer. 879 */ screenshotToBuffer(Rect sourceCrop, int width, int height, int minLayer, int maxLayer, boolean useIdentityTransform, int rotation)880 public static GraphicBuffer screenshotToBuffer(Rect sourceCrop, int width, int height, 881 int minLayer, int maxLayer, boolean useIdentityTransform, 882 int rotation) { 883 IBinder displayToken = SurfaceControl.getBuiltInDisplay( 884 SurfaceControl.BUILT_IN_DISPLAY_ID_MAIN); 885 return nativeScreenshotToBuffer(displayToken, sourceCrop, width, height, 886 minLayer, maxLayer, false, useIdentityTransform, rotation); 887 } 888 889 /** 890 * Like {@link SurfaceControl#screenshot(int, int, int, int, boolean)} but 891 * includes all Surfaces in the screenshot. 892 * 893 * @param width The desired width of the returned bitmap; the raw 894 * screen will be scaled down to this size. 895 * @param height The desired height of the returned bitmap; the raw 896 * screen will be scaled down to this size. 897 * @return Returns a Bitmap containing the screen contents, or null 898 * if an error occurs. Make sure to call Bitmap.recycle() as soon as 899 * possible, once its content is not needed anymore. 900 */ screenshot(int width, int height)901 public static Bitmap screenshot(int width, int height) { 902 // TODO: should take the display as a parameter 903 IBinder displayToken = SurfaceControl.getBuiltInDisplay( 904 SurfaceControl.BUILT_IN_DISPLAY_ID_MAIN); 905 return nativeScreenshot(displayToken, new Rect(), width, height, 0, 0, true, 906 false, Surface.ROTATION_0); 907 } 908 screenshot(IBinder display, Surface consumer, Rect sourceCrop, int width, int height, int minLayer, int maxLayer, boolean allLayers, boolean useIdentityTransform)909 private static void screenshot(IBinder display, Surface consumer, Rect sourceCrop, 910 int width, int height, int minLayer, int maxLayer, boolean allLayers, 911 boolean useIdentityTransform) { 912 if (display == null) { 913 throw new IllegalArgumentException("displayToken must not be null"); 914 } 915 if (consumer == null) { 916 throw new IllegalArgumentException("consumer must not be null"); 917 } 918 nativeScreenshot(display, consumer, sourceCrop, width, height, 919 minLayer, maxLayer, allLayers, useIdentityTransform); 920 } 921 } 922