glut_template.cpp
5.33 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
/* Don't change this file. Make a copy in your project and change parameters as necessary.
In order to use this template, specify the following signature in your main.cpp file:
void glut_init(int argc, char* argv[]);
*/
#ifndef GLUT_TEMPLATE_H
#define GLUT_TEMPLATE_H
#include <stim/visualization/camera.h>
#include <GL/glut.h>
void render_scene();
void draw_colorcube() {
glBegin(GL_LINES); //start a line series
glColor3f(0, 0, 0);
glVertex3f(-0.5, -0.5, -0.5);
glColor3f(1, 0, 0);
glVertex3f(0.5, -0.5, -0.5);
glColor3f(0, 0, 0);
glVertex3f(-0.5, -0.5, -0.5);
glColor3f(0, 1, 0);
glVertex3f(-0.5, 0.5, -0.5);
glColor3f(0, 0, 0);
glVertex3f(-0.5, -0.5, -0.5);
glColor3f(0, 0, 1);
glVertex3f(-0.5, -0.5, 0.5);
glColor3f(1, 1, 1);
glVertex3f(0.5, 0.5, 0.5);
glColor3f(1, 1, 0);
glVertex3f(0.5, 0.5, -0.5);
glColor3f(1, 1, 1);
glVertex3f(0.5, 0.5, 0.5);
glColor3f(1, 0, 1);
glVertex3f(0.5, -0.5, 0.5);
glColor3f(1, 1, 1);
glVertex3f(0.5, 0.5, 0.5);
glColor3f(0, 1, 1);
glVertex3f(-0.5, 0.5, 0.5);
glColor3f(1, 0, 0);
glVertex3f(0.5, -0.5, -0.5);
glColor3f(1, 1, 0);
glVertex3f(0.5, 0.5, -0.5);
glColor3f(1, 0, 0);
glVertex3f(0.5, -0.5, -0.5);
glColor3f(1, 0, 1);
glVertex3f(0.5, -0.5, 0.5);
glColor3f(0, 1, 0);
glVertex3f(-0.5, 0.5, -0.5);
glColor3f(1, 1, 0);
glVertex3f(0.5, 0.5, -0.5);
glColor3f(0, 1, 0);
glVertex3f(-0.5, 0.5, -0.5);
glColor3f(0, 1, 1);
glVertex3f(-0.5, 0.5, 0.5);
glColor3f(0, 0, 1);
glVertex3f(-0.5, -0.5, 0.5);
glColor3f(1, 0, 1);
glVertex3f(0.5, -0.5, 0.5);
glColor3f(0, 0, 1);
glVertex3f(-0.5, -0.5, 0.5);
glColor3f(0, 1, 1);
glVertex3f(-0.5, 0.5, 0.5);
glEnd();
}}
struct glut_template_struct {
float theta_scale = 0.01f;
float phi_scale = 0.01f;
float zoom_scale = 0.1f;
stim::camera cam; //create a camera object
int mx, my; //mouse coordinates in the window space
float d = 1.5; //initial distance between the camera and the sphere
bool rotate_zoom = true; //sets the current camera mode (rotation = true, zoom = false)
bool axis = false; //render the z-axis (set via a command line flag)
} gt;
//render the XYZ axes
void render_axes() {
glDisable(GL_TEXTURE_2D); //turn off texture mapping
glBegin(GL_LINES);
glColor3f(1.0f, 0.0f, 0.0f); //set the color to RED and render X
glVertex3f(0.0, 0.0, 0.0);
glVertex3f(100.0, 0.0, 0.0);
glColor3f(0.0f, 1.0f, 0.0f); //set the color to RED and render X
glVertex3f(0.0, 0.0, 0.0);
glVertex3f(0.0, 100.0, 0.0);
glColor3f(0.0f, 0.0f, 1.0f); //set the color to RED and render X
glVertex3f(0.0, 0.0, 0.0);
glVertex3f(0.0, 0.0, 100.0);
glEnd();
}
//display function executed to update every frame
void glut_display() {
glClear(GL_DEPTH_BUFFER_BIT | GL_COLOR_BUFFER_BIT); //clear the screen
glMatrixMode(GL_PROJECTION); //put the projection matrix on the stack
glLoadIdentity(); //set it to the identity matrix
gluPerspective(gt.cam.getFOV(), 1, 0.001, 1000000); //set up a perspective projection
glMatrixMode(GL_MODELVIEW); //load the model view matrix to the stack
glLoadIdentity(); //set it to the identity matrix
stim::vec3<float> p = gt.cam.getPosition(); //get the camera parameters
stim::vec3<float> u = gt.cam.getUp();
stim::vec3<float> c = gt.cam.getLookAt();
gluLookAt(p[0], p[1], p[2], c[0], c[1], c[2], u[0], u[1], u[2]); //specify the camera parameters to OpenGL
render_axes(); //render the axes if the user requests them
draw_colorcube();
glutSwapBuffers(); //swap in the back buffer (double-buffering is used to prevent tearing)
}
//process mouse press events
void glut_mouse_press(int button, int state, int x, int y) {
if (button == GLUT_LEFT_BUTTON) //set the camera motion mode based on the mouse button pressed
gt.rotate_zoom = true;
else if (button == GLUT_RIGHT_BUTTON)
gt.rotate_zoom = false;
if (state == GLUT_DOWN) { //if the mouse is pressed
gt.mx = x; gt.my = y; //set the current mouse position
}
}
//process mouse drags to update the camera
void glut_mouse_drag(int x, int y) {
if (gt.rotate_zoom == true) { //if the camera is in rotation mode, rotate
float theta = gt.theta_scale * (gt.mx - x);
float phi = -gt.phi_scale * (gt.my - y);
gt.cam.OrbitFocus(theta, phi); //if the mouse is dragged
}
else { //otherwize zoom
gt.cam.Push(gt.zoom_scale*(gt.my - y));
}
gt.mx = x; gt.my = y; //update the mouse position
glutPostRedisplay();
}
void glut_init(int argc, char* argv[]) {
glutInit(&argc, argv); //initialize GLUT
glutInitWindowSize(500, 500); //set the size of the GLUT window
glutInitDisplayMode(GLUT_DEPTH | GLUT_RGBA | GLUT_DOUBLE);
glutCreateWindow("3D Tensor Visualization"); //create the GLUT window (and an OpenGL context)
glutDisplayFunc(glut_display); //set the display function (which will be called repeatedly by glutMainLoop)
glutMouseFunc(glut_mouse_press); //set the mouse press function (called when a mouse button is pressed)
glutMotionFunc(glut_mouse_drag); //set the mouse motion function (which will be called any time the mouse is dragged)
glClearColor(0.0f, 0.0f, 0.0f, 1.0f); //set the clear color to white
gt.cam.setPosition(gt.d, gt.d, gt.d); //initialize the camera
gt.cam.LookAt(0, 0, 0, 0, 1, 1);
gt.cam.setFOV(40);
glutMainLoop(); //enter the main loop
}
#endif