Index: chrome/browser/debugger/devtools_window.cc |
=================================================================== |
--- chrome/browser/debugger/devtools_window.cc (revision 19938) |
+++ chrome/browser/debugger/devtools_window.cc (working copy) |
@@ -14,7 +14,6 @@ |
#include "chrome/browser/tab_contents/navigation_controller.h" |
#include "chrome/browser/tab_contents/navigation_entry.h" |
#include "chrome/browser/tab_contents/tab_contents.h" |
-#include "chrome/browser/tab_contents/tab_contents_delegate.h" |
#include "chrome/browser/tab_contents/tab_contents_view.h" |
#include "chrome/browser/tabs/tab_strip_model.h" |
#include "chrome/common/bindings_policy.h" |
@@ -25,85 +24,13 @@ |
#include "chrome/common/url_constants.h" |
#include "grit/generated_resources.h" |
-namespace { |
-class FloatingWindow : public DevToolsWindow, |
- TabStripModelObserver { |
- public: |
- FloatingWindow(Profile* profile); |
- virtual ~FloatingWindow(); |
- virtual void Show(); |
- virtual void Activate(); |
- virtual void InspectedTabClosing(); |
- |
- // TabStripModelObserver implementation |
- virtual void TabClosingAt(TabContents* contents, int index); |
- virtual void TabStripEmpty(); |
- |
- private: |
- bool inspected_tab_closing_; |
- DISALLOW_COPY_AND_ASSIGN(FloatingWindow); |
-}; |
- |
-class DockedWindow : public DevToolsWindow, |
- TabContentsDelegate { |
- public: |
- DockedWindow(Profile* profile, BrowserWindow* window); |
- virtual ~DockedWindow(); |
- virtual void Activate() {} |
- virtual void Show(); |
- virtual void InspectedTabClosing(); |
- |
- private: |
- // Overridden from TabContentsDelegate: |
- virtual void OpenURLFromTab(TabContents* source, |
- const GURL& url, |
- const GURL& referrer, |
- WindowOpenDisposition disposition, |
- PageTransition::Type transition) {} |
- virtual void NavigationStateChanged(const TabContents* source, |
- unsigned changed_flags) {} |
- virtual void AddNewContents(TabContents* source, |
- TabContents* new_contents, |
- WindowOpenDisposition disposition, |
- const gfx::Rect& initial_pos, |
- bool user_gesture) {} |
- virtual void ActivateContents(TabContents* contents) {} |
- virtual void LoadingStateChanged(TabContents* source) {} |
- virtual void CloseContents(TabContents* source) {} |
- virtual void MoveContents(TabContents* source, const gfx::Rect& pos) {} |
- virtual bool IsPopup(TabContents* source) { return false; } |
- virtual void URLStarredChanged(TabContents* source, bool starred) {} |
- virtual void UpdateTargetURL(TabContents* source, const GURL& url) {} |
- virtual void ToolbarSizeChanged(TabContents* source, bool is_animating) {} |
- |
- BrowserWindow* window_; |
- DISALLOW_COPY_AND_ASSIGN(DockedWindow); |
-}; |
- |
-} // namespace |
- |
// static |
-DevToolsWindow* DevToolsWindow::CreateDevToolsWindow( |
- Profile* profile, |
- RenderViewHost* inspected_rvh, |
- bool docked) { |
- if (docked) { |
- BrowserWindow* window = DevToolsWindow::GetBrowserWindow(inspected_rvh); |
- if (window) { |
- return new DockedWindow(profile, window); |
- } |
- } |
- return new FloatingWindow(profile); |
-} |
- |
-// static |
TabContents* DevToolsWindow::GetDevToolsContents(TabContents* inspected_tab) { |
if (!inspected_tab) { |
return NULL; |
} |
- DevToolsClientHost* client_host = |
- DevToolsManager::GetInstance()-> |
+ DevToolsClientHost* client_host = DevToolsManager::GetInstance()-> |
GetDevToolsClientHostFor(inspected_tab->render_view_host()); |
if (!client_host) { |
return NULL; |
@@ -116,8 +43,33 @@ |
return window->tab_contents(); |
} |
-DevToolsWindow::DevToolsWindow(bool docked) |
- : docked_(docked) { |
+DevToolsWindow::DevToolsWindow(Profile* profile, |
+ RenderViewHost* inspected_rvh, |
+ bool docked) |
+ : profile_(profile), |
+ browser_(NULL), |
+ inspected_window_(NULL), |
+ docked_(docked) { |
+ // Create TabContents with devtools. |
+ tab_contents_ = new TabContents(profile, NULL, MSG_ROUTING_NONE, NULL); |
+ GURL url(std::string(chrome::kChromeUIDevToolsURL) + "devtools.html"); |
+ tab_contents_->render_view_host()->AllowBindings(BindingsPolicy::DOM_UI); |
+ tab_contents_->controller().LoadURL(url, GURL(), PageTransition::START_PAGE); |
+ |
+ // Wipe out page icon so that the default application icon is used. |
+ NavigationEntry* entry = tab_contents_->controller().GetActiveEntry(); |
+ entry->favicon().set_bitmap(SkBitmap()); |
+ entry->favicon().set_is_valid(true); |
+ |
+ // Register on-load actions. |
+ registrar_.Add(this, |
+ NotificationType::LOAD_STOP, |
+ Source<NavigationController>(&tab_contents_->controller())); |
+ registrar_.Add(this, |
+ NotificationType::TAB_CLOSING, |
+ Source<NavigationController>(&tab_contents_->controller())); |
+ |
+ inspected_tab_ = inspected_rvh->delegate()->GetAsTabContents(); |
} |
DevToolsWindow::~DevToolsWindow() { |
@@ -127,10 +79,6 @@ |
return this; |
} |
-RenderViewHost* DevToolsWindow::GetRenderViewHost() { |
- return tab_contents_->render_view_host(); |
-} |
- |
void DevToolsWindow::SendMessageToClient(const IPC::Message& message) { |
RenderViewHost* target_host = tab_contents_->render_view_host(); |
IPC::Message* m = new IPC::Message(message); |
@@ -138,47 +86,83 @@ |
target_host->Send(m); |
} |
-void DevToolsWindow::Observe(NotificationType type, |
- const NotificationSource& source, |
- const NotificationDetails& details) { |
- tab_contents_->render_view_host()-> |
- ExecuteJavascriptInWebFrame( |
- L"", docked_ ? L"WebInspector.setAttachedWindow(true);" : |
- L"WebInspector.setAttachedWindow(false);"); |
+void DevToolsWindow::InspectedTabClosing() { |
+ if (docked_) { |
+ // Update dev tools to reflect removed dev tools window. |
+ inspected_window_->UpdateDevTools(); |
+ // In case of docked tab_contents we own it, so delete here. |
+ |
+ // Instead of deleting tab contents, we add it into the |
+ // stub browser and initiate regular closure; |
+ Browser* b = Browser::Create(profile_); |
+ b->tabstrip_model()->AddTabContents(tab_contents_, -1, false, |
+ PageTransition::START_PAGE, true); |
+ b->CloseAllTabs(); |
+ delete this; |
+ } else { |
+ // First, initiate self-destruct to free all the registrars. |
+ // Then close all tabs. Browser will take care of deleting tab_contents |
+ // for us. |
+ Browser* browser = browser_; |
+ delete this; |
+ browser->CloseAllTabs(); |
+ } |
} |
-GURL DevToolsWindow::GetContentsUrl() { |
- return GURL(std::string(chrome::kChromeUIDevToolsURL) + "devtools.html"); |
+void DevToolsWindow::Show() { |
+ if (docked_) { |
+ // Just tell inspected browser to update splitter. |
+ inspected_window_ = GetInspectedBrowserWindow(); |
+ if (inspected_window_) { |
+ tab_contents_->set_delegate(this); |
+ inspected_window_->UpdateDevTools(); |
+ tab_contents_->view()->SetInitialFocus(); |
+ return; |
+ } else { |
+ // Sometimes we don't know where to dock. Stay undocked. |
+ docked_ = false; |
+ } |
+ } |
+ |
+ if (!browser_) { |
+ CreateDevToolsBrowser(); |
+ } |
+ browser_->window()->Show(); |
+ tab_contents_->view()->SetInitialFocus(); |
} |
-void DevToolsWindow::InitTabContents(TabContents* tab_contents) { |
- tab_contents_ = tab_contents; |
- registrar_.Add(this, NotificationType::LOAD_STOP, |
- Source<NavigationController>(&tab_contents_->controller())); |
+void DevToolsWindow::Activate() { |
+ if (!docked_ && !browser_->window()->IsActive()) { |
+ browser_->window()->Activate(); |
+ } |
} |
-// static |
-BrowserWindow* DevToolsWindow::GetBrowserWindow(RenderViewHost* rvh) { |
- for (BrowserList::const_iterator it = BrowserList::begin(); |
- it != BrowserList::end(); ++it) { |
- Browser* browser = *it; |
- for (int i = 0; i < browser->tab_count(); ++i) { |
- TabContents* tab_contents = browser->GetTabContentsAt(i); |
- if (tab_contents->render_view_host() == rvh) { |
- return browser->window(); |
- } |
- } |
+void DevToolsWindow::SetDocked(bool docked) { |
+ if (docked_ == docked) { |
+ return; |
} |
- return NULL; |
+ docked_ = docked; |
+ |
+ if (docked) { |
+ // Detach window from the external devtools browser. It will lead to |
+ // the browser object's close and delete. Remove observer first. |
+ TabStripModel* tabstrip_model = browser_->tabstrip_model(); |
+ tabstrip_model->DetachTabContentsAt( |
+ tabstrip_model->GetIndexOfTabContents(tab_contents_)); |
+ browser_ = NULL; |
+ } else { |
+ // Update inspected window to hide split and reset it. |
+ inspected_window_->UpdateDevTools(); |
+ inspected_window_ = NULL; |
+ } |
+ Show(); |
} |
-// |
-// Floating window implementation |
-// |
-FloatingWindow::FloatingWindow(Profile* profile) |
- : DevToolsWindow(false), |
- TabStripModelObserver(), |
- inspected_tab_closing_(false) { |
+RenderViewHost* DevToolsWindow::GetRenderViewHost() { |
+ return tab_contents_->render_view_host(); |
+} |
+ |
+void DevToolsWindow::CreateDevToolsBrowser() { |
// TODO(pfeldman): Make browser's getter for this key static. |
std::wstring wp_key = L""; |
wp_key.append(prefs::kBrowserWindowPlacement); |
@@ -201,75 +185,42 @@ |
defaults->SetBoolean(L"always_on_top", false); |
} |
- browser_ = Browser::CreateForApp(L"DevToolsApp", profile, false); |
- browser_->AddTabWithURL(GetContentsUrl(), GURL(), PageTransition::START_PAGE, |
- true, -1, false, NULL); |
- TabContents* tab_contents = browser_->GetSelectedTabContents(); |
- browser_->tabstrip_model()->AddObserver(this); |
- |
- // Wipe out page icon so that the default application icon is used. |
- NavigationEntry* entry = tab_contents->controller().GetActiveEntry(); |
- entry->favicon().set_bitmap(SkBitmap()); |
- entry->favicon().set_is_valid(true); |
- |
- InitTabContents(tab_contents); |
+ browser_ = Browser::CreateForApp(L"DevToolsApp", profile_, false); |
+ browser_->tabstrip_model()->AddTabContents( |
+ tab_contents_, -1, false, PageTransition::START_PAGE, true); |
} |
-FloatingWindow::~FloatingWindow() { |
-} |
- |
-void FloatingWindow::Activate() { |
- if (!browser_->window()->IsActive()) { |
- browser_->window()->Activate(); |
+BrowserWindow* DevToolsWindow::GetInspectedBrowserWindow() { |
+ for (BrowserList::const_iterator it = BrowserList::begin(); |
+ it != BrowserList::end(); ++it) { |
+ Browser* browser = *it; |
+ for (int i = 0; i < browser->tab_count(); ++i) { |
+ TabContents* tab_contents = browser->GetTabContentsAt(i); |
+ if (tab_contents == inspected_tab_) { |
+ return browser->window(); |
+ } |
+ } |
} |
+ return NULL; |
} |
-void FloatingWindow::Show() { |
- browser_->window()->Show(); |
- tab_contents_->view()->SetInitialFocus(); |
-} |
- |
-void FloatingWindow::InspectedTabClosing() { |
- inspected_tab_closing_ = true; |
- browser_->CloseAllTabs(); |
-} |
- |
-void FloatingWindow::TabClosingAt(TabContents* contents, int index) { |
- if (!inspected_tab_closing_ && contents == tab_contents_) { |
- // Notify manager that this DevToolsClientHost no longer exists. |
- NotifyCloseListener(); |
+void DevToolsWindow::Observe(NotificationType type, |
+ const NotificationSource& source, |
+ const NotificationDetails& details) { |
+ if (type == NotificationType::LOAD_STOP) { |
+ tab_contents_->render_view_host()-> |
+ ExecuteJavascriptInWebFrame( |
+ L"", docked_ ? L"WebInspector.setAttachedWindow(true);" : |
+ L"WebInspector.setAttachedWindow(false);"); |
+ } else if (type == NotificationType::TAB_CLOSING) { |
+ if (Source<NavigationController>(source).ptr() == |
+ &tab_contents_->controller()) { |
+ // This happens when browser closes all of its tabs as a result |
+ // of window.Close event. |
+ // Notify manager that this DevToolsClientHost no longer exists and |
+ // initiate self-destuct here. |
+ NotifyCloseListener(); |
+ delete this; |
+ } |
} |
} |
- |
-void FloatingWindow::TabStripEmpty() { |
- delete this; |
-} |
- |
-// |
-// Docked window implementation |
-// |
-DockedWindow::DockedWindow(Profile* profile, BrowserWindow* window) |
- : DevToolsWindow(true), |
- window_(window) { |
- TabContents* tab_contents = new TabContents(profile, |
- NULL, MSG_ROUTING_NONE, NULL); |
- tab_contents->render_view_host()->AllowBindings(BindingsPolicy::DOM_UI); |
- tab_contents->controller().LoadURL(GetContentsUrl(), GURL(), |
- PageTransition::START_PAGE); |
- tab_contents->set_delegate(this); |
- browser_ = NULL; |
- InitTabContents(tab_contents); |
-} |
- |
-DockedWindow::~DockedWindow() { |
-} |
- |
-void DockedWindow::Show() { |
- window_->UpdateDevTools(); |
- tab_contents_->view()->SetInitialFocus(); |
-} |
- |
-void DockedWindow::InspectedTabClosing() { |
- window_->UpdateDevTools(); |
- delete this; |
-} |