diff options
author | ben@chromium.org <ben@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2009-06-08 21:01:37 +0000 |
---|---|---|
committer | ben@chromium.org <ben@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2009-06-08 21:01:37 +0000 |
commit | bca924e224f92b919ac329147e7ba3526b9ce12e (patch) | |
tree | d6b0ea493ed3eba2d686386f33104fd967274483 /chrome/browser/views | |
parent | d30e8c59447987afbbd59aac74e927e9b4ed86b0 (diff) | |
download | chromium_src-bca924e224f92b919ac329147e7ba3526b9ce12e.zip chromium_src-bca924e224f92b919ac329147e7ba3526b9ce12e.tar.gz chromium_src-bca924e224f92b919ac329147e7ba3526b9ce12e.tar.bz2 |
Convert toolbar page and app menus over to use the new system.
TEST=test page and app menus thoroughly.
Review URL: http://codereview.chromium.org/119291
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@17897 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'chrome/browser/views')
-rw-r--r-- | chrome/browser/views/frame/browser_view.cc | 212 | ||||
-rw-r--r-- | chrome/browser/views/frame/browser_view.h | 50 | ||||
-rw-r--r-- | chrome/browser/views/toolbar_view.cc | 366 | ||||
-rw-r--r-- | chrome/browser/views/toolbar_view.h | 84 |
4 files changed, 446 insertions, 266 deletions
diff --git a/chrome/browser/views/frame/browser_view.cc b/chrome/browser/views/frame/browser_view.cc index 18f80a4..de8d082 100644 --- a/chrome/browser/views/frame/browser_view.cc +++ b/chrome/browser/views/frame/browser_view.cc @@ -22,7 +22,6 @@ #include "chrome/browser/browser.h" #include "chrome/browser/browser_list.h" #include "chrome/browser/download/download_manager.h" -#include "chrome/browser/encoding_menu_controller_delegate.h" #include "chrome/browser/extensions/extension_shelf.h" #include "chrome/browser/find_bar.h" #include "chrome/browser/find_bar_controller.h" @@ -107,35 +106,6 @@ static int explicit_show_state = -1; // Returned from BrowserView::GetClassName. static const char kBrowserViewClassName[] = "browser/views/BrowserView"; -static const struct MenuLayout { - bool separator; - int command; - int label; -} kMenuLayout[] = { - { true, 0, 0 }, - { false, IDC_TASK_MANAGER, IDS_TASK_MANAGER }, - { true, 0, 0 }, - { false, IDC_ENCODING_MENU, IDS_ENCODING_MENU }, - { false, IDC_ZOOM_MENU, IDS_ZOOM_MENU }, - { false, IDC_PRINT, IDS_PRINT }, - { false, IDC_SAVE_PAGE, IDS_SAVE_PAGE }, - { false, IDC_FIND, IDS_FIND }, - { true, 0, 0 }, - { false, IDC_PASTE, IDS_PASTE }, - { false, IDC_COPY, IDS_COPY }, - { false, IDC_CUT, IDS_CUT }, - { true, 0, 0 }, - { false, IDC_NEW_TAB, IDS_APP_MENU_NEW_WEB_PAGE }, - { false, IDC_SHOW_AS_TAB, IDS_SHOW_AS_TAB }, - { false, IDC_COPY_URL, IDS_APP_MENU_COPY_URL }, - { false, IDC_DUPLICATE_TAB, IDS_APP_MENU_DUPLICATE_APP_WINDOW }, - { false, IDC_RESTORE_TAB, IDS_RESTORE_TAB }, - { true, 0, 0 }, - { false, IDC_RELOAD, IDS_APP_MENU_RELOAD }, - { false, IDC_FORWARD, IDS_CONTENT_CONTEXT_FORWARD }, - { false, IDC_BACK, IDS_CONTENT_CONTEXT_BACK } -}; - /////////////////////////////////////////////////////////////////////////////// // ResizeCorner, private: @@ -532,27 +502,7 @@ SkBitmap BrowserView::GetOTRAvatarIcon() { #if defined(OS_WIN) void BrowserView::PrepareToRunSystemMenu(HMENU menu) { - for (int i = 0; i < arraysize(kMenuLayout); ++i) { - int command = kMenuLayout[i].command; - // |command| can be zero on submenu items (IDS_ENCODING, - // IDS_ZOOM) and on separators. - if (command != 0) { - bool enabled = browser_->command_updater()->IsCommandEnabled(command); - if (enabled && command == IDC_RESTORE_TAB) { - TabRestoreService* tab_restore_service = - browser_->profile()->GetTabRestoreService(); - if (tab_restore_service && !tab_restore_service->entries().empty()) { - system_menu_->SetMenuLabel(command, l10n_util::GetString( - tab_restore_service->entries().front()->type == - TabRestoreService::WINDOW ? IDS_RESTORE_WINDOW : - IDS_RESTORE_TAB)); - } else { - enabled = false; - } - } - system_menu_->EnableMenuItemByID(command, enabled); - } - } + system_menu_->UpdateStates(); } #endif @@ -1024,6 +974,50 @@ void BrowserView::TabStripEmpty() { } /////////////////////////////////////////////////////////////////////////////// +// BrowserView, views::SimpleMenuModel::Delegate implementation: + +void BrowserView::ExecuteCommand(views::Menu2Model* model, int command_id) { + browser_->ExecuteCommand(command_id); +} + +/////////////////////////////////////////////////////////////////////////////// +// BrowserView, views::SimpleMenuModel::Delegate implementation: + +bool BrowserView::IsCommandIdChecked(int command_id) const { + // TODO(beng): encoding menu. + // No items in our system menu are check-able. + return false; +} + +bool BrowserView::IsCommandIdEnabled(int command_id) const { + if (command_id == IDC_RESTORE_TAB) + return browser_->CanRestoreTab(); + return browser_->command_updater()->IsCommandEnabled(command_id); +} + +bool BrowserView::GetAcceleratorForCommandId(int command_id, + views::Accelerator* accelerator) { + // Let's let the ToolbarView own the canonical implementation of this method. + return toolbar_->GetAcceleratorForCommandId(command_id, accelerator); +} + +bool BrowserView::IsLabelForCommandIdDynamic(int command_id) const { + return command_id == IDC_RESTORE_TAB; +} + +std::wstring BrowserView::GetLabelForCommandId(int command_id) const { + DCHECK(command_id == IDC_RESTORE_TAB); + + int string_id = IDS_RESTORE_TAB; + if (IsCommandIdEnabled(command_id)) { + TabRestoreService* trs = browser_->profile()->GetTabRestoreService(); + if (trs && trs->entries().front()->type == TabRestoreService::WINDOW) + string_id = IDS_RESTORE_WINDOW; + } + return l10n_util::GetString(string_id); +} + +/////////////////////////////////////////////////////////////////////////////// // BrowserView, views::WindowDelegate implementation: bool BrowserView::CanResize() const { @@ -1377,32 +1371,26 @@ void BrowserView::Init() { AddChildView(extension_shelf_); } +#if defined(OS_WIN) InitSystemMenu(); +#endif } -void BrowserView::InitSystemMenu() { #if defined(OS_WIN) - system_menu_.reset( - views::Menu::GetSystemMenu(frame_->GetWindow()->GetNativeWindow())); - int insertion_index = std::max(0, system_menu_->ItemCount() - 1); +void BrowserView::InitSystemMenu() { + system_menu_contents_.reset(new views::SystemMenuModel(this)); // We add the menu items in reverse order so that insertion_index never needs // to change. - if (IsBrowserTypeNormal()) { - system_menu_->AddSeparator(insertion_index); - system_menu_->AddMenuItemWithLabel(insertion_index, IDC_TASK_MANAGER, - l10n_util::GetString(IDS_TASK_MANAGER)); - system_menu_->AddSeparator(insertion_index); - system_menu_->AddMenuItemWithLabel(insertion_index, IDC_RESTORE_TAB, - l10n_util::GetString(IDS_RESTORE_TAB)); - system_menu_->AddMenuItemWithLabel(insertion_index, IDC_NEW_TAB, - l10n_util::GetString(IDS_NEW_TAB)); - // If it's a regular browser window with tabs, we don't add any more items, - // since it already has menus (Page, Chrome). - } else { - BuildMenuForTabStriplessWindow(system_menu_.get(), insertion_index); - } -#endif + if (IsBrowserTypeNormal()) + BuildSystemMenuForBrowserWindow(); + else + BuildSystemMenuForPopupWindow(); + system_menu_.reset( + new views::NativeMenuWin(system_menu_contents_.get(), this, + frame_->GetWindow()->GetNativeWindow())); + system_menu_->Rebuild(); } +#endif int BrowserView::LayoutTabStrip() { gfx::Rect tabstrip_bounds = frame_->GetBoundsForTabStrip(tabstrip_); @@ -1630,44 +1618,54 @@ void BrowserView::LoadAccelerators() { #endif } -void BrowserView::BuildMenuForTabStriplessWindow(views::Menu* menu, - int insertion_index) { - encoding_menu_delegate_.reset(new EncodingMenuControllerDelegate( - browser_.get())); - - for (size_t i = 0; i < arraysize(kMenuLayout); ++i) { - if (kMenuLayout[i].separator) { - menu->AddSeparator(insertion_index); - } else { - int command = kMenuLayout[i].command; - if (command == IDC_ENCODING_MENU) { - views::Menu* encoding_menu = menu->AddSubMenu( - insertion_index, - IDC_ENCODING_MENU, - l10n_util::GetString(IDS_ENCODING_MENU)); - encoding_menu->set_delegate(encoding_menu_delegate_.get()); - EncodingMenuControllerDelegate::BuildEncodingMenu(browser_->profile(), - encoding_menu); - } else if (command == IDC_ZOOM_MENU) { - views::Menu* zoom_menu = - menu->AddSubMenu(insertion_index, IDC_ZOOM_MENU, - l10n_util::GetString(IDS_ZOOM_MENU)); - zoom_menu->AppendMenuItemWithLabel( - IDC_ZOOM_PLUS, - l10n_util::GetString(IDS_ZOOM_PLUS)); - zoom_menu->AppendMenuItemWithLabel( - IDC_ZOOM_NORMAL, - l10n_util::GetString(IDS_ZOOM_NORMAL)); - zoom_menu->AppendMenuItemWithLabel( - IDC_ZOOM_MINUS, - l10n_util::GetString(IDS_ZOOM_MINUS)); - } else { - menu->AddMenuItemWithLabel(insertion_index, command, - l10n_util::GetString(kMenuLayout[i].label)); - } - } - } +#if defined(OS_WIN) +void BrowserView::BuildSystemMenuForBrowserWindow() { + system_menu_contents_->AddSeparator(); + system_menu_contents_->AddItemWithStringId(IDC_TASK_MANAGER, + IDS_TASK_MANAGER); + system_menu_contents_->AddSeparator(); + system_menu_contents_->AddItemWithStringId(IDC_RESTORE_TAB, IDS_RESTORE_TAB); + system_menu_contents_->AddItemWithStringId(IDC_NEW_TAB, IDS_NEW_TAB); + // If it's a regular browser window with tabs, we don't add any more items, + // since it already has menus (Page, Chrome). +} + +void BrowserView::BuildSystemMenuForPopupWindow() { + system_menu_contents_->AddSeparator(); + system_menu_contents_->AddItemWithStringId(IDC_TASK_MANAGER, + IDS_TASK_MANAGER); + system_menu_contents_->AddSeparator(); + encoding_menu_contents_.reset(new EncodingMenuModel(browser_.get())); + system_menu_contents_->AddSubMenuWithStringId(IDS_ENCODING_MENU, + encoding_menu_contents_.get()); + zoom_menu_contents_.reset(new ZoomMenuModel(this)); + system_menu_contents_->AddSubMenuWithStringId(IDS_ZOOM_MENU, + zoom_menu_contents_.get()); + system_menu_contents_->AddItemWithStringId(IDC_PRINT, IDS_PRINT); + system_menu_contents_->AddItemWithStringId(IDC_SAVE_PAGE, + IDS_SAVE_PAGE); + system_menu_contents_->AddItemWithStringId(IDC_FIND, IDS_FIND); + system_menu_contents_->AddSeparator(); + system_menu_contents_->AddItemWithStringId(IDC_PASTE, IDS_PASTE); + system_menu_contents_->AddItemWithStringId(IDC_COPY, IDS_COPY); + system_menu_contents_->AddItemWithStringId(IDC_CUT, IDS_CUT); + system_menu_contents_->AddSeparator(); + system_menu_contents_->AddItemWithStringId(IDC_NEW_TAB, + IDS_APP_MENU_NEW_WEB_PAGE); + system_menu_contents_->AddItemWithStringId(IDC_SHOW_AS_TAB, IDS_SHOW_AS_TAB); + system_menu_contents_->AddItemWithStringId(IDC_COPY_URL, + IDS_APP_MENU_COPY_URL); + system_menu_contents_->AddItemWithStringId(IDC_DUPLICATE_TAB, + IDS_APP_MENU_DUPLICATE_APP_WINDOW); + system_menu_contents_->AddItemWithStringId(IDC_RESTORE_TAB, IDS_RESTORE_TAB); + system_menu_contents_->AddSeparator(); + system_menu_contents_->AddItemWithStringId(IDC_RELOAD, IDS_APP_MENU_RELOAD); + system_menu_contents_->AddItemWithStringId(IDC_FORWARD, + IDS_CONTENT_CONTEXT_FORWARD); + system_menu_contents_->AddItemWithStringId(IDC_BACK, + IDS_CONTENT_CONTEXT_BACK); } +#endif int BrowserView::GetCommandIDForAppCommandID(int app_command_id) const { #if defined(OS_WIN) diff --git a/chrome/browser/views/frame/browser_view.h b/chrome/browser/views/frame/browser_view.h index 3b15d55..a2e705c 100644 --- a/chrome/browser/views/frame/browser_view.h +++ b/chrome/browser/views/frame/browser_view.h @@ -11,15 +11,18 @@ #include "build/build_config.h" #include "chrome/browser/browser.h" #include "chrome/browser/browser_window.h" -#include "chrome/browser/tabs/tab_strip_model.h" -#include "chrome/browser/views/frame/browser_frame.h" -#include "views/window/client_view.h" -#include "views/window/window_delegate.h" - #if defined(OS_WIN) #include "chrome/browser/hang_monitor/hung_plugin_action.h" #include "chrome/browser/hang_monitor/hung_window_detector.h" #endif +#include "chrome/browser/tabs/tab_strip_model.h" +#include "chrome/browser/views/frame/browser_frame.h" +#if defined(OS_WIN) +#include "views/controls/menu/native_menu_win.h" +#endif +#include "views/controls/menu/simple_menu_model.h" +#include "views/window/client_view.h" +#include "views/window/window_delegate.h" // NOTE: For more information about the objects and files in this directory, // view: http://dev.chromium.org/developers/design-documents/browser-window @@ -28,15 +31,17 @@ class BookmarkBarView; class Browser; class BrowserBubble; class DownloadShelfView; -class EncodingMenuControllerDelegate; +class EncodingMenuModel; class ExtensionShelf; class FullscreenExitBubble; class HtmlDialogUIDelegate; class InfoBarContainer; +class LocationBarView; class StatusBubbleViews; class TabContentsContainer; class TabStrip; class ToolbarView; +class ZoomMenuModel; namespace views { class Menu; @@ -52,6 +57,8 @@ class BrowserView : public BrowserWindow, public BrowserWindowTesting, public NotificationObserver, public TabStripModelObserver, + public views::Menu2Delegate, + public views::SimpleMenuModel::Delegate, public views::WindowDelegate, public views::ClientView { public: @@ -250,6 +257,17 @@ class BrowserView : public BrowserWindow, bool user_gesture); virtual void TabStripEmpty(); + // Overridden from views::Menu2Delegate: + virtual void ExecuteCommand(views::Menu2Model* model, int command_id); + + // Overridden from views::SimpleMenuModel::Delegate: + virtual bool IsCommandIdChecked(int command_id) const; + virtual bool IsCommandIdEnabled(int command_id) const; + virtual bool GetAcceleratorForCommandId(int command_id, + views::Accelerator* accelerator); + virtual bool IsLabelForCommandIdDynamic(int command_id) const; + virtual std::wstring GetLabelForCommandId(int command_id) const; + // Overridden from views::WindowDelegate: virtual bool CanResize() const; virtual bool CanMaximize() const; @@ -286,8 +304,10 @@ class BrowserView : public BrowserWindow, // Browser window related initializations. void Init(); +#if defined(OS_WIN) // Creates the system menu. void InitSystemMenu(); +#endif // Layout the TabStrip, returns the coordinate of the bottom of the TabStrip, // for laying out subsequent controls. @@ -338,8 +358,11 @@ class BrowserView : public BrowserWindow, // use. void LoadAccelerators(); +#if defined(OS_WIN) // Builds the correct menu for when we have minimal chrome. - void BuildMenuForTabStriplessWindow(views::Menu* menu, int insertion_index); + void BuildSystemMenuForBrowserWindow(); + void BuildSystemMenuForPopupWindow(); +#endif // Retrieves the command id for the specified Windows app command. int GetCommandIDForAppCommandID(int app_command_id) const; @@ -400,19 +423,20 @@ class BrowserView : public BrowserWindow, scoped_ptr<FullscreenExitBubble> fullscreen_bubble_; - // Lazily created representation of the system menu. - scoped_ptr<views::Menu> system_menu_; - // The default favicon image. static SkBitmap default_favicon_; // The OTR avatar image. static SkBitmap otr_avatar_; - // The delegate for the encoding menu. - scoped_ptr<EncodingMenuControllerDelegate> encoding_menu_delegate_; - #if defined(OS_WIN) + // The additional items we insert into the system menu. + scoped_ptr<views::SystemMenuModel> system_menu_contents_; + scoped_ptr<ZoomMenuModel> zoom_menu_contents_; + scoped_ptr<EncodingMenuModel> encoding_menu_contents_; + // The wrapped system menu itself. + scoped_ptr<views::NativeMenuWin> system_menu_; + // This object is used to perform periodic actions in a worker // thread. It is currently used to monitor hung plugin windows. WorkerThreadTicker ticker_; diff --git a/chrome/browser/views/toolbar_view.cc b/chrome/browser/views/toolbar_view.cc index 00de1f4..986aab5 100644 --- a/chrome/browser/views/toolbar_view.cc +++ b/chrome/browser/views/toolbar_view.cc @@ -21,6 +21,7 @@ #include "chrome/browser/browser_process.h" #include "chrome/browser/browser_window.h" #include "chrome/browser/character_encoding.h" +#include "chrome/browser/encoding_menu_controller.h" #include "chrome/browser/metrics/user_metrics.h" #include "chrome/browser/profile.h" #include "chrome/browser/tab_contents/navigation_controller.h" @@ -81,11 +82,87 @@ static const int kOmniboxButtonsHorizontalMargin = 2; static SkBitmap* kPopupBackgroundEdge = NULL; //////////////////////////////////////////////////////////////////////////////// +// EncodingMenuModel + +EncodingMenuModel::EncodingMenuModel(Browser* browser) + : SimpleMenuModel(this), + browser_(browser) { + Build(); +} + +void EncodingMenuModel::Build() { + EncodingMenuController::EncodingMenuItemList encoding_menu_items; + EncodingMenuController encoding_menu_controller; + encoding_menu_controller.GetEncodingMenuItems(browser_->profile(), + &encoding_menu_items); + + int group_id = 0; + EncodingMenuController::EncodingMenuItemList::iterator it = + encoding_menu_items.begin(); + for (; it != encoding_menu_items.end(); ++it) { + int id = it->first; + std::wstring& label = it->second; + if (id == 0) { + AddSeparator(); + } else { + if (id == IDC_ENCODING_AUTO_DETECT) { + AddCheckItem(id, label); + } else { + // Use the id of the first radio command as the id of the group. + if (group_id <= 0) + group_id = id; + AddRadioItem(id, label, group_id); + } + } + } +} + +bool EncodingMenuModel::IsCommandIdChecked(int command_id) const { + TabContents* current_tab = browser_->GetSelectedTabContents(); + EncodingMenuController controller; + return controller.IsItemChecked(browser_->profile(), + current_tab->encoding(), command_id); +} + +bool EncodingMenuModel::IsCommandIdEnabled(int command_id) const { + return browser_->command_updater()->IsCommandEnabled(command_id); +} + +bool EncodingMenuModel::GetAcceleratorForCommandId( + int command_id, + views::Accelerator* accelerator) { + return false; +} + +bool EncodingMenuModel::IsLabelForCommandIdDynamic(int command_id) const { + // None of our items have dynamic labels. + return false; +} + +std::wstring EncodingMenuModel::GetLabelForCommandId(int command_id) const { + return std::wstring(); +} + + +//////////////////////////////////////////////////////////////////////////////// +// EncodingMenuModel + +ZoomMenuModel::ZoomMenuModel(views::SimpleMenuModel::Delegate* delegate) + : SimpleMenuModel(delegate) { + Build(); +} + +void ZoomMenuModel::Build() { + AddItemWithStringId(IDC_ZOOM_PLUS, IDS_ZOOM_PLUS); + AddItemWithStringId(IDC_ZOOM_NORMAL, IDS_ZOOM_NORMAL); + AddItemWithStringId(IDC_ZOOM_MINUS, IDS_ZOOM_MINUS); +} + +//////////////////////////////////////////////////////////////////////////////// // ToolbarView, public: ToolbarView::ToolbarView(Browser* browser) - : EncodingMenuControllerDelegate(browser), - model_(browser->toolbar_model()), + : model_(browser->toolbar_model()), acc_focused_view_(NULL), back_(NULL), forward_(NULL), @@ -179,17 +256,6 @@ int ToolbarView::GetNextAccessibleViewIndex(int view_index, bool nav_left) { } //////////////////////////////////////////////////////////////////////////////// -// ToolbarView, EncodingMenuControllerDelegate implementation: - -bool ToolbarView::IsItemChecked(int id) const { - if (!profile_) - return false; - if (id == IDC_SHOW_BOOKMARK_BAR) - return profile_->GetPrefs()->GetBoolean(prefs::kShowBookmarkBar); - return EncodingMenuControllerDelegate::IsItemChecked(id); -} - -//////////////////////////////////////////////////////////////////////////////// // ToolbarView, Menu::BaseControllerDelegate overrides: bool ToolbarView::GetAcceleratorInfo(int id, views::Accelerator* accel) { @@ -351,6 +417,55 @@ void ToolbarView::Observe(NotificationType type, } //////////////////////////////////////////////////////////////////////////////// +// ToolbarView, views::Menu2Delegate implementation: + +void ToolbarView::ExecuteCommand(views::Menu2Model* model, int command_id) { + browser_->ExecuteCommand(command_id); +} + +//////////////////////////////////////////////////////////////////////////////// +// ToolbarView, views::SimpleMenuModel::Delegate implementation: + +bool ToolbarView::IsCommandIdChecked(int command_id) const { + if (command_id == IDC_SHOW_BOOKMARK_BAR) + return profile_->GetPrefs()->GetBoolean(prefs::kShowBookmarkBar); + return false; +} + +bool ToolbarView::IsCommandIdEnabled(int command_id) const { + return browser_->command_updater()->IsCommandEnabled(command_id); +} + +bool ToolbarView::GetAcceleratorForCommandId(int command_id, + views::Accelerator* accelerator) { + // The standard Ctrl-X, Ctrl-V and Ctrl-C are not defined as accelerators + // anywhere so we need to check for them explicitly here. + // TODO(cpu) Bug 1109102. Query WebKit land for the actual bindings. + switch (command_id) { + case IDC_CUT: + *accelerator = views::Accelerator(L'X', false, true, false); + return true; + case IDC_COPY: + *accelerator = views::Accelerator(L'C', false, true, false); + return true; + case IDC_PASTE: + *accelerator = views::Accelerator(L'V', false, true, false); + return true; + } + // Else, we retrieve the accelerator information from the frame. + return GetWidget()->GetAccelerator(command_id, accelerator); +} + +bool ToolbarView::IsLabelForCommandIdDynamic(int command_id) const { + // None of our menu items have dynamic labels. + return false; +} + +std::wstring ToolbarView::GetLabelForCommandId(int command_id) const { + return std::wstring(); +} + +//////////////////////////////////////////////////////////////////////////////// // ToolbarView, views::View overrides: gfx::Size ToolbarView::GetPreferredSize() { @@ -657,12 +772,7 @@ void ToolbarView::SetAccessibleName(const std::wstring& name) { } //////////////////////////////////////////////////////////////////////////////// -// ToolbarView, private: - -int ToolbarView::PopupTopSpacing() const { - return GetWindow()->GetNonClientView()->UseNativeFrame() ? - 0 : kPopupTopSpacingNonGlass; -} +// ToolbarView, views::DragController implementation: void ToolbarView::WriteDragData(views::View* sender, int press_x, @@ -709,6 +819,14 @@ int ToolbarView::GetDragOperations(views::View* sender, int x, int y) { return DragDropTypes::DRAG_COPY | DragDropTypes::DRAG_LINK; } +//////////////////////////////////////////////////////////////////////////////// +// ToolbarView, private: + +int ToolbarView::PopupTopSpacing() const { + return GetWindow()->GetNonClientView()->UseNativeFrame() ? + 0 : kPopupTopSpacingNonGlass; +} + void ToolbarView::CreateLeftSideControls() { back_ = new views::ButtonDropDown(this, back_menu_model_.get()); back_->set_triggerable_event_flags(views::Event::EF_LEFT_BUTTON_DOWN | @@ -895,137 +1013,113 @@ void ToolbarView::LoadRightSideControlsImages() { } void ToolbarView::RunPageMenu(const gfx::Point& pt, gfx::NativeView parent) { - views::Menu::AnchorPoint anchor = views::Menu::TOPRIGHT; - if (UILayoutIsRightToLeft()) - anchor = views::Menu::TOPLEFT; - - scoped_ptr<views::Menu> menu(views::Menu::Create(this, anchor, parent)); - menu->AppendMenuItemWithLabel(IDC_CREATE_SHORTCUTS, - l10n_util::GetString(IDS_CREATE_SHORTCUTS)); - menu->AppendSeparator(); - menu->AppendMenuItemWithLabel(IDC_CUT, l10n_util::GetString(IDS_CUT)); - menu->AppendMenuItemWithLabel(IDC_COPY, l10n_util::GetString(IDS_COPY)); - menu->AppendMenuItemWithLabel(IDC_PASTE, l10n_util::GetString(IDS_PASTE)); - menu->AppendSeparator(); - - menu->AppendMenuItemWithLabel(IDC_FIND, - l10n_util::GetString(IDS_FIND)); - menu->AppendMenuItemWithLabel(IDC_SAVE_PAGE, - l10n_util::GetString(IDS_SAVE_PAGE)); - menu->AppendMenuItemWithLabel(IDC_PRINT, l10n_util::GetString(IDS_PRINT)); - menu->AppendSeparator(); - - views::Menu* zoom_menu = menu->AppendSubMenu( - IDC_ZOOM_MENU, l10n_util::GetString(IDS_ZOOM_MENU)); - zoom_menu->AppendMenuItemWithLabel(IDC_ZOOM_PLUS, - l10n_util::GetString(IDS_ZOOM_PLUS)); - zoom_menu->AppendMenuItemWithLabel(IDC_ZOOM_NORMAL, - l10n_util::GetString(IDS_ZOOM_NORMAL)); - zoom_menu->AppendMenuItemWithLabel(IDC_ZOOM_MINUS, - l10n_util::GetString(IDS_ZOOM_MINUS)); - - // Create encoding menu. - views::Menu* encoding_menu = menu->AppendSubMenu( - IDC_ENCODING_MENU, l10n_util::GetString(IDS_ENCODING_MENU)); - - EncodingMenuControllerDelegate::BuildEncodingMenu(profile_, encoding_menu); + CreatePageMenu(); + page_menu_menu_->RunMenuAt(pt, views::Menu2::ALIGN_TOPRIGHT); +} -#if defined(OS_WIN) - const struct MenuCreateMaterial { - unsigned int menu_id; - unsigned int menu_label_id; - } developer_menu_materials[] = { - { IDC_VIEW_SOURCE, IDS_VIEW_SOURCE }, - { IDC_DEBUGGER, IDS_DEBUGGER }, - { IDC_JS_CONSOLE, IDS_JS_CONSOLE }, - { IDC_TASK_MANAGER, IDS_TASK_MANAGER } - }; - // Append developer menu. - menu->AppendSeparator(); - views::Menu* developer_menu = menu->AppendSubMenu(IDC_DEVELOPER_MENU, - l10n_util::GetString(IDS_DEVELOPER_MENU)); +void ToolbarView::RunAppMenu(const gfx::Point& pt, gfx::NativeView parent) { + CreateAppMenu(); + app_menu_menu_->RunMenuAt(pt, views::Menu2::ALIGN_TOPRIGHT); +} - const CommandLine& command_line = *CommandLine::ForCurrentProcess(); - bool new_tools = !command_line.HasSwitch( - switches::kDisableOutOfProcessDevTools); +void ToolbarView::CreatePageMenu() { + if (page_menu_contents_.get()) + return; - for (int i = 0; i < arraysize(developer_menu_materials); ++i) { - if (new_tools && developer_menu_materials[i].menu_id == IDC_DEBUGGER) - continue; - if (developer_menu_materials[i].menu_id) { - developer_menu->AppendMenuItemWithLabel( - developer_menu_materials[i].menu_id, - l10n_util::GetString(developer_menu_materials[i].menu_label_id)); - } else { - developer_menu->AppendSeparator(); - } - } + page_menu_contents_.reset(new views::SimpleMenuModel(this)); + page_menu_contents_->AddItemWithStringId(IDC_CREATE_SHORTCUTS, + IDS_CREATE_SHORTCUTS); + page_menu_contents_->AddSeparator(); + page_menu_contents_->AddItemWithStringId(IDC_CUT, IDS_CUT); + page_menu_contents_->AddItemWithStringId(IDC_COPY, IDS_COPY); + page_menu_contents_->AddItemWithStringId(IDC_PASTE, IDS_PASTE); + page_menu_contents_->AddSeparator(); + page_menu_contents_->AddItemWithStringId(IDC_FIND, IDS_FIND); + page_menu_contents_->AddItemWithStringId(IDC_SAVE_PAGE, IDS_SAVE_PAGE); + page_menu_contents_->AddItemWithStringId(IDC_PRINT, IDS_PRINT); + page_menu_contents_->AddSeparator(); + + zoom_menu_contents_.reset(new ZoomMenuModel(this)); + page_menu_contents_->AddSubMenuWithStringId( + IDS_ZOOM_MENU, zoom_menu_contents_.get()); + + encoding_menu_contents_.reset(new EncodingMenuModel(browser_)); + page_menu_contents_->AddSubMenuWithStringId( + IDS_ENCODING_MENU, encoding_menu_contents_.get()); + +#if defined(OS_WIN) + CreateDevToolsMenuContents(); + page_menu_contents_->AddSeparator(); + page_menu_contents_->AddSubMenuWithStringId( + IDS_DEVELOPER_MENU, devtools_menu_contents_.get()); #endif - menu->AppendSeparator(); + page_menu_contents_->AddSeparator(); + page_menu_contents_->AddItemWithStringId(IDC_REPORT_BUG, IDS_REPORT_BUG); - menu->AppendMenuItemWithLabel(IDC_REPORT_BUG, - l10n_util::GetString(IDS_REPORT_BUG)); - menu->RunMenuAt(pt.x(), pt.y()); + page_menu_menu_.reset(new views::Menu2(page_menu_contents_.get(), this)); } -void ToolbarView::RunAppMenu(const gfx::Point& pt, gfx::NativeView parent) { - views::Menu::AnchorPoint anchor = views::Menu::TOPRIGHT; - if (UILayoutIsRightToLeft()) - anchor = views::Menu::TOPLEFT; - - scoped_ptr<views::Menu> menu(views::Menu::Create(this, anchor, parent)); - menu->AppendMenuItemWithLabel(IDC_NEW_TAB, l10n_util::GetString(IDS_NEW_TAB)); - menu->AppendMenuItemWithLabel(IDC_NEW_WINDOW, - l10n_util::GetString(IDS_NEW_WINDOW)); - menu->AppendMenuItemWithLabel(IDC_NEW_INCOGNITO_WINDOW, - l10n_util::GetString(IDS_NEW_INCOGNITO_WINDOW)); - - // Enumerate profiles asynchronously and then create the parent menu item. - // We will create the child menu items for this once the asynchronous call is - // done. See OnGetProfilesDone(). +#if defined(OS_WIN) +void ToolbarView::CreateDevToolsMenuContents() { + devtools_menu_contents_.reset(new views::SimpleMenuModel(this)); + devtools_menu_contents_->AddItem(IDC_VIEW_SOURCE, + l10n_util::GetString(IDS_VIEW_SOURCE)); const CommandLine& command_line = *CommandLine::ForCurrentProcess(); - if (command_line.HasSwitch(switches::kEnableUserDataDirProfiles)) { - profiles_helper_->GetProfiles(NULL); - profiles_menu_ = menu->AppendSubMenu( - IDC_PROFILE_MENU, l10n_util::GetString(IDS_PROFILE_MENU)); + if (command_line.HasSwitch(switches::kDisableOutOfProcessDevTools)) { + devtools_menu_contents_->AddItem(IDC_DEBUGGER, + l10n_util::GetString(IDS_DEBUGGER)); } + devtools_menu_contents_->AddItem(IDC_JS_CONSOLE, + l10n_util::GetString(IDS_JS_CONSOLE)); + devtools_menu_contents_->AddItem(IDC_TASK_MANAGER, + l10n_util::GetString(IDS_TASK_MANAGER)); +} +#endif + +void ToolbarView::CreateAppMenu() { + if (app_menu_contents_.get()) + return; - menu->AppendSeparator(); - menu->AppendMenuItemWithLabel(IDC_SHOW_BOOKMARK_BAR, - l10n_util::GetString(IDS_SHOW_BOOKMARK_BAR)); - menu->AppendMenuItemWithLabel(IDC_FULLSCREEN, - l10n_util::GetString(IDS_FULLSCREEN)); - menu->AppendSeparator(); - menu->AppendMenuItemWithLabel(IDC_SHOW_HISTORY, - l10n_util::GetString(IDS_SHOW_HISTORY)); - menu->AppendMenuItemWithLabel(IDC_SHOW_BOOKMARK_MANAGER, - l10n_util::GetString(IDS_BOOKMARK_MANAGER)); - menu->AppendMenuItemWithLabel(IDC_SHOW_DOWNLOADS, - l10n_util::GetString(IDS_SHOW_DOWNLOADS)); - menu->AppendSeparator(); + app_menu_contents_.reset(new views::SimpleMenuModel(this)); + app_menu_contents_->AddItemWithStringId(IDC_NEW_TAB, IDS_NEW_TAB); + app_menu_contents_->AddItemWithStringId(IDC_NEW_WINDOW, IDS_NEW_WINDOW); + app_menu_contents_->AddItemWithStringId(IDC_NEW_INCOGNITO_WINDOW, + IDS_NEW_INCOGNITO_WINDOW); + app_menu_contents_->AddSeparator(); + app_menu_contents_->AddCheckItemWithStringId(IDC_SHOW_BOOKMARK_BAR, + IDS_SHOW_BOOKMARK_BAR); + app_menu_contents_->AddItemWithStringId(IDC_FULLSCREEN, IDS_FULLSCREEN); + app_menu_contents_->AddSeparator(); + app_menu_contents_->AddItemWithStringId(IDC_SHOW_HISTORY, IDS_SHOW_HISTORY); + app_menu_contents_->AddItemWithStringId(IDC_SHOW_BOOKMARK_MANAGER, + IDS_BOOKMARK_MANAGER); + app_menu_contents_->AddItemWithStringId(IDC_SHOW_DOWNLOADS, + IDS_SHOW_DOWNLOADS); + app_menu_contents_->AddSeparator(); #ifdef CHROME_PERSONALIZATION if (!Personalization::IsP13NDisabled(profile_)) { - menu->AppendMenuItemWithLabel(IDC_P13N_INFO, + app_menu_contents_->AddItem( + IDC_P13N_INFO, Personalization::GetMenuItemInfoText(browser())); } #endif - menu->AppendMenuItemWithLabel(IDC_CLEAR_BROWSING_DATA, - l10n_util::GetString(IDS_CLEAR_BROWSING_DATA)); - menu->AppendMenuItemWithLabel(IDC_IMPORT_SETTINGS, - l10n_util::GetString(IDS_IMPORT_SETTINGS)); - menu->AppendSeparator(); - menu->AppendMenuItemWithLabel(IDC_OPTIONS, l10n_util::GetStringF(IDS_OPTIONS, - l10n_util::GetString(IDS_PRODUCT_NAME))); - menu->AppendMenuItemWithLabel(IDC_ABOUT, l10n_util::GetStringF(IDS_ABOUT, - l10n_util::GetString(IDS_PRODUCT_NAME))); - menu->AppendMenuItemWithLabel(IDC_HELP_PAGE, - l10n_util::GetString(IDS_HELP_PAGE)); - menu->AppendSeparator(); - menu->AppendMenuItemWithLabel(IDC_EXIT, l10n_util::GetString(IDS_EXIT)); - - menu->RunMenuAt(pt.x(), pt.y()); - - // Menu is going away, so set the profiles menu pointer to NULL. - profiles_menu_ = NULL; + app_menu_contents_->AddItemWithStringId(IDC_CLEAR_BROWSING_DATA, + IDS_CLEAR_BROWSING_DATA); + app_menu_contents_->AddItemWithStringId(IDC_IMPORT_SETTINGS, + IDS_IMPORT_SETTINGS); + app_menu_contents_->AddSeparator(); + app_menu_contents_->AddItem(IDC_OPTIONS, + l10n_util::GetStringF( + IDS_OPTIONS, + l10n_util::GetString(IDS_PRODUCT_NAME))); + app_menu_contents_->AddItem(IDC_ABOUT, + l10n_util::GetStringF( + IDS_ABOUT, + l10n_util::GetString(IDS_PRODUCT_NAME))); + app_menu_contents_->AddItemWithStringId(IDC_HELP_PAGE, IDS_HELP_PAGE); + app_menu_contents_->AddSeparator(); + app_menu_contents_->AddItemWithStringId(IDC_EXIT, IDS_EXIT); + + app_menu_menu_.reset(new views::Menu2(app_menu_contents_.get(), this)); } diff --git a/chrome/browser/views/toolbar_view.h b/chrome/browser/views/toolbar_view.h index e6fcdac..18a6365 100644 --- a/chrome/browser/views/toolbar_view.h +++ b/chrome/browser/views/toolbar_view.h @@ -10,7 +10,6 @@ #include "base/ref_counted.h" #include "base/scoped_ptr.h" #include "chrome/browser/command_updater.h" -#include "chrome/browser/encoding_menu_controller_delegate.h" #include "chrome/browser/user_data_manager.h" #include "chrome/browser/views/autocomplete/autocomplete_popup_contents_view.h" #include "chrome/browser/views/go_button.h" @@ -18,6 +17,7 @@ #include "chrome/common/pref_member.h" #include "views/controls/button/menu_button.h" #include "views/controls/menu/menu.h" +#include "views/controls/menu/simple_menu_model.h" #include "views/controls/menu/view_menu_delegate.h" #include "views/view.h" @@ -25,12 +25,50 @@ class BackForwardMenuModelViews; class Browser; class Profile; class ToolbarStarToggle; +namespace views { +class SimpleMenuModel; +} + +// A menu model that builds the contents of an encoding menu. +class EncodingMenuModel : public views::SimpleMenuModel, + public views::SimpleMenuModel::Delegate { + public: + explicit EncodingMenuModel(Browser* browser); + virtual ~EncodingMenuModel() {} + + // Overridden from views::SimpleMenuModel::Delegate: + virtual bool IsCommandIdChecked(int command_id) const; + virtual bool IsCommandIdEnabled(int command_id) const; + virtual bool GetAcceleratorForCommandId(int command_id, + views::Accelerator* accelerator); + virtual bool IsLabelForCommandIdDynamic(int command_id) const; + virtual std::wstring GetLabelForCommandId(int command_id) const; + + private: + void Build(); + + Browser* browser_; + + DISALLOW_COPY_AND_ASSIGN(EncodingMenuModel); +}; + +class ZoomMenuModel : public views::SimpleMenuModel { + public: + explicit ZoomMenuModel(views::SimpleMenuModel::Delegate* delegate); + virtual ~ZoomMenuModel() {} + + private: + void Build(); + + DISALLOW_COPY_AND_ASSIGN(ZoomMenuModel); +}; // The Browser Window's toolbar. Used within BrowserView. class ToolbarView : public views::View, - public EncodingMenuControllerDelegate, public views::ViewMenuDelegate, public views::DragController, + public views::Menu2Delegate, + public views::SimpleMenuModel::Delegate, public LocationBarView::Delegate, public NotificationObserver, public GetProfilesHelper::Delegate, @@ -70,9 +108,6 @@ class ToolbarView : public views::View, GoButton* go_button() const { return go_; } LocationBarView* location_bar() const { return location_bar_; } - // Overridden from EncodingMenuControllerDelegate: - virtual bool IsItemChecked(int id) const; - // Overridden from Menu::BaseControllerDelegate: virtual bool GetAcceleratorInfo(int id, views::Accelerator* accel); @@ -101,6 +136,17 @@ class ToolbarView : public views::View, const NotificationSource& source, const NotificationDetails& details); + // Overridden from views::Menu2Delegate: + virtual void ExecuteCommand(views::Menu2Model* model, int command_id); + + // Overridden from views::SimpleMenuModel::Delegate: + virtual bool IsCommandIdChecked(int command_id) const; + virtual bool IsCommandIdEnabled(int command_id) const; + virtual bool GetAcceleratorForCommandId(int command_id, + views::Accelerator* accelerator); + virtual bool IsLabelForCommandIdDynamic(int command_id) const; + virtual std::wstring GetLabelForCommandId(int command_id) const; + // Overridden from views::View: virtual gfx::Size GetPreferredSize(); virtual void Layout(); @@ -117,17 +163,16 @@ class ToolbarView : public views::View, virtual View* GetAccFocusedChildView() { return acc_focused_view_; } private: - // Returns the number of pixels above the location bar in non-normal display. - int PopupTopSpacing() const; - - // DragController methods for the star button. These allow the drag if the - // user hasn't edited the text, the url is valid and should be displayed. + // Overridden from views::DragController: virtual void WriteDragData(View* sender, int press_x, int press_y, OSExchangeData* data); virtual int GetDragOperations(View* sender, int x, int y); + // Returns the number of pixels above the location bar in non-normal display. + int PopupTopSpacing() const; + // Set up the various Views in the toolbar void CreateLeftSideControls(); void CreateCenterStack(Profile* profile); @@ -140,6 +185,14 @@ class ToolbarView : public views::View, void RunPageMenu(const gfx::Point& pt, gfx::NativeView hwnd); void RunAppMenu(const gfx::Point& pt, gfx::NativeView hwnd); + void CreatePageMenu(); + void CreateZoomMenuContents(); + void CreateEncodingMenuContents(); +#if defined(OS_WIN) + void CreateDevToolsMenuContents(); +#endif + void CreateAppMenu(); + // Types of display mode this toolbar can have. enum DisplayMode { DISPLAYMODE_NORMAL, // Normal toolbar with buttons, etc. @@ -191,6 +244,17 @@ class ToolbarView : public views::View, // The display mode used when laying out the toolbar. DisplayMode display_mode_; + + // The contents of the various menus. + scoped_ptr<views::SimpleMenuModel> page_menu_contents_; + scoped_ptr<ZoomMenuModel> zoom_menu_contents_; + scoped_ptr<EncodingMenuModel> encoding_menu_contents_; + scoped_ptr<views::SimpleMenuModel> devtools_menu_contents_; + scoped_ptr<views::SimpleMenuModel> app_menu_contents_; + + // TODO(beng): build these into MenuButton. + scoped_ptr<views::Menu2> page_menu_menu_; + scoped_ptr<views::Menu2> app_menu_menu_; }; #endif // CHROME_BROWSER_VIEWS_TOOLBAR_VIEW_H_ |