// Copyright 2022 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
package org.chromium.chrome.browser.toolbar.top;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertTrue;
import static org.mockito.ArgumentMatchers.anyInt;
import static org.mockito.Mockito.atLeastOnce;
import static org.mockito.Mockito.doReturn;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;
import android.animation.ObjectAnimator;
import android.animation.ValueAnimator;
import android.app.Activity;
import android.content.res.ColorStateList;
import android.graphics.Color;
import android.graphics.drawable.Drawable;
import android.os.Looper;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.View.OnLongClickListener;
import android.widget.ImageButton;
import android.widget.LinearLayout;
import androidx.appcompat.content.res.AppCompatResources;
import org.junit.After;
import org.junit.Assert;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.Mock;
import org.mockito.Mockito;
import org.mockito.MockitoAnnotations;
import org.robolectric.Robolectric;
import org.robolectric.Shadows;
import org.robolectric.annotation.LooperMode;
import org.robolectric.shadows.ShadowLooper;
import org.robolectric.shadows.ShadowToast;
import org.chromium.base.test.BaseRobolectricTestRunner;
import org.chromium.base.test.util.Features.DisableFeatures;
import org.chromium.base.test.util.Features.EnableFeatures;
import org.chromium.chrome.browser.flags.ChromeFeatureList;
import org.chromium.chrome.browser.omnibox.LocationBarCoordinator;
import org.chromium.chrome.browser.omnibox.LocationBarCoordinatorTablet;
import org.chromium.chrome.browser.omnibox.LocationBarLayout;
import org.chromium.chrome.browser.omnibox.NewTabPageDelegate;
import org.chromium.chrome.browser.omnibox.status.StatusCoordinator;
import org.chromium.chrome.browser.theme.ThemeUtils;
import org.chromium.chrome.browser.toolbar.ButtonData.ButtonSpec;
import org.chromium.chrome.browser.toolbar.ButtonDataImpl;
import org.chromium.chrome.browser.toolbar.R;
import org.chromium.chrome.browser.toolbar.ToolbarDataProvider;
import org.chromium.chrome.browser.toolbar.adaptive.AdaptiveToolbarButtonVariant;
import org.chromium.chrome.browser.toolbar.menu_button.MenuButtonCoordinator;
import org.chromium.chrome.browser.toolbar.top.CaptureReadinessResult.TopToolbarAllowCaptureReason;
import org.chromium.chrome.browser.toolbar.top.CaptureReadinessResult.TopToolbarBlockCaptureReason;
import org.chromium.chrome.browser.toolbar.top.TopToolbarCoordinator.ToolbarColorObserver;
import org.chromium.chrome.browser.toolbar.top.tab_strip.TabStripTransitionCoordinator;
import org.chromium.chrome.browser.ui.theme.BrandedColorScheme;
import org.chromium.ui.widget.ToastManager;
import java.util.ArrayList;
import java.util.List;
/** Unit tests for @{@link ToolbarTablet} */
@LooperMode(LooperMode.Mode.PAUSED)
@RunWith(BaseRobolectricTestRunner.class)
public final class ToolbarTabletUnitTest {
@Mock private LocationBarCoordinator mLocationBar;
@Mock private LocationBarCoordinatorTablet mLocationBarTablet;
@Mock private ToggleTabStackButtonCoordinator mTabSwitcherButtonCoordinator;
@Mock private StatusCoordinator mStatusCoordinator;
@Mock private MenuButtonCoordinator mMenuButtonCoordinator;
@Mock private TabStripTransitionCoordinator mTabStripTransitionCoordinator;
@Mock private ToolbarColorObserver mToolbarColorObserver;
@Mock private ToolbarDataProvider mToolbarDataProvider;
@Mock private NewTabPageDelegate mNewTabPageDelegate;
private Activity mActivity;
private ToolbarTablet mToolbarTablet;
private LinearLayout mToolbarTabletLayout;
private ImageButton mHomeButton;
private ImageButton mReloadingButton;
private ImageButton mBackButton;
private ImageButton mForwardButton;
private ImageButton mMenuButton;
private ToggleTabStackButton mTabSwitcherButton;
private ImageButton mBookmarkButton;
private ImageButton mSaveOfflineButton;
private View mLocationBarButton;
@Before
public void setUp() {
MockitoAnnotations.initMocks(this);
mActivity = Robolectric.buildActivity(Activity.class).setup().get();
mActivity.setTheme(R.style.Theme_BrowserUI_DayNight);
ToolbarTablet realView =
(ToolbarTablet)
mActivity.getLayoutInflater().inflate(R.layout.toolbar_tablet, null);
mToolbarTablet = Mockito.spy(realView);
when(mLocationBar.getTabletCoordinator()).thenReturn(mLocationBarTablet);
mToolbarTablet.setLocationBarCoordinator(mLocationBar);
LocationBarLayout locationBarLayout = mToolbarTablet.findViewById(R.id.location_bar);
locationBarLayout.setStatusCoordinatorForTesting(mStatusCoordinator);
mToolbarTablet.setMenuButtonCoordinatorForTesting(mMenuButtonCoordinator);
mToolbarTablet.setTabSwitcherButtonCoordinatorForTesting(mTabSwitcherButtonCoordinator);
mToolbarTablet.setTabStripTransitionCoordinator(mTabStripTransitionCoordinator);
mToolbarTablet.setToolbarColorObserver(mToolbarColorObserver);
mToolbarTabletLayout =
(LinearLayout) mToolbarTablet.findViewById(R.id.toolbar_tablet_layout);
mHomeButton = mToolbarTablet.findViewById(R.id.home_button);
mBackButton = mToolbarTablet.findViewById(R.id.back_button);
mForwardButton = mToolbarTablet.findViewById(R.id.forward_button);
mReloadingButton = mToolbarTablet.findViewById(R.id.refresh_button);
mMenuButton = mToolbarTablet.findViewById(R.id.menu_button);
mTabSwitcherButton = mToolbarTablet.findViewById(R.id.tab_switcher_button);
when(mTabSwitcherButtonCoordinator.getContainerView()).thenReturn(mTabSwitcherButton);
mLocationBarButton = mToolbarTablet.findViewById(R.id.location_bar_status_icon);
mBookmarkButton = mToolbarTablet.findViewById(R.id.bookmark_button);
mSaveOfflineButton = mToolbarTablet.findViewById(R.id.save_offline_button);
}
@After
public void tearDown() {
ToastManager.resetForTesting();
}
@Test
public void testButtonPosition() {
mToolbarTablet.onFinishInflate();
assertEquals(
"Home button position is not as expected",
mHomeButton,
mToolbarTabletLayout.getChildAt(0));
assertEquals(
"Back button position is not as expected",
mBackButton,
mToolbarTabletLayout.getChildAt(1));
assertEquals(
"Forward button position is not as expected",
mForwardButton,
mToolbarTabletLayout.getChildAt(2));
assertEquals(
"Reloading button position is not as expected",
mReloadingButton,
mToolbarTabletLayout.getChildAt(3));
}
@EnableFeatures(ChromeFeatureList.TAB_STRIP_INCOGNITO_MIGRATION)
@Test
public void testButtonPositionIncognito() {
mToolbarTablet.onFinishInflate();
mToolbarTablet.initialize(
mToolbarDataProvider,
null,
mMenuButtonCoordinator,
mTabSwitcherButtonCoordinator,
null,
() -> false,
null,
null,
null);
when(mToolbarDataProvider.getNewTabPageDelegate()).thenReturn(mNewTabPageDelegate);
when(mToolbarDataProvider.isIncognitoBranded()).thenReturn(true);
mToolbarTablet.onTabOrModelChanged();
assertEquals(
"Home button position is not as expected",
mHomeButton,
mToolbarTabletLayout.getChildAt(0));
assertEquals(
"Back button position is not as expected",
mBackButton,
mToolbarTabletLayout.getChildAt(1));
assertEquals(
"Forward button position is not as expected",
mForwardButton,
mToolbarTabletLayout.getChildAt(2));
assertEquals(
"Reloading button position is not as expected",
mReloadingButton,
mToolbarTabletLayout.getChildAt(3));
View incognitoIndicator = mToolbarTabletLayout.findViewById(R.id.incognito_indicator);
assertNotNull("Incognito indicator is not inflated", incognitoIndicator);
assertEquals(
"Incognito indicator visibility is not as expected.",
View.VISIBLE,
incognitoIndicator.getVisibility());
}
@Test
@EnableFeatures({ChromeFeatureList.TABLET_TOOLBAR_REORDERING})
public void testButtonPosition_TSR() {
mToolbarTablet.onFinishInflate();
assertEquals(
"Back button position is not as expected for Tab Strip Redesign",
mBackButton,
mToolbarTabletLayout.getChildAt(0));
assertEquals(
"Forward button position is not as expected for Tab Strip Redesign",
mForwardButton,
mToolbarTabletLayout.getChildAt(1));
assertEquals(
"Reloading button position is not as expected for Tab Strip Redesign",
mReloadingButton,
mToolbarTabletLayout.getChildAt(2));
assertEquals(
"Home button position is not as expected for Tab Strip Redesign",
mHomeButton,
mToolbarTabletLayout.getChildAt(3));
}
@Test
@DisableFeatures(ChromeFeatureList.TABLET_TOOLBAR_REORDERING)
public void testButtonPosition_ShutoffToolbarReordering() {
mToolbarTablet.onFinishInflate();
assertEquals(
"Home button position is not as expected for TSR disable Toolbar reordering",
mHomeButton,
mToolbarTabletLayout.getChildAt(0));
assertEquals(
"Back button position is not as expected for TSR disable Toolbar reordering",
mBackButton,
mToolbarTabletLayout.getChildAt(1));
assertEquals(
"Forward button position is not as expected for TSR disable Toolbar reordering",
mForwardButton,
mToolbarTabletLayout.getChildAt(2));
assertEquals(
"Reloading button position is not as expected for TSR disable Toolbar reordering",
mReloadingButton,
mToolbarTabletLayout.getChildAt(3));
}
@Test
public void onMeasureShortWidth_hidesToolbarButtons() {
mToolbarTablet.measure(300, 300);
ImageButton[] btns = mToolbarTablet.getToolbarButtons();
for (ImageButton btn : btns) {
assertEquals(
"Toolbar button visibility is not as expected", View.GONE, btn.getVisibility());
}
}
@Test
public void onMeasureLargeWidth_showsToolbarButtons() {
mToolbarTablet.measure(700, 300);
ImageButton[] btns = mToolbarTablet.getToolbarButtons();
for (ImageButton btn : btns) {
assertEquals(
"Toolbar button visibility is not as expected",
View.VISIBLE,
btn.getVisibility());
}
}
@Test
@EnableFeatures(ChromeFeatureList.TAB_STRIP_INCOGNITO_MIGRATION)
public void onMeasureIncognito_flipIncognitoVisibility() {
mToolbarTablet.onFinishInflate();
mToolbarTablet.initialize(
mToolbarDataProvider,
null,
mMenuButtonCoordinator,
mTabSwitcherButtonCoordinator,
null,
() -> false,
null,
null,
null);
when(mToolbarDataProvider.getNewTabPageDelegate()).thenReturn(mNewTabPageDelegate);
when(mToolbarDataProvider.isIncognitoBranded()).thenReturn(true);
mToolbarTablet.onTabOrModelChanged();
View incognitoIndicator = mToolbarTablet.findViewById(R.id.incognito_indicator);
assertNotNull(incognitoIndicator);
// Measure with wide width - indicator visible
mToolbarTablet.measure(700, 300);
assertEquals(
"Incognito indicator visibility is not as expected.",
View.VISIBLE,
incognitoIndicator.getVisibility());
// Measure with smaller width - indicator invisible
mToolbarTablet.measure(300, 300);
assertEquals(
"Incognito indicator visibility is not as expected.",
View.GONE,
incognitoIndicator.getVisibility());
}
@Test
public void onMeasureSmallWidthWithAnimation_hidesToolbarButtons() {
doReturn(true).when(mToolbarTablet).isShown();
for (ImageButton btn : mToolbarTablet.getToolbarButtons()) {
when(mLocationBar.createHideButtonAnimatorForTablet(btn))
.thenReturn(ObjectAnimator.ofFloat(btn, View.ALPHA, 0.f));
}
when(mLocationBar.getHideButtonsWhenUnfocusedAnimatorsForTablet(anyInt()))
.thenReturn(new ArrayList<>());
mToolbarTablet.enableButtonVisibilityChangeAnimationForTesting();
// Call
mToolbarTablet.measure(300, 300);
verify(mTabStripTransitionCoordinator).requestDeferTabStripTransitionToken();
Shadows.shadowOf(Looper.getMainLooper()).idle();
// Verify
ImageButton[] btns = mToolbarTablet.getToolbarButtons();
for (ImageButton btn : btns) {
assertEquals(
"Toolbar button visibility is not as expected", View.GONE, btn.getVisibility());
}
verify(mTabStripTransitionCoordinator, atLeastOnce()).releaseTabStripToken(anyInt());
}
@Test
public void onMeasureLargeWidthWithAnimation_showsToolbarButtons() {
doReturn(true).when(mToolbarTablet).isShown();
mToolbarTablet.setToolbarButtonsVisibleForTesting(false);
mToolbarTablet.enableButtonVisibilityChangeAnimationForTesting();
for (ImageButton btn : mToolbarTablet.getToolbarButtons()) {
when(mLocationBar.createShowButtonAnimatorForTablet(btn))
.thenReturn(ObjectAnimator.ofFloat(btn, View.ALPHA, 1.f));
}
when(mLocationBar.getShowButtonsWhenUnfocusedAnimatorsForTablet(anyInt()))
.thenReturn(new ArrayList<>());
// Call
mToolbarTablet.measure(700, 300);
verify(mTabStripTransitionCoordinator).requestDeferTabStripTransitionToken();
Shadows.shadowOf(Looper.getMainLooper()).idle();
// Verify
ImageButton[] btns = mToolbarTablet.getToolbarButtons();
for (ImageButton btn : btns) {
assertEquals(
"Toolbar button visibility is not as expected",
View.VISIBLE,
btn.getVisibility());
}
verify(mTabStripTransitionCoordinator, atLeastOnce()).releaseTabStripToken(anyInt());
}
@Test
public void testSetTabSwitcherModeOff_toolbarStillVisible() {
assertEquals(
"Initial Toolbar visibility is not as expected",
View.VISIBLE,
mToolbarTablet.getVisibility());
// Call
mToolbarTablet.setTabSwitcherMode(false);
assertEquals(
"Toolbar visibility is not as expected",
View.VISIBLE,
mToolbarTablet.getVisibility());
verify(mLocationBar).setUrlBarFocusable(true);
}
@Test
public void testSetTabSwitcherModeOn_toolbarStillVisible() {
assertEquals(
"Initial Toolbar visibility is not as expected",
View.VISIBLE,
mToolbarTablet.getVisibility());
// Call
mToolbarTablet.setTabSwitcherMode(true);
assertEquals(
"Toolbar visibility is not as expected",
View.VISIBLE,
mToolbarTablet.getVisibility());
verify(mLocationBar).setUrlBarFocusable(false);
}
@Test
public void testOnLongClick() {
longClickAndVerifyToast(R.id.refresh_button, R.string.refresh);
longClickAndVerifyToast(R.id.bookmark_button, R.string.menu_bookmark);
longClickAndVerifyToast(R.id.save_offline_button, R.string.menu_download);
}
@Test
public void testUpdateBackButtonVisibility() {
ImageButton btn = mToolbarTablet.findViewById(R.id.back_button);
mToolbarTablet.updateBackButtonVisibility(true);
assertTrue("Button should be enabled", btn.isEnabled());
assertTrue("Button should be focused", btn.isFocusable());
mToolbarTablet.updateBackButtonVisibility(false);
assertFalse("Button should not be enabled", btn.isEnabled());
assertFalse("Button should not be focused", btn.isFocusable());
}
@Test
public void testUpdateForwardButtonVisibility() {
ImageButton btn = mToolbarTablet.findViewById(R.id.forward_button);
mToolbarTablet.updateForwardButtonVisibility(true);
assertTrue("Button should be enabled", btn.isEnabled());
assertTrue("Button should be focused", btn.isFocusable());
mToolbarTablet.updateForwardButtonVisibility(false);
assertFalse("Button should not be enabled", btn.isEnabled());
assertFalse("Button should not be focused", btn.isFocusable());
}
@Test
public void testUpdateReloadButtonVisibility() {
ImageButton btn = mToolbarTablet.findViewById(R.id.refresh_button);
mToolbarTablet.updateReloadButtonVisibility(true);
assertTrue("Button should be enabled", btn.isEnabled());
assertEquals("Button drawable level is not as expected", 1, btn.getDrawable().getLevel());
assertEquals(
"Button description is not as expected",
mActivity.getResources().getString(R.string.accessibility_btn_stop_loading),
btn.getContentDescription());
mToolbarTablet.updateReloadButtonVisibility(false);
assertEquals("Button drawable level is not as expected", 0, btn.getDrawable().getLevel());
assertEquals(
"Button description is not as expected",
mActivity.getResources().getString(R.string.accessibility_btn_refresh),
btn.getContentDescription());
assertTrue("Button should be enabled", btn.isEnabled());
}
@Test
@DisableFeatures(ChromeFeatureList.SUPPRESS_TOOLBAR_CAPTURES)
public void testIsReadyForTextureCapture_NoSuppression() {
CaptureReadinessResult result = mToolbarTablet.isReadyForTextureCapture();
Assert.assertTrue(result.isReady);
Assert.assertEquals(TopToolbarAllowCaptureReason.UNKNOWN, result.allowReason);
}
@Test
@EnableFeatures(ChromeFeatureList.SUPPRESS_TOOLBAR_CAPTURES)
public void testIsReadyForTextureCapture_HasFocus() {
mToolbarTablet.onUrlFocusChange(/* hasFocus= */ true);
CaptureReadinessResult result = mToolbarTablet.isReadyForTextureCapture();
Assert.assertFalse(result.isReady);
Assert.assertEquals(TopToolbarBlockCaptureReason.URL_BAR_HAS_FOCUS, result.blockReason);
}
@Test
public void testHoverTooltipText() {
// verify tooltip texts for tablet toolbar button are set.
Assert.assertEquals(
"Tooltip text for Home button is not as expected",
mActivity.getResources().getString(R.string.accessibility_toolbar_btn_home),
mHomeButton.getTooltipText());
Assert.assertEquals(
"Tooltip text for Reload button is not as expected",
mActivity.getResources().getString(R.string.accessibility_btn_refresh),
mReloadingButton.getTooltipText());
Assert.assertEquals(
"Tooltip text for Forward button is not as expected",
mActivity.getResources().getString(R.string.accessibility_menu_forward),
mForwardButton.getTooltipText());
Assert.assertEquals(
"Tooltip text for Back button is not as expected",
mActivity.getResources().getString(R.string.accessibility_toolbar_btn_back),
mBackButton.getTooltipText());
Assert.assertEquals(
"Tooltip text for Tab Switcher button is not as expected",
mActivity
.getResources()
.getString(R.string.accessibility_toolbar_btn_tabswitcher_toggle_default),
mTabSwitcherButton.getTooltipText());
Assert.assertEquals(
"Tooltip text for Bookmark button is not as expected",
mActivity.getResources().getString(R.string.accessibility_menu_bookmark),
mBookmarkButton.getTooltipText());
Assert.assertEquals(
"Tooltip text for Save Offline button is not as expected",
mActivity.getResources().getString(R.string.download_page),
mSaveOfflineButton.getTooltipText());
}
@Test
public void testOptionalButtonTooltipText() {
Drawable iconDrawable = AppCompatResources.getDrawable(mActivity, R.drawable.new_tab_icon);
OnClickListener clickListener = mock(OnClickListener.class);
OnLongClickListener longClickListener = mock(OnLongClickListener.class);
String contentDescription = mActivity.getString(R.string.actionbar_share);
ButtonDataImpl buttonData = new ButtonDataImpl();
// Verify reader mode tooltip text is null.
ButtonSpec buttonSpec =
new ButtonSpec(
iconDrawable,
clickListener,
longClickListener,
contentDescription,
true,
null,
/* buttonVariant= */ AdaptiveToolbarButtonVariant.READER_MODE,
0,
0,
false);
buttonData.setButtonSpec(buttonSpec);
mToolbarTablet.updateOptionalButton(buttonData);
Assert.assertEquals(
null, mToolbarTablet.getOptionalButtonViewForTesting().getTooltipText());
// Test whether share button tooltip Text is set correctly.
buttonSpec =
new ButtonSpec(
iconDrawable,
clickListener,
longClickListener,
contentDescription,
true,
null,
/* buttonVariant= */ AdaptiveToolbarButtonVariant.SHARE,
0,
R.string.adaptive_toolbar_button_preference_share,
true);
buttonData.setButtonSpec(buttonSpec);
mToolbarTablet.updateOptionalButton(buttonData);
Assert.assertEquals(
mActivity
.getResources()
.getString(R.string.adaptive_toolbar_button_preference_share),
mToolbarTablet.getOptionalButtonViewForTesting().getTooltipText());
// Test whether voice search button tooltip Text is set correctly.
buttonSpec =
new ButtonSpec(
iconDrawable,
clickListener,
longClickListener,
contentDescription,
true,
null,
/* buttonVariant= */ AdaptiveToolbarButtonVariant.VOICE,
0,
R.string.adaptive_toolbar_button_preference_voice_search,
true);
buttonData.setButtonSpec(buttonSpec);
mToolbarTablet.updateOptionalButton(buttonData);
Assert.assertEquals(
mActivity
.getResources()
.getString(R.string.adaptive_toolbar_button_preference_voice_search),
mToolbarTablet.getOptionalButtonViewForTesting().getTooltipText());
// Test whether new tab button tooltip Text is set correctly.
buttonSpec =
new ButtonSpec(
iconDrawable,
clickListener,
longClickListener,
contentDescription,
true,
null,
/* buttonVariant= */ AdaptiveToolbarButtonVariant.NEW_TAB,
0,
R.string.new_tab_title,
true);
buttonData.setButtonSpec(buttonSpec);
mToolbarTablet.updateOptionalButton(buttonData);
Assert.assertEquals(
mActivity.getResources().getString(R.string.new_tab_title),
mToolbarTablet.getOptionalButtonViewForTesting().getTooltipText());
}
@Test
@EnableFeatures(ChromeFeatureList.SUPPRESS_TOOLBAR_CAPTURES)
public void testIsReadyForTextureCapture_InTabSwitcher() {
mToolbarTablet.setTabSwitcherMode(/* inTabSwitcherMode= */ true);
CaptureReadinessResult result = mToolbarTablet.isReadyForTextureCapture();
Assert.assertFalse(result.isReady);
Assert.assertEquals(TopToolbarBlockCaptureReason.TAB_SWITCHER_MODE, result.blockReason);
}
@Test
@EnableFeatures(ChromeFeatureList.SUPPRESS_TOOLBAR_CAPTURES)
public void testIsReadyForTextureCapture_ButtonShowAnimationInProgress() {
mToolbarTablet.setToolbarButtonsVisibleForTesting(false);
mToolbarTablet.enableButtonVisibilityChangeAnimationForTesting();
// Set a test-only animator so the animation can have an in-between state.
ValueAnimator animator = ValueAnimator.ofFloat(0.f, 1.f);
when(mLocationBar.getShowButtonsWhenUnfocusedAnimatorsForTablet(anyInt()))
.thenReturn(List.of(animator));
// Run animation.
mToolbarTablet.measure(700, 300);
CaptureReadinessResult result = mToolbarTablet.isReadyForTextureCapture();
Assert.assertFalse(result.isReady);
Assert.assertEquals(
TopToolbarBlockCaptureReason.TABLET_BUTTON_ANIMATION_IN_PROGRESS,
result.blockReason);
ShadowLooper.runUiThreadTasksIncludingDelayedTasks();
result = mToolbarTablet.isReadyForTextureCapture();
Assert.assertTrue(result.isReady);
Assert.assertEquals(TopToolbarAllowCaptureReason.SNAPSHOT_DIFFERENCE, result.allowReason);
}
@Test
@EnableFeatures(ChromeFeatureList.SUPPRESS_TOOLBAR_CAPTURES)
public void testIsReadyForTextureCapture_ButtonHideAnimationInProgress() {
mToolbarTablet.setToolbarButtonsVisibleForTesting(true);
mToolbarTablet.enableButtonVisibilityChangeAnimationForTesting();
// Set a test-only animator so the animation can have an in-between state.
ValueAnimator animator = ValueAnimator.ofFloat(0.f, 1.f);
when(mLocationBar.getHideButtonsWhenUnfocusedAnimatorsForTablet(anyInt()))
.thenReturn(List.of(animator));
// Run animation.
mToolbarTablet.measure(300, 300);
CaptureReadinessResult result = mToolbarTablet.isReadyForTextureCapture();
Assert.assertFalse(result.isReady);
Assert.assertEquals(
TopToolbarBlockCaptureReason.TABLET_BUTTON_ANIMATION_IN_PROGRESS,
result.blockReason);
ShadowLooper.runUiThreadTasksIncludingDelayedTasks();
result = mToolbarTablet.isReadyForTextureCapture();
Assert.assertTrue(result.isReady);
Assert.assertEquals(TopToolbarAllowCaptureReason.SNAPSHOT_DIFFERENCE, result.allowReason);
}
@Test
@EnableFeatures(ChromeFeatureList.SUPPRESS_TOOLBAR_CAPTURES)
public void testIsReadyForTextureCapture_Snapshot() {
{
CaptureReadinessResult result = mToolbarTablet.isReadyForTextureCapture();
Assert.assertTrue(result.isReady);
Assert.assertEquals(
TopToolbarAllowCaptureReason.SNAPSHOT_DIFFERENCE, result.allowReason);
Assert.assertEquals(ToolbarSnapshotDifference.NULL, result.snapshotDifference);
}
{
CaptureReadinessResult result = mToolbarTablet.isReadyForTextureCapture();
Assert.assertTrue(result.isReady);
}
mToolbarTablet.setTextureCaptureMode(/* textureMode= */ true);
{
CaptureReadinessResult result = mToolbarTablet.isReadyForTextureCapture();
Assert.assertFalse(result.isReady);
Assert.assertEquals(TopToolbarBlockCaptureReason.SNAPSHOT_SAME, result.blockReason);
}
mToolbarTablet.updateBookmarkButton(/* isBookmarked= */ true, /* editingAllowed= */ true);
{
CaptureReadinessResult result = mToolbarTablet.isReadyForTextureCapture();
Assert.assertTrue(result.isReady);
Assert.assertEquals(
TopToolbarAllowCaptureReason.SNAPSHOT_DIFFERENCE, result.allowReason);
Assert.assertEquals(
ToolbarSnapshotDifference.BOOKMARK_BUTTON, result.snapshotDifference);
}
}
@Test
@DisableFeatures(ChromeFeatureList.TAB_STRIP_LAYOUT_OPTIMIZATION)
public void testThemeColorChange() {
int color = Color.BLACK;
mToolbarTablet.onThemeColorChanged(color, false);
// Verify that ToolbarColorObserver is notified of the color change.
verify(mToolbarColorObserver).onToolbarColorChanged(color);
}
@Test
public void testOnTintChanged_UnfocusedActivityTint() {
var tint =
ThemeUtils.getThemedToolbarIconTint(
mToolbarTablet.getContext(), BrandedColorScheme.APP_DEFAULT);
var unfocusedTint =
ThemeUtils.getThemedToolbarIconTintForActivityState(
mToolbarTablet.getContext(),
BrandedColorScheme.APP_DEFAULT,
/* isActivityFocused= */ false);
// Setup.
ButtonDataImpl buttonData = new ButtonDataImpl();
var buttonSpec =
new ButtonSpec(
AppCompatResources.getDrawable(mActivity, R.drawable.new_tab_icon),
(OnClickListener) v -> {},
(OnLongClickListener) v -> false,
"",
true,
null,
/* buttonVariant= */ AdaptiveToolbarButtonVariant.NEW_TAB,
0,
R.string.adaptive_toolbar_button_preference_new_tab,
true);
buttonData.setButtonSpec(buttonSpec);
mToolbarTablet.updateOptionalButton(buttonData);
// Verify the toolbar icon tints, assuming that the activity is initially focused.
verifyToolbarIconTints(tint, tint);
// Simulate a tint change triggered when the activity loses focus.
mToolbarTablet.onTintChanged(tint, unfocusedTint, BrandedColorScheme.APP_DEFAULT);
// Verify the icon tints for the unfocused activity.
verifyToolbarIconTints(tint, unfocusedTint);
Assert.assertEquals(
"Tab switcher button tint is incorrect.",
unfocusedTint.getDefaultColor(),
mTabSwitcherButton.getImageTintList().getDefaultColor());
}
private void verifyToolbarIconTints(ColorStateList tint, ColorStateList activityFocusTint) {
Assert.assertEquals(
"Home button tint is incorrect.",
activityFocusTint.getDefaultColor(),
mHomeButton.getImageTintList().getDefaultColor());
Assert.assertEquals(
"Back button tint is incorrect.",
activityFocusTint.getDefaultColor(),
mBackButton.getImageTintList().getDefaultColor());
Assert.assertEquals(
"Forward button tint is incorrect.",
activityFocusTint.getDefaultColor(),
mForwardButton.getImageTintList().getDefaultColor());
Assert.assertEquals(
"Reload button tint is incorrect.",
activityFocusTint.getDefaultColor(),
mReloadingButton.getImageTintList().getDefaultColor());
Assert.assertEquals(
"Save offline button tint is incorrect.",
tint.getDefaultColor(),
mSaveOfflineButton.getImageTintList().getDefaultColor());
Assert.assertEquals(
"Bookmark button tint is incorrect.",
tint.getDefaultColor(),
mBookmarkButton.getImageTintList().getDefaultColor());
Assert.assertEquals(
"Optional button tint is incorrect.",
activityFocusTint.getDefaultColor(),
((ImageButton) mToolbarTablet.getOptionalButtonViewForTesting())
.getImageTintList()
.getDefaultColor());
}
private void longClickAndVerifyToast(int viewId, int stringId) {
mToolbarTablet.onLongClick(mToolbarTablet.findViewById(viewId));
assertTrue(
"Toast is not as expected",
ShadowToast.showedCustomToast(
mActivity.getResources().getString(stringId), R.id.toast_text));
ToastManager.resetForTesting();
}
}