rayzor

view src/modeller.cc @ 22:5380ff64e83f

minor changes from dos, and line endings cleanup
author John Tsiombikas <nuclear@member.fsf.org>
date Fri, 02 May 2014 14:32:58 +0300
parents 79609d482762
children
line source
1 #include <stdio.h>
2 #include <string.h>
3 #include <assert.h>
4 #include "modeller.h"
5 #include "min3d.h"
6 #include "rayzor.h"
7 #include "scene.h"
8 #include "keyb.h"
9 #include "scrman.h"
10 #include "logger.h"
11 #include "timer.h"
13 struct ModellerImpl {
14 int mx, my;
15 float cam_theta, cam_phi, cam_dist, cam_fov;
16 Camera *viewport_cam;
18 struct m3d_image rbuf;
20 bool bnstate[8];
21 int prev_x, prev_y;
23 float orig_theta;
24 bool screensaver;
25 };
27 static void draw_grid(float size, float spacing);
29 Modeller::Modeller()
30 {
31 set_name("modeller");
32 }
34 Modeller::~Modeller()
35 {
36 shutdown();
37 }
39 bool Modeller::init()
40 {
41 mod = new ModellerImpl;
42 memset(mod, 0, sizeof *mod);
44 mod->viewport_cam = new Camera;
46 mod->cam_phi = 25;
47 mod->cam_dist = 5;
48 mod->cam_fov = 50.0;
50 m3d_init();
51 mod->rbuf.pixels = fb_pixels;
52 mod->rbuf.xsz = fb_width;
53 mod->rbuf.ysz = fb_height;
54 m3d_set_buffers(&mod->rbuf, 0);
56 m3d_matrix_mode(M3D_PROJECTION);
57 m3d_load_identity();
58 m3d_perspective(mod->cam_fov, (float)fb_width / (float)fb_height, 0.5, 500.0);
60 m3d_enable(M3D_CULL_FACE);
61 return true;
62 }
64 void Modeller::shutdown()
65 {
66 if(mod) {
67 m3d_shutdown();
69 delete mod;
70 mod = 0;
71 }
72 }
74 void Modeller::draw() const
75 {
76 if(mod->screensaver) {
77 mod->cam_theta = get_msec() / 100.0f;
78 }
80 m3d_clear(M3D_COLOR_BUFFER_BIT);
82 m3d_matrix_mode(M3D_MODELVIEW);
83 m3d_load_identity();
84 m3d_translate(0, 0, -mod->cam_dist);
85 m3d_rotate(mod->cam_phi, 1, 0, 0);
86 m3d_rotate(mod->cam_theta, 0, 1, 0);
88 draw_grid(10.0, 1.0);
90 scene->draw();
91 }
94 static void draw_grid(float size, float spacing)
95 {
96 int num_lines = size / spacing;
97 float dist = size / 2.0;
99 m3d_disable(M3D_LIGHTING);
101 m3d_begin(M3D_LINES);
102 m3d_color(0.4, 0.4, 0.4);
104 float x = -dist;
105 for(int i=0; i<=num_lines; i++) {
106 if(i != num_lines / 2) {
107 m3d_vertex(-dist, 0, x);
108 m3d_vertex(dist, 0, x);
109 m3d_vertex(x, 0, -dist);
110 m3d_vertex(x, 0, dist);
111 }
112 x += spacing;
113 }
114 m3d_end();
116 m3d_begin(M3D_LINES);
117 m3d_color(0.8, 0, 0);
118 m3d_vertex(-dist, 0, 0);
119 m3d_vertex(dist, 0, 0);
120 m3d_color(0.1, 0.3, 0.8);
121 m3d_vertex(0, 0, -dist);
122 m3d_vertex(0, 0, dist);
123 m3d_end();
124 }
127 void Modeller::handle_keyboard(int key, bool press)
128 {
129 if(press) {
130 switch(key) {
131 case 'q':
132 quit_app();
133 break;
135 case 27:
136 scene->clear_selection();
137 break;
139 case '\t':
140 {
141 int s = scene->get_selection();
142 if(s >= 0) {
143 s = (s + 1) % scene->get_node_count();
144 scene->clear_selection();
145 } else {
146 s = 0;
147 }
148 scene->select(s);
149 }
150 break;
152 case 'r':
153 case 'p':
154 if(kb_isdown(KB_ALT) || kb_isdown(KB_CTRL)) {
155 case KB_F5:
156 case KB_F6:
157 Screen *rs = get_screen("renderer");
158 if(rs) {
159 activate_screen(rs);
161 if(key == 'r' || key == KB_F5) {
162 // start a rendering, and make sure there is a camera
163 if(!scene->get_active_camera()) {
164 scene->set_active_camera(mod->viewport_cam);
165 }
166 Vector3 dir;
167 float theta = -DEG2RAD(mod->cam_theta);
168 float phi = DEG2RAD(mod->cam_phi);
169 dir.x = sin(theta) * cos(phi) * mod->cam_dist;
170 dir.y = sin(phi) * mod->cam_dist;
171 dir.z = cos(theta) * cos(phi) * mod->cam_dist;
172 mod->viewport_cam->set_position(dir);
173 mod->viewport_cam->set_target(Vector3(0, 0, 0));
174 mod->viewport_cam->set_fov(DEG2RAD(mod->cam_fov));
176 rs->message(message_atom("start"));
177 }
178 } else {
179 printlog("failed to find renderer screen!\n");
180 }
181 }
182 break;
184 case KB_F1:
185 mod->screensaver = !mod->screensaver;
186 if(mod->screensaver) {
187 mod->orig_theta = mod->cam_theta;
188 } else {
189 mod->cam_theta = mod->orig_theta;
190 }
191 break;
193 default:
194 break;
195 }
196 }
197 }
199 void Modeller::handle_mbutton(int bn, bool press, int x, int y)
200 {
201 mod->bnstate[bn] = press;
202 mod->prev_x = x;
203 mod->prev_y = y;
204 }
206 void Modeller::handle_mmotion(int x, int y)
207 {
208 int dx = x - mod->prev_x;
209 int dy = y - mod->prev_y;
210 mod->prev_x = x;
211 mod->prev_y = y;
213 if(kb_isdown(KB_ALT) || kb_isdown(KB_CTRL)) {
214 if(mod->bnstate[0]) {
215 mod->cam_theta += dx * 0.5;
216 mod->cam_phi += dy * 0.5;
218 if(mod->cam_phi < -90) mod->cam_phi = -90;
219 if(mod->cam_phi > 90) mod->cam_phi = 90;
220 }
221 if(mod->bnstate[1]) {
222 mod->cam_dist += dy * 0.1;
223 if(mod->cam_dist < 0) mod->cam_dist = 0;
224 }
225 }
226 }