• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2019 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package android.view;
18 
19 import android.annotation.NonNull;
20 import android.annotation.Nullable;
21 import android.app.WindowConfiguration;
22 import android.content.res.Configuration;
23 import android.graphics.PixelFormat;
24 import android.graphics.Rect;
25 import android.graphics.Region;
26 import android.os.IBinder;
27 import android.os.RemoteCallback;
28 import android.os.RemoteException;
29 import android.util.Log;
30 import android.util.MergedConfiguration;
31 import android.view.View.FocusDirection;
32 import android.view.WindowInsets.Type.InsetsType;
33 import android.view.inputmethod.ImeTracker;
34 import android.window.ClientWindowFrames;
35 import android.window.InputTransferToken;
36 import android.window.OnBackInvokedCallbackInfo;
37 
38 import java.util.HashMap;
39 import java.util.List;
40 import java.util.Objects;
41 
42 /**
43 * A simplistic implementation of IWindowSession. Rather than managing Surfaces
44 * as children of the display, it manages Surfaces as children of a given root.
45 *
46 * By parcelling the root surface, the app can offer another app content for embedding.
47 * @hide
48 */
49 public class WindowlessWindowManager implements IWindowSession {
50     private final static String TAG = "WindowlessWindowManager";
51 
52     private class State {
53         SurfaceControl mSurfaceControl;
54         final WindowManager.LayoutParams mParams = new WindowManager.LayoutParams();
55         final WindowManager.LayoutParams mLastReportedParams = new WindowManager.LayoutParams();
56         int mDisplayId;
57         IBinder mInputChannelToken;
58         Region mInputRegion;
59         IWindow mClient;
60         SurfaceControl mLeash;
61         Rect mFrame;
62         Rect mAttachedFrame;
63         InputTransferToken mInputTransferToken;
64 
State(SurfaceControl sc, WindowManager.LayoutParams p, int displayId, IWindow client, SurfaceControl leash, Rect frame)65         State(SurfaceControl sc, WindowManager.LayoutParams p, int displayId, IWindow client,
66                 SurfaceControl leash, Rect frame) {
67             mSurfaceControl = sc;
68             mParams.copyFrom(p);
69             mDisplayId = displayId;
70             mClient = client;
71             mLeash = leash;
72             mFrame = frame;
73         }
74     };
75 
76     /**
77      * Used to store SurfaceControl we've built for clients to
78      * reconfigure them if relayout is called.
79      */
80     final HashMap<IBinder, State> mStateForWindow = new HashMap<IBinder, State>();
81 
82     public interface ResizeCompleteCallback {
finished(SurfaceControl.Transaction completion)83         public void finished(SurfaceControl.Transaction completion);
84     }
85 
86     final HashMap<IBinder, ResizeCompleteCallback> mResizeCompletionForWindow =
87         new HashMap<IBinder, ResizeCompleteCallback>();
88 
89     protected final SurfaceControl mRootSurface;
90     private final Configuration mConfiguration;
91     private final IWindowSession mRealWm;
92     final InputTransferToken mHostInputTransferToken;
93     private final InputTransferToken mInputTransferToken = new InputTransferToken();
94     private InsetsState mInsetsState;
95     private final ClientWindowFrames mTmpFrames = new ClientWindowFrames();
96     private final MergedConfiguration mTmpConfig = new MergedConfiguration();
97     private final WindowlessWindowLayout mLayout = new WindowlessWindowLayout();
98 
99     private ISurfaceControlViewHostParent mParentInterface;
100 
WindowlessWindowManager(Configuration c, SurfaceControl rootSurface, InputTransferToken hostInputTransferToken)101     public WindowlessWindowManager(Configuration c, SurfaceControl rootSurface,
102             InputTransferToken hostInputTransferToken) {
103         mRootSurface = rootSurface;
104         mConfiguration = new Configuration(c);
105         mRealWm = WindowManagerGlobal.getWindowSession();
106         mHostInputTransferToken = hostInputTransferToken;
107     }
108 
setConfiguration(Configuration configuration)109     public void setConfiguration(Configuration configuration) {
110         mConfiguration.setTo(configuration);
111     }
112 
getInputTransferToken(IBinder window)113     InputTransferToken getInputTransferToken(IBinder window) {
114         synchronized (this) {
115             // This can only happen if someone requested the focusGrantToken before setView was
116             // called for the SCVH. In that case, use the root focusGrantToken since this will be
117             // the same token sent to WMS for the root window once setView is called.
118             if (mStateForWindow.isEmpty()) {
119                 return mInputTransferToken;
120             }
121             State state = mStateForWindow.get(window);
122             if (state != null) {
123                 return state.mInputTransferToken;
124             }
125         }
126 
127         Log.w(TAG, "Failed to get focusGrantToken. Returning null token");
128         return null;
129     }
130 
131     /**
132      * Utility API.
133      */
setCompletionCallback(IBinder window, ResizeCompleteCallback callback)134     void setCompletionCallback(IBinder window, ResizeCompleteCallback callback) {
135         if (mResizeCompletionForWindow.get(window) != null) {
136             Log.w(TAG, "Unsupported overlapping resizes");
137         }
138         mResizeCompletionForWindow.put(window, callback);
139     }
140 
setTouchRegion(IBinder window, @Nullable Region region)141     protected void setTouchRegion(IBinder window, @Nullable Region region) {
142         State state;
143         synchronized (this) {
144             // Do everything while locked so that we synchronize with relayout. This should be a
145             // very infrequent operation.
146             state = mStateForWindow.get(window);
147             if (state == null) {
148                 return;
149             }
150             if (Objects.equals(region, state.mInputRegion)) {
151                 return;
152             }
153             state.mInputRegion = region != null ? new Region(region) : null;
154             if (state.mInputChannelToken != null) {
155                 try {
156                     mRealWm.updateInputChannel(state.mInputChannelToken, state.mDisplayId,
157                             state.mSurfaceControl, state.mParams.flags, state.mParams.privateFlags,
158                             state.mParams.inputFeatures, state.mInputRegion);
159                 } catch (RemoteException e) {
160                     Log.e(TAG, "Failed to update surface input channel: ", e);
161                 }
162             }
163         }
164     }
165 
getParentSurface(IWindow window, WindowManager.LayoutParams attrs)166     protected SurfaceControl getParentSurface(IWindow window, WindowManager.LayoutParams attrs) {
167         // If this is the first window, the state map is empty and the parent surface is the
168         // root. Otherwise, the parent surface is in the state map.
169         synchronized (this) {
170             if (mStateForWindow.isEmpty()) {
171                 return mRootSurface;
172             }
173             return mStateForWindow.get(attrs.token).mLeash;
174         }
175     }
176 
177     /**
178      * IWindowSession implementation.
179      */
180     @Override
addToDisplay(IWindow window, WindowManager.LayoutParams attrs, int viewVisibility, int displayId, @InsetsType int requestedVisibleTypes, InputChannel outInputChannel, InsetsState outInsetsState, InsetsSourceControl.Array outActiveControls, Rect outAttachedFrame, float[] outSizeCompatScale)181     public int addToDisplay(IWindow window, WindowManager.LayoutParams attrs,
182             int viewVisibility, int displayId, @InsetsType int requestedVisibleTypes,
183             InputChannel outInputChannel, InsetsState outInsetsState,
184             InsetsSourceControl.Array outActiveControls, Rect outAttachedFrame,
185             float[] outSizeCompatScale) {
186         final SurfaceControl leash = new SurfaceControl.Builder()
187                 .setName(attrs.getTitle().toString() + "Leash")
188                 .setCallsite("WindowlessWindowManager.addToDisplay")
189                 .setParent(getParentSurface(window, attrs))
190                 .build();
191 
192         final SurfaceControl sc = new SurfaceControl.Builder()
193                 .setFormat(attrs.format)
194                 .setBLASTLayer()
195                 .setName(attrs.getTitle().toString())
196                 .setCallsite("WindowlessWindowManager.addToDisplay")
197                 .setHidden(false)
198                 .setParent(leash)
199                 .build();
200 
201         final State state = new State(sc, attrs, displayId, window, leash, /* frame= */ new Rect());
202         synchronized (this) {
203             State parentState = mStateForWindow.get(attrs.token);
204             if (parentState != null) {
205                 state.mAttachedFrame = parentState.mFrame;
206             }
207 
208             // Give the first window the mFocusGrantToken since that's the token the host can use
209             // to give focus to the embedded.
210             if (mStateForWindow.isEmpty()) {
211                 state.mInputTransferToken = mInputTransferToken;
212             } else {
213                 state.mInputTransferToken = new InputTransferToken();
214             }
215 
216             mStateForWindow.put(window.asBinder(), state);
217         }
218 
219         if (state.mAttachedFrame == null) {
220             outAttachedFrame.set(0, 0, -1, -1);
221         } else {
222             outAttachedFrame.set(state.mAttachedFrame);
223         }
224         outSizeCompatScale[0] = 1f;
225 
226         if (((attrs.inputFeatures &
227                 WindowManager.LayoutParams.INPUT_FEATURE_NO_INPUT_CHANNEL) == 0)) {
228             try {
229                 if (mRealWm instanceof IWindowSession.Stub) {
230                     mRealWm.grantInputChannel(displayId,
231                             new SurfaceControl(sc, "WindowlessWindowManager.addToDisplay"),
232                             window.asBinder(), mHostInputTransferToken, attrs.flags,
233                             attrs.privateFlags, attrs.inputFeatures, attrs.type, attrs.token,
234                             state.mInputTransferToken, attrs.getTitle().toString(),
235                             outInputChannel);
236                 } else {
237                     mRealWm.grantInputChannel(displayId, sc, window.asBinder(),
238                             mHostInputTransferToken, attrs.flags, attrs.privateFlags,
239                             attrs.inputFeatures, attrs.type, attrs.token, state.mInputTransferToken,
240                             attrs.getTitle().toString(), outInputChannel);
241                 }
242                 state.mInputChannelToken =
243                         outInputChannel != null ? outInputChannel.getToken() : null;
244             } catch (RemoteException e) {
245                 Log.e(TAG, "Failed to grant input to surface: ", e);
246             }
247         }
248 
249         final int res = WindowManagerGlobal.ADD_OKAY | WindowManagerGlobal.ADD_FLAG_APP_VISIBLE;
250 
251         sendLayoutParamsToParent();
252         // Include whether the window is in touch mode.
253         return isInTouchModeInternal(displayId) ? res | WindowManagerGlobal.ADD_FLAG_IN_TOUCH_MODE
254                 : res;
255     }
256 
257     /**
258      * IWindowSession implementation. Currently this class doesn't need to support for multi-user.
259      */
260     @Override
addToDisplayAsUser(IWindow window, WindowManager.LayoutParams attrs, int viewVisibility, int displayId, int userId, @InsetsType int requestedVisibleTypes, InputChannel outInputChannel, InsetsState outInsetsState, InsetsSourceControl.Array outActiveControls, Rect outAttachedFrame, float[] outSizeCompatScale)261     public int addToDisplayAsUser(IWindow window, WindowManager.LayoutParams attrs,
262             int viewVisibility, int displayId, int userId, @InsetsType int requestedVisibleTypes,
263             InputChannel outInputChannel, InsetsState outInsetsState,
264             InsetsSourceControl.Array outActiveControls, Rect outAttachedFrame,
265             float[] outSizeCompatScale) {
266         return addToDisplay(window, attrs, viewVisibility, displayId, requestedVisibleTypes,
267                 outInputChannel, outInsetsState, outActiveControls, outAttachedFrame,
268                 outSizeCompatScale);
269     }
270 
271     @Override
addToDisplayWithoutInputChannel(android.view.IWindow window, android.view.WindowManager.LayoutParams attrs, int viewVisibility, int layerStackId, android.view.InsetsState insetsState, Rect outAttachedFrame, float[] outSizeCompatScale)272     public int addToDisplayWithoutInputChannel(android.view.IWindow window,
273             android.view.WindowManager.LayoutParams attrs, int viewVisibility, int layerStackId,
274             android.view.InsetsState insetsState, Rect outAttachedFrame,
275             float[] outSizeCompatScale) {
276         return 0;
277     }
278 
279     @Override
remove(IBinder clientToken)280     public void remove(IBinder clientToken) throws RemoteException {
281         mRealWm.remove(clientToken);
282         State state;
283         synchronized (this) {
284             state = mStateForWindow.remove(clientToken);
285         }
286         if (state == null) {
287             throw new IllegalArgumentException(
288                     "Invalid window token (never added or removed already)");
289         }
290         removeSurface(state.mSurfaceControl);
291         removeSurface(state.mLeash);
292     }
293 
294     /** Separate from {@link #remove} so that subclasses can put removal on a sync transaction. */
removeSurface(SurfaceControl sc)295     protected void removeSurface(SurfaceControl sc) {
296         try (SurfaceControl.Transaction t = new SurfaceControl.Transaction()) {
297             t.remove(sc).apply();
298         }
299     }
300 
isOpaque(WindowManager.LayoutParams attrs)301     private boolean isOpaque(WindowManager.LayoutParams attrs) {
302         if (attrs.surfaceInsets != null && attrs.surfaceInsets.left != 0 ||
303                 attrs.surfaceInsets.top != 0 || attrs.surfaceInsets.right != 0 ||
304                 attrs.surfaceInsets.bottom != 0) {
305             return false;
306         }
307         return !PixelFormat.formatHasAlpha(attrs.format);
308     }
309 
isInTouchModeInternal(int displayId)310     private boolean isInTouchModeInternal(int displayId) {
311         try {
312             return WindowManagerGlobal.getWindowManagerService().isInTouchMode(displayId);
313         } catch (RemoteException e) {
314             Log.e(TAG, "Unable to check if the window is in touch mode", e);
315         }
316         return false;
317     }
318 
319     /** Access to package members for SystemWindow leashing
320      * @hide
321      */
getWindowBinder(View rootView)322     protected IBinder getWindowBinder(View rootView) {
323         final ViewRootImpl root = rootView.getViewRootImpl();
324         if (root == null) {
325             return null;
326         }
327         return root.mWindow.asBinder();
328     }
329 
330     /** @hide */
331     @Nullable
getSurfaceControl(View rootView)332     protected SurfaceControl getSurfaceControl(View rootView) {
333         final ViewRootImpl root = rootView.getViewRootImpl();
334         if (root == null) {
335             return null;
336         }
337         return getSurfaceControl(root.mWindow);
338     }
339 
340     /** @hide */
341     @Nullable
getSurfaceControl(IWindow window)342     protected SurfaceControl getSurfaceControl(IWindow window) {
343         final State s = mStateForWindow.get(window.asBinder());
344         if (s == null) {
345             return null;
346         }
347         return s.mSurfaceControl;
348     }
349 
350     @Override
relayout(IWindow window, WindowManager.LayoutParams inAttrs, int requestedWidth, int requestedHeight, int viewFlags, int flags, int seq, int lastSyncSeqId, WindowRelayoutResult outRelayoutResult)351     public int relayout(IWindow window, WindowManager.LayoutParams inAttrs,
352             int requestedWidth, int requestedHeight, int viewFlags, int flags, int seq,
353             int lastSyncSeqId, WindowRelayoutResult outRelayoutResult) {
354         final ClientWindowFrames outFrames;
355         final MergedConfiguration outMergedConfiguration;
356         final SurfaceControl outSurfaceControl;
357         final InsetsState outInsetsState;
358         final InsetsSourceControl.Array outActiveControls;
359         if (outRelayoutResult != null) {
360             outFrames = outRelayoutResult.frames;
361             outMergedConfiguration = outRelayoutResult.mergedConfiguration;
362             outSurfaceControl = outRelayoutResult.surfaceControl;
363             outInsetsState = outRelayoutResult.insetsState;
364             outActiveControls = outRelayoutResult.activeControls;
365         } else {
366             outFrames = null;
367             outMergedConfiguration = null;
368             outSurfaceControl = null;
369             outInsetsState = null;
370             outActiveControls = null;
371         }
372         return relayoutInner(window, inAttrs, requestedWidth, requestedHeight, viewFlags, flags,
373                 seq, lastSyncSeqId, outFrames, outMergedConfiguration, outSurfaceControl,
374                 outInsetsState, outActiveControls);
375     }
376 
relayoutInner(IWindow window, WindowManager.LayoutParams inAttrs, int requestedWidth, int requestedHeight, int viewFlags, int flags, int seq, int lastSyncSeqId, ClientWindowFrames outFrames, MergedConfiguration outMergedConfiguration, SurfaceControl outSurfaceControl, InsetsState outInsetsState, InsetsSourceControl.Array outActiveControls)377     private int relayoutInner(IWindow window, WindowManager.LayoutParams inAttrs,
378             int requestedWidth, int requestedHeight, int viewFlags, int flags, int seq,
379             int lastSyncSeqId, ClientWindowFrames outFrames,
380             MergedConfiguration outMergedConfiguration, SurfaceControl outSurfaceControl,
381             InsetsState outInsetsState, InsetsSourceControl.Array outActiveControls) {
382         final State state;
383         synchronized (this) {
384             state = mStateForWindow.get(window.asBinder());
385         }
386         if (state == null) {
387             throw new IllegalArgumentException(
388                     "Invalid window token (never added or removed already)");
389         }
390         SurfaceControl sc = state.mSurfaceControl;
391         SurfaceControl leash = state.mLeash;
392         SurfaceControl.Transaction t = new SurfaceControl.Transaction();
393 
394         int attrChanges = 0;
395         if (inAttrs != null) {
396             attrChanges = state.mParams.copyFrom(inAttrs);
397         }
398         WindowManager.LayoutParams attrs = state.mParams;
399 
400         ClientWindowFrames frames = new ClientWindowFrames();
401         frames.attachedFrame = state.mAttachedFrame;
402 
403         mLayout.computeFrames(attrs, null, null, null, WindowConfiguration.WINDOWING_MODE_UNDEFINED,
404                 requestedWidth, requestedHeight, 0, 0,
405                 frames);
406 
407         state.mFrame.set(frames.frame);
408         if (outFrames != null) {
409             outFrames.frame.set(frames.frame);
410             outFrames.parentFrame.set(frames.parentFrame);
411             outFrames.displayFrame.set(frames.displayFrame);
412         }
413 
414         t.setPosition(leash, frames.frame.left, frames.frame.top);
415 
416         if (viewFlags == View.VISIBLE) {
417             // TODO(b/262892794) ViewRootImpl modifies the app's rendering SurfaceControl
418             // opaqueness. We shouldn't need to modify opaqueness for this SurfaceControl here or
419             // in the real WindowManager.
420             t.setOpaque(sc, isOpaque(attrs)).show(leash).apply();
421             if (outSurfaceControl != null) {
422                 outSurfaceControl.copyFrom(sc, "WindowlessWindowManager.relayout");
423             }
424         } else {
425             t.hide(leash).apply();
426             if (outSurfaceControl != null) {
427                 outSurfaceControl.release();
428             }
429         }
430 
431         if (outMergedConfiguration != null) {
432             outMergedConfiguration.setConfiguration(mConfiguration, mConfiguration);
433         }
434 
435         final int inputChangeMask = WindowManager.LayoutParams.FLAGS_CHANGED
436                 | WindowManager.LayoutParams.INPUT_FEATURES_CHANGED;
437         if ((attrChanges & inputChangeMask) != 0 && state.mInputChannelToken != null) {
438             try {
439                 if (mRealWm instanceof IWindowSession.Stub) {
440                     mRealWm.updateInputChannel(state.mInputChannelToken, state.mDisplayId,
441                             new SurfaceControl(sc, "WindowlessWindowManager.relayout"),
442                             attrs.flags, attrs.privateFlags, attrs.inputFeatures,
443                             state.mInputRegion);
444                 } else {
445                     mRealWm.updateInputChannel(state.mInputChannelToken, state.mDisplayId, sc,
446                             attrs.flags, attrs.privateFlags, attrs.inputFeatures,
447                             state.mInputRegion);
448                 }
449             } catch (RemoteException e) {
450                 Log.e(TAG, "Failed to update surface input channel: ", e);
451             }
452         }
453 
454         if (outInsetsState != null && mInsetsState != null) {
455             outInsetsState.set(mInsetsState);
456         }
457 
458         sendLayoutParamsToParent();
459         return 0;
460     }
461 
462     @Override
relayoutAsync(IWindow window, WindowManager.LayoutParams inAttrs, int requestedWidth, int requestedHeight, int viewFlags, int flags, int seq, int lastSyncSeqId)463     public void relayoutAsync(IWindow window, WindowManager.LayoutParams inAttrs,
464             int requestedWidth, int requestedHeight, int viewFlags, int flags, int seq,
465             int lastSyncSeqId) {
466         relayoutInner(window, inAttrs, requestedWidth, requestedHeight, viewFlags, flags, seq,
467                 lastSyncSeqId, null /* outFrames */, null /* outMergedConfiguration */,
468                 null /* outSurfaceControl */, null /* outInsetsState */,
469                 null /* outActiveControls */);
470     }
471 
472     @Override
outOfMemory(android.view.IWindow window)473     public boolean outOfMemory(android.view.IWindow window) {
474         return false;
475     }
476 
477     @Override
setInsets(android.view.IWindow window, int touchableInsets, android.graphics.Rect contentInsets, android.graphics.Rect visibleInsets, android.graphics.Region touchableRegion)478     public void setInsets(android.view.IWindow window, int touchableInsets,
479             android.graphics.Rect contentInsets, android.graphics.Rect visibleInsets,
480             android.graphics.Region touchableRegion) {
481         setTouchRegion(window.asBinder(), touchableRegion);
482     }
483 
484     @Override
clearTouchableRegion(android.view.IWindow window)485     public void clearTouchableRegion(android.view.IWindow window) {
486         setTouchRegion(window.asBinder(), null);
487     }
488 
489     @Override
finishDrawing(android.view.IWindow window, android.view.SurfaceControl.Transaction postDrawTransaction, int seqId)490     public void finishDrawing(android.view.IWindow window,
491             android.view.SurfaceControl.Transaction postDrawTransaction, int seqId) {
492         synchronized (this) {
493             final ResizeCompleteCallback c =
494                 mResizeCompletionForWindow.get(window.asBinder());
495             if (c == null) {
496                 // No one wanted the callback, but it wasn't necessarily unexpected.
497                 postDrawTransaction.apply();
498                 return;
499             }
500             c.finished(postDrawTransaction);
501             mResizeCompletionForWindow.remove(window.asBinder());
502         }
503     }
504 
505     @Override
performDrag(android.view.IWindow window, int flags, android.view.SurfaceControl surface, int touchSource, int touchDeviceId, int touchPointerId, float touchX, float touchY, float thumbCenterX, float thumbCenterY, android.content.ClipData data)506     public android.os.IBinder performDrag(android.view.IWindow window, int flags,
507             android.view.SurfaceControl surface, int touchSource, int touchDeviceId,
508             int touchPointerId, float touchX, float touchY, float thumbCenterX, float thumbCenterY,
509             android.content.ClipData data) {
510         return null;
511     }
512 
513     @Override
reportDropResult(android.view.IWindow window, boolean consumed)514     public void reportDropResult(android.view.IWindow window, boolean consumed) {
515     }
516 
517     @Override
cancelDragAndDrop(android.os.IBinder dragToken, boolean skipAnimation)518     public void cancelDragAndDrop(android.os.IBinder dragToken, boolean skipAnimation) {
519     }
520 
521     @Override
dragRecipientEntered(android.view.IWindow window)522     public void dragRecipientEntered(android.view.IWindow window) {
523     }
524 
525     @Override
dragRecipientExited(android.view.IWindow window)526     public void dragRecipientExited(android.view.IWindow window) {
527     }
528 
529     @Override
setWallpaperPosition(android.os.IBinder windowToken, float x, float y, float xstep, float ystep)530     public void setWallpaperPosition(android.os.IBinder windowToken, float x, float y,
531             float xstep, float ystep) {
532     }
533 
534     @Override
setWallpaperZoomOut(android.os.IBinder windowToken, float zoom)535     public void setWallpaperZoomOut(android.os.IBinder windowToken, float zoom) {
536     }
537 
538     @Override
setShouldZoomOutWallpaper(android.os.IBinder windowToken, boolean shouldZoom)539     public void setShouldZoomOutWallpaper(android.os.IBinder windowToken, boolean shouldZoom) {
540     }
541 
542     @Override
wallpaperOffsetsComplete(android.os.IBinder window)543     public void wallpaperOffsetsComplete(android.os.IBinder window) {
544     }
545 
546     @Override
setWallpaperDisplayOffset(android.os.IBinder windowToken, int x, int y)547     public void setWallpaperDisplayOffset(android.os.IBinder windowToken, int x, int y) {
548     }
549 
550     @Override
sendWallpaperCommand(android.os.IBinder window, java.lang.String action, int x, int y, int z, android.os.Bundle extras, boolean sync)551     public void sendWallpaperCommand(android.os.IBinder window,
552             java.lang.String action, int x, int y, int z, android.os.Bundle extras, boolean sync) {
553     }
554 
555     @Override
wallpaperCommandComplete(android.os.IBinder window, android.os.Bundle result)556     public void wallpaperCommandComplete(android.os.IBinder window, android.os.Bundle result) {
557     }
558 
559     @Override
onRectangleOnScreenRequested(android.os.IBinder token, android.graphics.Rect rectangle)560     public void onRectangleOnScreenRequested(android.os.IBinder token,
561             android.graphics.Rect rectangle) {
562     }
563 
564     @Override
getWindowId(android.os.IBinder window)565     public android.view.IWindowId getWindowId(android.os.IBinder window) {
566         return null;
567     }
568 
569     @Override
pokeDrawLock(android.os.IBinder window)570     public void pokeDrawLock(android.os.IBinder window) {
571     }
572 
573     @Override
startMovingTask(android.view.IWindow window, float startX, float startY)574     public boolean startMovingTask(android.view.IWindow window, float startX, float startY) {
575         return false;
576     }
577 
578     @Override
finishMovingTask(android.view.IWindow window)579     public void finishMovingTask(android.view.IWindow window) {
580     }
581 
582     @Override
updateTapExcludeRegion(android.view.IWindow window, android.graphics.Region region)583     public void updateTapExcludeRegion(android.view.IWindow window,
584             android.graphics.Region region) {
585     }
586 
587     @Override
updateRequestedVisibleTypes(IWindow window, @InsetsType int requestedVisibleTypes, @Nullable ImeTracker.Token imeStatsToken)588     public void updateRequestedVisibleTypes(IWindow window,
589             @InsetsType int requestedVisibleTypes, @Nullable ImeTracker.Token imeStatsToken)
590             throws RemoteException {
591         if (android.view.inputmethod.Flags.refactorInsetsController()) {
592             // Embedded windows do not control insets (except for IME). The host window is
593             // responsible for controlling the insets.
594             mRealWm.updateRequestedVisibleTypes(window,
595                     requestedVisibleTypes & WindowInsets.Type.ime(), imeStatsToken);
596         }
597     }
598 
599     @Override
updateAnimatingTypes(IWindow window, @InsetsType int animatingTypes, @Nullable ImeTracker.Token statsToken)600     public void updateAnimatingTypes(IWindow window, @InsetsType int animatingTypes,
601             @Nullable ImeTracker.Token statsToken) {
602         // NO-OP
603     }
604 
605     @Override
reportSystemGestureExclusionChanged(android.view.IWindow window, List<Rect> exclusionRects)606     public void reportSystemGestureExclusionChanged(android.view.IWindow window,
607             List<Rect> exclusionRects) {
608     }
609 
610     @Override
reportDecorViewGestureInterceptionChanged(IWindow window, boolean intercepted)611     public void reportDecorViewGestureInterceptionChanged(IWindow window, boolean intercepted) {}
612 
613     @Override
reportKeepClearAreasChanged( android.view.IWindow window, List<Rect> restrictedRects, List<Rect> unrestrictedRects)614     public void reportKeepClearAreasChanged(
615             android.view.IWindow window,
616             List<Rect> restrictedRects,
617             List<Rect> unrestrictedRects) {}
618 
619     @Override
grantInputChannel(int displayId, SurfaceControl surface, IBinder clientToken, InputTransferToken hostInputToken, int flags, int privateFlags, int inputFeatures, int type, IBinder windowToken, InputTransferToken embeddedInputTransferToken, String inputHandleName, InputChannel outInputChannel)620     public void grantInputChannel(int displayId, SurfaceControl surface, IBinder clientToken,
621             InputTransferToken hostInputToken, int flags, int privateFlags, int inputFeatures,
622             int type, IBinder windowToken, InputTransferToken embeddedInputTransferToken,
623             String inputHandleName, InputChannel outInputChannel) {
624     }
625 
626     @Override
updateInputChannel(IBinder channelToken, int displayId, SurfaceControl surface, int flags, int privateFlags, int inputFeatures, Region region)627     public void updateInputChannel(IBinder channelToken, int displayId, SurfaceControl surface,
628             int flags, int privateFlags, int inputFeatures, Region region) {
629     }
630 
631     @Override
asBinder()632     public android.os.IBinder asBinder() {
633         return null;
634     }
635 
636     @Override
grantEmbeddedWindowFocus(IWindow callingWindow, InputTransferToken targetInputToken, boolean grantFocus)637     public void grantEmbeddedWindowFocus(IWindow callingWindow, InputTransferToken targetInputToken,
638                                          boolean grantFocus) {
639     }
640 
641     @Override
generateDisplayHash(IWindow window, Rect boundsInWindow, String hashAlgorithm, RemoteCallback callback)642     public void generateDisplayHash(IWindow window, Rect boundsInWindow, String hashAlgorithm,
643             RemoteCallback callback) {
644     }
645 
646     @Override
setOnBackInvokedCallbackInfo(IWindow iWindow, OnBackInvokedCallbackInfo callbackInfo)647     public void setOnBackInvokedCallbackInfo(IWindow iWindow,
648             OnBackInvokedCallbackInfo callbackInfo) throws RemoteException { }
649 
650     @Override
dropForAccessibility(IWindow window, int x, int y)651     public boolean dropForAccessibility(IWindow window, int x, int y) {
652         return false;
653     }
654 
setInsetsState(InsetsState state)655     public void setInsetsState(InsetsState state) {
656         mInsetsState = state;
657         for (State s : mStateForWindow.values()) {
658             try {
659                 mTmpFrames.frame.set(0, 0, s.mParams.width, s.mParams.height);
660                 mTmpFrames.displayFrame.set(mTmpFrames.frame);
661                 mTmpConfig.setConfiguration(mConfiguration, mConfiguration);
662                 s.mClient.resized(mTmpFrames, false /* reportDraw */, mTmpConfig, state,
663                         false /* forceLayout */, false /* alwaysConsumeSystemBars */, s.mDisplayId,
664                         Integer.MAX_VALUE, false /* dragResizing */, null /* activityWindowInfo */);
665             } catch (RemoteException e) {
666                 // Too bad
667             }
668         }
669     }
670 
671     @Override
cancelDraw(IWindow window)672     public boolean cancelDraw(IWindow window) {
673         return false;
674     }
675 
676     @Override
moveFocusToAdjacentWindow(IWindow fromWindow, @FocusDirection int direction)677     public boolean moveFocusToAdjacentWindow(IWindow fromWindow, @FocusDirection int direction) {
678         Log.e(TAG, "Received request to moveFocusToAdjacentWindow on"
679                 + " WindowlessWindowManager. We shouldn't get here!");
680         return false;
681     }
682 
683     @Override
notifyImeWindowVisibilityChangedFromClient(IWindow window, boolean visible, @NonNull ImeTracker.Token statsToken)684     public void notifyImeWindowVisibilityChangedFromClient(IWindow window, boolean visible,
685             @NonNull ImeTracker.Token statsToken) {
686     }
687 
setParentInterface(@ullable ISurfaceControlViewHostParent parentInterface)688     void setParentInterface(@Nullable ISurfaceControlViewHostParent parentInterface) {
689         IBinder oldInterface = mParentInterface == null ? null : mParentInterface.asBinder();
690         IBinder newInterface = parentInterface == null ? null : parentInterface.asBinder();
691         // If the parent interface has changed, it needs to clear the last reported params so it
692         // will update the new interface with the params.
693         if (oldInterface != newInterface) {
694             clearLastReportedParams();
695         }
696         mParentInterface = parentInterface;
697         sendLayoutParamsToParent();
698     }
699 
clearLastReportedParams()700     private void clearLastReportedParams() {
701         WindowManager.LayoutParams emptyParam = new WindowManager.LayoutParams();
702         for (State windowInfo : mStateForWindow.values()) {
703             windowInfo.mLastReportedParams.copyFrom(emptyParam);
704         }
705     }
706 
sendLayoutParamsToParent()707     private void sendLayoutParamsToParent() {
708         if (mParentInterface == null) {
709             return;
710         }
711         WindowManager.LayoutParams[] params =
712                 new WindowManager.LayoutParams[mStateForWindow.size()];
713         int index = 0;
714         boolean hasChanges = false;
715         for (State windowInfo : mStateForWindow.values()) {
716             int changes = windowInfo.mLastReportedParams.copyFrom(windowInfo.mParams);
717             hasChanges |= (changes != 0);
718             params[index++] = windowInfo.mParams;
719         }
720 
721         if (hasChanges) {
722             try {
723                 mParentInterface.updateParams(params);
724             } catch (RemoteException e) {
725             }
726         }
727     }
728 
forwardBackKeyToParent(@onNull KeyEvent keyEvent)729     boolean forwardBackKeyToParent(@NonNull KeyEvent keyEvent) {
730         if (mParentInterface == null) {
731             return false;
732         }
733         try {
734             mParentInterface.forwardBackKeyToParent(keyEvent);
735         } catch (RemoteException e) {
736             Log.e(TAG, "Failed to forward back key To Parent: ", e);
737             return false;
738         }
739         return true;
740     }
741 }
742