Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(299)

Side by Side Diff: content/public/android/java/src/org/chromium/content/browser/ContentViewCore.java

Issue 2779033004: [Android] Focus/Blur contents when window focus changes (Closed)
Patch Set: Add comments Created 3 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2012 The Chromium Authors. All rights reserved. 1 // Copyright 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 package org.chromium.content.browser; 5 package org.chromium.content.browser;
6 6
7 import android.annotation.SuppressLint; 7 import android.annotation.SuppressLint;
8 import android.annotation.TargetApi; 8 import android.annotation.TargetApi;
9 import android.app.assist.AssistStructure.ViewNode; 9 import android.app.assist.AssistStructure.ViewNode;
10 import android.content.ClipData; 10 import android.content.ClipData;
(...skipping 342 matching lines...) Expand 10 before | Expand all | Expand 10 after
353 // screen orientation. 353 // screen orientation.
354 private boolean mFullscreenRequiredForOrientationLock = true; 354 private boolean mFullscreenRequiredForOrientationLock = true;
355 355
356 // A ViewAndroidDelegate that delegates to the current container view. 356 // A ViewAndroidDelegate that delegates to the current container view.
357 private ViewAndroidDelegate mViewAndroidDelegate; 357 private ViewAndroidDelegate mViewAndroidDelegate;
358 358
359 // NOTE: This object will not be released by Android framework until the mat ching 359 // NOTE: This object will not be released by Android framework until the mat ching
360 // ResultReceiver in the InputMethodService (IME app) gets gc'ed. 360 // ResultReceiver in the InputMethodService (IME app) gets gc'ed.
361 private ShowKeyboardResultReceiver mShowKeyboardResultReceiver; 361 private ShowKeyboardResultReceiver mShowKeyboardResultReceiver;
362 362
363 // Whether this ContentViewCore has view focus.
364 private boolean mHasViewFocus;
365 // Whether this ContentViewCore has window focus.
366 private boolean mHasWindowFocus;
367
363 // The list of observers that are notified when ContentViewCore changes its WindowAndroid. 368 // The list of observers that are notified when ContentViewCore changes its WindowAndroid.
364 private final ObserverList<WindowAndroidChangedObserver> mWindowAndroidChang edObservers; 369 private final ObserverList<WindowAndroidChangedObserver> mWindowAndroidChang edObservers;
365 370
366 /** 371 /**
367 * @param webContents The {@link WebContents} to find a {@link ContentViewCo re} of. 372 * @param webContents The {@link WebContents} to find a {@link ContentViewCo re} of.
368 * @return A {@link ContentViewCore} that is connected to {@code webContents} or 373 * @return A {@link ContentViewCore} that is connected to {@code webContents} or
369 * {@code null} if none exists. 374 * {@code null} if none exists.
370 */ 375 */
371 public static ContentViewCore fromWebContents(WebContents webContents) { 376 public static ContentViewCore fromWebContents(WebContents webContents) {
372 return nativeFromWebContentsAndroid(webContents); 377 return nativeFromWebContentsAndroid(webContents);
(...skipping 172 matching lines...) Expand 10 before | Expand all | Expand 10 after
545 // is a vital component of the ContentViewCore, so embedders must exercise c aution in what 550 // is a vital component of the ContentViewCore, so embedders must exercise c aution in what
546 // they do with the ContentViewCore before calling initialize(). 551 // they do with the ContentViewCore before calling initialize().
547 // We supply the nativeWebContents pointer here rather than in the construct or to allow us 552 // We supply the nativeWebContents pointer here rather than in the construct or to allow us
548 // to set the private browsing mode at a later point for the WebView impleme ntation. 553 // to set the private browsing mode at a later point for the WebView impleme ntation.
549 // Note that the caller remains the owner of the nativeWebContents and is re sponsible for 554 // Note that the caller remains the owner of the nativeWebContents and is re sponsible for
550 // deleting it after destroying the ContentViewCore. 555 // deleting it after destroying the ContentViewCore.
551 public void initialize(ViewAndroidDelegate viewDelegate, 556 public void initialize(ViewAndroidDelegate viewDelegate,
552 InternalAccessDelegate internalDispatcher, WebContents webContents, 557 InternalAccessDelegate internalDispatcher, WebContents webContents,
553 WindowAndroid windowAndroid) { 558 WindowAndroid windowAndroid) {
554 mViewAndroidDelegate = viewDelegate; 559 mViewAndroidDelegate = viewDelegate;
555 setContainerView(viewDelegate.getContainerView()); 560 setContainerView(viewDelegate.getContainerView(), false);
aelias_OOO_until_Jul13 2017/04/03 21:57:56 Could you try just moving this to the end of the c
mthiesse 2017/04/05 14:11:23 Done.
556 long windowNativePointer = windowAndroid.getNativePointer(); 561 long windowNativePointer = windowAndroid.getNativePointer();
557 assert windowNativePointer != 0; 562 assert windowNativePointer != 0;
558 563
559 final float dipScale = windowAndroid.getDisplay().getDipScale(); 564 final float dipScale = windowAndroid.getDisplay().getDipScale();
560 565
561 mRenderCoordinates.reset(); 566 mRenderCoordinates.reset();
562 mRenderCoordinates.setDeviceScaleFactor(dipScale, windowAndroid.getConte xt()); 567 mRenderCoordinates.setDeviceScaleFactor(dipScale, windowAndroid.getConte xt());
563 568
564 mNativeContentViewCore = nativeInit(webContents, mViewAndroidDelegate, w indowNativePointer, 569 mNativeContentViewCore = nativeInit(webContents, mViewAndroidDelegate, w indowNativePointer,
565 dipScale, mRetainedJavaScriptObjects); 570 dipScale, mRetainedJavaScriptObjects);
566 mWebContents = nativeGetWebContentsAndroid(mNativeContentViewCore); 571 mWebContents = nativeGetWebContentsAndroid(mNativeContentViewCore);
567 572
568 setContainerViewInternals(internalDispatcher); 573 setContainerViewInternals(internalDispatcher);
569 574
570 initPopupZoomer(mContext); 575 initPopupZoomer(mContext);
571 mImeAdapter = createImeAdapter(); 576 mImeAdapter = createImeAdapter();
572 attachImeAdapter(); 577 attachImeAdapter();
573 578
574 mSelectionPopupController = new SelectionPopupController(mContext, windo wAndroid, 579 mSelectionPopupController = new SelectionPopupController(mContext, windo wAndroid,
575 webContents, viewDelegate.getContainerView(), mRenderCoordinates , mImeAdapter); 580 webContents, viewDelegate.getContainerView(), mRenderCoordinates , mImeAdapter);
576 mSelectionPopupController.setCallback(ActionModeCallbackHelper.EMPTY_CAL LBACK); 581 mSelectionPopupController.setCallback(ActionModeCallbackHelper.EMPTY_CAL LBACK);
577 mSelectionPopupController.setContainerView(getContainerView()); 582 mSelectionPopupController.setContainerView(getContainerView());
578 583
579 mWebContentsObserver = new ContentViewWebContentsObserver(this); 584 mWebContentsObserver = new ContentViewWebContentsObserver(this);
580 585
581 mShouldRequestUnbufferedDispatch = Build.VERSION.SDK_INT >= Build.VERSIO N_CODES.LOLLIPOP 586 mShouldRequestUnbufferedDispatch = Build.VERSION.SDK_INT >= Build.VERSIO N_CODES.LOLLIPOP
582 && ContentFeatureList.isEnabled(ContentFeatureList.REQUEST_UNBUF FERED_DISPATCH); 587 && ContentFeatureList.isEnabled(ContentFeatureList.REQUEST_UNBUF FERED_DISPATCH);
588
589 onFocusChangedInternal(getRealWindowFocusedState(), mContainerView.hasFo cus(),
590 false /* hideKeyboardOnBlur */);
583 } 591 }
584 592
585 /** 593 /**
586 * Updates the native {@link ContentViewCore} with a new window. This moves the NativeView and 594 * Updates the native {@link ContentViewCore} with a new window. This moves the NativeView and
587 * attached it to the new NativeWindow linked with the given {@link WindowAn droid}. 595 * attached it to the new NativeWindow linked with the given {@link WindowAn droid}.
588 * @param windowAndroid The new {@link WindowAndroid} for this {@link Conten tViewCore}. 596 * @param windowAndroid The new {@link WindowAndroid} for this {@link Conten tViewCore}.
589 */ 597 */
590 public void updateWindowAndroid(WindowAndroid windowAndroid) { 598 public void updateWindowAndroid(WindowAndroid windowAndroid) {
591 removeDisplayAndroidObserver(); 599 removeDisplayAndroidObserver();
592 long windowNativePointer = windowAndroid == null ? 0 : windowAndroid.get NativePointer(); 600 long windowNativePointer = windowAndroid == null ? 0 : windowAndroid.get NativePointer();
(...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after
632 } 640 }
633 641
634 private void removeDisplayAndroidObserver() { 642 private void removeDisplayAndroidObserver() {
635 WindowAndroid windowAndroid = getWindowAndroid(); 643 WindowAndroid windowAndroid = getWindowAndroid();
636 if (windowAndroid != null) { 644 if (windowAndroid != null) {
637 windowAndroid.getDisplay().removeObserver(this); 645 windowAndroid.getDisplay().removeObserver(this);
638 } 646 }
639 } 647 }
640 648
641 /** 649 /**
642 * Sets a new container view for this {@link ContentViewCore}. 650 * Replaces the container view for this {@link ContentViewCore}. This Conten tViewCore must
651 * already have been initialized.
643 * 652 *
644 * <p>WARNING: This method can also be used to replace the existing containe r view, 653 * <p>WARNING: You should only use this method if you have a very good reaso n to. Replacing the
645 * but you should only do it if you have a very good reason to. Replacing th e 654 * container view has been designed to support fullscreen in the Webview so it might not be
646 * container view has been designed to support fullscreen in the Webview so it 655 * appropriate for other use cases.
647 * might not be appropriate for other use cases.
648 * 656 *
649 * <p>This method only performs a small part of replacing the container view and 657 * <p>This method only performs a small part of replacing the container view and
650 * embedders are responsible for: 658 * embedders are responsible for:
651 * <ul> 659 * <ul>
652 * <li>Disconnecting the old container view from this ContentViewCore</l i> 660 * <li>Disconnecting the old container view from this ContentViewCore</l i>
653 * <li>Updating the InternalAccessDelegate</li> 661 * <li>Updating the InternalAccessDelegate</li>
654 * <li>Reconciling the state of this ContentViewCore with the new contai ner view</li> 662 * <li>Reconciling the state of this ContentViewCore with the new contai ner view</li>
655 * <li>Tearing down and recreating the native GL rendering where appropr iate</li> 663 * <li>Tearing down and recreating the native GL rendering where appropr iate</li>
656 * <li>etc.</li> 664 * <li>etc.</li>
657 * </ul> 665 * </ul>
658 */ 666 */
659 public void setContainerView(ViewGroup containerView) { 667 public void replaceContainerView(ViewGroup containerView) {
668 assert mContainerView != null;
669 setContainerView(containerView, true);
670 }
671
672 /**
673 * Sets the container view for this {@link ContentViewCore}.
674 */
675 private void setContainerView(ViewGroup containerView, boolean initialized) {
660 try { 676 try {
661 TraceEvent.begin("ContentViewCore.setContainerView"); 677 TraceEvent.begin("ContentViewCore.setContainerView");
662 if (mContainerView != null) { 678 if (mContainerView != null) {
663 hideSelectPopupWithCancelMessage(); 679 hideSelectPopupWithCancelMessage();
664 mPopupZoomer.hide(false); 680 mPopupZoomer.hide(false);
665 } 681 }
666 682
667 mContainerView = containerView; 683 mContainerView = containerView;
668 mContainerView.setClickable(true); 684 mContainerView.setClickable(true);
669 if (mSelectionPopupController != null) { 685 if (mSelectionPopupController != null) {
670 mSelectionPopupController.setContainerView(containerView); 686 mSelectionPopupController.setContainerView(containerView);
671 } 687 }
672 if (mJoystickScrollProvider != null) { 688 if (mJoystickScrollProvider != null) {
673 mJoystickScrollProvider.setContainerView(containerView); 689 mJoystickScrollProvider.setContainerView(containerView);
674 } 690 }
675 if (mJoystickZoomProvider != null) { 691 if (mJoystickZoomProvider != null) {
676 mJoystickZoomProvider.setContainerView(containerView); 692 mJoystickZoomProvider.setContainerView(containerView);
677 } 693 }
694 if (initialized) {
695 onFocusChangedInternal(getRealWindowFocusedState(), mContainerVi ew.hasFocus(),
696 false /* hideKeyboardOnBlur */);
697 }
678 } finally { 698 } finally {
679 TraceEvent.end("ContentViewCore.setContainerView"); 699 TraceEvent.end("ContentViewCore.setContainerView");
680 } 700 }
681 } 701 }
682 702
703 /**
704 * Note: We don't use View#hasWindowFocus() because it returns incorrect val ues when the View
705 * doesn't have View focus.
706 * @return Whether the containerView actually has Window focus.
707 */
708 private boolean getRealWindowFocusedState() {
709 int[] states = mContainerView.getDrawableState();
710 for (int state : states) {
711 if ((state & android.R.attr.state_window_focused) != 0) return true;
712 }
713 return false;
714 }
715
683 @CalledByNative 716 @CalledByNative
684 private void onNativeContentViewCoreDestroyed(long nativeContentViewCore) { 717 private void onNativeContentViewCoreDestroyed(long nativeContentViewCore) {
685 assert nativeContentViewCore == mNativeContentViewCore; 718 assert nativeContentViewCore == mNativeContentViewCore;
686 mNativeContentViewCore = 0; 719 mNativeContentViewCore = 0;
687 } 720 }
688 721
689 /** 722 /**
690 * Set the Container view Internals. 723 * Set the Container view Internals.
691 * @param internalDispatcher Handles dispatching all hidden or super methods to the 724 * @param internalDispatcher Handles dispatching all hidden or super methods to the
692 * containerView. 725 * containerView.
(...skipping 627 matching lines...) Expand 10 before | Expand all | Expand 10 after
1320 } 1353 }
1321 1354
1322 private void cancelRequestToScrollFocusedEditableNodeIntoView() { 1355 private void cancelRequestToScrollFocusedEditableNodeIntoView() {
1323 // Zero-ing the rect will prevent |updateAfterSizeChanged()| from 1356 // Zero-ing the rect will prevent |updateAfterSizeChanged()| from
1324 // issuing the delayed form focus event. 1357 // issuing the delayed form focus event.
1325 mFocusPreOSKViewportRect.setEmpty(); 1358 mFocusPreOSKViewportRect.setEmpty();
1326 } 1359 }
1327 1360
1328 /** 1361 /**
1329 * @see View#onWindowFocusChanged(boolean) 1362 * @see View#onWindowFocusChanged(boolean)
1363 *
1364 * This function must only be called after this ContentViewCore has been ini tialized.
1330 */ 1365 */
1331 public void onWindowFocusChanged(boolean hasWindowFocus) { 1366 public void onWindowFocusChanged(boolean hasWindowFocus) {
1367 if (mHasWindowFocus == hasWindowFocus) return;
1332 mImeAdapter.onWindowFocusChanged(hasWindowFocus); 1368 mImeAdapter.onWindowFocusChanged(hasWindowFocus);
1333 if (!hasWindowFocus) resetGestureDetection(); 1369 if (!hasWindowFocus) resetGestureDetection();
1334 mSelectionPopupController.onWindowFocusChanged(hasWindowFocus); 1370 mSelectionPopupController.onWindowFocusChanged(hasWindowFocus);
1335 for (mGestureStateListenersIterator.rewind(); mGestureStateListenersIter ator.hasNext();) { 1371 for (mGestureStateListenersIterator.rewind(); mGestureStateListenersIter ator.hasNext();) {
1336 mGestureStateListenersIterator.next().onWindowFocusChanged(hasWindow Focus); 1372 mGestureStateListenersIterator.next().onWindowFocusChanged(hasWindow Focus);
1337 } 1373 }
1374 onFocusChangedInternal(hasWindowFocus, mHasViewFocus, true /* hideKeyboa rdOnBlur */);
1338 } 1375 }
1339 1376
1340 public void onFocusChanged(boolean gainFocus, boolean hideKeyboardOnBlur) { 1377 /**
1341 mImeAdapter.onViewFocusChanged(gainFocus, hideKeyboardOnBlur); 1378 * Called when the View focus for this ContentViewCore changes.
1379 *
1380 * This function must only be called after this ContentViewCore has been ini tialized.
1381 */
1382 public void onFocusChanged(boolean hasViewFocus, boolean hideKeyboardOnBlur) {
1383 if (mHasViewFocus == hasViewFocus) return;
1384 mImeAdapter.onViewFocusChanged(hasViewFocus, hideKeyboardOnBlur);
1385 onFocusChangedInternal(mHasWindowFocus, hasViewFocus, hideKeyboardOnBlur );
1386 }
1387
1388 private void onFocusChangedInternal(
1389 boolean hasWindowFocus, boolean hasViewFocus, boolean hideKeyboardOn Blur) {
1390 boolean hadInputFocus = mHasWindowFocus && mHasViewFocus;
1391 boolean hasInputFocus = hasWindowFocus && hasViewFocus;
1392 mHasWindowFocus = hasWindowFocus;
1393 mHasViewFocus = hasViewFocus;
1394 if (hasInputFocus == hadInputFocus) return;
1342 1395
1343 if (mJoystickScrollProvider != null) { 1396 if (mJoystickScrollProvider != null) {
1344 mJoystickScrollProvider.setEnabled(gainFocus && !isFocusedNodeEditab le()); 1397 mJoystickScrollProvider.setEnabled(hasInputFocus && !isFocusedNodeEd itable());
1345 } 1398 }
1346 1399
1347 if (gainFocus) { 1400 if (hasInputFocus) {
1348 restoreSelectionPopupsIfNecessary(); 1401 restoreSelectionPopupsIfNecessary();
1349 } else { 1402 } else {
1350 cancelRequestToScrollFocusedEditableNodeIntoView(); 1403 cancelRequestToScrollFocusedEditableNodeIntoView();
1351 if (mPreserveSelectionOnNextLossOfFocus) { 1404 if (mPreserveSelectionOnNextLossOfFocus) {
1352 mPreserveSelectionOnNextLossOfFocus = false; 1405 mPreserveSelectionOnNextLossOfFocus = false;
1353 hidePopupsAndPreserveSelection(); 1406 hidePopupsAndPreserveSelection();
1354 } else { 1407 } else {
1355 hidePopupsAndClearSelection(); 1408 hidePopupsAndClearSelection();
1356 // Clear the selection. The selection is cleared on destroying I ME 1409 // Clear the selection. The selection is cleared on destroying I ME
1357 // and also here since we may receive destroy first, for example 1410 // and also here since we may receive destroy first, for example
1358 // when focus is lost in webview. 1411 // when focus is lost in webview.
1359 clearSelection(); 1412 clearSelection();
1360 } 1413 }
1361 } 1414 }
1362 if (mNativeContentViewCore != 0) nativeSetFocus(mNativeContentViewCore, gainFocus); 1415 if (mNativeContentViewCore != 0) nativeSetFocus(mNativeContentViewCore, hasInputFocus);
1363 } 1416 }
1364 1417
1365 /** 1418 /**
1366 * @see View#onKeyUp(int, KeyEvent) 1419 * @see View#onKeyUp(int, KeyEvent)
1367 */ 1420 */
1368 public boolean onKeyUp(int keyCode, KeyEvent event) { 1421 public boolean onKeyUp(int keyCode, KeyEvent event) {
1369 if (mPopupZoomer.isShowing() && keyCode == KeyEvent.KEYCODE_BACK) { 1422 if (mPopupZoomer.isShowing() && keyCode == KeyEvent.KEYCODE_BACK) {
1370 mPopupZoomer.backButtonPressed(); 1423 mPopupZoomer.backButtonPressed();
1371 return true; 1424 return true;
1372 } 1425 }
(...skipping 1312 matching lines...) Expand 10 before | Expand all | Expand 10 after
2685 private native void nativeSetTextTrackSettings(long nativeContentViewCoreImp l, 2738 private native void nativeSetTextTrackSettings(long nativeContentViewCoreImp l,
2686 boolean textTracksEnabled, String textTrackBackgroundColor, String t extTrackFontFamily, 2739 boolean textTracksEnabled, String textTrackBackgroundColor, String t extTrackFontFamily,
2687 String textTrackFontStyle, String textTrackFontVariant, String textT rackTextColor, 2740 String textTrackFontStyle, String textTrackFontVariant, String textT rackTextColor,
2688 String textTrackTextShadow, String textTrackTextSize); 2741 String textTrackTextShadow, String textTrackTextSize);
2689 2742
2690 private native void nativeSetBackgroundOpaque(long nativeContentViewCoreImpl , boolean opaque); 2743 private native void nativeSetBackgroundOpaque(long nativeContentViewCoreImpl , boolean opaque);
2691 private native boolean nativeIsTouchDragDropEnabled(long nativeContentViewCo reImpl); 2744 private native boolean nativeIsTouchDragDropEnabled(long nativeContentViewCo reImpl);
2692 private native void nativeOnDragEvent(long nativeContentViewCoreImpl, int ac tion, int x, int y, 2745 private native void nativeOnDragEvent(long nativeContentViewCoreImpl, int ac tion, int x, int y,
2693 int screenX, int screenY, String[] mimeTypes, String content); 2746 int screenX, int screenY, String[] mimeTypes, String content);
2694 } 2747 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698