Chromium Code Reviews| 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 // Implementation notes: This needs to work on a variety of hardware | 5 // Implementation notes: This needs to work on a variety of hardware |
| 6 // configurations where the speed of the CPU and GPU greatly affect overall | 6 // configurations where the speed of the CPU and GPU greatly affect overall |
| 7 // performance. Spanning several threads, the process of capturing has been | 7 // performance. Spanning several threads, the process of capturing has been |
| 8 // split up into four conceptual stages: | 8 // split up into four conceptual stages: |
| 9 // | 9 // |
| 10 // 1. Reserve Buffer: Before a frame can be captured, a slot in the client's | 10 // 1. Reserve Buffer: Before a frame can be captured, a slot in the client's |
| (...skipping 624 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 635 } | 635 } |
| 636 | 636 |
| 637 gfx::Size WebContentsCaptureMachine::ComputeOptimalViewSize() const { | 637 gfx::Size WebContentsCaptureMachine::ComputeOptimalViewSize() const { |
| 638 DCHECK_CURRENTLY_ON(BrowserThread::UI); | 638 DCHECK_CURRENTLY_ON(BrowserThread::UI); |
| 639 | 639 |
| 640 // TODO(miu): Propagate capture frame size changes as new "preferred size" | 640 // TODO(miu): Propagate capture frame size changes as new "preferred size" |
| 641 // updates, rather than just using the max frame size. | 641 // updates, rather than just using the max frame size. |
| 642 // http://crbug.com/350491 | 642 // http://crbug.com/350491 |
| 643 gfx::Size optimal_size = oracle_proxy_->max_frame_size(); | 643 gfx::Size optimal_size = oracle_proxy_->max_frame_size(); |
| 644 | 644 |
| 645 // If the max frame size is close to a common video aspect ratio, compute a | |
| 646 // standard resolution for that aspect ratio. For example, given 1365x768, | |
| 647 // which is very close to 16:9, the optimal size would be 1280x720. The | |
| 648 // purpose of this logic is to prevent scaling quality issues caused by "one | |
| 649 // pixel stretching" and/or odd-to-even dimension scaling, and to improve the | |
| 650 // performance of consumers of the captured video. | |
| 651 const auto HasIntendedAspectRatio = [](const gfx::Size& size, int x, int y) { | |
|
Kevin M
2015/07/30 00:23:06
Can you factor this out into a standalone fn that
miu
2015/07/30 20:22:53
Done. Didn't factor anything out, but did write u
| |
| 652 const int a = y * size.width(); | |
| 653 const int b = x * size.height(); | |
| 654 const int percentage_diff = 100 * std::abs((a - b)) / b; | |
| 655 return percentage_diff <= 1; // Effectively, anything strictly <2%. | |
| 656 }; | |
| 657 const auto RoundToExactAspectRatio = [](const gfx::Size& size, int x, int y) { | |
| 658 const int adjusted_height = | |
|
Kevin M
2015/07/30 00:23:06
Can you add some comments or pick a more descripti
miu
2015/07/30 20:22:53
Done.
| |
| 659 std::max(size.height() - (size.height() % y), y); | |
| 660 DCHECK_EQ((adjusted_height * x) % y, 0); | |
| 661 return gfx::Size(adjusted_height * x / y, adjusted_height); | |
| 662 }; | |
| 663 if (HasIntendedAspectRatio(optimal_size, 16, 9)) | |
| 664 optimal_size = RoundToExactAspectRatio(optimal_size, 160, 90); | |
| 665 else if (HasIntendedAspectRatio(optimal_size, 4, 3)) | |
| 666 optimal_size = RoundToExactAspectRatio(optimal_size, 64, 48); | |
| 667 // Else, do not make an adjustment. | |
| 668 | |
| 645 // If the ratio between physical and logical pixels is greater than 1:1, | 669 // If the ratio between physical and logical pixels is greater than 1:1, |
| 646 // shrink |optimal_size| by that amount. Then, when external code resizes the | 670 // shrink |optimal_size| by that amount. Then, when external code resizes the |
| 647 // render widget to the "preferred size," the widget will be physically | 671 // render widget to the "preferred size," the widget will be physically |
| 648 // rendered at the exact capture size, thereby eliminating unnecessary scaling | 672 // rendered at the exact capture size, thereby eliminating unnecessary scaling |
| 649 // operations in the graphics pipeline. | 673 // operations in the graphics pipeline. |
| 650 RenderWidgetHost* const rwh = tracker_->GetTargetRenderWidgetHost(); | 674 RenderWidgetHost* const rwh = tracker_->GetTargetRenderWidgetHost(); |
| 651 RenderWidgetHostView* const rwhv = rwh ? rwh->GetView() : NULL; | 675 RenderWidgetHostView* const rwhv = rwh ? rwh->GetView() : NULL; |
| 652 if (rwhv) { | 676 if (rwhv) { |
| 653 const gfx::NativeView view = rwhv->GetNativeView(); | 677 const gfx::NativeView view = rwhv->GetNativeView(); |
| 654 const float scale = ui::GetScaleFactorForNativeView(view); | 678 const float scale = ui::GetScaleFactorForNativeView(view); |
| (...skipping 144 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 799 scoped_ptr<Client> client) { | 823 scoped_ptr<Client> client) { |
| 800 DVLOG(1) << "Allocating " << params.requested_format.frame_size.ToString(); | 824 DVLOG(1) << "Allocating " << params.requested_format.frame_size.ToString(); |
| 801 core_->AllocateAndStart(params, client.Pass()); | 825 core_->AllocateAndStart(params, client.Pass()); |
| 802 } | 826 } |
| 803 | 827 |
| 804 void WebContentsVideoCaptureDevice::StopAndDeAllocate() { | 828 void WebContentsVideoCaptureDevice::StopAndDeAllocate() { |
| 805 core_->StopAndDeAllocate(); | 829 core_->StopAndDeAllocate(); |
| 806 } | 830 } |
| 807 | 831 |
| 808 } // namespace content | 832 } // namespace content |
| OLD | NEW |