1 // Copyright 2014 The Chromium Authors
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 #ifndef COMPONENTS_RENDERER_CONTEXT_MENU_RENDER_VIEW_CONTEXT_MENU_BASE_H_
6 #define COMPONENTS_RENDERER_CONTEXT_MENU_RENDER_VIEW_CONTEXT_MENU_BASE_H_
16 #include "base/memory/raw_ptr.h"
17 #include "base/observer_list.h"
18 #include "components/renderer_context_menu/context_menu_content_type.h"
19 #include "components/renderer_context_menu/render_view_context_menu_observer.h"
20 #include "components/renderer_context_menu/render_view_context_menu_proxy.h"
21 #include "content/public/browser/context_menu_params.h"
22 #include "content/public/browser/page_navigator.h"
23 #include "content/public/browser/site_instance.h"
24 #include "ppapi/buildflags/buildflags.h"
25 #include "third_party/blink/public/common/tokens/tokens.h"
26 #include "ui/base/models/simple_menu_model.h"
27 #include "ui/base/page_transition_types.h"
28 #include "ui/base/window_open_disposition.h"
31 class RenderFrameHost;
35 class RenderViewContextMenuBase : public ui::SimpleMenuModel::Delegate,
36 public RenderViewContextMenuProxy {
38 // A delegate interface to communicate with the toolkit used by
40 class ToolkitDelegate {
42 virtual ~ToolkitDelegate() {}
43 // Initialize the toolkit's menu.
44 virtual void Init(ui::SimpleMenuModel* menu_model) = 0;
46 virtual void Cancel() = 0;
48 // Updates the actual menu items controlled by the toolkit.
49 virtual void UpdateMenuItem(int command_id,
52 const std::u16string& title) {}
54 // Recreates the menu using the |menu_model_|.
55 virtual void RebuildMenu(){}
58 static const size_t kMaxSelectionTextLength;
60 static void SetContentCustomCommandIdRange(int first, int last);
62 // Convert a command ID so that it fits within the range for
63 // content context menu.
64 static int ConvertToContentCustomCommandId(int id);
66 // True if the given id is the one generated for content context menu.
67 static bool IsContentCustomCommandId(int id);
69 RenderViewContextMenuBase(content::RenderFrameHost& render_frame_host,
70 const content::ContextMenuParams& params);
72 RenderViewContextMenuBase(const RenderViewContextMenuBase&) = delete;
73 RenderViewContextMenuBase& operator=(const RenderViewContextMenuBase&) =
76 ~RenderViewContextMenuBase() override;
79 // Different platform will have their own implementation.
80 virtual void Show() = 0;
82 // Initializes the context menu.
85 // Programmatically closes the context menu.
88 const ui::SimpleMenuModel& menu_model() const { return menu_model_; }
89 const content::ContextMenuParams& params() const { return params_; }
91 // Returns true if the specified command id is known and valid for
92 // this menu. If the command is known |enabled| is set to indicate
93 // if the command is enabled.
94 bool IsCommandIdKnown(int command_id, bool* enabled) const;
96 // SimpleMenuModel::Delegate implementation.
97 bool IsCommandIdChecked(int command_id) const override;
98 void ExecuteCommand(int command_id, int event_flags) override;
99 void OnMenuWillShow(ui::SimpleMenuModel* source) override;
100 void MenuClosed(ui::SimpleMenuModel* source) override;
102 // RenderViewContextMenuProxy implementation.
103 void AddMenuItem(int command_id, const std::u16string& title) override;
104 void AddMenuItemWithIcon(int command_id,
105 const std::u16string& title,
106 const ui::ImageModel& icon) override;
107 void AddCheckItem(int command_id, const std::u16string& title) override;
108 void AddSeparator() override;
109 void AddSubMenu(int command_id,
110 const std::u16string& label,
111 ui::MenuModel* model) override;
112 void AddSubMenuWithStringIdAndIcon(int command_id,
114 ui::MenuModel* model,
115 const ui::ImageModel& icon) override;
116 void UpdateMenuItem(int command_id,
119 const std::u16string& title) override;
120 void UpdateMenuIcon(int command_id, const ui::ImageModel& icon) override;
121 void RemoveMenuItem(int command_id) override;
122 void RemoveAdjacentSeparators() override;
123 void RemoveSeparatorBeforeMenuItem(int command_id) override;
124 content::RenderViewHost* GetRenderViewHost() const override;
125 content::WebContents* GetWebContents() const override;
126 content::BrowserContext* GetBrowserContext() const override;
128 // May return nullptr if the frame was deleted while the menu was open.
129 content::RenderFrameHost* GetRenderFrameHost() const;
132 friend class RenderViewContextMenuTest;
133 friend class RenderViewContextMenuPrefsTest;
135 void set_content_type(std::unique_ptr<ContextMenuContentType> content_type) {
136 content_type_ = std::move(content_type);
139 void set_toolkit_delegate(std::unique_ptr<ToolkitDelegate> delegate) {
140 toolkit_delegate_ = std::move(delegate);
143 ToolkitDelegate* toolkit_delegate() {
144 return toolkit_delegate_.get();
147 // TODO(oshima): Make these methods delegate.
149 // Menu Construction.
150 virtual void InitMenu();
152 // Increments histogram value for used items specified by |id|.
153 virtual void RecordUsedItem(int id) = 0;
155 // Increments histogram value for visible context menu item specified by |id|.
156 virtual void RecordShownItem(int id, bool is_submenu) = 0;
158 #if BUILDFLAG(ENABLE_PLUGINS)
159 virtual void HandleAuthorizeAllPlugins() = 0;
162 // Subclasses should send notification.
163 virtual void NotifyMenuShown() = 0;
165 // TODO(oshima): Remove this.
166 virtual void AppendPlatformEditableItems() {}
167 virtual void ExecOpenInReadAnything() = 0;
169 bool IsCustomItemChecked(int id) const;
170 bool IsCustomItemEnabled(int id) const;
172 // Opens the specified URL string in a new tab.
173 void OpenURL(const GURL& url,
174 const GURL& referrer,
175 WindowOpenDisposition disposition,
176 ui::PageTransition transition);
178 // Opens the specified URL string in a new tab with the extra headers.
179 void OpenURLWithExtraHeaders(const GURL& url,
180 const GURL& referrer,
181 WindowOpenDisposition disposition,
182 ui::PageTransition transition,
183 const std::string& extra_headers,
184 bool started_from_context_menu);
186 // Populates OpenURLParams for opening the specified URL string in a new tab
187 // with the extra headers.
188 content::OpenURLParams GetOpenURLParamsWithExtraHeaders(
190 const GURL& referring_url,
191 WindowOpenDisposition disposition,
192 ui::PageTransition transition,
193 const std::string& extra_headers,
194 bool started_from_context_menu);
196 content::ContextMenuParams params_;
197 const raw_ptr<content::WebContents, DanglingUntriaged> source_web_contents_;
198 const raw_ptr<content::BrowserContext, DanglingUntriaged> browser_context_;
200 ui::SimpleMenuModel menu_model_;
202 // Renderer's frame id.
203 const int render_frame_id_;
205 // Renderer's frame token.
206 const blink::LocalFrameToken render_frame_token_;
208 // The RenderFrameHost's IDs.
209 const int render_process_id_;
211 // Renderer's frame SiteInstance.
212 scoped_refptr<content::SiteInstance> site_instance_;
215 mutable base::ObserverList<RenderViewContextMenuObserver>::Unchecked
218 // Whether a command has been executed. Used to track whether menu observers
219 // should be notified of menu closing without execution.
220 bool command_executed_;
222 std::unique_ptr<ContextMenuContentType> content_type_;
225 bool AppendCustomItems();
227 std::unique_ptr<ToolkitDelegate> toolkit_delegate_;
229 std::vector<std::unique_ptr<ui::SimpleMenuModel>> custom_submenus_;
232 #endif // COMPONENTS_RENDERER_CONTEXT_MENU_RENDER_VIEW_CONTEXT_MENU_BASE_H_