|
|
1.1 root 1: /******************************Module*Header*******************************\
2: * Module Name: loadbmp.c
3: *
4: * Contains function that loads a bitmap file
5: *
6: * Created: 08-Jan-1992 11:06:37
7: * Author: Petrus Wong
8: *
9: * Copyright (c) 1990 Microsoft Corporation
10: *
11: * Contains the main routine for loading a DI bitmap file.
12: *
13: * Dependencies:
14: *
15: * (#defines)
16: * (#includes)
17: * #include <windows.h>
18: * #include "jtypes.h"
19: *
20: \**************************************************************************/
1.1.1.2 ! root 21: /**************************************************************************\
! 22: *
! 23: *
! 24: * Summary: In Win32, saving or loading a bitmap in DIB format is basically
! 25: * the same as in Win16. However, care must be taken in DWORD
! 26: * alignment, especially on the MIPS platform.
! 27: *
! 28: * SYMPTOMS Exception on loading or saving a bitmap on the MIPS platform.
! 29: * In NTSD, get the error message of "data mis-alignment."
! 30: *
! 31: * CAUSE Passed a Non-DWORD aligned actual parameter to, say, GetDIBits().
! 32: *
! 33: * STATUS/RESOLUTION
! 34: *
! 35: * The DIB file format contains the BITMAPFILEHEADER then followed
! 36: * immediately by the BITMAPINFOHEADER. Notice that the BITMAPFILEHEADER is
! 37: * not DWORD aligned. Thus, the structure that follows it, the
! 38: * BITMAPINFOHEADER is not on a DWORD boundary. If a pointer to this DWORD
! 39: * mis-aligned structure is passed to the 6th argument of GetDIBits(), an
! 40: * exception will occur.
! 41: *
! 42: * The remedy is to copy the data in the structure over to a DWORD
! 43: * aligned memory and passes the pointer to the latter structure to the
! 44: * function instead. See below for detail.
! 45: *
! 46: *
! 47: * =========================================================================
! 48: *
! 49: *
! 50: * Summary: When saving a bitmap in DIB format in file, the GDI function is
! 51: * used to retrieve the bitmap information. Though the general use
! 52: * of this function and the technics for saving a bitmap in DIB
! 53: * format are largely unchanged, this article provide more details
! 54: * in the use of the Win32 version of the GetDIBits() api.
! 55: *
! 56: *
! 57: * The function can be used to retrieve the following information:
! 58: * 1. Just retrieving the data in the BitmapInfoHeader, no color table and
! 59: * no bits.
! 60: *
! 61: * 2. Retrieving the data in the BitmapInfoHeader and the color table.
! 62: *
! 63: * 3. Retrieving all the data, BitmapInfoHeader, color table and the bits.
! 64: *
! 65: * The 5th and the 6th parameters of the function are used to tell the
! 66: * graphics engine what exactly the appllication wants it to return. If the
! 67: * 5th parameteris NULL, then no bits will be returned. If the biBitCount
! 68: * is 0 in the 6th parameter, then no color table will be returned. In
! 69: * addition, the biSize field of the BitmapInfoHeader must be set to either
! 70: * the size of BitmapInfoHeader or BitmapCoreHeader for the function to work.
! 71: * See the following for details.
! 72: *
! 73: *
! 74: *
! 75: \**************************************************************************/
! 76: //#define STRICT
1.1 root 77: #include <windows.h>
78: #include "jtypes.h"
79:
80: extern HWND ghwndMain;
81: extern VOID ErrorOut();
82: BOOL LoadBitmapFile(HDC, PINFO, PSTR);
83:
84: /******************************Public*Routine******************************\
85: *
86: * LoadBitmapFile
87: *
88: * Effects: Loads the bitmap from file and put into pInfo->hBmpSaved
89: *
90: * Warnings: pszFileName contains the full path
91: *
92: * History:
93: * 09-Jan-1992 -by- Petrus Wong
94: * Wrote it.
95: \**************************************************************************/
96:
97: BOOL LoadBitmapFile(HDC hDC, PINFO pInfo, PSTR pszFileName)
98: {
99: BOOL bSuccess;
100: HANDLE hFile, hMapFile;
101: LPVOID pMapFile;
102: LPBITMAPINFOHEADER pbmh;
103: LPBITMAPINFO pbmi;
104: PBYTE pjTmp;
105: ULONG sizBMI;
1.1.1.2 ! root 106: INT iNumClr;
! 107: #ifdef LATER
! 108: RGBQUAD *pRGBQuad;
! 109: RGBTRIPLE *pRGBTriple;
! 110: INT iEntry, i;
! 111: #endif
1.1 root 112:
113: bSuccess = TRUE;
114:
115: if ((hFile = CreateFile(pszFileName, GENERIC_READ, FILE_SHARE_READ, NULL,
116: OPEN_EXISTING, FILE_ATTRIBUTE_READONLY, NULL)) == (HANDLE)-1) {
117: ErrorOut("Fail in file open");
118: bSuccess = FALSE;
119: goto ErrExit1;
120: }
121:
122: //
123: // Create a map file of the opened file
124: //
125: if ((hMapFile = CreateFileMapping(hFile, NULL,
126: PAGE_READONLY, 0, 0, "MapF")) == (HANDLE)-1) {
127: ErrorOut("Fail in creating map file");
128: bSuccess = FALSE;
129: goto ErrExit2;
130:
131: }
132:
133: //
134: // Map a view of the whole file
135: //
136: if ((pMapFile = MapViewOfFile(hMapFile, FILE_MAP_READ, 0, 0, 0)) == NULL) {
137: ErrorOut("Fail in mapping view of the Map File object");
138: bSuccess = FALSE;
139: goto ErrExit3;
140: }
141:
142: //
143: // First check that it is a bitmap file
144: //
145: if (*((PWORD)pMapFile) != 0x4d42) { // 'BM'
146: MessageBox(ghwndMain, "This is not a DIB bitmap file!", "Error", MB_OK);
147: bSuccess = FALSE;
148: goto ErrExit3;
149: }
150:
1.1.1.2 ! root 151: #ifndef LATER
1.1 root 152: //
1.1.1.2 ! root 153: // The file header doesn't end on DWORD boundary...
1.1 root 154: //
1.1.1.2 ! root 155: pbmh = (LPBITMAPINFOHEADER)((PBYTE)pMapFile + sizeof(BITMAPFILEHEADER));
! 156:
1.1 root 157: {
1.1.1.2 ! root 158: BITMAPCOREHEADER bmch, *pbmch;
! 159: BITMAPINFOHEADER bmih, *pbmih;
! 160: PBYTE pjTmp;
! 161: ULONG ulSiz;
! 162:
! 163: pbmch = &bmch;
! 164: pbmih = &bmih;
! 165:
! 166: pjTmp = (PBYTE)pbmh;
! 167: ulSiz = sizeof(BITMAPCOREHEADER);
! 168: while (ulSiz--) {
! 169: *(((PBYTE)pbmch)++) = *(((PBYTE)pjTmp)++);
! 170: }
! 171:
! 172: pjTmp = (PBYTE)pbmh;
! 173: ulSiz = sizeof(BITMAPINFOHEADER);
! 174: while (ulSiz--) {
! 175: *(((PBYTE)pbmih)++) = *(((PBYTE)pjTmp)++);
! 176: }
! 177:
! 178: //
! 179: // Use the size to determine if it is a BitmapCoreHeader or
! 180: // BitmapInfoHeader
! 181: //
! 182: if (bmch.bcSize == sizeof(BITMAPCOREHEADER))
! 183: {
! 184: WORD wBitCount;
! 185:
! 186: wBitCount = bmch.bcBitCount;
! 187: iNumClr = ((wBitCount == 24) ? 0 : (1 << wBitCount));
! 188: sizBMI = sizeof(BITMAPCOREHEADER)+sizeof(RGBTRIPLE)*iNumClr;
! 189: }
! 190: else // BITMAPINFOHEADER
! 191: {
! 192: WORD wBitCount;
! 193:
! 194: wBitCount = bmih.biBitCount;
! 195: iNumClr = ((wBitCount == 24) ? 0 : (1 << wBitCount));
! 196: sizBMI = sizeof(BITMAPINFOHEADER)+sizeof(RGBQUAD)*iNumClr;
! 197: }
! 198:
! 199:
1.1 root 200: }
201:
202: if ((pbmi = (LPBITMAPINFO) LocalAlloc(LMEM_FIXED,sizBMI)) == NULL) {
203: MessageBox(ghwndMain, "Fail in Memory Allocation!", "Error", MB_OK);
204: bSuccess = FALSE;
205: goto ErrExit3;
206: }
207:
208: //
209: // Make sure we pass in a DWORD aligned BitmapInfo to CreateDIBitmap
210: // Otherwise, exception on the MIPS platform
211: // CR!!! Equivalent to memcpy
1.1.1.2 ! root 212: // WARNING! This is not handling the RGBTRIPLE case correctly
1.1 root 213: //
214: pjTmp = (PBYTE)pbmi;
215:
216: while(sizBMI--)
217: {
218: *(((PBYTE)pjTmp)++) = *(((PBYTE)pbmh)++);
219: }
1.1.1.2 ! root 220: #else
! 221: pbmh = (LPBITMAPINFOHEADER)((PBYTE)pMapFile + sizeof(BITMAPFILEHEADER));
! 222:
! 223: if (pbmh->biSize == sizeof(BITMAPCOREHEADER))
! 224: {
! 225:
! 226: DebugBreak();
! 227:
! 228: iEntry = ((((LPBITMAPCOREHEADER)pbmh)->bcBitCount == 24)
! 229: ? 0
! 230: : (1 << ((LPBITMAPCOREHEADER)pbmh)->bcBitCount));
! 231:
! 232: sizBMI = sizeof(BITMAPCOREHEADER)+sizeof(RGBQUAD)*iEntry;
! 233:
! 234: if ((pbmi = (LPBITMAPINFO) LocalAlloc(LMEM_FIXED,sizBMI)) == NULL) {
! 235: MessageBox(ghwndMain, "Fail in Memory Allocation!", "Error", MB_OK);
! 236: bSuccess = FALSE;
! 237: goto ErrExit3;
! 238: }
! 239:
! 240: pjTmp = (PBYTE)pbmi;
! 241:
! 242: sizBMI = sizeof(BITMAPCOREHEADER);
! 243: while(sizBMI--)
! 244: {
! 245: *(((PBYTE)pjTmp)++) = *(((PBYTE)pbmh)++);
! 246: }
! 247:
! 248: ((PBYTE)pjTmp)--;
! 249: ((PBYTE)pbmh)--;
! 250:
! 251: pRGBQuad = (RGBQUAD *)pbmh;
! 252: pRGBTriple = (RGBTRIPLE *)pjTmp;
! 253:
! 254: for (i=0; i < iEntry; i++, pRGBTriple++, pRGBQuad++)
! 255: {
! 256: pRGBQuad->rgbBlue = pRGBTriple->rgbtBlue;
! 257: pRGBQuad->rgbGreen = pRGBTriple->rgbtGreen;
! 258: pRGBQuad->rgbRed = pRGBTriple->rgbtRed;
! 259: pRGBQuad->rgbReserved = 0x0;
! 260: }
! 261:
! 262:
! 263: }
! 264: else // BITMAPINFOHEADER
! 265: {
! 266: sizBMI = sizeof(BITMAPINFOHEADER)+sizeof(RGBQUAD)*
! 267: ((pbmh->biBitCount == 24) ? 0 : (1 << pbmh->biBitCount));
! 268:
! 269: while(sizBMI--)
! 270: {
! 271: *(((PBYTE)pjTmp)++) = *(((PBYTE)pbmh)++);
! 272: }
! 273:
! 274: }
1.1 root 275:
1.1.1.2 ! root 276: #endif
1.1 root 277: pMapFile = (PBYTE)pMapFile + ((BITMAPFILEHEADER *)pMapFile)->bfOffBits;
278:
1.1.1.2 ! root 279:
1.1 root 280: if ((pInfo->hBmpSaved = CreateDIBitmap(hDC, (LPBITMAPINFOHEADER)pbmi,
281: CBM_INIT, pMapFile, pbmi, DIB_RGB_COLORS)) == NULL) {
282: ErrorOut("Fail in creating DIB bitmap from file!");
283: bSuccess = FALSE;
284: goto ErrExit4;
285: }
286:
287:
288:
289: ErrExit4:
290: LocalFree(pbmi);
291: ErrExit3:
292: CloseHandle(hMapFile);
293: ErrExit2:
294: CloseHandle(hFile);
295: ErrExit1:
296:
297: return (bSuccess);
298:
299: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.