[CYLFRAC] Fix a MSVC-x64 warning about hwnd (#1158)
[reactos.git] / modules / rosapps / applications / screensavers / cylfrac / cylfrac.c
1 /*
2 * Copyright 2003 J Brown
3 * Copyright 2006 Andrey Korotaev <unC0Rr@inbox.ru>
4 *
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or
8 * (at your option) any later version.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 *
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Software
17 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
18 */
19
20 #include <windows.h>
21 #include <GL/gl.h>
22 #include <GL/glu.h>
23 #include <tchar.h>
24 #include <scrnsave.h>
25 #include "resource.h"
26
27 #define APPNAME _T("Cylfrac")
28 #define wfactor 0.9
29 #define rotfactor 1.5
30 #define FPS 100
31 #define timerdelay 1000/FPS
32
33 POINT initpoint;
34 HDC dc;
35 HGLRC hrc;
36 DWORD oldticks;
37 MMRESULT TimerID;
38
39 DWORD lvls = 7;
40 int cylquality = 8;
41
42 HINSTANCE hInstance;
43
44 GLUquadricObj * cylinder;
45
46 float angle = 0;
47 float colorh = 0.0;
48 float rval, gval, bval;
49
50 BOOL fullscreen = FALSE;
51
52 float _RGB(float H, float M1, float M2)
53 {
54 if(H < 0.0) H += 360.0;
55 else if(H > 360.0) H -= 360.0;
56 if(H < 60) return M1 + (M2 - M1) * H / 60.0;
57 if((H >= 60 )&&(H < 180)) return M2;
58 if((H >= 180)&&(H < 240)) return M1 + (M2 - M1)*(240 - H) / 60.0;
59 return M1;
60 }
61
62 void HLStoRGB(float H, float L, float S,
63 float* R, float* G, float* B)
64 {
65 float M1, M2;
66 if(S <= 0.5) M2 = S * (1 + L);
67 else M2 = S * (1 - L) + L;
68 M1 = 2 * S - M2;
69 if (L == 0.0)
70 {
71 *R = S;
72 *G = S;
73 *B = S;
74 } else {
75 *R = _RGB(H + 120.0, M1, M2);
76 *G = _RGB(H , M1, M2);
77 *B = _RGB(H - 120.0, M1, M2);
78 }
79 }
80
81 void DrawCylinder(int n, float rota, float width)
82 {
83 glPushMatrix();
84 glColor3f(rval/n, gval/n, bval/n);
85 glRotatef(rota, 0.0, 1.0, 0.0);
86 gluCylinder(cylinder, width, width * wfactor, n * 0.5, cylquality, 1);
87 glTranslatef(0.0, 0.0, -n * 0.5);
88 gluCylinder(cylinder, width * wfactor, width, n * 0.5, cylquality, 1);
89 if(n > 1)
90 {
91 float r = rota * rotfactor;
92 glRotatef(90.0, 1.0, 0.0, 0.0);
93 DrawCylinder(n - 1, r, width * wfactor);
94 glTranslatef(0.0, n, 0.0);
95 DrawCylinder(n - 1, -r, width * wfactor);
96 }
97 glPopMatrix();
98 }
99
100 void DrawScene(HWND hwnd, HDC dc, int ticks)
101 {
102 PAINTSTRUCT ps;
103 dc = BeginPaint(hwnd, &ps);
104 glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
105 glRotatef(ticks * 0.01, 0.0, 1.0, -0.5);
106 angle += ticks * 0.01;
107 colorh += ticks * 0.003;
108 if (colorh > 360.0) colorh -= 360.0;
109 HLStoRGB(colorh, 1.0, 0.7, &rval, &gval, &bval);
110 DrawCylinder(lvls, angle, 0.2);
111 SwapBuffers(dc);
112 EndPaint(hwnd, &ps);
113 }
114
115 void CALLBACK TimeProc(UINT uID, UINT uMsg, DWORD dwUser, DWORD dw1, DWORD dw2)
116 {
117 InvalidateRect((HWND)dwUser, NULL, 0);
118 }
119
120 void MyPixelFormat(HDC dc)
121 {
122 int npf;
123 PIXELFORMATDESCRIPTOR pfd;
124
125 ZeroMemory(&pfd, sizeof(pfd));
126 pfd.nSize = sizeof(pfd);
127 pfd.nVersion = 1;
128 pfd.dwFlags = PFD_DOUBLEBUFFER | PFD_SUPPORT_OPENGL | PFD_DRAW_TO_WINDOW;
129
130 npf = ChoosePixelFormat(dc, &pfd);
131 if(npf != 0)
132 SetPixelFormat(dc, npf, &pfd);
133 }
134
135 void InitGL(HWND hwnd)
136 {
137 GLfloat lightpos[4] = {2.0, 2.0, -2.0, 0.7};
138 GLfloat ca = 1.0;
139 dc = GetDC(hwnd);
140 MyPixelFormat(dc);
141 hrc = wglCreateContext(dc);
142 wglMakeCurrent(dc, hrc);
143 cylinder = gluNewQuadric();
144 glEnable(GL_DEPTH_TEST);
145 glEnable(GL_LIGHT0);
146 glLightfv(GL_LIGHT0, GL_POSITION, (GLfloat *)&lightpos);
147 glLightfv(GL_LIGHT0, GL_LINEAR_ATTENUATION, &ca);
148 glEnable(GL_LIGHTING);
149 glEnable(GL_COLOR_MATERIAL);
150 }
151
152 LRESULT WINAPI ScreenSaverProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
153 {
154 switch(msg) {
155 case WM_CREATE:
156 {
157 GetCursorPos(&initpoint);
158 InitGL(hwnd);
159 oldticks = GetTickCount();
160 TimerID = timeSetEvent(timerdelay, 0, TimeProc, (DWORD_PTR)hwnd, TIME_PERIODIC);
161 }
162 break;
163 case WM_PAINT:
164 {
165 DWORD ticks = oldticks;
166 POINT currpoint;
167 oldticks = GetTickCount();
168 DrawScene(hwnd, dc, oldticks - ticks);
169 if(fullscreen)
170 {
171 GetCursorPos(&currpoint);
172 if(abs(currpoint.x - initpoint.x) + (abs(currpoint.y - initpoint.y)) > 10)
173 PostMessage(hwnd, WM_CLOSE, 0, 0);
174 }
175 }
176 break;
177 case WM_DESTROY:
178 {
179 timeKillEvent(TimerID);
180 gluDeleteQuadric(cylinder);
181 wglMakeCurrent(0, 0);
182 wglDeleteContext(hrc);
183 ReleaseDC(hwnd, dc);
184 DeleteDC(dc);
185 if (fullscreen)
186 ShowCursor(TRUE);
187 PostQuitMessage(0);
188 }
189 break;
190 case WM_SIZE:
191 {
192 int width = LOWORD(lParam);
193 int height = HIWORD(lParam);
194 float fscale;
195 glViewport(0, 0, width, height);
196 glMatrixMode(GL_MODELVIEW);
197 glLoadIdentity();
198 fscale = 0.8/(float)lvls;
199 glScalef(fscale, fscale, fscale);
200 }
201 break;
202 default:
203 return DefScreenSaverProc(hwnd, msg, wParam, lParam);
204 }
205 return 0;
206 }
207
208 BOOL WINAPI ScreenSaverConfigureDialog(HWND hWnd, UINT message, WPARAM wparam, LPARAM lparam)
209 {
210 return FALSE;
211 }
212
213 BOOL WINAPI RegisterDialogClasses(HANDLE hmodule)
214 {
215 TCHAR szTitle[256];
216 TCHAR szText[256];
217
218 LoadString(hmodule,
219 IDS_TITLE,
220 szTitle,
221 256);
222
223 LoadString(hmodule,
224 IDS_TEXT,
225 szText,
226 256);
227
228 MessageBox(0,
229 szText,
230 szTitle,
231 MB_OK | MB_ICONWARNING);
232 return FALSE;
233 }