Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 8c28c7c2 authored by Adrian Roos's avatar Adrian Roos
Browse files

Cutout: Add developer setting to mask the display cutout

Adds an option to mask the cutout by effectively shrinking the logical display
such that developers can test apps as if the device did not have a notch.

Bug: 112876936
Test: Go to Settings > Developer Options > Simulate display with cutout > "No cutout". Cutout should be hidden. Rotate screen, take screenshots, screenrecord, screen off animation should all work as expected.
Change-Id: I5cdb201734d238bf3785ab55843114e4b5b4ee41
parent d82da978
Loading
Loading
Loading
Loading
+17 −7
Original line number Diff line number Diff line
@@ -325,6 +325,7 @@ public final class DisplayCutout {
     *
     * @hide
     */
    @VisibleForTesting
    public static DisplayCutout fromBoundingRect(int left, int top, int right, int bottom) {
        Region r = Region.obtain();
        r.set(left, top, right, bottom);
@@ -422,8 +423,11 @@ public final class DisplayCutout {
        m.postTranslate(offsetX, 0);
        p.transform(m);

        addToRegion(p, r);
        final Rect tmpRect = new Rect();
        toRectAndAddToRegion(p, r, tmpRect);
        final int topInset = tmpRect.bottom;

        final int bottomInset;
        if (bottomSpec != null) {
            final Path bottomPath;
            try {
@@ -436,10 +440,17 @@ public final class DisplayCutout {
            m.postTranslate(0, displayHeight);
            bottomPath.transform(m);
            p.addPath(bottomPath);
            addToRegion(bottomPath, r);
            toRectAndAddToRegion(bottomPath, r, tmpRect);
            bottomInset = displayHeight - tmpRect.top;
        } else {
            bottomInset = 0;
        }

        final Pair<Path, DisplayCutout> result = new Pair<>(p, fromBounds(r));
        // Reuse tmpRect as the inset rect we store into the DisplayCutout instance.
        tmpRect.set(0, topInset, 0, bottomInset);
        final DisplayCutout cutout = new DisplayCutout(tmpRect, r, false /* copyArguments */);

        final Pair<Path, DisplayCutout> result = new Pair<>(p, cutout);
        synchronized (CACHE_LOCK) {
            sCachedSpec = spec;
            sCachedDisplayWidth = displayWidth;
@@ -450,12 +461,11 @@ public final class DisplayCutout {
        return result;
    }

    private static void addToRegion(Path p, Region r) {
    private static void toRectAndAddToRegion(Path p, Region inoutRegion, Rect inoutRect) {
        final RectF rectF = new RectF();
        final Rect rect = new Rect();
        p.computeBounds(rectF, false /* unused */);
        rectF.round(rect);
        r.op(rect, Op.UNION);
        rectF.round(inoutRect);
        inoutRegion.op(inoutRect, Op.UNION);
    }

    private static Region boundingRectsToRegion(List<Rect> rects) {
+4 −0
Original line number Diff line number Diff line
@@ -2981,6 +2981,10 @@
         -->
    <bool name="config_fillMainBuiltInDisplayCutout">false</bool>

    <!-- If true, and there is a cutout on the main built in display, the cutout will be masked
         by shrinking the display such that it does not overlap the cutout area. -->
    <bool name="config_maskMainBuiltInDisplayCutout">false</bool>

    <!-- Ultrasound support for Mic/speaker path -->
    <!-- Whether the default microphone audio source supports near-ultrasound frequencies
         (range of 18 - 21 kHz). -->
+9 −0
Original line number Diff line number Diff line
@@ -61,6 +61,15 @@
    <!-- Margin at the edge of the screen to ignore touch events for in the windowshade. -->
    <dimen name="status_bar_edge_ignore">5dp</dimen>

    <!-- Default radius of the software rounded corners. -->
    <dimen name="rounded_corner_radius">0dp</dimen>
    <!-- Radius of the software rounded corners at the top of the display in its natural
        orientation. If zero, the value of rounded_corner_radius is used. -->
    <dimen name="rounded_corner_radius_top">0dp</dimen>
    <!-- Radius of the software rounded corners at the bottom of the display in its natural
        orientation. If zero, the value of rounded_corner_radius is used. -->
    <dimen name="rounded_corner_radius_bottom">0dp</dimen>

    <!-- Width of the window of the divider bar used to resize docked stacks. -->
    <dimen name="docked_stack_divider_thickness">48dp</dimen>

+2 −0
Original line number Diff line number Diff line
@@ -3407,6 +3407,8 @@
  <java-symbol type="integer" name="config_defaultHapticFeedbackIntensity" />
  <java-symbol type="integer" name="config_defaultNotificationVibrationIntensity" />

  <java-symbol type="bool" name="config_maskMainBuiltInDisplayCutout" />

  <java-symbol type="array" name="config_disableApksUnlessMatchedSku_apk_list" />
  <java-symbol type="array" name="config_disableApkUnlessMatchedSku_skus_list" />
</resources>
+14 −0
Original line number Diff line number Diff line
@@ -19,6 +19,7 @@ package android.view;
import static android.view.DisplayCutout.NO_CUTOUT;
import static android.view.DisplayCutout.fromSpec;

import static org.hamcrest.Matchers.equalTo;
import static org.hamcrest.Matchers.not;
import static org.hamcrest.Matchers.sameInstance;
import static org.junit.Assert.assertEquals;
@@ -219,6 +220,19 @@ public class DisplayCutoutTest {
        assertThat(fromSpec("L1,0 L1,1 L0,1 z", 200, 400, 1f), not(sameInstance(cached)));
    }

    @Test
    public void fromSpec_setsSafeInsets_top() {
        DisplayCutout cutout = fromSpec("M -50,0 v 20 h 100 v -20 z", 200, 400, 2f);
        assertThat(cutout.getSafeInsets(), equalTo(new Rect(0, 20, 0, 0)));
    }

    @Test
    public void fromSpec_setsSafeInsets_top_and_bottom() {
        DisplayCutout cutout = fromSpec("M -50,0 v 20 h 100 v -20 z"
                + "@bottom M -50,0 v -10,0 h 100 v 20 z", 200, 400, 2f);
        assertThat(cutout.getSafeInsets(), equalTo(new Rect(0, 20, 0, 10)));
    }

    @Test
    public void parcel_unparcel_nocutout() {
        Parcel p = Parcel.obtain();
Loading