| OLD | NEW |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "remoting/codec/video_decoder_verbatim.h" | 5 #include "remoting/codec/video_decoder_verbatim.h" |
| 6 | 6 |
| 7 #include "base/logging.h" | 7 #include "base/logging.h" |
| 8 #include "remoting/base/util.h" | 8 #include "remoting/base/util.h" |
| 9 | 9 |
| 10 namespace remoting { | 10 namespace remoting { |
| 11 | 11 |
| 12 namespace { | 12 namespace { |
| 13 // Both input and output data are assumed to be RGBA32. | 13 // Both input and output data are assumed to be RGBA32. |
| 14 const int kBytesPerPixel = 4; | 14 const int kBytesPerPixel = 4; |
| 15 } // namespace | 15 } // namespace |
| 16 | 16 |
| 17 VideoDecoderVerbatim::VideoDecoderVerbatim() | 17 VideoDecoderVerbatim::VideoDecoderVerbatim() {} |
| 18 : screen_size_(SkISize::Make(0, 0)) {} | |
| 19 | 18 |
| 20 VideoDecoderVerbatim::~VideoDecoderVerbatim() {} | 19 VideoDecoderVerbatim::~VideoDecoderVerbatim() {} |
| 21 | 20 |
| 22 bool VideoDecoderVerbatim::IsReadyForData() { | 21 bool VideoDecoderVerbatim::IsReadyForData() { |
| 23 return true; | 22 return true; |
| 24 } | 23 } |
| 25 | 24 |
| 26 void VideoDecoderVerbatim::Initialize(const SkISize& screen_size) { | 25 void VideoDecoderVerbatim::Initialize(const webrtc::DesktopSize& screen_size) { |
| 27 updated_region_.setEmpty(); | 26 updated_region_.Clear(); |
| 28 screen_buffer_.reset(); | 27 screen_buffer_.reset(); |
| 29 | 28 |
| 30 screen_size_ = screen_size; | 29 screen_size_ = screen_size; |
| 31 // Allocate the screen buffer, if necessary. | 30 // Allocate the screen buffer, if necessary. |
| 32 if (!screen_size_.isEmpty()) { | 31 if (!screen_size_.is_empty()) { |
| 33 screen_buffer_.reset( | 32 screen_buffer_.reset( |
| 34 new uint8 | 33 new uint8 |
| 35 [screen_size_.width() * screen_size_.height() * kBytesPerPixel]); | 34 [screen_size_.width() * screen_size_.height() * kBytesPerPixel]); |
| 36 } | 35 } |
| 37 } | 36 } |
| 38 | 37 |
| 39 VideoDecoder::DecodeResult VideoDecoderVerbatim::DecodePacket( | 38 VideoDecoder::DecodeResult VideoDecoderVerbatim::DecodePacket( |
| 40 const VideoPacket* packet) { | 39 const VideoPacket* packet) { |
| 41 SkRegion region; | 40 webrtc::DesktopRegion region; |
| 42 | 41 |
| 43 const char* in = packet->data().data(); | 42 const char* in = packet->data().data(); |
| 44 int stride = kBytesPerPixel * screen_size_.width(); | 43 int stride = kBytesPerPixel * screen_size_.width(); |
| 45 for (int i = 0; i < packet->dirty_rects_size(); ++i) { | 44 for (int i = 0; i < packet->dirty_rects_size(); ++i) { |
| 46 Rect proto_rect = packet->dirty_rects(i); | 45 Rect proto_rect = packet->dirty_rects(i); |
| 47 SkIRect rect = SkIRect::MakeXYWH(proto_rect.x(), | 46 webrtc::DesktopRect rect = |
| 48 proto_rect.y(), | 47 webrtc::DesktopRect::MakeXYWH(proto_rect.x(), proto_rect.y(), |
| 49 proto_rect.width(), | 48 proto_rect.width(), proto_rect.height()); |
| 50 proto_rect.height()); | 49 region.AddRect(rect); |
| 51 region.op(rect, SkRegion::kUnion_Op); | |
| 52 | 50 |
| 53 if (!SkIRect::MakeSize(screen_size_).contains(rect)) { | 51 if (!DoesRectContain(webrtc::DesktopRect::MakeSize(screen_size_), rect)) { |
| 54 LOG(ERROR) << "Invalid packet received"; | 52 LOG(ERROR) << "Invalid packet received"; |
| 55 return DECODE_ERROR; | 53 return DECODE_ERROR; |
| 56 } | 54 } |
| 57 | 55 |
| 58 int rect_row_size = kBytesPerPixel * rect.width(); | 56 int rect_row_size = kBytesPerPixel * rect.width(); |
| 59 uint8_t* out = screen_buffer_.get() + rect.y() * stride + | 57 uint8_t* out = screen_buffer_.get() + rect.top() * stride + |
| 60 rect.x() * kBytesPerPixel; | 58 rect.left() * kBytesPerPixel; |
| 61 for (int y = rect.y(); y < rect.y() + rect.height(); ++y) { | 59 for (int y = rect.top(); y < rect.top() + rect.height(); ++y) { |
| 62 if (in + rect_row_size > packet->data().data() + packet->data().size()) { | 60 if (in + rect_row_size > packet->data().data() + packet->data().size()) { |
| 63 LOG(ERROR) << "Invalid packet received"; | 61 LOG(ERROR) << "Invalid packet received"; |
| 64 return DECODE_ERROR; | 62 return DECODE_ERROR; |
| 65 } | 63 } |
| 66 memcpy(out, in, rect_row_size); | 64 memcpy(out, in, rect_row_size); |
| 67 in += rect_row_size; | 65 in += rect_row_size; |
| 68 out += stride; | 66 out += stride; |
| 69 } | 67 } |
| 70 } | 68 } |
| 71 | 69 |
| 72 if (in != packet->data().data() + packet->data().size()) { | 70 if (in != packet->data().data() + packet->data().size()) { |
| 73 LOG(ERROR) << "Invalid packet received"; | 71 LOG(ERROR) << "Invalid packet received"; |
| 74 return DECODE_ERROR; | 72 return DECODE_ERROR; |
| 75 } | 73 } |
| 76 | 74 |
| 77 updated_region_.op(region, SkRegion::kUnion_Op); | 75 updated_region_.AddRegion(region); |
| 78 | 76 |
| 79 return DECODE_DONE; | 77 return DECODE_DONE; |
| 80 } | 78 } |
| 81 | 79 |
| 82 VideoPacketFormat::Encoding VideoDecoderVerbatim::Encoding() { | 80 VideoPacketFormat::Encoding VideoDecoderVerbatim::Encoding() { |
| 83 return VideoPacketFormat::ENCODING_VERBATIM; | 81 return VideoPacketFormat::ENCODING_VERBATIM; |
| 84 } | 82 } |
| 85 | 83 |
| 86 void VideoDecoderVerbatim::Invalidate(const SkISize& view_size, | 84 void VideoDecoderVerbatim::Invalidate(const webrtc::DesktopSize& view_size, |
| 87 const SkRegion& region) { | 85 const webrtc::DesktopRegion& region) { |
| 88 updated_region_.op(region, SkRegion::kUnion_Op); | 86 updated_region_.AddRegion(region); |
| 89 } | 87 } |
| 90 | 88 |
| 91 void VideoDecoderVerbatim::RenderFrame(const SkISize& view_size, | 89 void VideoDecoderVerbatim::RenderFrame(const webrtc::DesktopSize& view_size, |
| 92 const SkIRect& clip_area, | 90 const webrtc::DesktopRect& clip_area, |
| 93 uint8* image_buffer, | 91 uint8* image_buffer, |
| 94 int image_stride, | 92 int image_stride, |
| 95 SkRegion* output_region) { | 93 webrtc::DesktopRegion* output_region) { |
| 96 output_region->setEmpty(); | 94 output_region->Clear(); |
| 97 | 95 |
| 98 // TODO(alexeypa): scaling is not implemented. | 96 // TODO(alexeypa): scaling is not implemented. |
| 99 SkIRect clip_rect = SkIRect::MakeSize(screen_size_); | 97 webrtc::DesktopRect clip_rect = webrtc::DesktopRect::MakeSize(screen_size_); |
| 100 if (!clip_rect.intersect(clip_area)) | 98 clip_rect.IntersectWith(clip_area); |
| 99 if (clip_rect.is_empty()) |
| 101 return; | 100 return; |
| 102 | 101 |
| 103 int screen_stride = screen_size_.width() * kBytesPerPixel; | 102 int screen_stride = screen_size_.width() * kBytesPerPixel; |
| 104 | 103 |
| 105 for (SkRegion::Iterator i(updated_region_); !i.done(); i.next()) { | 104 for (webrtc::DesktopRegion::Iterator i(updated_region_); |
| 106 SkIRect rect(i.rect()); | 105 !i.IsAtEnd(); i.Advance()) { |
| 107 if (!rect.intersect(clip_rect)) | 106 webrtc::DesktopRect rect(i.rect()); |
| 107 rect.IntersectWith(clip_rect); |
| 108 if (rect.is_empty()) |
| 108 continue; | 109 continue; |
| 109 | 110 |
| 110 CopyRGB32Rect(screen_buffer_.get(), screen_stride, | 111 CopyRGB32Rect(screen_buffer_.get(), screen_stride, |
| 111 clip_rect, | 112 clip_rect, |
| 112 image_buffer, image_stride, | 113 image_buffer, image_stride, |
| 113 clip_area, | 114 clip_area, |
| 114 rect); | 115 rect); |
| 115 output_region->op(rect, SkRegion::kUnion_Op); | 116 output_region->AddRect(rect); |
| 116 } | 117 } |
| 117 | 118 |
| 118 updated_region_.setEmpty(); | 119 updated_region_.Clear(); |
| 119 } | 120 } |
| 120 | 121 |
| 121 const SkRegion* VideoDecoderVerbatim::GetImageShape() { | 122 const webrtc::DesktopRegion* VideoDecoderVerbatim::GetImageShape() { |
| 122 return NULL; | 123 return NULL; |
| 123 } | 124 } |
| 124 | 125 |
| 125 } // namespace remoting | 126 } // namespace remoting |
| OLD | NEW |