Commit 8df15ddf authored by Ilya Nikolaevskiy's avatar Ilya Nikolaevskiy Committed by Commit Bot

WebrtcVideoTrackSource: don't set update_rect if there's no update information

This change reflects change in Webrtc API: Now update_rect in VideoFrame is optional
and should only be set if capturer knows that update is contained in some rect and is
close to it.

Bug: webrtc:11058
Change-Id: Ia8bbfb8dfbd0c51828386a8b2420d0053dfaa259
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/1911784
Auto-Submit: Ilya Nikolaevskiy <ilnik@chromium.org>
Commit-Queue: Ilya Nikolaevskiy <ilnik@chromium.org>
Reviewed-by: default avatarGuido Urdaneta <guidou@chromium.org>
Cr-Commit-Position: refs/heads/master@{#714460}
parent 5adda3eb
...@@ -98,15 +98,22 @@ void WebRtcVideoTrackSource::OnFrameCaptured( ...@@ -98,15 +98,22 @@ void WebRtcVideoTrackSource::OnFrameCaptured(
DVLOG(3) << "has_valid_update_rect = " << has_valid_update_rect; DVLOG(3) << "has_valid_update_rect = " << has_valid_update_rect;
if (has_capture_counter) if (has_capture_counter)
previous_capture_counter_ = capture_counter; previous_capture_counter_ = capture_counter;
if (has_valid_update_rect) if (has_valid_update_rect) {
accumulated_update_rect_.Union(update_rect); if (!accumulated_update_rect_) {
else accumulated_update_rect_ = update_rect;
accumulated_update_rect_.Union(gfx::Rect(frame->coded_size())); } else {
accumulated_update_rect_->Union(update_rect);
}
} else {
accumulated_update_rect_ = base::nullopt;
}
DVLOG(3) << "accumulated_update_rect_ = [" << accumulated_update_rect_.x() if (accumulated_update_rect_) {
<< ", " << accumulated_update_rect_.y() << ", " DVLOG(3) << "accumulated_update_rect_ = [" << accumulated_update_rect_->x()
<< accumulated_update_rect_.width() << ", " << ", " << accumulated_update_rect_->y() << ", "
<< accumulated_update_rect_.height() << "]"; << accumulated_update_rect_->width() << ", "
<< accumulated_update_rect_->height() << "]";
}
// Calculate desired target cropping and scaling of the received frame. Note, // Calculate desired target cropping and scaling of the received frame. Note,
// that the frame may already have some cropping and scaling soft-applied via // that the frame may already have some cropping and scaling soft-applied via
...@@ -132,9 +139,14 @@ void WebRtcVideoTrackSource::OnFrameCaptured( ...@@ -132,9 +139,14 @@ void WebRtcVideoTrackSource::OnFrameCaptured(
frame->storage_type() != media::VideoFrame::STORAGE_GPU_MEMORY_BUFFER) { frame->storage_type() != media::VideoFrame::STORAGE_GPU_MEMORY_BUFFER) {
// The webrtc::VideoFrame::UpdateRect expected by WebRTC must // The webrtc::VideoFrame::UpdateRect expected by WebRTC must
// be relative to the |visible_rect()|. We need to translate. // be relative to the |visible_rect()|. We need to translate.
const auto cropped_rect = base::Optional<gfx::Rect> cropped_rect;
CropRectangle(accumulated_update_rect_, frame->visible_rect()); if (accumulated_update_rect_) {
DeliverFrame(std::move(frame), cropped_rect, translated_camera_time_us); cropped_rect =
CropRectangle(*accumulated_update_rect_, frame->visible_rect());
}
DeliverFrame(std::move(frame), OptionalOrNullptr(cropped_rect),
translated_camera_time_us);
return; return;
} }
...@@ -174,9 +186,12 @@ void WebRtcVideoTrackSource::OnFrameCaptured( ...@@ -174,9 +186,12 @@ void WebRtcVideoTrackSource::OnFrameCaptured(
if (video_frame->natural_size() == video_frame->visible_rect().size()) { if (video_frame->natural_size() == video_frame->visible_rect().size()) {
// The webrtc::VideoFrame::UpdateRect expected by WebRTC must be // The webrtc::VideoFrame::UpdateRect expected by WebRTC must be
// relative to the |visible_rect()|. We need to translate. // relative to the |visible_rect()|. We need to translate.
const auto cropped_rect = base::Optional<gfx::Rect> cropped_rect;
CropRectangle(accumulated_update_rect_, video_frame->visible_rect()); if (accumulated_update_rect_) {
DeliverFrame(std::move(video_frame), cropped_rect, cropped_rect =
CropRectangle(*accumulated_update_rect_, frame->visible_rect());
}
DeliverFrame(std::move(video_frame), OptionalOrNullptr(cropped_rect),
translated_camera_time_us); translated_camera_time_us);
return; return;
} }
...@@ -184,13 +199,15 @@ void WebRtcVideoTrackSource::OnFrameCaptured( ...@@ -184,13 +199,15 @@ void WebRtcVideoTrackSource::OnFrameCaptured(
// Delay scaling if |video_frame| is backed by GpuMemoryBuffer. // Delay scaling if |video_frame| is backed by GpuMemoryBuffer.
if (video_frame->storage_type() == if (video_frame->storage_type() ==
media::VideoFrame::STORAGE_GPU_MEMORY_BUFFER) { media::VideoFrame::STORAGE_GPU_MEMORY_BUFFER) {
// When scaling is applied and any part of the frame has changed, we mark // When scaling is applied and any part of the frame has changed, we don't
// the whole frame as changed. // have reliable changed rect information.
const auto update_rect_on_scaled = if (accumulated_update_rect_.has_value() &&
accumulated_update_rect_.IsEmpty() !accumulated_update_rect_->IsEmpty()) {
? gfx::Rect() accumulated_update_rect_ = base::nullopt;
: gfx::Rect(video_frame->natural_size()); }
DeliverFrame(std::move(video_frame), update_rect_on_scaled,
DeliverFrame(std::move(video_frame),
OptionalOrNullptr(accumulated_update_rect_),
translated_camera_time_us); translated_camera_time_us);
return; return;
} }
...@@ -228,14 +245,15 @@ void WebRtcVideoTrackSource::OnFrameCaptured( ...@@ -228,14 +245,15 @@ void WebRtcVideoTrackSource::OnFrameCaptured(
adapted_size.width(), adapted_size.height(), adapted_size.width(), adapted_size.height(),
libyuv::kFilterBilinear); libyuv::kFilterBilinear);
} }
// When scaling is applied and any part of the frame has changed, we mark the // When scaling is applied and any part of the frame has changed, we don't
// whole frame as changed. // have a reliable update rect information.
DeliverFrame( if (accumulated_update_rect_.has_value() &&
std::move(scaled_frame), !accumulated_update_rect_->IsEmpty()) {
accumulated_update_rect_.IsEmpty() accumulated_update_rect_ = base::nullopt;
? gfx::Rect() }
: gfx::Rect(0, 0, adapted_size.width(), adapted_size.height()), DeliverFrame(std::move(scaled_frame),
translated_camera_time_us); OptionalOrNullptr(accumulated_update_rect_),
translated_camera_time_us);
} }
WebRtcVideoTrackSource::FrameAdaptationParams WebRtcVideoTrackSource::FrameAdaptationParams
...@@ -254,11 +272,13 @@ WebRtcVideoTrackSource::ComputeAdaptationParams(int width, ...@@ -254,11 +272,13 @@ WebRtcVideoTrackSource::ComputeAdaptationParams(int width,
void WebRtcVideoTrackSource::DeliverFrame( void WebRtcVideoTrackSource::DeliverFrame(
scoped_refptr<media::VideoFrame> frame, scoped_refptr<media::VideoFrame> frame,
gfx::Rect update_rect, gfx::Rect* update_rect,
int64_t timestamp_us) { int64_t timestamp_us) {
DVLOG(3) << "update_rect = " if (update_rect) {
<< "[" << update_rect.x() << ", " << update_rect.y() << ", " DVLOG(3) << "update_rect = "
<< update_rect.width() << ", " << update_rect.height() << "]"; << "[" << update_rect->x() << ", " << update_rect->y() << ", "
<< update_rect->width() << ", " << update_rect->height() << "]";
}
// If the cropping or the size have changed since the previous // If the cropping or the size have changed since the previous
// frame, even if nothing in the incoming coded frame content has changed, we // frame, even if nothing in the incoming coded frame content has changed, we
...@@ -267,27 +287,24 @@ void WebRtcVideoTrackSource::DeliverFrame( ...@@ -267,27 +287,24 @@ void WebRtcVideoTrackSource::DeliverFrame(
frame->natural_size() != natural_size_of_previous_delivered_frame_) { frame->natural_size() != natural_size_of_previous_delivered_frame_) {
cropping_rect_of_previous_delivered_frame_ = frame->visible_rect(); cropping_rect_of_previous_delivered_frame_ = frame->visible_rect();
natural_size_of_previous_delivered_frame_ = frame->natural_size(); natural_size_of_previous_delivered_frame_ = frame->natural_size();
if (frame->storage_type() == media::VideoFrame::STORAGE_GPU_MEMORY_BUFFER) { update_rect = nullptr;
// Use the frame natural size since we delay the scaling.
update_rect = gfx::Rect(frame->natural_size());
} else {
update_rect = gfx::Rect(0, 0, frame->visible_rect().width(),
frame->visible_rect().height());
}
} }
// Clear accumulated_update_rect_. // Clear accumulated_update_rect_.
accumulated_update_rect_ = gfx::Rect(); accumulated_update_rect_ = gfx::Rect();
OnFrame(webrtc::VideoFrame::Builder() webrtc::VideoFrame::Builder frame_builder =
.set_video_frame_buffer( webrtc::VideoFrame::Builder()
new rtc::RefCountedObject<WebRtcVideoFrameAdapter>(frame)) .set_video_frame_buffer(
.set_rotation(webrtc::kVideoRotation_0) new rtc::RefCountedObject<WebRtcVideoFrameAdapter>(frame))
.set_timestamp_us(timestamp_us) .set_rotation(webrtc::kVideoRotation_0)
.set_update_rect(webrtc::VideoFrame::UpdateRect{ .set_timestamp_us(timestamp_us);
update_rect.x(), update_rect.y(), update_rect.width(), if (update_rect) {
update_rect.height()}) frame_builder.set_update_rect(webrtc::VideoFrame::UpdateRect{
.build()); update_rect->x(), update_rect->y(), update_rect->width(),
update_rect->height()});
}
OnFrame(frame_builder.build());
} }
} // namespace blink } // namespace blink
...@@ -58,7 +58,7 @@ class PLATFORM_EXPORT WebRtcVideoTrackSource ...@@ -58,7 +58,7 @@ class PLATFORM_EXPORT WebRtcVideoTrackSource
// |frame->visible_rect()|) has changed since the last delivered frame, the // |frame->visible_rect()|) has changed since the last delivered frame, the
// whole frame is marked as updated. // whole frame is marked as updated.
void DeliverFrame(scoped_refptr<media::VideoFrame> frame, void DeliverFrame(scoped_refptr<media::VideoFrame> frame,
gfx::Rect update_rect, gfx::Rect* update_rect,
int64_t timestamp_us); int64_t timestamp_us);
// |thread_checker_| is bound to the libjingle worker thread. // |thread_checker_| is bound to the libjingle worker thread.
...@@ -72,7 +72,7 @@ class PLATFORM_EXPORT WebRtcVideoTrackSource ...@@ -72,7 +72,7 @@ class PLATFORM_EXPORT WebRtcVideoTrackSource
// Stores the accumulated value of CAPTURE_UPDATE_RECT in case that frames // Stores the accumulated value of CAPTURE_UPDATE_RECT in case that frames
// are dropped. // are dropped.
gfx::Rect accumulated_update_rect_; base::Optional<gfx::Rect> accumulated_update_rect_;
base::Optional<int> previous_capture_counter_; base::Optional<int> previous_capture_counter_;
gfx::Rect cropping_rect_of_previous_delivered_frame_; gfx::Rect cropping_rect_of_previous_delivered_frame_;
gfx::Size natural_size_of_previous_delivered_frame_; gfx::Size natural_size_of_previous_delivered_frame_;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment