diff options
| author | Svetoslav Ganov <svetoslavganov@google.com> | 2012-01-30 16:37:33 -0800 |
|---|---|---|
| committer | Android (Google) Code Review <android-gerrit@google.com> | 2012-01-30 16:37:33 -0800 |
| commit | 12df3cf156885a421beccfa6b6e20fd1a188847a (patch) | |
| tree | b72fe4d32ebffbadf5006e525a1027aeb3c380fb /core/java/android/view | |
| parent | f68af846d472e59f1a8280f250a1f0b9ac13abd9 (diff) | |
| parent | c6fd88e213703a581fe4680259981f09ae0444f2 (diff) | |
| download | frameworks_base-12df3cf156885a421beccfa6b6e20fd1a188847a.zip frameworks_base-12df3cf156885a421beccfa6b6e20fd1a188847a.tar.gz frameworks_base-12df3cf156885a421beccfa6b6e20fd1a188847a.tar.bz2 | |
Merge "Incorrect behavior of View clear focus."
Diffstat (limited to 'core/java/android/view')
| -rw-r--r-- | core/java/android/view/View.java | 23 | ||||
| -rw-r--r-- | core/java/android/view/ViewGroup.java | 19 | ||||
| -rw-r--r-- | core/java/android/view/ViewRootImpl.java | 35 |
3 files changed, 53 insertions, 24 deletions
diff --git a/core/java/android/view/View.java b/core/java/android/view/View.java index 39f603d..343891a 100644 --- a/core/java/android/view/View.java +++ b/core/java/android/view/View.java @@ -3770,6 +3770,14 @@ public class View implements Drawable.Callback, Drawable.Callback2, KeyEvent.Cal } if ((mPrivateFlags & FOCUSED) != 0) { + // If this is the first focusable do not clear focus since the we + // try to give it focus every time a view clears its focus. Hence, + // the view that would gain focus already has it. + View firstFocusable = getFirstFocusable(); + if (firstFocusable == this) { + return; + } + mPrivateFlags &= ~FOCUSED; if (mParent != null) { @@ -3778,9 +3786,24 @@ public class View implements Drawable.Callback, Drawable.Callback2, KeyEvent.Cal onFocusChanged(false, 0, null); refreshDrawableState(); + + // The view cleared focus and invoked the callbacks, so now is the + // time to give focus to the the first focusable to ensure that the + // gain focus is announced after clear focus. + if (firstFocusable != null) { + firstFocusable.requestFocus(FOCUS_FORWARD); + } } } + private View getFirstFocusable() { + ViewRootImpl viewRoot = getViewRootImpl(); + if (viewRoot != null) { + return viewRoot.focusSearch(null, FOCUS_FORWARD); + } + return null; + } + /** * Called to clear the focus of a view that is about to be removed. * Doesn't call clearChildFocus, which prevents this view from taking diff --git a/core/java/android/view/ViewGroup.java b/core/java/android/view/ViewGroup.java index d906a16..7559862 100644 --- a/core/java/android/view/ViewGroup.java +++ b/core/java/android/view/ViewGroup.java @@ -675,11 +675,14 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager */ @Override public void clearFocus() { - super.clearFocus(); - - // clear any child focus if it exists - if (mFocused != null) { + if (DBG) { + System.out.println(this + " clearFocus()"); + } + if (mFocused == null) { + super.clearFocus(); + } else { mFocused.clearFocus(); + mFocused = null; } } @@ -691,12 +694,12 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager if (DBG) { System.out.println(this + " unFocus()"); } - - super.unFocus(); - if (mFocused != null) { + if (mFocused == null) { + super.unFocus(); + } else { mFocused.unFocus(); + mFocused = null; } - mFocused = null; } /** diff --git a/core/java/android/view/ViewRootImpl.java b/core/java/android/view/ViewRootImpl.java index 1a4bdf4..2ef843b 100644 --- a/core/java/android/view/ViewRootImpl.java +++ b/core/java/android/view/ViewRootImpl.java @@ -168,6 +168,7 @@ public final class ViewRootImpl extends Handler implements ViewParent, View mView; View mFocusedView; View mRealFocusedView; // this is not set to null in touch mode + View mOldFocusedView; int mViewVisibility; boolean mAppVisible = true; int mOrigWindowType = -1; @@ -2226,32 +2227,33 @@ public final class ViewRootImpl extends Handler implements ViewParent, public void requestChildFocus(View child, View focused) { checkThread(); - if (mFocusedView != focused) { - mAttachInfo.mTreeObserver.dispatchOnGlobalFocusChange(mFocusedView, focused); - scheduleTraversals(); + + if (DEBUG_INPUT_RESIZE) { + Log.v(TAG, "Request child focus: focus now " + focused); } + + mAttachInfo.mTreeObserver.dispatchOnGlobalFocusChange(mOldFocusedView, focused); + scheduleTraversals(); + mFocusedView = mRealFocusedView = focused; - if (DEBUG_INPUT_RESIZE) Log.v(TAG, "Request child focus: focus now " - + mFocusedView); } public void clearChildFocus(View child) { checkThread(); - View oldFocus = mFocusedView; + if (DEBUG_INPUT_RESIZE) { + Log.v(TAG, "Clearing child focus"); + } + + mOldFocusedView = mFocusedView; - if (DEBUG_INPUT_RESIZE) Log.v(TAG, "Clearing child focus"); - mFocusedView = mRealFocusedView = null; - if (mView != null && !mView.hasFocus()) { - // If a view gets the focus, the listener will be invoked from requestChildFocus() - if (!mView.requestFocus(View.FOCUS_FORWARD)) { - mAttachInfo.mTreeObserver.dispatchOnGlobalFocusChange(oldFocus, null); - } - } else if (oldFocus != null) { - mAttachInfo.mTreeObserver.dispatchOnGlobalFocusChange(oldFocus, null); + // Invoke the listener only if there is no view to take focus + if (focusSearch(null, View.FOCUS_FORWARD) == null) { + mAttachInfo.mTreeObserver.dispatchOnGlobalFocusChange(mOldFocusedView, null); } - } + mFocusedView = mRealFocusedView = null; + } public void focusableViewAvailable(View v) { checkThread(); @@ -2724,6 +2726,7 @@ public final class ViewRootImpl extends Handler implements ViewParent, mView.unFocus(); mAttachInfo.mTreeObserver.dispatchOnGlobalFocusChange(focused, null); mFocusedView = null; + mOldFocusedView = null; return true; } } |
