OLD | NEW |
(Empty) | |
| 1 /* |
| 2 * Copyright 2017 The WebRTC project authors. All Rights Reserved. |
| 3 * |
| 4 * Use of this source code is governed by a BSD-style license |
| 5 * that can be found in the LICENSE file in the root of the source |
| 6 * tree. An additional intellectual property rights grant can be found |
| 7 * in the file PATENTS. All contributing project authors may |
| 8 * be found in the AUTHORS file in the root of the source tree. |
| 9 */ |
| 10 |
| 11 #include "webrtc/sdk/objc/Framework/Classes/VideoToolbox/objc_video_decoder_fact
ory.h" |
| 12 |
| 13 #import "RTCVideoCodec+Private.h" |
| 14 #import "WebRTC/RTCVideoCodec.h" |
| 15 #import "WebRTC/RTCVideoCodecFactory.h" |
| 16 #import "WebRTC/RTCVideoCodecH264.h" |
| 17 #import "WebRTC/RTCVideoFrame.h" |
| 18 #import "WebRTC/RTCVideoFrameBuffer.h" |
| 19 |
| 20 #include "webrtc/api/video_codecs/video_decoder.h" |
| 21 #include "webrtc/modules/include/module_common_types.h" |
| 22 #include "webrtc/modules/video_coding/include/video_codec_interface.h" |
| 23 #include "webrtc/modules/video_coding/include/video_error_codes.h" |
| 24 #include "webrtc/rtc_base/logging.h" |
| 25 #include "webrtc/rtc_base/timeutils.h" |
| 26 #include "webrtc/sdk/objc/Framework/Classes/Video/objc_frame_buffer.h" |
| 27 |
| 28 namespace webrtc { |
| 29 |
| 30 namespace { |
| 31 class ObjCVideoDecoder : public VideoDecoder { |
| 32 public: |
| 33 ObjCVideoDecoder(id<RTCVideoDecoder> decoder) : decoder_(decoder) {} |
| 34 ~ObjCVideoDecoder() { [decoder_ destroy]; } |
| 35 |
| 36 int32_t InitDecode(const VideoCodec *codec_settings, int32_t number_of_cores)
{ |
| 37 RTCVideoEncoderSettings *settings = |
| 38 [[RTCVideoEncoderSettings alloc] initWithVideoCodec:codec_settings]; |
| 39 return [decoder_ startDecodeWithSettings:settings numberOfCores:number_of_co
res]; |
| 40 } |
| 41 |
| 42 int32_t Decode(const EncodedImage &input_image, |
| 43 bool missing_frames, |
| 44 const RTPFragmentationHeader *fragmentation, |
| 45 const CodecSpecificInfo *codec_specific_info = NULL, |
| 46 int64_t render_time_ms = -1) { |
| 47 RTCEncodedImage *encodedImage = |
| 48 [[RTCEncodedImage alloc] initWithNativeEncodedImage:input_image]; |
| 49 RTCRtpFragmentationHeader *header = |
| 50 [[RTCRtpFragmentationHeader alloc] initWithFragmentationHeader:fragmenta
tion]; |
| 51 |
| 52 // webrtc::CodecSpecificInfo only handles a hard coded list of codecs |
| 53 id<RTCCodecSpecificInfo> rtcCodecSpecificInfo = nil; |
| 54 if (codec_specific_info) { |
| 55 if (codec_specific_info->codecType == kVideoCodecH264) { |
| 56 RTCCodecSpecificInfoH264 *h264Info = [[RTCCodecSpecificInfoH264 alloc] i
nit]; |
| 57 h264Info.packetizationMode = |
| 58 (RTCH264PacketizationMode)codec_specific_info->codecSpecific.H264.pa
cketization_mode; |
| 59 rtcCodecSpecificInfo = h264Info; |
| 60 } |
| 61 } |
| 62 |
| 63 return [decoder_ decode:encodedImage |
| 64 missingFrames:missing_frames |
| 65 fragmentationHeader:header |
| 66 codecSpecificInfo:rtcCodecSpecificInfo |
| 67 renderTimeMs:render_time_ms]; |
| 68 } |
| 69 |
| 70 int32_t RegisterDecodeCompleteCallback(DecodedImageCallback *callback) { |
| 71 [decoder_ setCallback:^(RTCVideoFrame *frame) { |
| 72 const rtc::scoped_refptr<VideoFrameBuffer> buffer = |
| 73 new rtc::RefCountedObject<ObjCFrameBuffer>(frame.buffer); |
| 74 VideoFrame videoFrame(buffer, |
| 75 (uint32_t)(frame.timeStampNs / rtc::kNumNanosecsPerM
icrosec), |
| 76 0, |
| 77 (VideoRotation)frame.rotation); |
| 78 videoFrame.set_timestamp(frame.timeStamp); |
| 79 |
| 80 callback->Decoded(videoFrame); |
| 81 }]; |
| 82 |
| 83 return WEBRTC_VIDEO_CODEC_OK; |
| 84 } |
| 85 |
| 86 int32_t Release() { return [decoder_ releaseDecoder]; } |
| 87 |
| 88 private: |
| 89 id<RTCVideoDecoder> decoder_; |
| 90 }; |
| 91 } // namespace |
| 92 |
| 93 ObjCVideoDecoderFactory::ObjCVideoDecoderFactory(id<RTCVideoDecoderFactory> deco
der_factory) |
| 94 : decoder_factory_(decoder_factory) {} |
| 95 |
| 96 ObjCVideoDecoderFactory::~ObjCVideoDecoderFactory() {} |
| 97 |
| 98 id<RTCVideoDecoderFactory> ObjCVideoDecoderFactory::wrapped_decoder_factory() co
nst { |
| 99 return decoder_factory_; |
| 100 } |
| 101 |
| 102 VideoDecoder *ObjCVideoDecoderFactory::CreateVideoDecoder(VideoCodecType type) { |
| 103 const rtc::Optional<const char *> codec_name = CodecTypeToPayloadName(type); |
| 104 if (!codec_name) { |
| 105 LOG(LS_ERROR) << "Invalid codec type: " << type; |
| 106 return nullptr; |
| 107 } |
| 108 |
| 109 NSString *codecName = [NSString stringWithUTF8String:codec_name.value()]; |
| 110 for (RTCVideoCodecInfo *codecInfo in decoder_factory_.supportedCodecs) { |
| 111 if ([codecName isEqualToString:codecInfo.name]) { |
| 112 id<RTCVideoDecoder> decoder = [decoder_factory_ createDecoder:codecInfo]; |
| 113 return new ObjCVideoDecoder(decoder); |
| 114 } |
| 115 } |
| 116 |
| 117 return nullptr; |
| 118 } |
| 119 |
| 120 void ObjCVideoDecoderFactory::DestroyVideoDecoder(VideoDecoder *decoder) { |
| 121 delete decoder; |
| 122 decoder = nullptr; |
| 123 } |
| 124 |
| 125 } // namespace webrtc |
OLD | NEW |