ifish/Ifish/controllers/IfishYooseeFile/IfishYsooseeNewLib/rtsp/FfmpegInterface.m

120 lines
3.4 KiB
Objective-C

//
// FfmpegInterface.m
// 2cu
//
// Created by wutong on 15/9/16.
// Copyright (c) 2015年 guojunyi. All rights reserved.
//
#import "FfmpegInterface.h"
@implementation FfmpegInterface
+ (id)sharedDefault
{
static FfmpegInterface *manager = nil;
@synchronized([self class]){
if(manager==nil){
manager = [[FfmpegInterface alloc] init];
manager->_isInited = NO;
}
}
return manager;
}
- (void) vInitVideoDecoder
{
@synchronized(self)
{
avcodec_register_all();
// av_register_all();
[self add_decode_context];
_isInited = YES;
}
}
- (void) vDestoryVideoDecoder
{
@synchronized(self)
{
if (!_isInited) {
return;
}
av_free_packet(&_sDecodePkt);
// Close the codec
if(_pDecodeAVC)
{
avcodec_close(_pDecodeAVC);
av_free(_pDecodeAVC);
_pDecodeAVC = NULL;
}
// Free the YUV frame
if(_pDecodeOutputFrame)
{
av_free(_pDecodeOutputFrame);
_pDecodeOutputFrame= NULL;
}
_isInited = NO;
}
}
- (void)add_decode_context
{
AVCodec *codec;
_pDecodeAVC = NULL;
// 寻找编码器
codec = avcodec_find_decoder(CODEC_ID_H264);
if (!codec) {
NSLog(@"codec not found\n");
}
_pDecodeAVC = avcodec_alloc_context3(codec);
_pDecodeAVC->bit_rate = 4000000;
_pDecodeAVC->time_base.den = 15;/////may be remote frame rate
_pDecodeAVC->time_base.num = 1;
_pDecodeAVC->pix_fmt = PIX_FMT_YUV420P;
_pDecodeAVC->codec_type = AVMEDIA_TYPE_VIDEO;
_pDecodeAVC->rc_buffer_aggressivity = 1.0;
//浮点数. 表示开启解码器码流缓冲(decoder bitstream buffer)
_pDecodeAVC->flags |= CODEC_FLAG_GLOBAL_HEADER| CODEC_FLAG_LOOP_FILTER;
_pDecodeAVC->flags2 |= CODEC_FLAG2_FAST;
if (avcodec_open2(_pDecodeAVC, codec, NULL) < 0) {
NSLog(@"could not open encode-codec\n");
}
// 定义图片缓存变量
_pDecodeOutputFrame = avcodec_alloc_frame();
av_init_packet(&_sDecodePkt);
_sDecodePkt.flags = AV_PKT_FLAG_KEY;
}
-(BOOL) fgDecodePictureFrame:(Byte *)pBuffer dwSize:(DWORD)dwSize u6PTS:(UInt64)u6PTS pFrame:(GAVFrame*)pFrame
{
@synchronized(self)
{
// 填充输入缓冲区
int frameFinished = 0;
_sDecodePkt.data = pBuffer;
_sDecodePkt.size = dwSize;
_sDecodePkt.pts = u6PTS ;
frameFinished = avcodec_decode_video2(_pDecodeAVC, _pDecodeOutputFrame, &frameFinished, &_sDecodePkt);
if (!_pDecodeOutputFrame->data[0] || frameFinished <= 0)
{
return FALSE;
}
pFrame->height = _pDecodeOutputFrame->height;
pFrame->width = _pDecodeOutputFrame->width;
pFrame->pts = _pDecodeOutputFrame->pts;
pFrame->linesize[0] = _pDecodeOutputFrame->linesize[0];
pFrame->linesize[1] = _pDecodeOutputFrame->linesize[1];
pFrame->linesize[2] = _pDecodeOutputFrame->linesize[2];
memcpy(pFrame->data[0], _pDecodeOutputFrame->data[0], _pDecodeOutputFrame->linesize[0]*_pDecodeOutputFrame->height);
memcpy(pFrame->data[1], _pDecodeOutputFrame->data[1], _pDecodeOutputFrame->linesize[1]*_pDecodeOutputFrame->height/2);
memcpy(pFrame->data[2], _pDecodeOutputFrame->data[2], _pDecodeOutputFrame->linesize[2]*_pDecodeOutputFrame->height/2);
return TRUE ;
}
}
@end