directshow获取一帧的数据如何做成.bmp的图片文件格式?

用Directshow进行截图并保存为.bmp格式,当我的源级filter是摄像头,采用IBasicVideo::GetCurrentImage获取不到数据;当源级fil... 用Directshow进行截图并保存为.bmp格式,当我的源级filter是摄像头,采用IBasicVideo::GetCurrentImage获取不到数据;当源级filter是一个视频文件的时候采用IBasicVideo::GetCurrentImage可以获取到数据,这是怎么回事??
还有就是自己提取一帧数据,写入到.bmp的文件中,文件显示损坏或过大,打不开,下面是我的程序
展开
 我来答
hero06111001
2016-01-04 · 超过19用户采纳过TA的回答
知道答主
回答量:50
采纳率:0%
帮助的人:26.4万
展开全部
 

//保存buffer到bmp文件

//iWidth:图像宽; iHeight:图像高;pBuffer:图像RGB数据;filePath:存储路径;fileName:保存文件名;fileNum:保存文件编号
//SaveDIB2Bmp(100, "frame", "D://screenshot")
bool MyDC::SaveDIB2Bmp(int fileNum, const char * fileName, const char * filePath, int iWidth, int iHeight, BYTE *pBuffer)
{
 
 BITMAPINFOHEADER bih;
 ConstructBih(iWidth,iHeight,bih);
 BITMAPFILEHEADER bhh;
 ContructBhh(iWidth,iHeight,bhh);
 
 TCHAR BMPFileName[1024];
 int widthStep = (((iWidth * 24) + 31) & (~31)) / 8 ; //每行实际占用的大小(每行都被填充到一个4字节边界)
 int DIBSize = widthStep * iHeight ;  //buffer的大小 (字节为单位)

 //save
 char path[1024];
 char str[1024];

 sprintf(str,"%d",fileNum);  
 strcat(str, fileName);
 strcat(str,".bmp");  //frame100.bmp
 sprintf(path,"%s", filePath);
 strcat(path,str); //Path//frame100.bmp

 strcpy(BMPFileName,path);
 CFile file;
 try
 {
  if(file.Open(BMPFileName,CFile::modeWrite | CFile::modeCreate))
  {//写入文件
  
   file.Write((LPSTR)&bhh,sizeof(BITMAPFILEHEADER));
   file.Write((LPSTR)&bih,sizeof(BITMAPINFOHEADER));
   file.Write(pBuffer,DIBSize);
   file.Close();
   return true;
  }

 }
 catch (...) 
 {
  AfxMessageBox("MyDC::SaveDIB2Bmp");
 }
 return false;
}

 

//构建BMP位图文件头
void MyDC::ContructBhh(int nWidth,int nHeight,BITMAPFILEHEADER& bhh) //add 2010-9-04
{
 int widthStep = (((nWidth * 24) + 31) & (~31)) / 8 ; //每行实际占用的大小(每行都被填充到一个4字节边界)
 bhh.bfType = ((WORD) ('M' << 8) | 'B');  //'BM'
 bhh.bfSize = (DWORD)sizeof(BITMAPFILEHEADER) + (DWORD)sizeof(BITMAPINFOHEADER) + widthStep * nHeight;
 bhh.bfReserved1 = 0;
 bhh.bfReserved2 = 0;
 bhh.bfOffBits = (DWORD)sizeof(BITMAPFILEHEADER) + (DWORD)sizeof(BITMAPINFOHEADER);

}


//构建BMP文件信息头
void MyDC::ConstructBih(int nWidth,int nHeight,BITMAPINFOHEADER& bih) 
{
 int widthStep = (((nWidth * 24) + 31) & (~31)) / 8 ; 

 bih.biSize=40;       // header size
 bih.biWidth=nWidth;
 bih.biHeight=nHeight;
 bih.biPlanes=1;
 bih.biBitCount=24;     // RGB encoded, 24 bit
 bih.biCompression=BI_RGB;   // no compression 非压缩
 bih.biSizeImage=widthStep*nHeight*3;
 bih.biXPelsPerMeter=0;
 bih.biYPelsPerMeter=0;
 bih.biClrUsed=0;
 bih.biClrImportant=0; 

}
asas77888
推荐于2016-01-24
知道答主
回答量:14
采纳率:0%
帮助的人:8.6万
展开全部
摄像头时,你有枚举设备,然后获取设备吗?
图片保存,一般用ISampleGrabber获取缓存。
pSampleGrabber->GetConnectedMediaType(&am_media_type); //检索采集卡输入的媒体类型
VIDEOINFOHEADER *pVideoInfoHeader = //数据格式
(VIDEOINFOHEADER *)am_media_type.pbFormat;
pSampleGrabber->SetBufferSamples(TRUE);
// 准备好buffer
long nBufferSize = am_media_type.lSampleSize; //定义一个long,存放样本大小。
long *pBuffer = (long *)malloc(nBufferSize); //指向nBufferSize的指针pBuffer。
// 将现在显示的图像获取为静止画面
pSampleGrabber->GetCurrentBuffer(&nBufferSize,
pBuffer);
//
// 保存到Bitmap。
// 此sample为了看到截图结果,
// 将其保存为Bitmap。
//
HANDLE fh;
BITMAPFILEHEADER bmphdr; //包含的信息的类型,规模和布局的文件
DWORD nWritten; //双字节
memset(&bmphdr, 0, sizeof(bmphdr)); //设置到指定的字符缓冲区(指针的目的地,字符集,字符数)
bmphdr.bfType = ('M' << 8) | 'B'; //按位或,为BM。
bmphdr.bfSize = sizeof(bmphdr) + sizeof(BITMAPINFOHEADER) + nBufferSize; //位图文件头数据(类型,大小),位图信息头数据(尺度),图片数据(每一个像素值。
bmphdr.bfOffBits = sizeof(bmphdr) + sizeof(BITMAPINFOHEADER); //位图数据起始位,在文件头和信息头之后。
fh = CreateFile(TEXT("result.bmp"), //创建文件名,写文件,不共享读写,缺省安全属性,如果文件存在,也创建,一般的文件,模板文件为空。
GENERIC_WRITE, 0, NULL,
CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
WriteFile(fh, &bmphdr, sizeof(bmphdr), &nWritten, NULL); //文件句柄,读写数据缓冲区,多少数据要写入,已经写入多少数据,异步读写(大多使用NULL)
WriteFile(fh, //包含的信息类型,规模和布局的文件,图像的位图的颜色和尺寸信息,显示图像获取静止画面的数据)
&pVideoInfoHeader->bmiHeader,
sizeof(BITMAPINFOHEADER), &nWritten, NULL);
WriteFile(fh, pBuffer, nBufferSize, &nWritten, NULL);
CloseHandle(fh);
free(pBuffer);
本回答被提问者采纳
已赞过 已踩过<
你对这个回答的评价是?
评论 收起
青昂BC
2018-04-25
知道答主
回答量:1
采纳率:0%
帮助的人:882
展开全部
bool CDXGraph::SnapshotBitmap(TCHAR* outFile) {
if (pBasicVideo == NULL) {
return false;
}
long bitmapSize = 0;
HRESULT hr = pBasicVideo->GetCurrentImage(&bitmapSize, NULL);
if (FAILED(hr)) {
return false;
}
char * buffer = new char[bitmapSize];
hr = pBasicVideo->GetCurrentImage(&bitmapSize, (long*)buffer);
if (FAILED(hr)) {
delete[] buffer;
return false;
}
LPBITMAPINFOHEADER lpbi;
lpbi = (LPBITMAPINFOHEADER)buffer;
BITMAPFILEHEADER hdr;
int nColors = 0;
if (lpbi->biBitCount < 8) {
nColors = 1 << lpbi->biBitCount;
}
ZeroMemory(&hdr, sizeof(BITMAPFILEHEADER));
hdr.bfType = ((WORD)('M' << 8) | 'B');
hdr.bfSize = sizeof(hdr) + bitmapSize;
hdr.bfReserved1 = 0;
hdr.bfReserved2 = 0;
hdr.bfOffBits = sizeof(BITMAPFILEHEADER) + lpbi->biSize + nColors*sizeof(RGBQUAD);
CFile bitmapFile(outFile, CFile::modeReadWrite | CFile::modeCreate | CFile::typeBinary);
bitmapFile.Write(&hdr, sizeof(hdr));
bitmapFile.Write(buffer, bitmapSize);
bitmapFile.Close();
delete[] buffer;
return true;
}
已赞过 已踩过<
你对这个回答的评价是?
评论 收起
收起 1条折叠回答
推荐律师服务: 若未解决您的问题,请您详细描述您的问题,通过百度律临进行免费专业咨询

为你推荐:

下载百度知道APP,抢鲜体验
使用百度知道APP,立即抢鲜体验。你的手机镜头里或许有别人想知道的答案。
扫描二维码下载
×

类别

我们会通过消息、邮箱等方式尽快将举报结果通知您。

说明

0/200

提交
取消

辅 助

模 式