Loading api/current.txt +1 −1 Original line number Diff line number Diff line Loading @@ -44754,7 +44754,7 @@ package android.view { method public final void requestUnbufferedDispatch(android.view.MotionEvent); method public static int resolveSize(int, int); method public static int resolveSizeAndState(int, int, int); method public boolean restoreDefaultFocus(int); method public boolean restoreDefaultFocus(); method public void restoreHierarchyState(android.util.SparseArray<android.os.Parcelable>); method public void saveHierarchyState(android.util.SparseArray<android.os.Parcelable>); method public void scheduleDrawable(android.graphics.drawable.Drawable, java.lang.Runnable, long); api/system-current.txt +1 −1 Original line number Diff line number Diff line Loading @@ -48170,7 +48170,7 @@ package android.view { method public final void requestUnbufferedDispatch(android.view.MotionEvent); method public static int resolveSize(int, int); method public static int resolveSizeAndState(int, int, int); method public boolean restoreDefaultFocus(int); method public boolean restoreDefaultFocus(); method public void restoreHierarchyState(android.util.SparseArray<android.os.Parcelable>); method public void saveHierarchyState(android.util.SparseArray<android.os.Parcelable>); method public void scheduleDrawable(android.graphics.drawable.Drawable, java.lang.Runnable, long); api/test-current.txt +1 −1 Original line number Diff line number Diff line Loading @@ -45061,7 +45061,7 @@ package android.view { method public final void requestUnbufferedDispatch(android.view.MotionEvent); method public static int resolveSize(int, int); method public static int resolveSizeAndState(int, int, int); method public boolean restoreDefaultFocus(int); method public boolean restoreDefaultFocus(); method public void restoreHierarchyState(android.util.SparseArray<android.os.Parcelable>); method public void saveHierarchyState(android.util.SparseArray<android.os.Parcelable>); method public void scheduleDrawable(android.graphics.drawable.Drawable, java.lang.Runnable, long); core/java/android/view/View.java +31 −8 Original line number Diff line number Diff line Loading @@ -6125,9 +6125,7 @@ public class View implements Drawable.Callback, KeyEvent.Callback, if (mParent != null) { mParent.requestChildFocus(this, this); if (mParent instanceof ViewGroup) { ((ViewGroup) mParent).setDefaultFocus(this); } setFocusedInCluster(); } if (mAttachInfo != null) { Loading Loading @@ -9244,6 +9242,19 @@ public class View implements Drawable.Callback, KeyEvent.Callback, } } /** * Sets this View as the one which receives focus the next time cluster navigation jumps * to the cluster containing this View. This does NOT change focus even if the cluster * containing this view is current. * * @hide */ public void setFocusedInCluster() { if (mParent instanceof ViewGroup) { ((ViewGroup) mParent).setFocusInCluster(this); } } /** * Returns whether this View should receive focus when the focus is restored for the view * hierarchy containing this view. Loading Loading @@ -9290,7 +9301,7 @@ public class View implements Drawable.Callback, KeyEvent.Callback, if (isFocusedByDefault) { ((ViewGroup) mParent).setDefaultFocus(this); } else { ((ViewGroup) mParent).cleanDefaultFocus(this); ((ViewGroup) mParent).clearDefaultFocus(this); } } } Loading Loading @@ -9669,16 +9680,28 @@ public class View implements Drawable.Callback, KeyEvent.Callback, return requestFocus(View.FOCUS_DOWN); } /** * Public for testing. This will request focus for whichever View was last focused within this * cluster before a focus-jump out of it. * * @hide */ public boolean restoreFocusInCluster(@FocusRealDirection int direction) { // Prioritize focusableByDefault over algorithmic focus selection. if (restoreDefaultFocus()) { return true; } return requestFocus(direction); } /** * Gives focus to the default-focus view in the view hierarchy that has this view as a root. * If the default-focus view cannot be found, falls back to calling {@link #requestFocus(int)}. * Nested keyboard navigation clusters are excluded from the hierarchy. * * @param direction The direction of the focus * @return Whether this view or one of its descendants actually took focus */ public boolean restoreDefaultFocus(@FocusDirection int direction) { return requestFocus(direction); public boolean restoreDefaultFocus() { return requestFocus(View.FOCUS_DOWN); } /** Loading core/java/android/view/ViewGroup.java +98 −25 Original line number Diff line number Diff line Loading @@ -141,6 +141,8 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager // The view contained within this ViewGroup (excluding nested keyboard navigation clusters) // that is or contains a default-focus view. private View mDefaultFocus; // The last child of this ViewGroup which held focus within the current cluster private View mFocusedInCluster; /** * A Transformation used when drawing children, to Loading Loading @@ -724,7 +726,7 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager if (mFocused != null) { mFocused.unFocus(this); mFocused = null; mDefaultFocus = null; mFocusedInCluster = null; } super.handleFocusGainInternal(direction, previouslyFocusedRect); } Loading Loading @@ -754,14 +756,9 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager } } /** * Sets the specified child view as the default focus for this view and all its ancestors. * If the view is inside a keyboard navigation cluster, stops at the root of the cluster since * the cluster forms a separate keyboard navigation hierarchy from the default focus point of * view. */ void setDefaultFocus(View child) { if (child.isKeyboardNavigationCluster()) { // Stop at any higher view which is explicitly focused-by-default if (mDefaultFocus != null && mDefaultFocus.isFocusedByDefault()) { return; } Loading @@ -773,21 +770,33 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager } /** * Destroys the default focus chain. * Clears the default-focus chain from {@param child} up to the first parent which has another * default-focusable branch below it or until there is no default-focus chain. * * @param child */ void cleanDefaultFocus(View child) { if (mDefaultFocus != child) { void clearDefaultFocus(View child) { // Stop at any higher view which is explicitly focused-by-default if (mDefaultFocus != child && mDefaultFocus != null && mDefaultFocus.isFocusedByDefault()) { return; } if (child.isKeyboardNavigationCluster()) { mDefaultFocus = null; // Search child siblings for default focusables. for (int i = 0; i < mChildrenCount; ++i) { View sibling = mChildren[i]; if (sibling.isFocusedByDefault()) { mDefaultFocus = sibling; return; } else if (mDefaultFocus == null && sibling.hasDefaultFocus()) { mDefaultFocus = sibling; } } mDefaultFocus = null; if (mParent instanceof ViewGroup) { ((ViewGroup) mParent).cleanDefaultFocus(this); ((ViewGroup) mParent).clearDefaultFocus(this); } } Loading @@ -796,6 +805,35 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager return mDefaultFocus != null || super.hasDefaultFocus(); } void setFocusInCluster(View child) { // Stop at the root of the cluster if (child.isKeyboardNavigationCluster()) { return; } mFocusedInCluster = child; if (mParent instanceof ViewGroup) { ((ViewGroup) mParent).setFocusInCluster(this); } } void clearFocusInCluster(View child) { if (mFocusedInCluster != child) { return; } if (child.isKeyboardNavigationCluster()) { return; } mFocusedInCluster = null; if (mParent instanceof ViewGroup) { ((ViewGroup) mParent).clearFocusInCluster(this); } } @Override public void focusableViewAvailable(View v) { if (mParent != null Loading Loading @@ -3115,14 +3153,28 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager } @Override public boolean restoreDefaultFocus(@FocusDirection int direction) { if (mDefaultFocus != null && !mDefaultFocus.isKeyboardNavigationCluster() public boolean restoreDefaultFocus() { if (mDefaultFocus != null && getDescendantFocusability() != FOCUS_BLOCK_DESCENDANTS && (mDefaultFocus.mViewFlags & VISIBILITY_MASK) == VISIBLE && mDefaultFocus.restoreDefaultFocus(direction)) { && mDefaultFocus.restoreDefaultFocus()) { return true; } return super.restoreDefaultFocus(); } /** * @hide */ @Override public boolean restoreFocusInCluster(@FocusRealDirection int direction) { if (mFocusedInCluster != null && !mFocusedInCluster.isKeyboardNavigationCluster() && getDescendantFocusability() != FOCUS_BLOCK_DESCENDANTS && (mFocusedInCluster.mViewFlags & VISIBILITY_MASK) == VISIBLE && mFocusedInCluster.restoreFocusInCluster(direction)) { return true; } return super.restoreDefaultFocus(direction); return super.restoreFocusInCluster(direction); } /** Loading Loading @@ -5004,8 +5056,8 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager view.unFocus(null); clearChildFocus = true; } if (view == mDefaultFocus) { mDefaultFocus = null; if (view == mFocusedInCluster) { clearFocusInCluster(view); } view.clearAccessibilityFocus(); Loading @@ -5028,6 +5080,9 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager removeFromArray(index); if (view == mDefaultFocus) { clearDefaultFocus(view); } if (clearChildFocus) { clearChildFocus(view); if (!rootViewRequestFocus()) { Loading Loading @@ -5103,6 +5158,7 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager final View focused = mFocused; final boolean detach = mAttachInfo != null; boolean clearChildFocus = false; View clearDefaultFocus = null; final View[] children = mChildren; Loading @@ -5118,7 +5174,10 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager clearChildFocus = true; } if (view == mDefaultFocus) { mDefaultFocus = null; clearDefaultFocus = view; } if (view == mFocusedInCluster) { clearFocusInCluster(view); } view.clearAccessibilityFocus(); Loading @@ -5144,6 +5203,9 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager removeFromArray(start, count); if (clearDefaultFocus != null) { clearDefaultFocus(clearDefaultFocus); } if (clearChildFocus) { clearChildFocus(focused); if (!rootViewRequestFocus()) { Loading Loading @@ -5193,7 +5255,6 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager boolean clearChildFocus = false; needGlobalAttributesUpdate(false); mDefaultFocus = null; for (int i = count - 1; i >= 0; i--) { final View view = children[i]; Loading Loading @@ -5229,6 +5290,9 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager children[i] = null; } if (mDefaultFocus != null) { clearDefaultFocus(mDefaultFocus); } if (clearChildFocus) { clearChildFocus(focused); if (!rootViewRequestFocus()) { Loading Loading @@ -5266,7 +5330,10 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager child.clearFocus(); } if (child == mDefaultFocus) { mDefaultFocus = null; clearDefaultFocus(child); } if (child == mFocusedInCluster) { clearFocusInCluster(child); } child.clearAccessibilityFocus(); Loading Loading @@ -6251,6 +6318,12 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager Log.d(VIEW_LOG_TAG, output); mDefaultFocus.debug(depth + 1); } if (mFocusedInCluster != null) { output = debugIndent(depth); output += "mFocusedInCluster"; Log.d(VIEW_LOG_TAG, output); mFocusedInCluster.debug(depth + 1); } if (mChildrenCount != 0) { output = debugIndent(depth); output += "{"; Loading Loading
api/current.txt +1 −1 Original line number Diff line number Diff line Loading @@ -44754,7 +44754,7 @@ package android.view { method public final void requestUnbufferedDispatch(android.view.MotionEvent); method public static int resolveSize(int, int); method public static int resolveSizeAndState(int, int, int); method public boolean restoreDefaultFocus(int); method public boolean restoreDefaultFocus(); method public void restoreHierarchyState(android.util.SparseArray<android.os.Parcelable>); method public void saveHierarchyState(android.util.SparseArray<android.os.Parcelable>); method public void scheduleDrawable(android.graphics.drawable.Drawable, java.lang.Runnable, long);
api/system-current.txt +1 −1 Original line number Diff line number Diff line Loading @@ -48170,7 +48170,7 @@ package android.view { method public final void requestUnbufferedDispatch(android.view.MotionEvent); method public static int resolveSize(int, int); method public static int resolveSizeAndState(int, int, int); method public boolean restoreDefaultFocus(int); method public boolean restoreDefaultFocus(); method public void restoreHierarchyState(android.util.SparseArray<android.os.Parcelable>); method public void saveHierarchyState(android.util.SparseArray<android.os.Parcelable>); method public void scheduleDrawable(android.graphics.drawable.Drawable, java.lang.Runnable, long);
api/test-current.txt +1 −1 Original line number Diff line number Diff line Loading @@ -45061,7 +45061,7 @@ package android.view { method public final void requestUnbufferedDispatch(android.view.MotionEvent); method public static int resolveSize(int, int); method public static int resolveSizeAndState(int, int, int); method public boolean restoreDefaultFocus(int); method public boolean restoreDefaultFocus(); method public void restoreHierarchyState(android.util.SparseArray<android.os.Parcelable>); method public void saveHierarchyState(android.util.SparseArray<android.os.Parcelable>); method public void scheduleDrawable(android.graphics.drawable.Drawable, java.lang.Runnable, long);
core/java/android/view/View.java +31 −8 Original line number Diff line number Diff line Loading @@ -6125,9 +6125,7 @@ public class View implements Drawable.Callback, KeyEvent.Callback, if (mParent != null) { mParent.requestChildFocus(this, this); if (mParent instanceof ViewGroup) { ((ViewGroup) mParent).setDefaultFocus(this); } setFocusedInCluster(); } if (mAttachInfo != null) { Loading Loading @@ -9244,6 +9242,19 @@ public class View implements Drawable.Callback, KeyEvent.Callback, } } /** * Sets this View as the one which receives focus the next time cluster navigation jumps * to the cluster containing this View. This does NOT change focus even if the cluster * containing this view is current. * * @hide */ public void setFocusedInCluster() { if (mParent instanceof ViewGroup) { ((ViewGroup) mParent).setFocusInCluster(this); } } /** * Returns whether this View should receive focus when the focus is restored for the view * hierarchy containing this view. Loading Loading @@ -9290,7 +9301,7 @@ public class View implements Drawable.Callback, KeyEvent.Callback, if (isFocusedByDefault) { ((ViewGroup) mParent).setDefaultFocus(this); } else { ((ViewGroup) mParent).cleanDefaultFocus(this); ((ViewGroup) mParent).clearDefaultFocus(this); } } } Loading Loading @@ -9669,16 +9680,28 @@ public class View implements Drawable.Callback, KeyEvent.Callback, return requestFocus(View.FOCUS_DOWN); } /** * Public for testing. This will request focus for whichever View was last focused within this * cluster before a focus-jump out of it. * * @hide */ public boolean restoreFocusInCluster(@FocusRealDirection int direction) { // Prioritize focusableByDefault over algorithmic focus selection. if (restoreDefaultFocus()) { return true; } return requestFocus(direction); } /** * Gives focus to the default-focus view in the view hierarchy that has this view as a root. * If the default-focus view cannot be found, falls back to calling {@link #requestFocus(int)}. * Nested keyboard navigation clusters are excluded from the hierarchy. * * @param direction The direction of the focus * @return Whether this view or one of its descendants actually took focus */ public boolean restoreDefaultFocus(@FocusDirection int direction) { return requestFocus(direction); public boolean restoreDefaultFocus() { return requestFocus(View.FOCUS_DOWN); } /** Loading
core/java/android/view/ViewGroup.java +98 −25 Original line number Diff line number Diff line Loading @@ -141,6 +141,8 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager // The view contained within this ViewGroup (excluding nested keyboard navigation clusters) // that is or contains a default-focus view. private View mDefaultFocus; // The last child of this ViewGroup which held focus within the current cluster private View mFocusedInCluster; /** * A Transformation used when drawing children, to Loading Loading @@ -724,7 +726,7 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager if (mFocused != null) { mFocused.unFocus(this); mFocused = null; mDefaultFocus = null; mFocusedInCluster = null; } super.handleFocusGainInternal(direction, previouslyFocusedRect); } Loading Loading @@ -754,14 +756,9 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager } } /** * Sets the specified child view as the default focus for this view and all its ancestors. * If the view is inside a keyboard navigation cluster, stops at the root of the cluster since * the cluster forms a separate keyboard navigation hierarchy from the default focus point of * view. */ void setDefaultFocus(View child) { if (child.isKeyboardNavigationCluster()) { // Stop at any higher view which is explicitly focused-by-default if (mDefaultFocus != null && mDefaultFocus.isFocusedByDefault()) { return; } Loading @@ -773,21 +770,33 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager } /** * Destroys the default focus chain. * Clears the default-focus chain from {@param child} up to the first parent which has another * default-focusable branch below it or until there is no default-focus chain. * * @param child */ void cleanDefaultFocus(View child) { if (mDefaultFocus != child) { void clearDefaultFocus(View child) { // Stop at any higher view which is explicitly focused-by-default if (mDefaultFocus != child && mDefaultFocus != null && mDefaultFocus.isFocusedByDefault()) { return; } if (child.isKeyboardNavigationCluster()) { mDefaultFocus = null; // Search child siblings for default focusables. for (int i = 0; i < mChildrenCount; ++i) { View sibling = mChildren[i]; if (sibling.isFocusedByDefault()) { mDefaultFocus = sibling; return; } else if (mDefaultFocus == null && sibling.hasDefaultFocus()) { mDefaultFocus = sibling; } } mDefaultFocus = null; if (mParent instanceof ViewGroup) { ((ViewGroup) mParent).cleanDefaultFocus(this); ((ViewGroup) mParent).clearDefaultFocus(this); } } Loading @@ -796,6 +805,35 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager return mDefaultFocus != null || super.hasDefaultFocus(); } void setFocusInCluster(View child) { // Stop at the root of the cluster if (child.isKeyboardNavigationCluster()) { return; } mFocusedInCluster = child; if (mParent instanceof ViewGroup) { ((ViewGroup) mParent).setFocusInCluster(this); } } void clearFocusInCluster(View child) { if (mFocusedInCluster != child) { return; } if (child.isKeyboardNavigationCluster()) { return; } mFocusedInCluster = null; if (mParent instanceof ViewGroup) { ((ViewGroup) mParent).clearFocusInCluster(this); } } @Override public void focusableViewAvailable(View v) { if (mParent != null Loading Loading @@ -3115,14 +3153,28 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager } @Override public boolean restoreDefaultFocus(@FocusDirection int direction) { if (mDefaultFocus != null && !mDefaultFocus.isKeyboardNavigationCluster() public boolean restoreDefaultFocus() { if (mDefaultFocus != null && getDescendantFocusability() != FOCUS_BLOCK_DESCENDANTS && (mDefaultFocus.mViewFlags & VISIBILITY_MASK) == VISIBLE && mDefaultFocus.restoreDefaultFocus(direction)) { && mDefaultFocus.restoreDefaultFocus()) { return true; } return super.restoreDefaultFocus(); } /** * @hide */ @Override public boolean restoreFocusInCluster(@FocusRealDirection int direction) { if (mFocusedInCluster != null && !mFocusedInCluster.isKeyboardNavigationCluster() && getDescendantFocusability() != FOCUS_BLOCK_DESCENDANTS && (mFocusedInCluster.mViewFlags & VISIBILITY_MASK) == VISIBLE && mFocusedInCluster.restoreFocusInCluster(direction)) { return true; } return super.restoreDefaultFocus(direction); return super.restoreFocusInCluster(direction); } /** Loading Loading @@ -5004,8 +5056,8 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager view.unFocus(null); clearChildFocus = true; } if (view == mDefaultFocus) { mDefaultFocus = null; if (view == mFocusedInCluster) { clearFocusInCluster(view); } view.clearAccessibilityFocus(); Loading @@ -5028,6 +5080,9 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager removeFromArray(index); if (view == mDefaultFocus) { clearDefaultFocus(view); } if (clearChildFocus) { clearChildFocus(view); if (!rootViewRequestFocus()) { Loading Loading @@ -5103,6 +5158,7 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager final View focused = mFocused; final boolean detach = mAttachInfo != null; boolean clearChildFocus = false; View clearDefaultFocus = null; final View[] children = mChildren; Loading @@ -5118,7 +5174,10 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager clearChildFocus = true; } if (view == mDefaultFocus) { mDefaultFocus = null; clearDefaultFocus = view; } if (view == mFocusedInCluster) { clearFocusInCluster(view); } view.clearAccessibilityFocus(); Loading @@ -5144,6 +5203,9 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager removeFromArray(start, count); if (clearDefaultFocus != null) { clearDefaultFocus(clearDefaultFocus); } if (clearChildFocus) { clearChildFocus(focused); if (!rootViewRequestFocus()) { Loading Loading @@ -5193,7 +5255,6 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager boolean clearChildFocus = false; needGlobalAttributesUpdate(false); mDefaultFocus = null; for (int i = count - 1; i >= 0; i--) { final View view = children[i]; Loading Loading @@ -5229,6 +5290,9 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager children[i] = null; } if (mDefaultFocus != null) { clearDefaultFocus(mDefaultFocus); } if (clearChildFocus) { clearChildFocus(focused); if (!rootViewRequestFocus()) { Loading Loading @@ -5266,7 +5330,10 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager child.clearFocus(); } if (child == mDefaultFocus) { mDefaultFocus = null; clearDefaultFocus(child); } if (child == mFocusedInCluster) { clearFocusInCluster(child); } child.clearAccessibilityFocus(); Loading Loading @@ -6251,6 +6318,12 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager Log.d(VIEW_LOG_TAG, output); mDefaultFocus.debug(depth + 1); } if (mFocusedInCluster != null) { output = debugIndent(depth); output += "mFocusedInCluster"; Log.d(VIEW_LOG_TAG, output); mFocusedInCluster.debug(depth + 1); } if (mChildrenCount != 0) { output = debugIndent(depth); output += "{"; Loading