Home | History | Annotate | Download | only in gtk
      1 // Copyright (c) 2011 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 #ifndef CHROME_BROWSER_UI_GTK_GLOBAL_HISTORY_MENU_H_
      6 #define CHROME_BROWSER_UI_GTK_GLOBAL_HISTORY_MENU_H_
      7 
      8 #include <map>
      9 
     10 #include "base/compiler_specific.h"
     11 #include "chrome/browser/common/cancelable_request.h"
     12 #include "chrome/browser/history/history_types.h"
     13 #include "chrome/browser/sessions/tab_restore_service.h"
     14 #include "chrome/browser/sessions/tab_restore_service_observer.h"
     15 #include "chrome/browser/ui/gtk/global_menu_owner.h"
     16 #include "content/public/browser/notification_observer.h"
     17 #include "content/public/browser/notification_registrar.h"
     18 #include "ui/base/gtk/gtk_signal.h"
     19 
     20 class Browser;
     21 class Profile;
     22 
     23 namespace history {
     24 class TopSites;
     25 }
     26 
     27 typedef struct _GdkPixbuf GdkPixbuf;
     28 
     29 // Controls the History menu.
     30 class GlobalHistoryMenu : public GlobalMenuOwner,
     31                           public content::NotificationObserver,
     32                           public TabRestoreServiceObserver {
     33  public:
     34   explicit GlobalHistoryMenu(Browser* browser);
     35   virtual ~GlobalHistoryMenu();
     36 
     37   // Takes the history menu we need to modify based on the tab restore/most
     38   // visited state.
     39   virtual void Init(GtkWidget* history_menu,
     40                     GtkWidget* history_menu_item) OVERRIDE;
     41 
     42  private:
     43   class HistoryItem;
     44   struct ClearMenuClosure;
     45   struct GetIndexClosure;
     46 
     47   typedef std::map<GtkWidget*, HistoryItem*> MenuItemToHistoryMap;
     48 
     49   // Sends a message off to History for data.
     50   void GetTopSitesData();
     51 
     52   // Callback to receive data requested from GetTopSitesData().
     53   void OnTopSitesReceived(const history::MostVisitedURLList& visited_list);
     54 
     55   // Returns the currently existing HistoryItem associated with
     56   // |menu_item|. Can return NULL.
     57   HistoryItem* HistoryItemForMenuItem(GtkWidget* menu_item);
     58 
     59   // Returns whether there's a valid HistoryItem representation of |entry|.
     60   bool HasValidHistoryItemForTab(const TabRestoreService::Tab& entry);
     61 
     62   // Creates a HistoryItem from the data in |entry|.
     63   HistoryItem* HistoryItemForTab(const TabRestoreService::Tab& entry);
     64 
     65   // Creates a menu item form |item| and inserts it in |menu| at |index|.
     66   GtkWidget* AddHistoryItemToMenu(HistoryItem* item,
     67                                   GtkWidget* menu,
     68                                   int tag,
     69                                   int index);
     70 
     71   // Find the first index of the item in |menu| with the tag |tag_id|.
     72   int GetIndexOfMenuItemWithTag(GtkWidget* menu, int tag_id);
     73 
     74   // This will remove all menu items in |menu| with |tag| as their tag. This
     75   // clears state about HistoryItems* that we keep to prevent that data from
     76   // going stale. That's why this method recurses into its child menus.
     77   void ClearMenuSection(GtkWidget* menu, int tag);
     78 
     79   // Implementation detail of GetIndexOfMenuItemWithTag.
     80   static void GetIndexCallback(GtkWidget* widget, GetIndexClosure* closure);
     81 
     82   // Implementation detail of ClearMenuSection.
     83   static void ClearMenuCallback(GtkWidget* widget, ClearMenuClosure* closure);
     84 
     85   // content::NotificationObserver:
     86   virtual void Observe(int type,
     87                        const content::NotificationSource& source,
     88                        const content::NotificationDetails& details) OVERRIDE;
     89 
     90   // For TabRestoreServiceObserver
     91   virtual void TabRestoreServiceChanged(TabRestoreService* service) OVERRIDE;
     92   virtual void TabRestoreServiceDestroyed(TabRestoreService* service) OVERRIDE;
     93 
     94   CHROMEGTK_CALLBACK_0(GlobalHistoryMenu, void, OnRecentlyClosedItemActivated);
     95 
     96   // Listen for the first menu show command so we can then connect to the
     97   // TabRestoreService. With how the global menus work, I'd prefer to register
     98   // with the TabRestoreService as soon as we're constructed, but this breaks
     99   // unit tests which test the service (because they force different
    100   // construction ordering while us connecting to the TabRestoreService loads
    101   // data now!)
    102   CHROMEGTK_CALLBACK_0(GlobalHistoryMenu, void, OnMenuActivate);
    103 
    104   Browser* browser_;
    105   Profile* profile_;
    106 
    107   // The history menu. We keep this since we need to rewrite parts of it
    108   // periodically.
    109   GtkWidget* history_menu_;
    110 
    111   history::TopSites* top_sites_;
    112 
    113   // For callbacks may be run after destruction.
    114   base::WeakPtrFactory<GlobalHistoryMenu> weak_ptr_factory_;
    115 
    116   TabRestoreService* tab_restore_service_;  // weak
    117 
    118   // A mapping from GtkMenuItems to HistoryItems that maintain data.
    119   MenuItemToHistoryMap menu_item_history_map_;
    120 
    121   content::NotificationRegistrar registrar_;
    122 };
    123 
    124 #endif  // CHROME_BROWSER_UI_GTK_GLOBAL_HISTORY_MENU_H_
    125