截屏代码
1 #define ALIGNEDONDWORD(theBytes) ( ( ( (DWORD)(theBytes) + 31 ) & ~31 ) >> 3 ) 2 3 BOOL BmpFromHandle( HDC hDC, HBITMAP hBitmap, WORD nBits, LPCTSTR lpszFile ) 4 { 5 BITMAP bmp; 6 WORD cClrBits; 7 LPBITMAPINFO bi; 8 BITMAPFILEHEADER bf; 9 LPVOID lpData; 10 HANDLE hFile; 11 DWORD dwBytes; 12 int nRet; 13 BOOL bRet; 14 15 nRet = ::GetObject( ( HANDLE )hBitmap, sizeof( BITMAP ), &bmp ); 16 if ( nRet != sizeof( BITMAP ) ) 17 { 18 return FALSE; 19 } 20 21 bmp.bmBitsPixel = nBits; 22 23 cClrBits = ( WORD )( bmp.bmPlanes * bmp.bmBitsPixel ); 24 25 if ( cClrBits == 1 ) 26 { 27 cClrBits = 1; 28 } 29 else if ( cClrBits <= 4 ) 30 { 31 cClrBits = 4; 32 } 33 else if ( cClrBits <= 8 ) 34 { 35 cClrBits = 8; 36 } 37 else if ( cClrBits <= 16 ) 38 { 39 cClrBits = 16; 40 } 41 else if ( cClrBits <= 24 ) 42 { 43 cClrBits = 24; 44 } 45 else 46 { 47 cClrBits = 32; 48 } 49 50 if ( cClrBits < 24 ) 51 { 52 bi = ( LPBITMAPINFO )calloc( 1, sizeof( BITMAPINFOHEADER ) + sizeof( RGBQUAD ) * ( 1 << cClrBits ) ); 53 } 54 else 55 { 56 bi = ( LPBITMAPINFO )calloc( 1, sizeof( BITMAPINFOHEADER ) ); 57 } 58 59 if ( bi == NULL ) 60 { 61 return FALSE; 62 } 63 64 bi->bmiHeader.biSize = sizeof( BITMAPINFOHEADER ); 65 bi->bmiHeader.biWidth = bmp.bmWidth; 66 bi->bmiHeader.biHeight = bmp.bmHeight; 67 bi->bmiHeader.biPlanes = bmp.bmPlanes; 68 bi->bmiHeader.biBitCount = bmp.bmBitsPixel; 69 bi->bmiHeader.biCompression = BI_RGB; 70 bi->bmiHeader.biSizeImage = ( ( ( bi->bmiHeader.biWidth * cClrBits + 31 ) & ~31 ) >> 3 ) * bi->bmiHeader.biHeight; 71 /*bi->bmiHeader.biXPelsPerMeter = 0; 72 bi->bmiHeader.biYPelsPerMeter = 0;*/ 73 74 if ( cClrBits < 24 ) 75 { 76 bi->bmiHeader.biClrUsed = ( 1 << cClrBits ); 77 } 78 /*else 79 { 80 bi->bmiHeader.biClrUsed = 0; 81 }*/ 82 83 /*bi->bmiHeader.biClrImportant = 0;*/ 84 85 86 lpData = calloc( ( bi->bmiHeader.biSizeImage + 4095 ) >> 12, 4096 ); 87 if ( lpData == NULL ) 88 { 89 free( bi ); 90 return FALSE; 91 } 92 93 nRet = ::GetDIBits( hDC, hBitmap, 0, bi->bmiHeader.biHeight, lpData, bi, DIB_RGB_COLORS ); 94 if ( nRet != bi->bmiHeader.biHeight ) 95 { 96 goto err_exit; 97 } 98 99 if ( cClrBits < 24 ) 100 { 101 bi->bmiHeader.biClrUsed = ( 1 << cClrBits ); 102 } 103 104 memset( &bf, 0, sizeof( BITMAPFILEHEADER ) ); 105 bf.bfType = 0x4d42; 106 bf.bfSize = sizeof( BITMAPFILEHEADER ) + sizeof( BITMAPINFOHEADER ) + bi->bmiHeader.biClrUsed * sizeof( RGBQUAD ) + bi->bmiHeader.biSizeImage; 107 /*bf.bfReserved1 = 0; 108 bf.bfReserved2 = 0;*/ 109 bf.bfOffBits = bf.bfSize - bi->bmiHeader.biSizeImage; 110 111 hFile = ::CreateFile( lpszFile, GENERIC_WRITE, 0, NULL, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL ); 112 if ( hFile == INVALID_HANDLE_VALUE ) 113 { 114 goto err_exit; 115 } 116 117 bRet = ::WriteFile( hFile, &bf, sizeof( BITMAPFILEHEADER ), &dwBytes, NULL ); 118 if ( !bRet || dwBytes != sizeof( BITMAPFILEHEADER ) ) 119 { 120 ::CloseHandle( hFile ); 121 goto err_exit; 122 } 123 124 bRet = ::WriteFile( hFile, bi, bf.bfOffBits - sizeof( BITMAPFILEHEADER ), &dwBytes, NULL ); 125 if ( !bRet || dwBytes != bf.bfOffBits - sizeof( BITMAPFILEHEADER ) ) 126 { 127 ::CloseHandle( hFile ); 128 goto err_exit; 129 } 130 131 bRet = ::WriteFile( hFile, lpData, bi->bmiHeader.biSizeImage, &dwBytes, NULL ); 132 if ( !bRet || dwBytes != bi->bmiHeader.biSizeImage ) 133 { 134 ::CloseHandle( hFile ); 135 goto err_exit; 136 } 137 138 ::CloseHandle( hFile ); 139 140 free( lpData ); 141 free( bi ); 142 return TRUE; 143 144 err_exit: 145 free( lpData ); 146 free( bi ); 147 return FALSE; 148 } 149 150 BOOL CopyScreen( LPCTSTR lpszFile, WORD nBits = 24 ) 151 { 152 HDC hDC, hMemDC; 153 HBITMAP hBitmap, hBitmapOld; 154 int nWidth, nHeight; 155 BOOL bRet; 156 157 bRet = TRUE; 158 159 hDC = ::GetDC( NULL ); 160 nWidth = ::GetSystemMetrics( SM_CXSCREEN ); 161 nHeight = ::GetSystemMetrics( SM_CYSCREEN ); 162 hMemDC = ::CreateCompatibleDC( hDC ); 163 hBitmap = ::CreateCompatibleBitmap( hDC, nWidth, nHeight ); 164 hBitmapOld = ( HBITMAP )::SelectObject( hMemDC, ( HGDIOBJ )hBitmap ); 165 166 bRet = ::BitBlt( hMemDC, 0, 0, nWidth, nHeight, hDC, 0, 0, SRCCOPY ); 167 if ( bRet ) 168 { 169 bRet = BmpFromHandle( hMemDC, hBitmap, nBits, lpszFile ); 170 } 171 172 ::SelectObject( hMemDC, ( HGDIOBJ )hBitmapOld ); 173 ::DeleteObject( ( HGDIOBJ )hBitmap ); 174 ::DeleteDC( hMemDC ); 175 ::ReleaseDC( NULL, hDC ); 176 return bRet; 177 } 178 179 BOOL CopyRC( UINT nBitmapID, LPCTSTR lpszFile, WORD nBits = 24 ) 180 { 181 HDC hDC; 182 HBITMAP hBitmap; 183 BOOL bRet; 184 185 bRet = TRUE; 186 187 hDC = ::GetDC( NULL ); 188 189 hBitmap = ::LoadBitmap( ::GetModuleHandle( NULL ), MAKEINTRESOURCE( nBitmapID ) ); 190 if ( hBitmap ) 191 { 192 bRet = BmpFromHandle( hDC, hBitmap, nBits, lpszFile ); 193 } 194 else 195 { 196 bRet = FALSE; 197 } 198 199 ::DeleteObject( ( HGDIOBJ )hBitmap ); 200 ::ReleaseDC( NULL, hDC ); 201 202 return bRet; 203 }