blob: 5f12bf04d931bf1c5f28fa1872d13ab3c27d1b32 [file] [log] [blame]
Jorim Jaggi5bb571d2018-11-06 14:42:04 +01001/*
2 * Copyright (C) 2018 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
Adrian Roosdb5b0c22020-02-12 15:05:27 -080014 * limitations under the License.
Jorim Jaggi5bb571d2018-11-06 14:42:04 +010015 */
16
17package android.view;
18
Tiger Huang332793b2019-10-29 23:21:27 +080019import static android.view.InsetsState.ITYPE_NAVIGATION_BAR;
20import static android.view.InsetsState.ITYPE_STATUS_BAR;
Tarandeep Singh215929b2019-01-11 18:24:37 -080021import static android.view.ViewRootImpl.NEW_INSETS_MODE_FULL;
Tarandeep Singh215929b2019-01-11 18:24:37 -080022import static android.view.WindowInsets.Type.systemBars;
Adrian Roos53989972020-03-19 20:15:57 +010023
Tadashi G. Takaoka82eb7a52019-03-26 18:22:01 +090024import static org.junit.Assert.assertEquals;
Adrian Roos02a3eb62020-03-18 18:03:39 +010025import static org.junit.Assert.assertFalse;
26import static org.junit.Assert.assertTrue;
Tarandeep Singh215929b2019-01-11 18:24:37 -080027import static org.junit.Assert.fail;
Adrian Roos53989972020-03-19 20:15:57 +010028import static org.mockito.ArgumentMatchers.any;
Tiger Huang41ae5e82020-01-17 18:17:20 +080029import static org.mockito.ArgumentMatchers.anyBoolean;
30import static org.mockito.ArgumentMatchers.anyInt;
Tarandeep Singh215929b2019-01-11 18:24:37 -080031import static org.mockito.ArgumentMatchers.eq;
Jorim Jaggif1035882020-03-31 22:47:12 +020032import static org.mockito.Mockito.doAnswer;
Tiger Huang41ae5e82020-01-17 18:17:20 +080033import static org.mockito.Mockito.doNothing;
Adrian Roos53989972020-03-19 20:15:57 +010034import static org.mockito.Mockito.never;
Jorim Jaggi5bb571d2018-11-06 14:42:04 +010035import static org.mockito.Mockito.verify;
Tarandeep Singh215929b2019-01-11 18:24:37 -080036import static org.mockito.Mockito.when;
Jorim Jaggi5bb571d2018-11-06 14:42:04 +010037
38import android.graphics.Insets;
39import android.graphics.Matrix;
Tarandeep Singh215929b2019-01-11 18:24:37 -080040import android.graphics.Point;
Jorim Jaggi5bb571d2018-11-06 14:42:04 +010041import android.graphics.Rect;
42import android.graphics.RectF;
43import android.platform.test.annotations.Presubmit;
Jorim Jaggi5bb571d2018-11-06 14:42:04 +010044import android.util.SparseArray;
45import android.view.SurfaceControl.Transaction;
46import android.view.SyncRtSurfaceTransactionApplier.SurfaceParams;
Jorim Jaggidd3304e2020-01-20 17:24:51 +010047import android.view.animation.LinearInterpolator;
Charles Chen2783faf2019-04-16 17:39:23 +080048import android.view.test.InsetsModeSession;
Jorim Jaggi5bb571d2018-11-06 14:42:04 +010049
Adrian Roos53989972020-03-19 20:15:57 +010050import androidx.test.runner.AndroidJUnit4;
51
Charles Chen2783faf2019-04-16 17:39:23 +080052import org.junit.AfterClass;
Jorim Jaggi5bb571d2018-11-06 14:42:04 +010053import org.junit.Before;
Charles Chen2783faf2019-04-16 17:39:23 +080054import org.junit.BeforeClass;
Jorim Jaggi5bb571d2018-11-06 14:42:04 +010055import org.junit.Test;
56import org.junit.runner.RunWith;
57import org.mockito.ArgumentCaptor;
58import org.mockito.Mock;
59import org.mockito.MockitoAnnotations;
60
61import java.util.List;
62
Tadashi G. Takaoka82eb7a52019-03-26 18:22:01 +090063/**
64 * Tests for {@link InsetsAnimationControlImpl}.
65 *
66 * <p>Build/Install/Run:
67 * atest FrameworksCoreTests:InsetsAnimationControlImplTest
68 *
69 * <p>This test class is a part of Window Manager Service tests and specified in
70 * {@link com.android.server.wm.test.filters.FrameworksTestsFilter}.
71 */
Jorim Jaggi5bb571d2018-11-06 14:42:04 +010072@Presubmit
Jorim Jaggi5bb571d2018-11-06 14:42:04 +010073@RunWith(AndroidJUnit4.class)
74public class InsetsAnimationControlImplTest {
75
76 private InsetsAnimationControlImpl mController;
77
78 private SurfaceSession mSession = new SurfaceSession();
79 private SurfaceControl mTopLeash;
80 private SurfaceControl mNavLeash;
Tarandeep Singh215929b2019-01-11 18:24:37 -080081 private InsetsState mInsetsState;
Charles Chen2783faf2019-04-16 17:39:23 +080082 private static InsetsModeSession sInsetsModeSession;
Jorim Jaggi5bb571d2018-11-06 14:42:04 +010083
84 @Mock Transaction mMockTransaction;
85 @Mock InsetsController mMockController;
86 @Mock WindowInsetsAnimationControlListener mMockListener;
Jorim Jaggi5bb571d2018-11-06 14:42:04 +010087
Charles Chen2783faf2019-04-16 17:39:23 +080088 @BeforeClass
89 public static void setupOnce() {
90 sInsetsModeSession = new InsetsModeSession(NEW_INSETS_MODE_FULL);
91 }
92
93 @AfterClass
Jorim Jaggi28620472019-01-02 23:21:49 +010094 public static void tearDownOnce() {
Charles Chen2783faf2019-04-16 17:39:23 +080095 sInsetsModeSession.close();
96 }
97
Jorim Jaggi5bb571d2018-11-06 14:42:04 +010098 @Before
99 public void setup() {
100 MockitoAnnotations.initMocks(this);
Tiger Huang41ae5e82020-01-17 18:17:20 +0800101 doNothing().when(mMockController).updateCompatSysUiVisibility(
102 anyInt(), anyBoolean(), anyBoolean());
Jorim Jaggi5bb571d2018-11-06 14:42:04 +0100103 mTopLeash = new SurfaceControl.Builder(mSession)
104 .setName("testSurface")
105 .build();
106 mNavLeash = new SurfaceControl.Builder(mSession)
107 .setName("testSurface")
108 .build();
Tarandeep Singh215929b2019-01-11 18:24:37 -0800109 mInsetsState = new InsetsState();
Tiger Huang332793b2019-10-29 23:21:27 +0800110 mInsetsState.getSource(ITYPE_STATUS_BAR).setFrame(new Rect(0, 0, 500, 100));
111 mInsetsState.getSource(ITYPE_NAVIGATION_BAR).setFrame(new Rect(400, 0, 500, 500));
112 InsetsSourceConsumer topConsumer = new InsetsSourceConsumer(ITYPE_STATUS_BAR, mInsetsState,
Jorim Jaggi5bb571d2018-11-06 14:42:04 +0100113 () -> mMockTransaction, mMockController);
Tiger Huang332793b2019-10-29 23:21:27 +0800114 topConsumer.setControl(
Jorim Jaggi3182ef12020-01-30 00:16:18 +0100115 new InsetsSourceControl(ITYPE_STATUS_BAR, mTopLeash, new Point(0, 0)),
116 new int[1], new int[1]);
Jorim Jaggi5bb571d2018-11-06 14:42:04 +0100117
Tiger Huang332793b2019-10-29 23:21:27 +0800118 InsetsSourceConsumer navConsumer = new InsetsSourceConsumer(ITYPE_NAVIGATION_BAR,
Tarandeep Singh215929b2019-01-11 18:24:37 -0800119 mInsetsState, () -> mMockTransaction, mMockController);
Tiger Huang332793b2019-10-29 23:21:27 +0800120 navConsumer.setControl(new InsetsSourceControl(ITYPE_NAVIGATION_BAR, mNavLeash,
Jorim Jaggi3182ef12020-01-30 00:16:18 +0100121 new Point(400, 0)), new int[1], new int[1]);
122 navConsumer.hide();
Jorim Jaggi5bb571d2018-11-06 14:42:04 +0100123
Yunfan Chen02abf552019-12-05 14:51:09 +0900124 SparseArray<InsetsSourceControl> controls = new SparseArray<>();
125 controls.put(ITYPE_STATUS_BAR, topConsumer.getControl());
126 controls.put(ITYPE_NAVIGATION_BAR, navConsumer.getControl());
127 mController = new InsetsAnimationControlImpl(controls,
Tarandeep Singh215929b2019-01-11 18:24:37 -0800128 new Rect(0, 0, 500, 500), mInsetsState, mMockListener, systemBars(),
Jorim Jaggidd3304e2020-01-20 17:24:51 +0100129 mMockController, 10 /* durationMs */, new LinearInterpolator(),
Jorim Jaggi5875cca2020-03-17 13:44:57 +0100130 0 /* animationType */);
Adrian Roos53989972020-03-19 20:15:57 +0100131 mController.mReadyDispatched = true;
Jorim Jaggi5bb571d2018-11-06 14:42:04 +0100132 }
133
134 @Test
135 public void testGetters() {
136 assertEquals(Insets.of(0, 100, 100, 0), mController.getShownStateInsets());
137 assertEquals(Insets.of(0, 0, 0, 0), mController.getHiddenStateInsets());
138 assertEquals(Insets.of(0, 100, 0, 0), mController.getCurrentInsets());
Tarandeep Singh215929b2019-01-11 18:24:37 -0800139 assertEquals(systemBars(), mController.getTypes());
Jorim Jaggi5bb571d2018-11-06 14:42:04 +0100140 }
141
142 @Test
Adrian Roos02a3eb62020-03-18 18:03:39 +0100143 public void testReady() {
144 assertTrue(mController.isReady());
145 assertFalse(mController.isFinished());
146 assertFalse(mController.isCancelled());
147 }
148
149 @Test
Jorim Jaggi5bb571d2018-11-06 14:42:04 +0100150 public void testChangeInsets() {
Tarandeep Singh54554e22019-11-01 14:43:05 -0700151 mController.setInsetsAndAlpha(Insets.of(0, 30, 40, 0), 1f /* alpha */,
152 0f /* fraction */);
Jorim Jaggifae3e272019-01-14 14:05:05 +0100153 mController.applyChangeInsets(new InsetsState());
Jorim Jaggi5bb571d2018-11-06 14:42:04 +0100154 assertEquals(Insets.of(0, 30, 40, 0), mController.getCurrentInsets());
Tarandeep Singh699aa672019-11-22 23:19:30 -0800155 assertEquals(1f, mController.getCurrentAlpha(), 1f - mController.getCurrentAlpha());
Jorim Jaggi5bb571d2018-11-06 14:42:04 +0100156
157 ArgumentCaptor<SurfaceParams> captor = ArgumentCaptor.forClass(SurfaceParams.class);
Yunfan Chen02abf552019-12-05 14:51:09 +0900158 verify(mMockController).applySurfaceParams(captor.capture());
Jorim Jaggi5bb571d2018-11-06 14:42:04 +0100159 List<SurfaceParams> params = captor.getAllValues();
160 assertEquals(2, params.size());
161 SurfaceParams first = params.get(0);
162 SurfaceParams second = params.get(1);
163 SurfaceParams topParams = first.surface == mTopLeash ? first : second;
164 SurfaceParams navParams = first.surface == mNavLeash ? first : second;
165 assertPosition(topParams.matrix, new Rect(0, 0, 500, 100), new Rect(0, -70, 500, 30));
166 assertPosition(navParams.matrix, new Rect(400, 0, 500, 500), new Rect(460, 0, 560, 500));
167 }
168
Jorim Jaggi5ed50cc2019-01-23 16:59:42 +0100169 @Test
Tarandeep Singh699aa672019-11-22 23:19:30 -0800170 public void testChangeAlphaNoInsets() {
171 Insets initialInsets = mController.getCurrentInsets();
172 mController.setInsetsAndAlpha(null, 0.5f, 0f /* fraction*/);
173 mController.applyChangeInsets(new InsetsState());
174 assertEquals(0.5f, mController.getCurrentAlpha(), 0.5f - mController.getCurrentAlpha());
175 assertEquals(initialInsets, mController.getCurrentInsets());
176 }
177
178 @Test
179 public void testChangeInsetsAndAlpha() {
180 mController.setInsetsAndAlpha(Insets.of(0, 30, 40, 0), 0.5f, 1f);
181 mController.applyChangeInsets(new InsetsState());
182 assertEquals(0.5f, mController.getCurrentAlpha(), 0.5f - mController.getCurrentAlpha());
183 assertEquals(Insets.of(0, 30, 40, 0), mController.getCurrentInsets());
184 }
185
186 @Test
Jorim Jaggi5ed50cc2019-01-23 16:59:42 +0100187 public void testFinishing() {
188 when(mMockController.getState()).thenReturn(mInsetsState);
Tarandeep Singh54554e22019-11-01 14:43:05 -0700189 mController.finish(true /* shown */);
Jorim Jaggi5ed50cc2019-01-23 16:59:42 +0100190 mController.applyChangeInsets(mInsetsState);
Tarandeep Singh54554e22019-11-01 14:43:05 -0700191 assertEquals(Insets.of(0, 100, 100, 0), mController.getCurrentInsets());
192 verify(mMockController).notifyFinished(eq(mController), eq(true /* shown */));
Adrian Roos02a3eb62020-03-18 18:03:39 +0100193 assertFalse(mController.isReady());
194 assertTrue(mController.isFinished());
195 assertFalse(mController.isCancelled());
196 verify(mMockListener).onFinished(mController);
Jorim Jaggi5ed50cc2019-01-23 16:59:42 +0100197 }
198
199 @Test
200 public void testCancelled() {
Jorim Jaggi6d5c8012020-02-28 01:40:27 +0100201 mController.cancel();
Jorim Jaggi5ed50cc2019-01-23 16:59:42 +0100202 try {
Tarandeep Singh54554e22019-11-01 14:43:05 -0700203 mController.setInsetsAndAlpha(Insets.NONE, 1f /*alpha */, 0f /* fraction */);
Jorim Jaggi5ed50cc2019-01-23 16:59:42 +0100204 fail("Expected exception to be thrown");
205 } catch (IllegalStateException ignored) {
206 }
Adrian Roos02a3eb62020-03-18 18:03:39 +0100207 assertFalse(mController.isReady());
208 assertFalse(mController.isFinished());
209 assertTrue(mController.isCancelled());
Adrian Roos5d557ed2020-03-17 20:04:35 +0100210 verify(mMockListener).onCancelled(mController);
Tarandeep Singh54554e22019-11-01 14:43:05 -0700211 mController.finish(true /* shown */);
Adrian Roos53989972020-03-19 20:15:57 +0100212 verify(mMockListener, never()).onFinished(any());
213 }
214
215 @Test
216 public void testCancelled_beforeReadyDispatched() {
217 mController.mReadyDispatched = false;
218 mController.cancel();
219 assertFalse(mController.isReady());
220 assertFalse(mController.isFinished());
221 assertTrue(mController.isCancelled());
222 verify(mMockListener).onCancelled(null);
223 verify(mMockListener, never()).onFinished(any());
Jorim Jaggi5ed50cc2019-01-23 16:59:42 +0100224 }
225
Jorim Jaggif1035882020-03-31 22:47:12 +0200226 @Test
227 public void testFinish_immediately() {
228 when(mMockController.getState()).thenReturn(mInsetsState);
229 doAnswer(invocation -> {
230 mController.applyChangeInsets(mInsetsState);
231 return null;
Adrian Roos6a4448f2020-04-01 15:01:08 +0200232 }).when(mMockController).scheduleApplyChangeInsets(any());
Jorim Jaggif1035882020-03-31 22:47:12 +0200233 mController.finish(true /* shown */);
234 assertEquals(Insets.of(0, 100, 100, 0), mController.getCurrentInsets());
235 verify(mMockController).notifyFinished(eq(mController), eq(true /* shown */));
236 assertFalse(mController.isReady());
237 assertTrue(mController.isFinished());
238 assertFalse(mController.isCancelled());
239 verify(mMockListener).onFinished(mController);
240 }
241
Jorim Jaggi5bb571d2018-11-06 14:42:04 +0100242 private void assertPosition(Matrix m, Rect original, Rect transformed) {
243 RectF rect = new RectF(original);
244 rect.offsetTo(0, 0);
245 m.mapRect(rect);
246 rect.round(original);
247 assertEquals(original, transformed);
248 }
249}