1 /* 2 * Copyright (C) 2012 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.hardware.display; 18 19 import static android.view.Display.DEFAULT_DISPLAY; 20 import static android.view.Display.HdrCapabilities.HdrType; 21 22 import android.Manifest; 23 import android.annotation.FloatRange; 24 import android.annotation.IntDef; 25 import android.annotation.IntRange; 26 import android.annotation.LongDef; 27 import android.annotation.NonNull; 28 import android.annotation.Nullable; 29 import android.annotation.RequiresPermission; 30 import android.annotation.SystemApi; 31 import android.annotation.SystemService; 32 import android.annotation.TestApi; 33 import android.app.KeyguardManager; 34 import android.compat.annotation.UnsupportedAppUsage; 35 import android.content.Context; 36 import android.content.pm.IPackageManager; 37 import android.content.res.Resources; 38 import android.graphics.Point; 39 import android.media.projection.MediaProjection; 40 import android.os.Build; 41 import android.os.Handler; 42 import android.os.HandlerExecutor; 43 import android.os.Looper; 44 import android.os.Process; 45 import android.os.RemoteException; 46 import android.os.ServiceManager; 47 import android.util.Pair; 48 import android.util.Slog; 49 import android.util.SparseArray; 50 import android.view.Display; 51 import android.view.Surface; 52 53 import com.android.internal.R; 54 import com.android.internal.annotations.GuardedBy; 55 56 import java.lang.annotation.Retention; 57 import java.lang.annotation.RetentionPolicy; 58 import java.lang.ref.WeakReference; 59 import java.util.ArrayList; 60 import java.util.List; 61 import java.util.Objects; 62 import java.util.concurrent.Executor; 63 import java.util.function.Predicate; 64 65 66 /** 67 * Manages the properties of attached displays. 68 */ 69 @SystemService(Context.DISPLAY_SERVICE) 70 public final class DisplayManager { 71 private static final String TAG = "DisplayManager"; 72 private static final boolean DEBUG = false; 73 private static final boolean ENABLE_VIRTUAL_DISPLAY_REFRESH_RATE = true; 74 75 /** 76 * The hdr output control feature flag, the value should be read via 77 * {@link android.provider.DeviceConfig#getBoolean(String, String, boolean)} with 78 * {@link android.provider.DeviceConfig#NAMESPACE_DISPLAY_MANAGER} as the namespace. 79 * @hide 80 */ 81 @TestApi 82 public static final String HDR_OUTPUT_CONTROL_FLAG = "enable_hdr_output_control"; 83 84 private final Context mContext; 85 private final DisplayManagerGlobal mGlobal; 86 87 private final Object mLock = new Object(); 88 @GuardedBy("mLock") 89 private final WeakDisplayCache mDisplayCache = new WeakDisplayCache(); 90 91 /** 92 * Broadcast receiver that indicates when the Wifi display status changes. 93 * <p> 94 * The status is provided as a {@link WifiDisplayStatus} object in the 95 * {@link #EXTRA_WIFI_DISPLAY_STATUS} extra. 96 * </p><p> 97 * This broadcast is only sent to registered receivers and can only be sent by the system. 98 * </p> 99 * @hide 100 */ 101 @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553) 102 public static final String ACTION_WIFI_DISPLAY_STATUS_CHANGED = 103 "android.hardware.display.action.WIFI_DISPLAY_STATUS_CHANGED"; 104 105 /** 106 * Contains a {@link WifiDisplayStatus} object. 107 * @hide 108 */ 109 @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553) 110 public static final String EXTRA_WIFI_DISPLAY_STATUS = 111 "android.hardware.display.extra.WIFI_DISPLAY_STATUS"; 112 113 /** 114 * Display category: Presentation displays. 115 * <p> 116 * This category can be used to identify secondary displays that are suitable for 117 * use as presentation displays such as external or wireless displays. Applications 118 * may automatically project their content to presentation displays to provide 119 * richer second screen experiences. 120 * </p> 121 * 122 * @see android.app.Presentation 123 * @see Display#FLAG_PRESENTATION 124 * @see #getDisplays(String) 125 */ 126 public static final String DISPLAY_CATEGORY_PRESENTATION = 127 "android.hardware.display.category.PRESENTATION"; 128 129 /** 130 * Display category: Rear displays. 131 * <p> 132 * This category can be used to identify complementary internal displays that are facing away 133 * from the user. 134 * Certain applications may present to this display. 135 * Similar to presentation displays. 136 * </p> 137 * 138 * @see android.app.Presentation 139 * @see Display#FLAG_PRESENTATION 140 * @see #getDisplays(String) 141 * @hide 142 */ 143 @TestApi 144 public static final String DISPLAY_CATEGORY_REAR = 145 "android.hardware.display.category.REAR"; 146 147 /** 148 * Display category: All displays, including disabled displays. 149 * <p> 150 * This returns all displays, including currently disabled and inaccessible displays. 151 * 152 * @see #getDisplays(String) 153 * @hide 154 */ 155 public static final String DISPLAY_CATEGORY_ALL_INCLUDING_DISABLED = 156 "android.hardware.display.category.ALL_INCLUDING_DISABLED"; 157 158 /** @hide **/ 159 @IntDef(prefix = "VIRTUAL_DISPLAY_FLAG_", flag = true, value = { 160 VIRTUAL_DISPLAY_FLAG_PUBLIC, 161 VIRTUAL_DISPLAY_FLAG_PRESENTATION, 162 VIRTUAL_DISPLAY_FLAG_SECURE, 163 VIRTUAL_DISPLAY_FLAG_OWN_CONTENT_ONLY, 164 VIRTUAL_DISPLAY_FLAG_AUTO_MIRROR, 165 VIRTUAL_DISPLAY_FLAG_CAN_SHOW_WITH_INSECURE_KEYGUARD, 166 VIRTUAL_DISPLAY_FLAG_SUPPORTS_TOUCH, 167 VIRTUAL_DISPLAY_FLAG_ROTATES_WITH_CONTENT, 168 VIRTUAL_DISPLAY_FLAG_DESTROY_CONTENT_ON_REMOVAL, 169 VIRTUAL_DISPLAY_FLAG_SHOULD_SHOW_SYSTEM_DECORATIONS, 170 VIRTUAL_DISPLAY_FLAG_TRUSTED, 171 VIRTUAL_DISPLAY_FLAG_OWN_DISPLAY_GROUP, 172 VIRTUAL_DISPLAY_FLAG_ALWAYS_UNLOCKED, 173 VIRTUAL_DISPLAY_FLAG_TOUCH_FEEDBACK_DISABLED, 174 VIRTUAL_DISPLAY_FLAG_OWN_FOCUS, 175 VIRTUAL_DISPLAY_FLAG_STEAL_TOP_FOCUS_DISABLED, 176 }) 177 @Retention(RetentionPolicy.SOURCE) 178 public @interface VirtualDisplayFlag {} 179 180 /** 181 * Virtual display flag: Create a public display. 182 * 183 * <h3>Public virtual displays</h3> 184 * <p> 185 * When this flag is set, the virtual display is public. 186 * </p><p> 187 * A public virtual display behaves just like most any other display that is connected 188 * to the system such as an external or wireless display. Applications can open 189 * windows on the display and the system may mirror the contents of other displays 190 * onto it. 191 * </p><p> 192 * Creating a public virtual display that isn't restricted to own-content only implicitly 193 * creates an auto-mirroring display. See {@link #VIRTUAL_DISPLAY_FLAG_AUTO_MIRROR} for 194 * restrictions on who is allowed to create an auto-mirroring display. 195 * </p> 196 * 197 * <h3>Private virtual displays</h3> 198 * <p> 199 * When this flag is not set, the virtual display is private as defined by the 200 * {@link Display#FLAG_PRIVATE} display flag. 201 * </p> 202 * 203 * <p> 204 * A private virtual display belongs to the application that created it. Only the a owner of a 205 * private virtual display and the apps that are already on that display are allowed to place 206 * windows upon it. The private virtual display also does not participate in display mirroring: 207 * it will neither receive mirrored content from another display nor allow its own content to be 208 * mirrored elsewhere. More precisely, the only processes that are allowed to enumerate or 209 * interact with the private display are those that have the same UID as the application that 210 * originally created the private virtual display or as the activities that are already on that 211 * display. 212 * </p> 213 * 214 * @see #createVirtualDisplay 215 * @see #VIRTUAL_DISPLAY_FLAG_OWN_CONTENT_ONLY 216 * @see #VIRTUAL_DISPLAY_FLAG_AUTO_MIRROR 217 */ 218 public static final int VIRTUAL_DISPLAY_FLAG_PUBLIC = 1 << 0; 219 220 /** 221 * Virtual display flag: Create a presentation display. 222 * 223 * <h3>Presentation virtual displays</h3> 224 * <p> 225 * When this flag is set, the virtual display is registered as a presentation 226 * display in the {@link #DISPLAY_CATEGORY_PRESENTATION presentation display category}. 227 * Applications may automatically project their content to presentation displays 228 * to provide richer second screen experiences. 229 * </p> 230 * 231 * <h3>Non-presentation virtual displays</h3> 232 * <p> 233 * When this flag is not set, the virtual display is not registered as a presentation 234 * display. Applications can still project their content on the display but they 235 * will typically not do so automatically. This option is appropriate for 236 * more special-purpose displays. 237 * </p> 238 * 239 * @see android.app.Presentation 240 * @see #createVirtualDisplay 241 * @see #DISPLAY_CATEGORY_PRESENTATION 242 * @see Display#FLAG_PRESENTATION 243 */ 244 public static final int VIRTUAL_DISPLAY_FLAG_PRESENTATION = 1 << 1; 245 246 /** 247 * Virtual display flag: Create a secure display. 248 * 249 * <h3>Secure virtual displays</h3> 250 * <p> 251 * When this flag is set, the virtual display is considered secure as defined 252 * by the {@link Display#FLAG_SECURE} display flag. The caller promises to take 253 * reasonable measures, such as over-the-air encryption, to prevent the contents 254 * of the display from being intercepted or recorded on a persistent medium. 255 * </p><p> 256 * Creating a secure virtual display requires the CAPTURE_SECURE_VIDEO_OUTPUT permission. 257 * This permission is reserved for use by system components and is not available to 258 * third-party applications. 259 * </p> 260 * 261 * <h3>Non-secure virtual displays</h3> 262 * <p> 263 * When this flag is not set, the virtual display is considered unsecure. 264 * The content of secure windows will be blanked if shown on this display. 265 * </p> 266 * 267 * @see Display#FLAG_SECURE 268 * @see #createVirtualDisplay 269 */ 270 public static final int VIRTUAL_DISPLAY_FLAG_SECURE = 1 << 2; 271 272 /** 273 * Virtual display flag: Only show this display's own content; do not mirror 274 * the content of another display. 275 * 276 * <p> 277 * This flag is used in conjunction with {@link #VIRTUAL_DISPLAY_FLAG_PUBLIC}. 278 * Ordinarily public virtual displays will automatically mirror the content of the 279 * default display if they have no windows of their own. When this flag is 280 * specified, the virtual display will only ever show its own content and 281 * will be blanked instead if it has no windows. 282 * </p> 283 * 284 * <p> 285 * This flag is mutually exclusive with {@link #VIRTUAL_DISPLAY_FLAG_AUTO_MIRROR}. If both 286 * flags are specified then the own-content only behavior will be applied. 287 * </p> 288 * 289 * <p> 290 * This behavior of this flag is implied whenever neither {@link #VIRTUAL_DISPLAY_FLAG_PUBLIC} 291 * nor {@link #VIRTUAL_DISPLAY_FLAG_AUTO_MIRROR} have been set. This flag is only required to 292 * override the default behavior when creating a public display. 293 * </p> 294 * 295 * @see #createVirtualDisplay 296 */ 297 public static final int VIRTUAL_DISPLAY_FLAG_OWN_CONTENT_ONLY = 1 << 3; 298 299 300 /** 301 * Virtual display flag: Allows content to be mirrored on private displays when no content is 302 * being shown. 303 * 304 * <p> 305 * This flag is mutually exclusive with {@link #VIRTUAL_DISPLAY_FLAG_OWN_CONTENT_ONLY}. 306 * If both flags are specified then the own-content only behavior will be applied. 307 * </p> 308 * 309 * <p> 310 * The behavior of this flag is implied whenever {@link #VIRTUAL_DISPLAY_FLAG_PUBLIC} is set 311 * and {@link #VIRTUAL_DISPLAY_FLAG_OWN_CONTENT_ONLY} has not been set. This flag is only 312 * required to override the default behavior when creating a private display. 313 * </p> 314 * 315 * <p> 316 * Creating an auto-mirroing virtual display requires the CAPTURE_VIDEO_OUTPUT 317 * or CAPTURE_SECURE_VIDEO_OUTPUT permission. 318 * These permissions are reserved for use by system components and are not available to 319 * third-party applications. 320 * 321 * Alternatively, an appropriate {@link MediaProjection} may be used to create an 322 * auto-mirroring virtual display. 323 * </p> 324 * 325 * @see #createVirtualDisplay 326 */ 327 public static final int VIRTUAL_DISPLAY_FLAG_AUTO_MIRROR = 1 << 4; 328 329 /** 330 * Virtual display flag: Allows content to be displayed on private virtual displays when 331 * keyguard is shown but is insecure. 332 * 333 * <p> 334 * This might be used in a case when the content of a virtual display is captured and sent to an 335 * external hardware display that is not visible to the system directly. This flag will allow 336 * the continued display of content while other displays will be covered by a keyguard which 337 * doesn't require providing credentials to unlock. This means that there is either no password 338 * or other authentication method set, or the device is in a trusted state - 339 * {@link android.service.trust.TrustAgentService} has available and active trust agent. 340 * </p><p> 341 * This flag can only be applied to private displays as defined by the 342 * {@link Display#FLAG_PRIVATE} display flag. It is mutually exclusive with 343 * {@link #VIRTUAL_DISPLAY_FLAG_PUBLIC}. If both flags are specified then this flag's behavior 344 * will not be applied. 345 * </p> 346 * 347 * @see #createVirtualDisplay 348 * @see KeyguardManager#isDeviceSecure() 349 * @see KeyguardManager#isDeviceLocked() 350 * @hide 351 */ 352 // TODO (b/114338689): Remove the flag and use IWindowManager#shouldShowWithInsecureKeyguard 353 // TODO: Update name and documentation and un-hide the flag. Don't change the value before that. 354 public static final int VIRTUAL_DISPLAY_FLAG_CAN_SHOW_WITH_INSECURE_KEYGUARD = 1 << 5; 355 356 /** 357 * Virtual display flag: Specifies that the virtual display can be associated with a 358 * touchpad device that matches its uniqueId. 359 * 360 * @see #createVirtualDisplay 361 * @hide 362 */ 363 public static final int VIRTUAL_DISPLAY_FLAG_SUPPORTS_TOUCH = 1 << 6; 364 365 /** 366 * Virtual display flag: Indicates that the orientation of this display device is coupled to 367 * the rotation of its associated logical display. 368 * 369 * @see #createVirtualDisplay 370 * @hide 371 */ 372 public static final int VIRTUAL_DISPLAY_FLAG_ROTATES_WITH_CONTENT = 1 << 7; 373 374 /** 375 * Virtual display flag: Indicates that the contents will be destroyed once 376 * the display is removed. 377 * 378 * Public virtual displays without this flag will move their content to main display 379 * stack once they're removed. Private vistual displays will always destroy their 380 * content on removal even without this flag. 381 * 382 * @see #createVirtualDisplay 383 * @hide 384 */ 385 // TODO (b/114338689): Remove the flag and use WindowManager#REMOVE_CONTENT_MODE_DESTROY 386 public static final int VIRTUAL_DISPLAY_FLAG_DESTROY_CONTENT_ON_REMOVAL = 1 << 8; 387 388 /** 389 * Virtual display flag: Indicates that the display should support system decorations. Virtual 390 * displays without this flag shouldn't show home, IME or any other system decorations. 391 * <p>This flag doesn't work without {@link #VIRTUAL_DISPLAY_FLAG_TRUSTED}</p> 392 * 393 * @see #createVirtualDisplay 394 * @see #VIRTUAL_DISPLAY_FLAG_TRUSTED 395 * @hide 396 */ 397 // TODO (b/114338689): Remove the flag and use IWindowManager#setShouldShowSystemDecors 398 @TestApi 399 public static final int VIRTUAL_DISPLAY_FLAG_SHOULD_SHOW_SYSTEM_DECORATIONS = 1 << 9; 400 401 /** 402 * Virtual display flags: Indicates that the display is trusted to show system decorations and 403 * receive inputs without users' touch. 404 * 405 * @see #createVirtualDisplay 406 * @see #VIRTUAL_DISPLAY_FLAG_SHOULD_SHOW_SYSTEM_DECORATIONS 407 * @hide 408 */ 409 @SystemApi 410 public static final int VIRTUAL_DISPLAY_FLAG_TRUSTED = 1 << 10; 411 412 /** 413 * Virtual display flags: Indicates that the display should not be a part of the default 414 * DisplayGroup and instead be part of a new DisplayGroup. 415 * 416 * @see #createVirtualDisplay 417 * @hide 418 */ 419 public static final int VIRTUAL_DISPLAY_FLAG_OWN_DISPLAY_GROUP = 1 << 11; 420 421 /** 422 * Virtual display flags: Indicates that the virtual display should always be unlocked and not 423 * have keyguard displayed on it. Only valid for virtual displays that aren't in the default 424 * display group. 425 * 426 * @see #createVirtualDisplay 427 * @see #VIRTUAL_DISPLAY_FLAG_OWN_DISPLAY_GROUP 428 * @hide 429 */ 430 public static final int VIRTUAL_DISPLAY_FLAG_ALWAYS_UNLOCKED = 1 << 12; 431 432 /** 433 * Virtual display flags: Indicates that the display should not play sound effects or perform 434 * haptic feedback when the user touches the screen. 435 * 436 * @see #createVirtualDisplay 437 * @hide 438 */ 439 public static final int VIRTUAL_DISPLAY_FLAG_TOUCH_FEEDBACK_DISABLED = 1 << 13; 440 441 /** 442 * Virtual display flags: Indicates that the display maintains its own focus and touch mode. 443 * 444 * This flag is similar to {@link com.android.internal.R.bool.config_perDisplayFocusEnabled} in 445 * behavior, but only applies to the specific display instead of system-wide to all displays. 446 * 447 * Note: The display must be trusted in order to have its own focus. 448 * 449 * @see #createVirtualDisplay 450 * @see #VIRTUAL_DISPLAY_FLAG_TRUSTED 451 * @hide 452 */ 453 @TestApi 454 public static final int VIRTUAL_DISPLAY_FLAG_OWN_FOCUS = 1 << 14; 455 456 /** 457 * Virtual display flags: Indicates that the display should not be a part of the default 458 * DisplayGroup and instead be part of a DisplayGroup associated with its virtual device. 459 * 460 * @see #createVirtualDisplay 461 * @hide 462 */ 463 public static final int VIRTUAL_DISPLAY_FLAG_DEVICE_DISPLAY_GROUP = 1 << 15; 464 465 466 /** 467 * Virtual display flags: Indicates that the display should not become the top focused display 468 * by stealing the top focus from another display. 469 * 470 * @see Display#FLAG_STEAL_TOP_FOCUS_DISABLED 471 * @see #createVirtualDisplay 472 * @see #VIRTUAL_DISPLAY_FLAG_OWN_FOCUS 473 * @hide 474 */ 475 @SystemApi 476 public static final int VIRTUAL_DISPLAY_FLAG_STEAL_TOP_FOCUS_DISABLED = 1 << 16; 477 478 /** @hide */ 479 @IntDef(prefix = {"MATCH_CONTENT_FRAMERATE_"}, value = { 480 MATCH_CONTENT_FRAMERATE_UNKNOWN, 481 MATCH_CONTENT_FRAMERATE_NEVER, 482 MATCH_CONTENT_FRAMERATE_SEAMLESSS_ONLY, 483 MATCH_CONTENT_FRAMERATE_ALWAYS, 484 }) 485 @Retention(RetentionPolicy.SOURCE) 486 public @interface MatchContentFrameRateType {} 487 488 /** 489 * Match content frame rate user preference is unknown. 490 */ 491 public static final int MATCH_CONTENT_FRAMERATE_UNKNOWN = -1; 492 493 /** 494 * No mode switching is allowed. 495 */ 496 public static final int MATCH_CONTENT_FRAMERATE_NEVER = 0; 497 498 /** 499 * Only refresh rate switches without visual interruptions are allowed. 500 */ 501 public static final int MATCH_CONTENT_FRAMERATE_SEAMLESSS_ONLY = 1; 502 503 /** 504 * Refresh rate switches between all refresh rates are allowed even if they have visual 505 * interruptions for the user. 506 */ 507 public static final int MATCH_CONTENT_FRAMERATE_ALWAYS = 2; 508 509 /** @hide */ 510 @IntDef(prefix = {"SWITCHING_TYPE_"}, value = { 511 SWITCHING_TYPE_NONE, 512 SWITCHING_TYPE_WITHIN_GROUPS, 513 SWITCHING_TYPE_ACROSS_AND_WITHIN_GROUPS, 514 SWITCHING_TYPE_RENDER_FRAME_RATE_ONLY, 515 }) 516 @Retention(RetentionPolicy.SOURCE) 517 public @interface SwitchingType {} 518 519 /** 520 * No display mode switching will happen. 521 * @hide 522 */ 523 @TestApi 524 public static final int SWITCHING_TYPE_NONE = 0; 525 526 /** 527 * Allow only refresh rate switching between modes in the same configuration group. This way 528 * only switches without visual interruptions for the user will be allowed. 529 * @hide 530 */ 531 @TestApi 532 public static final int SWITCHING_TYPE_WITHIN_GROUPS = 1; 533 534 /** 535 * Allow refresh rate switching between all refresh rates even if the switch with have visual 536 * interruptions for the user. 537 * @hide 538 */ 539 @TestApi 540 public static final int SWITCHING_TYPE_ACROSS_AND_WITHIN_GROUPS = 2; 541 542 /** 543 * Allow render frame rate switches, but not physical modes. 544 * @hide 545 */ 546 @TestApi 547 public static final int SWITCHING_TYPE_RENDER_FRAME_RATE_ONLY = 3; 548 549 /** 550 * @hide 551 */ 552 @LongDef(flag = true, prefix = {"EVENT_FLAG_"}, value = { 553 EVENT_FLAG_DISPLAY_ADDED, 554 EVENT_FLAG_DISPLAY_CHANGED, 555 EVENT_FLAG_DISPLAY_REMOVED, 556 EVENT_FLAG_DISPLAY_BRIGHTNESS, 557 EVENT_FLAG_HDR_SDR_RATIO_CHANGED 558 }) 559 @Retention(RetentionPolicy.SOURCE) 560 public @interface EventsMask {} 561 562 /** 563 * Event type for when a new display is added. 564 * 565 * @see #registerDisplayListener(DisplayListener, Handler, long) 566 * 567 * @hide 568 */ 569 public static final long EVENT_FLAG_DISPLAY_ADDED = 1L << 0; 570 571 /** 572 * Event type for when a display is removed. 573 * 574 * @see #registerDisplayListener(DisplayListener, Handler, long) 575 * 576 * @hide 577 */ 578 public static final long EVENT_FLAG_DISPLAY_REMOVED = 1L << 1; 579 580 /** 581 * Event type for when a display is changed. 582 * 583 * @see #registerDisplayListener(DisplayListener, Handler, long) 584 * 585 * @hide 586 */ 587 public static final long EVENT_FLAG_DISPLAY_CHANGED = 1L << 2; 588 589 /** 590 * Event flag to register for a display's brightness changes. This notification is sent 591 * through the {@link DisplayListener#onDisplayChanged} callback method. New brightness 592 * values can be retrieved via {@link android.view.Display#getBrightnessInfo()}. 593 * 594 * @see #registerDisplayListener(DisplayListener, Handler, long) 595 * 596 * @hide 597 */ 598 public static final long EVENT_FLAG_DISPLAY_BRIGHTNESS = 1L << 3; 599 600 /** 601 * Event flag to register for a display's hdr/sdr ratio changes. This notification is sent 602 * through the {@link DisplayListener#onDisplayChanged} callback method. New hdr/sdr 603 * values can be retrieved via {@link Display#getHdrSdrRatio()}. 604 * 605 * Requires that {@link Display#isHdrSdrRatioAvailable()} is true. 606 * 607 * @see #registerDisplayListener(DisplayListener, Handler, long) 608 * 609 * @hide 610 */ 611 public static final long EVENT_FLAG_HDR_SDR_RATIO_CHANGED = 1L << 4; 612 613 /** @hide */ DisplayManager(Context context)614 public DisplayManager(Context context) { 615 mContext = context; 616 mGlobal = DisplayManagerGlobal.getInstance(); 617 } 618 619 /** 620 * Gets information about a logical display. 621 * 622 * The display metrics may be adjusted to provide compatibility 623 * for legacy applications. 624 * 625 * @param displayId The logical display id. 626 * @return The display object, or null if there is no valid display with the given id. 627 */ getDisplay(int displayId)628 public Display getDisplay(int displayId) { 629 return getOrCreateDisplay(displayId, false /*assumeValid*/); 630 } 631 632 /** 633 * Gets all currently valid logical displays. 634 * 635 * @return An array containing all displays. 636 */ getDisplays()637 public Display[] getDisplays() { 638 return getDisplays(null); 639 } 640 641 /** 642 * Gets all currently valid logical displays of the specified category. 643 * <p> 644 * When there are multiple displays in a category the returned displays are sorted 645 * of preference. For example, if the requested category is 646 * {@link #DISPLAY_CATEGORY_PRESENTATION} and there are multiple presentation displays 647 * then the displays are sorted so that the first display in the returned array 648 * is the most preferred presentation display. The application may simply 649 * use the first display or allow the user to choose. 650 * </p> 651 * 652 * @param category The requested display category or null to return all displays. 653 * @return An array containing all displays sorted by order of preference. 654 * 655 * @see #DISPLAY_CATEGORY_PRESENTATION 656 */ getDisplays(String category)657 public Display[] getDisplays(String category) { 658 boolean includeDisabled = (category != null 659 && category.equals(DISPLAY_CATEGORY_ALL_INCLUDING_DISABLED)); 660 final int[] displayIds = mGlobal.getDisplayIds(includeDisabled); 661 if (DISPLAY_CATEGORY_PRESENTATION.equals(category)) { 662 return getDisplays(displayIds, DisplayManager::isPresentationDisplay); 663 } else if (DISPLAY_CATEGORY_REAR.equals(category)) { 664 return getDisplays(displayIds, DisplayManager::isRearDisplay); 665 } else if (category == null || DISPLAY_CATEGORY_ALL_INCLUDING_DISABLED.equals(category)) { 666 return getDisplays(displayIds, Objects::nonNull); 667 } 668 return new Display[0]; 669 } 670 getDisplays(int[] displayIds, Predicate<Display> predicate)671 private Display[] getDisplays(int[] displayIds, Predicate<Display> predicate) { 672 ArrayList<Display> tmpDisplays = new ArrayList<>(); 673 for (int displayId : displayIds) { 674 Display display = getOrCreateDisplay(displayId, /*assumeValid=*/true); 675 if (predicate.test(display)) { 676 tmpDisplays.add(display); 677 } 678 } 679 return tmpDisplays.toArray(new Display[tmpDisplays.size()]); 680 } 681 isPresentationDisplay(@ullable Display display)682 private static boolean isPresentationDisplay(@Nullable Display display) { 683 if (display == null || (display.getDisplayId() == DEFAULT_DISPLAY) 684 || (display.getFlags() & Display.FLAG_PRESENTATION) == 0) { 685 return false; 686 } 687 switch (display.getType()) { 688 case Display.TYPE_INTERNAL: 689 case Display.TYPE_EXTERNAL: 690 case Display.TYPE_WIFI: 691 case Display.TYPE_OVERLAY: 692 case Display.TYPE_VIRTUAL: 693 return true; 694 default: 695 return false; 696 } 697 } 698 isRearDisplay(@ullable Display display)699 private static boolean isRearDisplay(@Nullable Display display) { 700 return display != null && display.getDisplayId() != DEFAULT_DISPLAY 701 && display.getType() == Display.TYPE_INTERNAL 702 && (display.getFlags() & Display.FLAG_REAR) != 0; 703 } 704 getOrCreateDisplay(int displayId, boolean assumeValid)705 private Display getOrCreateDisplay(int displayId, boolean assumeValid) { 706 Display display; 707 synchronized (mLock) { 708 display = mDisplayCache.get(displayId); 709 if (display == null) { 710 // TODO: We cannot currently provide any override configurations for metrics on 711 // displays other than the display the context is associated with. 712 final Resources resources = mContext.getDisplayId() == displayId 713 ? mContext.getResources() : null; 714 715 display = mGlobal.getCompatibleDisplay(displayId, resources); 716 if (display != null) { 717 mDisplayCache.put(display); 718 } 719 } else if (!assumeValid && !display.isValid()) { 720 display = null; 721 } 722 } 723 return display; 724 } 725 726 /** 727 * Registers a display listener to receive notifications about when 728 * displays are added, removed or changed. 729 * 730 * @param listener The listener to register. 731 * @param handler The handler on which the listener should be invoked, or null 732 * if the listener should be invoked on the calling thread's looper. 733 * 734 * @see #unregisterDisplayListener 735 */ registerDisplayListener(DisplayListener listener, Handler handler)736 public void registerDisplayListener(DisplayListener listener, Handler handler) { 737 registerDisplayListener(listener, handler, EVENT_FLAG_DISPLAY_ADDED 738 | EVENT_FLAG_DISPLAY_CHANGED | EVENT_FLAG_DISPLAY_REMOVED); 739 } 740 741 /** 742 * Registers a display listener to receive notifications about given display event types. 743 * 744 * @param listener The listener to register. 745 * @param handler The handler on which the listener should be invoked, or null 746 * if the listener should be invoked on the calling thread's looper. 747 * @param eventsMask A bitmask of the event types for which this listener is subscribed. 748 * 749 * @see #EVENT_FLAG_DISPLAY_ADDED 750 * @see #EVENT_FLAG_DISPLAY_CHANGED 751 * @see #EVENT_FLAG_DISPLAY_REMOVED 752 * @see #EVENT_FLAG_DISPLAY_BRIGHTNESS 753 * @see #registerDisplayListener(DisplayListener, Handler) 754 * @see #unregisterDisplayListener 755 * 756 * @hide 757 */ registerDisplayListener(@onNull DisplayListener listener, @Nullable Handler handler, @EventsMask long eventsMask)758 public void registerDisplayListener(@NonNull DisplayListener listener, 759 @Nullable Handler handler, @EventsMask long eventsMask) { 760 mGlobal.registerDisplayListener(listener, handler, eventsMask); 761 } 762 763 /** 764 * Unregisters a display listener. 765 * 766 * @param listener The listener to unregister. 767 * 768 * @see #registerDisplayListener 769 */ unregisterDisplayListener(DisplayListener listener)770 public void unregisterDisplayListener(DisplayListener listener) { 771 mGlobal.unregisterDisplayListener(listener); 772 } 773 774 /** 775 * Starts scanning for available Wifi displays. 776 * The results are sent as a {@link #ACTION_WIFI_DISPLAY_STATUS_CHANGED} broadcast. 777 * <p> 778 * Calls to this method nest and must be matched by an equal number of calls to 779 * {@link #stopWifiDisplayScan()}. 780 * </p><p> 781 * Requires {@link android.Manifest.permission#CONFIGURE_WIFI_DISPLAY}. 782 * </p> 783 * 784 * @hide 785 */ 786 @UnsupportedAppUsage startWifiDisplayScan()787 public void startWifiDisplayScan() { 788 mGlobal.startWifiDisplayScan(); 789 } 790 791 /** 792 * Stops scanning for available Wifi displays. 793 * <p> 794 * Requires {@link android.Manifest.permission#CONFIGURE_WIFI_DISPLAY}. 795 * </p> 796 * 797 * @hide 798 */ 799 @UnsupportedAppUsage stopWifiDisplayScan()800 public void stopWifiDisplayScan() { 801 mGlobal.stopWifiDisplayScan(); 802 } 803 804 /** 805 * Connects to a Wifi display. 806 * The results are sent as a {@link #ACTION_WIFI_DISPLAY_STATUS_CHANGED} broadcast. 807 * <p> 808 * Automatically remembers the display after a successful connection, if not 809 * already remembered. 810 * </p><p> 811 * Requires {@link android.Manifest.permission#CONFIGURE_WIFI_DISPLAY}. 812 * </p> 813 * 814 * @param deviceAddress The MAC address of the device to which we should connect. 815 * @hide 816 */ 817 @UnsupportedAppUsage connectWifiDisplay(String deviceAddress)818 public void connectWifiDisplay(String deviceAddress) { 819 mGlobal.connectWifiDisplay(deviceAddress); 820 } 821 822 /** @hide */ 823 @UnsupportedAppUsage pauseWifiDisplay()824 public void pauseWifiDisplay() { 825 mGlobal.pauseWifiDisplay(); 826 } 827 828 /** @hide */ 829 @UnsupportedAppUsage resumeWifiDisplay()830 public void resumeWifiDisplay() { 831 mGlobal.resumeWifiDisplay(); 832 } 833 834 /** 835 * Disconnects from the current Wifi display. 836 * The results are sent as a {@link #ACTION_WIFI_DISPLAY_STATUS_CHANGED} broadcast. 837 * @hide 838 */ 839 @UnsupportedAppUsage disconnectWifiDisplay()840 public void disconnectWifiDisplay() { 841 mGlobal.disconnectWifiDisplay(); 842 } 843 844 /** 845 * Renames a Wifi display. 846 * <p> 847 * The display must already be remembered for this call to succeed. In other words, 848 * we must already have successfully connected to the display at least once and then 849 * not forgotten it. 850 * </p><p> 851 * Requires {@link android.Manifest.permission#CONFIGURE_WIFI_DISPLAY}. 852 * </p> 853 * 854 * @param deviceAddress The MAC address of the device to rename. 855 * @param alias The alias name by which to remember the device, or null 856 * or empty if no alias should be used. 857 * @hide 858 */ 859 @UnsupportedAppUsage renameWifiDisplay(String deviceAddress, String alias)860 public void renameWifiDisplay(String deviceAddress, String alias) { 861 mGlobal.renameWifiDisplay(deviceAddress, alias); 862 } 863 864 /** 865 * Forgets a previously remembered Wifi display. 866 * <p> 867 * Automatically disconnects from the display if currently connected to it. 868 * </p><p> 869 * Requires {@link android.Manifest.permission#CONFIGURE_WIFI_DISPLAY}. 870 * </p> 871 * 872 * @param deviceAddress The MAC address of the device to forget. 873 * @hide 874 */ 875 @UnsupportedAppUsage forgetWifiDisplay(String deviceAddress)876 public void forgetWifiDisplay(String deviceAddress) { 877 mGlobal.forgetWifiDisplay(deviceAddress); 878 } 879 880 /** 881 * Gets the current Wifi display status. 882 * Watch for changes in the status by registering a broadcast receiver for 883 * {@link #ACTION_WIFI_DISPLAY_STATUS_CHANGED}. 884 * 885 * @return The current Wifi display status. 886 * @hide 887 */ 888 @UnsupportedAppUsage getWifiDisplayStatus()889 public WifiDisplayStatus getWifiDisplayStatus() { 890 return mGlobal.getWifiDisplayStatus(); 891 } 892 893 /** 894 * Set the level of color saturation to apply to the display. 895 * @param level The amount of saturation to apply, between 0 and 1 inclusive. 896 * 0 produces a grayscale image, 1 is normal. 897 * 898 * @hide 899 * @deprecated use {@link ColorDisplayManager#setSaturationLevel(int)} instead. The level passed 900 * as a parameter here will be rounded to the nearest hundredth. 901 */ 902 @SystemApi 903 @RequiresPermission(Manifest.permission.CONTROL_DISPLAY_SATURATION) setSaturationLevel(float level)904 public void setSaturationLevel(float level) { 905 if (level < 0f || level > 1f) { 906 throw new IllegalArgumentException("Saturation level must be between 0 and 1"); 907 } 908 final ColorDisplayManager cdm = mContext.getSystemService(ColorDisplayManager.class); 909 cdm.setSaturationLevel(Math.round(level * 100f)); 910 } 911 912 /** 913 * Sets the HDR types that have been disabled by user. 914 * @param userDisabledTypes the HDR types to disable. 915 * @hide 916 */ 917 @TestApi 918 @RequiresPermission(Manifest.permission.WRITE_SECURE_SETTINGS) setUserDisabledHdrTypes(@onNull @drType int[] userDisabledTypes)919 public void setUserDisabledHdrTypes(@NonNull @HdrType int[] userDisabledTypes) { 920 mGlobal.setUserDisabledHdrTypes(userDisabledTypes); 921 } 922 923 /** 924 * Sets whether or not the user disabled HDR types are returned from 925 * {@link Display#getHdrCapabilities}. 926 * 927 * @param areUserDisabledHdrTypesAllowed If true, the user-disabled types 928 * are ignored and returned, if the display supports them. If false, the 929 * user-disabled types are taken into consideration and are never returned, 930 * even if the display supports them. 931 * @hide 932 */ 933 @TestApi 934 @RequiresPermission(Manifest.permission.WRITE_SECURE_SETTINGS) setAreUserDisabledHdrTypesAllowed(boolean areUserDisabledHdrTypesAllowed)935 public void setAreUserDisabledHdrTypesAllowed(boolean areUserDisabledHdrTypesAllowed) { 936 mGlobal.setAreUserDisabledHdrTypesAllowed(areUserDisabledHdrTypesAllowed); 937 } 938 939 /** 940 * Returns whether or not the user-disabled HDR types are returned from 941 * {@link Display#getHdrCapabilities}. 942 * 943 * @hide 944 */ 945 @TestApi areUserDisabledHdrTypesAllowed()946 public boolean areUserDisabledHdrTypesAllowed() { 947 return mGlobal.areUserDisabledHdrTypesAllowed(); 948 } 949 950 /** 951 * Returns the HDR formats disabled by the user. 952 * 953 * @hide 954 */ 955 @TestApi getUserDisabledHdrTypes()956 public @NonNull int[] getUserDisabledHdrTypes() { 957 return mGlobal.getUserDisabledHdrTypes(); 958 } 959 960 /** 961 * Overrides HDR modes for a display device. 962 * 963 * @hide 964 */ 965 @RequiresPermission(Manifest.permission.ACCESS_SURFACE_FLINGER) 966 @TestApi overrideHdrTypes(int displayId, @NonNull int[] modes)967 public void overrideHdrTypes(int displayId, @NonNull int[] modes) { 968 mGlobal.overrideHdrTypes(displayId, modes); 969 } 970 971 /** 972 * Creates a virtual display. 973 * 974 * @see #createVirtualDisplay(String, int, int, int, Surface, int, 975 * VirtualDisplay.Callback, Handler) 976 */ createVirtualDisplay(@onNull String name, @IntRange(from = 1) int width, @IntRange(from = 1) int height, @IntRange(from = 1) int densityDpi, @Nullable Surface surface, @VirtualDisplayFlag int flags)977 public VirtualDisplay createVirtualDisplay(@NonNull String name, 978 @IntRange(from = 1) int width, 979 @IntRange(from = 1) int height, 980 @IntRange(from = 1) int densityDpi, 981 @Nullable Surface surface, 982 @VirtualDisplayFlag int flags) { 983 return createVirtualDisplay(name, width, height, densityDpi, surface, flags, null, null); 984 } 985 986 /** 987 * Creates a virtual display. 988 * <p> 989 * The content of a virtual display is rendered to a {@link Surface} provided 990 * by the application. 991 * </p><p> 992 * The virtual display should be {@link VirtualDisplay#release released} 993 * when no longer needed. Because a virtual display renders to a surface 994 * provided by the application, it will be released automatically when the 995 * process terminates and all remaining windows on it will be forcibly removed. 996 * </p><p> 997 * The behavior of the virtual display depends on the flags that are provided 998 * to this method. By default, virtual displays are created to be private, 999 * non-presentation and unsecure. Permissions may be required to use certain flags. 1000 * </p><p> 1001 * As of {@link android.os.Build.VERSION_CODES#KITKAT_WATCH}, the surface may 1002 * be attached or detached dynamically using {@link VirtualDisplay#setSurface}. 1003 * Previously, the surface had to be non-null when {@link #createVirtualDisplay} 1004 * was called and could not be changed for the lifetime of the display. 1005 * </p><p> 1006 * Detaching the surface that backs a virtual display has a similar effect to 1007 * turning off the screen. 1008 * </p> 1009 * 1010 * @param name The name of the virtual display, must be non-empty. 1011 * @param width The width of the virtual display in pixels, must be greater than 0. 1012 * @param height The height of the virtual display in pixels, must be greater than 0. 1013 * @param densityDpi The density of the virtual display in dpi, must be greater than 0. 1014 * @param surface The surface to which the content of the virtual display should 1015 * be rendered, or null if there is none initially. 1016 * @param flags A combination of virtual display flags: 1017 * {@link #VIRTUAL_DISPLAY_FLAG_PUBLIC}, {@link #VIRTUAL_DISPLAY_FLAG_PRESENTATION}, 1018 * {@link #VIRTUAL_DISPLAY_FLAG_SECURE}, {@link #VIRTUAL_DISPLAY_FLAG_OWN_CONTENT_ONLY}, 1019 * or {@link #VIRTUAL_DISPLAY_FLAG_AUTO_MIRROR}. 1020 * @param callback Callback to call when the state of the {@link VirtualDisplay} changes 1021 * @param handler The handler on which the listener should be invoked, or null 1022 * if the listener should be invoked on the calling thread's looper. 1023 * @return The newly created virtual display, or null if the application could 1024 * not create the virtual display. 1025 * 1026 * @throws SecurityException if the caller does not have permission to create 1027 * a virtual display with the specified flags. 1028 */ createVirtualDisplay(@onNull String name, @IntRange(from = 1) int width, @IntRange(from = 1) int height, @IntRange(from = 1) int densityDpi, @Nullable Surface surface, @VirtualDisplayFlag int flags, @Nullable VirtualDisplay.Callback callback, @Nullable Handler handler)1029 public VirtualDisplay createVirtualDisplay(@NonNull String name, 1030 @IntRange(from = 1) int width, 1031 @IntRange(from = 1) int height, 1032 @IntRange(from = 1) int densityDpi, 1033 @Nullable Surface surface, 1034 @VirtualDisplayFlag int flags, 1035 @Nullable VirtualDisplay.Callback callback, 1036 @Nullable Handler handler) { 1037 final VirtualDisplayConfig.Builder builder = 1038 new VirtualDisplayConfig.Builder(name, width, height, densityDpi); 1039 builder.setFlags(flags); 1040 if (surface != null) { 1041 builder.setSurface(surface); 1042 } 1043 return createVirtualDisplay(builder.build(), handler, callback); 1044 } 1045 1046 /** 1047 * Creates a virtual display. 1048 * 1049 * @see #createVirtualDisplay(VirtualDisplayConfig, Handler, VirtualDisplay.Callback) 1050 */ 1051 @Nullable createVirtualDisplay(@onNull VirtualDisplayConfig config)1052 public VirtualDisplay createVirtualDisplay(@NonNull VirtualDisplayConfig config) { 1053 return createVirtualDisplay(config, /*handler=*/null, /*callback=*/null); 1054 } 1055 1056 /** 1057 * Creates a virtual display. 1058 * <p> 1059 * The content of a virtual display is rendered to a {@link Surface} provided 1060 * by the application. 1061 * </p><p> 1062 * The virtual display should be {@link VirtualDisplay#release released} 1063 * when no longer needed. Because a virtual display renders to a surface 1064 * provided by the application, it will be released automatically when the 1065 * process terminates and all remaining windows on it will be forcibly removed. 1066 * </p><p> 1067 * The behavior of the virtual display depends on the flags that are provided 1068 * to this method. By default, virtual displays are created to be private, 1069 * non-presentation and unsecure. Permissions may be required to use certain flags. 1070 * </p><p> 1071 * As of {@link android.os.Build.VERSION_CODES#KITKAT_WATCH}, the surface may 1072 * be attached or detached dynamically using {@link VirtualDisplay#setSurface}. 1073 * Previously, the surface had to be non-null when {@link #createVirtualDisplay} 1074 * was called and could not be changed for the lifetime of the display. 1075 * </p><p> 1076 * Detaching the surface that backs a virtual display has a similar effect to 1077 * turning off the screen. 1078 * </p> 1079 * 1080 * @param config The configuration of the virtual display, must be non-null. 1081 * @param handler The handler on which the listener should be invoked, or null 1082 * if the listener should be invoked on the calling thread's looper. 1083 * @param callback Callback to call when the state of the {@link VirtualDisplay} changes 1084 * @return The newly created virtual display, or null if the application could 1085 * not create the virtual display. 1086 * 1087 * @throws SecurityException if the caller does not have permission to create 1088 * a virtual display with flags specified in the configuration. 1089 */ 1090 @Nullable createVirtualDisplay( @onNull VirtualDisplayConfig config, @Nullable Handler handler, @Nullable VirtualDisplay.Callback callback)1091 public VirtualDisplay createVirtualDisplay( 1092 @NonNull VirtualDisplayConfig config, 1093 @Nullable Handler handler, 1094 @Nullable VirtualDisplay.Callback callback) { 1095 return createVirtualDisplay(null /* projection */, config, callback, handler); 1096 } 1097 1098 // TODO : Remove this hidden API after remove all callers. (Refer to MultiDisplayService) 1099 /** @hide */ createVirtualDisplay( @ullable MediaProjection projection, @NonNull String name, @IntRange(from = 1) int width, @IntRange(from = 1) int height, @IntRange(from = 1) int densityDpi, @Nullable Surface surface, @VirtualDisplayFlag int flags, @Nullable VirtualDisplay.Callback callback, @Nullable Handler handler, @Nullable String uniqueId)1100 public VirtualDisplay createVirtualDisplay( 1101 @Nullable MediaProjection projection, 1102 @NonNull String name, 1103 @IntRange(from = 1) int width, 1104 @IntRange(from = 1) int height, 1105 @IntRange(from = 1) int densityDpi, 1106 @Nullable Surface surface, 1107 @VirtualDisplayFlag int flags, 1108 @Nullable VirtualDisplay.Callback callback, 1109 @Nullable Handler handler, 1110 @Nullable String uniqueId) { 1111 final VirtualDisplayConfig.Builder builder = new VirtualDisplayConfig.Builder(name, width, 1112 height, densityDpi); 1113 builder.setFlags(flags); 1114 if (uniqueId != null) { 1115 builder.setUniqueId(uniqueId); 1116 } 1117 if (surface != null) { 1118 builder.setSurface(surface); 1119 } 1120 return createVirtualDisplay(projection, builder.build(), callback, handler); 1121 } 1122 1123 /** @hide */ createVirtualDisplay(@ullable MediaProjection projection, @NonNull VirtualDisplayConfig virtualDisplayConfig, @Nullable VirtualDisplay.Callback callback, @Nullable Handler handler)1124 public VirtualDisplay createVirtualDisplay(@Nullable MediaProjection projection, 1125 @NonNull VirtualDisplayConfig virtualDisplayConfig, 1126 @Nullable VirtualDisplay.Callback callback, @Nullable Handler handler) { 1127 Executor executor = null; 1128 // If callback is null, the executor will not be used. Avoid creating the handler and the 1129 // handler executor. 1130 if (callback != null) { 1131 executor = new HandlerExecutor( 1132 Handler.createAsync(handler != null ? handler.getLooper() : Looper.myLooper())); 1133 } 1134 return mGlobal.createVirtualDisplay(mContext, projection, virtualDisplayConfig, callback, 1135 executor); 1136 } 1137 1138 /** 1139 * Gets the stable device display size, in pixels. 1140 * 1141 * This should really only be used for things like server-side filtering of available 1142 * applications. Most applications don't need the level of stability guaranteed by this and 1143 * should instead query either the size of the display they're currently running on or the 1144 * size of the default display. 1145 * @hide 1146 */ 1147 @SystemApi getStableDisplaySize()1148 public Point getStableDisplaySize() { 1149 return mGlobal.getStableDisplaySize(); 1150 } 1151 1152 /** 1153 * Fetch {@link BrightnessChangeEvent}s. 1154 * @hide until we make it a system api. 1155 */ 1156 @SystemApi 1157 @RequiresPermission(Manifest.permission.BRIGHTNESS_SLIDER_USAGE) getBrightnessEvents()1158 public List<BrightnessChangeEvent> getBrightnessEvents() { 1159 return mGlobal.getBrightnessEvents(mContext.getOpPackageName()); 1160 } 1161 1162 /** 1163 * Fetch {@link AmbientBrightnessDayStats}s. 1164 * 1165 * @hide until we make it a system api 1166 */ 1167 @SystemApi 1168 @RequiresPermission(Manifest.permission.ACCESS_AMBIENT_LIGHT_STATS) getAmbientBrightnessStats()1169 public List<AmbientBrightnessDayStats> getAmbientBrightnessStats() { 1170 return mGlobal.getAmbientBrightnessStats(); 1171 } 1172 1173 /** 1174 * Sets the global display brightness configuration. 1175 * 1176 * @hide 1177 */ 1178 @SystemApi 1179 @RequiresPermission(Manifest.permission.CONFIGURE_DISPLAY_BRIGHTNESS) setBrightnessConfiguration(BrightnessConfiguration c)1180 public void setBrightnessConfiguration(BrightnessConfiguration c) { 1181 setBrightnessConfigurationForUser(c, mContext.getUserId(), mContext.getPackageName()); 1182 } 1183 1184 /** 1185 * Sets the brightness configuration for the specified display. 1186 * If the specified display doesn't exist, then this will return and do nothing. 1187 * 1188 * @hide 1189 */ 1190 @SystemApi 1191 @RequiresPermission(Manifest.permission.CONFIGURE_DISPLAY_BRIGHTNESS) setBrightnessConfigurationForDisplay(@onNull BrightnessConfiguration c, @NonNull String uniqueId)1192 public void setBrightnessConfigurationForDisplay(@NonNull BrightnessConfiguration c, 1193 @NonNull String uniqueId) { 1194 mGlobal.setBrightnessConfigurationForDisplay(c, uniqueId, mContext.getUserId(), 1195 mContext.getPackageName()); 1196 } 1197 1198 /** 1199 * Gets the brightness configuration for the specified display and default user. 1200 * Returns the default configuration if unset or display is invalid. 1201 * 1202 * @hide 1203 */ 1204 @Nullable 1205 @SystemApi 1206 @RequiresPermission(Manifest.permission.CONFIGURE_DISPLAY_BRIGHTNESS) getBrightnessConfigurationForDisplay( @onNull String uniqueId)1207 public BrightnessConfiguration getBrightnessConfigurationForDisplay( 1208 @NonNull String uniqueId) { 1209 return mGlobal.getBrightnessConfigurationForDisplay(uniqueId, mContext.getUserId()); 1210 } 1211 1212 /** 1213 * Sets the global display brightness configuration for a specific user. 1214 * 1215 * Note this requires the INTERACT_ACROSS_USERS permission if setting the configuration for a 1216 * user other than the one you're currently running as. 1217 * 1218 * @hide 1219 */ setBrightnessConfigurationForUser(BrightnessConfiguration c, int userId, String packageName)1220 public void setBrightnessConfigurationForUser(BrightnessConfiguration c, int userId, 1221 String packageName) { 1222 mGlobal.setBrightnessConfigurationForUser(c, userId, packageName); 1223 } 1224 1225 /** 1226 * Gets the global display brightness configuration or the default curve if one hasn't been set. 1227 * 1228 * @hide 1229 */ 1230 @SystemApi 1231 @RequiresPermission(Manifest.permission.CONFIGURE_DISPLAY_BRIGHTNESS) getBrightnessConfiguration()1232 public BrightnessConfiguration getBrightnessConfiguration() { 1233 return getBrightnessConfigurationForUser(mContext.getUserId()); 1234 } 1235 1236 /** 1237 * Gets the global display brightness configuration or the default curve if one hasn't been set 1238 * for a specific user. 1239 * 1240 * Note this requires the INTERACT_ACROSS_USERS permission if getting the configuration for a 1241 * user other than the one you're currently running as. 1242 * 1243 * @hide 1244 */ getBrightnessConfigurationForUser(int userId)1245 public BrightnessConfiguration getBrightnessConfigurationForUser(int userId) { 1246 return mGlobal.getBrightnessConfigurationForUser(userId); 1247 } 1248 1249 /** 1250 * Gets the default global display brightness configuration or null one hasn't 1251 * been configured. 1252 * 1253 * @hide 1254 */ 1255 @SystemApi 1256 @RequiresPermission(Manifest.permission.CONFIGURE_DISPLAY_BRIGHTNESS) 1257 @Nullable getDefaultBrightnessConfiguration()1258 public BrightnessConfiguration getDefaultBrightnessConfiguration() { 1259 return mGlobal.getDefaultBrightnessConfiguration(); 1260 } 1261 1262 1263 /** 1264 * Gets the last requested minimal post processing setting for the display with displayId. 1265 * 1266 * @hide 1267 */ 1268 @TestApi isMinimalPostProcessingRequested(int displayId)1269 public boolean isMinimalPostProcessingRequested(int displayId) { 1270 return mGlobal.isMinimalPostProcessingRequested(displayId); 1271 } 1272 1273 /** 1274 * Temporarily sets the brightness of the display. 1275 * <p> 1276 * Requires the {@link android.Manifest.permission#CONTROL_DISPLAY_BRIGHTNESS} permission. 1277 * </p> 1278 * 1279 * @param brightness The brightness value from 0.0f to 1.0f. 1280 * 1281 * @hide Requires signature permission. 1282 */ setTemporaryBrightness(int displayId, float brightness)1283 public void setTemporaryBrightness(int displayId, float brightness) { 1284 mGlobal.setTemporaryBrightness(displayId, brightness); 1285 } 1286 1287 1288 /** 1289 * Sets the brightness of the specified display. 1290 * <p> 1291 * Requires the {@link android.Manifest.permission#CONTROL_DISPLAY_BRIGHTNESS} 1292 * permission. 1293 * </p> 1294 * 1295 * @param displayId the logical display id 1296 * @param brightness The brightness value from 0.0f to 1.0f. 1297 * 1298 * @hide 1299 */ 1300 @RequiresPermission(Manifest.permission.CONTROL_DISPLAY_BRIGHTNESS) setBrightness(int displayId, @FloatRange(from = 0f, to = 1f) float brightness)1301 public void setBrightness(int displayId, @FloatRange(from = 0f, to = 1f) float brightness) { 1302 mGlobal.setBrightness(displayId, brightness); 1303 } 1304 1305 1306 /** 1307 * Gets the brightness of the specified display. 1308 * <p> 1309 * Requires the {@link android.Manifest.permission#CONTROL_DISPLAY_BRIGHTNESS} 1310 * permission. 1311 * </p> 1312 * 1313 * @param displayId The display of which brightness value to get from. 1314 * 1315 * @hide 1316 */ 1317 @RequiresPermission(Manifest.permission.CONTROL_DISPLAY_BRIGHTNESS) 1318 @FloatRange(from = 0f, to = 1f) getBrightness(int displayId)1319 public float getBrightness(int displayId) { 1320 return mGlobal.getBrightness(displayId); 1321 } 1322 1323 1324 /** 1325 * Temporarily sets the auto brightness adjustment factor. 1326 * <p> 1327 * Requires the {@link android.Manifest.permission#CONTROL_DISPLAY_BRIGHTNESS} permission. 1328 * </p> 1329 * 1330 * @param adjustment The adjustment factor from -1.0 to 1.0. 1331 * 1332 * @hide Requires signature permission. 1333 */ setTemporaryAutoBrightnessAdjustment(float adjustment)1334 public void setTemporaryAutoBrightnessAdjustment(float adjustment) { 1335 mGlobal.setTemporaryAutoBrightnessAdjustment(adjustment); 1336 } 1337 1338 /** 1339 * Returns the minimum brightness curve, which guarantess that any brightness curve that dips 1340 * below it is rejected by the system. 1341 * This prevent auto-brightness from setting the screen so dark as to prevent the user from 1342 * resetting or disabling it, and maps lux to the absolute minimum nits that are still readable 1343 * in that ambient brightness. 1344 * 1345 * @return The minimum brightness curve (as lux values and their corresponding nits values). 1346 * 1347 * @hide 1348 */ 1349 @SystemApi getMinimumBrightnessCurve()1350 public Pair<float[], float[]> getMinimumBrightnessCurve() { 1351 return mGlobal.getMinimumBrightnessCurve(); 1352 } 1353 1354 /** 1355 * Sets the global default {@link Display.Mode}. The display mode includes preference for 1356 * resolution and refresh rate. The mode change is applied globally, i.e. to all the connected 1357 * displays. If the mode specified is not supported by a connected display, then no mode change 1358 * occurs for that display. 1359 * 1360 * @param mode The {@link Display.Mode} to set, which can include resolution and/or 1361 * refresh-rate. It is created using {@link Display.Mode.Builder}. 1362 *` 1363 * @hide 1364 */ 1365 @TestApi 1366 @RequiresPermission(Manifest.permission.MODIFY_USER_PREFERRED_DISPLAY_MODE) setGlobalUserPreferredDisplayMode(@onNull Display.Mode mode)1367 public void setGlobalUserPreferredDisplayMode(@NonNull Display.Mode mode) { 1368 // Create a new object containing default values for the unused fields like mode ID and 1369 // alternative refresh rates. 1370 Display.Mode preferredMode = new Display.Mode(mode.getPhysicalWidth(), 1371 mode.getPhysicalHeight(), mode.getRefreshRate()); 1372 mGlobal.setUserPreferredDisplayMode(Display.INVALID_DISPLAY, preferredMode); 1373 } 1374 1375 /** 1376 * Removes the global user preferred display mode. 1377 * User preferred display mode is cleared for all the connected displays. 1378 * 1379 * @hide 1380 */ 1381 @TestApi 1382 @RequiresPermission(Manifest.permission.MODIFY_USER_PREFERRED_DISPLAY_MODE) clearGlobalUserPreferredDisplayMode()1383 public void clearGlobalUserPreferredDisplayMode() { 1384 mGlobal.setUserPreferredDisplayMode(Display.INVALID_DISPLAY, null); 1385 } 1386 1387 /** 1388 * Returns the global user preferred display mode. 1389 * If no user preferred mode has been set, or it has been cleared, this method returns null. 1390 * 1391 * @hide 1392 */ 1393 @TestApi 1394 @Nullable getGlobalUserPreferredDisplayMode()1395 public Display.Mode getGlobalUserPreferredDisplayMode() { 1396 return mGlobal.getUserPreferredDisplayMode(Display.INVALID_DISPLAY); 1397 } 1398 1399 /** 1400 * Sets the HDR conversion mode for the device. 1401 * 1402 * @param hdrConversionMode The {@link HdrConversionMode} to set. 1403 * Note, {@code HdrConversionMode.preferredHdrOutputType} is only applicable when 1404 * {@code HdrConversionMode.conversionMode} is {@link HdrConversionMode#HDR_CONVERSION_FORCE}. 1405 * If {@code HdrConversionMode.preferredHdrOutputType} is not set in case when 1406 * {@code HdrConversionMode.conversionMode} is {@link HdrConversionMode#HDR_CONVERSION_FORCE}, 1407 * it means that preferred output type is SDR. 1408 * 1409 * @throws IllegalArgumentException if hdrConversionMode.preferredHdrOutputType is set but 1410 * hdrConversionMode.conversionMode is not {@link HdrConversionMode#HDR_CONVERSION_FORCE}. 1411 * 1412 * @see #getHdrConversionMode 1413 * @see #getHdrConversionModeSetting 1414 * @see #getSupportedHdrOutputTypes 1415 * @hide 1416 */ 1417 @TestApi 1418 @RequiresPermission(Manifest.permission.MODIFY_HDR_CONVERSION_MODE) setHdrConversionMode(@onNull HdrConversionMode hdrConversionMode)1419 public void setHdrConversionMode(@NonNull HdrConversionMode hdrConversionMode) { 1420 mGlobal.setHdrConversionMode(hdrConversionMode); 1421 } 1422 1423 /** 1424 * Returns the {@link HdrConversionMode} of the device, which is set by the user. 1425 * 1426 * When {@link HdrConversionMode#getConversionMode} is 1427 * {@link HdrConversionMode#HDR_CONVERSION_SYSTEM}, the 1428 * {@link HdrConversionMode#getPreferredHdrOutputType} depicts the systemPreferredHdrOutputType. 1429 * The HDR conversion mode chosen by user which considers the app override is returned. Apps can 1430 * override HDR conversion using 1431 * {@link android.view.WindowManager.LayoutParams#setHdrConversionEnabled(boolean)}. 1432 */ 1433 @NonNull getHdrConversionMode()1434 public HdrConversionMode getHdrConversionMode() { 1435 return mGlobal.getHdrConversionMode(); 1436 } 1437 1438 /** 1439 * Returns the {@link HdrConversionMode} of the device, which is set by the user. 1440 1441 * The HDR conversion mode chosen by user is returned irrespective of whether HDR conversion 1442 * is disabled by an app. 1443 * 1444 * @see #setHdrConversionMode 1445 * @see #getSupportedHdrOutputTypes 1446 * @see #getHdrConversionMode 1447 * @hide 1448 */ 1449 @TestApi 1450 @NonNull getHdrConversionModeSetting()1451 public HdrConversionMode getHdrConversionModeSetting() { 1452 return mGlobal.getHdrConversionModeSetting(); 1453 } 1454 1455 /** 1456 * Returns the HDR output types supported by the device. 1457 * 1458 * @see #getHdrConversionMode 1459 * @see #setHdrConversionMode 1460 * @hide 1461 */ 1462 @TestApi 1463 @NonNull getSupportedHdrOutputTypes()1464 public @HdrType int[] getSupportedHdrOutputTypes() { 1465 return mGlobal.getSupportedHdrOutputTypes(); 1466 } 1467 1468 /** 1469 * When enabled the app requested mode is always selected regardless of user settings and 1470 * policies for low brightness, low battery, etc. 1471 * 1472 * @hide 1473 */ 1474 @TestApi 1475 @RequiresPermission(Manifest.permission.OVERRIDE_DISPLAY_MODE_REQUESTS) setShouldAlwaysRespectAppRequestedMode(boolean enabled)1476 public void setShouldAlwaysRespectAppRequestedMode(boolean enabled) { 1477 mGlobal.setShouldAlwaysRespectAppRequestedMode(enabled); 1478 } 1479 1480 /** 1481 * Returns whether we are running in a mode which always selects the app requested display mode 1482 * and ignores user settings and policies for low brightness, low battery etc. 1483 * 1484 * @hide 1485 */ 1486 @TestApi 1487 @RequiresPermission(Manifest.permission.OVERRIDE_DISPLAY_MODE_REQUESTS) shouldAlwaysRespectAppRequestedMode()1488 public boolean shouldAlwaysRespectAppRequestedMode() { 1489 return mGlobal.shouldAlwaysRespectAppRequestedMode(); 1490 } 1491 1492 /** 1493 * Returns whether device supports seamless refresh rate switching. 1494 * 1495 * Match content frame rate setting has three options: seamless, non-seamless and never. 1496 * The seamless option does nothing if the device does not support seamless refresh rate 1497 * switching. This API is used in such a case to hide the seamless option. 1498 * 1499 * @see DisplayManager#setRefreshRateSwitchingType 1500 * @see DisplayManager#getMatchContentFrameRateUserPreference 1501 * @hide 1502 */ supportsSeamlessRefreshRateSwitching()1503 public boolean supportsSeamlessRefreshRateSwitching() { 1504 return mContext.getResources().getBoolean( 1505 R.bool.config_supportsSeamlessRefreshRateSwitching); 1506 } 1507 1508 /** 1509 * Sets the refresh rate switching type. 1510 * This matches {@link android.provider.Settings.Secure.MATCH_CONTENT_FRAME_RATE} 1511 * 1512 * @hide 1513 */ 1514 @TestApi 1515 @RequiresPermission(Manifest.permission.MODIFY_REFRESH_RATE_SWITCHING_TYPE) setRefreshRateSwitchingType(@witchingType int newValue)1516 public void setRefreshRateSwitchingType(@SwitchingType int newValue) { 1517 mGlobal.setRefreshRateSwitchingType(newValue); 1518 } 1519 1520 /** 1521 * Returns the user preference for "Match content frame rate". 1522 * <p> 1523 * Never: Even if the app requests it, the device will never try to match its output to the 1524 * original frame rate of the content. 1525 * </p><p> 1526 * Seamless: If the app requests it, the device will match its output to the original frame 1527 * rate of the content, ONLY if the display can transition seamlessly. 1528 * </p><p> 1529 * Always: If the app requests it, the device will match its output to the original 1530 * frame rate of the content. This may cause the screen to go blank for a 1531 * second when exiting or entering a video playback. 1532 * </p> 1533 */ getMatchContentFrameRateUserPreference()1534 @MatchContentFrameRateType public int getMatchContentFrameRateUserPreference() { 1535 return toMatchContentFrameRateSetting(mGlobal.getRefreshRateSwitchingType()); 1536 } 1537 1538 @MatchContentFrameRateType toMatchContentFrameRateSetting(@witchingType int switchingType)1539 private int toMatchContentFrameRateSetting(@SwitchingType int switchingType) { 1540 switch (switchingType) { 1541 case SWITCHING_TYPE_NONE: 1542 return MATCH_CONTENT_FRAMERATE_NEVER; 1543 case SWITCHING_TYPE_RENDER_FRAME_RATE_ONLY: 1544 case SWITCHING_TYPE_WITHIN_GROUPS: 1545 return MATCH_CONTENT_FRAMERATE_SEAMLESSS_ONLY; 1546 case SWITCHING_TYPE_ACROSS_AND_WITHIN_GROUPS: 1547 return MATCH_CONTENT_FRAMERATE_ALWAYS; 1548 default: 1549 Slog.e(TAG, switchingType + " is not a valid value of switching type."); 1550 return MATCH_CONTENT_FRAMERATE_UNKNOWN; 1551 } 1552 } 1553 1554 /** 1555 * Creates a VirtualDisplay that will mirror the content of displayIdToMirror 1556 * @param name The name for the virtual display 1557 * @param width The initial width for the virtual display 1558 * @param height The initial height for the virtual display 1559 * @param displayIdToMirror The displayId that will be mirrored into the virtual display. 1560 * @return VirtualDisplay that can be used to update properties. 1561 * 1562 * @hide 1563 */ 1564 @RequiresPermission(Manifest.permission.CAPTURE_VIDEO_OUTPUT) 1565 @Nullable 1566 @SystemApi createVirtualDisplay(@onNull String name, int width, int height, int displayIdToMirror, @Nullable Surface surface)1567 public static VirtualDisplay createVirtualDisplay(@NonNull String name, int width, int height, 1568 int displayIdToMirror, @Nullable Surface surface) { 1569 IDisplayManager sDm = IDisplayManager.Stub.asInterface( 1570 ServiceManager.getService(Context.DISPLAY_SERVICE)); 1571 IPackageManager sPackageManager = IPackageManager.Stub.asInterface( 1572 ServiceManager.getService("package")); 1573 1574 // Density doesn't matter since this virtual display is only used for mirroring. 1575 VirtualDisplayConfig.Builder builder = new VirtualDisplayConfig.Builder(name, width, 1576 height, 1 /* densityDpi */) 1577 .setFlags(VIRTUAL_DISPLAY_FLAG_AUTO_MIRROR) 1578 .setDisplayIdToMirror(displayIdToMirror); 1579 if (surface != null) { 1580 builder.setSurface(surface); 1581 } 1582 VirtualDisplayConfig virtualDisplayConfig = builder.build(); 1583 1584 String[] packages; 1585 try { 1586 packages = sPackageManager.getPackagesForUid(Process.myUid()); 1587 } catch (RemoteException ex) { 1588 throw ex.rethrowFromSystemServer(); 1589 } 1590 1591 // Just use the first one since it just needs to match the package when looking it up by 1592 // calling UID in system server. 1593 // The call may come from a rooted device, in that case the requesting uid will be root so 1594 // it will not have any package name 1595 String packageName = packages == null ? null : packages[0]; 1596 DisplayManagerGlobal.VirtualDisplayCallback 1597 callbackWrapper = new DisplayManagerGlobal.VirtualDisplayCallback(null, null); 1598 int displayId; 1599 try { 1600 displayId = sDm.createVirtualDisplay(virtualDisplayConfig, callbackWrapper, null, 1601 packageName); 1602 } catch (RemoteException ex) { 1603 throw ex.rethrowFromSystemServer(); 1604 } 1605 return DisplayManagerGlobal.getInstance().createVirtualDisplayWrapper(virtualDisplayConfig, 1606 callbackWrapper, displayId); 1607 } 1608 1609 /** 1610 * Listens for changes in available display devices. 1611 */ 1612 public interface DisplayListener { 1613 /** 1614 * Called whenever a logical display has been added to the system. 1615 * Use {@link DisplayManager#getDisplay} to get more information about 1616 * the display. 1617 * 1618 * @param displayId The id of the logical display that was added. 1619 */ onDisplayAdded(int displayId)1620 void onDisplayAdded(int displayId); 1621 1622 /** 1623 * Called whenever a logical display has been removed from the system. 1624 * 1625 * @param displayId The id of the logical display that was removed. 1626 */ onDisplayRemoved(int displayId)1627 void onDisplayRemoved(int displayId); 1628 1629 /** 1630 * Called whenever the properties of a logical {@link android.view.Display}, 1631 * such as size and density, have changed. 1632 * 1633 * @param displayId The id of the logical display that changed. 1634 */ onDisplayChanged(int displayId)1635 void onDisplayChanged(int displayId); 1636 } 1637 1638 /** 1639 * Interface for accessing keys belonging to {@link 1640 * android.provider.DeviceConfig#NAMESPACE_DISPLAY_MANAGER}. 1641 * @hide 1642 */ 1643 public interface DeviceConfig { 1644 1645 /** 1646 * Key for refresh rate in the low zone defined by thresholds. 1647 * 1648 * Note that the name and value don't match because they were added before we had a high 1649 * zone to consider. 1650 * @see android.provider.DeviceConfig#NAMESPACE_DISPLAY_MANAGER 1651 * @see android.R.integer#config_defaultZoneBehavior 1652 */ 1653 String KEY_REFRESH_RATE_IN_LOW_ZONE = "refresh_rate_in_zone"; 1654 1655 /** 1656 * Key for accessing the low display brightness thresholds for the configured refresh 1657 * rate zone. 1658 * The value will be a pair of comma separated integers representing the minimum and maximum 1659 * thresholds of the zone, respectively, in display backlight units (i.e. [0, 255]). 1660 * 1661 * Note that the name and value don't match because they were added before we had a high 1662 * zone to consider. 1663 * 1664 * @see android.provider.DeviceConfig#NAMESPACE_DISPLAY_MANAGER 1665 * @see android.R.array#config_brightnessThresholdsOfPeakRefreshRate 1666 * @hide 1667 */ 1668 String KEY_FIXED_REFRESH_RATE_LOW_DISPLAY_BRIGHTNESS_THRESHOLDS = 1669 "peak_refresh_rate_brightness_thresholds"; 1670 1671 /** 1672 * Key for accessing the low ambient brightness thresholds for the configured refresh 1673 * rate zone. The value will be a pair of comma separated integers representing the minimum 1674 * and maximum thresholds of the zone, respectively, in lux. 1675 * 1676 * Note that the name and value don't match because they were added before we had a high 1677 * zone to consider. 1678 * 1679 * @see android.provider.DeviceConfig#NAMESPACE_DISPLAY_MANAGER 1680 * @see android.R.array#config_ambientThresholdsOfPeakRefreshRate 1681 * @hide 1682 */ 1683 String KEY_FIXED_REFRESH_RATE_LOW_AMBIENT_BRIGHTNESS_THRESHOLDS = 1684 "peak_refresh_rate_ambient_thresholds"; 1685 /** 1686 * Key for refresh rate in the high zone defined by thresholds. 1687 * 1688 * @see android.provider.DeviceConfig#NAMESPACE_DISPLAY_MANAGER 1689 * @see android.R.integer#config_fixedRefreshRateInHighZone 1690 */ 1691 String KEY_REFRESH_RATE_IN_HIGH_ZONE = "refresh_rate_in_high_zone"; 1692 1693 /** 1694 * Key for accessing the display brightness thresholds for the configured refresh rate zone. 1695 * The value will be a pair of comma separated integers representing the minimum and maximum 1696 * thresholds of the zone, respectively, in display backlight units (i.e. [0, 255]). 1697 * 1698 * @see android.provider.DeviceConfig#NAMESPACE_DISPLAY_MANAGER 1699 * @see android.R.array#config_brightnessHighThresholdsOfFixedRefreshRate 1700 * @hide 1701 */ 1702 String KEY_FIXED_REFRESH_RATE_HIGH_DISPLAY_BRIGHTNESS_THRESHOLDS = 1703 "fixed_refresh_rate_high_display_brightness_thresholds"; 1704 1705 /** 1706 * Key for accessing the ambient brightness thresholds for the configured refresh rate zone. 1707 * The value will be a pair of comma separated integers representing the minimum and maximum 1708 * thresholds of the zone, respectively, in lux. 1709 * 1710 * @see android.provider.DeviceConfig#NAMESPACE_DISPLAY_MANAGER 1711 * @see android.R.array#config_ambientHighThresholdsOfFixedRefreshRate 1712 * @hide 1713 */ 1714 String KEY_FIXED_REFRESH_RATE_HIGH_AMBIENT_BRIGHTNESS_THRESHOLDS = 1715 "fixed_refresh_rate_high_ambient_brightness_thresholds"; 1716 1717 /** 1718 * Key for refresh rate when the device is in high brightness mode for sunlight visility. 1719 * 1720 * @see android.provider.DeviceConfig#NAMESPACE_DISPLAY_MANAGER 1721 * @see android.R.integer#config_defaultRefreshRateInHbmSunlight 1722 */ 1723 String KEY_REFRESH_RATE_IN_HBM_SUNLIGHT = "refresh_rate_in_hbm_sunlight"; 1724 1725 /** 1726 * Key for refresh rate when the device is in high brightness mode for HDR. 1727 * 1728 * @see android.provider.DeviceConfig#NAMESPACE_DISPLAY_MANAGER 1729 * @see android.R.integer#config_defaultRefreshRateInHbmHdr 1730 */ 1731 String KEY_REFRESH_RATE_IN_HBM_HDR = "refresh_rate_in_hbm_hdr"; 1732 1733 /** 1734 * Key for default peak refresh rate 1735 * 1736 * @see android.provider.DeviceConfig#NAMESPACE_DISPLAY_MANAGER 1737 * @see android.R.integer#config_defaultPeakRefreshRate 1738 * @hide 1739 */ 1740 String KEY_PEAK_REFRESH_RATE_DEFAULT = "peak_refresh_rate_default"; 1741 1742 // TODO(b/162536543): rename it once it is proved not harmful for users. 1743 /** 1744 * Key for controlling which packages are explicitly blocked from running at refresh rates 1745 * higher than 60hz. An app may be added to this list if they exhibit performance issues at 1746 * higher refresh rates. 1747 * 1748 * @see android.provider.DeviceConfig#NAMESPACE_DISPLAY_MANAGER 1749 * @see android.R.array#config_highRefreshRateBlacklist 1750 * @hide 1751 */ 1752 String KEY_HIGH_REFRESH_RATE_BLACKLIST = "high_refresh_rate_blacklist"; 1753 1754 /** 1755 * Key for the brightness throttling data as a String formatted: 1756 * <displayId>,<no of throttling levels>,[<severity as string>,<brightness cap>] 1757 * [,<throttlingId>]? 1758 * Where [<severity as string>,<brightness cap>] is repeated for each throttling level. 1759 * The entirety is repeated for each display and throttling id, separated by a semicolon. 1760 * For example: 1761 * 123,1,critical,0.8;456,2,moderate,0.9,critical,0.7 1762 * 123,1,critical,0.8,default;123,1,moderate,0.6,id_2;456,2,moderate,0.9,critical,0.7 1763 */ 1764 String KEY_BRIGHTNESS_THROTTLING_DATA = "brightness_throttling_data"; 1765 1766 /** 1767 * Key for new power controller feature flag. If enabled new DisplayPowerController will 1768 * be used. 1769 * Read value via {@link android.provider.DeviceConfig#getBoolean(String, String, boolean)} 1770 * with {@link android.provider.DeviceConfig#NAMESPACE_DISPLAY_MANAGER} as the namespace. 1771 * @hide 1772 */ 1773 String KEY_NEW_POWER_CONTROLLER = "use_newly_structured_display_power_controller"; 1774 1775 /** 1776 * Key for normal brightness mode controller feature flag. 1777 * It enables NormalBrightnessModeController. 1778 * Read value via {@link android.provider.DeviceConfig#getBoolean(String, String, boolean)} 1779 * with {@link android.provider.DeviceConfig#NAMESPACE_DISPLAY_MANAGER} as the namespace. 1780 * @hide 1781 */ 1782 String KEY_USE_NORMAL_BRIGHTNESS_MODE_CONTROLLER = "use_normal_brightness_mode_controller"; 1783 1784 /** 1785 * Key for disabling screen wake locks while apps are in cached state. 1786 * Read value via {@link android.provider.DeviceConfig#getBoolean(String, String, boolean)} 1787 * with {@link android.provider.DeviceConfig#NAMESPACE_DISPLAY_MANAGER} as the namespace. 1788 * @hide 1789 */ 1790 String KEY_DISABLE_SCREEN_WAKE_LOCKS_WHILE_CACHED = 1791 "disable_screen_wake_locks_while_cached"; 1792 } 1793 1794 /** 1795 * Helper class to maintain cache of weak references to Display instances. 1796 * 1797 * Note this class is not thread-safe, so external synchronization is needed if accessed 1798 * concurrently. 1799 */ 1800 private static final class WeakDisplayCache { 1801 private final SparseArray<WeakReference<Display>> mDisplayCache = new SparseArray<>(); 1802 1803 /** 1804 * Return cached {@link Display} instance for the provided display id. 1805 * 1806 * @param displayId - display id of the requested {@link Display} instance. 1807 * @return cached {@link Display} instance or null 1808 */ get(int displayId)1809 Display get(int displayId) { 1810 WeakReference<Display> wrDisplay = mDisplayCache.get(displayId); 1811 if (wrDisplay == null) { 1812 return null; 1813 } 1814 return wrDisplay.get(); 1815 } 1816 1817 /** 1818 * Insert new {@link Display} instance in the cache. This replaced the previously cached 1819 * {@link Display} instance, if there's already one with the same display id. 1820 * 1821 * @param display - Display instance to cache. 1822 */ put(Display display)1823 void put(Display display) { 1824 removeStaleEntries(); 1825 mDisplayCache.put(display.getDisplayId(), new WeakReference<>(display)); 1826 } 1827 1828 /** 1829 * Evict gc-ed entries from the cache. 1830 */ removeStaleEntries()1831 private void removeStaleEntries() { 1832 ArrayList<Integer> staleEntriesIndices = new ArrayList(); 1833 for (int i = 0; i < mDisplayCache.size(); i++) { 1834 if (mDisplayCache.valueAt(i).get() == null) { 1835 staleEntriesIndices.add(i); 1836 } 1837 } 1838 1839 for (int i = 0; i < staleEntriesIndices.size(); i++) { 1840 // removeAt call to SparseArray doesn't compact the underlying array 1841 // so the indices stay valid even after removal. 1842 mDisplayCache.removeAt(staleEntriesIndices.get(i)); 1843 } 1844 } 1845 } 1846 } 1847