Add concept of whether video renderer supports rotation.

Rotation is best done when rendered in GPU, added the shader code which rotates the frame. For renderers which don't support rotation, the rotation will be done before sending down the frame to render. By default, assume renderer can't do rotation.

Tested with peerconnection_client on windows, AppRTCDemo on Mac.

BUG=4145
R=glaznev@webrtc.org, pthatcher@webrtc.org

Committed: https://code.google.com/p/webrtc/source/detail?r=8660

Committed: https://code.google.com/p/webrtc/source/detail?r=8661

Review URL: https://webrtc-codereview.appspot.com/43569004

Cr-Commit-Position: refs/heads/master@{#8705}
git-svn-id: http://webrtc.googlecode.com/svn/trunk@8705 4adac7df-926f-26a2-2b94-8c16560cd09d
This commit is contained in:
guoweis@webrtc.org
2015-03-12 21:37:26 +00:00
parent 04cd69887d
commit 00c509ad1c
23 changed files with 379 additions and 119 deletions

View File

@ -293,4 +293,49 @@ void WebRtcVideoFrame::InitToEmptyBuffer(int w, int h, size_t pixel_width,
rotation_ = webrtc::kVideoRotation_0;
}
const VideoFrame* WebRtcVideoFrame::GetCopyWithRotationApplied() const {
// If the frame is not rotated, the caller should reuse this frame instead of
// making a redundant copy.
if (GetVideoRotation() == webrtc::kVideoRotation_0) {
return this;
}
// If the video frame is backed up by a native handle, it resides in the GPU
// memory which we can't rotate here. The assumption is that the renderers
// which uses GPU to render should be able to rotate themselves.
DCHECK(!GetNativeHandle());
if (rotated_frame_) {
return rotated_frame_.get();
}
int width = static_cast<int>(GetWidth());
int height = static_cast<int>(GetHeight());
int rotated_width = width;
int rotated_height = height;
if (GetVideoRotation() == webrtc::kVideoRotation_90 ||
GetVideoRotation() == webrtc::kVideoRotation_270) {
rotated_width = height;
rotated_height = width;
}
rotated_frame_.reset(CreateEmptyFrame(rotated_width, rotated_height,
GetPixelWidth(), GetPixelHeight(),
GetElapsedTime(), GetTimeStamp()));
// TODO(guoweis): Add a function in webrtc_libyuv.cc to convert from
// VideoRotation to libyuv::RotationMode.
int ret = libyuv::I420Rotate(
GetYPlane(), GetYPitch(), GetUPlane(), GetUPitch(), GetVPlane(),
GetVPitch(), rotated_frame_->GetYPlane(), rotated_frame_->GetYPitch(),
rotated_frame_->GetUPlane(), rotated_frame_->GetUPitch(),
rotated_frame_->GetVPlane(), rotated_frame_->GetVPitch(), width, height,
static_cast<libyuv::RotationMode>(GetVideoRotation()));
if (ret == 0) {
return rotated_frame_.get();
}
return nullptr;
}
} // namespace cricket