获取.h264视频宽高的方法

花了2个通宵终于搞定。(后面附上完整代码)

http://write.blog.csdn.net/postedit/7852406

图像的高和宽在H264的SPS帧中。
在H264码流中,都是以"0x00 0x00 0x01"或者"0x00 0x00 0x00 0x01"为开始码的,找到开始码之后,使用开始码之后的第一个字节的低5位判断是否为7(sps),等于7表示该帧就是SPS帧,从该帧就可以解析出高和宽,SPS是个结构体,里面有两个成员:pic_width_in_mbs_minus1,pic_height_in_map_units_minus_1,分别表示图像的宽和高,以宏块(16x16)为单位的值减1,因此,实际的宽为 (pic_width_in_mbs_minus1+1)*16,高为 (pic_height_in_map_units_minus_1+1)*16

http://write.blog.csdn.net/postedit/7852406

 UINT Ue(BYTE *pBuff, UINT nLen, UINT &nStartBit)
{
//计算0bit的个数
UINT nZeroNum = ;
while (nStartBit < nLen * )
{
if (pBuff[nStartBit / ] & (0x80 >> (nStartBit % ))) //&:按位与,%取余
{
break;
}
nZeroNum++;
nStartBit++;
}
nStartBit ++; //计算结果
DWORD dwRet = ;
for (UINT i=; i<nZeroNum; i++)
{
dwRet <<= ;
if (pBuff[nStartBit / ] & (0x80 >> (nStartBit % )))
{
dwRet += ;
}
nStartBit++;
}
return ( << nZeroNum) - + dwRet;
} int Se(BYTE *pBuff, UINT nLen, UINT &nStartBit)
{ int UeVal=Ue(pBuff,nLen,nStartBit);
double k=UeVal;
int nValue=ceil(k/);//ceil函数:ceil函数的作用是求不小于给定实数的最小整数。ceil(2)=ceil(1.2)=cei(1.5)=2.00
if (UeVal % ==)
nValue=-nValue;
return nValue; } DWORD u(UINT BitCount,BYTE * buf,UINT &nStartBit)
{
DWORD dwRet = ;
for (UINT i=; i<BitCount; i++)
{
dwRet <<= ;
if (buf[nStartBit / ] & (0x80 >> (nStartBit % )))
{
dwRet += ;
}
nStartBit++;
}
return dwRet;
} bool h264_decode_seq_parameter_set(BYTE * buf,UINT nLen,int &Width,int &Height)
{
UINT StartBit=;
int forbidden_zero_bit=u(,buf,StartBit);
int nal_ref_idc=u(,buf,StartBit);
int nal_unit_type=u(,buf,StartBit);
if(nal_unit_type==)
{
int profile_idc=u(,buf,StartBit);
int constraint_set0_flag=u(,buf,StartBit);//(buf[1] & 0x80)>>7;
int constraint_set1_flag=u(,buf,StartBit);//(buf[1] & 0x40)>>6;
int constraint_set2_flag=u(,buf,StartBit);//(buf[1] & 0x20)>>5;
int constraint_set3_flag=u(,buf,StartBit);//(buf[1] & 0x10)>>4;
int reserved_zero_4bits=u(,buf,StartBit);
int level_idc=u(,buf,StartBit); int seq_parameter_set_id=Ue(buf,nLen,StartBit); if( profile_idc == || profile_idc == ||
profile_idc == || profile_idc == )
{
int chroma_format_idc=Ue(buf,nLen,StartBit);
if( chroma_format_idc == )
int residual_colour_transform_flag=u(,buf,StartBit);
int bit_depth_luma_minus8=Ue(buf,nLen,StartBit);
int bit_depth_chroma_minus8=Ue(buf,nLen,StartBit);
int qpprime_y_zero_transform_bypass_flag=u(,buf,StartBit);
int seq_scaling_matrix_present_flag=u(,buf,StartBit); int seq_scaling_list_present_flag[];
if( seq_scaling_matrix_present_flag )
{
for( int i = ; i < ; i++ ) {
seq_scaling_list_present_flag[i]=u(,buf,StartBit);
}
}
}
int log2_max_frame_num_minus4=Ue(buf,nLen,StartBit);
int pic_order_cnt_type=Ue(buf,nLen,StartBit);
if( pic_order_cnt_type == )
int log2_max_pic_order_cnt_lsb_minus4=Ue(buf,nLen,StartBit);
else if( pic_order_cnt_type == )
{
int delta_pic_order_always_zero_flag=u(,buf,StartBit);
int offset_for_non_ref_pic=Se(buf,nLen,StartBit);
int offset_for_top_to_bottom_field=Se(buf,nLen,StartBit);
int num_ref_frames_in_pic_order_cnt_cycle=Ue(buf,nLen,StartBit); int *offset_for_ref_frame=new int[num_ref_frames_in_pic_order_cnt_cycle];
for( int i = ; i < num_ref_frames_in_pic_order_cnt_cycle; i++ )
offset_for_ref_frame[i]=Se(buf,nLen,StartBit);
delete [] offset_for_ref_frame;
}
int num_ref_frames=Ue(buf,nLen,StartBit);
int gaps_in_frame_num_value_allowed_flag=u(,buf,StartBit);
int pic_width_in_mbs_minus1=Ue(buf,nLen,StartBit);
int pic_height_in_map_units_minus1=Ue(buf,nLen,StartBit); Width=(pic_width_in_mbs_minus1+)*;
Height=(pic_height_in_map_units_minus1+)*; return true;
}
else
return false;
} void CCommDlg::OnOK()
{
CString str;
//数据必须把H264的头0x000001去掉
BYTE bytes[]={0x67,0x64,0x08,0x1F,0xAC,0x34,0xC1,0x08,0x28,0x0F,0x64};
UINT startbit=;
int Width,Height;
if (h264_decode_seq_parameter_set(bytes,,Width,Height))
{
str.Format("%d-%d",Width,Height); AfxMessageBox(str);
}
}

从H264码流中获取视频宽高 (SPS帧)的更多相关文章

  1. 从H264码流中获取视频宽高 (SPS帧) 升级篇

    之前写过 <从H264码流中获取视频宽高 (SPS帧)> . 但发现很多局限性,而且有时解出来是错误的. 所以重新去研究了. 用了 官方提供的代码库来解析. 花了点时间,从代码库里单独把解 ...

  2. H264码流中SPS PPS详解<转>

    转载地址:https://zhuanlan.zhihu.com/p/27896239 1 SPS和PPS从何处而来? 2 SPS和PPS中的每个参数起什么作用? 3 如何解析SDP中包含的H.264的 ...

  3. Activity启动过程中获取组件宽高的五种方式

    第一种:(重写Activity的onWindowFocusChanged方法) /** * 重写Acitivty的onWindowFocusChanged方法 */ @Override public ...

  4. H.264从SPS中提取视频宽高

    H.264有两种封装模式: (1)annexb模式:传统模式,使用start code来分隔NAL, SPS和PPS是在ES流的头部: (2)mp4模式:没有start code,使用NALU长度(固 ...

  5. Vue中获取元素宽高

    <div ref="init"></div> 写在 页面 方法 部分 这里的 offsetHeight 是返回元素的宽度(包括元素宽度.内边距和边框,不包括 ...

  6. android onCreate中获取view宽高为0的解决方法

    view.post(runnable) 通过post可以将一个runnable投递到消息队列的尾部,然后等待UI线程Looper调用此runnable的时候,view也已经初始化好了. view.po ...

  7. ffmpeg 获取视频宽高

    int main(int argc, char *argv[]) { const char* file_name = "video.mp4"; int ret; unsigned ...

  8. Activity正确获取View宽高

    在View的measure完成后,一般可以通过getMeasureWidth/getMeasureWidth方法可以正确的获取View的宽高,而在特殊情况下,可能需要多次measure才能确定最终的测 ...

  9. H264码流打包分析

    转自:http://www.360doc.com/content/13/0124/08/9008018_262076786.shtml   SODB 数据比特串-->最原始的编码数据 RBSP ...

随机推荐

  1. insertAdjacentHTML方法示例

    添加HTML内容与文本内容以前用的是innerHTML与innerText方法,最近发现还有insertAdjacentHTML和insertAdjacentText方法,这两个方法更灵活,可以在指定 ...

  2. Qt 环境下的mapx控件-------2

    今天花了一天的时间去查找mapx相关的资料,但是到最后想要的东西还是一无所获,不过还是学到了很多东西.下面以大家分享一下: mapx软件的安装:下载后安装mapx软件,成功后会在安装路径下存在acti ...

  3. System.Threading.Timer 定时器的用法

    System.Threading.Timer 是C# 中的一个定时器,可以定时(不断循环)执行一个任务.它是在线程上执行的,具有很好的安全性.为此  .Net Framework 提供了5个重载的构造 ...

  4. iOS在label上加横杠

    UILabel * label = [[UILabel alloc]initWithFrame:CGRectMake(20, 50, 200, 50)];    [self.view addSubvi ...

  5. 最新原创:Power8伴随云计算横空出世

    Power8伴随云计算横空出世 自从IBM将并不赚钱的x86服务器业务转手给联想之后,从此IBM便开始了硬件转型的新里程碑.伴随此事继续发酵的还有Power System Linux落户北京,从此IB ...

  6. 浅尝辄止——使用ActiveX装载WPF控件

    1 引言 使用VC编写的容器类编辑器,很多都可以挂接ActiveX控件,因为基于COM的ActiveX控件不仅封装性不错,还可以显示一些不错的界面图元. 但是随着技术不断的进步,已被抛弃的Active ...

  7. js语言精粹读书笔记一

    一.语法 1.

  8. 关于C#的委托(delegate)的自我理解

    首先描述一个事情,一个老师饿了,他要去买东西填饱肚子,然后他发现他的学生“小李”在玩,没学习,于是就委托“小李”去帮他买吃的. 根据这件事我们来分析: 首先得有个老师(老师饿了是他的方法,老师买东西也 ...

  9. css左右居中的几种常见方法

    本人是前端的新人,这是第一次写技术博客,各位大大,本文有错误请指正,手中的板砖尽量轻拍,我怕疼~~ 对于水平居中和垂直居中我也用过很多方法,但是有的时候管用有的时候又嗝屁不好使了.涉及到的情况很多,所 ...

  10. 计算机缺失缺少mfc110.dll等相关文件的解决办法

    去https://www.microsoft.com/zh-CN/download/details.aspx?id=30679下载 VSU4\vcredist_x64.exe 和VSU4\vcredi ...