blob: 5eb9c3fe624b2f7119dbd7262acfdf6c218da0ae [file] [log] [blame]
// Copyright 2021 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef CHROME_BROWSER_UI_VIEWS_EXTENSIONS_EXTENSIONS_TABBED_MENU_VIEW_H_
#define CHROME_BROWSER_UI_VIEWS_EXTENSIONS_EXTENSIONS_TABBED_MENU_VIEW_H_
#include "base/memory/raw_ptr.h"
#include "chrome/browser/extensions/site_permissions_helper.h"
#include "chrome/browser/ui/extensions/extension_action_view_controller.h"
#include "chrome/browser/ui/tabs/tab_strip_model_observer.h"
#include "chrome/browser/ui/toolbar/toolbar_actions_model.h"
#include "chrome/browser/ui/views/controls/hover_button.h"
#include "chrome/browser/ui/views/extensions/extensions_toolbar_button.h"
#include "extensions/browser/permissions_manager.h"
#include "ui/base/metadata/metadata_header_macros.h"
#include "ui/views/bubble/bubble_dialog_delegate_view.h"
namespace views {
class View;
class TabbedPane;
} // namespace views
class InstalledExtensionMenuItemView;
class SiteAccessMenuItemView;
class ExtensionsContainer;
class SiteSettingsExpandButton;
// ExtensionsTabbedMenuView is the extensions menu dialog with a tabbed pane.
// TODO(crbug.com/1263311): Brief explanation of each tabs goal after
// implementing them.
class ExtensionsTabbedMenuView
: public views::BubbleDialogDelegateView,
public TabStripModelObserver,
public ToolbarActionsModel::Observer,
public extensions::PermissionsManager::Observer {
public:
METADATA_HEADER(ExtensionsTabbedMenuView);
ExtensionsTabbedMenuView(views::View* anchor_view,
Browser* browser,
ExtensionsContainer* extensions_container,
bool allow_pinning);
~ExtensionsTabbedMenuView() override;
ExtensionsTabbedMenuView(const ExtensionsTabbedMenuView&) = delete;
const ExtensionsTabbedMenuView& operator=(const ExtensionsTabbedMenuView&) =
delete;
// Returns the currently-showing extension items in the extensions tab, if any
// exists.
std::vector<InstalledExtensionMenuItemView*> GetInstalledItemsForTesting()
const;
// Returns the currently-showing `has_access_` extension items in the site
// access tab, if any exists.
std::vector<SiteAccessMenuItemView*> GetVisibleHasAccessItemsForTesting()
const;
// Returns the currently-showing `requests_access_` extension items in the
// site access tab, if any exists.
std::vector<SiteAccessMenuItemView*> GetVisibleRequestsAccessItemsForTesting()
const;
// Returns the site access message view in the site access tab.
views::Label* GetSiteAccessMessageForTesting() const;
// Returns the `discover_more_button_` in the extensions tab.
HoverButton* GetDiscoverMoreButtonForTesting() const;
// Returns the `site_settings_button_` in the site access tab.
HoverButton* GetSiteSettingsButtonForTesting() const;
// Returns the `site_settings_` in the site access tab.
views::View* GetSiteSettingsForTesting() const;
// Returns the index of the currently selected tab.
size_t GetSelectedTabIndex() const;
// views::BubbleDialogDelegateView:
std::u16string GetAccessibleWindowTitle() const override;
// TabStripModelObserver:
void TabChangedAt(content::WebContents* contents,
int index,
TabChangeType change_type) override;
void OnTabStripModelChanged(
TabStripModel* tab_strip_model,
const TabStripModelChange& change,
const TabStripSelectionChange& selection) override;
// ToolbarActionsModel::Observer:
void OnToolbarActionAdded(
const ToolbarActionsModel::ActionId& action_id) override;
void OnToolbarActionRemoved(
const ToolbarActionsModel::ActionId& action_id) override;
void OnToolbarActionUpdated(
const ToolbarActionsModel::ActionId& action_id) override;
void OnToolbarModelInitialized() override;
void OnToolbarPinnedActionsChanged() override;
// PermissionsManager::Observer:
void OnUserPermissionsSettingsChanged(
const extensions::PermissionsManager::UserPermissionsSettings& settings)
override;
private:
struct SiteAccessSection {
// The root view for this section used to toggle the visibility of the
// entire section (depending on whether there are any menu items).
raw_ptr<views::View> container;
// The view containing the section heder. The text changes based on the
// current site.
raw_ptr<views::Label> header;
// The view containing only the menu items for this section.
raw_ptr<views::View> items;
// The id of the string to use for the section heading. Does not include the
// current site string.
const int header_string_id;
};
// Initially creates the tabs.
void Populate();
// Updates the menu.
void Update();
void CreateSiteAccessTab();
void CreateExtensionsTab();
// Creates and adds a menu item for `id` in the installed extensions for a
// newly-added extension.
void CreateAndInsertInstalledExtension(
const ToolbarActionsModel::ActionId& id,
size_t index);
// Creates and adds a menu item for `id` in its corresponding site access
// section if the associated extension has or requests access to the current
// site.
void MaybeCreateAndInsertSiteAccessItem(
const ToolbarActionsModel::ActionId& id);
// Adds `item` to the items list of `section`.
void InsertSiteAccessItem(std::unique_ptr<SiteAccessMenuItemView> item,
SiteAccessSection* section);
// Updates the installed extension menu items corresponding to `action_ids`,
// and their positions in the extensions tab.
void UpdateInstalledExtensionMenuItems(
const base::flat_set<ToolbarActionsModel::ActionId>& action_ids);
// Updates the site access menu items corresponding to `action_ids`, and their
// positions in their corresponding site access section (moving the item
// between sections if necessary). Note that if there is no site access item
// for an action id, it creates and inserts a site access item in its
// corresponding site access section.
void UpdateSiteAccessMenuItems(
const base::flat_set<ToolbarActionsModel::ActionId>& action_ids);
// Updates the visibility and contents of the site access tab based on the
// current site setting.
void UpdateSiteAccessTab();
// Updates the visibility and header of the site access sections, and whether
// their items should `show_combobox`. A given section should be visible if
// there are any extensions displayed in it.
void UpdateSiteAccessSectionsVisibility(bool show_combobox);
// Returns the section corresponding to `site_interaction`, or nullptr.
SiteAccessSection* GetSectionForAction(ToolbarActionViewController* action);
// Returns the currently-showing menu items for `section` in the
// site access tab, if any exists.
std::vector<SiteAccessMenuItemView*> GetVisibleMenuItemsOf(
SiteAccessSection section) const;
// Returns the current web contents in `browser_`.
content::WebContents* GetActiveWebContents();
// Handles the selection of a site setting radio button.
void OnSiteSettingSelected(
extensions::PermissionsManager::UserSiteSetting site_setting);
// Shows or hides the site setting options when `site_settings_button_` is
// pressed.
void OnSiteSettingsButtonPressed();
// Runs a set of consistency checks on the appearance of the menu. This is a
// no-op if DCHECKs are disabled.
void ConsistencyCheck();
const raw_ptr<Browser> browser_;
const raw_ptr<ExtensionsContainer> extensions_container_;
const raw_ptr<ToolbarActionsModel> toolbar_model_;
const bool allow_pinning_;
base::ScopedObservation<ToolbarActionsModel, ToolbarActionsModel::Observer>
toolbar_model_observation_{this};
base::ScopedObservation<extensions::PermissionsManager,
extensions::PermissionsManager::Observer>
permissions_manager_observation_{this};
// The view containing the menu's two tabs.
raw_ptr<views::TabbedPane> tabbed_pane_ = nullptr;
// The view containing the installed menu items in the extensions tab. This is
// separated for easy insertion and iteration of menu items. The children are
// guaranteed to only be ExtensionMenuItemViews.
views::View* installed_items_ = nullptr;
// The button used to open the webstore page in the extensions tab.
HoverButton* discover_more_button_ = nullptr;
// The view containing a message in the site access tab.
raw_ptr<views::Label> site_access_message_ = nullptr;
// The button used to open the site settings in the site access tab.
raw_ptr<SiteSettingsExpandButton> site_settings_button_ = nullptr;
// The view containing the site settings in the site access tab.
raw_ptr<views::View> site_settings_ = nullptr;
// The visibility of the site settings view. By default, it is not visible.
bool show_site_settings_ = false;
// The different sections in the site access tab.
SiteAccessSection requests_access_;
SiteAccessSection has_access_;
};
BEGIN_VIEW_BUILDER(/* no export */,
ExtensionsTabbedMenuView,
views::BubbleDialogDelegateView)
END_VIEW_BUILDER
DEFINE_VIEW_BUILDER(/* no export */, ExtensionsTabbedMenuView)
#endif // CHROME_BROWSER_UI_VIEWS_EXTENSIONS_EXTENSIONS_TABBED_MENU_VIEW_H_