diff --git a/talk/media/base/nullvideoframe.h b/talk/media/base/nullvideoframe.h index 26741ad46..fce8545d8 100644 --- a/talk/media/base/nullvideoframe.h +++ b/talk/media/base/nullvideoframe.h @@ -35,10 +35,18 @@ namespace cricket { // Simple subclass for use in mocks. class NullVideoFrame : public VideoFrame { public: - virtual bool Reset(uint32 format, int w, int h, int dw, int dh, uint8 *sample, - size_t sample_size, size_t pixel_width, - size_t pixel_height, int64 elapsed_time, int64 time_stamp, - int rotation) { + virtual bool Reset(uint32 format, + int w, + int h, + int dw, + int dh, + uint8* sample, + size_t sample_size, + size_t pixel_width, + size_t pixel_height, + int64 elapsed_time, + int64 time_stamp, + webrtc::kVideoRotation rotation) { return false; } virtual bool InitToBlack(int w, int h, size_t pixel_width, @@ -65,7 +73,9 @@ class NullVideoFrame : public VideoFrame { virtual int64 GetTimeStamp() const { return 0; } virtual void SetElapsedTime(int64 elapsed_time) {} virtual void SetTimeStamp(int64 time_stamp) {} - virtual int GetRotation() const { return 0; } + virtual webrtc::kVideoRotation GetRotation() const { + return webrtc::kVideoRotation_0; + } virtual VideoFrame *Copy() const { return NULL; } diff --git a/talk/media/base/videocapturer.cc b/talk/media/base/videocapturer.cc index f26b2ce49..7a2619809 100644 --- a/talk/media/base/videocapturer.cc +++ b/talk/media/base/videocapturer.cc @@ -98,6 +98,11 @@ bool CapturedFrame::GetDataSize(uint32* size) const { return true; } +webrtc::kVideoRotation CapturedFrame::GetRotation() const { + ASSERT(rotation == 0 || rotation == 90 || rotation == 180 || rotation == 270); + return static_cast(rotation); +} + ///////////////////////////////////////////////////////////////////// // Implementation of class VideoCapturer ///////////////////////////////////////////////////////////////////// diff --git a/talk/media/base/videocapturer.h b/talk/media/base/videocapturer.h index 98d9f764b..d088d3a9f 100644 --- a/talk/media/base/videocapturer.h +++ b/talk/media/base/videocapturer.h @@ -79,6 +79,10 @@ struct CapturedFrame { // fourcc. Return true if succeeded. bool GetDataSize(uint32* size) const; + // TODO(guoweis): Change the type of |rotation| from int to + // webrtc::kVideoRotation once chromium gets the code. + webrtc::kVideoRotation GetRotation() const; + // The width and height of the captured frame could be different from those // of VideoFormat. Once the first frame is captured, the width, height, // fourcc, pixel_width, and pixel_height should keep the same over frames. @@ -92,7 +96,11 @@ struct CapturedFrame { int64 time_stamp; // timestamp of when the frame was captured, in unix // time with nanosecond units. uint32 data_size; // number of bytes of the frame data + + // TODO(guoweis): This can't be converted to kVideoRotation yet as it's + // used by chrome now. int rotation; // rotation in degrees of the frame (0, 90, 180, 270) + void* data; // pointer to the frame data. This object allocates the // memory or points to an existing memory. diff --git a/talk/media/base/videoframe.h b/talk/media/base/videoframe.h index 1c499e070..b44c5f724 100644 --- a/talk/media/base/videoframe.h +++ b/talk/media/base/videoframe.h @@ -30,17 +30,10 @@ #include "webrtc/base/basictypes.h" #include "webrtc/base/stream.h" +#include "webrtc/common_video/rotation.h" namespace cricket { -// Simple rotation constants. -enum { - ROTATION_0 = 0, - ROTATION_90 = 90, - ROTATION_180 = 180, - ROTATION_270 = 270 -}; - // Represents a YUV420 (a.k.a. I420) video frame. class VideoFrame { public: @@ -55,10 +48,18 @@ class VideoFrame { // |dw| is destination width; can be less than |w| if cropping is desired. // |dh| is destination height, like |dw|, but must be a positive number. // Returns whether the function succeeded or failed. - virtual bool Reset(uint32 fourcc, int w, int h, int dw, int dh, uint8 *sample, - size_t sample_size, size_t pixel_width, - size_t pixel_height, int64_t elapsed_time, - int64_t time_stamp, int rotation) = 0; + virtual bool Reset(uint32 fourcc, + int w, + int h, + int dw, + int dh, + uint8* sample, + size_t sample_size, + size_t pixel_width, + size_t pixel_height, + int64_t elapsed_time, + int64_t time_stamp, + webrtc::kVideoRotation rotation) = 0; // Basic accessors. virtual size_t GetWidth() const = 0; @@ -94,7 +95,7 @@ class VideoFrame { virtual void SetTimeStamp(int64_t time_stamp) = 0; // Indicates the rotation angle in degrees. - virtual int GetRotation() const = 0; + virtual webrtc::kVideoRotation GetRotation() const = 0; // Make a shallow copy of the frame. The frame buffer itself is not copied. // Both the current and new VideoFrame will share a single reference-counted diff --git a/talk/media/base/videoframe_unittest.h b/talk/media/base/videoframe_unittest.h index 483fc34d8..cc6735886 100644 --- a/talk/media/base/videoframe_unittest.h +++ b/talk/media/base/videoframe_unittest.h @@ -42,6 +42,7 @@ #include "webrtc/base/pathutils.h" #include "webrtc/base/stream.h" #include "webrtc/base/stringutils.h" +#include "webrtc/common_video/rotation.h" #if defined(_MSC_VER) #define ALIGN16(var) __declspec(align(16)) var @@ -83,11 +84,16 @@ class VideoFrameTest : public testing::Test { bool LoadFrame(const std::string& filename, uint32 format, int32 width, int32 height, T* frame) { - return LoadFrame(filename, format, width, height, - width, abs(height), 0, frame); + return LoadFrame(filename, format, width, height, width, abs(height), + webrtc::kVideoRotation_0, frame); } - bool LoadFrame(const std::string& filename, uint32 format, - int32 width, int32 height, int dw, int dh, int rotation, + bool LoadFrame(const std::string& filename, + uint32 format, + int32 width, + int32 height, + int dw, + int dh, + webrtc::kVideoRotation rotation, T* frame) { rtc::scoped_ptr ms(LoadSample(filename)); return LoadFrame(ms.get(), format, width, height, dw, dh, rotation, frame); @@ -95,11 +101,16 @@ class VideoFrameTest : public testing::Test { // Load a video frame from a memory stream. bool LoadFrame(rtc::MemoryStream* ms, uint32 format, int32 width, int32 height, T* frame) { - return LoadFrame(ms, format, width, height, - width, abs(height), 0, frame); + return LoadFrame(ms, format, width, height, width, abs(height), + webrtc::kVideoRotation_0, frame); } - bool LoadFrame(rtc::MemoryStream* ms, uint32 format, - int32 width, int32 height, int dw, int dh, int rotation, + bool LoadFrame(rtc::MemoryStream* ms, + uint32 format, + int32 width, + int32 height, + int dw, + int dh, + webrtc::kVideoRotation rotation, T* frame) { if (!ms) { return false; @@ -116,11 +127,17 @@ class VideoFrameTest : public testing::Test { // Load a frame from a raw buffer. bool LoadFrame(uint8* sample, size_t sample_size, uint32 format, int32 width, int32 height, T* frame) { - return LoadFrame(sample, sample_size, format, width, height, - width, abs(height), 0, frame); + return LoadFrame(sample, sample_size, format, width, height, width, + abs(height), webrtc::kVideoRotation_0, frame); } - bool LoadFrame(uint8* sample, size_t sample_size, uint32 format, - int32 width, int32 height, int dw, int dh, int rotation, + bool LoadFrame(uint8* sample, + size_t sample_size, + uint32 format, + int32 width, + int32 height, + int dw, + int dh, + webrtc::kVideoRotation rotation, T* frame) { bool ret = false; for (int i = 0; i < repeat_; ++i) { @@ -805,32 +822,30 @@ class VideoFrameTest : public testing::Test { // Macro to help test different rotations #define TEST_MIRROR(FOURCC, BPP) \ -void Construct##FOURCC##Mirror() { \ + void Construct##FOURCC##Mirror() { \ T frame1, frame2, frame3; \ - rtc::scoped_ptr ms( \ + rtc::scoped_ptr ms( \ CreateYuvSample(kWidth, kHeight, BPP)); \ ASSERT_TRUE(ms.get() != NULL); \ - EXPECT_TRUE(LoadFrame(ms.get(), cricket::FOURCC_##FOURCC, \ - kWidth, -kHeight, kWidth, kHeight, \ - cricket::ROTATION_180, &frame1)); \ + EXPECT_TRUE(LoadFrame(ms.get(), cricket::FOURCC_##FOURCC, kWidth, \ + -kHeight, kWidth, kHeight, \ + webrtc::kVideoRotation_180, &frame1)); \ size_t data_size; \ bool ret = ms->GetSize(&data_size); \ EXPECT_TRUE(ret); \ - EXPECT_TRUE(frame2.Init(cricket::FOURCC_##FOURCC, \ - kWidth, kHeight, kWidth, kHeight, \ + EXPECT_TRUE(frame2.Init(cricket::FOURCC_##FOURCC, kWidth, kHeight, kWidth, \ + kHeight, \ reinterpret_cast(ms->GetBuffer()), \ - data_size, \ - 1, 1, 0, 0, 0)); \ + data_size, 1, 1, 0, 0, webrtc::kVideoRotation_0)); \ int width_rotate = static_cast(frame1.GetWidth()); \ int height_rotate = static_cast(frame1.GetHeight()); \ EXPECT_TRUE(frame3.InitToBlack(width_rotate, height_rotate, 1, 1, 0, 0)); \ - libyuv::I420Mirror(frame2.GetYPlane(), frame2.GetYPitch(), \ - frame2.GetUPlane(), frame2.GetUPitch(), \ - frame2.GetVPlane(), frame2.GetVPitch(), \ - frame3.GetYPlane(), frame3.GetYPitch(), \ - frame3.GetUPlane(), frame3.GetUPitch(), \ - frame3.GetVPlane(), frame3.GetVPitch(), \ - kWidth, kHeight); \ + libyuv::I420Mirror( \ + frame2.GetYPlane(), frame2.GetYPitch(), frame2.GetUPlane(), \ + frame2.GetUPitch(), frame2.GetVPlane(), frame2.GetVPitch(), \ + frame3.GetYPlane(), frame3.GetYPitch(), frame3.GetUPlane(), \ + frame3.GetUPitch(), frame3.GetVPlane(), frame3.GetVPitch(), kWidth, \ + kHeight); \ EXPECT_TRUE(IsEqual(frame1, frame3, 0)); \ } @@ -838,32 +853,30 @@ void Construct##FOURCC##Mirror() { \ // Macro to help test different rotations #define TEST_ROTATE(FOURCC, BPP, ROTATE) \ -void Construct##FOURCC##Rotate##ROTATE() { \ + void Construct##FOURCC##Rotate##ROTATE() { \ T frame1, frame2, frame3; \ - rtc::scoped_ptr ms( \ + rtc::scoped_ptr ms( \ CreateYuvSample(kWidth, kHeight, BPP)); \ ASSERT_TRUE(ms.get() != NULL); \ - EXPECT_TRUE(LoadFrame(ms.get(), cricket::FOURCC_##FOURCC, \ - kWidth, kHeight, kWidth, kHeight, \ - cricket::ROTATION_##ROTATE, &frame1)); \ + EXPECT_TRUE(LoadFrame(ms.get(), cricket::FOURCC_##FOURCC, kWidth, kHeight, \ + kWidth, kHeight, webrtc::kVideoRotation_##ROTATE, \ + &frame1)); \ size_t data_size; \ bool ret = ms->GetSize(&data_size); \ EXPECT_TRUE(ret); \ - EXPECT_TRUE(frame2.Init(cricket::FOURCC_##FOURCC, \ - kWidth, kHeight, kWidth, kHeight, \ + EXPECT_TRUE(frame2.Init(cricket::FOURCC_##FOURCC, kWidth, kHeight, kWidth, \ + kHeight, \ reinterpret_cast(ms->GetBuffer()), \ - data_size, \ - 1, 1, 0, 0, 0)); \ + data_size, 1, 1, 0, 0, webrtc::kVideoRotation_0)); \ int width_rotate = static_cast(frame1.GetWidth()); \ int height_rotate = static_cast(frame1.GetHeight()); \ EXPECT_TRUE(frame3.InitToBlack(width_rotate, height_rotate, 1, 1, 0, 0)); \ - libyuv::I420Rotate(frame2.GetYPlane(), frame2.GetYPitch(), \ - frame2.GetUPlane(), frame2.GetUPitch(), \ - frame2.GetVPlane(), frame2.GetVPitch(), \ - frame3.GetYPlane(), frame3.GetYPitch(), \ - frame3.GetUPlane(), frame3.GetUPitch(), \ - frame3.GetVPlane(), frame3.GetVPitch(), \ - kWidth, kHeight, libyuv::kRotate##ROTATE); \ + libyuv::I420Rotate( \ + frame2.GetYPlane(), frame2.GetYPitch(), frame2.GetUPlane(), \ + frame2.GetUPitch(), frame2.GetVPlane(), frame2.GetVPitch(), \ + frame3.GetYPlane(), frame3.GetYPitch(), frame3.GetUPlane(), \ + frame3.GetUPitch(), frame3.GetVPlane(), frame3.GetVPitch(), kWidth, \ + kHeight, libyuv::kRotate##ROTATE); \ EXPECT_TRUE(IsEqual(frame1, frame3, 0)); \ } @@ -899,9 +912,8 @@ void Construct##FOURCC##Rotate##ROTATE() { \ rtc::scoped_ptr ms( CreateYuv422Sample(cricket::FOURCC_UYVY, kWidth, kHeight)); ASSERT_TRUE(ms.get() != NULL); - EXPECT_TRUE(LoadFrame(ms.get(), cricket::FOURCC_UYVY, - kWidth, kHeight, kWidth, kHeight, - cricket::ROTATION_90, &frame2)); + EXPECT_TRUE(LoadFrame(ms.get(), cricket::FOURCC_UYVY, kWidth, kHeight, + kWidth, kHeight, webrtc::kVideoRotation_90, &frame2)); } // Test constructing an image from a UYVY buffer rotated 180 degrees. @@ -910,9 +922,9 @@ void Construct##FOURCC##Rotate##ROTATE() { \ rtc::scoped_ptr ms( CreateYuv422Sample(cricket::FOURCC_UYVY, kWidth, kHeight)); ASSERT_TRUE(ms.get() != NULL); - EXPECT_TRUE(LoadFrame(ms.get(), cricket::FOURCC_UYVY, - kWidth, kHeight, kWidth, kHeight, - cricket::ROTATION_180, &frame2)); + EXPECT_TRUE(LoadFrame(ms.get(), cricket::FOURCC_UYVY, kWidth, kHeight, + kWidth, kHeight, webrtc::kVideoRotation_180, + &frame2)); } // Test constructing an image from a UYVY buffer rotated 270 degrees. @@ -921,9 +933,9 @@ void Construct##FOURCC##Rotate##ROTATE() { \ rtc::scoped_ptr ms( CreateYuv422Sample(cricket::FOURCC_UYVY, kWidth, kHeight)); ASSERT_TRUE(ms.get() != NULL); - EXPECT_TRUE(LoadFrame(ms.get(), cricket::FOURCC_UYVY, - kWidth, kHeight, kWidth, kHeight, - cricket::ROTATION_270, &frame2)); + EXPECT_TRUE(LoadFrame(ms.get(), cricket::FOURCC_UYVY, kWidth, kHeight, + kWidth, kHeight, webrtc::kVideoRotation_270, + &frame2)); } // Test constructing an image from a YUY2 buffer rotated 90 degrees. @@ -932,9 +944,8 @@ void Construct##FOURCC##Rotate##ROTATE() { \ rtc::scoped_ptr ms( CreateYuv422Sample(cricket::FOURCC_YUY2, kWidth, kHeight)); ASSERT_TRUE(ms.get() != NULL); - EXPECT_TRUE(LoadFrame(ms.get(), cricket::FOURCC_YUY2, - kWidth, kHeight, kWidth, kHeight, - cricket::ROTATION_90, &frame2)); + EXPECT_TRUE(LoadFrame(ms.get(), cricket::FOURCC_YUY2, kWidth, kHeight, + kWidth, kHeight, webrtc::kVideoRotation_90, &frame2)); } // Test constructing an image from a YUY2 buffer rotated 180 degrees. @@ -943,9 +954,9 @@ void Construct##FOURCC##Rotate##ROTATE() { \ rtc::scoped_ptr ms( CreateYuv422Sample(cricket::FOURCC_YUY2, kWidth, kHeight)); ASSERT_TRUE(ms.get() != NULL); - EXPECT_TRUE(LoadFrame(ms.get(), cricket::FOURCC_YUY2, - kWidth, kHeight, kWidth, kHeight, - cricket::ROTATION_180, &frame2)); + EXPECT_TRUE(LoadFrame(ms.get(), cricket::FOURCC_YUY2, kWidth, kHeight, + kWidth, kHeight, webrtc::kVideoRotation_180, + &frame2)); } // Test constructing an image from a YUY2 buffer rotated 270 degrees. @@ -954,9 +965,9 @@ void Construct##FOURCC##Rotate##ROTATE() { \ rtc::scoped_ptr ms( CreateYuv422Sample(cricket::FOURCC_YUY2, kWidth, kHeight)); ASSERT_TRUE(ms.get() != NULL); - EXPECT_TRUE(LoadFrame(ms.get(), cricket::FOURCC_YUY2, - kWidth, kHeight, kWidth, kHeight, - cricket::ROTATION_270, &frame2)); + EXPECT_TRUE(LoadFrame(ms.get(), cricket::FOURCC_YUY2, kWidth, kHeight, + kWidth, kHeight, webrtc::kVideoRotation_270, + &frame2)); } // Test 1 pixel edge case image I420 buffer. @@ -964,9 +975,9 @@ void Construct##FOURCC##Rotate##ROTATE() { \ T frame; uint8 pixel[3] = { 1, 2, 3 }; for (int i = 0; i < repeat_; ++i) { - EXPECT_TRUE(frame.Init(cricket::FOURCC_I420, 1, 1, 1, 1, - pixel, sizeof(pixel), - 1, 1, 0, 0, 0)); + EXPECT_TRUE(frame.Init(cricket::FOURCC_I420, 1, 1, 1, 1, pixel, + sizeof(pixel), 1, 1, 0, 0, + webrtc::kVideoRotation_0)); } const uint8* y = pixel; const uint8* u = y + 1; @@ -981,9 +992,9 @@ void Construct##FOURCC##Rotate##ROTATE() { \ uint8 pixels5x5[5 * 5 + ((5 + 1) / 2 * (5 + 1) / 2) * 2]; memset(pixels5x5, 1, 5 * 5 + ((5 + 1) / 2 * (5 + 1) / 2) * 2); for (int i = 0; i < repeat_; ++i) { - EXPECT_TRUE(frame.Init(cricket::FOURCC_I420, 5, 5, 5, 5, - pixels5x5, sizeof(pixels5x5), - 1, 1, 0, 0, 0)); + EXPECT_TRUE(frame.Init(cricket::FOURCC_I420, 5, 5, 5, 5, pixels5x5, + sizeof(pixels5x5), 1, 1, 0, 0, + webrtc::kVideoRotation_0)); } EXPECT_EQ(4u, frame.GetWidth()); EXPECT_EQ(4u, frame.GetHeight()); @@ -997,9 +1008,9 @@ void Construct##FOURCC##Rotate##ROTATE() { \ T frame; uint8 pixel[4] = { 64, 128, 192, 255 }; for (int i = 0; i < repeat_; ++i) { - EXPECT_TRUE(frame.Init(cricket::FOURCC_ARGB, 1, 1, 1, 1, - pixel, sizeof(pixel), - 1, 1, 0, 0, 0)); + EXPECT_TRUE(frame.Init(cricket::FOURCC_ARGB, 1, 1, 1, 1, pixel, + sizeof(pixel), 1, 1, 0, 0, + webrtc::kVideoRotation_0)); } // Convert back to ARGB. size_t out_size = 4; @@ -1034,9 +1045,9 @@ void Construct##FOURCC##Rotate##ROTATE() { \ 255, 255, 255, 255 }; for (int i = 0; i < repeat_; ++i) { - EXPECT_TRUE(frame.Init(cricket::FOURCC_ARGB, 10, 1, 10, 1, - pixel, sizeof(pixel), - 1, 1, 0, 0, 0)); + EXPECT_TRUE(frame.Init(cricket::FOURCC_ARGB, 10, 1, 10, 1, pixel, + sizeof(pixel), 1, 1, 0, 0, + webrtc::kVideoRotation_0)); } // Convert back to ARGB size_t out_size = 10 * 4; @@ -1057,7 +1068,8 @@ void Construct##FOURCC##Rotate##ROTATE() { \ T frame1, frame2; ASSERT_TRUE(LoadFrameNoRepeat(&frame1)); ASSERT_TRUE(LoadFrame(kImageFilename, cricket::FOURCC_I420, kWidth, kHeight, - kWidth * 3 / 4, kHeight, 0, &frame2)); + kWidth * 3 / 4, kHeight, webrtc::kVideoRotation_0, + &frame2)); EXPECT_TRUE(IsEqualWithCrop(frame2, frame1, kWidth / 8, 0, 0)); } @@ -1070,7 +1082,8 @@ void Construct##FOURCC##Rotate##ROTATE() { \ EXPECT_TRUE(ConvertYuv422(ms.get(), cricket::FOURCC_YUY2, kWidth, kHeight, &frame1)); EXPECT_TRUE(LoadFrame(ms.get(), cricket::FOURCC_YUY2, kWidth, kHeight, - kWidth * 3 / 4, kHeight, 0, &frame2)); + kWidth * 3 / 4, kHeight, webrtc::kVideoRotation_0, + &frame2)); EXPECT_TRUE(IsEqualWithCrop(frame2, frame1, kWidth / 8, 0, 0)); } @@ -1083,7 +1096,8 @@ void Construct##FOURCC##Rotate##ROTATE() { \ EXPECT_TRUE(ConvertRgb(ms.get(), cricket::FOURCC_ARGB, kWidth, kHeight, &frame1)); EXPECT_TRUE(LoadFrame(ms.get(), cricket::FOURCC_ARGB, kWidth, kHeight, - kWidth * 3 / 4, kHeight, 0, &frame2)); + kWidth * 3 / 4, kHeight, webrtc::kVideoRotation_0, + &frame2)); EXPECT_TRUE(IsEqualWithCrop(frame2, frame1, kWidth / 8, 0, 2)); } @@ -1092,7 +1106,8 @@ void Construct##FOURCC##Rotate##ROTATE() { \ T frame1, frame2; ASSERT_TRUE(LoadFrameNoRepeat(&frame1)); ASSERT_TRUE(LoadFrame(kImageFilename, cricket::FOURCC_I420, kWidth, kHeight, - kWidth, kHeight * 3 / 4, 0, &frame2)); + kWidth, kHeight * 3 / 4, webrtc::kVideoRotation_0, + &frame2)); EXPECT_TRUE(IsEqualWithCrop(frame2, frame1, 0, kHeight / 8, 0)); } @@ -1410,10 +1425,9 @@ void Construct##FOURCC##Rotate##ROTATE() { \ EXPECT_TRUE(frame2.InitToBlack(kWidth, kHeight, 1, 1, 0, 0)); EXPECT_TRUE(IsBlack(frame1)); EXPECT_TRUE(IsEqual(frame1, frame2, 0)); - EXPECT_TRUE(frame1.Reset(cricket::FOURCC_I420, - kWidth, kHeight, kWidth, kHeight, - reinterpret_cast(ms->GetBuffer()), - data_size, 1, 1, 0, 0, 0)); + EXPECT_TRUE(frame1.Reset(cricket::FOURCC_I420, kWidth, kHeight, kWidth, + kHeight, reinterpret_cast(ms->GetBuffer()), + data_size, 1, 1, 0, 0, webrtc::kVideoRotation_0)); EXPECT_FALSE(IsBlack(frame1)); EXPECT_FALSE(IsEqual(frame1, frame2, 0)); } @@ -1866,10 +1880,9 @@ void Construct##FOURCC##Rotate##ROTATE() { \ v, kWidth / 2, kWidth, kHeight)); } - EXPECT_TRUE(frame2.Init(cricket::FOURCC_I422, - kWidth, kHeight, kWidth, kHeight, - y, - out_size, 1, 1, 0, 0, cricket::ROTATION_0)); + EXPECT_TRUE(frame2.Init(cricket::FOURCC_I422, kWidth, kHeight, kWidth, + kHeight, y, out_size, 1, 1, 0, 0, + webrtc::kVideoRotation_0)); EXPECT_TRUE(IsEqual(frame1, frame2, 1)); } @@ -2074,9 +2087,9 @@ void Construct##FOURCC##Rotate##ROTATE() { \ memset(out.get(), 0xfb, out_size + 1); // Fill buffer uint8 pixel[3] = { 1, 2, 3 }; T frame; - EXPECT_TRUE(frame.Init(cricket::FOURCC_I420, 1, 1, 1, 1, - pixel, sizeof(pixel), - 1, 1, 0, 0, 0)); + EXPECT_TRUE(frame.Init(cricket::FOURCC_I420, 1, 1, 1, 1, pixel, + sizeof(pixel), 1, 1, 0, 0, + webrtc::kVideoRotation_0)); for (int i = 0; i < repeat_; ++i) { EXPECT_EQ(out_size, frame.CopyToBuffer(out.get(), out_size)); } diff --git a/talk/media/webrtc/webrtctexturevideoframe.cc b/talk/media/webrtc/webrtctexturevideoframe.cc index bf33243d2..d7135cbcc 100644 --- a/talk/media/webrtc/webrtctexturevideoframe.cc +++ b/talk/media/webrtc/webrtctexturevideoframe.cc @@ -52,10 +52,18 @@ bool WebRtcTextureVideoFrame::InitToBlack( return false; } -bool WebRtcTextureVideoFrame::Reset( - uint32 fourcc, int w, int h, int dw, int dh, uint8* sample, - size_t sample_size, size_t pixel_width, size_t pixel_height, - int64_t elapsed_time, int64_t time_stamp, int rotation) { +bool WebRtcTextureVideoFrame::Reset(uint32 fourcc, + int w, + int h, + int dw, + int dh, + uint8* sample, + size_t sample_size, + size_t pixel_width, + size_t pixel_height, + int64_t elapsed_time, + int64_t time_stamp, + webrtc::kVideoRotation rotation) { UNIMPLEMENTED; return false; } diff --git a/talk/media/webrtc/webrtctexturevideoframe.h b/talk/media/webrtc/webrtctexturevideoframe.h index 8918a8bb2..511de27f3 100644 --- a/talk/media/webrtc/webrtctexturevideoframe.h +++ b/talk/media/webrtc/webrtctexturevideoframe.h @@ -46,11 +46,18 @@ class WebRtcTextureVideoFrame : public VideoFrame { virtual bool InitToBlack(int w, int h, size_t pixel_width, size_t pixel_height, int64_t elapsed_time, int64_t time_stamp); - virtual bool Reset(uint32 fourcc, int w, int h, int dw, int dh, uint8* sample, - size_t sample_size, size_t pixel_width, - size_t pixel_height, int64_t elapsed_time, + virtual bool Reset(uint32 fourcc, + int w, + int h, + int dw, + int dh, + uint8* sample, + size_t sample_size, + size_t pixel_width, + size_t pixel_height, + int64_t elapsed_time, int64_t time_stamp, - int rotation); + webrtc::kVideoRotation rotation); virtual size_t GetWidth() const { return width_; } virtual size_t GetHeight() const { return height_; } virtual const uint8* GetYPlane() const; @@ -70,7 +77,9 @@ class WebRtcTextureVideoFrame : public VideoFrame { elapsed_time_ = elapsed_time; } virtual void SetTimeStamp(int64_t time_stamp) { time_stamp_ = time_stamp; } - virtual int GetRotation() const { return 0; } + virtual webrtc::kVideoRotation GetRotation() const { + return webrtc::kVideoRotation_0; + } virtual VideoFrame* Copy() const; virtual bool MakeExclusive(); virtual size_t CopyToBuffer(uint8* buffer, size_t size) const; diff --git a/talk/media/webrtc/webrtcvideoengine.cc b/talk/media/webrtc/webrtcvideoengine.cc index e4d6447e6..2e500df33 100644 --- a/talk/media/webrtc/webrtcvideoengine.cc +++ b/talk/media/webrtc/webrtcvideoengine.cc @@ -430,8 +430,8 @@ class WebRtcRenderAdapter : public webrtc::ExternalRenderer { int DeliverBufferFrame(unsigned char* buffer, size_t buffer_size, int64 time_stamp, int64 elapsed_time) { WebRtcVideoFrame video_frame; - video_frame.Alias(buffer, buffer_size, width_, height_, - 1, 1, elapsed_time, time_stamp, 0); + video_frame.Alias(buffer, buffer_size, width_, height_, 1, 1, elapsed_time, + time_stamp, webrtc::kVideoRotation_0); // Sanity check on decoded frame size. if (buffer_size != VideoFrame::SizeOf(width_, height_)) { diff --git a/talk/media/webrtc/webrtcvideoframe.cc b/talk/media/webrtc/webrtcvideoframe.cc index 2dd4799f9..42b87e065 100644 --- a/talk/media/webrtc/webrtcvideoframe.cc +++ b/talk/media/webrtc/webrtcvideoframe.cc @@ -115,10 +115,18 @@ WebRtcVideoFrame::WebRtcVideoFrame() WebRtcVideoFrame::~WebRtcVideoFrame() {} -bool WebRtcVideoFrame::Init( - uint32 format, int w, int h, int dw, int dh, uint8* sample, - size_t sample_size, size_t pixel_width, size_t pixel_height, - int64_t elapsed_time, int64_t time_stamp, int rotation) { +bool WebRtcVideoFrame::Init(uint32 format, + int w, + int h, + int dw, + int dh, + uint8* sample, + size_t sample_size, + size_t pixel_width, + size_t pixel_height, + int64_t elapsed_time, + int64_t time_stamp, + webrtc::kVideoRotation rotation) { return Reset(format, w, h, dw, dh, sample, sample_size, pixel_width, pixel_height, elapsed_time, time_stamp, rotation); } @@ -127,24 +135,19 @@ bool WebRtcVideoFrame::Init(const CapturedFrame* frame, int dw, int dh) { return Reset(frame->fourcc, frame->width, frame->height, dw, dh, static_cast(frame->data), frame->data_size, frame->pixel_width, frame->pixel_height, frame->elapsed_time, - frame->time_stamp, frame->rotation); + frame->time_stamp, frame->GetRotation()); } bool WebRtcVideoFrame::Alias(const CapturedFrame* frame, int dw, int dh) { - if (CanonicalFourCC(frame->fourcc) != FOURCC_I420 || frame->rotation != 0 || + if (CanonicalFourCC(frame->fourcc) != FOURCC_I420 || + (frame->GetRotation() != webrtc::kVideoRotation_0) || frame->width != dw || frame->height != dh) { // TODO(fbarchard): Enable aliasing of more formats. return Init(frame, dw, dh); } else { - Alias(static_cast(frame->data), - frame->data_size, - frame->width, - frame->height, - frame->pixel_width, - frame->pixel_height, - frame->elapsed_time, - frame->time_stamp, - frame->rotation); + Alias(static_cast(frame->data), frame->data_size, frame->width, + frame->height, frame->pixel_width, frame->pixel_height, + frame->elapsed_time, frame->time_stamp, frame->GetRotation()); return true; } } @@ -156,10 +159,15 @@ bool WebRtcVideoFrame::InitToBlack(int w, int h, size_t pixel_width, return SetToBlack(); } -void WebRtcVideoFrame::Alias( - uint8* buffer, size_t buffer_size, int w, int h, size_t pixel_width, - size_t pixel_height, int64_t elapsed_time, int64_t time_stamp, - int rotation) { +void WebRtcVideoFrame::Alias(uint8* buffer, + size_t buffer_size, + int w, + int h, + size_t pixel_width, + size_t pixel_height, + int64_t elapsed_time, + int64_t time_stamp, + webrtc::kVideoRotation rotation) { rtc::scoped_refptr video_buffer( new RefCountedBuffer()); video_buffer->Alias(buffer, buffer_size); @@ -257,10 +265,15 @@ size_t WebRtcVideoFrame::ConvertToRgbBuffer(uint32 to_fourcc, uint8* buffer, return VideoFrame::ConvertToRgbBuffer(to_fourcc, buffer, size, stride_rgb); } -void WebRtcVideoFrame::Attach( - RefCountedBuffer* video_buffer, size_t buffer_size, int w, int h, - size_t pixel_width, size_t pixel_height, int64_t elapsed_time, - int64_t time_stamp, int rotation) { +void WebRtcVideoFrame::Attach(RefCountedBuffer* video_buffer, + size_t buffer_size, + int w, + int h, + size_t pixel_width, + size_t pixel_height, + int64_t elapsed_time, + int64_t time_stamp, + webrtc::kVideoRotation rotation) { if (video_buffer_.get() == video_buffer) { return; } @@ -282,10 +295,18 @@ const webrtc::VideoFrame* WebRtcVideoFrame::frame() const { return video_buffer_->frame(); } -bool WebRtcVideoFrame::Reset( - uint32 format, int w, int h, int dw, int dh, uint8* sample, - size_t sample_size, size_t pixel_width, size_t pixel_height, - int64_t elapsed_time, int64_t time_stamp, int rotation) { +bool WebRtcVideoFrame::Reset(uint32 format, + int w, + int h, + int dw, + int dh, + uint8* sample, + size_t sample_size, + size_t pixel_width, + size_t pixel_height, + int64_t elapsed_time, + int64_t time_stamp, + webrtc::kVideoRotation rotation) { if (!Validate(format, w, h, sample, sample_size)) { return false; } @@ -313,7 +334,7 @@ bool WebRtcVideoFrame::Reset( // Since the libyuv::ConvertToI420 will handle the rotation, so the // new frame's rotation should always be 0. Attach(video_buffer.get(), desired_size, new_width, new_height, pixel_width, - pixel_height, elapsed_time, time_stamp, 0); + pixel_height, elapsed_time, time_stamp, webrtc::kVideoRotation_0); int horiz_crop = ((w - dw) / 2) & ~1; // ARGB on Windows has negative height. @@ -356,7 +377,7 @@ void WebRtcVideoFrame::InitToEmptyBuffer(int w, int h, size_t pixel_width, rtc::scoped_refptr video_buffer( new RefCountedBuffer(buffer_size)); Attach(video_buffer.get(), buffer_size, w, h, pixel_width, pixel_height, - elapsed_time, time_stamp, 0); + elapsed_time, time_stamp, webrtc::kVideoRotation_0); } WebRtcVideoRenderFrame::WebRtcVideoRenderFrame( @@ -386,7 +407,7 @@ bool WebRtcVideoRenderFrame::Reset(uint32 fourcc, size_t pixel_height, int64_t elapsed_time, int64_t time_stamp, - int rotation) { + webrtc::kVideoRotation rotation) { UNIMPLEMENTED; return false; } @@ -455,9 +476,9 @@ void WebRtcVideoRenderFrame::SetTimeStamp(int64_t time_stamp) { UNIMPLEMENTED; } -int WebRtcVideoRenderFrame::GetRotation() const { +webrtc::kVideoRotation WebRtcVideoRenderFrame::GetRotation() const { UNIMPLEMENTED; - return ROTATION_0; + return webrtc::kVideoRotation_0; } // TODO(magjed): Make this copy shallow instead of deep, BUG=1128. There is no diff --git a/talk/media/webrtc/webrtcvideoframe.h b/talk/media/webrtc/webrtcvideoframe.h index f025163db..35f80f2a4 100644 --- a/talk/media/webrtc/webrtcvideoframe.h +++ b/talk/media/webrtc/webrtcvideoframe.h @@ -52,9 +52,18 @@ class WebRtcVideoFrame : public VideoFrame { // "h" can be negative indicating a vertically flipped image. // "dh" is destination height if cropping is desired and is always positive. // Returns "true" if successful. - bool Init(uint32 format, int w, int h, int dw, int dh, uint8* sample, - size_t sample_size, size_t pixel_width, size_t pixel_height, - int64_t elapsed_time, int64_t time_stamp, int rotation); + bool Init(uint32 format, + int w, + int h, + int dw, + int dh, + uint8* sample, + size_t sample_size, + size_t pixel_width, + size_t pixel_height, + int64_t elapsed_time, + int64_t time_stamp, + webrtc::kVideoRotation rotation); bool Init(const CapturedFrame* frame, int dw, int dh); @@ -70,18 +79,32 @@ class WebRtcVideoFrame : public VideoFrame { // Aliases this WebRtcVideoFrame to a memory buffer. |buffer| must outlive // this WebRtcVideoFrame. - void Alias(uint8* buffer, size_t buffer_size, int w, int h, - size_t pixel_width, size_t pixel_height, int64_t elapsed_time, - int64_t time_stamp, int rotation); + void Alias(uint8* buffer, + size_t buffer_size, + int w, + int h, + size_t pixel_width, + size_t pixel_height, + int64_t elapsed_time, + int64_t time_stamp, + webrtc::kVideoRotation rotation); webrtc::VideoFrame* frame(); const webrtc::VideoFrame* frame() const; // From base class VideoFrame. - virtual bool Reset(uint32 format, int w, int h, int dw, int dh, uint8* sample, - size_t sample_size, size_t pixel_width, - size_t pixel_height, int64_t elapsed_time, - int64_t time_stamp, int rotation); + virtual bool Reset(uint32 format, + int w, + int h, + int dw, + int dh, + uint8* sample, + size_t sample_size, + size_t pixel_width, + size_t pixel_height, + int64_t elapsed_time, + int64_t time_stamp, + webrtc::kVideoRotation rotation); virtual size_t GetWidth() const; virtual size_t GetHeight() const; @@ -105,7 +128,7 @@ class WebRtcVideoFrame : public VideoFrame { } virtual void SetTimeStamp(int64_t time_stamp) { time_stamp_ = time_stamp; } - virtual int GetRotation() const { return rotation_; } + virtual webrtc::kVideoRotation GetRotation() const { return rotation_; } virtual VideoFrame* Copy() const; virtual bool MakeExclusive(); @@ -117,9 +140,15 @@ class WebRtcVideoFrame : public VideoFrame { class FrameBuffer; typedef rtc::RefCountedObject RefCountedBuffer; - void Attach(RefCountedBuffer* video_buffer, size_t buffer_size, int w, int h, - size_t pixel_width, size_t pixel_height, int64_t elapsed_time, - int64_t time_stamp, int rotation); + void Attach(RefCountedBuffer* video_buffer, + size_t buffer_size, + int w, + int h, + size_t pixel_width, + size_t pixel_height, + int64_t elapsed_time, + int64_t time_stamp, + webrtc::kVideoRotation rotation); virtual VideoFrame* CreateEmptyFrame(int w, int h, size_t pixel_width, size_t pixel_height, @@ -131,7 +160,7 @@ class WebRtcVideoFrame : public VideoFrame { size_t pixel_height_; int64_t elapsed_time_; int64_t time_stamp_; - int rotation_; + webrtc::kVideoRotation rotation_; }; // Thin map between VideoFrame and an existing webrtc::I420VideoFrame @@ -160,7 +189,7 @@ class WebRtcVideoRenderFrame : public VideoFrame { size_t pixel_height, int64_t elapsed_time, int64_t time_stamp, - int rotation) OVERRIDE; + webrtc::kVideoRotation rotation) OVERRIDE; virtual size_t GetWidth() const OVERRIDE; virtual size_t GetHeight() const OVERRIDE; virtual const uint8* GetYPlane() const OVERRIDE; @@ -179,7 +208,7 @@ class WebRtcVideoRenderFrame : public VideoFrame { virtual int64_t GetTimeStamp() const OVERRIDE; virtual void SetElapsedTime(int64_t elapsed_time) OVERRIDE; virtual void SetTimeStamp(int64_t time_stamp) OVERRIDE; - virtual int GetRotation() const OVERRIDE; + virtual webrtc::kVideoRotation GetRotation() const OVERRIDE; virtual VideoFrame* Copy() const OVERRIDE; virtual bool MakeExclusive() OVERRIDE; virtual size_t CopyToBuffer(uint8* buffer, size_t size) const OVERRIDE; diff --git a/talk/media/webrtc/webrtcvideoframe_unittest.cc b/talk/media/webrtc/webrtcvideoframe_unittest.cc index 5f65c5822..656183c31 100644 --- a/talk/media/webrtc/webrtcvideoframe_unittest.cc +++ b/talk/media/webrtc/webrtcvideoframe_unittest.cc @@ -44,7 +44,7 @@ class WebRtcVideoFrameTest : public VideoFrameTest { captured_frame.pixel_height = 1; captured_frame.elapsed_time = 1234; captured_frame.time_stamp = 5678; - captured_frame.rotation = 0; + captured_frame.rotation = webrtc::kVideoRotation_0; captured_frame.width = frame_width; captured_frame.height = frame_height; captured_frame.data_size = (frame_width * frame_height) + @@ -62,7 +62,7 @@ class WebRtcVideoFrameTest : public VideoFrameTest { EXPECT_EQ(1u, frame.GetPixelHeight()); EXPECT_EQ(1234, frame.GetElapsedTime()); EXPECT_EQ(5678, frame.GetTimeStamp()); - EXPECT_EQ(0, frame.GetRotation()); + EXPECT_EQ(webrtc::kVideoRotation_0, frame.GetRotation()); // The size of the new frame should have been cropped to multiple of 4. EXPECT_EQ(static_cast(cropped_width & ~3), frame.GetWidth()); EXPECT_EQ(static_cast(cropped_height & ~3), frame.GetHeight()); @@ -266,9 +266,9 @@ TEST_F(WebRtcVideoFrameTest, Alias) { const int64 time_stamp = INT64_C(0x7FFFFFFFFFFFFFF0); frame1.SetTimeStamp(time_stamp); EXPECT_EQ(time_stamp, frame1.GetTimeStamp()); - frame2.Alias(frame1.frame()->Buffer(), frame1.frame()->Size(), - kWidth, kHeight, 1, 1, - frame1.GetElapsedTime(), frame1.GetTimeStamp(), 0); + frame2.Alias(frame1.frame()->Buffer(), frame1.frame()->Size(), kWidth, + kHeight, 1, 1, frame1.GetElapsedTime(), frame1.GetTimeStamp(), + webrtc::kVideoRotation_0); EXPECT_TRUE(IsEqual(frame1, frame2, 0)); } diff --git a/webrtc/common_video/rotation.h b/webrtc/common_video/rotation.h new file mode 100644 index 000000000..ec301ab2c --- /dev/null +++ b/webrtc/common_video/rotation.h @@ -0,0 +1,28 @@ +/* + * Copyright (c) 2015 The WebRTC project authors. All Rights Reserved. + * + * Use of this source code is governed by a BSD-style license + * that can be found in the LICENSE file in the root of the source + * tree. An additional intellectual property rights grant can be found + * in the file PATENTS. All contributing project authors may + * be found in the AUTHORS file in the root of the source tree. + */ + +#ifndef WEBRTC_COMMON_VIDEO_ROTATION_H_ +#define WEBRTC_COMMON_VIDEO_ROTATION_H_ + +#include "webrtc/base/common.h" + +namespace webrtc { + +// enum for clockwise rotation. +enum kVideoRotation { + kVideoRotation_0 = 0, + kVideoRotation_90 = 90, + kVideoRotation_180 = 180, + kVideoRotation_270 = 270 +}; + +} // namespace webrtc + +#endif // WEBRTC_COMMON_VIDEO_ROTATION_H_