[email protected] | dbb03fb | 2014-02-15 05:36:33 | [diff] [blame] | 1 | // Copyright 2014 The Chromium Authors. All rights reserved. |
[email protected] | cb610dc | 2012-08-31 17:16:56 | [diff] [blame] | 2 | // Use of this source code is governed by a BSD-style license that can be |
| 3 | // found in the LICENSE file. |
| 4 | |
[email protected] | dbb03fb | 2014-02-15 05:36:33 | [diff] [blame] | 5 | #ifndef APPS_APP_WINDOW_GEOMETRY_CACHE_H_ |
| 6 | #define APPS_APP_WINDOW_GEOMETRY_CACHE_H_ |
[email protected] | cb610dc | 2012-08-31 17:16:56 | [diff] [blame] | 7 | |
| 8 | #include <map> |
| 9 | #include <set> |
| 10 | #include <string> |
| 11 | |
| 12 | #include "base/memory/scoped_ptr.h" |
[email protected] | 71e0c30 | 2013-05-17 09:26:15 | [diff] [blame] | 13 | #include "base/memory/singleton.h" |
[email protected] | 6349da0 | 2013-11-29 17:08:18 | [diff] [blame] | 14 | #include "base/observer_list.h" |
[email protected] | 829f046 | 2014-05-10 04:40:00 | [diff] [blame] | 15 | #include "base/scoped_observer.h" |
[email protected] | 1e84c63 | 2013-06-27 23:12:21 | [diff] [blame] | 16 | #include "base/time/time.h" |
| 17 | #include "base/timer/timer.h" |
[email protected] | cb610dc | 2012-08-31 17:16:56 | [diff] [blame] | 18 | #include "base/values.h" |
[email protected] | 12b7af3 | 2014-03-13 05:28:20 | [diff] [blame] | 19 | #include "components/keyed_service/content/browser_context_keyed_service_factory.h" |
| 20 | #include "components/keyed_service/core/keyed_service.h" |
[email protected] | 829f046 | 2014-05-10 04:40:00 | [diff] [blame] | 21 | #include "extensions/browser/extension_registry_observer.h" |
[email protected] | 68eeede | 2013-05-09 06:10:57 | [diff] [blame] | 22 | #include "ui/base/ui_base_types.h" |
[email protected] | cb610dc | 2012-08-31 17:16:56 | [diff] [blame] | 23 | #include "ui/gfx/rect.h" |
| 24 | |
| 25 | class Profile; |
| 26 | |
| 27 | namespace extensions { |
[email protected] | af3920f | 2012-12-13 00:49:24 | [diff] [blame] | 28 | class ExtensionPrefs; |
[email protected] | 829f046 | 2014-05-10 04:40:00 | [diff] [blame] | 29 | class ExtensionRegistry; |
[email protected] | 71e0c30 | 2013-05-17 09:26:15 | [diff] [blame] | 30 | } |
| 31 | |
| 32 | namespace apps { |
[email protected] | cb610dc | 2012-08-31 17:16:56 | [diff] [blame] | 33 | |
[email protected] | dbb03fb | 2014-02-15 05:36:33 | [diff] [blame] | 34 | // A cache for persisted geometry of app windows, both to not have to wait |
[email protected] | cb610dc | 2012-08-31 17:16:56 | [diff] [blame] | 35 | // for IO when creating a new window, and to not cause IO on every window |
| 36 | // geometry change. |
[email protected] | 12b7af3 | 2014-03-13 05:28:20 | [diff] [blame] | 37 | class AppWindowGeometryCache : public KeyedService, |
[email protected] | 829f046 | 2014-05-10 04:40:00 | [diff] [blame] | 38 | public extensions::ExtensionRegistryObserver { |
[email protected] | cb610dc | 2012-08-31 17:16:56 | [diff] [blame] | 39 | public: |
[email protected] | f1484c5 | 2013-05-22 23:25:44 | [diff] [blame] | 40 | class Factory : public BrowserContextKeyedServiceFactory { |
[email protected] | 71e0c30 | 2013-05-17 09:26:15 | [diff] [blame] | 41 | public: |
[email protected] | dbb03fb | 2014-02-15 05:36:33 | [diff] [blame] | 42 | static AppWindowGeometryCache* GetForContext( |
[email protected] | 71e0c30 | 2013-05-17 09:26:15 | [diff] [blame] | 43 | content::BrowserContext* context, |
| 44 | bool create); |
| 45 | |
| 46 | static Factory* GetInstance(); |
[email protected] | dbb03fb | 2014-02-15 05:36:33 | [diff] [blame] | 47 | |
[email protected] | 71e0c30 | 2013-05-17 09:26:15 | [diff] [blame] | 48 | private: |
| 49 | friend struct DefaultSingletonTraits<Factory>; |
| 50 | |
| 51 | Factory(); |
| 52 | virtual ~Factory(); |
| 53 | |
[email protected] | f1484c5 | 2013-05-22 23:25:44 | [diff] [blame] | 54 | // BrowserContextKeyedServiceFactory |
[email protected] | 12b7af3 | 2014-03-13 05:28:20 | [diff] [blame] | 55 | virtual KeyedService* BuildServiceInstanceFor( |
[email protected] | 71e0c30 | 2013-05-17 09:26:15 | [diff] [blame] | 56 | content::BrowserContext* context) const OVERRIDE; |
| 57 | virtual bool ServiceIsNULLWhileTesting() const OVERRIDE; |
| 58 | virtual content::BrowserContext* GetBrowserContextToUse( |
| 59 | content::BrowserContext* context) const OVERRIDE; |
| 60 | }; |
| 61 | |
[email protected] | 6349da0 | 2013-11-29 17:08:18 | [diff] [blame] | 62 | class Observer { |
| 63 | public: |
| 64 | virtual void OnGeometryCacheChanged(const std::string& extension_id, |
| 65 | const std::string& window_id, |
| 66 | const gfx::Rect& bounds) = 0; |
| 67 | |
| 68 | protected: |
[email protected] | 2919a5e | 2014-04-24 08:34:05 | [diff] [blame] | 69 | virtual ~Observer() {} |
[email protected] | 6349da0 | 2013-11-29 17:08:18 | [diff] [blame] | 70 | }; |
| 71 | |
[email protected] | dbb03fb | 2014-02-15 05:36:33 | [diff] [blame] | 72 | AppWindowGeometryCache(Profile* profile, extensions::ExtensionPrefs* prefs); |
[email protected] | cb610dc | 2012-08-31 17:16:56 | [diff] [blame] | 73 | |
[email protected] | dbb03fb | 2014-02-15 05:36:33 | [diff] [blame] | 74 | virtual ~AppWindowGeometryCache(); |
[email protected] | cb610dc | 2012-08-31 17:16:56 | [diff] [blame] | 75 | |
[email protected] | 71e0c30 | 2013-05-17 09:26:15 | [diff] [blame] | 76 | // Returns the instance for the given browsing context. |
[email protected] | dbb03fb | 2014-02-15 05:36:33 | [diff] [blame] | 77 | static AppWindowGeometryCache* Get(content::BrowserContext* context); |
[email protected] | 71e0c30 | 2013-05-17 09:26:15 | [diff] [blame] | 78 | |
[email protected] | 68eeede | 2013-05-09 06:10:57 | [diff] [blame] | 79 | // Save the geometry and state associated with |extension_id| and |window_id|. |
[email protected] | cb610dc | 2012-08-31 17:16:56 | [diff] [blame] | 80 | void SaveGeometry(const std::string& extension_id, |
[email protected] | 2b0fc08a | 2012-11-07 23:54:26 | [diff] [blame] | 81 | const std::string& window_id, |
[email protected] | 68eeede | 2013-05-09 06:10:57 | [diff] [blame] | 82 | const gfx::Rect& bounds, |
[email protected] | 36e44c6 | 2013-06-23 14:20:58 | [diff] [blame] | 83 | const gfx::Rect& screen_bounds, |
[email protected] | 68eeede | 2013-05-09 06:10:57 | [diff] [blame] | 84 | ui::WindowShowState state); |
[email protected] | cb610dc | 2012-08-31 17:16:56 | [diff] [blame] | 85 | |
[email protected] | 68eeede | 2013-05-09 06:10:57 | [diff] [blame] | 86 | // Get any saved geometry and state associated with |extension_id| and |
[email protected] | 837af56 | 2013-08-01 20:12:42 | [diff] [blame] | 87 | // |window_id|. If saved data exists, sets |bounds|, |screen_bounds| and |
| 88 | // |state| if not NULL and returns true. |
[email protected] | cb610dc | 2012-08-31 17:16:56 | [diff] [blame] | 89 | bool GetGeometry(const std::string& extension_id, |
[email protected] | 2b0fc08a | 2012-11-07 23:54:26 | [diff] [blame] | 90 | const std::string& window_id, |
[email protected] | 68eeede | 2013-05-09 06:10:57 | [diff] [blame] | 91 | gfx::Rect* bounds, |
[email protected] | 36e44c6 | 2013-06-23 14:20:58 | [diff] [blame] | 92 | gfx::Rect* screen_bounds, |
[email protected] | e9f195e | 2013-06-13 06:37:42 | [diff] [blame] | 93 | ui::WindowShowState* state); |
[email protected] | 2b0fc08a | 2012-11-07 23:54:26 | [diff] [blame] | 94 | |
[email protected] | 12b7af3 | 2014-03-13 05:28:20 | [diff] [blame] | 95 | // KeyedService |
[email protected] | 71e0c30 | 2013-05-17 09:26:15 | [diff] [blame] | 96 | virtual void Shutdown() OVERRIDE; |
| 97 | |
[email protected] | 6349da0 | 2013-11-29 17:08:18 | [diff] [blame] | 98 | void AddObserver(Observer* observer); |
| 99 | void RemoveObserver(Observer* observer); |
| 100 | |
[email protected] | af3920f | 2012-12-13 00:49:24 | [diff] [blame] | 101 | // Maximum number of windows we'll cache the geometry for per app. |
| 102 | static const size_t kMaxCachedWindows = 100; |
| 103 | |
[email protected] | 2b0fc08a | 2012-11-07 23:54:26 | [diff] [blame] | 104 | protected: |
[email protected] | dbb03fb | 2014-02-15 05:36:33 | [diff] [blame] | 105 | friend class AppWindowGeometryCacheTest; |
[email protected] | 2b0fc08a | 2012-11-07 23:54:26 | [diff] [blame] | 106 | |
| 107 | // For tests, this modifies the timeout delay for saving changes from calls |
| 108 | // to SaveGeometry. (Note that even if this is set to 0, you still need to |
| 109 | // run the message loop to see the results of any SyncToStorage call). |
| 110 | void SetSyncDelayForTests(int timeout_ms); |
[email protected] | cb610dc | 2012-08-31 17:16:56 | [diff] [blame] | 111 | |
| 112 | private: |
[email protected] | af3920f | 2012-12-13 00:49:24 | [diff] [blame] | 113 | // Data stored for each window. |
| 114 | struct WindowData { |
[email protected] | 36e44c6 | 2013-06-23 14:20:58 | [diff] [blame] | 115 | WindowData(); |
| 116 | ~WindowData(); |
[email protected] | af3920f | 2012-12-13 00:49:24 | [diff] [blame] | 117 | gfx::Rect bounds; |
[email protected] | 36e44c6 | 2013-06-23 14:20:58 | [diff] [blame] | 118 | gfx::Rect screen_bounds; |
[email protected] | 68eeede | 2013-05-09 06:10:57 | [diff] [blame] | 119 | ui::WindowShowState window_state; |
[email protected] | af3920f | 2012-12-13 00:49:24 | [diff] [blame] | 120 | base::Time last_change; |
| 121 | }; |
| 122 | |
| 123 | // Data stored for each extension. |
| 124 | typedef std::map<std::string, WindowData> ExtensionData; |
| 125 | |
[email protected] | 829f046 | 2014-05-10 04:40:00 | [diff] [blame] | 126 | // ExtensionRegistryObserver implementation. |
| 127 | virtual void OnExtensionLoaded( |
| 128 | content::BrowserContext* browser_context, |
| 129 | const extensions::Extension* extension) OVERRIDE; |
| 130 | virtual void OnExtensionUnloaded( |
| 131 | content::BrowserContext* browser_context, |
| 132 | const extensions::Extension* extension, |
| 133 | extensions::UnloadedExtensionInfo::Reason reason) OVERRIDE; |
[email protected] | cb610dc | 2012-08-31 17:16:56 | [diff] [blame] | 134 | |
[email protected] | e9f195e | 2013-06-13 06:37:42 | [diff] [blame] | 135 | void LoadGeometryFromStorage(const std::string& extension_id); |
[email protected] | cb610dc | 2012-08-31 17:16:56 | [diff] [blame] | 136 | void SyncToStorage(); |
| 137 | |
[email protected] | af3920f | 2012-12-13 00:49:24 | [diff] [blame] | 138 | // Preferences storage. |
[email protected] | 71e0c30 | 2013-05-17 09:26:15 | [diff] [blame] | 139 | extensions::ExtensionPrefs* prefs_; |
[email protected] | cb610dc | 2012-08-31 17:16:56 | [diff] [blame] | 140 | |
[email protected] | 829f046 | 2014-05-10 04:40:00 | [diff] [blame] | 141 | // Cached data. |
[email protected] | af3920f | 2012-12-13 00:49:24 | [diff] [blame] | 142 | std::map<std::string, ExtensionData> cache_; |
[email protected] | cb610dc | 2012-08-31 17:16:56 | [diff] [blame] | 143 | |
[email protected] | 829f046 | 2014-05-10 04:40:00 | [diff] [blame] | 144 | // Data that still needs saving. |
[email protected] | cb610dc | 2012-08-31 17:16:56 | [diff] [blame] | 145 | std::set<std::string> unsynced_extensions_; |
| 146 | |
[email protected] | 829f046 | 2014-05-10 04:40:00 | [diff] [blame] | 147 | // The timer used to save the data. |
[email protected] | dbb03fb | 2014-02-15 05:36:33 | [diff] [blame] | 148 | base::OneShotTimer<AppWindowGeometryCache> sync_timer_; |
[email protected] | cb610dc | 2012-08-31 17:16:56 | [diff] [blame] | 149 | |
[email protected] | 2b0fc08a | 2012-11-07 23:54:26 | [diff] [blame] | 150 | // The timeout value we'll use for |sync_timer_|. |
| 151 | base::TimeDelta sync_delay_; |
| 152 | |
[email protected] | 829f046 | 2014-05-10 04:40:00 | [diff] [blame] | 153 | // Listen to extension load, unloaded notifications. |
| 154 | ScopedObserver<extensions::ExtensionRegistry, |
| 155 | extensions::ExtensionRegistryObserver> |
| 156 | extension_registry_observer_; |
| 157 | |
[email protected] | 6349da0 | 2013-11-29 17:08:18 | [diff] [blame] | 158 | ObserverList<Observer> observers_; |
[email protected] | cb610dc | 2012-08-31 17:16:56 | [diff] [blame] | 159 | }; |
| 160 | |
[email protected] | 71e0c30 | 2013-05-17 09:26:15 | [diff] [blame] | 161 | } // namespace apps |
[email protected] | cb610dc | 2012-08-31 17:16:56 | [diff] [blame] | 162 | |
[email protected] | dbb03fb | 2014-02-15 05:36:33 | [diff] [blame] | 163 | #endif // APPS_APP_WINDOW_GEOMETRY_CACHE_H_ |