1 // Copyright (c) 2006-2008 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.
5 #ifndef CHROME_BROWSER_TAB_CONTENTS_H_
6 #define CHROME_BROWSER_TAB_CONTENTS_H_
11 #include "chrome/browser/autocomplete/autocomplete_edit.h"
12 #include "chrome/browser/constrained_window.h"
13 #include "chrome/browser/navigation_controller.h"
14 #include "chrome/browser/page_navigator.h"
15 #include "chrome/browser/tab_contents_type.h"
16 #include "chrome/common/navigation_types.h"
25 class DownloadShelfView
;
27 class LoadNotificationDetails
;
29 class TabContentsDelegate
;
30 class TabContentsFactory
;
35 // Describes what goes in the main content area of a tab. For example,
36 // the WebContents is one such thing.
38 // When instantiating a new TabContents explicitly, the TabContents will not
39 // have an associated NavigationController. To setup a NavigationController
40 // for the TabContents, its SetupController method should be called.
42 // Once they reside within a NavigationController, TabContents objects are
43 // owned by that NavigationController. When the active TabContents within that
44 // NavigationController is closed, that TabContents destroys the
45 // NavigationController, which then destroys all of the TabContentses in it.
47 // NOTE: When the NavigationController is navigated to an URL corresponding to
48 // a different type of TabContents (see the TabContents::TypeForURL method),
49 // the NavigationController makes the active TabContents inactive, notifies the
50 // TabContentsDelegate that the TabContents is being replaced, and then
51 // activates the new TabContents.
52 class TabContents
: public PageNavigator
,
53 public ConstrainedTabContentsDelegate
{
55 // Flags passed to the TabContentsDelegate.NavigationStateChanged to tell it
56 // what has changed. Combine them to update more than one thing.
57 enum InvalidateTypes
{
58 INVALIDATE_URL
= 1, // The URL has changed.
59 INVALIDATE_TITLE
= 2, // The title has changed.
60 INVALIDATE_FAVICON
= 4, // The favicon has changed.
61 INVALIDATE_LOAD
= 8, // The loading state has changed
63 // Helper for forcing a refresh.
64 INVALIDATE_EVERYTHING
= 0xFFFFFFFF
67 static void RegisterUserPrefs(PrefService
* prefs
);
69 // Factory -------------------------------------------------------------------
70 // (implemented in tab_contents_factory.cc)
72 // Creates a new TabContents of the given type. Will reuse the given
73 // instance's renderer, if it is not null.
74 static TabContents
* CreateWithType(TabContentsType type
,
77 SiteInstance
* instance
);
79 // Returns the type of TabContents needed to handle the URL. |url| may
80 // end up being modified to contain the _real_ url being loaded if the
81 // parameter was an alias (such as about: urls and chrome- urls).
82 static TabContentsType
TypeForURL(GURL
* url
);
84 // This method can be used to register a new TabContents type dynamically,
85 // which can be very useful for unit testing. If factory is null, then the
86 // tab contents type is unregistered. Returns the previously registered
87 // factory for the given type or null if there was none.
88 static TabContentsFactory
* RegisterFactory(TabContentsType type
,
89 TabContentsFactory
* factory
);
91 // Creation & destruction ----------------------------------------------------
93 // Request this tab to shut down. This kills the tab's NavigationController,
94 // which then Destroy()s all tabs it controls.
97 // Unregister/shut down any pending tasks involving this tab.
98 // This is called as the tab is shutting down, before the
99 // NavigationController (and consequently profile) are gone.
101 // If you override this, be sure to call this implementation at the end
104 virtual void Destroy();
106 // Intrinsic tab state -------------------------------------------------------
108 // Returns the type of tab this is. See also the As* functions following.
109 TabContentsType
type() const { return type_
; }
111 // Returns this object as a WebContents if it is one, and NULL otherwise.
112 virtual WebContents
* AsWebContents() { return NULL
; }
114 // Const version of above for situations where const TabContents*'s are used.
115 WebContents
* AsWebContents() const {
116 return const_cast<TabContents
*>(this)->AsWebContents();
119 // Returns this object as a DOMUIHost if it is one, and NULL otherwise.
120 virtual DOMUIHost
* AsDOMUIHost() { return NULL
; }
122 TabContentsDelegate
* delegate() const { return delegate_
; }
123 void set_delegate(TabContentsDelegate
* d
) { delegate_
= d
; }
125 // This can only be null if the TabContents has been created but
126 // SetupController has not been called. The controller should always outlive
128 NavigationController
* controller() const { return controller_
; }
129 void set_controller(NavigationController
* c
) { controller_
= c
; }
131 // Sets up a new NavigationController for this TabContents.
132 // |profile| is the user profile that should be associated with
133 // the new controller.
135 // TODO(brettw) this seems bogus and I couldn't find any legitimate need for
136 // it. I think it should be passed in the constructor.
137 void SetupController(Profile
* profile
);
139 // Returns the user profile associated with this TabContents (via the
140 // NavigationController). This will return NULL if there isn't yet a
141 // NavigationController on this TabContents.
142 // TODO(darin): make it so that controller_ can never be null
143 Profile
* profile() const {
144 return controller_
? controller_
->profile() : NULL
;
147 // Returns whether this tab contents supports the provided URL. By default,
148 // this method matches the tab contents type with the result of TypeForURL().
149 // |url| points to the actual URL that will be used. It can be modified as
151 // Override this method if your TabContents subclass supports various URL
152 // schemes but doesn't want to be the default handler for these schemes.
153 // For example, the NewTabUIContents overrides this method to support
155 virtual bool SupportsURL(GURL
* url
);
157 // Tab navigation state ------------------------------------------------------
159 // Returns the current navigation properties, which if a navigation is
160 // pending may be provisional (e.g., the navigation could result in a
161 // download, in which case the URL would revert to what it was previously).
162 const GURL
& GetURL() const;
163 virtual const std::wstring
& GetTitle() const;
165 // The max PageID of any page that this TabContents has loaded. PageIDs
166 // increase with each new page that is loaded by a tab. If this is a
167 // WebContents, then the max PageID is kept separately on each SiteInstance.
168 // Returns -1 if no PageIDs have yet been seen.
169 int32
GetMaxPageID();
171 // Updates the max PageID to be at least the given PageID.
172 void UpdateMaxPageID(int32 page_id
);
174 // Returns the site instance associated with the current page. By default,
175 // there is no site instance. WebContents overrides this to provide proper
176 // access to its site instance.
177 virtual SiteInstance
* GetSiteInstance() const { return NULL
; }
179 // Initial title assigned to NavigationEntries from Navigate.
180 virtual const std::wstring
GetDefaultTitle() const;
182 // Defines whether this tab's URL should be displayed in the browser's URL
183 // bar. Normally this is true so you can see the URL. This is set to false
184 // for the new tab page and related pages so that the URL bar is empty and
185 // the user is invited to type into it.
186 virtual bool ShouldDisplayURL() { return true; }
188 // Returns the favicon for this tab, or an isNull() bitmap if the tab does not
189 // have a favicon. The default implementation uses the current navigation
191 virtual SkBitmap
GetFavIcon() const;
193 // Returns whether the favicon should be displayed. If this returns false, no
194 // space is provided for the favicon, and the favicon is never displayed.
195 virtual bool ShouldDisplayFavIcon() { return true; }
197 // SSL related states.
198 SecurityStyle
GetSecurityStyle() const;
200 // Sets |ev_text| to the text that should be displayed in the EV label of
201 // the location bar and |ev_tooltip_text| to the tooltip for that label.
202 // Returns false and sets these strings to empty if the current page is either
203 // not served over HTTPS or if HTTPS does not use an EV cert.
204 bool GetSSLEVText(std::wstring
* ev_text
, std::wstring
* ev_tooltip_text
) const;
206 // Returns a human-readable description the tab's loading state.
207 virtual std::wstring
GetStatusText() const { return std::wstring(); }
209 const std::wstring
& encoding() { return encoding_name_
; }
210 void set_encoding(const std::wstring
& encoding_name
) {
211 encoding_name_
= encoding_name
;
214 // Return whether this tab contents is loading a resource.
215 bool is_loading() const { return is_loading_
; }
217 // Returns whether this tab contents is waiting for a first-response for the
218 // main resource of the page. This controls whether the throbber state is
219 // "waiting" or "loading."
220 bool waiting_for_response() const { return waiting_for_response_
; }
222 // Internal state ------------------------------------------------------------
224 // For use when switching tabs, these functions allow the tab contents to
225 // hold the per-tab state of the location bar. The tab contents takes
226 // ownership of the pointer.
227 void set_saved_location_bar_state(const AutocompleteEditState
* state
) {
228 saved_location_bar_state_
.reset(state
);
230 const AutocompleteEditState
* saved_location_bar_state() const {
231 return saved_location_bar_state_
.get();
234 // This flag indicates whether the tab contents is currently being
235 // screenshotted by the DraggedTabController.
236 bool capturing_contents() const { return capturing_contents_
; }
237 void set_capturing_contents(bool cap
) { capturing_contents_
= cap
; }
239 // Indicates whether this tab should be considered crashed. The setter will
240 // also notify the delegate when the flag is changed.
241 bool is_crashed() const { return is_crashed_
; }
242 void SetIsCrashed(bool state
);
244 // Set whether this tab contents is active. A tab content is active for a
245 // given tab if it is currently being used to display some contents. Note that
246 // this is different from whether a tab is selected.
247 bool is_active() const { return is_active_
; }
248 void set_is_active(bool active
) { is_active_
= active
; }
250 // Convenience method for notifying the delegate of a navigation state
251 // change. See TabContentsDelegate.
252 void NotifyNavigationStateChanged(unsigned changed_flags
);
254 // Invoked when the tab contents becomes selected. If you override, be sure
255 // and invoke super's implementation.
256 virtual void DidBecomeSelected();
258 // Invoked when the tab contents becomes hidden.
259 // NOTE: If you override this, call the superclass version too!
260 virtual void WasHidden();
262 // Activates this contents within its containing window, bringing that window
263 // to the foreground if necessary.
264 virtual void Activate();
266 // Commands ------------------------------------------------------------------
268 // Implementation of PageNavigator.
269 virtual void OpenURL(const GURL
& url
,
270 WindowOpenDisposition disposition
,
271 PageTransition::Type transition
);
273 // Called by the NavigationController to cause the TabContents to navigate to
274 // the current pending entry. The NavigationController should be called back
275 // with CommitPendingEntry/RendererDidNavigate on success or
276 // DiscardPendingEntry. The callbacks can be inside of this function, or at
279 // The entry has a PageID of -1 if newly created (corresponding to navigation
282 // If this method returns false, then the navigation is discarded (equivalent
283 // to calling DiscardPendingEntry on the NavigationController).
284 virtual bool NavigateToPendingEntry(bool reload
);
286 // Stop any pending navigation.
287 virtual void Stop() {}
289 // An asynchronous call to trigger the string search in the page.
290 // It sends an IPC message to the Renderer that handles the string
291 // search, selecting the matches and setting the caret positions.
292 // This function also starts the asynchronous scoping effort.
293 virtual void StartFinding(int request_id
,
294 const std::wstring
& string
,
295 bool forward
, bool match_case
,
298 // An asynchronous call to stop the string search in the page. If
299 // |clear_selection| is true, it will also clear the selection on the
301 virtual void StopFinding(bool clear_selection
) { }
303 // TODO(erg): HACK ALERT! This was thrown together for beta and
304 // needs to be completely removed after we ship it. Right now, the
305 // cut/copy/paste menu items are always enabled and will send a
306 // cut/copy/paste command to the currently visible
307 // TabContents. Post-beta, this needs to be replaced with a unified
308 // interface for supporting cut/copy/paste, and managing who has
309 // cut/copy/paste focus. (http://b/1117225)
310 virtual void Cut() { }
311 virtual void Copy() { }
312 virtual void Paste() { }
314 // Window management ---------------------------------------------------------
316 // Create a new window constrained to this TabContents' clip and visibility.
317 // The window is initialized by using the supplied delegate to obtain basic
318 // window characteristics, and the supplied view for the content. The window
319 // is sized according to the preferred size of the content_view, and centered
320 // within the contents.
321 ConstrainedWindow
* CreateConstrainedDialog(
322 ChromeViews::WindowDelegate
* window_delegate
,
323 ChromeViews::View
* contents_view
);
325 // Adds a new tab or window with the given already-created contents
326 void AddNewContents(TabContents
* new_contents
,
327 WindowOpenDisposition disposition
,
328 const gfx::Rect
& initial_pos
,
331 // Builds a ConstrainedWindow* for the incoming |new_contents| and
332 // adds it to child_windows_.
333 void AddConstrainedPopup(TabContents
* new_contents
,
334 const gfx::Rect
& initial_pos
);
336 // When a tab is closed, this method is called for all the remaining tabs. If
337 // they all return false or if no tabs are left, the window is closed. The
338 // default is to return true
339 virtual bool ShouldPreventWindowClose() { return true; }
341 // Closes all constrained windows that represent web popups that have not yet
342 // been activated by the user and are as such auto-positioned in the bottom
343 // right of the screen. This is a quick way for users to "clean up" a flurry
344 // of unwanted popups.
345 void CloseAllSuppressedPopups();
347 // Show, Hide and Size the TabContents.
348 // TODO(beng): (Cleanup) Show/Size TabContents should be made to actually
349 // show and size the View. For simplicity sake, for now they're
350 // just empty. This is currently a bit of a mess and is just a
352 virtual void ShowContents() {}
353 virtual void HideContents();
354 virtual void SizeContents(const gfx::Size
& size
) {}
356 // Views and focus -----------------------------------------------------------
358 // Returns the actual window that is focused when this TabContents is shown.
359 virtual HWND
GetContentHWND() {
360 return GetContainerHWND();
363 // Tell the subclass to set up the view (e.g. create the container HWND if
364 // applicable) and any other create-time setup.
365 virtual void CreateView(HWND parent_hwnd
, const gfx::Rect
& initial_bounds
) {}
367 // Returns the HWND associated with this TabContents. Outside of automation
368 // in the context of the UI, this is required to be implemented.
369 virtual HWND
GetContainerHWND() const { return NULL
; }
371 // Returns the bounds of this TabContents in the screen coordinate system.
372 virtual void GetContainerBounds(gfx::Rect
*out
) const {
373 out
->SetRect(0, 0, 0, 0);
376 // Make the tab the focused window.
377 virtual void Focus();
379 // Stores the currently focused view.
380 virtual void StoreFocus();
382 // Restores focus to the last focus view. If StoreFocus has not yet been
383 // invoked, SetInitialFocus is invoked.
384 virtual void RestoreFocus();
386 // Invoked the first time this tab is getting the focus through TAB traversal.
387 // By default this does nothing, but is overridden to set the focus for the
388 // first element in the page.
390 // |reverse| indicates if the user is going forward or backward, so we know
391 // whether to set the first or last element focus.
393 // See also SetInitialFocus(no arg).
394 // FIXME(brettw) having two SetInitialFocus that do different things is silly.
395 virtual void SetInitialFocus(bool reverse
) { }
397 // TabContents that contain View hierarchy (such as NativeUIContents) should
398 // return their RootView. Other TabContents (such as WebContents) should
400 // This is used by the focus manager to figure out what to focus when the tab
401 // is focused (when a tab with no view hierarchy is focused, the
402 // TabContentsContainerView is focused) and how to process tab events. If
403 // this returns NULL, the TabContents is supposed to know how to process TAB
404 // key events and is just sent the key messages. If this returns a RootView,
405 // the focus is passed to the RootView.
406 virtual ChromeViews::RootView
* GetContentsRootView() { return NULL
; }
408 // Toolbars and such ---------------------------------------------------------
410 // Returns whether the bookmark bar should be visible.
411 virtual bool IsBookmarkBarAlwaysVisible() { return false; }
413 // Whether or not the shelf view is visible.
414 virtual void SetDownloadShelfVisible(bool visible
);
415 bool IsDownloadShelfVisible() { return shelf_visible_
; }
417 // Notify our delegate that some of our content has animated.
418 void ToolbarSizeChanged(bool is_animating
);
420 // Displays the download shelf and animation when a download occurs.
421 void OnStartDownload(DownloadItem
* download
);
423 // Returns the DownloadShelfView, creating it if necessary.
424 DownloadShelfView
* GetDownloadShelfView();
426 // Transfer the shelf view from |tab_contents| to the receiving TabContents.
427 // |tab_contents| no longer owns the shelf after this call. The shelf is owned
428 // by the receiving TabContents.
429 void MigrateShelfViewFrom(TabContents
* tab_contents
);
431 // Migrate the shelf view between 2 TabContents. This helper function is
432 // currently called by NavigationController::DiscardPendingEntry. We may
433 // want to generalize this if we need to migrate some other state.
434 static void MigrateShelfView(TabContents
* from
, TabContents
* to
);
436 // ConstrainedTabContentsDelegate --------------------------------------------
438 virtual void AddNewContents(ConstrainedWindow
* window
,
439 TabContents
* contents
,
440 WindowOpenDisposition disposition
,
441 const gfx::Rect
& initial_pos
,
443 virtual void OpenURL(ConstrainedWindow
* window
,
445 WindowOpenDisposition disposition
,
446 PageTransition::Type transition
);
447 virtual void WillClose(ConstrainedWindow
* window
);
448 virtual void DetachContents(ConstrainedWindow
* window
,
449 TabContents
* contents
,
450 const gfx::Rect
& contents_bounds
,
451 const gfx::Point
& mouse_pt
,
452 int frame_component
);
453 virtual void DidMoveOrResize(ConstrainedWindow
* window
);
456 friend class NavigationController
;
457 // Used to access the child_windows_ (ConstrainedWindowList) for testing
458 // automation purposes.
459 friend class AutomationProvider
;
461 explicit TabContents(TabContentsType type
);
463 // Some tab contents types need to override the type.
464 void set_type(TabContentsType type
) { type_
= type
; }
466 // NOTE: the TabContents destructor can run after the NavigationController
467 // has gone away, so any complicated unregistering that expects the profile
468 // or other shared objects to still be around does not belong in a
470 // For those purposes, instead see Destroy().
471 // Protected so that others don't try to delete this directly.
472 virtual ~TabContents();
474 // Sets focus to the tab contents window, but doesn't actuall set focus to
475 // a particular element in it (see also SetInitialFocus(bool) which does
476 // that in different circumstances).
477 // FIXME(brettw) having two SetInitialFocus that do different things is silly.
478 virtual void SetInitialFocus();
480 // Changes the IsLoading state and notifies delegate as needed
481 // |details| is used to provide details on the load that just finished
482 // (but can be null if not applicable). Can be overridden.
483 virtual void SetIsLoading(bool is_loading
, LoadNotificationDetails
* details
);
485 // Called by a derived class when the TabContents is resized, causing
486 // suppressed constrained web popups to be repositioned to the new bounds
488 void RepositionSupressedPopupsToFit(const gfx::Size
& new_size
);
490 // Releases the download shelf. This method is used by MigrateShelfViewFrom.
491 // Sub-classes should clear any pointer they might keep to the shelf view and
492 // invoke TabContents::ReleaseDownloadShelfView().
493 virtual void ReleaseDownloadShelfView();
495 // Called by derived classes to indicate that we're no longer waiting for a
496 // response. This won't actually update the throbber, but it will get picked
497 // up at the next animation step if the throbber is going.
498 void SetNotWaitingForResponse() { waiting_for_response_
= false; }
500 typedef std::vector
<ConstrainedWindow
*> ConstrainedWindowList
;
501 ConstrainedWindowList child_windows_
;
504 // Data ----------------------------------------------------------------------
506 TabContentsType type_
;
508 TabContentsDelegate
* delegate_
;
509 NavigationController
* controller_
;
511 // Indicates whether we're currently loading a resource.
514 // See is_active() getter above.
517 bool is_crashed_
; // true if the tab is considered crashed.
519 // See waiting_for_response() above.
520 bool waiting_for_response_
;
522 scoped_ptr
<const AutocompleteEditState
> saved_location_bar_state_
;
524 // The download shelf view (view at the bottom of the page).
525 scoped_ptr
<DownloadShelfView
> download_shelf_view_
;
527 // Whether the shelf view is visible.
530 // Indicates the largest PageID we've seen. This field is ignored if we are
531 // a WebContents, in which case the max page ID is stored separately with
532 // each SiteInstance.
535 // The id used in the ViewStorage to store the last focused view.
536 int last_focused_view_storage_id_
;
538 std::wstring encoding_name_
;
540 // See capturing_contents() above.
541 bool capturing_contents_
;
543 DISALLOW_COPY_AND_ASSIGN(TabContents
);
546 #endif // CHROME_BROWSER_TAB_CONTENTS_H_