1 /* 2 * Copyright (C) 2014 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.app.ActivityTaskManager; 20 import android.graphics.Region; 21 import android.os.IBinder; 22 import android.os.Parcel; 23 import android.os.Parcelable; 24 import android.util.Pools; 25 import android.view.accessibility.AccessibilityNodeInfo; 26 27 import java.util.ArrayList; 28 import java.util.List; 29 30 /** 31 * This class represents information about a window from the 32 * window manager to another part of the system. 33 * 34 * @hide 35 */ 36 public class WindowInfo implements Parcelable { 37 private static final int MAX_POOL_SIZE = 10; 38 39 private static final Pools.SynchronizedPool<WindowInfo> sPool = 40 new Pools.SynchronizedPool<WindowInfo>(MAX_POOL_SIZE); 41 42 public int type; 43 public int layer; 44 public IBinder token; 45 public IBinder parentToken; 46 public IBinder activityToken; 47 public boolean focused; 48 public Region regionInScreen = new Region(); 49 public List<IBinder> childTokens; 50 public CharSequence title; 51 public long accessibilityIdOfAnchor = AccessibilityNodeInfo.UNDEFINED_NODE_ID; 52 public boolean inPictureInPicture; 53 public boolean hasFlagWatchOutsideTouch; 54 public int displayId = Display.INVALID_DISPLAY; 55 public int taskId = ActivityTaskManager.INVALID_TASK_ID; 56 WindowInfo()57 private WindowInfo() { 58 /* do nothing - hide constructor */ 59 } 60 obtain()61 public static WindowInfo obtain() { 62 WindowInfo window = sPool.acquire(); 63 if (window == null) { 64 window = new WindowInfo(); 65 } 66 return window; 67 } 68 obtain(WindowInfo other)69 public static WindowInfo obtain(WindowInfo other) { 70 WindowInfo window = obtain(); 71 window.displayId = other.displayId; 72 window.taskId = other.taskId; 73 window.type = other.type; 74 window.layer = other.layer; 75 window.token = other.token; 76 window.parentToken = other.parentToken; 77 window.activityToken = other.activityToken; 78 window.focused = other.focused; 79 window.regionInScreen.set(other.regionInScreen); 80 window.title = other.title; 81 window.accessibilityIdOfAnchor = other.accessibilityIdOfAnchor; 82 window.inPictureInPicture = other.inPictureInPicture; 83 window.hasFlagWatchOutsideTouch = other.hasFlagWatchOutsideTouch; 84 85 if (other.childTokens != null && !other.childTokens.isEmpty()) { 86 if (window.childTokens == null) { 87 window.childTokens = new ArrayList<IBinder>(other.childTokens); 88 } else { 89 window.childTokens.addAll(other.childTokens); 90 } 91 } 92 93 return window; 94 } 95 recycle()96 public void recycle() { 97 clear(); 98 sPool.release(this); 99 } 100 101 @Override describeContents()102 public int describeContents() { 103 return 0; 104 } 105 106 @Override writeToParcel(Parcel parcel, int flags)107 public void writeToParcel(Parcel parcel, int flags) { 108 parcel.writeInt(displayId); 109 parcel.writeInt(taskId); 110 parcel.writeInt(type); 111 parcel.writeInt(layer); 112 parcel.writeStrongBinder(token); 113 parcel.writeStrongBinder(parentToken); 114 parcel.writeStrongBinder(activityToken); 115 parcel.writeInt(focused ? 1 : 0); 116 regionInScreen.writeToParcel(parcel, flags); 117 parcel.writeCharSequence(title); 118 parcel.writeLong(accessibilityIdOfAnchor); 119 parcel.writeInt(inPictureInPicture ? 1 : 0); 120 parcel.writeInt(hasFlagWatchOutsideTouch ? 1 : 0); 121 122 if (childTokens != null && !childTokens.isEmpty()) { 123 parcel.writeInt(1); 124 parcel.writeBinderList(childTokens); 125 } else { 126 parcel.writeInt(0); 127 } 128 } 129 130 @Override toString()131 public String toString() { 132 StringBuilder builder = new StringBuilder(); 133 builder.append("WindowInfo["); 134 builder.append("title=").append(title); 135 builder.append(", displayId=").append(displayId); 136 builder.append(", taskId=").append(taskId); 137 builder.append(", type=").append(type); 138 builder.append(", layer=").append(layer); 139 builder.append(", token=").append(token); 140 builder.append(", region=").append(regionInScreen); 141 builder.append(", bounds=").append(regionInScreen.getBounds()); 142 builder.append(", parent=").append(parentToken); 143 builder.append(", focused=").append(focused); 144 builder.append(", children=").append(childTokens); 145 builder.append(", accessibility anchor=").append(accessibilityIdOfAnchor); 146 builder.append(", pictureInPicture=").append(inPictureInPicture); 147 builder.append(", watchOutsideTouch=").append(hasFlagWatchOutsideTouch); 148 builder.append(']'); 149 return builder.toString(); 150 } 151 initFromParcel(Parcel parcel)152 private void initFromParcel(Parcel parcel) { 153 displayId = parcel.readInt(); 154 taskId = parcel.readInt(); 155 type = parcel.readInt(); 156 layer = parcel.readInt(); 157 token = parcel.readStrongBinder(); 158 parentToken = parcel.readStrongBinder(); 159 activityToken = parcel.readStrongBinder(); 160 focused = (parcel.readInt() == 1); 161 regionInScreen = Region.CREATOR.createFromParcel(parcel); 162 title = parcel.readCharSequence(); 163 accessibilityIdOfAnchor = parcel.readLong(); 164 inPictureInPicture = (parcel.readInt() == 1); 165 hasFlagWatchOutsideTouch = (parcel.readInt() == 1); 166 167 final boolean hasChildren = (parcel.readInt() == 1); 168 if (hasChildren) { 169 if (childTokens == null) { 170 childTokens = new ArrayList<IBinder>(); 171 } 172 parcel.readBinderList(childTokens); 173 } 174 } 175 clear()176 private void clear() { 177 displayId = Display.INVALID_DISPLAY; 178 taskId = ActivityTaskManager.INVALID_TASK_ID; 179 type = 0; 180 layer = 0; 181 token = null; 182 parentToken = null; 183 activityToken = null; 184 focused = false; 185 regionInScreen.setEmpty(); 186 if (childTokens != null) { 187 childTokens.clear(); 188 } 189 inPictureInPicture = false; 190 hasFlagWatchOutsideTouch = false; 191 } 192 193 public static final @android.annotation.NonNull Parcelable.Creator<WindowInfo> CREATOR = 194 new Creator<WindowInfo>() { 195 @Override 196 public WindowInfo createFromParcel(Parcel parcel) { 197 WindowInfo window = obtain(); 198 window.initFromParcel(parcel); 199 return window; 200 } 201 202 @Override 203 public WindowInfo[] newArray(int size) { 204 return new WindowInfo[size]; 205 } 206 }; 207 } 208