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

Unified Diff: content/browser/media/capture/content_video_capture_device_core.cc

Issue 965123002: Crash fix for desktop capture size calculations, and some minor things. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: rebase Created 5 years, 10 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 side-by-side diff with in-line comments
Download patch
Index: content/browser/media/capture/content_video_capture_device_core.cc
diff --git a/content/browser/media/capture/content_video_capture_device_core.cc b/content/browser/media/capture/content_video_capture_device_core.cc
index b470bcdb18d0b1de3e42f66a2bdb1d5ef827027b..08741e0e58506d42c710d52db3f979cb06fadd1b 100644
--- a/content/browser/media/capture/content_video_capture_device_core.cc
+++ b/content/browser/media/capture/content_video_capture_device_core.cc
@@ -48,20 +48,7 @@ ThreadSafeCaptureOracle::ThreadSafeCaptureOracle(
oracle_(base::TimeDelta::FromMicroseconds(
static_cast<int64>(1000000.0 / params.requested_format.frame_rate +
0.5 /* to round to nearest int */))),
- params_(params),
- capture_size_updated_(false) {
- switch (params_.requested_format.pixel_format) {
- case media::PIXEL_FORMAT_I420:
- video_frame_format_ = media::VideoFrame::I420;
- break;
- case media::PIXEL_FORMAT_TEXTURE:
- video_frame_format_ = media::VideoFrame::NATIVE_TEXTURE;
- break;
- default:
- LOG(FATAL) << "Unexpected pixel_format "
- << params_.requested_format.pixel_format;
- }
-}
+ params_(params) {}
ThreadSafeCaptureOracle::~ThreadSafeCaptureOracle() {}
@@ -76,14 +63,20 @@ bool ThreadSafeCaptureOracle::ObserveEventAndDecideCapture(
if (!client_)
return false; // Capture is stopped.
+ const media::VideoFrame::Format video_frame_format =
+ params_.requested_format.pixel_format == media::PIXEL_FORMAT_TEXTURE ?
+ media::VideoFrame::NATIVE_TEXTURE : media::VideoFrame::I420;
+
+ if (capture_size_.IsEmpty())
+ capture_size_ = max_frame_size();
+ const gfx::Size visible_size = capture_size_;
// Always round up the coded size to multiple of 16 pixels.
// See http://crbug.com/402151.
- const gfx::Size visible_size = params_.requested_format.frame_size;
const gfx::Size coded_size((visible_size.width() + 15) & ~15,
(visible_size.height() + 15) & ~15);
scoped_refptr<media::VideoCaptureDevice::Client::Buffer> output_buffer =
- client_->ReserveOutputBuffer(video_frame_format_, coded_size);
+ client_->ReserveOutputBuffer(video_frame_format, coded_size);
const bool should_capture =
oracle_.ObserveEventAndDecideCapture(event, damage_rect, event_time);
const bool content_is_dirty =
@@ -126,9 +119,9 @@ bool ThreadSafeCaptureOracle::ObserveEventAndDecideCapture(
"trigger", event_name);
// NATIVE_TEXTURE frames wrap a texture mailbox, which we don't have at the
// moment. We do not construct those frames.
- if (video_frame_format_ != media::VideoFrame::NATIVE_TEXTURE) {
+ if (video_frame_format != media::VideoFrame::NATIVE_TEXTURE) {
*storage = media::VideoFrame::WrapExternalPackedMemory(
- video_frame_format_,
+ video_frame_format,
coded_size,
gfx::Rect(visible_size),
visible_size,
@@ -138,6 +131,7 @@ bool ThreadSafeCaptureOracle::ObserveEventAndDecideCapture(
0,
base::TimeDelta(),
base::Closure());
+ DCHECK(*storage);
}
*callback = base::Bind(&ThreadSafeCaptureOracle::DidCaptureFrame,
this,
@@ -148,30 +142,29 @@ bool ThreadSafeCaptureOracle::ObserveEventAndDecideCapture(
gfx::Size ThreadSafeCaptureOracle::GetCaptureSize() const {
base::AutoLock guard(lock_);
- return params_.requested_format.frame_size;
+ return capture_size_.IsEmpty() ? max_frame_size() : capture_size_;
}
void ThreadSafeCaptureOracle::UpdateCaptureSize(const gfx::Size& source_size) {
base::AutoLock guard(lock_);
- // If this is the first call to UpdateCaptureSize(), or the receiver supports
- // variable resolution, then determine the capture size by treating the
- // requested width and height as maxima.
- if (!capture_size_updated_ || params_.resolution_change_policy ==
+ // Update |capture_size_| based on |source_size| if either: 1) The resolution
+ // change policy specifies fixed frame sizes and |capture_size_| has not yet
+ // been set; or 2) The resolution change policy specifies dynamic frame
+ // sizes.
+ if (capture_size_.IsEmpty() || params_.resolution_change_policy ==
media::RESOLUTION_POLICY_DYNAMIC_WITHIN_LIMIT) {
- // The capture resolution should not exceed the source frame size.
- // In other words it should downscale the image but not upscale it.
- if (source_size.width() > params_.requested_format.frame_size.width() ||
- source_size.height() > params_.requested_format.frame_size.height()) {
- gfx::Rect capture_rect = media::ComputeLetterboxRegion(
- gfx::Rect(params_.requested_format.frame_size), source_size);
- params_.requested_format.frame_size.SetSize(
- MakeEven(capture_rect.width()), MakeEven(capture_rect.height()));
- } else {
- params_.requested_format.frame_size.SetSize(
- MakeEven(source_size.width()), MakeEven(source_size.height()));
+ capture_size_ = source_size;
+ // The capture size should not exceed the maximum frame size.
+ if (capture_size_.width() > max_frame_size().width() ||
+ capture_size_.height() > max_frame_size().height()) {
+ capture_size_ = media::ComputeLetterboxRegion(
+ gfx::Rect(max_frame_size()), capture_size_).size();
}
- capture_size_updated_ = true;
+ // The capture size must be even and not less than the minimum frame size.
+ capture_size_ = gfx::Size(
+ std::max(kMinFrameWidth, MakeEven(capture_size_.width())),
+ std::max(kMinFrameHeight, MakeEven(capture_size_.height())));
}
}

Powered by Google App Engine
This is Rietveld 408576698