真实的国产乱ⅩXXX66竹夫人,五月香六月婷婷激情综合,亚洲日本VA一区二区三区,亚洲精品一区二区三区麻豆

成都創(chuàng)新互聯(lián)網(wǎng)站制作重慶分公司

ios視頻格式開發(fā),ios視頻支持格式

iphone手機(jī)拍的視頻是什么格式?

MOV格式。

資陽網(wǎng)站建設(shè)公司創(chuàng)新互聯(lián)建站,資陽網(wǎng)站設(shè)計(jì)制作,有大型網(wǎng)站制作公司豐富經(jīng)驗(yàn)。已為資陽上1000家提供企業(yè)網(wǎng)站建設(shè)服務(wù)。企業(yè)網(wǎng)站搭建\外貿(mào)網(wǎng)站制作要多少錢,請找那個售后服務(wù)好的資陽做網(wǎng)站的公司定做!

MOV是由Apple公司開發(fā)的音頻、視頻文件格式,同時也是QuickTime影片格式。常用于存儲常用數(shù)字媒體類型,如音頻和視頻。MOV格式文件是以軌道的形式組織起來的,一個MOV格式文件結(jié)構(gòu)中可以包含很多軌道。在某些方面它比WMV和RM更優(yōu)秀,并能被眾多的多媒體編輯及視頻處理軟件所支持。

QuickTime視頻文件播放程序,除了播放MP3外,QuickTime還支持MIDI播放。并且可以收聽/收網(wǎng)絡(luò)播放,支持HTTP、RTP和RTSP標(biāo)準(zhǔn)。該軟件還支持主要的圖像格式,比如:JPEG、BMP、PICT、PNG和GIF。該軟件的其他特性還有:支持?jǐn)?shù)字視頻文件,包括:MiniDV、DVCPro、DVCam、AVI、AVR、MPEG-1、OpenDML以及MacromediaFlash等。QuickTime用于保存音頻和視頻信息,現(xiàn)在它被包括AppleMacOS,MicrosoftWindows95/98/NT/2003/XP/VISTA在內(nèi)的所有主流電腦平臺支持。

QuickTime文件格式支持25位彩色,支持領(lǐng)先的集成壓縮技術(shù),提供150多種視頻效果,并配有提供了200多種MIDI兼容音響和設(shè)備的聲音裝置。它無論是在本地播放還是作為視頻流格式在網(wǎng)上傳播,都是一種優(yōu)良的視頻編碼格式。

iOS音視頻采集與格式轉(zhuǎn)換(yuv轉(zhuǎn)rgb)

基本流程

1.初始化輸入設(shè)備

2.初始化輸出設(shè)備

3.創(chuàng)建AVCaptureSession,用來管理視頻與數(shù)據(jù)的捕獲

4.創(chuàng)建預(yù)覽視圖

前面介紹了如何通過相機(jī)實(shí)時獲取音視頻數(shù)據(jù),我們接下來就需要了解獲取到的數(shù)據(jù)到底是什么樣的,使用系統(tǒng)提供的接口獲取到的音視頻數(shù)據(jù)都保存在CMSampleBufferRef中,這個結(jié)構(gòu)在iOS中表示一幀音頻/視頻數(shù)據(jù),它里面包含了這一幀數(shù)據(jù)的內(nèi)容和格式,我們可以把它的內(nèi)容取出來,提取出/轉(zhuǎn)換成我們想要的數(shù)據(jù)。

代表視頻的CMSampleBufferRef中保存的數(shù)據(jù)是yuv420格式的視頻幀(因?yàn)槲覀冊谝曨l輸出設(shè)置中將輸出格式設(shè)為:kCVPixelFormatType_420YpCbCr8BiPlanarVideoRange)。

在下面的回調(diào)中,可以拿到最終的CMSampleBufferRef數(shù)據(jù)

視頻是由一幀一幀的數(shù)據(jù)連接而成,而一幀視頻數(shù)據(jù)其實(shí)就是一張圖片。

yuv是一種圖片儲存格式,跟RGB格式類似。

RGB格式的圖片很好理解,計(jì)算機(jī)中的大多數(shù)圖片,都是以RGB格式存儲的。

yuv中,y表示亮度,單獨(dú)只有y數(shù)據(jù)就可以形成一張圖片,只不過這張圖片是灰色的。u和v表示色差(u和v也被稱為:Cb-藍(lán)色差,Cr-紅色差),

為什么要yuv?

有一定歷史原因,最早的電視信號,為了兼容黑白電視,采用的就是yuv格式。

一張yuv的圖像,去掉uv,只保留y,這張圖片就是黑白的。

而且yuv可以通過拋棄色差來進(jìn)行帶寬優(yōu)化。

比如yuv420格式圖像相比RGB來說,要節(jié)省一半的字節(jié)大小,拋棄相鄰的色差對于人眼來說,差別不大。

一張yuv格式的圖像,占用字節(jié)數(shù)為 (width * height + (width * height) / 4 + (width * height) / 4) = (width * height) * 3 / 2

一張RGB格式的圖像,占用字節(jié)數(shù)為(width * height) * 3

在傳輸上,yuv格式的視頻也更靈活(yuv3種數(shù)據(jù)可分別傳輸)。

很多視頻編碼器最初是不支持rgb格式的。但是所有的視頻編碼器都支持yuv格式。

我們這里使用的就是yuv420格式的視頻。

yuv420也包含不同的數(shù)據(jù)排列格式:I420,NV12,NV21.

其格式分別如下,

I420格式:y,u,v 3個部分分別存儲:Y0,Y1...Yn,U0,U1...Un/2,V0,V1...Vn/2

NV12格式:y和uv 2個部分分別存儲:Y0,Y1...Yn,U0,V0,U1,V1...Un/2,Vn/2

NV21格式:同NV12,只是U和V的順序相反。

綜合來說,除了存儲順序不同之外,上述格式對于顯示來說沒有任何區(qū)別。

使用哪種視頻的格式,取決于初始化相機(jī)時設(shè)置的視頻輸出格式。

設(shè)置為kCVPixelFormatType_420YpCbCr8BiPlanarVideoRange時,表示輸出的視頻格式為NV12;

設(shè)置為kCVPixelFormatType_420YpCbCr8Planar時,表示使用I420。

設(shè)置為kCVPixelFormatType_32RGBA時,表示使用BGRA。

GPUImage設(shè)置相機(jī)輸出數(shù)據(jù)時,使用的就是NV12.

為了一致,我們這里也選擇NV12格式輸出視頻。

libyuv是Google開源的實(shí)現(xiàn)各種YUV與RGB之間相互轉(zhuǎn)換、旋轉(zhuǎn)、縮放的庫。它是跨平臺的,可在Windows、Linux、Mac、Android等操作系統(tǒng),x86、x64、arm架構(gòu)上進(jìn)行編譯運(yùn)行,支持SSE、AVX、NEON等SIMD指令加速.

導(dǎo)入libyuv庫,并設(shè)置頭文件搜索路徑,不然會報錯

文章只介紹了使用AVFoundation進(jìn)行視頻采集和使用libyuv進(jìn)行格式轉(zhuǎn)換,音視頻相關(guān)的知識還有很多,這里不再做詳細(xì)介紹了。

iOS視頻推流格式轉(zhuǎn)換

視頻采集會得到格式為CMSampleBufferRef的視頻包,視頻推流一般把視頻流轉(zhuǎn)換成flv格式

(1)首先將視頻流轉(zhuǎn)換成YUV的數(shù)據(jù)格式

//獲取yuv數(shù)據(jù)

- (NSData*)convertVideoSmapleBufferToYuvData:(CMSampleBufferRef)videoSample {

//通過CMSampleBufferGetImageBuffer方法,獲得CVImageBufferRef,里面就包含了YUV420數(shù)據(jù)的指針

CVImageBufferRef pixelBuffer = CMSampleBufferGetImageBuffer(videoSample);

//鎖住格式轉(zhuǎn)換線程,開始轉(zhuǎn)換格式

CVPixelBufferLockBaseAddress(pixelBuffer,0);

//獲取圖像寬度(像素)

size_t pixelWidth = CVPixelBufferGetWidth(pixelBuffer);

//獲取圖像高度(像素)

size_t pixelHeight = CVPixelBufferGetHeight(pixelBuffer);

//計(jì)算YUV中的Y所占字節(jié)數(shù)

size_t y_size = pixelWidth * pixelHeight;

//計(jì)算YUV中的U和V分別所占的字節(jié)數(shù)

size_t uv_size = y_size /4;

uint8_t * yuv_frame = aw_alloc(uv_size *2+ y_size);

//獲取pixelBuffer中的Y數(shù)據(jù)

uint8_t * y_frame = CVPixelBufferGetBaseAddressOfPlane(pixelBuffer,0);

memcpy(yuv_frame, y_frame, y_size);

//獲取pixelBuffer中的UV數(shù)據(jù)

uint8_t * uv_frame = CVPixelBufferGetBaseAddressOfPlane(pixelBuffer,1);

memcpy(yuv_frame + y_size, uv_frame, uv_size *2);

//獲取到想要的數(shù)據(jù),解鎖格式轉(zhuǎn)換線程

CVPixelBufferUnlockBaseAddress(pixelBuffer,0);

//yuv格式----nv12格式

NSData * yuvData = [NSData dataWithBytesNoCopy:yuv_frame length:y_size + uv_size *2];

//由于相機(jī)偏轉(zhuǎn),我們需要對的到的視頻頁面進(jìn)行旋轉(zhuǎn)

return [self rotateNV12Data:nv12Data];

}

(2)由于相機(jī)偏轉(zhuǎn),我們需要對的到的視頻頁面進(jìn)行旋轉(zhuǎn)

- (NSData*)rotateNV12Data:(NSData*)nv12Data {

int degree = 0;

switch(self.videoConfig.orientation) {

case UIInterfaceOrientationLandscapeLeft:

degree = 90;

break;

case UIInterfaceOrientationLandscapeRight:

degree = 270;

break;

default:

//do nothing

break;

}

if(degree !=0) {

uint8_ t * src_nv12_bytes = (uint8_t*)nv12Data.bytes;

uint32_t width = (uint32_t)self.videoConfig.width;

uint32_t height = (uint32_t)self.videoConfig.height;

uint32_t w_x_h = (uint32_t)(self.videoConfig.width*self.videoConfig.height);

uint8_t * rotatedI420Bytes =aw_alloc(nv12Data.length);

NV12ToI420Rotate(src_nv12_bytes, width,

src_nv12_bytes + w_x_h, width,

rotatedI420Bytes, height,

rotatedI420Bytes + w_x_h, height /2,

rotatedI420Bytes + w_x_h + w_x_h /4, height /2,

width, height, (RotationModeEnum)degree);

I420ToNV12(rotatedI420Bytes, height,

rotatedI420Bytes + w_x_h, height /2,

rotatedI420Bytes + w_x_h + w_x_h /4, height /2,

src_nv12_bytes, height, src_nv12_bytes + w_x_h, height,

height, width);

aw_free(rotatedI420Bytes);

}

return nv12Data;

}

(3)將nv12格式的數(shù)據(jù)合成為flv格式

- (aw_flv_video_tag*)encodeYUVDataToFlvTag:(NSData*)yuvData{

if(!_vEnSession) {

return NULL;

}

OSStatus status = noErr;

//獲取視頻寬度

size_t pixelWidth = self.videoConfig.pushStreamWidth;

//獲取視頻高度

size_t pixelHeight = self.videoConfig.pushStreamHeight;

//NV12數(shù)據(jù)-CVPixelBufferRef中

//硬編碼主要調(diào)用VTCompressionSessionEncodeFrame函數(shù),此函數(shù)處理的是CVPixelBufferRef類型。

CVPixelBufferRef pixelBuf =NULL;

//初始化pixelBuf

CVPixelBufferCreate(NULL, pixelWidth, pixelHeight,kCVPixelFormatType_420YpCbCr8BiPlanarVideoRange,NULL, pixelBuf);

if(CVPixelBufferLockBaseAddress(pixelBuf,0) != kCVReturnSuccess){

NSLog(@"encode video lock base address failed");?

return NULL;

}

//將YUV數(shù)據(jù)填充到CVPixelBufferRef中

size_t y_size = aw_stride(pixelWidth) * pixelHeight;

size_t uv_size = y_size /4;

uint8_t * yuv_frame = (uint8_t*)yuvData.bytes;

//獲取y frame

uint8_t * y_frame = CVPixelBufferGetBaseAddressOfPlane(pixelBuf,0);

memcpy(y_frame, yuv_frame, y_size);

//獲取uv frame

uint8_t * uv_frame = CVPixelBufferGetBaseAddressOfPlane(pixelBuf,1);

memcpy(uv_frame, yuv_frame + y_size, uv_size *2);

//編碼CMSampleBufRef

//獲取時間戳,由于視頻幀是有順序的,所以timestamp可以自定義一個累加字段

uint32_t ptsMs = timestamp+1;//self.vFrameCount++ * 1000.f / self.videoConfig.fps;

CMTime pts =CMTimeMake(ptsMs,1000);

//將NV12數(shù)據(jù)的PixelBuf送到硬編碼器中,進(jìn)行編碼。

status = VTCompressionSessionEncodeFrame(_vEnSession, pixelBuf, pts,kCMTimeInvalid,NULL, pixelBuf,NULL);

if(status == noErr) {

dispatch_semaphore_wait(self.vSemaphore,DISPATCH_TIME_FOREVER);

if(_naluData) {

//硬編碼成功,_naluData內(nèi)的數(shù)據(jù)即為h264視頻幀。

//因?yàn)槭峭屏?,所以需要獲取幀長度,轉(zhuǎn)成大端字節(jié)序,放到數(shù)據(jù)的最前面

uint32_t naluLen = (uint32_t)_naluData.length;

//小端轉(zhuǎn)大端。計(jì)算機(jī)內(nèi)一般都是小端,而網(wǎng)絡(luò)和文件中一般都是大端。大端轉(zhuǎn)小端和小端轉(zhuǎn)大端算法一樣,就是字節(jié)序反轉(zhuǎn)就行了。

uint8_t naluLenArr[4] = {naluLen 240xff, naluLen 160xff, naluLen 80xff, naluLen 0xff};

//數(shù)據(jù)拼接

NSMutableData * mutableData = [NSMutableData dataWithBytes:naluLenArr length:4];

[mutableData appendData:_naluData];

//h264 - flv tag,合成flvtag之后就可以直接發(fā)送到服務(wù)端了。

aw_flv_video_tag * video_tag = aw_encoder_create_video_tag((int8_t*)mutableData.bytes, mutableData.length, ptsMs,0,self.isKeyFrame);

//編碼完成,釋放數(shù)據(jù)。

_naluData = nil;

_isKeyFrame = NO;

CVPixelBufferUnlockBaseAddress(pixelBuf,0);

CFRelease(pixelBuf);

return video_tag;

}

}else {

NSLog(@"encode video frame error");

}

CVPixelBufferUnlockBaseAddress(pixelBuf,0);

CFRelease(pixelBuf);

return NULL;

}

iOS開發(fā):視頻快進(jìn)、慢進(jìn)、快退(倍速播放)

快進(jìn):AVPlayer .rate 1

慢放: 0 AVPlayer .rate 1

快退: AVPlayer .rate 0 (m3u8 不能快退)

MP4:如果快進(jìn)到了緩存不夠的地方:KVC監(jiān)聽 AVPlayerItem .isPlaybackBufferEmpty = yes

快退到頭會走通知AVPlayerItemDidPlayToEndTimeNotification

m3u8(靜態(tài)):快進(jìn)與MP4格式視頻一致,可以10倍 20倍播放。

m3u8(動態(tài)):快進(jìn)到了緩存不夠的地方,會走通知AVPlayerItemDidPlayToEndTimeNotification。

備注:使用[AVPlayerItem stepByCount:-24];

將AVPlayerItem 向前或向后移動指定的步數(shù),正數(shù)前進(jìn),負(fù)數(shù)后退。 每個步數(shù)的大小取決于AVPlayerItem啟用的AVPlayerItemTracks對象;

注冊監(jiān)聽和通知

蘋果最新推出的ProRes視頻是什么?實(shí)用嗎?

比較蘋果的ProRes格式是在十多年前開發(fā)的,現(xiàn)在支持高達(dá)8K的分辨率,對于需要視頻編輯的人來說非常實(shí)用。 Final Cut Pro經(jīng)過編碼,可高效處理和編輯ProRes內(nèi)容,并廣泛用于專業(yè)視頻行業(yè)中。

iPhone 13 Pro 機(jī)型還將首次能夠以 ProRes 視頻格式進(jìn)行錄制,為專業(yè)人士提供更高質(zhì)量的輸出。

蘋果手機(jī)優(yōu)點(diǎn)如下:

1、iOS系統(tǒng)

我們知道蘋果手機(jī)的iOS系統(tǒng)是獨(dú)有的,只有在蘋果手機(jī)中才能夠體驗(yàn)到這種系統(tǒng),而這個手機(jī)系統(tǒng)是非常流暢的,安卓手機(jī)的系統(tǒng)在使用一段時間之后都會有不同程度的卡頓,但是蘋果手機(jī)的iOS系統(tǒng)依舊非常流暢。

2、應(yīng)用生態(tài)優(yōu)異

蘋果手機(jī)對于開發(fā)者上傳在應(yīng)用商店的軟件有著很嚴(yán)格的審核,像是一些不安全的軟件或者是沒有質(zhì)量的軟件是不會在應(yīng)用商店里存在的,對于軟件有一個質(zhì)量上的保障,但是很多的安卓手機(jī)并不是這樣。

3、iOS系統(tǒng)安全性好

在使用安卓手機(jī)的時候,很多軟件在打開的時候都會開放很多的運(yùn)用權(quán)限,因?yàn)椴婚_的話完全沒有辦法正常使用,這一點(diǎn)是很容易造成用戶信息的泄露,而且在很多的游戲上還有一不小心點(diǎn)到就被扣費(fèi)。


文章名稱:ios視頻格式開發(fā),ios視頻支持格式
分享鏈接:http://weahome.cn/article/dsssjcg.html

其他資訊

在線咨詢

微信咨詢

電話咨詢

028-86922220(工作日)

18980820575(7×24)

提交需求

返回頂部