| OLD | NEW |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "chrome/browser/devtools/devtools_window.h" | 5 #include "chrome/browser/devtools/devtools_window.h" |
| 6 | |
| 7 #include <algorithm> | 6 #include <algorithm> |
| 8 | 7 |
| 9 #include "base/command_line.h" | 8 #include "base/command_line.h" |
| 10 #include "base/json/json_reader.h" | 9 #include "base/json/json_reader.h" |
| 11 #include "base/json/json_writer.h" | 10 #include "base/json/json_writer.h" |
| 12 #include "base/lazy_instance.h" | 11 #include "base/lazy_instance.h" |
| 13 #include "base/prefs/scoped_user_pref_update.h" | 12 #include "base/prefs/scoped_user_pref_update.h" |
| 14 #include "base/strings/string_number_conversions.h" | 13 #include "base/strings/string_number_conversions.h" |
| 15 #include "base/strings/string_util.h" | 14 #include "base/strings/string_util.h" |
| 16 #include "base/strings/utf_string_conversions.h" | 15 #include "base/strings/utf_string_conversions.h" |
| (...skipping 204 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 221 } | 220 } |
| 222 | 221 |
| 223 // DevToolsWindow ------------------------------------------------------------- | 222 // DevToolsWindow ------------------------------------------------------------- |
| 224 | 223 |
| 225 namespace { | 224 namespace { |
| 226 | 225 |
| 227 typedef std::vector<DevToolsWindow*> DevToolsWindows; | 226 typedef std::vector<DevToolsWindow*> DevToolsWindows; |
| 228 base::LazyInstance<DevToolsWindows>::Leaky g_instances = | 227 base::LazyInstance<DevToolsWindows>::Leaky g_instances = |
| 229 LAZY_INSTANCE_INITIALIZER; | 228 LAZY_INSTANCE_INITIALIZER; |
| 230 | 229 |
| 231 const char kPrefBottom[] = "dock_bottom"; | 230 // TODO(dgozman): remove after switching to SetIsDocked. |
| 232 const char kPrefRight[] = "dock_right"; | |
| 233 const char kPrefUndocked[] = "undocked"; | |
| 234 | |
| 235 const char kDockSideBottom[] = "bottom"; | |
| 236 const char kDockSideRight[] = "right"; | |
| 237 const char kDockSideUndocked[] = "undocked"; | 231 const char kDockSideUndocked[] = "undocked"; |
| 238 const char kDockSideMinimized[] = "minimized"; | |
| 239 | 232 |
| 240 static const char kFrontendHostId[] = "id"; | 233 static const char kFrontendHostId[] = "id"; |
| 241 static const char kFrontendHostMethod[] = "method"; | 234 static const char kFrontendHostMethod[] = "method"; |
| 242 static const char kFrontendHostParams[] = "params"; | 235 static const char kFrontendHostParams[] = "params"; |
| 243 | 236 |
| 244 std::string SkColorToRGBAString(SkColor color) { | 237 std::string SkColorToRGBAString(SkColor color) { |
| 245 // We avoid StringPrintf because it will use locale specific formatters for | 238 // We avoid StringPrintf because it will use locale specific formatters for |
| 246 // the double (e.g. ',' instead of '.' in German). | 239 // the double (e.g. ',' instead of '.' in German). |
| 247 return "rgba(" + base::IntToString(SkColorGetR(color)) + "," + | 240 return "rgba(" + base::IntToString(SkColorGetR(color)) + "," + |
| 248 base::IntToString(SkColorGetG(color)) + "," + | 241 base::IntToString(SkColorGetG(color)) + "," + |
| (...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 283 | 276 |
| 284 // static | 277 // static |
| 285 std::string DevToolsWindow::GetDevToolsWindowPlacementPrefKey() { | 278 std::string DevToolsWindow::GetDevToolsWindowPlacementPrefKey() { |
| 286 return std::string(prefs::kBrowserWindowPlacement) + "_" + | 279 return std::string(prefs::kBrowserWindowPlacement) + "_" + |
| 287 std::string(kDevToolsApp); | 280 std::string(kDevToolsApp); |
| 288 } | 281 } |
| 289 | 282 |
| 290 // static | 283 // static |
| 291 void DevToolsWindow::RegisterProfilePrefs( | 284 void DevToolsWindow::RegisterProfilePrefs( |
| 292 user_prefs::PrefRegistrySyncable* registry) { | 285 user_prefs::PrefRegistrySyncable* registry) { |
| 293 registry->RegisterBooleanPref( | |
| 294 prefs::kDevToolsOpenDocked, true, | |
| 295 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF); | |
| 296 registry->RegisterStringPref( | |
| 297 prefs::kDevToolsDockSide, kDockSideBottom, | |
| 298 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF); | |
| 299 registry->RegisterDictionaryPref( | 286 registry->RegisterDictionaryPref( |
| 300 prefs::kDevToolsEditedFiles, | 287 prefs::kDevToolsEditedFiles, |
| 301 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF); | 288 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF); |
| 302 registry->RegisterDictionaryPref( | 289 registry->RegisterDictionaryPref( |
| 303 prefs::kDevToolsFileSystemPaths, | 290 prefs::kDevToolsFileSystemPaths, |
| 304 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF); | 291 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF); |
| 305 registry->RegisterStringPref( | 292 registry->RegisterStringPref( |
| 306 prefs::kDevToolsAdbKey, std::string(), | 293 prefs::kDevToolsAdbKey, std::string(), |
| 307 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF); | 294 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF); |
| 308 | 295 |
| (...skipping 16 matching lines...) Expand all Loading... |
| 325 registry->RegisterDictionaryPref( | 312 registry->RegisterDictionaryPref( |
| 326 prefs::kDevToolsPortForwardingConfig, | 313 prefs::kDevToolsPortForwardingConfig, |
| 327 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF); | 314 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF); |
| 328 } | 315 } |
| 329 | 316 |
| 330 // static | 317 // static |
| 331 DevToolsWindow* DevToolsWindow::GetDockedInstanceForInspectedTab( | 318 DevToolsWindow* DevToolsWindow::GetDockedInstanceForInspectedTab( |
| 332 content::WebContents* inspected_web_contents) { | 319 content::WebContents* inspected_web_contents) { |
| 333 DevToolsWindow* window = GetInstanceForInspectedRenderViewHost( | 320 DevToolsWindow* window = GetInstanceForInspectedRenderViewHost( |
| 334 inspected_web_contents->GetRenderViewHost()); | 321 inspected_web_contents->GetRenderViewHost()); |
| 335 return (window && window->IsDocked()) ? window : NULL; | 322 if (!window) |
| 323 return NULL; |
| 324 // Not yet loaded window is treated as docked, but we should not present it |
| 325 // until we decided on docking. |
| 326 bool is_docked_set = window->load_state_ == kLoadCompleted || |
| 327 window->load_state_ == kIsDockedSet; |
| 328 return window->is_docked_ && is_docked_set ? window : NULL; |
| 336 } | 329 } |
| 337 | 330 |
| 338 // static | 331 // static |
| 339 DevToolsWindow* DevToolsWindow::GetInstanceForInspectedRenderViewHost( | 332 DevToolsWindow* DevToolsWindow::GetInstanceForInspectedRenderViewHost( |
| 340 content::RenderViewHost* inspected_rvh) { | 333 content::RenderViewHost* inspected_rvh) { |
| 341 if (!inspected_rvh || !DevToolsAgentHost::HasFor(inspected_rvh)) | 334 if (!inspected_rvh || !DevToolsAgentHost::HasFor(inspected_rvh)) |
| 342 return NULL; | 335 return NULL; |
| 343 | 336 |
| 344 scoped_refptr<DevToolsAgentHost> agent(DevToolsAgentHost::GetOrCreateFor( | 337 scoped_refptr<DevToolsAgentHost> agent(DevToolsAgentHost::GetOrCreateFor( |
| 345 inspected_rvh)); | 338 inspected_rvh)); |
| 346 return FindDevToolsWindow(agent.get()); | 339 return FindDevToolsWindow(agent.get()); |
| 347 } | 340 } |
| 348 | 341 |
| 349 // static | 342 // static |
| 350 bool DevToolsWindow::IsDevToolsWindow(content::RenderViewHost* window_rvh) { | 343 bool DevToolsWindow::IsDevToolsWindow(content::RenderViewHost* window_rvh) { |
| 351 return AsDevToolsWindow(window_rvh) != NULL; | 344 return AsDevToolsWindow(window_rvh) != NULL; |
| 352 } | 345 } |
| 353 | 346 |
| 354 // static | 347 // static |
| 355 DevToolsWindow* DevToolsWindow::OpenDevToolsWindowForWorker( | 348 DevToolsWindow* DevToolsWindow::OpenDevToolsWindowForWorker( |
| 356 Profile* profile, | 349 Profile* profile, |
| 357 DevToolsAgentHost* worker_agent) { | 350 DevToolsAgentHost* worker_agent) { |
| 358 DevToolsWindow* window = FindDevToolsWindow(worker_agent); | 351 DevToolsWindow* window = FindDevToolsWindow(worker_agent); |
| 359 if (!window) { | 352 if (!window) { |
| 360 window = DevToolsWindow::CreateDevToolsWindowForWorker(profile); | 353 window = DevToolsWindow::CreateDevToolsWindowForWorker(profile); |
| 361 // Will disconnect the current client host if there is one. | 354 // Will disconnect the current client host if there is one. |
| 362 content::DevToolsManager::GetInstance()->RegisterDevToolsClientHostFor( | 355 content::DevToolsManager::GetInstance()->RegisterDevToolsClientHostFor( |
| 363 worker_agent, window->frontend_host_.get()); | 356 worker_agent, window->frontend_host_.get()); |
| 364 } | 357 } |
| 365 window->Show(DevToolsToggleAction::Show()); | 358 window->ScheduleShow(DevToolsToggleAction::Show()); |
| 366 return window; | 359 return window; |
| 367 } | 360 } |
| 368 | 361 |
| 369 // static | 362 // static |
| 370 DevToolsWindow* DevToolsWindow::CreateDevToolsWindowForWorker( | 363 DevToolsWindow* DevToolsWindow::CreateDevToolsWindowForWorker( |
| 371 Profile* profile) { | 364 Profile* profile) { |
| 372 content::RecordAction(base::UserMetricsAction("DevTools_InspectWorker")); | 365 content::RecordAction(base::UserMetricsAction("DevTools_InspectWorker")); |
| 373 return Create(profile, GURL(), NULL, DEVTOOLS_DOCK_SIDE_UNDOCKED, true, | 366 return Create(profile, GURL(), NULL, true, false, false); |
| 374 false, false); | |
| 375 } | 367 } |
| 376 | 368 |
| 377 // static | 369 // static |
| 378 DevToolsWindow* DevToolsWindow::OpenDevToolsWindow( | 370 DevToolsWindow* DevToolsWindow::OpenDevToolsWindow( |
| 379 content::RenderViewHost* inspected_rvh) { | 371 content::RenderViewHost* inspected_rvh) { |
| 380 return ToggleDevToolsWindow( | 372 return ToggleDevToolsWindow( |
| 381 inspected_rvh, true, DevToolsToggleAction::Show()); | 373 inspected_rvh, true, DevToolsToggleAction::Show()); |
| 382 } | 374 } |
| 383 | 375 |
| 384 // static | 376 // static |
| 377 DevToolsWindow* DevToolsWindow::OpenDevToolsWindow( |
| 378 content::RenderViewHost* inspected_rvh, |
| 379 const DevToolsToggleAction& action) { |
| 380 return ToggleDevToolsWindow( |
| 381 inspected_rvh, true, action); |
| 382 } |
| 383 |
| 384 // static |
| 385 DevToolsWindow* DevToolsWindow::OpenDevToolsWindowForTest( |
| 386 content::RenderViewHost* inspected_rvh, |
| 387 bool is_docked) { |
| 388 DevToolsWindow* window = OpenDevToolsWindow(inspected_rvh); |
| 389 window->SetIsDockedAndShowImmediatelyForTest(is_docked); |
| 390 return window; |
| 391 } |
| 392 |
| 393 // static |
| 394 DevToolsWindow* DevToolsWindow::OpenDevToolsWindowForTest( |
| 395 Browser* browser, |
| 396 bool is_docked) { |
| 397 return OpenDevToolsWindowForTest( |
| 398 browser->tab_strip_model()->GetActiveWebContents()->GetRenderViewHost(), |
| 399 is_docked); |
| 400 } |
| 401 |
| 402 // static |
| 385 DevToolsWindow* DevToolsWindow::ToggleDevToolsWindow( | 403 DevToolsWindow* DevToolsWindow::ToggleDevToolsWindow( |
| 386 Browser* browser, | 404 Browser* browser, |
| 387 const DevToolsToggleAction& action) { | 405 const DevToolsToggleAction& action) { |
| 388 if (action.type() == DevToolsToggleAction::kToggle && | 406 if (action.type() == DevToolsToggleAction::kToggle && |
| 389 browser->is_devtools()) { | 407 browser->is_devtools()) { |
| 390 browser->tab_strip_model()->CloseAllTabs(); | 408 browser->tab_strip_model()->CloseAllTabs(); |
| 391 return NULL; | 409 return NULL; |
| 392 } | 410 } |
| 393 | 411 |
| 394 return ToggleDevToolsWindow( | 412 return ToggleDevToolsWindow( |
| 395 browser->tab_strip_model()->GetActiveWebContents()->GetRenderViewHost(), | 413 browser->tab_strip_model()->GetActiveWebContents()->GetRenderViewHost(), |
| 396 action.type() == DevToolsToggleAction::kInspect, action); | 414 action.type() == DevToolsToggleAction::kInspect, action); |
| 397 } | 415 } |
| 398 | 416 |
| 399 // static | 417 // static |
| 400 void DevToolsWindow::OpenExternalFrontend( | 418 void DevToolsWindow::OpenExternalFrontend( |
| 401 Profile* profile, | 419 Profile* profile, |
| 402 const std::string& frontend_url, | 420 const std::string& frontend_url, |
| 403 content::DevToolsAgentHost* agent_host) { | 421 content::DevToolsAgentHost* agent_host) { |
| 404 DevToolsWindow* window = FindDevToolsWindow(agent_host); | 422 DevToolsWindow* window = FindDevToolsWindow(agent_host); |
| 405 if (!window) { | 423 if (!window) { |
| 406 window = Create(profile, DevToolsUI::GetProxyURL(frontend_url), NULL, | 424 window = Create(profile, DevToolsUI::GetProxyURL(frontend_url), NULL, |
| 407 DEVTOOLS_DOCK_SIDE_UNDOCKED, false, true, false); | 425 false, true, false); |
| 408 content::DevToolsManager::GetInstance()->RegisterDevToolsClientHostFor( | 426 content::DevToolsManager::GetInstance()->RegisterDevToolsClientHostFor( |
| 409 agent_host, window->frontend_host_.get()); | 427 agent_host, window->frontend_host_.get()); |
| 410 } | 428 } |
| 411 window->Show(DevToolsToggleAction::Show()); | 429 window->ScheduleShow(DevToolsToggleAction::Show()); |
| 412 } | 430 } |
| 413 | 431 |
| 414 // static | 432 // static |
| 415 DevToolsWindow* DevToolsWindow::ToggleDevToolsWindow( | 433 DevToolsWindow* DevToolsWindow::ToggleDevToolsWindow( |
| 416 content::RenderViewHost* inspected_rvh, | 434 content::RenderViewHost* inspected_rvh, |
| 417 bool force_open, | 435 bool force_open, |
| 418 const DevToolsToggleAction& action) { | 436 const DevToolsToggleAction& action) { |
| 419 scoped_refptr<DevToolsAgentHost> agent( | 437 scoped_refptr<DevToolsAgentHost> agent( |
| 420 DevToolsAgentHost::GetOrCreateFor(inspected_rvh)); | 438 DevToolsAgentHost::GetOrCreateFor(inspected_rvh)); |
| 421 content::DevToolsManager* manager = content::DevToolsManager::GetInstance(); | 439 content::DevToolsManager* manager = content::DevToolsManager::GetInstance(); |
| 422 DevToolsWindow* window = FindDevToolsWindow(agent.get()); | 440 DevToolsWindow* window = FindDevToolsWindow(agent.get()); |
| 423 bool do_open = force_open; | 441 bool do_open = force_open; |
| 424 if (!window) { | 442 if (!window) { |
| 425 Profile* profile = Profile::FromBrowserContext( | 443 Profile* profile = Profile::FromBrowserContext( |
| 426 inspected_rvh->GetProcess()->GetBrowserContext()); | 444 inspected_rvh->GetProcess()->GetBrowserContext()); |
| 427 DevToolsDockSide dock_side = GetDockSideFromPrefs(profile); | |
| 428 content::RecordAction( | 445 content::RecordAction( |
| 429 base::UserMetricsAction("DevTools_InspectRenderer")); | 446 base::UserMetricsAction("DevTools_InspectRenderer")); |
| 430 window = Create(profile, GURL(), inspected_rvh, dock_side, false, false, | 447 window = Create(profile, GURL(), inspected_rvh, false, false, true); |
| 431 true); | |
| 432 manager->RegisterDevToolsClientHostFor(agent.get(), | 448 manager->RegisterDevToolsClientHostFor(agent.get(), |
| 433 window->frontend_host_.get()); | 449 window->frontend_host_.get()); |
| 434 do_open = true; | 450 do_open = true; |
| 435 } | 451 } |
| 436 | 452 |
| 437 // Update toolbar to reflect DevTools changes. | 453 // Update toolbar to reflect DevTools changes. |
| 438 window->UpdateBrowserToolbar(); | 454 window->UpdateBrowserToolbar(); |
| 439 | 455 |
| 440 // If window is docked and visible, we hide it on toggle. If window is | 456 // If window is docked and visible, we hide it on toggle. If window is |
| 441 // undocked, we show (activate) it. If window is minimized, we maximize it. | 457 // undocked, we show (activate) it. |
| 442 if (window->dock_side_ == DEVTOOLS_DOCK_SIDE_MINIMIZED) | 458 if (!window->is_docked_ || do_open) |
| 443 window->Restore(); | 459 window->ScheduleShow(action); |
| 444 else if (!window->IsDocked() || do_open) | |
| 445 window->Show(action); | |
| 446 else | 460 else |
| 447 window->CloseWindow(); | 461 window->CloseWindow(); |
| 448 | 462 |
| 449 return window; | 463 return window; |
| 450 } | 464 } |
| 451 | 465 |
| 452 // static | 466 // static |
| 453 void DevToolsWindow::InspectElement(content::RenderViewHost* inspected_rvh, | 467 void DevToolsWindow::InspectElement(content::RenderViewHost* inspected_rvh, |
| 454 int x, | 468 int x, |
| 455 int y) { | 469 int y) { |
| 456 scoped_refptr<DevToolsAgentHost> agent( | 470 scoped_refptr<DevToolsAgentHost> agent( |
| 457 DevToolsAgentHost::GetOrCreateFor(inspected_rvh)); | 471 DevToolsAgentHost::GetOrCreateFor(inspected_rvh)); |
| 458 agent->InspectElement(x, y); | 472 agent->InspectElement(x, y); |
| 459 // TODO(loislo): we should initiate DevTools window opening from within | 473 // TODO(loislo): we should initiate DevTools window opening from within |
| 460 // renderer. Otherwise, we still can hit a race condition here. | 474 // renderer. Otherwise, we still can hit a race condition here. |
| 461 OpenDevToolsWindow(inspected_rvh); | 475 OpenDevToolsWindow(inspected_rvh); |
| 462 } | 476 } |
| 463 | 477 |
| 464 // static | 478 // static |
| 465 int DevToolsWindow::GetMinimizedHeight() { | 479 int DevToolsWindow::GetMinimizedHeight() { |
| 466 const int kMinimizedDevToolsHeight = 24; | 480 const int kMinimizedDevToolsHeight = 24; |
| 467 return kMinimizedDevToolsHeight; | 481 return kMinimizedDevToolsHeight; |
| 468 } | 482 } |
| 469 | 483 |
| 470 void DevToolsWindow::InspectedContentsClosing() { | 484 void DevToolsWindow::InspectedContentsClosing() { |
| 471 intercepted_page_beforeunload_ = false; | 485 intercepted_page_beforeunload_ = false; |
| 486 // This will prevent any activity after frontend is loaded. |
| 487 action_on_load_ = DevToolsToggleAction::NoOp(); |
| 472 web_contents_->GetRenderViewHost()->ClosePage(); | 488 web_contents_->GetRenderViewHost()->ClosePage(); |
| 473 } | 489 } |
| 474 | 490 |
| 475 content::RenderViewHost* DevToolsWindow::GetRenderViewHost() { | 491 content::RenderViewHost* DevToolsWindow::GetRenderViewHost() { |
| 476 return web_contents_->GetRenderViewHost(); | 492 return web_contents_->GetRenderViewHost(); |
| 477 } | 493 } |
| 478 | 494 |
| 479 content::DevToolsClientHost* DevToolsWindow::GetDevToolsClientHostForTest() { | |
| 480 return frontend_host_.get(); | |
| 481 } | |
| 482 | |
| 483 gfx::Insets DevToolsWindow::GetContentsInsets() const { | 495 gfx::Insets DevToolsWindow::GetContentsInsets() const { |
| 484 return contents_insets_; | 496 return contents_insets_; |
| 485 } | 497 } |
| 486 | 498 |
| 487 gfx::Size DevToolsWindow::GetMinimumSize() const { | 499 gfx::Size DevToolsWindow::GetMinimumSize() const { |
| 488 const gfx::Size kMinDevToolsSize = gfx::Size(200, 100); | 500 const gfx::Size kMinDevToolsSize = gfx::Size(200, 100); |
| 489 return kMinDevToolsSize; | 501 return kMinDevToolsSize; |
| 490 } | 502 } |
| 491 | 503 |
| 504 void DevToolsWindow::ScheduleShow(const DevToolsToggleAction& action) { |
| 505 if (load_state_ == kLoadCompleted) { |
| 506 Show(action); |
| 507 return; |
| 508 } |
| 509 |
| 510 // Action will be done only after load completed. |
| 511 action_on_load_ = action; |
| 512 |
| 513 if (!can_dock_) { |
| 514 // No harm to show always-undocked window right away. |
| 515 is_docked_ = false; |
| 516 Show(DevToolsToggleAction::Show()); |
| 517 } |
| 518 } |
| 519 |
| 492 void DevToolsWindow::Show(const DevToolsToggleAction& action) { | 520 void DevToolsWindow::Show(const DevToolsToggleAction& action) { |
| 493 if (IsDocked()) { | 521 if (action.type() == DevToolsToggleAction::kNoOp) |
| 522 return; |
| 523 |
| 524 if (is_docked_) { |
| 525 DCHECK(can_dock_); |
| 494 Browser* inspected_browser = NULL; | 526 Browser* inspected_browser = NULL; |
| 495 int inspected_tab_index = -1; | 527 int inspected_tab_index = -1; |
| 528 FindInspectedBrowserAndTabIndex(GetInspectedWebContents(), |
| 529 &inspected_browser, |
| 530 &inspected_tab_index); |
| 531 DCHECK(inspected_browser); |
| 532 DCHECK(inspected_tab_index != -1); |
| 533 |
| 496 // Tell inspected browser to update splitter and switch to inspected panel. | 534 // Tell inspected browser to update splitter and switch to inspected panel. |
| 497 if (!IsInspectedBrowserPopup() && | 535 BrowserWindow* inspected_window = inspected_browser->window(); |
| 498 FindInspectedBrowserAndTabIndex(GetInspectedWebContents(), | 536 web_contents_->SetDelegate(this); |
| 499 &inspected_browser, | 537 inspected_window->UpdateDevTools(); |
| 500 &inspected_tab_index)) { | 538 web_contents_->GetView()->SetInitialFocus(); |
| 501 BrowserWindow* inspected_window = inspected_browser->window(); | 539 inspected_window->Show(); |
| 502 web_contents_->SetDelegate(this); | |
| 503 inspected_window->UpdateDevTools(); | |
| 504 web_contents_->GetView()->SetInitialFocus(); | |
| 505 inspected_window->Show(); | |
| 506 TabStripModel* tab_strip_model = inspected_browser->tab_strip_model(); | |
| 507 tab_strip_model->ActivateTabAt(inspected_tab_index, true); | |
| 508 PrefsTabHelper::CreateForWebContents(web_contents_); | |
| 509 GetRenderViewHost()->SyncRendererPrefs(); | |
| 510 ScheduleAction(action); | |
| 511 return; | |
| 512 } | |
| 513 | 540 |
| 514 // Sometimes we don't know where to dock. Stay undocked. | 541 TabStripModel* tab_strip_model = inspected_browser->tab_strip_model(); |
| 515 dock_side_ = DEVTOOLS_DOCK_SIDE_UNDOCKED; | 542 tab_strip_model->ActivateTabAt(inspected_tab_index, true); |
| 543 PrefsTabHelper::CreateForWebContents(web_contents_); |
| 544 GetRenderViewHost()->SyncRendererPrefs(); |
| 545 |
| 546 DoAction(action); |
| 547 return; |
| 516 } | 548 } |
| 517 | 549 |
| 518 // Avoid consecutive window switching if the devtools window has been opened | 550 // Avoid consecutive window switching if the devtools window has been opened |
| 519 // and the Inspect Element shortcut is pressed in the inspected tab. | 551 // and the Inspect Element shortcut is pressed in the inspected tab. |
| 520 bool should_show_window = | 552 bool should_show_window = |
| 521 !browser_ || (action.type() != DevToolsToggleAction::kInspect); | 553 !browser_ || (action.type() != DevToolsToggleAction::kInspect); |
| 522 | 554 |
| 523 if (!browser_) | 555 if (!browser_) |
| 524 CreateDevToolsBrowser(); | 556 CreateDevToolsBrowser(); |
| 525 | 557 |
| 526 if (should_show_window) { | 558 if (should_show_window) { |
| 527 browser_->window()->Show(); | 559 browser_->window()->Show(); |
| 528 web_contents_->GetView()->SetInitialFocus(); | 560 web_contents_->GetView()->SetInitialFocus(); |
| 529 } | 561 } |
| 530 | 562 |
| 531 ScheduleAction(action); | 563 DoAction(action); |
| 532 } | 564 } |
| 533 | 565 |
| 534 // static | 566 // static |
| 535 bool DevToolsWindow::HandleBeforeUnload(content::WebContents* frontend_contents, | 567 bool DevToolsWindow::HandleBeforeUnload(content::WebContents* frontend_contents, |
| 536 bool proceed, bool* proceed_to_fire_unload) { | 568 bool proceed, bool* proceed_to_fire_unload) { |
| 537 DevToolsWindow* window = AsDevToolsWindow( | 569 DevToolsWindow* window = AsDevToolsWindow( |
| 538 frontend_contents->GetRenderViewHost()); | 570 frontend_contents->GetRenderViewHost()); |
| 539 if (!window) | 571 if (!window) |
| 540 return false; | 572 return false; |
| 541 if (!window->intercepted_page_beforeunload_) | 573 if (!window->intercepted_page_beforeunload_) |
| 542 return false; | 574 return false; |
| 543 window->BeforeUnloadFired(frontend_contents, proceed, | 575 window->BeforeUnloadFired(frontend_contents, proceed, |
| 544 proceed_to_fire_unload); | 576 proceed_to_fire_unload); |
| 545 return true; | 577 return true; |
| 546 } | 578 } |
| 547 | 579 |
| 548 // static | 580 // static |
| 549 bool DevToolsWindow::InterceptPageBeforeUnload(content::WebContents* contents) { | 581 bool DevToolsWindow::InterceptPageBeforeUnload(content::WebContents* contents) { |
| 550 DevToolsWindow* window = | 582 DevToolsWindow* window = |
| 551 DevToolsWindow::GetInstanceForInspectedRenderViewHost( | 583 DevToolsWindow::GetInstanceForInspectedRenderViewHost( |
| 552 contents->GetRenderViewHost()); | 584 contents->GetRenderViewHost()); |
| 553 if (!window || window->intercepted_page_beforeunload_) | 585 if (!window || window->intercepted_page_beforeunload_) |
| 554 return false; | 586 return false; |
| 555 | 587 |
| 588 // Not yet loaded frontend will not handle beforeunload. |
| 589 if (window->load_state_ != kLoadCompleted) |
| 590 return false; |
| 591 |
| 556 window->intercepted_page_beforeunload_ = true; | 592 window->intercepted_page_beforeunload_ = true; |
| 557 // Handle case of devtools inspecting another devtools instance by passing | 593 // Handle case of devtools inspecting another devtools instance by passing |
| 558 // the call up to the inspecting devtools instance. | 594 // the call up to the inspecting devtools instance. |
| 559 if (!DevToolsWindow::InterceptPageBeforeUnload(window->web_contents())) { | 595 if (!DevToolsWindow::InterceptPageBeforeUnload(window->web_contents())) { |
| 560 window->web_contents()->GetRenderViewHost()->FirePageBeforeUnload(false); | 596 window->web_contents()->GetRenderViewHost()->FirePageBeforeUnload(false); |
| 561 } | 597 } |
| 562 return true; | 598 return true; |
| 563 } | 599 } |
| 564 | 600 |
| 565 // static | 601 // static |
| (...skipping 27 matching lines...) Expand all Loading... |
| 593 DevToolsWindow *window = | 629 DevToolsWindow *window = |
| 594 DevToolsWindow::GetInstanceForInspectedRenderViewHost( | 630 DevToolsWindow::GetInstanceForInspectedRenderViewHost( |
| 595 contents->GetRenderViewHost()); | 631 contents->GetRenderViewHost()); |
| 596 if (!window) | 632 if (!window) |
| 597 return; | 633 return; |
| 598 window->intercepted_page_beforeunload_ = false; | 634 window->intercepted_page_beforeunload_ = false; |
| 599 // Propagate to devtools opened on devtools if any. | 635 // Propagate to devtools opened on devtools if any. |
| 600 DevToolsWindow::OnPageCloseCanceled(window->web_contents()); | 636 DevToolsWindow::OnPageCloseCanceled(window->web_contents()); |
| 601 } | 637 } |
| 602 | 638 |
| 603 void DevToolsWindow::SetDockSideForTest(DevToolsDockSide dock_side) { | |
| 604 SetDockSide(SideToString(dock_side)); | |
| 605 } | |
| 606 | |
| 607 DevToolsWindow::DevToolsWindow(Profile* profile, | 639 DevToolsWindow::DevToolsWindow(Profile* profile, |
| 608 const GURL& url, | 640 const GURL& url, |
| 609 content::RenderViewHost* inspected_rvh, | 641 content::RenderViewHost* inspected_rvh, |
| 610 DevToolsDockSide dock_side) | 642 bool can_dock) |
| 611 : profile_(profile), | 643 : profile_(profile), |
| 612 browser_(NULL), | 644 browser_(NULL), |
| 613 dock_side_(dock_side), | 645 is_docked_(true), |
| 614 is_loaded_(false), | 646 can_dock_(can_dock), |
| 615 action_on_load_(DevToolsToggleAction::Show()), | 647 // This initialization allows external front-end to work without changes. |
| 616 dock_side_before_minimized_(dock_side), | 648 // We don't wait for docking call, but instead immediately show undocked. |
| 649 // Passing "dockSide=undocked" parameter ensures proper UI. |
| 650 load_state_(can_dock ? kNotLoaded : kIsDockedSet), |
| 651 action_on_load_(DevToolsToggleAction::NoOp()), |
| 652 ignore_set_is_docked_for_test_(false), |
| 617 intercepted_page_beforeunload_(false), | 653 intercepted_page_beforeunload_(false), |
| 618 weak_factory_(this) { | 654 weak_factory_(this) { |
| 619 web_contents_ = | 655 web_contents_ = |
| 620 content::WebContents::Create(content::WebContents::CreateParams(profile)); | 656 content::WebContents::Create(content::WebContents::CreateParams(profile)); |
| 621 frontend_contents_observer_.reset(new FrontendWebContentsObserver(this)); | 657 frontend_contents_observer_.reset(new FrontendWebContentsObserver(this)); |
| 622 | 658 |
| 659 // Set up delegate, so we get fully-functional window immediately. |
| 660 // It will not appear in UI though until |load_state_ == kLoadCompleted|. |
| 661 web_contents_->SetDelegate(this); |
| 662 |
| 623 web_contents_->GetController().LoadURL(url, content::Referrer(), | 663 web_contents_->GetController().LoadURL(url, content::Referrer(), |
| 624 content::PAGE_TRANSITION_AUTO_TOPLEVEL, std::string()); | 664 content::PAGE_TRANSITION_AUTO_TOPLEVEL, std::string()); |
| 625 | 665 |
| 626 frontend_host_.reset(content::DevToolsClientHost::CreateDevToolsFrontendHost( | 666 frontend_host_.reset(content::DevToolsClientHost::CreateDevToolsFrontendHost( |
| 627 web_contents_, this)); | 667 web_contents_, this)); |
| 628 file_helper_.reset(new DevToolsFileHelper(web_contents_, profile)); | 668 file_helper_.reset(new DevToolsFileHelper(web_contents_, profile)); |
| 629 file_system_indexer_ = new DevToolsFileSystemIndexer(); | 669 file_system_indexer_ = new DevToolsFileSystemIndexer(); |
| 630 extensions::ExtensionWebContentsObserver::CreateForWebContents(web_contents_); | 670 extensions::ExtensionWebContentsObserver::CreateForWebContents(web_contents_); |
| 631 | 671 |
| 632 g_instances.Get().push_back(this); | 672 g_instances.Get().push_back(this); |
| (...skipping 17 matching lines...) Expand all Loading... |
| 650 | 690 |
| 651 embedder_message_dispatcher_.reset( | 691 embedder_message_dispatcher_.reset( |
| 652 new DevToolsEmbedderMessageDispatcher(this)); | 692 new DevToolsEmbedderMessageDispatcher(this)); |
| 653 } | 693 } |
| 654 | 694 |
| 655 // static | 695 // static |
| 656 DevToolsWindow* DevToolsWindow::Create( | 696 DevToolsWindow* DevToolsWindow::Create( |
| 657 Profile* profile, | 697 Profile* profile, |
| 658 const GURL& frontend_url, | 698 const GURL& frontend_url, |
| 659 content::RenderViewHost* inspected_rvh, | 699 content::RenderViewHost* inspected_rvh, |
| 660 DevToolsDockSide dock_side, | |
| 661 bool shared_worker_frontend, | 700 bool shared_worker_frontend, |
| 662 bool external_frontend, | 701 bool external_frontend, |
| 663 bool can_dock) { | 702 bool can_dock) { |
| 664 if (inspected_rvh) { | 703 if (inspected_rvh) { |
| 665 // Check for a place to dock. | 704 // Check for a place to dock. |
| 666 Browser* browser = NULL; | 705 Browser* browser = NULL; |
| 667 int tab; | 706 int tab; |
| 668 content::WebContents* inspected_web_contents = | 707 content::WebContents* inspected_web_contents = |
| 669 content::WebContents::FromRenderViewHost(inspected_rvh); | 708 content::WebContents::FromRenderViewHost(inspected_rvh); |
| 670 if (!FindInspectedBrowserAndTabIndex(inspected_web_contents, | 709 if (!FindInspectedBrowserAndTabIndex(inspected_web_contents, |
| 671 &browser, &tab) || | 710 &browser, &tab) || |
| 672 browser->is_type_popup()) { | 711 browser->is_type_popup()) { |
| 673 can_dock = false; | 712 can_dock = false; |
| 674 } | 713 } |
| 675 } | 714 } |
| 676 | 715 |
| 677 // Create WebContents with devtools. | 716 // Create WebContents with devtools. |
| 678 GURL url(GetDevToolsURL(profile, frontend_url, dock_side, | 717 GURL url(GetDevToolsURL(profile, frontend_url, |
| 679 shared_worker_frontend, | 718 shared_worker_frontend, |
| 680 external_frontend, | 719 external_frontend, |
| 681 can_dock)); | 720 can_dock)); |
| 682 return new DevToolsWindow(profile, url, inspected_rvh, dock_side); | 721 return new DevToolsWindow(profile, url, inspected_rvh, can_dock); |
| 683 } | 722 } |
| 684 | 723 |
| 685 // static | 724 // static |
| 686 GURL DevToolsWindow::GetDevToolsURL(Profile* profile, | 725 GURL DevToolsWindow::GetDevToolsURL(Profile* profile, |
| 687 const GURL& base_url, | 726 const GURL& base_url, |
| 688 DevToolsDockSide dock_side, | |
| 689 bool shared_worker_frontend, | 727 bool shared_worker_frontend, |
| 690 bool external_frontend, | 728 bool external_frontend, |
| 691 bool can_dock) { | 729 bool can_dock) { |
| 692 if (base_url.SchemeIs("data")) | 730 if (base_url.SchemeIs("data")) |
| 693 return base_url; | 731 return base_url; |
| 694 | 732 |
| 695 std::string frontend_url( | 733 std::string frontend_url( |
| 696 base_url.is_empty() ? chrome::kChromeUIDevToolsURL : base_url.spec()); | 734 base_url.is_empty() ? chrome::kChromeUIDevToolsURL : base_url.spec()); |
| 697 ThemeService* tp = ThemeServiceFactory::GetForProfile(profile); | 735 ThemeService* tp = ThemeServiceFactory::GetForProfile(profile); |
| 698 DCHECK(tp); | 736 DCHECK(tp); |
| 699 std::string url_string( | 737 std::string url_string( |
| 700 frontend_url + | 738 frontend_url + |
| 701 ((frontend_url.find("?") == std::string::npos) ? "?" : "&") + | 739 ((frontend_url.find("?") == std::string::npos) ? "?" : "&") + |
| 702 "dockSide=" + SideToString(dock_side) + | 740 "dockSide=undocked" + // TODO(dgozman): remove this support in M38. |
| 703 "&toolbarColor=" + | 741 "&toolbarColor=" + |
| 704 SkColorToRGBAString(tp->GetColor(ThemeProperties::COLOR_TOOLBAR)) + | 742 SkColorToRGBAString(tp->GetColor(ThemeProperties::COLOR_TOOLBAR)) + |
| 705 "&textColor=" + | 743 "&textColor=" + |
| 706 SkColorToRGBAString(tp->GetColor(ThemeProperties::COLOR_BOOKMARK_TEXT))); | 744 SkColorToRGBAString(tp->GetColor(ThemeProperties::COLOR_BOOKMARK_TEXT))); |
| 707 if (shared_worker_frontend) | 745 if (shared_worker_frontend) |
| 708 url_string += "&isSharedWorker=true"; | 746 url_string += "&isSharedWorker=true"; |
| 709 if (external_frontend) | 747 if (external_frontend) |
| 710 url_string += "&remoteFrontend=true"; | 748 url_string += "&remoteFrontend=true"; |
| 711 if (can_dock) | 749 if (can_dock) |
| 712 url_string += "&can_dock=true"; | 750 url_string += "&can_dock=true"; |
| (...skipping 25 matching lines...) Expand all Loading... |
| 738 return NULL; | 776 return NULL; |
| 739 DevToolsWindows* instances = &g_instances.Get(); | 777 DevToolsWindows* instances = &g_instances.Get(); |
| 740 for (DevToolsWindows::iterator it(instances->begin()); it != instances->end(); | 778 for (DevToolsWindows::iterator it(instances->begin()); it != instances->end(); |
| 741 ++it) { | 779 ++it) { |
| 742 if ((*it)->web_contents_->GetRenderViewHost() == window_rvh) | 780 if ((*it)->web_contents_->GetRenderViewHost() == window_rvh) |
| 743 return *it; | 781 return *it; |
| 744 } | 782 } |
| 745 return NULL; | 783 return NULL; |
| 746 } | 784 } |
| 747 | 785 |
| 786 // TODO(dgozman): remove after switch to SetIsDocked. |
| 748 // static | 787 // static |
| 749 DevToolsDockSide DevToolsWindow::GetDockSideFromPrefs(Profile* profile) { | 788 bool DevToolsWindow::IsDockedFromString(const std::string& dock_side) { |
| 750 std::string dock_side = | 789 return dock_side != kDockSideUndocked; |
| 751 profile->GetPrefs()->GetString(prefs::kDevToolsDockSide); | |
| 752 | |
| 753 // Migrate prefs. | |
| 754 const char kOldPrefBottom[] = "bottom"; | |
| 755 const char kOldPrefRight[] = "right"; | |
| 756 if ((dock_side == kOldPrefBottom) || (dock_side == kOldPrefRight)) { | |
| 757 if (!profile->GetPrefs()->GetBoolean(prefs::kDevToolsOpenDocked)) | |
| 758 return DEVTOOLS_DOCK_SIDE_UNDOCKED; | |
| 759 return (dock_side == kOldPrefBottom) ? | |
| 760 DEVTOOLS_DOCK_SIDE_BOTTOM : DEVTOOLS_DOCK_SIDE_RIGHT; | |
| 761 } | |
| 762 | |
| 763 if (dock_side == kPrefUndocked) | |
| 764 return DEVTOOLS_DOCK_SIDE_UNDOCKED; | |
| 765 if (dock_side == kPrefRight) | |
| 766 return DEVTOOLS_DOCK_SIDE_RIGHT; | |
| 767 // Default to docked to bottom. | |
| 768 return DEVTOOLS_DOCK_SIDE_BOTTOM; | |
| 769 } | |
| 770 | |
| 771 // static | |
| 772 std::string DevToolsWindow::SideToString(DevToolsDockSide dock_side) { | |
| 773 switch (dock_side) { | |
| 774 case DEVTOOLS_DOCK_SIDE_UNDOCKED: return kDockSideUndocked; | |
| 775 case DEVTOOLS_DOCK_SIDE_RIGHT: return kDockSideRight; | |
| 776 case DEVTOOLS_DOCK_SIDE_BOTTOM: return kDockSideBottom; | |
| 777 case DEVTOOLS_DOCK_SIDE_MINIMIZED: return kDockSideMinimized; | |
| 778 default: return kDockSideUndocked; | |
| 779 } | |
| 780 } | |
| 781 | |
| 782 // static | |
| 783 DevToolsDockSide DevToolsWindow::SideFromString( | |
| 784 const std::string& dock_side) { | |
| 785 if (dock_side == kDockSideRight) | |
| 786 return DEVTOOLS_DOCK_SIDE_RIGHT; | |
| 787 if (dock_side == kDockSideBottom) | |
| 788 return DEVTOOLS_DOCK_SIDE_BOTTOM; | |
| 789 return (dock_side == kDockSideMinimized) ? | |
| 790 DEVTOOLS_DOCK_SIDE_MINIMIZED : DEVTOOLS_DOCK_SIDE_UNDOCKED; | |
| 791 } | 790 } |
| 792 | 791 |
| 793 void DevToolsWindow::Observe(int type, | 792 void DevToolsWindow::Observe(int type, |
| 794 const content::NotificationSource& source, | 793 const content::NotificationSource& source, |
| 795 const content::NotificationDetails& details) { | 794 const content::NotificationDetails& details) { |
| 796 DCHECK_EQ(chrome::NOTIFICATION_BROWSER_THEME_CHANGED, type); | 795 DCHECK_EQ(chrome::NOTIFICATION_BROWSER_THEME_CHANGED, type); |
| 797 UpdateTheme(); | 796 UpdateTheme(); |
| 798 } | 797 } |
| 799 | 798 |
| 800 content::WebContents* DevToolsWindow::OpenURLFromTab( | 799 content::WebContents* DevToolsWindow::OpenURLFromTab( |
| (...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 833 bool* was_blocked) { | 832 bool* was_blocked) { |
| 834 content::WebContents* inspected_web_contents = GetInspectedWebContents(); | 833 content::WebContents* inspected_web_contents = GetInspectedWebContents(); |
| 835 if (inspected_web_contents) { | 834 if (inspected_web_contents) { |
| 836 inspected_web_contents->GetDelegate()->AddNewContents( | 835 inspected_web_contents->GetDelegate()->AddNewContents( |
| 837 source, new_contents, disposition, initial_pos, user_gesture, | 836 source, new_contents, disposition, initial_pos, user_gesture, |
| 838 was_blocked); | 837 was_blocked); |
| 839 } | 838 } |
| 840 } | 839 } |
| 841 | 840 |
| 842 void DevToolsWindow::CloseContents(content::WebContents* source) { | 841 void DevToolsWindow::CloseContents(content::WebContents* source) { |
| 843 CHECK(IsDocked()); | 842 CHECK(is_docked_); |
| 843 // This will prevent any activity after frontend is loaded. |
| 844 action_on_load_ = DevToolsToggleAction::NoOp(); |
| 844 // Update dev tools to reflect removed dev tools window. | 845 // Update dev tools to reflect removed dev tools window. |
| 845 BrowserWindow* inspected_window = GetInspectedBrowserWindow(); | 846 BrowserWindow* inspected_window = GetInspectedBrowserWindow(); |
| 846 if (inspected_window) | 847 if (inspected_window) |
| 847 inspected_window->UpdateDevTools(); | 848 inspected_window->UpdateDevTools(); |
| 848 // In case of docked web_contents_, we own it so delete here. | 849 // In case of docked web_contents_, we own it so delete here. |
| 849 // Embedding DevTools window will be deleted as a result of | 850 // Embedding DevTools window will be deleted as a result of |
| 850 // WebContentsDestroyed callback. | 851 // WebContentsDestroyed callback. |
| 851 delete web_contents_; | 852 delete web_contents_; |
| 852 } | 853 } |
| 853 | 854 |
| (...skipping 19 matching lines...) Expand all Loading... |
| 873 DCHECK(!should_proceed); | 874 DCHECK(!should_proceed); |
| 874 } | 875 } |
| 875 *proceed_to_fire_unload = false; | 876 *proceed_to_fire_unload = false; |
| 876 } | 877 } |
| 877 } | 878 } |
| 878 | 879 |
| 879 bool DevToolsWindow::PreHandleKeyboardEvent( | 880 bool DevToolsWindow::PreHandleKeyboardEvent( |
| 880 content::WebContents* source, | 881 content::WebContents* source, |
| 881 const content::NativeWebKeyboardEvent& event, | 882 const content::NativeWebKeyboardEvent& event, |
| 882 bool* is_keyboard_shortcut) { | 883 bool* is_keyboard_shortcut) { |
| 883 if (IsDocked()) { | 884 if (is_docked_) { |
| 884 BrowserWindow* inspected_window = GetInspectedBrowserWindow(); | 885 BrowserWindow* inspected_window = GetInspectedBrowserWindow(); |
| 885 if (inspected_window) { | 886 if (inspected_window) { |
| 886 return inspected_window->PreHandleKeyboardEvent(event, | 887 return inspected_window->PreHandleKeyboardEvent(event, |
| 887 is_keyboard_shortcut); | 888 is_keyboard_shortcut); |
| 888 } | 889 } |
| 889 } | 890 } |
| 890 return false; | 891 return false; |
| 891 } | 892 } |
| 892 | 893 |
| 893 void DevToolsWindow::HandleKeyboardEvent( | 894 void DevToolsWindow::HandleKeyboardEvent( |
| 894 content::WebContents* source, | 895 content::WebContents* source, |
| 895 const content::NativeWebKeyboardEvent& event) { | 896 const content::NativeWebKeyboardEvent& event) { |
| 896 if (IsDocked()) { | 897 if (is_docked_) { |
| 897 if (event.windowsKeyCode == 0x08) { | 898 if (event.windowsKeyCode == 0x08) { |
| 898 // Do not navigate back in history on Windows (http://crbug.com/74156). | 899 // Do not navigate back in history on Windows (http://crbug.com/74156). |
| 899 return; | 900 return; |
| 900 } | 901 } |
| 901 BrowserWindow* inspected_window = GetInspectedBrowserWindow(); | 902 BrowserWindow* inspected_window = GetInspectedBrowserWindow(); |
| 902 if (inspected_window) | 903 if (inspected_window) |
| 903 inspected_window->HandleKeyboardEvent(event); | 904 inspected_window->HandleKeyboardEvent(event); |
| 904 } | 905 } |
| 905 } | 906 } |
| 906 | 907 |
| (...skipping 12 matching lines...) Expand all Loading... |
| 919 } | 920 } |
| 920 | 921 |
| 921 void DevToolsWindow::RunFileChooser(content::WebContents* web_contents, | 922 void DevToolsWindow::RunFileChooser(content::WebContents* web_contents, |
| 922 const content::FileChooserParams& params) { | 923 const content::FileChooserParams& params) { |
| 923 FileSelectHelper::RunFileChooser(web_contents, params); | 924 FileSelectHelper::RunFileChooser(web_contents, params); |
| 924 } | 925 } |
| 925 | 926 |
| 926 void DevToolsWindow::WebContentsFocused(content::WebContents* contents) { | 927 void DevToolsWindow::WebContentsFocused(content::WebContents* contents) { |
| 927 Browser* inspected_browser = NULL; | 928 Browser* inspected_browser = NULL; |
| 928 int inspected_tab_index = -1; | 929 int inspected_tab_index = -1; |
| 929 if (IsDocked() && FindInspectedBrowserAndTabIndex(GetInspectedWebContents(), | 930 if (is_docked_ && FindInspectedBrowserAndTabIndex(GetInspectedWebContents(), |
| 930 &inspected_browser, | 931 &inspected_browser, |
| 931 &inspected_tab_index)) | 932 &inspected_tab_index)) |
| 932 inspected_browser->window()->WebContentsFocused(contents); | 933 inspected_browser->window()->WebContentsFocused(contents); |
| 933 } | 934 } |
| 934 | 935 |
| 935 void DevToolsWindow::DispatchOnEmbedder(const std::string& message) { | 936 void DevToolsWindow::DispatchOnEmbedder(const std::string& message) { |
| 936 std::string method; | 937 std::string method; |
| 937 base::ListValue empty_params; | 938 base::ListValue empty_params; |
| 938 base::ListValue* params = &empty_params; | 939 base::ListValue* params = &empty_params; |
| 939 | 940 |
| (...skipping 14 matching lines...) Expand all Loading... |
| 954 std::string error = embedder_message_dispatcher_->Dispatch(method, params); | 955 std::string error = embedder_message_dispatcher_->Dispatch(method, params); |
| 955 if (id) { | 956 if (id) { |
| 956 scoped_ptr<base::Value> id_value(base::Value::CreateIntegerValue(id)); | 957 scoped_ptr<base::Value> id_value(base::Value::CreateIntegerValue(id)); |
| 957 scoped_ptr<base::Value> error_value(base::Value::CreateStringValue(error)); | 958 scoped_ptr<base::Value> error_value(base::Value::CreateStringValue(error)); |
| 958 CallClientFunction("InspectorFrontendAPI.embedderMessageAck", | 959 CallClientFunction("InspectorFrontendAPI.embedderMessageAck", |
| 959 id_value.get(), error_value.get(), NULL); | 960 id_value.get(), error_value.get(), NULL); |
| 960 } | 961 } |
| 961 } | 962 } |
| 962 | 963 |
| 963 void DevToolsWindow::ActivateWindow() { | 964 void DevToolsWindow::ActivateWindow() { |
| 964 if (IsDocked() && GetInspectedBrowserWindow()) | 965 if (is_docked_ && GetInspectedBrowserWindow()) |
| 965 web_contents_->GetView()->Focus(); | 966 web_contents_->GetView()->Focus(); |
| 966 else if (!IsDocked() && !browser_->window()->IsActive()) | 967 else if (!is_docked_ && !browser_->window()->IsActive()) |
| 967 browser_->window()->Activate(); | 968 browser_->window()->Activate(); |
| 968 } | 969 } |
| 969 | 970 |
| 970 void DevToolsWindow::ActivateContents(content::WebContents* contents) { | 971 void DevToolsWindow::ActivateContents(content::WebContents* contents) { |
| 971 if (IsDocked()) { | 972 if (is_docked_) { |
| 972 content::WebContents* inspected_tab = this->GetInspectedWebContents(); | 973 content::WebContents* inspected_tab = this->GetInspectedWebContents(); |
| 973 inspected_tab->GetDelegate()->ActivateContents(inspected_tab); | 974 inspected_tab->GetDelegate()->ActivateContents(inspected_tab); |
| 974 } else { | 975 } else { |
| 975 browser_->window()->Activate(); | 976 browser_->window()->Activate(); |
| 976 } | 977 } |
| 977 } | 978 } |
| 978 | 979 |
| 979 void DevToolsWindow::CloseWindow() { | 980 void DevToolsWindow::CloseWindow() { |
| 980 DCHECK(IsDocked()); | 981 DCHECK(is_docked_); |
| 982 // This will prevent any activity after frontend is loaded. |
| 983 action_on_load_ = DevToolsToggleAction::NoOp(); |
| 981 web_contents_->GetRenderViewHost()->FirePageBeforeUnload(false); | 984 web_contents_->GetRenderViewHost()->FirePageBeforeUnload(false); |
| 982 } | 985 } |
| 983 | 986 |
| 984 void DevToolsWindow::SetContentsInsets( | 987 void DevToolsWindow::SetContentsInsets( |
| 985 int top, int left, int bottom, int right) { | 988 int top, int left, int bottom, int right) { |
| 986 if (contents_insets_.top() == top && | 989 if (contents_insets_.top() == top && |
| 987 contents_insets_.left() == left && | 990 contents_insets_.left() == left && |
| 988 contents_insets_.bottom() == bottom && | 991 contents_insets_.bottom() == bottom && |
| 989 contents_insets_.right() == right) { | 992 contents_insets_.right() == right) { |
| 990 return; | 993 return; |
| 991 } | 994 } |
| 992 | 995 |
| 993 contents_insets_ = gfx::Insets(top, left, bottom, right); | 996 contents_insets_ = gfx::Insets(top, left, bottom, right); |
| 994 if (IsDocked()) { | 997 if (is_docked_) { |
| 995 // Update inspected window. | 998 // Update inspected window. |
| 996 BrowserWindow* inspected_window = GetInspectedBrowserWindow(); | 999 BrowserWindow* inspected_window = GetInspectedBrowserWindow(); |
| 997 if (inspected_window) | 1000 if (inspected_window) |
| 998 inspected_window->UpdateDevTools(); | 1001 inspected_window->UpdateDevTools(); |
| 999 } | 1002 } |
| 1000 } | 1003 } |
| 1001 | 1004 |
| 1002 void DevToolsWindow::MoveWindow(int x, int y) { | 1005 void DevToolsWindow::MoveWindow(int x, int y) { |
| 1003 if (!IsDocked()) { | 1006 if (!is_docked_) { |
| 1004 gfx::Rect bounds = browser_->window()->GetBounds(); | 1007 gfx::Rect bounds = browser_->window()->GetBounds(); |
| 1005 bounds.Offset(x, y); | 1008 bounds.Offset(x, y); |
| 1006 browser_->window()->SetBounds(bounds); | 1009 browser_->window()->SetBounds(bounds); |
| 1007 } | 1010 } |
| 1008 } | 1011 } |
| 1009 | 1012 |
| 1013 void DevToolsWindow::SetIsDockedAndShowImmediatelyForTest(bool is_docked) { |
| 1014 DCHECK(!is_docked || can_dock_); |
| 1015 if (load_state_ == kLoadCompleted) { |
| 1016 SetIsDocked(is_docked); |
| 1017 } else { |
| 1018 is_docked_ = is_docked; |
| 1019 load_state_ = load_state_ == kNotLoaded ? kIsDockedSet : kLoadCompleted; |
| 1020 // Note that action_on_load_ will be performed after the load is actually |
| 1021 // completed. For now, just show the window. |
| 1022 Show(DevToolsToggleAction::Show()); |
| 1023 if (load_state_ == kLoadCompleted) |
| 1024 LoadCompleted(); |
| 1025 } |
| 1026 ignore_set_is_docked_for_test_ = true; |
| 1027 } |
| 1028 |
| 1010 void DevToolsWindow::SetDockSide(const std::string& side) { | 1029 void DevToolsWindow::SetDockSide(const std::string& side) { |
| 1011 DevToolsDockSide requested_side = SideFromString(side); | 1030 // TODO(dgozman): remove this method after frontend switches to SetIsDocked. |
| 1012 bool dock_requested = requested_side != DEVTOOLS_DOCK_SIDE_UNDOCKED; | 1031 SetIsDocked(IsDockedFromString(side)); |
| 1013 bool is_docked = IsDocked(); | 1032 } |
| 1014 | 1033 |
| 1015 if (dock_requested && | 1034 void DevToolsWindow::SetIsDocked(bool dock_requested) { |
| 1016 (!GetInspectedWebContents() || !GetInspectedBrowserWindow() || | 1035 if (ignore_set_is_docked_for_test_) |
| 1017 IsInspectedBrowserPopup())) { | 1036 return; |
| 1018 // Cannot dock, avoid window flashing due to close-reopen cycle. | 1037 |
| 1038 DCHECK(can_dock_ || !dock_requested); |
| 1039 if (!can_dock_) |
| 1040 dock_requested = false; |
| 1041 |
| 1042 bool was_docked = is_docked_; |
| 1043 is_docked_ = dock_requested; |
| 1044 |
| 1045 if (load_state_ != kLoadCompleted) { |
| 1046 // This is a first time call we waited for to initialize. |
| 1047 load_state_ = load_state_ == kNotLoaded ? kIsDockedSet : kLoadCompleted; |
| 1048 if (load_state_ == kLoadCompleted) |
| 1049 LoadCompleted(); |
| 1019 return; | 1050 return; |
| 1020 } | 1051 } |
| 1021 | 1052 |
| 1022 if ((dock_side_ != DEVTOOLS_DOCK_SIDE_MINIMIZED) && | 1053 if (dock_requested == was_docked) |
| 1023 (requested_side == DEVTOOLS_DOCK_SIDE_MINIMIZED)) | 1054 return; |
| 1024 dock_side_before_minimized_ = dock_side_; | |
| 1025 | 1055 |
| 1026 dock_side_ = requested_side; | 1056 if (dock_requested && !was_docked) { |
| 1027 if (dock_requested && !is_docked) { | |
| 1028 // Detach window from the external devtools browser. It will lead to | 1057 // Detach window from the external devtools browser. It will lead to |
| 1029 // the browser object's close and delete. Remove observer first. | 1058 // the browser object's close and delete. Remove observer first. |
| 1030 TabStripModel* tab_strip_model = browser_->tab_strip_model(); | 1059 TabStripModel* tab_strip_model = browser_->tab_strip_model(); |
| 1031 tab_strip_model->DetachWebContentsAt( | 1060 tab_strip_model->DetachWebContentsAt( |
| 1032 tab_strip_model->GetIndexOfWebContents(web_contents_)); | 1061 tab_strip_model->GetIndexOfWebContents(web_contents_)); |
| 1033 browser_ = NULL; | 1062 browser_ = NULL; |
| 1034 } else if (!dock_requested && is_docked) { | 1063 } else if (!dock_requested && was_docked) { |
| 1035 // Update inspected window to hide split and reset it. | 1064 // Update inspected window to hide split and reset it. |
| 1036 BrowserWindow* inspected_window = GetInspectedBrowserWindow(); | 1065 BrowserWindow* inspected_window = GetInspectedBrowserWindow(); |
| 1037 if (inspected_window) | 1066 if (inspected_window) |
| 1038 inspected_window->UpdateDevTools(); | 1067 inspected_window->UpdateDevTools(); |
| 1039 } | 1068 } |
| 1040 | 1069 |
| 1041 if (dock_side_ != DEVTOOLS_DOCK_SIDE_MINIMIZED) { | |
| 1042 std::string pref_value = kPrefBottom; | |
| 1043 switch (dock_side_) { | |
| 1044 case DEVTOOLS_DOCK_SIDE_UNDOCKED: | |
| 1045 pref_value = kPrefUndocked; | |
| 1046 break; | |
| 1047 case DEVTOOLS_DOCK_SIDE_RIGHT: | |
| 1048 pref_value = kPrefRight; | |
| 1049 break; | |
| 1050 case DEVTOOLS_DOCK_SIDE_BOTTOM: | |
| 1051 pref_value = kPrefBottom; | |
| 1052 break; | |
| 1053 case DEVTOOLS_DOCK_SIDE_MINIMIZED: | |
| 1054 // We don't persist minimized state. | |
| 1055 break; | |
| 1056 } | |
| 1057 profile_->GetPrefs()->SetString(prefs::kDevToolsDockSide, pref_value); | |
| 1058 } | |
| 1059 | |
| 1060 Show(DevToolsToggleAction::Show()); | 1070 Show(DevToolsToggleAction::Show()); |
| 1061 } | 1071 } |
| 1062 | 1072 |
| 1063 void DevToolsWindow::OpenInNewTab(const std::string& url) { | 1073 void DevToolsWindow::OpenInNewTab(const std::string& url) { |
| 1064 content::OpenURLParams params( | 1074 content::OpenURLParams params( |
| 1065 GURL(url), content::Referrer(), NEW_FOREGROUND_TAB, | 1075 GURL(url), content::Referrer(), NEW_FOREGROUND_TAB, |
| 1066 content::PAGE_TRANSITION_LINK, false); | 1076 content::PAGE_TRANSITION_LINK, false); |
| 1067 content::WebContents* inspected_web_contents = GetInspectedWebContents(); | 1077 content::WebContents* inspected_web_contents = GetInspectedWebContents(); |
| 1068 if (inspected_web_contents) { | 1078 if (inspected_web_contents) { |
| 1069 inspected_web_contents->OpenURL(params); | 1079 inspected_web_contents->OpenURL(params); |
| (...skipping 205 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1275 base::FundamentalValue request_id_value(request_id); | 1285 base::FundamentalValue request_id_value(request_id); |
| 1276 base::StringValue file_system_path_value(file_system_path); | 1286 base::StringValue file_system_path_value(file_system_path); |
| 1277 CallClientFunction("InspectorFrontendAPI.searchCompleted", &request_id_value, | 1287 CallClientFunction("InspectorFrontendAPI.searchCompleted", &request_id_value, |
| 1278 &file_system_path_value, &file_paths_value); | 1288 &file_system_path_value, &file_paths_value); |
| 1279 } | 1289 } |
| 1280 | 1290 |
| 1281 void DevToolsWindow::ShowDevToolsConfirmInfoBar( | 1291 void DevToolsWindow::ShowDevToolsConfirmInfoBar( |
| 1282 const base::string16& message, | 1292 const base::string16& message, |
| 1283 const InfoBarCallback& callback) { | 1293 const InfoBarCallback& callback) { |
| 1284 DevToolsConfirmInfoBarDelegate::Create( | 1294 DevToolsConfirmInfoBarDelegate::Create( |
| 1285 IsDocked() ? | 1295 is_docked_ ? |
| 1286 InfoBarService::FromWebContents(GetInspectedWebContents()) : | 1296 InfoBarService::FromWebContents(GetInspectedWebContents()) : |
| 1287 InfoBarService::FromWebContents(web_contents_), | 1297 InfoBarService::FromWebContents(web_contents_), |
| 1288 callback, message); | 1298 callback, message); |
| 1289 } | 1299 } |
| 1290 | 1300 |
| 1291 void DevToolsWindow::CreateDevToolsBrowser() { | 1301 void DevToolsWindow::CreateDevToolsBrowser() { |
| 1292 std::string wp_key = GetDevToolsWindowPlacementPrefKey(); | 1302 std::string wp_key = GetDevToolsWindowPlacementPrefKey(); |
| 1293 PrefService* prefs = profile_->GetPrefs(); | 1303 PrefService* prefs = profile_->GetPrefs(); |
| 1294 const base::DictionaryValue* wp_pref = prefs->GetDictionary(wp_key.c_str()); | 1304 const base::DictionaryValue* wp_pref = prefs->GetDictionary(wp_key.c_str()); |
| 1295 if (!wp_pref || wp_pref->empty()) { | 1305 if (!wp_pref || wp_pref->empty()) { |
| (...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1332 } | 1342 } |
| 1333 | 1343 |
| 1334 BrowserWindow* DevToolsWindow::GetInspectedBrowserWindow() { | 1344 BrowserWindow* DevToolsWindow::GetInspectedBrowserWindow() { |
| 1335 Browser* browser = NULL; | 1345 Browser* browser = NULL; |
| 1336 int tab; | 1346 int tab; |
| 1337 return FindInspectedBrowserAndTabIndex(GetInspectedWebContents(), | 1347 return FindInspectedBrowserAndTabIndex(GetInspectedWebContents(), |
| 1338 &browser, &tab) ? | 1348 &browser, &tab) ? |
| 1339 browser->window() : NULL; | 1349 browser->window() : NULL; |
| 1340 } | 1350 } |
| 1341 | 1351 |
| 1342 bool DevToolsWindow::IsInspectedBrowserPopup() { | 1352 void DevToolsWindow::DoAction(const DevToolsToggleAction& action) { |
| 1343 Browser* browser = NULL; | 1353 switch (action.type()) { |
| 1344 int tab; | |
| 1345 return FindInspectedBrowserAndTabIndex(GetInspectedWebContents(), | |
| 1346 &browser, &tab) && | |
| 1347 browser->is_type_popup(); | |
| 1348 } | |
| 1349 | |
| 1350 void DevToolsWindow::UpdateFrontendDockSide() { | |
| 1351 base::StringValue dock_side(SideToString(dock_side_)); | |
| 1352 CallClientFunction("InspectorFrontendAPI.setDockSide", &dock_side, NULL, | |
| 1353 NULL); | |
| 1354 base::FundamentalValue docked(IsDocked()); | |
| 1355 CallClientFunction("InspectorFrontendAPI.setAttachedWindow", &docked, NULL, | |
| 1356 NULL); | |
| 1357 } | |
| 1358 | |
| 1359 void DevToolsWindow::ScheduleAction(const DevToolsToggleAction& action) { | |
| 1360 action_on_load_ = action; | |
| 1361 if (is_loaded_) | |
| 1362 DoAction(); | |
| 1363 } | |
| 1364 | |
| 1365 void DevToolsWindow::DoAction() { | |
| 1366 UpdateFrontendDockSide(); | |
| 1367 switch (action_on_load_.type()) { | |
| 1368 case DevToolsToggleAction::kShowConsole: | 1354 case DevToolsToggleAction::kShowConsole: |
| 1369 CallClientFunction("InspectorFrontendAPI.showConsole", NULL, NULL, NULL); | 1355 CallClientFunction("InspectorFrontendAPI.showConsole", NULL, NULL, NULL); |
| 1370 break; | 1356 break; |
| 1371 | 1357 |
| 1372 case DevToolsToggleAction::kInspect: | 1358 case DevToolsToggleAction::kInspect: |
| 1373 CallClientFunction("InspectorFrontendAPI.enterInspectElementMode", NULL, | 1359 CallClientFunction("InspectorFrontendAPI.enterInspectElementMode", NULL, |
| 1374 NULL, NULL); | 1360 NULL, NULL); |
| 1375 break; | 1361 break; |
| 1376 | 1362 |
| 1377 case DevToolsToggleAction::kShow: | 1363 case DevToolsToggleAction::kShow: |
| 1378 case DevToolsToggleAction::kToggle: | 1364 case DevToolsToggleAction::kToggle: |
| 1379 // Do nothing. | 1365 // Do nothing. |
| 1380 break; | 1366 break; |
| 1381 | 1367 |
| 1382 case DevToolsToggleAction::kReveal: { | 1368 case DevToolsToggleAction::kReveal: { |
| 1383 const DevToolsToggleAction::RevealParams* params = | 1369 const DevToolsToggleAction::RevealParams* params = |
| 1384 action_on_load_.params(); | 1370 action.params(); |
| 1385 CHECK(params); | 1371 CHECK(params); |
| 1386 base::StringValue url_value(params->url); | 1372 base::StringValue url_value(params->url); |
| 1387 base::FundamentalValue line_value(static_cast<int>(params->line_number)); | 1373 base::FundamentalValue line_value(static_cast<int>(params->line_number)); |
| 1388 base::FundamentalValue column_value( | 1374 base::FundamentalValue column_value( |
| 1389 static_cast<int>(params->column_number)); | 1375 static_cast<int>(params->column_number)); |
| 1390 CallClientFunction("InspectorFrontendAPI.revealSourceLine", | 1376 CallClientFunction("InspectorFrontendAPI.revealSourceLine", |
| 1391 &url_value, | 1377 &url_value, |
| 1392 &line_value, | 1378 &line_value, |
| 1393 &column_value); | 1379 &column_value); |
| 1394 break; | 1380 break; |
| 1395 } | 1381 } |
| 1396 default: | 1382 default: |
| 1397 NOTREACHED(); | 1383 NOTREACHED(); |
| 1398 break; | 1384 break; |
| 1399 } | 1385 } |
| 1400 action_on_load_ = DevToolsToggleAction::Show(); | |
| 1401 } | 1386 } |
| 1402 | 1387 |
| 1403 void DevToolsWindow::UpdateTheme() { | 1388 void DevToolsWindow::UpdateTheme() { |
| 1404 ThemeService* tp = ThemeServiceFactory::GetForProfile(profile_); | 1389 ThemeService* tp = ThemeServiceFactory::GetForProfile(profile_); |
| 1405 DCHECK(tp); | 1390 DCHECK(tp); |
| 1406 | 1391 |
| 1407 std::string command("InspectorFrontendAPI.setToolbarColors(\"" + | 1392 std::string command("InspectorFrontendAPI.setToolbarColors(\"" + |
| 1408 SkColorToRGBAString(tp->GetColor(ThemeProperties::COLOR_TOOLBAR)) + | 1393 SkColorToRGBAString(tp->GetColor(ThemeProperties::COLOR_TOOLBAR)) + |
| 1409 "\", \"" + | 1394 "\", \"" + |
| 1410 SkColorToRGBAString(tp->GetColor(ThemeProperties::COLOR_BOOKMARK_TEXT)) + | 1395 SkColorToRGBAString(tp->GetColor(ThemeProperties::COLOR_BOOKMARK_TEXT)) + |
| (...skipping 64 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1475 web_contents_->GetRenderViewHost()->ExecuteJavascriptInWebFrame( | 1460 web_contents_->GetRenderViewHost()->ExecuteJavascriptInWebFrame( |
| 1476 base::string16(), javascript); | 1461 base::string16(), javascript); |
| 1477 } | 1462 } |
| 1478 | 1463 |
| 1479 void DevToolsWindow::UpdateBrowserToolbar() { | 1464 void DevToolsWindow::UpdateBrowserToolbar() { |
| 1480 BrowserWindow* inspected_window = GetInspectedBrowserWindow(); | 1465 BrowserWindow* inspected_window = GetInspectedBrowserWindow(); |
| 1481 if (inspected_window) | 1466 if (inspected_window) |
| 1482 inspected_window->UpdateToolbar(NULL); | 1467 inspected_window->UpdateToolbar(NULL); |
| 1483 } | 1468 } |
| 1484 | 1469 |
| 1485 bool DevToolsWindow::IsDocked() { | |
| 1486 return dock_side_ != DEVTOOLS_DOCK_SIDE_UNDOCKED; | |
| 1487 } | |
| 1488 | |
| 1489 void DevToolsWindow::Restore() { | |
| 1490 if (dock_side_ == DEVTOOLS_DOCK_SIDE_MINIMIZED) | |
| 1491 SetDockSide(SideToString(dock_side_before_minimized_)); | |
| 1492 } | |
| 1493 | |
| 1494 content::WebContents* DevToolsWindow::GetInspectedWebContents() { | 1470 content::WebContents* DevToolsWindow::GetInspectedWebContents() { |
| 1495 return inspected_contents_observer_ ? | 1471 return inspected_contents_observer_ ? |
| 1496 inspected_contents_observer_->web_contents() : NULL; | 1472 inspected_contents_observer_->web_contents() : NULL; |
| 1497 } | 1473 } |
| 1498 | 1474 |
| 1499 void DevToolsWindow::DocumentOnLoadCompletedInMainFrame() { | 1475 void DevToolsWindow::DocumentOnLoadCompletedInMainFrame() { |
| 1500 is_loaded_ = true; | 1476 load_state_ = load_state_ == kNotLoaded ? kOnLoadFired : kLoadCompleted; |
| 1477 if (load_state_ == kLoadCompleted) |
| 1478 LoadCompleted(); |
| 1479 } |
| 1480 |
| 1481 void DevToolsWindow::LoadCompleted() { |
| 1482 Show(action_on_load_); |
| 1483 action_on_load_ = DevToolsToggleAction::NoOp(); |
| 1501 UpdateTheme(); | 1484 UpdateTheme(); |
| 1502 DoAction(); | |
| 1503 AddDevToolsExtensionsToClient(); | 1485 AddDevToolsExtensionsToClient(); |
| 1504 } | 1486 } |
| OLD | NEW |