Chromium Code Reviews| Index: media/base/video_frame.cc |
| diff --git a/media/base/video_frame.cc b/media/base/video_frame.cc |
| index 089af93c0c88d11e68e5583fc94ac5163a9f6cca..4df8dff2c3453c25dec707cca57ecd06f7a81e60 100644 |
| --- a/media/base/video_frame.cc |
| +++ b/media/base/video_frame.cc |
| @@ -36,6 +36,8 @@ scoped_refptr<VideoFrame> VideoFrame::CreateFrame( |
| // request does not line up on sample boundaries. |
| gfx::Size new_coded_size(coded_size); |
| switch (format) { |
| + case VideoFrame::I444: |
| + break; |
| case VideoFrame::YV12: |
| case VideoFrame::YV12A: |
| case VideoFrame::I420: |
| @@ -85,6 +87,8 @@ std::string VideoFrame::FormatToString(VideoFrame::Format format) { |
| return "YV12J"; |
| case VideoFrame::NV12: |
| return "NV12"; |
| + case VideoFrame::I444: |
| + return "I444"; |
| } |
| NOTREACHED() << "Invalid videoframe format provided: " << format; |
| return ""; |
| @@ -112,12 +116,14 @@ bool VideoFrame::IsValidConfig(VideoFrame::Format format, |
| case VideoFrame::UNKNOWN: |
| return (coded_size.IsEmpty() && visible_rect.IsEmpty() && |
| natural_size.IsEmpty()); |
| + case VideoFrame::I444: |
| + break; |
| case VideoFrame::YV12: |
| case VideoFrame::YV12J: |
| case VideoFrame::I420: |
| case VideoFrame::YV12A: |
| case VideoFrame::NV12: |
| - // YUV formats have width/height requirements due to chroma subsampling. |
| + // Subsampled YUV formats have width/height requirements. |
| if (static_cast<size_t>(coded_size.height()) < |
| RoundUp(visible_rect.bottom(), 2)) |
| return false; |
| @@ -390,6 +396,7 @@ size_t VideoFrame::NumPlanes(Format format) { |
| case VideoFrame::YV16: |
| case VideoFrame::I420: |
| case VideoFrame::YV12J: |
| + case VideoFrame::I444: |
| return 3; |
| case VideoFrame::YV12A: |
| return 4; |
| @@ -413,12 +420,25 @@ size_t VideoFrame::AllocationSize(Format format, const gfx::Size& coded_size) { |
| gfx::Size VideoFrame::PlaneSize(Format format, |
| size_t plane, |
| const gfx::Size& coded_size) { |
| + // Align to multiple-of-two size overall. This ensures that non-subsampled |
| + // planes can be addressed by pixel with the same scaling as the subsampled |
| + // planes. |
| const int width = RoundUp(coded_size.width(), 2); |
| const int height = RoundUp(coded_size.height(), 2); |
| switch (format) { |
| + case VideoFrame::I444: |
| + switch (plane) { |
| + case VideoFrame::kYPlane: |
| + case VideoFrame::kUPlane: |
| + case VideoFrame::kVPlane: |
| + return gfx::Size(width, height); |
| + default: |
| + break; |
| + } |
| + break; |
| case VideoFrame::YV12: |
| case VideoFrame::YV12J: |
| - case VideoFrame::I420: { |
| + case VideoFrame::I420: |
| switch (plane) { |
| case VideoFrame::kYPlane: |
| return gfx::Size(width, height); |
| @@ -428,8 +448,8 @@ gfx::Size VideoFrame::PlaneSize(Format format, |
| default: |
| break; |
| } |
| - } |
| - case VideoFrame::YV12A: { |
| + break; |
| + case VideoFrame::YV12A: |
| switch (plane) { |
| case VideoFrame::kYPlane: |
| case VideoFrame::kAPlane: |
| @@ -440,8 +460,8 @@ gfx::Size VideoFrame::PlaneSize(Format format, |
| default: |
| break; |
| } |
| - } |
| - case VideoFrame::YV16: { |
| + break; |
| + case VideoFrame::YV16: |
| switch (plane) { |
| case VideoFrame::kYPlane: |
| return gfx::Size(width, height); |
| @@ -451,8 +471,8 @@ gfx::Size VideoFrame::PlaneSize(Format format, |
| default: |
| break; |
| } |
| - } |
| - case VideoFrame::NV12: { |
| + break; |
| + case VideoFrame::NV12: |
| switch (plane) { |
| case VideoFrame::kYPlane: |
| return gfx::Size(width, height); |
| @@ -461,7 +481,7 @@ gfx::Size VideoFrame::PlaneSize(Format format, |
| default: |
| break; |
| } |
| - } |
| + break; |
| case VideoFrame::UNKNOWN: |
| case VideoFrame::NATIVE_TEXTURE: |
| #if defined(VIDEO_HOLE) |
| @@ -484,14 +504,20 @@ size_t VideoFrame::PlaneAllocationSize(Format format, |
| // static |
| int VideoFrame::PlaneHorizontalBitsPerPixel(Format format, size_t plane) { |
| switch (format) { |
| - case VideoFrame::YV12A: |
| - if (plane == kAPlane) |
| - return 8; |
| - // fallthrough |
| + case VideoFrame::I444: |
| + switch (plane) { |
| + case kYPlane: |
| + case kUPlane: |
| + case kVPlane: |
| + return 8; |
| + default: |
| + break; |
| + } |
| + break; |
| case VideoFrame::YV12: |
| case VideoFrame::YV16: |
| case VideoFrame::I420: |
| - case VideoFrame::YV12J: { |
| + case VideoFrame::YV12J: |
| switch (plane) { |
| case kYPlane: |
| return 8; |
| @@ -501,9 +527,20 @@ int VideoFrame::PlaneHorizontalBitsPerPixel(Format format, size_t plane) { |
| default: |
| break; |
| } |
| - } |
| - |
| - case VideoFrame::NV12: { |
| + break; |
| + case VideoFrame::YV12A: |
| + switch (plane) { |
| + case kYPlane: |
| + case kAPlane: |
| + return 8; |
| + case kUPlane: |
| + case kVPlane: |
| + return 2; |
| + default: |
| + break; |
| + } |
| + break; |
| + case VideoFrame::NV12: |
| switch (plane) { |
| case kYPlane: |
| return 8; |
| @@ -512,12 +549,12 @@ int VideoFrame::PlaneHorizontalBitsPerPixel(Format format, size_t plane) { |
| default: |
| break; |
| } |
| - } |
| + break; |
| default: |
|
scherkus (not reviewing)
2014/05/22 23:45:11
can you replace the default cases w/ the other for
sandersd (OOO until July 31)
2014/05/23 00:45:22
Done.
|
| break; |
| } |
| - |
| - NOTREACHED() << "Unsupported video frame format: " << format; |
| + NOTREACHED() << "Unsupported video frame format/plane: " |
| + << format << "/" << plane; |
| return 0; |
| } |
| @@ -530,7 +567,7 @@ static void ReleaseData(uint8* data) { |
| void VideoFrame::AllocateYUV() { |
| DCHECK(format_ == VideoFrame::YV12 || format_ == VideoFrame::YV16 || |
| format_ == VideoFrame::YV12A || format_ == VideoFrame::I420 || |
| - format_ == VideoFrame::YV12J); |
| + format_ == VideoFrame::YV12J || format_ == VideoFrame::I444); |
| // Align Y rows at least at 16 byte boundaries. The stride for both |
| // YV12 and YV16 is 1/2 of the stride of Y. For YV12, every row of bytes for |
| // U and V applies to two rows of Y (one byte of UV for 4 bytes of Y), so in |
| @@ -541,11 +578,11 @@ void VideoFrame::AllocateYUV() { |
| // the Y values of the final row, but assumes that the last row of U & V |
| // applies to a full two rows of Y. YV12A is the same as YV12, but with an |
| // additional alpha plane that has the same size and alignment as the Y plane. |
| - |
| size_t y_stride = RoundUp(row_bytes(VideoFrame::kYPlane), |
| kFrameSizeAlignment); |
| size_t uv_stride = RoundUp(row_bytes(VideoFrame::kUPlane), |
| kFrameSizeAlignment); |
| + |
| // The *2 here is because some formats (e.g. h264) allow interlaced coding, |
| // and then the size needs to be a multiple of two macroblocks (vertically). |
| // See libavcodec/utils.c:avcodec_align_dimensions2(). |
| @@ -627,69 +664,117 @@ int VideoFrame::stride(size_t plane) const { |
| int VideoFrame::row_bytes(size_t plane) const { |
| DCHECK(IsValidPlane(plane)); |
| int width = coded_size_.width(); |
| + // Intentionally leave out non-production formats. |
| switch (format_) { |
| - // Planar, 8bpp. |
| - case YV12A: |
| - if (plane == kAPlane) |
| - return width; |
| - // Fallthrough. |
| + case I444: |
| + switch (plane) { |
| + case kYPlane: |
| + case kUPlane: |
| + case kVPlane: |
| + return width; |
| + default: |
| + break; |
| + } |
| + break; |
| case YV12: |
| case YV16: |
| case I420: |
| case YV12J: |
| - if (plane == kYPlane) |
| - return width; |
| - else if (plane <= kVPlane) |
| - return RoundUp(width, 2) / 2; |
| + switch (plane) { |
| + case kYPlane: |
| + return width; |
| + case kUPlane: |
| + case kVPlane: |
| + return RoundUp(width, 2) / 2; |
| + default: |
| + break; |
| + } |
| + break; |
| + case YV12A: |
| + switch (plane) { |
| + case kYPlane: |
| + case kAPlane: |
| + return width; |
| + case kUPlane: |
| + case kVPlane: |
| + return RoundUp(width, 2) / 2; |
| + default: |
| + break; |
| + } |
| break; |
| - |
| case NV12: |
| - if (plane <= kUVPlane) |
| - return width; |
| + switch (plane) { |
| + case kYPlane: |
| + case kUVPlane: |
| + return width; |
| + default: |
| + break; |
| + } |
| break; |
| - |
| default: |
|
scherkus (not reviewing)
2014/05/22 23:45:11
ditto -- and remove the comment about intentionall
sandersd (OOO until July 31)
2014/05/23 00:45:22
Done.
|
| break; |
| } |
| - |
| - // Intentionally leave out non-production formats. |
| - NOTREACHED() << "Unsupported video frame format: " << format_; |
| + NOTREACHED() << "Unsupported video frame format/plane: " |
| + << format_ << "/" << plane; |
| return 0; |
| } |
| int VideoFrame::rows(size_t plane) const { |
| DCHECK(IsValidPlane(plane)); |
| int height = coded_size_.height(); |
| + // Intentionally leave out non-production formats. |
| switch (format_) { |
| + case I444: |
| case YV16: |
| - return height; |
| - |
| - case YV12A: |
| - if (plane == kAPlane) |
| - return height; |
| - // Fallthrough. |
| + switch (plane) { |
| + case kYPlane: |
| + case kUPlane: |
| + case kVPlane: |
| + return height; |
| + default: |
| + break; |
| + } |
| + break; |
| case YV12: |
| case YV12J: |
| case I420: |
| - if (plane == kYPlane) |
| - return height; |
| - else if (plane <= kVPlane) |
| - return RoundUp(height, 2) / 2; |
| + switch (plane) { |
| + case kYPlane: |
| + return height; |
| + case kUPlane: |
| + case kVPlane: |
| + return RoundUp(height, 2) / 2; |
| + default: |
| + break; |
| + } |
| + break; |
| + case YV12A: |
| + switch (plane) { |
| + case kYPlane: |
| + case kAPlane: |
| + return height; |
| + case kUPlane: |
| + case kVPlane: |
| + return RoundUp(height, 2) / 2; |
| + default: |
| + break; |
| + } |
| break; |
| - |
| case NV12: |
| - if (plane == kYPlane) |
| - return height; |
| - else if (plane == kUVPlane) |
| - return RoundUp(height, 2) / 2; |
| + switch (plane) { |
| + case kYPlane: |
| + return height; |
| + case kUVPlane: |
| + return RoundUp(height, 2) / 2; |
| + default: |
| + break; |
| + } |
| break; |
| - |
| default: |
|
scherkus (not reviewing)
2014/05/22 23:45:11
ditto
sandersd (OOO until July 31)
2014/05/23 00:45:22
Done.
|
| break; |
| } |
| - |
| - // Intentionally leave out non-production formats. |
| - NOTREACHED() << "Unsupported video frame format: " << format_; |
| + NOTREACHED() << "Unsupported video frame format/plane: " |
| + << format_ << "/" << plane; |
| return 0; |
| } |