OLD | NEW |
---|---|
1 // Copyright 2014 The Chromium Authors. All rights reserved. | 1 // Copyright 2014 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 "content/shell/renderer/test_runner/web_test_proxy.h" | 5 #include "content/shell/renderer/test_runner/web_test_proxy.h" |
6 | 6 |
7 #include <cctype> | 7 #include <cctype> |
8 | 8 |
9 #include "base/callback_helpers.h" | 9 #include "base/callback_helpers.h" |
10 #include "base/debug/trace_event.h" | 10 #include "base/debug/trace_event.h" |
(...skipping 294 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
305 if (m_speechRecognizer.get()) m_speechRecognizer->setDelegate(delegate); | 305 if (m_speechRecognizer.get()) m_speechRecognizer->setDelegate(delegate); |
306 } | 306 } |
307 | 307 |
308 WebView* WebTestProxyBase::GetWebView() const { | 308 WebView* WebTestProxyBase::GetWebView() const { |
309 DCHECK(web_widget_); | 309 DCHECK(web_widget_); |
310 // TestRunner does not support popup widgets. So |web_widget|_ is always a | 310 // TestRunner does not support popup widgets. So |web_widget|_ is always a |
311 // WebView. | 311 // WebView. |
312 return static_cast<WebView*>(web_widget_); | 312 return static_cast<WebView*>(web_widget_); |
313 } | 313 } |
314 | 314 |
315 void WebTestProxyBase::DidForceResize() { | |
316 InvalidateAll(); | |
317 DiscardBackingStore(); | |
318 } | |
319 | |
320 void WebTestProxyBase::Reset() { | 315 void WebTestProxyBase::Reset() { |
321 paint_rect_ = WebRect(); | |
322 canvas_.reset(); | |
323 is_painting_ = false; | |
324 animate_scheduled_ = false; | 316 animate_scheduled_ = false; |
325 resource_identifier_map_.clear(); | 317 resource_identifier_map_.clear(); |
326 log_console_output_ = true; | 318 log_console_output_ = true; |
327 if (m_midiClient.get()) m_midiClient->resetMock(); | 319 if (m_midiClient.get()) m_midiClient->resetMock(); |
328 } | 320 } |
329 | 321 |
330 WebSpellCheckClient* WebTestProxyBase::GetSpellCheckClient() const { | 322 WebSpellCheckClient* WebTestProxyBase::GetSpellCheckClient() const { |
331 return spellcheck_.get(); | 323 return spellcheck_.get(); |
332 } | 324 } |
333 | 325 |
(...skipping 87 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
421 bitmap.info().fWidth, "y", bitmap.info().fHeight); | 413 bitmap.info().fWidth, "y", bitmap.info().fHeight); |
422 SkCanvas canvas(bitmap); | 414 SkCanvas canvas(bitmap); |
423 DrawSelectionRect(&canvas); | 415 DrawSelectionRect(&canvas); |
424 DCHECK(!composite_and_readback_callbacks_.empty()); | 416 DCHECK(!composite_and_readback_callbacks_.empty()); |
425 composite_and_readback_callbacks_.front().Run(bitmap); | 417 composite_and_readback_callbacks_.front().Run(bitmap); |
426 composite_and_readback_callbacks_.pop_front(); | 418 composite_and_readback_callbacks_.pop_front(); |
427 } | 419 } |
428 | 420 |
429 void WebTestProxyBase::CapturePixelsForPrinting( | 421 void WebTestProxyBase::CapturePixelsForPrinting( |
430 const base::Callback<void(const SkBitmap&)>& callback) { | 422 const base::Callback<void(const SkBitmap&)>& callback) { |
431 // TODO(enne): get rid of stateful canvas(). | |
432 web_widget_->layout(); | 423 web_widget_->layout(); |
433 PaintPagesWithBoundaries(); | 424 |
434 DrawSelectionRect(GetCanvas()); | 425 WebSize pageSizeInPixels = web_widget_->size(); |
435 SkBaseDevice* device = skia::GetTopDevice(*GetCanvas()); | 426 WebFrame* webFrame = GetWebView()->mainFrame(); |
427 | |
428 int pageCount = webFrame->printBegin(pageSizeInPixels); | |
danakj
2014/05/15 14:34:33
page_count, etc. if is_opaque is going to be chrom
enne (OOO)
2014/05/15 17:10:33
How about I just fix up this whole file afterwards
danakj
2014/05/15 17:11:02
Yes, please. :)
| |
429 int totalHeight = pageCount * (pageSizeInPixels.height + 1) - 1; | |
430 | |
431 bool is_opaque = false; | |
432 skia::RefPtr<SkCanvas> canvas(skia::AdoptRef(skia::TryCreateBitmapCanvas( | |
433 pageSizeInPixels.width, totalHeight, is_opaque))); | |
434 if (canvas.get()) | |
danakj
2014/05/15 14:34:33
nit: no .get() needed
enne (OOO)
2014/05/15 17:10:33
Done.
| |
435 webFrame->printPagesWithBoundaries(canvas.get(), pageSizeInPixels); | |
436 webFrame->printEnd(); | |
437 | |
438 DrawSelectionRect(canvas.get()); | |
439 SkBaseDevice* device = skia::GetTopDevice(*canvas.get()); | |
danakj
2014/05/15 14:34:33
nit: no .get() needed
enne (OOO)
2014/05/15 17:10:33
Done.
| |
436 const SkBitmap& bitmap = device->accessBitmap(false); | 440 const SkBitmap& bitmap = device->accessBitmap(false); |
437 callback.Run(bitmap); | 441 callback.Run(bitmap); |
438 } | 442 } |
439 | 443 |
440 void WebTestProxyBase::CapturePixelsAsync( | 444 void WebTestProxyBase::CapturePixelsAsync( |
441 const base::Callback<void(const SkBitmap&)>& callback) { | 445 const base::Callback<void(const SkBitmap&)>& callback) { |
442 TRACE_EVENT0("shell", "WebTestProxyBase::CapturePixelsAsync"); | 446 TRACE_EVENT0("shell", "WebTestProxyBase::CapturePixelsAsync"); |
443 | 447 |
444 DCHECK(web_widget_->isAcceleratedCompositingActive()); | 448 DCHECK(web_widget_->isAcceleratedCompositingActive()); |
445 DCHECK(!callback.is_null()); | 449 DCHECK(!callback.is_null()); |
446 | 450 |
447 if (test_interfaces_->testRunner()->isPrinting()) { | 451 if (test_interfaces_->testRunner()->isPrinting()) { |
448 base::MessageLoopProxy::current()->PostTask( | 452 base::MessageLoopProxy::current()->PostTask( |
449 FROM_HERE, base::Bind(&WebTestProxyBase::CapturePixelsForPrinting, | 453 FROM_HERE, base::Bind(&WebTestProxyBase::CapturePixelsForPrinting, |
450 base::Unretained(this), callback)); | 454 base::Unretained(this), callback)); |
451 return; | 455 return; |
452 } | 456 } |
453 | 457 |
454 composite_and_readback_callbacks_.push_back(callback); | 458 composite_and_readback_callbacks_.push_back(callback); |
455 web_widget_->compositeAndReadbackAsync(this); | 459 web_widget_->compositeAndReadbackAsync(this); |
456 } | 460 } |
457 | 461 |
458 void WebTestProxyBase::SetLogConsoleOutput(bool enabled) { | 462 void WebTestProxyBase::SetLogConsoleOutput(bool enabled) { |
459 log_console_output_ = enabled; | 463 log_console_output_ = enabled; |
460 } | 464 } |
461 | 465 |
462 void WebTestProxyBase::PaintPagesWithBoundaries() { | |
463 DCHECK(!is_painting_); | |
464 DCHECK(GetCanvas()); | |
465 is_painting_ = true; | |
466 | |
467 WebSize pageSizeInPixels = web_widget_->size(); | |
468 WebFrame* webFrame = GetWebView()->mainFrame(); | |
469 | |
470 int pageCount = webFrame->printBegin(pageSizeInPixels); | |
471 int totalHeight = pageCount * (pageSizeInPixels.height + 1) - 1; | |
472 | |
473 SkCanvas* testCanvas = | |
474 skia::TryCreateBitmapCanvas(pageSizeInPixels.width, totalHeight, false); | |
475 if (testCanvas) { | |
476 DiscardBackingStore(); | |
477 canvas_.reset(testCanvas); | |
478 } else { | |
479 webFrame->printEnd(); | |
480 return; | |
481 } | |
482 | |
483 webFrame->printPagesWithBoundaries(GetCanvas(), pageSizeInPixels); | |
484 webFrame->printEnd(); | |
485 | |
486 is_painting_ = false; | |
487 } | |
488 | |
489 SkCanvas* WebTestProxyBase::GetCanvas() { | |
490 if (canvas_.get()) return canvas_.get(); | |
491 WebSize widgetSize = web_widget_->size(); | |
492 float deviceScaleFactor = GetWebView()->deviceScaleFactor(); | |
493 int scaledWidth = static_cast<int>( | |
494 ceil(static_cast<float>(widgetSize.width) * deviceScaleFactor)); | |
495 int scaledHeight = static_cast<int>( | |
496 ceil(static_cast<float>(widgetSize.height) * deviceScaleFactor)); | |
497 // We're allocating the canvas to be non-opaque (third parameter), so we | |
498 // don't end up with uninitialized memory if a layout test doesn't damage | |
499 // the entire view. | |
500 canvas_.reset(skia::CreateBitmapCanvas(scaledWidth, scaledHeight, false)); | |
501 return canvas_.get(); | |
502 } | |
503 | |
504 void WebTestProxyBase::DidDisplayAsync(const base::Closure& callback, | 466 void WebTestProxyBase::DidDisplayAsync(const base::Closure& callback, |
505 const SkBitmap& bitmap) { | 467 const SkBitmap& bitmap) { |
506 // Verify we actually composited. | 468 // Verify we actually composited. |
507 CHECK_NE(0, bitmap.info().fWidth); | 469 CHECK_NE(0, bitmap.info().fWidth); |
508 CHECK_NE(0, bitmap.info().fHeight); | 470 CHECK_NE(0, bitmap.info().fHeight); |
509 if (!callback.is_null()) callback.Run(); | 471 if (!callback.is_null()) callback.Run(); |
510 } | 472 } |
511 | 473 |
512 void WebTestProxyBase::DisplayAsyncThen(const base::Closure& callback) { | 474 void WebTestProxyBase::DisplayAsyncThen(const base::Closure& callback) { |
513 TRACE_EVENT0("shell", "WebTestProxyBase::DisplayAsyncThen"); | 475 TRACE_EVENT0("shell", "WebTestProxyBase::DisplayAsyncThen"); |
514 | 476 |
515 CHECK(web_widget_->isAcceleratedCompositingActive()); | 477 CHECK(web_widget_->isAcceleratedCompositingActive()); |
516 CapturePixelsAsync(base::Bind(&WebTestProxyBase::DidDisplayAsync, | 478 CapturePixelsAsync(base::Bind(&WebTestProxyBase::DidDisplayAsync, |
517 base::Unretained(this), callback)); | 479 base::Unretained(this), callback)); |
518 } | 480 } |
519 | 481 |
520 void WebTestProxyBase::DiscardBackingStore() { canvas_.reset(); } | |
521 | |
522 WebMIDIClientMock* WebTestProxyBase::GetMIDIClientMock() { | 482 WebMIDIClientMock* WebTestProxyBase::GetMIDIClientMock() { |
523 if (!m_midiClient.get()) m_midiClient.reset(new WebMIDIClientMock); | 483 if (!m_midiClient.get()) m_midiClient.reset(new WebMIDIClientMock); |
524 return m_midiClient.get(); | 484 return m_midiClient.get(); |
525 } | 485 } |
526 | 486 |
527 MockWebSpeechRecognizer* WebTestProxyBase::GetSpeechRecognizerMock() { | 487 MockWebSpeechRecognizer* WebTestProxyBase::GetSpeechRecognizerMock() { |
528 if (!m_speechRecognizer.get()) { | 488 if (!m_speechRecognizer.get()) { |
529 m_speechRecognizer.reset(new MockWebSpeechRecognizer()); | 489 m_speechRecognizer.reset(new MockWebSpeechRecognizer()); |
530 m_speechRecognizer->setDelegate(delegate_); | 490 m_speechRecognizer->setDelegate(delegate_); |
531 } | 491 } |
532 return m_speechRecognizer.get(); | 492 return m_speechRecognizer.get(); |
533 } | 493 } |
534 | 494 |
535 void WebTestProxyBase::DidInvalidateRect(const WebRect& rect) { | 495 void WebTestProxyBase::ScheduleComposite() { |
danakj
2014/05/15 14:34:33
If this does nothing can it go away?
| |
536 // paint_rect_ = paint_rect_ U rect | |
537 if (rect.isEmpty()) return; | |
538 if (paint_rect_.isEmpty()) { | |
539 paint_rect_ = rect; | |
540 return; | |
541 } | |
542 int left = min(paint_rect_.x, rect.x); | |
543 int top = min(paint_rect_.y, rect.y); | |
544 int right = max(paint_rect_.x + paint_rect_.width, rect.x + rect.width); | |
545 int bottom = max(paint_rect_.y + paint_rect_.height, rect.y + rect.height); | |
546 paint_rect_ = WebRect(left, top, right - left, bottom - top); | |
547 } | 496 } |
548 | 497 |
549 void WebTestProxyBase::DidScrollRect(int, int, const WebRect& clipRect) { | |
550 DidInvalidateRect(clipRect); | |
551 } | |
552 | |
553 void WebTestProxyBase::InvalidateAll() { | |
554 paint_rect_ = WebRect(0, 0, INT_MAX, INT_MAX); | |
555 } | |
556 | |
557 void WebTestProxyBase::ScheduleComposite() { InvalidateAll(); } | |
558 | |
559 void WebTestProxyBase::ScheduleAnimation() { | 498 void WebTestProxyBase::ScheduleAnimation() { |
560 if (!test_interfaces_->testRunner()->TestIsRunning()) return; | 499 if (!test_interfaces_->testRunner()->TestIsRunning()) return; |
561 | 500 |
562 if (!animate_scheduled_) { | 501 if (!animate_scheduled_) { |
563 animate_scheduled_ = true; | 502 animate_scheduled_ = true; |
564 delegate_->postDelayedTask( | 503 delegate_->postDelayedTask( |
565 new HostMethodTask(this, &WebTestProxyBase::AnimateNow), 1); | 504 new HostMethodTask(this, &WebTestProxyBase::AnimateNow), 1); |
566 } | 505 } |
567 } | 506 } |
568 | 507 |
569 void WebTestProxyBase::AnimateNow() { | 508 void WebTestProxyBase::AnimateNow() { |
570 if (animate_scheduled_) { | 509 if (animate_scheduled_) { |
571 animate_scheduled_ = false; | 510 animate_scheduled_ = false; |
572 web_widget_->animate(0.0); | 511 web_widget_->animate(0.0); |
573 web_widget_->layout(); | 512 web_widget_->layout(); |
574 } | 513 } |
575 } | 514 } |
576 | 515 |
577 bool WebTestProxyBase::IsCompositorFramePending() const { | |
578 return animate_scheduled_ || !paint_rect_.isEmpty(); | |
579 } | |
580 | |
581 void WebTestProxyBase::Show(WebNavigationPolicy) { InvalidateAll(); } | |
582 | |
583 void WebTestProxyBase::SetWindowRect(const WebRect& rect) { | |
584 InvalidateAll(); | |
585 DiscardBackingStore(); | |
586 } | |
587 | |
588 void WebTestProxyBase::DidAutoResize(const WebSize&) { InvalidateAll(); } | |
589 | |
590 void WebTestProxyBase::PostAccessibilityEvent(const blink::WebAXObject& obj, | 516 void WebTestProxyBase::PostAccessibilityEvent(const blink::WebAXObject& obj, |
591 blink::WebAXEvent event) { | 517 blink::WebAXEvent event) { |
592 // Only hook the accessibility events occured during the test run. | 518 // Only hook the accessibility events occured during the test run. |
593 // This check prevents false positives in WebLeakDetector. | 519 // This check prevents false positives in WebLeakDetector. |
594 // The pending tasks in browser/renderer message queue may trigger | 520 // The pending tasks in browser/renderer message queue may trigger |
595 // accessibility events, | 521 // accessibility events, |
596 // and AccessibilityController will hold on to their target nodes if we don't | 522 // and AccessibilityController will hold on to their target nodes if we don't |
597 // ignore them here. | 523 // ignore them here. |
598 if (!test_interfaces_->testRunner()->TestIsRunning()) return; | 524 if (!test_interfaces_->testRunner()->TestIsRunning()) return; |
599 | 525 |
(...skipping 584 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1184 } | 1110 } |
1185 } | 1111 } |
1186 | 1112 |
1187 void WebTestProxyBase::ResetInputMethod() { | 1113 void WebTestProxyBase::ResetInputMethod() { |
1188 // If a composition text exists, then we need to let the browser process | 1114 // If a composition text exists, then we need to let the browser process |
1189 // to cancel the input method's ongoing composition session. | 1115 // to cancel the input method's ongoing composition session. |
1190 if (web_widget_) web_widget_->confirmComposition(); | 1116 if (web_widget_) web_widget_->confirmComposition(); |
1191 } | 1117 } |
1192 | 1118 |
1193 } // namespace content | 1119 } // namespace content |
OLD | NEW |