Using Videotoolbox hard-coded h.264< transfer >

Source: Internet
Author: User

Text/Falling Shadow Loyinglin (Jane book author)
Original link: http://www.jianshu.com/p/37784e363b8a
Copyright belongs to the author, please contact the author to obtain authorization, and Mark "book author".

===========================================

Using Videotoolbox hard-coded preface

It is a popular coding layer video compression format, currently the protocol layer in the project has rtmp and HTTP, but the video coding layer is the use of H.
In the process of being familiar with H. A, try to use videotoolbox hard coding and hard decoding of the original code stream for a better understanding of H.

Introduction 1, H.

The video coding layer (video Coding LAYER,VCL) is composed of the network abstraction layer,nal.
There is a built-in NAL network protocol adaptation layer, with NAL to provide the state of the network, so that VCL has better coding flexibility and error correction ability.
See here for an introduction to H.
The code flow structure of H.
Key objects:

    • Sequence parameter set SPS: Acts on a series of sequential coded images;
    • Image parameter set pps: One or more independent images acting on the encoded video sequence;



2, Videotoolbox

Videotoolbox is a hard-coded and hard-decoded API that is open after iOS8, a set of functions written in C. The use process is as follows:

    • 1. -initVideoToolBox call Vtcompressionsessioncreate to create the encoding session, and then call Vtsessionsetproperty to set the parameters, Finally call Vtcompressionsessionpreparetoencodeframes to start coding;
    • 2, start video recording, get to the camera video frame, incoming -encode: , call Vtcompressionsessionencodeframe incoming need to encode the video frame, if return failed, Call Vtcompressionsessioninvalidate to destroy the session and then release the session;
    • 3, each frame video encoding will call the pre-set encoding function didCompressH264 , if the keyframe needs to get cmformatdescriptionref with cmsamplebuffergetformatdescription, and then use
      Cmvideoformatdescriptiongeth264parametersetatindex obtain PPS and SPS;
      Finally, the first four bytes of all NALU data in each frame are converted to 0x00 00 00 01 Before the file is written;
    • 4. Call Vtcompressionsessioncompleteframes to complete the encoding, then destroy the Session:vtcompressionsessioninvalidate and release the session.
Effect Show

It's a decoded image.


Sticker Code
  • Create session
  • int 480 640 ;      void *) (self),  &encodingsession);

  • Set session Properties

  • //set real-time encoded output (avoid delays)Vtsessionsetproperty (encodingsession, Kvtcompressionpropertykey_realtime, kcfbooleantrue); Vtsessionsetproperty (Encodingsession, Kvtcompressionpropertykey_profilelevel, Kvtprofilelevel_h264_baseline_     Autolevel); //Set Keyframe (gopsize) interval     intFrameinterval =Ten; Cfnumberref Frameintervalref= Cfnumbercreate (Kcfallocatordefault, Kcfnumberinttype, &frameinterval);     Vtsessionsetproperty (Encodingsession, Kvtcompressionpropertykey_maxkeyframeinterval, FRAMEINTERVALREF); //set the desired frame rate     intfps =Ten; Cfnumberref Fpsref= Cfnumbercreate (Kcfallocatordefault, Kcfnumberinttype, &fps);      Vtsessionsetproperty (Encodingsession, Kvtcompressionpropertykey_expectedframerate, FPSREF); //set the bitrate, the upper limit, the unit is BPS     intBitrate = width * Height *3*4*8; Cfnumberref Bitrateref= Cfnumbercreate (Kcfallocatordefault, Kcfnumbersint32type, &bitrate);     Vtsessionsetproperty (Encodingsession, Kvtcompressionpropertykey_averagebitrate, BITRATEREF); //set the bitrate, the mean, in units of byte     intBitratelimit = width * Height *3*4; Cfnumberref Bitratelimitref= Cfnumbercreate (Kcfallocatordefault, Kcfnumbersint32type, &bitratelimit); Vtsessionsetproperty (Encodingsession, Kvtcompressionpropertykey_dataratelimits, bitRateLimitRef);

  • Incoming encoded frames

  • Cvimagebufferref Imagebuffer =//  frame time, if not set, causes the timeline to be too long.  vtcompressionsessionencodeframe= (encodingsession,                                                       Imagebuffer,                                                       Presentationtimestamp,                                                       kcmtimeinvalid,                                                       &flags);

  • Key frames for SPS and PPS

  •  BOOLKeyframe =! Cfdictionarycontainskey (Cfarraygetvalueatindex (Cmsamplebuffergetsampleattachmentsarray (SampleBuffer,true),0) ), Kcmsampleattachmentkey_notsync); //determines whether the current frame is a keyframe//get SPS & PPS Data if(keyframe) {cmformatdescriptionref format=cmsamplebuffergetformatdescription (Samplebuffer);     size_t sparametersetsize, Sparametersetcount; Constuint8_t *Sparameterset; Osstatus StatusCode= Cmvideoformatdescriptiongeth264parametersetatindex (format,0, &sparameterset, &sparametersetsize, &sparametersetcount,0 ); if(StatusCode = =NOERR) {         //Found SPS and now check for PPSsize_t pparametersetsize, Pparametersetcount; Constuint8_t *Pparameterset; Osstatus StatusCode= Cmvideoformatdescriptiongeth264parametersetatindex (format,1, &pparameterset, &pparametersetsize, &pparametersetcount,0 ); if(StatusCode = =NOERR) {             //Found ppsNSData *sps =[NSData Datawithbytes:sparameterset length:sparametersetsize]; NSData*pps =[NSData Datawithbytes:pparameterset length:pparametersetsize]; if(encoder) {[encoder gotspspps:sps Pps:pps]; }         }     } }

  • Write Data

  • Cmblockbufferref DataBuffer =Cmsamplebuffergetdatabuffer (samplebuffer); size_t length, totallength;Char*Datapointer; Osstatus Statuscoderet= Cmblockbuffergetdatapointer (DataBuffer,0, &length, &totallength, &datapointer); if(Statuscoderet = =NOERR) {size_t Bufferoffset=0; Static Const intAvccheaderlength =4;//The first four bytes of the returned NALU data are not 0001 Startcode, but the frame lengths of the big-endian mode length//cyclic acquisition of NALU data      while(Bufferoffset < Totallength-avccheaderlength) {uint32_t Nalunitlength=0; //Read the NAL unit lengthmemcpy (&nalunitlength, Datapointer +Bufferoffset, avccheaderlength); //turn the system end from the big-endianNalunitlength =Cfswapint32bigtohost (nalunitlength); NSData* data = [[NSData alloc] Initwithbytes: (datapointer + Bufferoffset +avccheaderlength) length:nalunitlength];         [Encoder gotencodeddata:data Iskeyframe:keyframe]; //Move to the next NAL unit in the block bufferBufferoffset + = Avccheaderlength +nalunitlength; } }
    Summarize

    Most of the Videotoolboxdemo code found on the Internet is similar, and more important is to try to implement it yourself.
    Learn hard coding and hard decoding, the purpose is to H264 code stream clearer understanding, in fact, we do not touch the development process of H264 real coding and decoding process, so the difficulty is far from the imagination so big.
    Here's the code address.

Using Videotoolbox hard-coded h.264< transfer >

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.