[lens overlay] Suppress the page action on the NTP Also adds interactive tests for focused location bar state. Bug: 344654856 Change-Id: I4001341075abf053738825bbfb347fa33a2ce96f Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/5594613 Commit-Queue: Thomas Lukaszewicz <tluk@chromium.org> Reviewed-by: Peter Boström <pbos@chromium.org> Code-Coverage: findit-for-me@appspot.gserviceaccount.com <findit-for-me@appspot.gserviceaccount.com> Reviewed-by: Eshwar Stalin <estalin@chromium.org> Cr-Commit-Position: refs/heads/main@{#1310205}
diff --git a/chrome/browser/ui/browser_element_identifiers.cc b/chrome/browser/ui/browser_element_identifiers.cc index cfa94e3..18482c3 100644 --- a/chrome/browser/ui/browser_element_identifiers.cc +++ b/chrome/browser/ui/browser_element_identifiers.cc
@@ -34,6 +34,7 @@ DEFINE_ELEMENT_IDENTIFIER_VALUE(kInactiveTabSettingElementId); DEFINE_ELEMENT_IDENTIFIER_VALUE(kInstallPwaElementId); DEFINE_ELEMENT_IDENTIFIER_VALUE(kIntentChipElementId); +DEFINE_ELEMENT_IDENTIFIER_VALUE(kLensOverlayPageActionIconElementId); DEFINE_ELEMENT_IDENTIFIER_VALUE(kLensPermissionDialogCancelButtonElementId); DEFINE_ELEMENT_IDENTIFIER_VALUE(kLensPermissionDialogOkButtonElementId); DEFINE_ELEMENT_IDENTIFIER_VALUE(kLensSearchBubbleElementId);
diff --git a/chrome/browser/ui/browser_element_identifiers.h b/chrome/browser/ui/browser_element_identifiers.h index 3b21c41..6c69dbd 100644 --- a/chrome/browser/ui/browser_element_identifiers.h +++ b/chrome/browser/ui/browser_element_identifiers.h
@@ -43,6 +43,7 @@ DECLARE_ELEMENT_IDENTIFIER_VALUE(kInactiveTabSettingElementId); DECLARE_ELEMENT_IDENTIFIER_VALUE(kInstallPwaElementId); DECLARE_ELEMENT_IDENTIFIER_VALUE(kIntentChipElementId); +DECLARE_ELEMENT_IDENTIFIER_VALUE(kLensOverlayPageActionIconElementId); DECLARE_ELEMENT_IDENTIFIER_VALUE(kLensPermissionDialogCancelButtonElementId); DECLARE_ELEMENT_IDENTIFIER_VALUE(kLensPermissionDialogOkButtonElementId); DECLARE_ELEMENT_IDENTIFIER_VALUE(kLensSearchBubbleElementId);
diff --git a/chrome/browser/ui/views/location_bar/lens_overlay_page_action_icon_view.cc b/chrome/browser/ui/views/location_bar/lens_overlay_page_action_icon_view.cc index 8c6a6c0b..cd4bf1d4 100644 --- a/chrome/browser/ui/views/location_bar/lens_overlay_page_action_icon_view.cc +++ b/chrome/browser/ui/views/location_bar/lens_overlay_page_action_icon_view.cc
@@ -4,15 +4,46 @@ #include "chrome/browser/ui/views/location_bar/lens_overlay_page_action_icon_view.h" +#include "chrome/browser/search/search.h" +#include "chrome/browser/ui/browser_element_identifiers.h" #include "chrome/browser/ui/color/chrome_color_id.h" #include "chrome/browser/ui/lens/lens_overlay_controller.h" #include "chrome/browser/ui/views/frame/browser_view.h" #include "chrome/browser/ui/views/location_bar/location_bar_view.h" #include "chrome/browser/ui/views/omnibox/omnibox_view_views.h" +#include "chrome/browser/ui/webui/new_tab_page/new_tab_page_ui.h" +#include "chrome/browser/ui/webui/new_tab_page_third_party/new_tab_page_third_party_ui.h" +#include "chrome/browser/ui/webui/ntp/new_tab_ui.h" #include "chrome/browser/user_education/user_education_service.h" #include "components/lens/lens_features.h" #include "components/vector_icons/vector_icons.h" +#include "content/public/browser/navigation_controller.h" +#include "content/public/browser/navigation_entry.h" #include "ui/base/metadata/metadata_impl_macros.h" +#include "ui/views/view_class_properties.h" + +namespace { + +// TODO(tluk): Similar bespoke checks are used throughout the codebase, this +// approach is taken from BookmarkTabHelper. This should be factored out as a +// common util and other callsites converted to use this. +bool IsNewTabPage(content::WebContents* const web_contents) { + // Use the committed entry (or the visible entry, if the committed entry is + // the initial NavigationEntry) so the bookmarks bar disappears at the same + // time the page does. + CHECK(web_contents); + content::NavigationEntry* entry = + web_contents->GetController().GetLastCommittedEntry(); + if (entry->IsInitialEntry()) { + entry = web_contents->GetController().GetVisibleEntry(); + } + const GURL& url = entry->GetURL(); + return NewTabUI::IsNewTab(url) || NewTabPageUI::IsNewTabPageOrigin(url) || + NewTabPageThirdPartyUI::IsNewTabPageOrigin(url) || + search::NavEntryIsInstantNTP(web_contents, entry); +} + +} // namespace LensOverlayPageActionIconView::LensOverlayPageActionIconView( Browser* browser, @@ -28,6 +59,8 @@ image_container_view()->SetFlipCanvasOnPaintForRTLUI(false); SetUpForInOutAnimation(); + SetProperty(views::kElementIdentifierKey, + kLensOverlayPageActionIconElementId); SetLabel(l10n_util::GetStringUTF16(IDS_CONTENT_CONTEXT_LENS_OVERLAY)); SetUseTonalColorsWhenExpanded(true); SetPaintLabelOverSolidBackground(true); @@ -45,9 +78,15 @@ focus_manager->GetFocusedView()); } } + + // The overlay is unavailable on the NTP as it is unlikely to be useful to + // users on the page, it would also appear immediately when a new tab or + // window is created due to focus immediatey jumping into the location bar. + auto* web_Contents = GetWebContents(); const bool lens_overlay_available = - GetWebContents() && - LensOverlayController::GetController(GetWebContents()) != nullptr; + web_Contents && + LensOverlayController::GetController(web_Contents) != nullptr && + !IsNewTabPage(web_Contents); SetVisible(location_bar_has_focus && lens_overlay_available); ResetSlideAnimation(true); @@ -56,6 +95,10 @@ // the last call to IconLabelBubbleView::UpdateBackground() seems to think // that the label isn't showing / shouldn't paint over a solid background. UpdateBackground(); + + if (update_callback_for_testing_) { + std::move(update_callback_for_testing_).Run(); + } } void LensOverlayPageActionIconView::OnExecuting(
diff --git a/chrome/browser/ui/views/location_bar/lens_overlay_page_action_icon_view.h b/chrome/browser/ui/views/location_bar/lens_overlay_page_action_icon_view.h index 4a4a60f0..962400b 100644 --- a/chrome/browser/ui/views/location_bar/lens_overlay_page_action_icon_view.h +++ b/chrome/browser/ui/views/location_bar/lens_overlay_page_action_icon_view.h
@@ -5,6 +5,7 @@ #ifndef CHROME_BROWSER_UI_VIEWS_LOCATION_BAR_LENS_OVERLAY_PAGE_ACTION_ICON_VIEW_H_ #define CHROME_BROWSER_UI_VIEWS_LOCATION_BAR_LENS_OVERLAY_PAGE_ACTION_ICON_VIEW_H_ +#include "base/functional/callback_forward.h" #include "base/memory/raw_ptr.h" #include "chrome/browser/ui/views/page_action/page_action_icon_view.h" #include "ui/base/metadata/metadata_header_macros.h" @@ -24,6 +25,10 @@ const LensOverlayPageActionIconView&) = delete; ~LensOverlayPageActionIconView() override; + void set_update_callback_for_testing(base::OnceClosure update_callback) { + update_callback_for_testing_ = std::move(update_callback); + } + protected: // PageActionIconView: void UpdateImpl() override; @@ -35,6 +40,7 @@ private: raw_ptr<Browser> browser_; + base::OnceClosure update_callback_for_testing_; }; #endif // CHROME_BROWSER_UI_VIEWS_LOCATION_BAR_LENS_OVERLAY_PAGE_ACTION_ICON_VIEW_H_
diff --git a/chrome/browser/ui/views/location_bar/lens_overlay_page_action_icon_view_interactive_uitest.cc b/chrome/browser/ui/views/location_bar/lens_overlay_page_action_icon_view_interactive_uitest.cc new file mode 100644 index 0000000..a3394fe --- /dev/null +++ b/chrome/browser/ui/views/location_bar/lens_overlay_page_action_icon_view_interactive_uitest.cc
@@ -0,0 +1,94 @@ +// Copyright 2024 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +// #include "build/build_config.h" +#include "chrome/browser/ui/browser_element_identifiers.h" +#include "chrome/browser/ui/views/frame/browser_view.h" +#include "chrome/browser/ui/views/location_bar/lens_overlay_page_action_icon_view.h" +#include "chrome/browser/ui/views/location_bar/location_bar_view.h" +#include "chrome/browser/ui/views/toolbar/toolbar_view.h" +#include "chrome/common/webui_url_constants.h" +#include "chrome/test/base/in_process_browser_test.h" +#include "chrome/test/base/ui_test_utils.h" +#include "components/lens/lens_features.h" +#include "content/public/test/browser_test.h" +#include "ui/views/interaction/element_tracker_views.h" +#include "url/url_constants.h" + +namespace { + +class LensOverlayPageActionIconViewTest : public InProcessBrowserTest { + public: + LensOverlayPageActionIconViewTest() { + scoped_feature_list_.InitWithFeatures({lens::features::kLensOverlay}, {}); + } + LensOverlayPageActionIconViewTest(const LensOverlayPageActionIconViewTest&) = + delete; + LensOverlayPageActionIconViewTest& operator=( + const LensOverlayPageActionIconViewTest&) = delete; + ~LensOverlayPageActionIconViewTest() override = default; + + LensOverlayPageActionIconView* lens_overlay_icon_view() { + views::View* const icon_view = + views::ElementTrackerViews::GetInstance()->GetFirstMatchingView( + kLensOverlayPageActionIconElementId, + browser()->window()->GetElementContext()); + return icon_view + ? views::AsViewClass<LensOverlayPageActionIconView>(icon_view) + : nullptr; + } + + LocationBarView* location_bar() { + BrowserView* browser_view = + BrowserView::GetBrowserViewForBrowser(browser()); + return views::AsViewClass<LocationBarView>( + browser_view->toolbar()->location_bar()); + } + + private: + base::test::ScopedFeatureList scoped_feature_list_; +}; + +IN_PROC_BROWSER_TEST_F(LensOverlayPageActionIconViewTest, + ShowsWhenLocationBarFocused) { + // Navigate to a non-NTP page. + ASSERT_TRUE( + ui_test_utils::NavigateToURL(browser(), GURL(url::kAboutBlankURL))); + + LensOverlayPageActionIconView* icon_view = lens_overlay_icon_view(); + views::FocusManager* focus_manager = icon_view->GetFocusManager(); + focus_manager->ClearFocus(); + EXPECT_FALSE(focus_manager->GetFocusedView()); + EXPECT_FALSE(icon_view->GetVisible()); + + // Focus in the location bar should show the icon. + base::RunLoop run_loop; + icon_view->set_update_callback_for_testing(run_loop.QuitClosure()); + location_bar()->FocusLocation(false); + EXPECT_TRUE(focus_manager->GetFocusedView()); + run_loop.Run(); + EXPECT_TRUE(icon_view->GetVisible()); +} + +IN_PROC_BROWSER_TEST_F(LensOverlayPageActionIconViewTest, DoesNotShowOnNTP) { + // Navigate to the NTP. + ASSERT_TRUE(ui_test_utils::NavigateToURL( + browser(), GURL(chrome::kChromeUINewTabPageURL))); + + LensOverlayPageActionIconView* icon_view = lens_overlay_icon_view(); + views::FocusManager* focus_manager = icon_view->GetFocusManager(); + focus_manager->ClearFocus(); + EXPECT_FALSE(focus_manager->GetFocusedView()); + EXPECT_FALSE(icon_view->GetVisible()); + + // The icon should remain hidden despite focus in the location bar. + base::RunLoop run_loop; + icon_view->set_update_callback_for_testing(run_loop.QuitClosure()); + location_bar()->FocusLocation(false); + EXPECT_TRUE(focus_manager->GetFocusedView()); + run_loop.Run(); + EXPECT_FALSE(icon_view->GetVisible()); +} + +} // namespace
diff --git a/chrome/test/BUILD.gn b/chrome/test/BUILD.gn index 8a87688c..35851a6 100644 --- a/chrome/test/BUILD.gn +++ b/chrome/test/BUILD.gn
@@ -11436,6 +11436,7 @@ "../browser/ui/views/fullscreen_control/fullscreen_control_view_interactive_uitest.cc", "../browser/ui/views/keyboard_access_interactive_uitest.cc", "../browser/ui/views/location_bar/cookie_controls/cookie_controls_interactive_uitest.cc", + "../browser/ui/views/location_bar/lens_overlay_page_action_icon_view_interactive_uitest.cc", "../browser/ui/views/location_bar/location_icon_view_interactive_uitest.cc", "../browser/ui/views/location_bar/read_anything_icon_view_interactive_uitest.cc", "../browser/ui/views/location_bar/selected_keyword_view_interactive_uitest.cc",