Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1071)

Side by Side Diff: headless/lib/browser/headless_devtools_manager_delegate.cc

Issue 2896763002: Implement window management devtools commands for headless. (Closed)
Patch Set: nit and rebase Created 3 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2016 The Chromium Authors. All rights reserved. 1 // Copyright 2016 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 "headless/lib/browser/headless_devtools_manager_delegate.h" 5 #include "headless/lib/browser/headless_devtools_manager_delegate.h"
6 6
7 #include <string> 7 #include <string>
8 #include <utility> 8 #include <utility>
9 9
10 #include "content/public/browser/browser_thread.h" 10 #include "content/public/browser/browser_thread.h"
11 #include "content/public/browser/devtools_agent_host.h" 11 #include "content/public/browser/devtools_agent_host.h"
12 #include "content/public/browser/devtools_frontend_host.h" 12 #include "content/public/browser/devtools_frontend_host.h"
13 #include "content/public/browser/render_widget_host_view.h"
13 #include "content/public/browser/web_contents.h" 14 #include "content/public/browser/web_contents.h"
14 #include "headless/grit/headless_lib_resources.h" 15 #include "headless/grit/headless_lib_resources.h"
15 #include "headless/lib/browser/headless_browser_context_impl.h" 16 #include "headless/lib/browser/headless_browser_context_impl.h"
16 #include "headless/lib/browser/headless_browser_impl.h" 17 #include "headless/lib/browser/headless_browser_impl.h"
17 #include "headless/lib/browser/headless_web_contents_impl.h" 18 #include "headless/lib/browser/headless_web_contents_impl.h"
18 #include "headless/public/devtools/domains/target.h" 19 #include "headless/public/devtools/domains/target.h"
19 #include "printing/units.h" 20 #include "printing/units.h"
20 #include "ui/base/resource/resource_bundle.h" 21 #include "ui/base/resource/resource_bundle.h"
21 22
22 namespace headless { 23 namespace headless {
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after
61 } 62 }
62 63
63 std::unique_ptr<base::DictionaryValue> CreateInvalidParamResponse( 64 std::unique_ptr<base::DictionaryValue> CreateInvalidParamResponse(
64 int command_id, 65 int command_id,
65 const std::string& param) { 66 const std::string& param) {
66 return CreateErrorResponse( 67 return CreateErrorResponse(
67 command_id, kErrorInvalidParam, 68 command_id, kErrorInvalidParam,
68 base::StringPrintf("Missing or invalid '%s' parameter", param.c_str())); 69 base::StringPrintf("Missing or invalid '%s' parameter", param.c_str()));
69 } 70 }
70 71
72 std::unique_ptr<base::DictionaryValue> CreateBoundsDict(
73 const HeadlessWebContentsImpl* web_contents) {
74 auto bounds_object = base::MakeUnique<base::DictionaryValue>();
75 gfx::Rect bounds =
76 web_contents->web_contents()->GetRenderWidgetHostView()->GetViewBounds();
77 bounds_object->SetInteger("left", bounds.x());
78 bounds_object->SetInteger("top", bounds.y());
79 bounds_object->SetInteger("width", bounds.width());
80 bounds_object->SetInteger("height", bounds.height());
81 bounds_object->SetString("windowState", web_contents->window_state());
82 return bounds_object;
83 }
84
71 #if BUILDFLAG(ENABLE_BASIC_PRINTING) 85 #if BUILDFLAG(ENABLE_BASIC_PRINTING)
72 void PDFCreated( 86 void PDFCreated(
73 const content::DevToolsManagerDelegate::CommandCallback& callback, 87 const content::DevToolsManagerDelegate::CommandCallback& callback,
74 int command_id, 88 int command_id,
75 printing::HeadlessPrintManager::PrintResult print_result, 89 printing::HeadlessPrintManager::PrintResult print_result,
76 const std::string& data) { 90 const std::string& data) {
77 std::unique_ptr<base::DictionaryValue> response; 91 std::unique_ptr<base::DictionaryValue> response;
78 if (print_result == printing::HeadlessPrintManager::PRINT_SUCCESS) { 92 if (print_result == printing::HeadlessPrintManager::PRINT_SUCCESS) {
79 response = CreateSuccessResponse( 93 response = CreateSuccessResponse(
80 command_id, 94 command_id,
(...skipping 81 matching lines...) Expand 10 before | Expand all | Expand 10 after
162 command_map_["Target.createTarget"] = base::Bind( 176 command_map_["Target.createTarget"] = base::Bind(
163 &HeadlessDevToolsManagerDelegate::CreateTarget, base::Unretained(this)); 177 &HeadlessDevToolsManagerDelegate::CreateTarget, base::Unretained(this));
164 command_map_["Target.closeTarget"] = base::Bind( 178 command_map_["Target.closeTarget"] = base::Bind(
165 &HeadlessDevToolsManagerDelegate::CloseTarget, base::Unretained(this)); 179 &HeadlessDevToolsManagerDelegate::CloseTarget, base::Unretained(this));
166 command_map_["Target.createBrowserContext"] = 180 command_map_["Target.createBrowserContext"] =
167 base::Bind(&HeadlessDevToolsManagerDelegate::CreateBrowserContext, 181 base::Bind(&HeadlessDevToolsManagerDelegate::CreateBrowserContext,
168 base::Unretained(this)); 182 base::Unretained(this));
169 command_map_["Target.disposeBrowserContext"] = 183 command_map_["Target.disposeBrowserContext"] =
170 base::Bind(&HeadlessDevToolsManagerDelegate::DisposeBrowserContext, 184 base::Bind(&HeadlessDevToolsManagerDelegate::DisposeBrowserContext,
171 base::Unretained(this)); 185 base::Unretained(this));
186 command_map_["Browser.getWindowForTarget"] =
187 base::Bind(&HeadlessDevToolsManagerDelegate::GetWindowForTarget,
188 base::Unretained(this));
189 command_map_["Browser.getWindowBounds"] =
190 base::Bind(&HeadlessDevToolsManagerDelegate::GetWindowBounds,
191 base::Unretained(this));
192 command_map_["Browser.setWindowBounds"] =
193 base::Bind(&HeadlessDevToolsManagerDelegate::SetWindowBounds,
194 base::Unretained(this));
172 195
173 async_command_map_["Page.printToPDF"] = base::Bind( 196 async_command_map_["Page.printToPDF"] = base::Bind(
174 &HeadlessDevToolsManagerDelegate::PrintToPDF, base::Unretained(this)); 197 &HeadlessDevToolsManagerDelegate::PrintToPDF, base::Unretained(this));
175 } 198 }
176 199
177 HeadlessDevToolsManagerDelegate::~HeadlessDevToolsManagerDelegate() {} 200 HeadlessDevToolsManagerDelegate::~HeadlessDevToolsManagerDelegate() {}
178 201
179 base::DictionaryValue* HeadlessDevToolsManagerDelegate::HandleCommand( 202 base::DictionaryValue* HeadlessDevToolsManagerDelegate::HandleCommand(
180 content::DevToolsAgentHost* agent_host, 203 content::DevToolsAgentHost* agent_host,
181 base::DictionaryValue* command) { 204 base::DictionaryValue* command) {
182 DCHECK_CURRENTLY_ON(content::BrowserThread::UI); 205 DCHECK_CURRENTLY_ON(content::BrowserThread::UI);
183 206
184 if (!browser_) 207 if (!browser_)
185 return nullptr; 208 return nullptr;
186 209
187 int id; 210 int id;
188 std::string method; 211 std::string method;
189 if (!command->GetInteger("id", &id) || !command->GetString("method", &method)) 212 if (!command->GetInteger("id", &id) || !command->GetString("method", &method))
190 return nullptr; 213 return nullptr;
191 214
192 auto find_it = command_map_.find(method); 215 auto find_it = command_map_.find(method);
193 if (find_it == command_map_.end()) 216 if (find_it == command_map_.end())
194 return nullptr; 217 return nullptr;
195 218
219 // Handle Browser domain commands only from Browser DevToolsAgentHost.
220 if (method.find("Browser.") == 0 &&
221 agent_host->GetType() != content::DevToolsAgentHost::kTypeBrowser)
222 return nullptr;
223
196 const base::DictionaryValue* params = nullptr; 224 const base::DictionaryValue* params = nullptr;
197 command->GetDictionary("params", &params); 225 command->GetDictionary("params", &params);
198 auto cmd_result = find_it->second.Run(id, params); 226 auto cmd_result = find_it->second.Run(id, params);
199 return cmd_result.release(); 227 return cmd_result.release();
200 } 228 }
201 229
202 bool HeadlessDevToolsManagerDelegate::HandleAsyncCommand( 230 bool HeadlessDevToolsManagerDelegate::HandleAsyncCommand(
203 content::DevToolsAgentHost* agent_host, 231 content::DevToolsAgentHost* agent_host,
204 base::DictionaryValue* command, 232 base::DictionaryValue* command,
205 const CommandCallback& callback) { 233 const CommandCallback& callback) {
(...skipping 165 matching lines...) Expand 10 before | Expand all | Expand 10 after
371 } 399 }
372 400
373 std::unique_ptr<base::Value> result( 401 std::unique_ptr<base::Value> result(
374 target::DisposeBrowserContextResult::Builder() 402 target::DisposeBrowserContextResult::Builder()
375 .SetSuccess(success) 403 .SetSuccess(success)
376 .Build() 404 .Build()
377 ->Serialize()); 405 ->Serialize());
378 return CreateSuccessResponse(command_id, std::move(result)); 406 return CreateSuccessResponse(command_id, std::move(result));
379 } 407 }
380 408
409 std::unique_ptr<base::DictionaryValue>
410 HeadlessDevToolsManagerDelegate::GetWindowForTarget(
411 int command_id,
412 const base::DictionaryValue* params) {
413 std::string target_id;
414 if (!params->GetString("targetId", &target_id))
415 return CreateInvalidParamResponse(command_id, "targetId");
416
417 HeadlessWebContentsImpl* web_contents = HeadlessWebContentsImpl::From(
418 browser_->GetWebContentsForDevToolsAgentHostId(target_id));
419 if (!web_contents) {
420 return CreateErrorResponse(command_id, kErrorServerError,
421 "No web contents for the given target id");
422 }
423
424 auto result = base::MakeUnique<base::DictionaryValue>();
425 result->SetInteger("windowId", web_contents->window_id());
426 result->Set("bounds", CreateBoundsDict(web_contents));
427 return CreateSuccessResponse(command_id, std::move(result));
428 }
429
430 std::unique_ptr<base::DictionaryValue>
431 HeadlessDevToolsManagerDelegate::GetWindowBounds(
432 int command_id,
433 const base::DictionaryValue* params) {
434 int window_id;
435 if (!params->GetInteger("windowId", &window_id))
436 return CreateInvalidParamResponse(command_id, "windowId");
437 HeadlessWebContentsImpl* web_contents =
438 browser_->GetWebContentsForWindowId(window_id);
439 if (!web_contents) {
440 return CreateErrorResponse(command_id, kErrorServerError,
441 "Browser window not found");
442 }
443
444 auto result = base::MakeUnique<base::DictionaryValue>();
445 result->Set("bounds", CreateBoundsDict(web_contents));
446 return CreateSuccessResponse(command_id, std::move(result));
447 }
448
449 std::unique_ptr<base::DictionaryValue>
450 HeadlessDevToolsManagerDelegate::SetWindowBounds(
451 int command_id,
452 const base::DictionaryValue* params) {
453 int window_id;
454 if (!params->GetInteger("windowId", &window_id))
455 return CreateInvalidParamResponse(command_id, "windowId");
456 HeadlessWebContentsImpl* web_contents =
457 browser_->GetWebContentsForWindowId(window_id);
458 if (!web_contents) {
459 return CreateErrorResponse(command_id, kErrorServerError,
460 "Browser window not found");
461 }
462
463 const base::Value* value = nullptr;
464 const base::DictionaryValue* bounds_dict = nullptr;
465 if (!params->Get("bounds", &value) || !value->GetAsDictionary(&bounds_dict))
466 return CreateInvalidParamResponse(command_id, "bounds");
467
468 std::string window_state;
469 if (!bounds_dict->GetString("windowState", &window_state)) {
470 window_state = "normal";
471 } else if (window_state != "normal" && window_state != "minimized" &&
472 window_state != "maximized" && window_state != "fullscreen") {
473 return CreateInvalidParamResponse(command_id, "windowState");
474 }
475
476 // Compute updated bounds when window state is normal.
477 bool set_bounds = false;
478 gfx::Rect bounds =
479 web_contents->web_contents()->GetRenderWidgetHostView()->GetViewBounds();
480 int left, top, width, height;
481 if (bounds_dict->GetInteger("left", &left)) {
482 bounds.set_x(left);
483 set_bounds = true;
484 }
485 if (bounds_dict->GetInteger("top", &top)) {
486 bounds.set_y(top);
487 set_bounds = true;
488 }
489 if (bounds_dict->GetInteger("width", &width)) {
490 if (width < 0)
491 return CreateInvalidParamResponse(command_id, "width");
492 bounds.set_width(width);
493 set_bounds = true;
494 }
495 if (bounds_dict->GetInteger("height", &height)) {
496 if (height < 0)
497 return CreateInvalidParamResponse(command_id, "height");
498 bounds.set_height(height);
499 set_bounds = true;
500 }
501
502 if (set_bounds && window_state != "normal") {
503 return CreateErrorResponse(
504 command_id, kErrorServerError,
505 "The 'minimized', 'maximized' and 'fullscreen' states cannot be "
506 "combined with 'left', 'top', 'width' or 'height'");
507 }
508
509 if (set_bounds && web_contents->window_state() != "normal") {
510 return CreateErrorResponse(
511 command_id, kErrorServerError,
512 "To resize minimized/maximized/fullscreen window, restore it to normal "
513 "state first.");
514 }
515
516 web_contents->set_window_state(window_state);
517 web_contents->web_contents()->GetRenderWidgetHostView()->SetBounds(bounds);
518 return CreateSuccessResponse(command_id, nullptr);
519 }
520
381 } // namespace headless 521 } // namespace headless
OLDNEW
« no previous file with comments | « headless/lib/browser/headless_devtools_manager_delegate.h ('k') | headless/lib/browser/headless_web_contents_impl.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698