1 // Copyright 2018 The Chromium Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 package org.chromium.chrome.browser.toolbar.top; 6 7 import android.graphics.Rect; 8 import android.graphics.drawable.Drawable; 9 import android.view.View; 10 import android.view.View.OnClickListener; 11 import android.view.View.OnLongClickListener; 12 13 import androidx.annotation.Nullable; 14 import androidx.annotation.VisibleForTesting; 15 16 import org.chromium.base.Callback; 17 import org.chromium.base.supplier.ObservableSupplier; 18 import org.chromium.base.supplier.OneShotCallback; 19 import org.chromium.base.supplier.OneshotSupplier; 20 import org.chromium.base.supplier.Supplier; 21 import org.chromium.chrome.R; 22 import org.chromium.chrome.browser.browser_controls.BrowserControlsStateProvider; 23 import org.chromium.chrome.browser.layouts.LayoutStateProvider; 24 import org.chromium.chrome.browser.omnibox.LocationBar; 25 import org.chromium.chrome.browser.tabmodel.IncognitoStateProvider; 26 import org.chromium.chrome.browser.tabmodel.TabModelSelector; 27 import org.chromium.chrome.browser.toolbar.ButtonData; 28 import org.chromium.chrome.browser.toolbar.ButtonDataProvider; 29 import org.chromium.chrome.browser.toolbar.TabCountProvider; 30 import org.chromium.chrome.browser.toolbar.ThemeColorProvider; 31 import org.chromium.chrome.browser.toolbar.ToolbarDataProvider; 32 import org.chromium.chrome.browser.toolbar.ToolbarProgressBar; 33 import org.chromium.chrome.browser.toolbar.ToolbarTabController; 34 import org.chromium.chrome.browser.toolbar.menu_button.MenuButton; 35 import org.chromium.chrome.browser.toolbar.menu_button.MenuButtonCoordinator; 36 import org.chromium.chrome.browser.ui.appmenu.AppMenuButtonHelper; 37 import org.chromium.chrome.browser.user_education.UserEducationHelper; 38 import org.chromium.chrome.features.start_surface.StartSurface; 39 import org.chromium.chrome.features.start_surface.StartSurfaceConfiguration; 40 import org.chromium.chrome.features.start_surface.StartSurfaceState; 41 import org.chromium.components.browser_ui.widget.ClipDrawableProgressBar; 42 import org.chromium.ui.resources.ResourceManager; 43 44 import java.util.List; 45 46 /** 47 * A coordinator for the top toolbar component. 48 */ 49 public class TopToolbarCoordinator implements Toolbar { 50 /** 51 * Observes toolbar URL expansion progress change. 52 */ 53 public interface UrlExpansionObserver { 54 /** 55 * Notified when toolbar URL expansion progress fraction changes. 56 * 57 * @param fraction The toolbar expansion progress. 0 indicates that the URL bar is not 58 * expanded. 1 indicates that the URL bar is expanded to the maximum 59 * width. 60 */ onUrlExpansionProgressChanged(float fraction)61 void onUrlExpansionProgressChanged(float fraction); 62 } 63 64 public static final int TAB_SWITCHER_MODE_NORMAL_ANIMATION_DURATION_MS = 200; 65 public static final int TAB_SWITCHER_MODE_GTS_ANIMATION_DURATION_MS = 150; 66 67 private final ToolbarLayout mToolbarLayout; 68 69 /** 70 * The coordinator for the tab switcher mode toolbar (phones only). This will be lazily created 71 * after ToolbarLayout is inflated. 72 */ 73 private @Nullable TabSwitcherModeTTCoordinatorPhone mTabSwitcherModeCoordinatorPhone; 74 /** 75 * The coordinator for the start surface mode toolbar (phones only) if the StartSurface is 76 * enabled. This will be lazily created after ToolbarLayout is inflated. 77 */ 78 private @Nullable StartSurfaceToolbarCoordinator mStartSurfaceToolbarCoordinator; 79 80 private OptionalBrowsingModeButtonController mOptionalButtonController; 81 82 private MenuButtonCoordinator mMenuButtonCoordinator; 83 private ObservableSupplier<AppMenuButtonHelper> mAppMenuButtonHelperSupplier; 84 private ObservableSupplier<TabModelSelector> mTabModelSelectorSupplier; 85 86 private Callback<ClipDrawableProgressBar.DrawingInfo> mProgressDrawInfoCallback; 87 private ToolbarControlContainer mControlContainer; 88 private Supplier<ResourceManager> mResourceManagerSupplier; 89 90 /** 91 * Creates a new {@link TopToolbarCoordinator}. 92 * @param controlContainer The {@link ToolbarControlContainer} for the containing activity. 93 * @param toolbarLayout The {@link ToolbarLayout}. 94 * @param userEducationHelper Helper class for showing in-product help text bubbles. 95 * @param buttonDataProviders List of classes that wish to display an optional button in the 96 * browsing mode toolbar. 97 * @param layoutStateProviderSupplier Supplier of the {@link LayoutStateProvider}. 98 * @param normalThemeColorProvider The {@link ThemeColorProvider} for normal mode. 99 * @param overviewThemeColorProvider The {@link ThemeColorProvider} for overview mode. 100 * @param tabModelSelectorSupplier Supplier of the {@link TabModelSelector}. 101 * @param homeButtonVisibilitySupplier Supplier of the visibility change of Home button. 102 * @param identityDiscStateSupplier Supplier of the state change of identity disc button. 103 * @param invalidatorCallback Callback that will be invoked when the toolbar attempts to 104 * invalidate the drawing surface. This will give the object that registers as the host 105 * for the {@link Invalidator} a chance to defer the actual invalidate to sync drawing. 106 * @param identityDiscButtonSupplier Supplier of Identity Disc button. 107 * @param startSurfaceSupplier Supplier of the StartSurface. 108 * @param resourceManagerSupplier A supplier of a resource manager for native textures. 109 */ TopToolbarCoordinator(ToolbarControlContainer controlContainer, ToolbarLayout toolbarLayout, ToolbarDataProvider toolbarDataProvider, ToolbarTabController tabController, UserEducationHelper userEducationHelper, List<ButtonDataProvider> buttonDataProviders, OneshotSupplier<LayoutStateProvider> layoutStateProviderSupplier, ThemeColorProvider normalThemeColorProvider, ThemeColorProvider overviewThemeColorProvider, MenuButtonCoordinator browsingModeMenuButtonCoordinator, MenuButtonCoordinator overviewModeMenuButtonCoordinator, ObservableSupplier<AppMenuButtonHelper> appMenuButtonHelperSupplier, ObservableSupplier<TabModelSelector> tabModelSelectorSupplier, ObservableSupplier<Boolean> homeButtonVisibilitySupplier, ObservableSupplier<Boolean> identityDiscStateSupplier, Callback<Runnable> invalidatorCallback, Supplier<ButtonData> identityDiscButtonSupplier, OneshotSupplier<StartSurface> startSurfaceSupplier, Runnable tabOrModelChangeRunnable, Supplier<ResourceManager> resourceManagerSupplier)110 public TopToolbarCoordinator(ToolbarControlContainer controlContainer, 111 ToolbarLayout toolbarLayout, ToolbarDataProvider toolbarDataProvider, 112 ToolbarTabController tabController, UserEducationHelper userEducationHelper, 113 List<ButtonDataProvider> buttonDataProviders, 114 OneshotSupplier<LayoutStateProvider> layoutStateProviderSupplier, 115 ThemeColorProvider normalThemeColorProvider, 116 ThemeColorProvider overviewThemeColorProvider, 117 MenuButtonCoordinator browsingModeMenuButtonCoordinator, 118 MenuButtonCoordinator overviewModeMenuButtonCoordinator, 119 ObservableSupplier<AppMenuButtonHelper> appMenuButtonHelperSupplier, 120 ObservableSupplier<TabModelSelector> tabModelSelectorSupplier, 121 ObservableSupplier<Boolean> homeButtonVisibilitySupplier, 122 ObservableSupplier<Boolean> identityDiscStateSupplier, 123 Callback<Runnable> invalidatorCallback, Supplier<ButtonData> identityDiscButtonSupplier, 124 OneshotSupplier<StartSurface> startSurfaceSupplier, Runnable tabOrModelChangeRunnable, 125 Supplier<ResourceManager> resourceManagerSupplier) { 126 mControlContainer = controlContainer; 127 mToolbarLayout = toolbarLayout; 128 mMenuButtonCoordinator = browsingModeMenuButtonCoordinator; 129 mOptionalButtonController = new OptionalBrowsingModeButtonController(buttonDataProviders, 130 userEducationHelper, mToolbarLayout, () -> toolbarDataProvider.getTab()); 131 mResourceManagerSupplier = resourceManagerSupplier; 132 mProgressDrawInfoCallback = (info) -> { 133 if (controlContainer == null) return; 134 controlContainer.getProgressBarDrawingInfo(info); 135 }; 136 137 mTabModelSelectorSupplier = tabModelSelectorSupplier; 138 139 if (mToolbarLayout instanceof ToolbarPhone) { 140 if (StartSurfaceConfiguration.isStartSurfaceEnabled()) { 141 mStartSurfaceToolbarCoordinator = new StartSurfaceToolbarCoordinator( 142 controlContainer.getRootView().findViewById(R.id.tab_switcher_toolbar_stub), 143 userEducationHelper, layoutStateProviderSupplier, identityDiscStateSupplier, 144 overviewThemeColorProvider, overviewModeMenuButtonCoordinator, 145 identityDiscButtonSupplier); 146 } else { 147 mTabSwitcherModeCoordinatorPhone = new TabSwitcherModeTTCoordinatorPhone( 148 controlContainer.getRootView().findViewById(R.id.tab_switcher_toolbar_stub), 149 overviewModeMenuButtonCoordinator); 150 } 151 } 152 controlContainer.setToolbar(this); 153 mToolbarLayout.initialize(toolbarDataProvider, tabController, mMenuButtonCoordinator, 154 tabOrModelChangeRunnable); 155 156 mToolbarLayout.setThemeColorProvider(normalThemeColorProvider); 157 mAppMenuButtonHelperSupplier = appMenuButtonHelperSupplier; 158 new OneShotCallback<>(mAppMenuButtonHelperSupplier, this::setAppMenuButtonHelper); 159 homeButtonVisibilitySupplier.addObserver((show) -> mToolbarLayout.onHomeButtonUpdate(show)); 160 mToolbarLayout.setInvalidatorCallback(invalidatorCallback); 161 } 162 163 /** 164 * @param appMenuButtonHelper The helper for managing menu button interactions. 165 */ setAppMenuButtonHelper(AppMenuButtonHelper appMenuButtonHelper)166 public void setAppMenuButtonHelper(AppMenuButtonHelper appMenuButtonHelper) { 167 mToolbarLayout.setAppMenuButtonHelper(appMenuButtonHelper); 168 } 169 170 /** 171 * Initialize the coordinator with the components that have native initialization dependencies. 172 * <p> 173 * Calling this must occur after the native library have completely loaded. 174 * 175 * @param layoutUpdater A {@link Runnable} used to request layout update upon scene change. 176 * @param tabSwitcherClickHandler The click handler for the tab switcher button. 177 * @param tabSwitcherLongClickHandler The long click handler for the tab switcher button. 178 * @param newTabClickHandler The click handler for the new tab button. 179 * @param bookmarkClickHandler The click handler for the bookmarks button. 180 * @param customTabsBackClickHandler The click handler for the custom tabs back button. 181 * @param browserControlsStateProvider Access to the state of the browser controls. 182 */ initializeWithNative(Runnable layoutUpdater, OnClickListener tabSwitcherClickHandler, OnLongClickListener tabSwitcherLongClickHandler, OnClickListener newTabClickHandler, OnClickListener bookmarkClickHandler, OnClickListener customTabsBackClickHandler, BrowserControlsStateProvider browserControlsStateProvider)183 public void initializeWithNative(Runnable layoutUpdater, 184 OnClickListener tabSwitcherClickHandler, 185 OnLongClickListener tabSwitcherLongClickHandler, OnClickListener newTabClickHandler, 186 OnClickListener bookmarkClickHandler, OnClickListener customTabsBackClickHandler, 187 BrowserControlsStateProvider browserControlsStateProvider) { 188 assert mTabModelSelectorSupplier.get() != null; 189 if (mTabSwitcherModeCoordinatorPhone != null) { 190 mTabSwitcherModeCoordinatorPhone.setOnTabSwitcherClickHandler(tabSwitcherClickHandler); 191 mTabSwitcherModeCoordinatorPhone.setOnNewTabClickHandler(newTabClickHandler); 192 mTabSwitcherModeCoordinatorPhone.setTabModelSelector(mTabModelSelectorSupplier.get()); 193 } else if (mStartSurfaceToolbarCoordinator != null) { 194 mStartSurfaceToolbarCoordinator.setOnNewTabClickHandler(newTabClickHandler); 195 mStartSurfaceToolbarCoordinator.setTabModelSelector(mTabModelSelectorSupplier.get()); 196 mStartSurfaceToolbarCoordinator.setTabSwitcherListener(tabSwitcherClickHandler); 197 mStartSurfaceToolbarCoordinator.setOnTabSwitcherLongClickHandler( 198 tabSwitcherLongClickHandler); 199 mStartSurfaceToolbarCoordinator.onNativeLibraryReady(); 200 } 201 202 mToolbarLayout.setTabModelSelector(mTabModelSelectorSupplier.get()); 203 getLocationBar().updateVisualsForState(); 204 mToolbarLayout.setOnTabSwitcherClickHandler(tabSwitcherClickHandler); 205 mToolbarLayout.setOnTabSwitcherLongClickHandler(tabSwitcherLongClickHandler); 206 mToolbarLayout.setBookmarkClickHandler(bookmarkClickHandler); 207 mToolbarLayout.setCustomTabCloseClickHandler(customTabsBackClickHandler); 208 mToolbarLayout.setLayoutUpdater(layoutUpdater); 209 210 mToolbarLayout.onNativeLibraryReady(); 211 } 212 213 /** 214 * @param urlExpansionObserver The observer that observes URL expansion progress change. 215 */ addUrlExpansionObserver(UrlExpansionObserver urlExpansionObserver)216 public void addUrlExpansionObserver(UrlExpansionObserver urlExpansionObserver) { 217 mToolbarLayout.addUrlExpansionObserver(urlExpansionObserver); 218 } 219 220 /** 221 * @param urlExpansionObserver The observer that observes URL expansion progress change. 222 */ removeUrlExpansionObserver(UrlExpansionObserver urlExpansionObserver)223 public void removeUrlExpansionObserver(UrlExpansionObserver urlExpansionObserver) { 224 mToolbarLayout.removeUrlExpansionObserver(urlExpansionObserver); 225 } 226 227 /** 228 * @see View#addOnAttachStateChangeListener(View.OnAttachStateChangeListener) 229 */ addOnAttachStateChangeListener(View.OnAttachStateChangeListener listener)230 public void addOnAttachStateChangeListener(View.OnAttachStateChangeListener listener) { 231 mToolbarLayout.addOnAttachStateChangeListener(listener); 232 } 233 234 /** 235 * Cleans up any code as necessary. 236 */ destroy()237 public void destroy() { 238 mToolbarLayout.destroy(); 239 if (mTabSwitcherModeCoordinatorPhone != null) { 240 mTabSwitcherModeCoordinatorPhone.destroy(); 241 } else if (mStartSurfaceToolbarCoordinator != null) { 242 mStartSurfaceToolbarCoordinator.destroy(); 243 } 244 245 if (mOptionalButtonController != null) { 246 mOptionalButtonController.destroy(); 247 mOptionalButtonController = null; 248 } 249 250 if (mAppMenuButtonHelperSupplier != null) { 251 mAppMenuButtonHelperSupplier = null; 252 } 253 if (mTabModelSelectorSupplier != null) { 254 mTabModelSelectorSupplier = null; 255 } 256 if (mControlContainer != null) { 257 mControlContainer = null; 258 } 259 } 260 261 @Override disableMenuButton()262 public void disableMenuButton() { 263 mMenuButtonCoordinator.disableMenuButton(); 264 mToolbarLayout.onMenuButtonDisabled(); 265 } 266 267 /** 268 * @return The wrapper for the browsing mode toolbar's menu button. 269 */ getMenuButtonWrapper()270 public MenuButton getMenuButtonWrapper() { 271 return mMenuButtonCoordinator.getMenuButton(); 272 } 273 274 @Nullable 275 @Override getProgressBar()276 public ToolbarProgressBar getProgressBar() { 277 return mToolbarLayout.getProgressBar(); 278 } 279 280 @Override getPrimaryColor()281 public int getPrimaryColor() { 282 return mToolbarLayout.getToolbarDataProvider().getPrimaryColor(); 283 } 284 285 @Override getPositionRelativeToContainer(View containerView, int[] position)286 public void getPositionRelativeToContainer(View containerView, int[] position) { 287 mToolbarLayout.getPositionRelativeToContainer(containerView, position); 288 } 289 290 /** 291 * Sets the {@link Invalidator} that will be called when the toolbar attempts to invalidate the 292 * drawing surface. This will give the object that registers as the host for the 293 * {@link Invalidator} a chance to defer the actual invalidate to sync drawing. 294 * @param invalidator An {@link Invalidator} instance. 295 */ setInvalidatorCallback(Callback<Runnable> callback)296 public void setInvalidatorCallback(Callback<Runnable> callback) { 297 mToolbarLayout.setInvalidatorCallback(callback); 298 } 299 300 /** 301 * Gives inheriting classes the chance to respond to 302 * {@link FindToolbar} state changes. 303 * @param showing Whether or not the {@code FindToolbar} will be showing. 304 */ handleFindLocationBarStateChange(boolean showing)305 public void handleFindLocationBarStateChange(boolean showing) { 306 mToolbarLayout.handleFindLocationBarStateChange(showing); 307 } 308 309 /** 310 * Sets whether the urlbar should be hidden on first page load. 311 */ setUrlBarHidden(boolean hidden)312 public void setUrlBarHidden(boolean hidden) { 313 mToolbarLayout.setUrlBarHidden(hidden); 314 } 315 316 /** 317 * @return The name of the publisher of the content if it can be reliably extracted, or null 318 * otherwise. 319 */ getContentPublisher()320 public String getContentPublisher() { 321 return mToolbarLayout.getContentPublisher(); 322 } 323 324 /** 325 * Tells the Toolbar to update what buttons it is currently displaying. 326 */ updateButtonVisibility()327 public void updateButtonVisibility() { 328 mToolbarLayout.updateButtonVisibility(); 329 mOptionalButtonController.updateButtonVisibility(); 330 } 331 332 /** 333 * Gives inheriting classes the chance to update the visibility of the 334 * back button. 335 * @param canGoBack Whether or not the current tab has any history to go back to. 336 */ updateBackButtonVisibility(boolean canGoBack)337 public void updateBackButtonVisibility(boolean canGoBack) { 338 mToolbarLayout.updateBackButtonVisibility(canGoBack); 339 } 340 341 /** 342 * Gives inheriting classes the chance to update the visibility of the 343 * forward button. 344 * @param canGoForward Whether or not the current tab has any history to go forward to. 345 */ updateForwardButtonVisibility(boolean canGoForward)346 public void updateForwardButtonVisibility(boolean canGoForward) { 347 mToolbarLayout.updateForwardButtonVisibility(canGoForward); 348 } 349 350 /** 351 * Gives inheriting classes the chance to update the visibility of the 352 * reload button. 353 * @param isReloading Whether or not the current tab is loading. 354 */ updateReloadButtonVisibility(boolean isReloading)355 public void updateReloadButtonVisibility(boolean isReloading) { 356 mToolbarLayout.updateReloadButtonVisibility(isReloading); 357 } 358 359 /** 360 * Gives inheriting classes the chance to update the visual status of the 361 * bookmark button. 362 * @param isBookmarked Whether or not the current tab is already bookmarked. 363 * @param editingAllowed Whether or not bookmarks can be modified (added, edited, or removed). 364 */ updateBookmarkButton(boolean isBookmarked, boolean editingAllowed)365 public void updateBookmarkButton(boolean isBookmarked, boolean editingAllowed) { 366 mToolbarLayout.updateBookmarkButton(isBookmarked, editingAllowed); 367 } 368 369 /** 370 * Gives inheriting classes the chance to respond to accessibility state changes. 371 * @param enabled Whether or not accessibility is enabled. 372 */ onAccessibilityStatusChanged(boolean enabled)373 public void onAccessibilityStatusChanged(boolean enabled) { 374 mToolbarLayout.onAccessibilityStatusChanged(enabled); 375 if (mTabSwitcherModeCoordinatorPhone != null) { 376 mTabSwitcherModeCoordinatorPhone.onAccessibilityStatusChanged(enabled); 377 } else if (mStartSurfaceToolbarCoordinator != null) { 378 mStartSurfaceToolbarCoordinator.onAccessibilityStatusChanged(enabled); 379 } 380 } 381 382 /** 383 * Gives inheriting classes the chance to do the necessary UI operations after Chrome is 384 * restored to a previously saved state. 385 */ onStateRestored()386 public void onStateRestored() { 387 mToolbarLayout.onStateRestored(); 388 } 389 390 /** 391 * Triggered when the current tab or model has changed. 392 * <p> 393 * As there are cases where you can select a model with no tabs (i.e. having incognito 394 * tabs but no normal tabs will still allow you to select the normal model), this should 395 * not guarantee that the model's current tab is non-null. 396 */ onTabOrModelChanged()397 public void onTabOrModelChanged() { 398 mToolbarLayout.onTabOrModelChanged(); 399 } 400 401 /** 402 * For extending classes to override and carry out the changes related with the primary color 403 * for the current tab changing. 404 */ onPrimaryColorChanged(boolean shouldAnimate)405 public void onPrimaryColorChanged(boolean shouldAnimate) { 406 mToolbarLayout.onPrimaryColorChanged(shouldAnimate); 407 } 408 409 /** 410 * Sets whether a title should be shown within the Toolbar. 411 * @param showTitle Whether a title should be shown. 412 */ setShowTitle(boolean showTitle)413 public void setShowTitle(boolean showTitle) { 414 getLocationBar().setShowTitle(showTitle); 415 } 416 417 /** 418 * Sets the icon drawable that the close button in the toolbar (if any) should show, or hides 419 * it if {@code drawable} is {@code null}. 420 */ setCloseButtonImageResource(@ullable Drawable drawable)421 public void setCloseButtonImageResource(@Nullable Drawable drawable) { 422 mToolbarLayout.setCloseButtonImageResource(drawable); 423 } 424 425 /** 426 * Adds a custom action button to the toolbar layout, if it is supported. 427 * @param drawable The icon for the button. 428 * @param description The content description for the button. 429 * @param listener The {@link View.OnClickListener} to use for clicks to the button. 430 */ addCustomActionButton( Drawable drawable, String description, View.OnClickListener listener)431 public void addCustomActionButton( 432 Drawable drawable, String description, View.OnClickListener listener) { 433 mToolbarLayout.addCustomActionButton(drawable, description, listener); 434 } 435 436 /** 437 * Updates the visual appearance of a custom action button in the toolbar layout, 438 * if it is supported. 439 * @param index The index of the button. 440 * @param drawable The icon for the button. 441 * @param description The content description for the button. 442 */ updateCustomActionButton(int index, Drawable drawable, String description)443 public void updateCustomActionButton(int index, Drawable drawable, String description) { 444 mToolbarLayout.updateCustomActionButton(index, drawable, description); 445 } 446 447 @Override getTabStripHeight()448 public int getTabStripHeight() { 449 return mToolbarLayout.getTabStripHeight(); 450 } 451 452 /** 453 * Triggered when the content view for the specified tab has changed. 454 */ onTabContentViewChanged()455 public void onTabContentViewChanged() { 456 mToolbarLayout.onTabContentViewChanged(); 457 } 458 459 @Override isReadyForTextureCapture()460 public boolean isReadyForTextureCapture() { 461 return mToolbarLayout.isReadyForTextureCapture(); 462 } 463 464 @Override setForceTextureCapture(boolean forceTextureCapture)465 public boolean setForceTextureCapture(boolean forceTextureCapture) { 466 return mToolbarLayout.setForceTextureCapture(forceTextureCapture); 467 } 468 469 /** 470 * @param attached Whether or not the web content is attached to the view heirarchy. 471 */ setContentAttached(boolean attached)472 public void setContentAttached(boolean attached) { 473 mToolbarLayout.setContentAttached(attached); 474 } 475 476 /** 477 * Gives inheriting classes the chance to show or hide the TabSwitcher mode of this toolbar. 478 * @param inTabSwitcherMode Whether or not TabSwitcher mode should be shown or hidden. 479 * @param showToolbar Whether or not to show the normal toolbar while animating. 480 * @param delayAnimation Whether or not to delay the animation until after the transition has 481 * finished (which can be detected by a call to 482 * {@link #onTabSwitcherTransitionFinished()}). 483 */ setTabSwitcherMode( boolean inTabSwitcherMode, boolean showToolbar, boolean delayAnimation)484 public void setTabSwitcherMode( 485 boolean inTabSwitcherMode, boolean showToolbar, boolean delayAnimation) { 486 mToolbarLayout.setTabSwitcherMode( 487 inTabSwitcherMode, showToolbar, delayAnimation, mMenuButtonCoordinator); 488 if (mTabSwitcherModeCoordinatorPhone != null) { 489 mTabSwitcherModeCoordinatorPhone.setTabSwitcherMode(inTabSwitcherMode); 490 } else if (mStartSurfaceToolbarCoordinator != null) { 491 mStartSurfaceToolbarCoordinator.setStartSurfaceMode(inTabSwitcherMode); 492 } 493 } 494 495 /** 496 * Gives inheriting classes the chance to update their state when the TabSwitcher transition has 497 * finished. 498 */ onTabSwitcherTransitionFinished()499 public void onTabSwitcherTransitionFinished() { 500 mToolbarLayout.onTabSwitcherTransitionFinished(); 501 } 502 503 /** 504 * Gives inheriting classes the chance to observe tab count changes. 505 * @param tabCountProvider The {@link TabCountProvider} subclasses can observe. 506 */ setTabCountProvider(TabCountProvider tabCountProvider)507 public void setTabCountProvider(TabCountProvider tabCountProvider) { 508 mToolbarLayout.setTabCountProvider(tabCountProvider); 509 if (mTabSwitcherModeCoordinatorPhone != null) { 510 mTabSwitcherModeCoordinatorPhone.setTabCountProvider(tabCountProvider); 511 } 512 if (mStartSurfaceToolbarCoordinator != null) { 513 mStartSurfaceToolbarCoordinator.setTabCountProvider(tabCountProvider); 514 } 515 } 516 517 /** 518 * @param provider The provider used to determine incognito state. 519 */ setIncognitoStateProvider(IncognitoStateProvider provider)520 public void setIncognitoStateProvider(IncognitoStateProvider provider) { 521 if (mTabSwitcherModeCoordinatorPhone != null) { 522 mTabSwitcherModeCoordinatorPhone.setIncognitoStateProvider(provider); 523 } else if (mStartSurfaceToolbarCoordinator != null) { 524 mStartSurfaceToolbarCoordinator.setIncognitoStateProvider(provider); 525 } 526 } 527 528 /** 529 * Gives inheriting classes the chance to update themselves based on default search engine 530 * changes. 531 */ onDefaultSearchEngineChanged()532 public void onDefaultSearchEngineChanged() { 533 mToolbarLayout.onDefaultSearchEngineChanged(); 534 } 535 536 @Override getLocationBarContentRect(Rect outRect)537 public void getLocationBarContentRect(Rect outRect) { 538 mToolbarLayout.getLocationBarContentRect(outRect); 539 } 540 541 @Override setTextureCaptureMode(boolean textureMode)542 public void setTextureCaptureMode(boolean textureMode) { 543 mToolbarLayout.setTextureCaptureMode(textureMode); 544 } 545 546 @Override shouldIgnoreSwipeGesture()547 public boolean shouldIgnoreSwipeGesture() { 548 return mToolbarLayout.shouldIgnoreSwipeGesture(); 549 } 550 551 /** 552 * Triggered when the URL input field has gained or lost focus. 553 * @param hasFocus Whether the URL field has gained focus. 554 */ onUrlFocusChange(boolean hasFocus)555 public void onUrlFocusChange(boolean hasFocus) { 556 mToolbarLayout.onUrlFocusChange(hasFocus); 557 } 558 559 /** 560 * Returns the elapsed realtime in ms of the time at which first draw for the toolbar occurred. 561 */ getFirstDrawTime()562 public long getFirstDrawTime() { 563 return mToolbarLayout.getFirstDrawTime(); 564 } 565 566 /** 567 * Notified when a navigation to a different page has occurred. 568 */ onNavigatedToDifferentPage()569 public void onNavigatedToDifferentPage() { 570 mToolbarLayout.onNavigatedToDifferentPage(); 571 } 572 573 /** 574 * @param enabled Whether the progress bar is enabled. 575 */ setProgressBarEnabled(boolean enabled)576 public void setProgressBarEnabled(boolean enabled) { 577 getProgressBar().setVisibility(enabled ? View.VISIBLE : View.GONE); 578 } 579 580 /** 581 * Finish any toolbar animations. 582 */ finishAnimations()583 public void finishAnimations() { 584 mToolbarLayout.finishAnimations(); 585 } 586 587 /** 588 * @return {@link LocationBar} object this {@link ToolbarLayout} contains. 589 */ getLocationBar()590 public LocationBar getLocationBar() { 591 return mToolbarLayout.getLocationBar(); 592 } 593 594 /** 595 * Update the start surface toolbar state. 596 * @param newState New Start Surface State. 597 * @param requestToShow Whether or not request showing the start surface toolbar. 598 */ updateStartSurfaceToolbarState( @tartSurfaceState int newState, boolean requestToShow)599 public void updateStartSurfaceToolbarState( 600 @StartSurfaceState int newState, boolean requestToShow) { 601 if (mStartSurfaceToolbarCoordinator == null 602 || mToolbarLayout.getToolbarDataProvider() == null) { 603 return; 604 } 605 mStartSurfaceToolbarCoordinator.onStartSurfaceStateChanged(newState, requestToShow); 606 updateToolbarContainerVisibility(); 607 } 608 609 /** 610 * Triggered when the offset of start surface header view is changed. 611 * @param verticalOffset The start surface header view's offset. 612 */ onStartSurfaceHeaderOffsetChanged(int verticalOffset)613 public void onStartSurfaceHeaderOffsetChanged(int verticalOffset) { 614 if (mStartSurfaceToolbarCoordinator != null) { 615 mStartSurfaceToolbarCoordinator.onStartSurfaceHeaderOffsetChanged(verticalOffset); 616 updateToolbarContainerVisibility(); 617 } 618 } 619 updateToolbarContainerVisibility()620 private void updateToolbarContainerVisibility() { 621 if (mStartSurfaceToolbarCoordinator != null) { 622 boolean shouldHideToolbarContainer = 623 mStartSurfaceToolbarCoordinator.shouldHideToolbarContainer(getHeight()); 624 mControlContainer.setToolbarContainerVisibility( 625 shouldHideToolbarContainer ? View.INVISIBLE : View.VISIBLE); 626 } 627 } 628 629 @Override getHeight()630 public int getHeight() { 631 return mToolbarLayout.getHeight(); 632 } 633 634 /** 635 * Sets the highlight on the new tab button shown during overview mode. 636 * @param highlight If the new tab button should be highlighted. 637 */ setNewTabButtonHighlight(boolean highlight)638 public void setNewTabButtonHighlight(boolean highlight) { 639 if (mTabSwitcherModeCoordinatorPhone != null) { 640 mTabSwitcherModeCoordinatorPhone.setNewTabButtonHighlight(highlight); 641 } else if (mStartSurfaceToolbarCoordinator != null) { 642 mStartSurfaceToolbarCoordinator.setNewTabButtonHighlight(highlight); 643 } 644 } 645 646 /** 647 * @return The {@link ToolbarLayout} that constitutes the toolbar. 648 */ 649 @VisibleForTesting getToolbarLayoutForTesting()650 public ToolbarLayout getToolbarLayoutForTesting() { 651 return mToolbarLayout; 652 } 653 654 @VisibleForTesting getStartSurfaceToolbarForTesting()655 public StartSurfaceToolbarCoordinator getStartSurfaceToolbarForTesting() { 656 return mStartSurfaceToolbarCoordinator; 657 } 658 } 659