Loading core/java/android/app/ActivityThread.java +11 −6 Original line number Diff line number Diff line Loading @@ -4183,12 +4183,10 @@ public final class ActivityThread { // window is being added. r.mPendingRemoveWindow = r.window; r.mPendingRemoveWindowManager = wm; if (r.mPreserveWindow) { // We can only keep the part of the view hierarchy that we control, // everything else must be removed, because it might not be able to // behave properly when activity is relaunching. r.window.clearContentView(); } } else { wm.removeViewImmediate(v); } Loading @@ -4196,6 +4194,13 @@ public final class ActivityThread { if (wtoken != null && r.mPendingRemoveWindow == null) { WindowManagerGlobal.getInstance().closeAll(wtoken, r.activity.getClass().getName(), "Activity"); } else if (r.mPendingRemoveWindow != null) { // We're preserving only one window, others should be closed so app views // will be detached before the final tear down. It should be done now because // some components (e.g. WebView) rely on detach callbacks to perform receiver // unregister and other cleanup. WindowManagerGlobal.getInstance().closeAllExceptView(token, v, r.activity.getClass().getName(), "Activity"); } r.activity.mDecor = null; } Loading core/java/android/view/WindowManagerGlobal.java +22 −5 Original line number Diff line number Diff line Loading @@ -391,17 +391,34 @@ public final class WindowManagerGlobal { } } /** * Remove all roots with specified token. * * @param token app or window token. * @param who name of caller, used in logs. * @param what type of caller, used in logs. */ public void closeAll(IBinder token, String who, String what) { closeAllExceptView(token, null /* view */, who, what); } /** * Remove all roots with specified token, except maybe one view. * * @param token app or window token. * @param view view that should be should be preserved along with it's root. * Pass null if everything should be removed. * @param who name of caller, used in logs. * @param what type of caller, used in logs. */ public void closeAllExceptView(IBinder token, View view, String who, String what) { synchronized (mLock) { int count = mViews.size(); //Log.i("foo", "Closing all windows of " + token); for (int i = 0; i < count; i++) { //Log.i("foo", "@ " + i + " token " + mParams[i].token // + " view " + mRoots[i].getView()); if (token == null || mParams.get(i).token == token) { if ((view == null || mViews.get(i) != view) && (token == null || mParams.get(i).token == token)) { ViewRootImpl root = mRoots.get(i); //Log.i("foo", "Force closing " + root); if (who != null) { WindowLeaked leak = new WindowLeaked( what + " " + who + " has leaked window " Loading Loading
core/java/android/app/ActivityThread.java +11 −6 Original line number Diff line number Diff line Loading @@ -4183,12 +4183,10 @@ public final class ActivityThread { // window is being added. r.mPendingRemoveWindow = r.window; r.mPendingRemoveWindowManager = wm; if (r.mPreserveWindow) { // We can only keep the part of the view hierarchy that we control, // everything else must be removed, because it might not be able to // behave properly when activity is relaunching. r.window.clearContentView(); } } else { wm.removeViewImmediate(v); } Loading @@ -4196,6 +4194,13 @@ public final class ActivityThread { if (wtoken != null && r.mPendingRemoveWindow == null) { WindowManagerGlobal.getInstance().closeAll(wtoken, r.activity.getClass().getName(), "Activity"); } else if (r.mPendingRemoveWindow != null) { // We're preserving only one window, others should be closed so app views // will be detached before the final tear down. It should be done now because // some components (e.g. WebView) rely on detach callbacks to perform receiver // unregister and other cleanup. WindowManagerGlobal.getInstance().closeAllExceptView(token, v, r.activity.getClass().getName(), "Activity"); } r.activity.mDecor = null; } Loading
core/java/android/view/WindowManagerGlobal.java +22 −5 Original line number Diff line number Diff line Loading @@ -391,17 +391,34 @@ public final class WindowManagerGlobal { } } /** * Remove all roots with specified token. * * @param token app or window token. * @param who name of caller, used in logs. * @param what type of caller, used in logs. */ public void closeAll(IBinder token, String who, String what) { closeAllExceptView(token, null /* view */, who, what); } /** * Remove all roots with specified token, except maybe one view. * * @param token app or window token. * @param view view that should be should be preserved along with it's root. * Pass null if everything should be removed. * @param who name of caller, used in logs. * @param what type of caller, used in logs. */ public void closeAllExceptView(IBinder token, View view, String who, String what) { synchronized (mLock) { int count = mViews.size(); //Log.i("foo", "Closing all windows of " + token); for (int i = 0; i < count; i++) { //Log.i("foo", "@ " + i + " token " + mParams[i].token // + " view " + mRoots[i].getView()); if (token == null || mParams.get(i).token == token) { if ((view == null || mViews.get(i) != view) && (token == null || mParams.get(i).token == token)) { ViewRootImpl root = mRoots.get(i); //Log.i("foo", "Force closing " + root); if (who != null) { WindowLeaked leak = new WindowLeaked( what + " " + who + " has leaked window " Loading