]> git.saurik.com Git - wxWidgets.git/blame - utils/glcanvas/samples/isosurf/isosurf.cpp
Added missing files to filelist.txt and regenerated makefiles.
[wxWidgets.git] / utils / glcanvas / samples / isosurf / isosurf.cpp
CommitLineData
c2265822
JS
1/////////////////////////////////////////////////////////////////////////////
2// Name: isosurf.cpp
3// Purpose: wxGLCanvas demo program
4// Author: Brian Paul (original gltk version), Wolfram Gloger
5// Modified by: Julian Smart
6// Created: 04/01/98
7// RCS-ID: $Id$
8// Copyright: (c) Julian Smart
9// Licence: wxWindows licence
10/////////////////////////////////////////////////////////////////////////////
11
12#ifdef __GNUG__
13#pragma implementation
14#pragma interface
15#endif
16
17// For compilers that support precompilation, includes "wx.h".
18#include "wx/wxprec.h"
19
20#ifdef __BORLANDC__
21#pragma hdrstop
22#endif
23
24#ifndef WX_PRECOMP
25#include "wx/wx.h"
26#endif
27
28#include "wx/timer.h"
29#include "glcanvas.h"
30
31#include <GL/gl.h>
32#include <GL/glu.h>
33
34#include "isosurf.h"
35
36// The following part is taken largely unchanged from the original C Version
37
38#include <math.h>
39
40GLboolean speed_test = GL_FALSE;
41GLboolean use_vertex_arrays = GL_FALSE;
42
43GLboolean doubleBuffer = GL_TRUE;
44
45GLboolean smooth = GL_TRUE;
46GLboolean lighting = GL_TRUE;
47
48
49#define MAXVERTS 10000
50
51static GLfloat verts[MAXVERTS][3];
52static GLfloat norms[MAXVERTS][3];
53static GLint numverts;
54
55static GLfloat xrot;
56static GLfloat yrot;
57
58
59static void read_surface( char *filename )
60{
61 FILE *f;
62
63 f = fopen(filename,"r");
64 if (!f) {
65 wxString msg("Couldn't read ");
66 msg += filename;
67 wxMessageBox(msg);
68 return;
69 }
70
71 numverts = 0;
72 while (!feof(f) && numverts<MAXVERTS) {
73 fscanf( f, "%f %f %f %f %f %f",
74 &verts[numverts][0], &verts[numverts][1], &verts[numverts][2],
75 &norms[numverts][0], &norms[numverts][1], &norms[numverts][2] );
76 numverts++;
77 }
78 numverts--;
79
80 printf("%d vertices, %d triangles\n", numverts, numverts-2);
81 fclose(f);
82}
83
84
85static void draw_surface( void )
86{
87 GLint i;
88
89#ifdef GL_EXT_vertex_array
90 if (use_vertex_arrays) {
91 glDrawArraysEXT( GL_TRIANGLE_STRIP, 0, numverts );
92 }
93 else {
94#endif
95 glBegin( GL_TRIANGLE_STRIP );
96 for (i=0;i<numverts;i++) {
97 glNormal3fv( norms[i] );
98 glVertex3fv( verts[i] );
99 }
100 glEnd();
101#ifdef GL_EXT_vertex_array
102 }
103#endif
104}
105
106
107static void draw1(void)
108{
109 glClear( GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT );
110 glPushMatrix();
111 glRotatef( yrot, 0.0, 1.0, 0.0 );
112 glRotatef( xrot, 1.0, 0.0, 0.0 );
113
114 draw_surface();
115
116 glPopMatrix();
117
118 glFlush();
119}
120
121
122static void InitMaterials(void)
123{
124 static float ambient[] = {0.1, 0.1, 0.1, 1.0};
125 static float diffuse[] = {0.5, 1.0, 1.0, 1.0};
126 static float position0[] = {0.0, 0.0, 20.0, 0.0};
127 static float position1[] = {0.0, 0.0, -20.0, 0.0};
128 static float front_mat_shininess[] = {60.0};
129 static float front_mat_specular[] = {0.2, 0.2, 0.2, 1.0};
130 static float front_mat_diffuse[] = {0.5, 0.28, 0.38, 1.0};
131 /*
132 static float back_mat_shininess[] = {60.0};
133 static float back_mat_specular[] = {0.5, 0.5, 0.2, 1.0};
134 static float back_mat_diffuse[] = {1.0, 1.0, 0.2, 1.0};
135 */
136 static float lmodel_ambient[] = {1.0, 1.0, 1.0, 1.0};
137 static float lmodel_twoside[] = {GL_FALSE};
138
139 glLightfv(GL_LIGHT0, GL_AMBIENT, ambient);
140 glLightfv(GL_LIGHT0, GL_DIFFUSE, diffuse);
141 glLightfv(GL_LIGHT0, GL_POSITION, position0);
142 glEnable(GL_LIGHT0);
143
144 glLightfv(GL_LIGHT1, GL_AMBIENT, ambient);
145 glLightfv(GL_LIGHT1, GL_DIFFUSE, diffuse);
146 glLightfv(GL_LIGHT1, GL_POSITION, position1);
147 glEnable(GL_LIGHT1);
148
149 glLightModelfv(GL_LIGHT_MODEL_AMBIENT, lmodel_ambient);
150 glLightModelfv(GL_LIGHT_MODEL_TWO_SIDE, lmodel_twoside);
151 glEnable(GL_LIGHTING);
152
153 glMaterialfv(GL_FRONT_AND_BACK, GL_SHININESS, front_mat_shininess);
154 glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, front_mat_specular);
155 glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, front_mat_diffuse);
156}
157
158
159static void Init(void)
160{
161 glClearColor(0.0, 0.0, 0.0, 0.0);
162
163 glShadeModel(GL_SMOOTH);
164 glEnable(GL_DEPTH_TEST);
165
166 InitMaterials();
167
168 glMatrixMode(GL_PROJECTION);
169 glLoadIdentity();
170 glFrustum( -1.0, 1.0, -1.0, 1.0, 5, 25 );
171
172 glMatrixMode(GL_MODELVIEW);
173 glLoadIdentity();
174 glTranslatef( 0.0, 0.0, -6.0 );
175
176#ifdef GL_EXT_vertex_array
177 if (use_vertex_arrays) {
178 glVertexPointerEXT( 3, GL_FLOAT, 0, numverts, verts );
179 glNormalPointerEXT( GL_FLOAT, 0, numverts, norms );
180 glEnable( GL_VERTEX_ARRAY_EXT );
181 glEnable( GL_NORMAL_ARRAY_EXT );
182 }
183#endif
184}
185
186
187static void Reshape(int width, int height)
188{
189 glViewport(0, 0, (GLint)width, (GLint)height);
190}
191
192
193static GLenum Args(int argc, char **argv)
194{
195 GLint i;
196
197 for (i = 1; i < argc; i++) {
198 if (strcmp(argv[i], "-sb") == 0) {
199 doubleBuffer = GL_FALSE;
200 }
201 else if (strcmp(argv[i], "-db") == 0) {
202 doubleBuffer = GL_TRUE;
203 }
204 else if (strcmp(argv[i], "-speed") == 0) {
205 speed_test = GL_TRUE;
206 doubleBuffer = GL_TRUE;
207 }
208 else if (strcmp(argv[i], "-va") == 0) {
209 use_vertex_arrays = GL_TRUE;
210 }
211 else {
212 wxString msg("Bad option: ");
213 msg += argv[i];
214 wxMessageBox(msg);
215 return GL_FALSE;
216 }
217 }
218
219 return GL_TRUE;
220}
221
222// The following part was written for wxWindows 1.66
223MyFrame *frame = NULL;
224
225IMPLEMENT_APP(MyApp)
226
227// `Main program' equivalent, creating windows and returning main app frame
228bool MyApp::OnInit(void)
229{
230 Args(argc, argv);
231
232 // Create the main frame window
233 frame = new MyFrame(NULL, "Isosurf GL Sample", wxPoint(50, 50), wxSize(200, 200));
234
235 // Give it an icon
236 frame->SetIcon(wxIcon("mondrian"));
237
238 // Make a menubar
239 wxMenu *fileMenu = new wxMenu;
240
241 fileMenu->Append(wxID_EXIT, "E&xit");
242 wxMenuBar *menuBar = new wxMenuBar;
243 menuBar->Append(fileMenu, "&File");
244 frame->SetMenuBar(menuBar);
245
246 // Make a TestGLCanvas
247
248 // JACS
249#ifdef __WXMSW__
250 int *gl_attrib = NULL;
251#else
252 int gl_attrib[20] = { GLX_RGBA, GLX_RED_SIZE, 1, GLX_GREEN_SIZE, 1,
253 GLX_BLUE_SIZE, 1, GLX_DEPTH_SIZE, 1,
254 GLX_DOUBLEBUFFER, None };
255#endif
256
5e1962f7 257 if(!doubleBuffer)
c2265822
JS
258 {
259 printf("don't have double buffer, disabling\n");
9838df2c 260#ifdef __WXGTK__
c2265822
JS
261 gl_attrib[9] = None;
262#endif
263 doubleBuffer = GL_FALSE;
264 }
265 frame->m_canvas = new TestGLCanvas(frame, -1, wxPoint(0, 0), wxSize(200, 200), 0, "TestGLCanvas",
266 gl_attrib);
267
268 // Show the frame
269 frame->Show(TRUE);
270
271 frame->m_canvas->SetCurrent();
272 read_surface( "isosurf.dat" );
273
274 Init();
275
276 return TRUE;
277}
278
279BEGIN_EVENT_TABLE(MyFrame, wxFrame)
280 EVT_MENU(wxID_EXIT, MyFrame::OnExit)
281END_EVENT_TABLE()
282
283// My frame constructor
284MyFrame::MyFrame(wxFrame *frame, const wxString& title, const wxPoint& pos,
285 const wxSize& size, long style):
286 wxFrame(frame, -1, title, pos, size, style)
287{
288 m_canvas = NULL;
289}
290
291// Intercept menu commands
292void MyFrame::OnExit(wxCommandEvent& event)
293{
294 Destroy();
295}
296
c2265822
JS
297/*
298 * TestGLCanvas implementation
299 */
300
301BEGIN_EVENT_TABLE(TestGLCanvas, wxGLCanvas)
302 EVT_SIZE(TestGLCanvas::OnSize)
303 EVT_PAINT(TestGLCanvas::OnPaint)
304 EVT_CHAR(TestGLCanvas::OnChar)
305 EVT_MOUSE_EVENTS(TestGLCanvas::OnMouseEvent)
306 EVT_ERASE_BACKGROUND(TestGLCanvas::OnEraseBackground)
307END_EVENT_TABLE()
308
309TestGLCanvas::TestGLCanvas(wxWindow *parent, wxWindowID id,
310 const wxPoint& pos, const wxSize& size, long style, const wxString& name, int* gl_attrib):
311 wxGLCanvas(parent, id, pos, size, style, name, gl_attrib)
312{
313 parent->Show(TRUE);
314 SetCurrent();
315 /* Make sure server supports the vertex array extension */
316 char* extensions = (char *) glGetString( GL_EXTENSIONS );
317 if (!extensions || !strstr( extensions, "GL_EXT_vertex_array" )) {
318 use_vertex_arrays = GL_FALSE;
319 }
320}
321
322
323TestGLCanvas::~TestGLCanvas(void)
324{
325}
326
327void TestGLCanvas::OnPaint( wxPaintEvent& event )
328{
329 // This is a dummy, to avoid an endless succession of paint messages.
330 // OnPaint handlers must always create a wxPaintDC.
331 wxPaintDC dc(this);
332
333 draw1();
334 SwapBuffers();
335}
336
337void TestGLCanvas::OnSize(wxSizeEvent& event)
338{
339 SetCurrent();
340 int width, height;
341 GetClientSize(& width, & height);
342 Reshape(width, height);
343}
344
345void TestGLCanvas::OnChar(wxKeyEvent& event)
346{
347 switch(event.KeyCode()) {
348 case WXK_ESCAPE:
349 exit(0);
350 case WXK_LEFT:
351 yrot -= 15.0;
352 break;
353 case WXK_RIGHT:
354 yrot += 15.0;
355 break;
356 case WXK_UP:
357 xrot += 15.0;
358 break;
359 case WXK_DOWN:
360 xrot -= 15.0;
361 break;
362 case 's': case 'S':
363 smooth = !smooth;
364 if (smooth) {
365 glShadeModel(GL_SMOOTH);
366 } else {
367 glShadeModel(GL_FLAT);
368 }
369 break;
370 case 'l': case 'L':
371 lighting = !lighting;
372 if (lighting) {
373 glEnable(GL_LIGHTING);
374 } else {
375 glDisable(GL_LIGHTING);
376 }
377 break;
3cdda6cd
RR
378 default:
379 {
380 event.Skip();
381 return;
382 }
c2265822
JS
383 }
384
06ad8636 385 Refresh(FALSE);
c2265822
JS
386}
387
388void TestGLCanvas::OnMouseEvent(wxMouseEvent& event)
389{
390 static int dragging = 0;
391 static float last_x, last_y;
392
393 //printf("%f %f %d\n", event.GetX(), event.GetY(), (int)event.LeftIsDown());
394 if(event.LeftIsDown()) {
395 if(!dragging) {
396 dragging = 1;
397 } else {
398 yrot += (event.GetX() - last_x)*1.0;
399 xrot += (event.GetY() - last_y)*1.0;
06ad8636 400 Refresh(FALSE);
c2265822
JS
401 }
402 last_x = event.GetX();
403 last_y = event.GetY();
404 } else
405 dragging = 0;
406}
407
408void TestGLCanvas::OnEraseBackground(wxEraseEvent& event)
409{
410 // Do nothing, to avoid flashing.
411}
412