glviewvol

annotate src/dicomview.cc @ 6:f22be47a3572

moved to TransferFuncs completely
author John Tsiombikas <nuclear@member.fsf.org>
date Tue, 30 Dec 2014 06:22:54 +0200
parents 04330eb80b36
children fb6d93471352
rev   line source
nuclear@3 1 #include <stdio.h>
nuclear@4 2 #include <stdlib.h>
nuclear@0 3 #include "opengl.h"
nuclear@0 4 #include "dicomview.h"
nuclear@1 5 #include "rend_fast.h"
nuclear@3 6 #include "opt.h"
nuclear@3 7 #include "volume.h"
nuclear@4 8 #include "xfer_view.h"
nuclear@0 9
nuclear@1 10 static int win_width, win_height;
nuclear@0 11 static float cam_theta, cam_phi, cam_dist = 6;
nuclear@4 12 static int splitter_y = -1;
nuclear@4 13
nuclear@4 14 #define SPLITTER_WIDTH 5
nuclear@0 15
nuclear@1 16 static Renderer *rend;
nuclear@3 17 static Volume *vol;
nuclear@6 18 static TransferFunc *xfer;
nuclear@1 19
nuclear@0 20 extern "C" {
nuclear@0 21
nuclear@0 22 int init()
nuclear@0 23 {
nuclear@3 24 if(!opt.fname) {
nuclear@3 25 fprintf(stderr, "you must specify the volume data filename\n");
nuclear@1 26 return -1;
nuclear@1 27 }
nuclear@1 28
nuclear@3 29 switch(opt.rend_type) {
nuclear@3 30 case REND_FAST:
nuclear@3 31 rend = new RendererFast;
nuclear@3 32 break;
nuclear@3 33 default:
nuclear@3 34 return -1;
nuclear@3 35 }
nuclear@3 36
nuclear@3 37 if(!rend->init()) {
nuclear@3 38 fprintf(stderr, "renderer initialization failed\n");
nuclear@3 39 return -1;
nuclear@3 40 }
nuclear@3 41
nuclear@3 42 VoxelVolume *voxvol = new VoxelVolume;
nuclear@3 43 if(!voxvol->load(opt.fname)) {
nuclear@3 44 fprintf(stderr, "failed to load volume data from: %s\n", opt.fname);
nuclear@3 45 return -1;
nuclear@3 46 }
nuclear@3 47 vol = voxvol;
nuclear@3 48 rend->set_volume(vol);
nuclear@3 49
nuclear@6 50 xfer = new TransferWindow;
nuclear@6 51 rend->set_transfer_function(xfer);
nuclear@6 52
nuclear@6 53 if(!xfview_init(xfer)) {
nuclear@4 54 return -1;
nuclear@4 55 }
nuclear@4 56
nuclear@1 57 return 0;
nuclear@0 58 }
nuclear@0 59
nuclear@0 60 void cleanup()
nuclear@0 61 {
nuclear@4 62 xfview_destroy();
nuclear@4 63
nuclear@1 64 rend->destroy();
nuclear@1 65 delete rend;
nuclear@3 66 delete vol;
nuclear@6 67 delete xfer;
nuclear@0 68 }
nuclear@0 69
nuclear@0 70 void ev_display()
nuclear@0 71 {
nuclear@0 72 glClear(GL_COLOR_BUFFER_BIT);
nuclear@1 73
nuclear@4 74 // render the main view
nuclear@4 75 glViewport(0, win_height - splitter_y, win_width, splitter_y);
nuclear@4 76
nuclear@4 77 glMatrixMode(GL_PROJECTION);
nuclear@4 78 glLoadIdentity();
nuclear@4 79 gluPerspective(50.0, (float)win_width / (float)splitter_y, 0.1, 100.0);
nuclear@4 80
nuclear@4 81 glMatrixMode(GL_MODELVIEW);
nuclear@4 82 glLoadIdentity();
nuclear@4 83 glTranslatef(0, 0, -cam_dist);
nuclear@4 84 glRotatef(cam_phi, 1, 0, 0);
nuclear@4 85 glRotatef(cam_theta, 0, 1, 0);
nuclear@4 86
nuclear@1 87 rend->update(0);
nuclear@1 88 rend->render();
nuclear@4 89
nuclear@4 90 // draw the transfer function view
nuclear@4 91 glViewport(0, 0, win_width, win_height - splitter_y);
nuclear@4 92
nuclear@4 93 xfview_draw();
nuclear@4 94
nuclear@4 95 // draw the GUI
nuclear@4 96 glViewport(0, 0, win_width, win_height);
nuclear@4 97
nuclear@4 98 glMatrixMode(GL_PROJECTION);
nuclear@4 99 glLoadIdentity();
nuclear@4 100 glOrtho(0, win_width, win_height, 0, -1, 1);
nuclear@4 101
nuclear@4 102 glMatrixMode(GL_MODELVIEW);
nuclear@4 103 glLoadIdentity();
nuclear@4 104
nuclear@4 105 glBegin(GL_QUADS);
nuclear@4 106 glColor3f(1, 1, 1);
nuclear@4 107 glVertex2f(0, splitter_y + SPLITTER_WIDTH / 2);
nuclear@4 108 glVertex2f(win_width, splitter_y + SPLITTER_WIDTH / 2);
nuclear@4 109 glVertex2f(win_width, splitter_y - SPLITTER_WIDTH / 2);
nuclear@4 110 glVertex2f(0, splitter_y - SPLITTER_WIDTH / 2);
nuclear@4 111 glEnd();
nuclear@4 112
nuclear@4 113 swap_buffers();
nuclear@0 114 }
nuclear@0 115
nuclear@0 116 void ev_reshape(int x, int y)
nuclear@0 117 {
nuclear@4 118 if(splitter_y < 0) { // not initialized yet
nuclear@4 119 splitter_y = (int)(y * 0.85);
nuclear@4 120 } else {
nuclear@4 121 // calculate where the splitter was relative to the window height
nuclear@4 122 // and based on that, it's new position
nuclear@4 123 float split = (float)splitter_y / (float)win_height;
nuclear@4 124 splitter_y = (int)(y * split);
nuclear@4 125 }
nuclear@4 126
nuclear@0 127 win_width = x;
nuclear@0 128 win_height = y;
nuclear@0 129
nuclear@1 130 glViewport(0, 0, x, y);
nuclear@4 131 if(rend) {
nuclear@4 132 rend->reshape(x, y);
nuclear@4 133 }
nuclear@0 134 }
nuclear@0 135
nuclear@1 136 void ev_keyboard(int key, int press, int x, int y)
nuclear@1 137 {
nuclear@1 138 if(press) {
nuclear@1 139 switch(key) {
nuclear@1 140 case 27:
nuclear@1 141 quit();
nuclear@1 142 }
nuclear@1 143 }
nuclear@1 144 }
nuclear@1 145
nuclear@4 146 static bool bnstate[8];
nuclear@4 147 static int prev_x, prev_y;
nuclear@4 148
nuclear@4 149 #define ON_SPLITTER(y) (abs(y - splitter_y) <= SPLITTER_WIDTH / 2)
nuclear@4 150 static bool splitter_dragging;
nuclear@4 151
nuclear@1 152 void ev_mouse_button(int bn, int press, int x, int y)
nuclear@1 153 {
nuclear@4 154 bnstate[bn] = press != 0;
nuclear@4 155 prev_x = x;
nuclear@4 156 prev_y = y;
nuclear@4 157
nuclear@4 158 splitter_dragging = bn == 0 && press && ON_SPLITTER(y);
nuclear@4 159
nuclear@4 160 if(!splitter_dragging && y > splitter_y) {
nuclear@4 161 xfview_button(bn, press, x, y);
nuclear@4 162 }
nuclear@1 163 }
nuclear@1 164
nuclear@1 165 void ev_mouse_motion(int x, int y)
nuclear@1 166 {
nuclear@4 167 int dx = x - prev_x;
nuclear@4 168 int dy = y - prev_y;
nuclear@4 169 prev_x = x;
nuclear@4 170 prev_y = y;
nuclear@4 171
nuclear@4 172 if((dx | dy) == 0) return;
nuclear@4 173
nuclear@4 174 if(splitter_dragging) {
nuclear@4 175 splitter_y += dy;
nuclear@4 176 redisplay();
nuclear@4 177 return;
nuclear@4 178 }
nuclear@4 179
nuclear@4 180 if(y > splitter_y) {
nuclear@4 181 xfview_motion(x, y);
nuclear@4 182 return;
nuclear@4 183 }
nuclear@4 184
nuclear@4 185 // main view motion handling
nuclear@4 186 if(bnstate[0]) {
nuclear@4 187 cam_theta += dx * 0.5;
nuclear@4 188 cam_phi += dy * 0.5;
nuclear@4 189
nuclear@4 190 if(cam_phi < -90) cam_phi = -90;
nuclear@4 191 if(cam_phi > 90) cam_phi = 90;
nuclear@4 192 redisplay();
nuclear@4 193 }
nuclear@4 194 if(bnstate[2]) {
nuclear@4 195 cam_dist += dy * 0.1;
nuclear@4 196
nuclear@4 197 if(cam_dist < 0.0) cam_dist = 0.0;
nuclear@4 198 redisplay();
nuclear@4 199 }
nuclear@1 200 }
nuclear@0 201
nuclear@0 202 } // extern "C"