update for HEAD-2003091401
[reactos.git] / apps / tests / palbitblt / pal.c
1 /* The idea of this test app is inspired from tutorial       *
2  * found at http://www.theparticle.com/pgraph.html           *
3  *                                                           *
4  * Developed by: Aleksey Bragin <aleksey@studiocerebral.com> *
5  * Version: 1.0                                              */
6
7 #include <windows.h>
8
9 #define W_WIDTH 320
10 #define W_HEIGHT 240
11
12 // special version of BITMAPINFO and LOGPALETTE for max of 256 palette entries
13 typedef struct
14 {
15         BITMAPINFOHEADER bmiHeader;
16         RGBQUAD bmiColors[256];
17 } BITMAPINFO256;
18
19 typedef struct {
20         WORD    palVersion;
21         WORD    palNumEntries;
22         PALETTEENTRY palPalEntry[256];
23 } LOGPALETTE256;
24
25 // The only global variable --- contents of the DIBitmap
26 BYTE* dibits;
27
28 void GeneratePalette(RGBQUAD* p)
29 {
30         int i;
31         for(i=0;i<256;i++)
32         {
33                 p[i].rgbRed = i;
34                 p[i].rgbGreen = i;
35                 p[i].rgbBlue = i;
36                 p[i].rgbReserved = 0;
37         }
38 }
39
40 void DoBlt(HBITMAP hBM)
41 {
42         HDC hDC,Context;
43         HWND ActiveWindow;
44         RECT dest;
45         HBITMAP dflBmp;
46
47         if((ActiveWindow = GetActiveWindow()) == NULL)
48                 return;
49
50         hDC = GetDC(ActiveWindow);
51         GetClientRect(ActiveWindow,&dest);
52         
53         Context = CreateCompatibleDC(0);
54         dflBmp = SelectObject(Context, hBM);
55         BitBlt(hDC, 0, 0, dest.right, dest.bottom, Context, 0, 0, SRCCOPY);
56         SelectObject(Context, dflBmp);
57         DeleteDC(Context);
58         DeleteObject(dflBmp);
59         ReleaseDC(ActiveWindow, hDC);
60 }
61
62 void UpdatePalette(HBITMAP hBM){
63         int i,y;
64         static unsigned int c=0;
65
66         for(i=0;i<W_WIDTH;i++){
67                 for(y=0;y<=W_HEIGHT-1;y++)
68                         dibits[y*320+i] = c % 256;
69
70                 if (c > 512)
71                         c = 0;
72                 else
73                         c++; // It's operation of incrementing of c variable, not reference of a cool OO language :-)
74         }
75         
76         DoBlt(hBM);
77 }
78
79 void InitBitmap(HANDLE *hBM){
80         HPALETTE PalHan;
81         HWND ActiveWindow;
82         HDC hDC;
83         RGBQUAD palette[256];
84         int i;
85         BITMAPINFO256 bmInf;
86         LOGPALETTE256 palInf;
87
88         ActiveWindow = GetActiveWindow();
89         hDC = GetDC(ActiveWindow);
90
91         bmInf.bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
92         bmInf.bmiHeader.biWidth = W_WIDTH;
93         bmInf.bmiHeader.biHeight = -abs(W_HEIGHT);
94         bmInf.bmiHeader.biPlanes = 1;
95         bmInf.bmiHeader.biBitCount = 8;
96         bmInf.bmiHeader.biCompression = BI_RGB;
97         bmInf.bmiHeader.biSizeImage = 0;
98         bmInf.bmiHeader.biXPelsPerMeter = 0;
99         bmInf.bmiHeader.biYPelsPerMeter = 0;
100         bmInf.bmiHeader.biClrUsed = 256;
101         bmInf.bmiHeader.biClrImportant = 256;
102
103         GeneratePalette(palette);
104
105         for(i=0;i<256;i++)
106                 bmInf.bmiColors[i] = palette[i];
107
108         palInf.palVersion = 0x300;
109         palInf.palNumEntries = 256;
110         for(i=0;i<256;i++){
111                 palInf.palPalEntry[i].peRed = palette[i].rgbRed;
112                 palInf.palPalEntry[i].peGreen = palette[i].rgbGreen;
113                 palInf.palPalEntry[i].peBlue = palette[i].rgbBlue;
114                 palInf.palPalEntry[i].peFlags = PC_NOCOLLAPSE;
115         }
116
117         // Create palette
118         PalHan = CreatePalette((LOGPALETTE*)&palInf);
119         
120         // Select it into hDC
121         SelectPalette(hDC,PalHan,FALSE);
122         
123         // Realize palette in hDC
124         RealizePalette(hDC);
125         
126         // Delete handle to palette
127         DeleteObject(PalHan);
128
129         // Create dib section
130         *hBM = CreateDIBSection(hDC,(BITMAPINFO*)&bmInf,
131                 DIB_RGB_COLORS,(void**)&dibits,0,0);
132
133         // Release dc
134         ReleaseDC(ActiveWindow,hDC);
135 }
136
137 LRESULT CALLBACK WndProc(HWND hWnd,UINT msg, WPARAM wParam,LPARAM lParam)
138 {
139         switch(msg){
140                 case WM_DESTROY:
141                         PostQuitMessage(0);
142                         return 0;
143                 default:
144                         return DefWindowProc(hWnd,msg,wParam,lParam);
145         }
146 }
147
148
149
150 int WINAPI WinMain(HINSTANCE hInstance,HINSTANCE hPrevInstance, LPSTR lpszCmdParam,int nCmdShow)
151 {
152         WNDCLASS WndClass;
153         HWND hWnd;
154         MSG msg;
155         char szName[] = "Palette BitBlt test";
156         BOOL exit = FALSE;
157         HBITMAP hBM;
158
159         // Create and register window class (not modified!!!!!!!!!!!1)
160         WndClass.style = CS_HREDRAW|CS_VREDRAW|CS_OWNDC;
161         WndClass.lpfnWndProc = WndProc;
162         WndClass.cbClsExtra = 0;
163         WndClass.cbWndExtra = 0;
164         WndClass.hbrBackground = NULL;//GetStockObject(BLACK_BRUSH);
165         WndClass.hIcon = NULL;//LoadIcon(hInstance,NULL);
166         WndClass.hCursor = NULL;//LoadCursor(NULL,IDC_ARROW);
167         WndClass.hInstance = hInstance;
168         WndClass.lpszClassName = szName;
169         WndClass.lpszMenuName = 0;
170
171         RegisterClass(&WndClass);
172
173         // Create and show window (change styles !!!!!!!!)
174         hWnd = CreateWindow(szName, "ReactOS palette bitblt test",
175                 WS_CAPTION|WS_MINIMIZEBOX|WS_SYSMENU,
176                 CW_USEDEFAULT,CW_USEDEFAULT,W_WIDTH,W_HEIGHT,
177                 0,0,hInstance,0);
178         ShowWindow(hWnd,nCmdShow);
179
180         // Prepare bitmap to be bitblt
181         InitBitmap(&hBM);       
182
183         // Main message loop
184         while (!exit)
185         {
186                 UpdatePalette(hBM);
187                 Sleep(200);
188                 
189                 if(PeekMessage(&msg,0,0,0,PM_NOREMOVE) == TRUE)
190                 {
191                         if (!GetMessage(&msg,0,0,0))
192                                 exit = TRUE;
193
194                         TranslateMessage(&msg);
195                         DispatchMessage(&msg);
196                 }
197         }
198
199         return msg.wParam;
200 }