OLD | NEW |
---|---|
1 // Copyright (c) 2010 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2010 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 "webkit/glue/webmediaplayer_impl.h" | 5 #include "webkit/glue/webmediaplayer_impl.h" |
6 | 6 |
7 #include <limits> | 7 #include <limits> |
8 | 8 |
9 #include "base/callback.h" | 9 #include "base/callback.h" |
10 #include "base/command_line.h" | 10 #include "base/command_line.h" |
(...skipping 545 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
556 } | 556 } |
557 | 557 |
558 void WebMediaPlayerImpl::paint(WebCanvas* canvas, | 558 void WebMediaPlayerImpl::paint(WebCanvas* canvas, |
559 const WebRect& rect) { | 559 const WebRect& rect) { |
560 DCHECK(MessageLoop::current() == main_loop_); | 560 DCHECK(MessageLoop::current() == main_loop_); |
561 DCHECK(proxy_); | 561 DCHECK(proxy_); |
562 | 562 |
563 #if WEBKIT_USING_SKIA | 563 #if WEBKIT_USING_SKIA |
564 proxy_->Paint(canvas, rect); | 564 proxy_->Paint(canvas, rect); |
565 #elif WEBKIT_USING_CG | 565 #elif WEBKIT_USING_CG |
566 // Get the current scaling in X and Y. | 566 if (CGBitmapContextGetData(canvas)) { |
567 CGAffineTransform mat = CGContextGetCTM(canvas); | 567 int width = CGBitmapContextGetWidth(canvas); |
568 float scale_x = sqrt(mat.a * mat.a + mat.b * mat.b); | 568 int height = CGBitmapContextGetHeight(canvas); |
569 float scale_y = sqrt(mat.c * mat.c + mat.d * mat.d); | 569 DCHECK(width != 0 && height != 0); |
570 float inverse_scale_x = SkScalarNearlyZero(scale_x) ? 0.0f : 1.0f / scale_x; | 570 skia::PlatformCanvas skia_canvas(width, height, true, canvas); |
571 float inverse_scale_y = SkScalarNearlyZero(scale_y) ? 0.0f : 1.0f / scale_y; | |
572 int scaled_width = static_cast<int>(rect.width * fabs(scale_x)); | |
573 int scaled_height = static_cast<int>(rect.height * fabs(scale_y)); | |
574 | 571 |
575 // Make sure we don't create a huge canvas. | 572 // Copy the transformation matrix from the context. |
576 // TODO(hclam): Respect the aspect ratio. | 573 CGAffineTransform cgMat = CGContextGetCTM(canvas); |
577 if (scaled_width > static_cast<int>(media::Limits::kMaxCanvas)) | 574 SkMatrix skMat; |
578 scaled_width = media::Limits::kMaxCanvas; | 575 skMat.reset(); |
579 if (scaled_height > static_cast<int>(media::Limits::kMaxCanvas)) | 576 skMat[SkMatrix::kMScaleX] = cgMat.a; |
580 scaled_height = media::Limits::kMaxCanvas; | 577 skMat[SkMatrix::kMScaleY] = -cgMat.d; |
578 skMat[SkMatrix::kMSkewX] = cgMat.b; | |
579 skMat[SkMatrix::kMSkewY] = -cgMat.c; | |
580 skMat[SkMatrix::kMTransX] = cgMat.tx; | |
581 skMat[SkMatrix::kMTransY] = height - cgMat.ty; | |
582 skia_canvas.setMatrix(skMat); | |
581 | 583 |
582 // If there is no preexisting platform canvas, or if the size has | 584 proxy_->Paint(&skia_canvas, rect); |
583 // changed, recreate the canvas. This is to avoid recreating the bitmap | 585 } else { |
584 // buffer over and over for each frame of video. | 586 // No bitmap context available, so we need to proxy via a bitmap. |
585 if (!skia_canvas_.get() || | 587 // TODO(sjl): Can this ever happen? |
brettw
2010/12/29 21:03:52
I was wondering the same thing as this todo says.
sjl
2010/12/31 05:55:49
That's my understanding too.
| |
586 skia_canvas_->getDevice()->width() != scaled_width || | 588 |
587 skia_canvas_->getDevice()->height() != scaled_height) { | 589 // Get the current scaling in X and Y. |
588 skia_canvas_.reset( | 590 CGAffineTransform mat = CGContextGetCTM(canvas); |
589 new skia::PlatformCanvas(scaled_width, scaled_height, true)); | 591 float scale_x = sqrt(mat.a * mat.a + mat.b * mat.b); |
592 float scale_y = sqrt(mat.c * mat.c + mat.d * mat.d); | |
593 float inverse_scale_x = SkScalarNearlyZero(scale_x) ? 0.0f : 1.0f / scale_x; | |
594 float inverse_scale_y = SkScalarNearlyZero(scale_y) ? 0.0f : 1.0f / scale_y; | |
595 int scaled_width = static_cast<int>(rect.width * fabs(scale_x)); | |
596 int scaled_height = static_cast<int>(rect.height * fabs(scale_y)); | |
597 | |
598 // Make sure we don't create a huge canvas. | |
599 // TODO(hclam): Respect the aspect ratio. | |
600 if (scaled_width > static_cast<int>(media::Limits::kMaxCanvas)) | |
601 scaled_width = media::Limits::kMaxCanvas; | |
602 if (scaled_height > static_cast<int>(media::Limits::kMaxCanvas)) | |
603 scaled_height = media::Limits::kMaxCanvas; | |
604 | |
605 // If there is no preexisting platform canvas, or if the size has | |
606 // changed, recreate the canvas. This is to avoid recreating the bitmap | |
607 // buffer over and over for each frame of video. | |
608 if (!skia_canvas_.get() || | |
609 skia_canvas_->getDevice()->width() != scaled_width || | |
610 skia_canvas_->getDevice()->height() != scaled_height) { | |
611 skia_canvas_.reset( | |
612 new skia::PlatformCanvas(scaled_width, scaled_height, true)); | |
613 } | |
614 | |
615 // Draw to our temporary skia canvas. | |
616 gfx::Rect normalized_rect(scaled_width, scaled_height); | |
617 proxy_->Paint(skia_canvas_.get(), normalized_rect); | |
618 | |
619 // The mac coordinate system is flipped vertical from the normal skia | |
620 // coordinates. During painting of the frame, flip the coordinates | |
621 // system and, for simplicity, also translate the clip rectangle to | |
622 // start at 0,0. | |
623 CGContextSaveGState(canvas); | |
624 CGContextTranslateCTM(canvas, rect.x, rect.height + rect.y); | |
625 CGContextScaleCTM(canvas, inverse_scale_x, -inverse_scale_y); | |
626 | |
627 // We need a local variable CGRect version for DrawToContext. | |
628 CGRect normalized_cgrect = | |
629 CGRectMake(normalized_rect.x(), normalized_rect.y(), | |
630 normalized_rect.width(), normalized_rect.height()); | |
631 | |
632 // Copy the frame rendered to our temporary skia canvas onto the passed in | |
633 // canvas. | |
634 | |
635 skia_canvas_->getTopPlatformDevice().DrawToContext(canvas, 0, 0, | |
636 &normalized_cgrect); | |
637 | |
638 CGContextRestoreGState(canvas); | |
590 } | 639 } |
591 | |
592 // Draw to our temporary skia canvas. | |
593 gfx::Rect normalized_rect(scaled_width, scaled_height); | |
594 proxy_->Paint(skia_canvas_.get(), normalized_rect); | |
595 | |
596 // The mac coordinate system is flipped vertical from the normal skia | |
597 // coordinates. During painting of the frame, flip the coordinates | |
598 // system and, for simplicity, also translate the clip rectangle to | |
599 // start at 0,0. | |
600 CGContextSaveGState(canvas); | |
601 CGContextTranslateCTM(canvas, rect.x, rect.height + rect.y); | |
602 CGContextScaleCTM(canvas, inverse_scale_x, -inverse_scale_y); | |
603 | |
604 // We need a local variable CGRect version for DrawToContext. | |
605 CGRect normalized_cgrect = | |
606 CGRectMake(normalized_rect.x(), normalized_rect.y(), | |
607 normalized_rect.width(), normalized_rect.height()); | |
608 | |
609 // Copy the frame rendered to our temporary skia canvas onto the passed in | |
610 // canvas. | |
611 skia_canvas_->getTopPlatformDevice().DrawToContext(canvas, 0, 0, | |
612 &normalized_cgrect); | |
613 | |
614 CGContextRestoreGState(canvas); | |
615 #else | 640 #else |
616 NOTIMPLEMENTED() << "We only support rendering to skia or CG"; | 641 NOTIMPLEMENTED() << "We only support rendering to skia or CG"; |
617 #endif | 642 #endif |
618 } | 643 } |
619 | 644 |
620 bool WebMediaPlayerImpl::hasSingleSecurityOrigin() const { | 645 bool WebMediaPlayerImpl::hasSingleSecurityOrigin() const { |
621 if (proxy_) | 646 if (proxy_) |
622 return proxy_->HasSingleOrigin(); | 647 return proxy_->HasSingleOrigin(); |
623 return true; | 648 return true; |
624 } | 649 } |
(...skipping 182 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
807 pipeline_stopped_.Signal(); | 832 pipeline_stopped_.Signal(); |
808 } | 833 } |
809 | 834 |
810 WebKit::WebMediaPlayerClient* WebMediaPlayerImpl::GetClient() { | 835 WebKit::WebMediaPlayerClient* WebMediaPlayerImpl::GetClient() { |
811 DCHECK(MessageLoop::current() == main_loop_); | 836 DCHECK(MessageLoop::current() == main_loop_); |
812 DCHECK(client_); | 837 DCHECK(client_); |
813 return client_; | 838 return client_; |
814 } | 839 } |
815 | 840 |
816 } // namespace webkit_glue | 841 } // namespace webkit_glue |
OLD | NEW |