2011-07-30 145 views
0

使用cygwin gcc编译器处理Windows 7 Service Pack 1环境。截图程序无法正常工作

以下程序应该截屏并将文件保存为.bmp文件指定的文件。它编译得很好,似乎在所需的目录中提供了一个.bmp文件,但运行时似乎只创建了一个没有屏幕截图数据的1kb文件。如果while循环给出while(1)的起始值,则会出现“无法创建位图文件”错误。我是这种编程的新手,似乎无法明白这是为什么。

任何想法?

(必须与-lgdi32编译)

代码:

#include <stdlib.h> 
#include <windows.h> 
#include <stdio.h> 

void TakeScreenShot(char* filename); 

int main() 
{ 
    TakeScreenShot("c:\\Screenshot.bmp"); 
    return 0; 
} 

// 
// Side Effects:N/A 
// 
//This code is copyrighted and has// limited warranties.Please see http:// 
// www.Planet-Source-Code.com/vb/scripts/Sh 
// owCode.asp?txtCodeId=10754&lngWId=3//for details.//************************************** 
// 

void TakeScreenShot(char* filename) 
{ 
    keybd_event(VK_SNAPSHOT, 0x45, KEYEVENTF_EXTENDEDKEY, 0); 
    keybd_event(VK_SNAPSHOT, 0x45, KEYEVENTF_EXTENDEDKEY | KEYEVENTF_KEYUP, 0); 
    HBITMAP h;   

    OpenClipboard(NULL); 
    h = (HBITMAP)GetClipboardData(CF_BITMAP); 
    CloseClipboard(); 
    HDC hdc=NULL; 

    FILE*fp=NULL; 
    LPVOID pBuf=NULL; 
    BITMAPINFO bmpInfo; 
    BITMAPFILEHEADER bmpFileHeader; 

    do 
    { 
     hdc=GetDC(NULL); 
     ZeroMemory(&bmpInfo,sizeof(BITMAPINFO)); 
     bmpInfo.bmiHeader.biSize=sizeof(BITMAPINFOHEADER); 
     GetDIBits(hdc,h,0,0,NULL,&bmpInfo,DIB_RGB_COLORS); 

     if(bmpInfo.bmiHeader.biSizeImage<=0) 
     bmpInfo.bmiHeader.biSizeImage=bmpInfo.bmiHeader.biWidth*abs(bmpInfo.bmiHeader.biHeight)*(bmpInfo.bmiHeader.biBitCount+7)/8; 
     if((pBuf = malloc(bmpInfo.bmiHeader.biSizeImage))==NULL) 
     { 
     MessageBox(NULL, "Unable to Allocate Bitmap Memory", "Error", MB_OK|MB_ICONERROR); 
     break; 
     } 
     bmpInfo.bmiHeader.biCompression=BI_RGB; 
     GetDIBits(hdc,h,0,bmpInfo.bmiHeader.biHeight,pBuf, &bmpInfo, DIB_RGB_COLORS); 

     if((fp = fopen(filename,"wb"))==NULL) 
     { 
     MessageBox(NULL, "Unable to Create Bitmap File", "Error", MB_OK|MB_ICONERROR); 
     break; 
     } 

     bmpFileHeader.bfReserved1=0; 
     bmpFileHeader.bfReserved2=0; 
     bmpFileHeader.bfSize=sizeof(BITMAPFILEHEADER)+sizeof(BITMAPINFOHEADER)+bmpInfo.bmiHeader.biSizeImage; 
     bmpFileHeader.bfType='MB'; 
     bmpFileHeader.bfOffBits=sizeof(BITMAPFILEHEADER)+sizeof(BITMAPINFOHEADER); 

     fwrite(&bmpFileHeader,sizeof(BITMAPFILEHEADER),1,fp); 
     fwrite(&bmpInfo.bmiHeader,sizeof(BITMAPINFOHEADER),1,fp); 
     fwrite(pBuf,bmpInfo.bmiHeader.biSizeImage,1,fp); 
    } 
    while(0); 

    if(hdc) 
     ReleaseDC(NULL,hdc); 

    if(pBuf) 
     free(pBuf); 

    if(fp) 
     fclose(fp); 
} 
+0

附加:似乎创建的.png文件无法用指示损坏的任何图像查看软件打开。 – Jeremy

回答

1

程序显然保存它从剪贴板中得到位图数据。如果剪贴板上没有数据,我认为它只保存一个空位图。它写入一个名为“Screenshot.bmp”的文件,而不是一个.png文件。

要将位图数据放在剪贴板上,我假设您必须先按下打印屏幕按钮。这将截图保存到剪贴板。现在,该程序可用于将此剪贴板数据保存到文件中。

+0

非常好。这似乎是对的钱。虽然不应该keybd_event(VK_SNAPSHOT,0x45,KEYEVENTF_EXTENDEDKEY,0);模拟按下的打印屏幕按钮?它确实创建了一个.bmp文件,那是我的不好之处。 – Jeremy

+0

我假设keybd_event()可能无法按预期在所有版本的Windows上运行。 http://msdn.microsoft.com/en-us/library/ms646304%28v=vs.85%29.aspx说:**注意此功能已被取代。改用SendInput。**我从来没有用过,但我想你应该调查这个功能。 –

+0

我已经在这个页面上添加了SendInput函数:http://www.codeguru.com/forum/showthread.php?t=377393事情是当任何密钥吸如VK_CAPITAL在那里使用,它工作正常,但VK_SCREENSHOT选项是唯一一个看起来不能正常工作的人! – Jeremy