~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~ [ freetext search ] ~ [ file search ] ~

Linux Cross Reference
Tina4/src/tools/nmr-segment/nmr_mouse.c

Version: ~
Architecture: ~ [ i386 ] ~ [ alpha ] ~ [ m68k ] ~ [ mips ] ~ [ ppc ] ~ [ sparc ] ~ [ sparc64 ] ~

  1 /*
  2    nmr_mouse.c
  3 
  4    a.lacey 6.5.98
  5 */
  6 
  7 
  8 #include <stdio.h>
  9 #include <math.h>
 10 #include <tina/sys.h>
 11 #include <tina/sysfuncs.h>
 12 #include <tina/math.h>
 13 #include <tina/mathfuncs.h>
 14 #include <tina/vision.h>
 15 #include <tina/visionfuncs.h>
 16 #include <tina/tv.h>
 17 #include <tina/tvfuncs.h>
 18 #include <tina/draw.h>
 19 #include <tina/drawfuncs.h>
 20 #include <tina/toolsfuncs.h>
 21 #include <tina/seqoral.h>
 22 #include <tina/seqpro.h>
 23 #include <tina/stimdef.h>
 24 
 25 
 26 extern void ***coreg_limits(int *lz, int *uz, int *ly,
 27                             int *uy, int *lx, int *ux);
 28 extern void ***coreg_slice_init(Vec3 *v);
 29 extern float nearest_pixel(void ***rasptrs, Vec3 post);
 30 
 31 
 32 static void ***imptrs = NULL;
 33 
 34 static Vec2 start_line;
 35 static Vec2 end_line;
 36 
 37 static Vec2 p1 = {Vec2_id};
 38 static Vec2 p2 = {Vec2_id};
 39 
 40 static List *roi_poly = NULL;
 41 
 42 
 43 
 44 
 45 static void  line_length_print()
 46 {
 47   Imrect  *im = NULL;
 48   List  *store = (List *)get_start_el();
 49   Vec3    *scale = NULL;
 50   double   o, a, theta, length_p, length_s;
 51 
 52   if (store != NULL)
 53     im = (Imrect *)(store->to);
 54   if (im != NULL)
 55     scale = (Vec3 *)prop_get(im->props, VOXELS);
 56 
 57   o = fabs(vec2_y(start_line) - vec2_y(end_line));
 58   a = fabs(vec2_x(start_line) - vec2_x(end_line));
 59 
 60   if (o < 0.01)
 61     length_p = a;
 62   else if (a < 0.01)
 63     length_p = o;
 64   else
 65     {
 66       theta = atan2(o, a);
 67       length_p = o/sin(theta);
 68     }
 69 
 70 
 71   if (scale != NULL)
 72     {
 73       o = (scale->el[1])*o;
 74       a = (scale->el[0])*a;
 75       if (o < 0.01)
 76         length_s = a;
 77       else if (a < 0.01)
 78         length_s = o;
 79       else
 80       {
 81         theta = atan2(o, a);
 82         length_s = o/sin(theta);
 83       }
 84     }
 85 
 86   if (scale != NULL)
 87     format("line length %4.2f pixels and %4.2f mm\n", length_p, length_s);
 88   else
 89     format("line length %4.2f pixels\n", length_p);
 90 
 91   return;
 92 }
 93 
 94 
 95 static void set_start_down(Tv * tv, Ipos pos)
 96 {
 97     Vec2    tv_backproj2();
 98 
 99     start_line = tv_backproj2(tv, pos);
100     end_line = tv_backproj2(tv, pos);
101     tv_set_overlay(tv);
102 }
103 
104 
105 static void draw_line_drag(Tv * tv, Ipos pos)
106 {
107     Vec2    tv_backproj2();
108 
109     tv_line2(tv, start_line, end_line);
110     end_line = tv_backproj2(tv, pos);
111     tv_line2(tv, start_line, end_line);
112 }
113 
114 
115 static void draw_line_up(Tv *tv, Ipos pos)
116 {
117     tv_line2(tv, start_line, end_line);
118     end_line = tv_backproj2(tv, pos);
119     tv_reset_draw(tv);
120     tv_set_overlay(tv);
121     tv_line2(tv, start_line, end_line);
122     tv_reset_draw(tv);
123     line_length_print();
124 }
125 
126 
127 Tv_mouse      nmr_linelen_mouse(void)
128 {
129     return (mouse_define(MOUSE_NAME, "line length",
130                          LEFT_NAME, "line",
131                          LEFT_DOWN, set_start_down,
132                          LEFT_DRAG, draw_line_drag,
133                          LEFT_UP,   draw_line_up,
134                          NULL));
135 }
136 
137 
138 static  void   mask_size_start_d(Tv *tv, Ipos pos)
139 {
140   tv_set_overlay(tv);    
141   p1 = p2 = tv_backproj2(tv, pos);
142   tv_rect2(tv, p1, p2);
143 }
144 
145 
146 static  void   mask_size_start_u(Tv *tv, Ipos pos)
147 {
148   tv_rect2(tv, p1, p2);
149   if (vec2_x(p1) < vec2_x(p2))
150     {
151       vec2_x(tv->ul) = vec2_x(p1);
152       vec2_x(tv->lr) = vec2_x(p2);
153     } 
154   else
155     {
156       vec2_x(tv->ul) = vec2_x(p2);
157       vec2_x(tv->lr) = vec2_x(p1);
158     }
159   if (vec2_y(p1) < vec2_y(p2))
160     {
161       vec2_y(tv->ul) = vec2_y(p1);
162       vec2_y(tv->lr) = vec2_y(p2);
163     } 
164   else
165     {
166       vec2_y(tv->ul) = vec2_y(p2);
167       vec2_y(tv->lr) = vec2_y(p1);
168     }
169   tv_reset_draw(tv);
170   p1 = p2; 
171   if (roi_poly!=NULL) dd_list_rm(roi_poly,vec2_free);
172   roi_poly = NULL;
173 }
174 
175 
176 static  void   mask_size_point_d(Tv *tv, Ipos pos)
177 {
178   tv_set_overlay(tv);    
179   p2 = tv_backproj2(tv, pos);
180   tv_line2(tv,p1,p2);
181 }
182 
183 
184 static  void   mask_size_point_u(Tv *tv, Ipos pos)
185 {
186   if (roi_poly==NULL) 
187     roi_poly = dd_ref_addtostart(roi_poly,(void *)vec2_copy
188                               (&p1),VEC2);
189   roi_poly = dd_ref_addtostart(roi_poly,(void *)vec2_copy(&p2),VEC2);
190   tv_reset_draw(tv);
191   p1 = p2;
192   if (vec2_x(p1)<vec2_x(tv->ul)) vec2_x(tv->ul) = vec2_x(p1);
193   if (vec2_x(p1)>vec2_x(tv->lr)) vec2_x(tv->lr) = vec2_x(p1);
194   if (vec2_y(p1)<vec2_y(tv->ul)) vec2_y(tv->ul) = vec2_y(p1);
195   if (vec2_y(p1)>vec2_y(tv->lr)) vec2_y(tv->lr) = vec2_y(p1);
196 }
197 
198 
199 int    calc_mask_size(Imrect *mask)
200 {
201   int      cs_area = 0;
202   int      i, j;
203 
204   if (mask == NULL || mask->vtype != uchar_v)
205     return (cs_area);
206 
207   for (i = mask->region->ly; i < mask->region->uy; i++)
208     for (j = mask->region->lx; j < mask->region->ux; j++)
209       {
210         if (IM_CHAR(mask, i, j) == 1)
211           cs_area++;
212       }
213 
214   return(cs_area);
215 }
216 
217 
218 
219 static void   mask_size_show(Tv *tv, Ipos pos)
220 {
221   Imrect  *im = NULL, *mask = NULL;
222   Imrect  *reg = NULL, *res = NULL;
223   List  *store = (List *)get_start_el();
224   Vec3    *scale = NULL;
225   int      cs_area = 0;
226   int      i, j, type;
227 
228   if (stack_check_types(IMRECT, NULL) == false)
229     {
230       error("mask_size_show: wrong type on stack", warning);
231       return;
232     }
233 
234   mask = (Imrect *) stack_pop(&type);
235   reg = im_alloc(mask->height, mask->width, NULL, char_v);
236   for (i = mask->region->ly; i < mask->region->uy; i++)
237     for (j = mask->region->lx; j < mask->region->ux; j++)
238       IM_CHAR(reg, i, j) = 1;
239   im_poly_crop(reg, roi_poly);
240   res = im_prod(mask, reg);
241   cs_area = calc_mask_size(res);
242 
243   if (store != NULL)
244     im = (Imrect *)(store->to);
245   if (im != NULL)
246     scale = (Vec3 *)prop_get(im->props, VOXELS);
247      
248   if (scale != NULL)
249     format("mask area %d pixels and %4.2f mm^2\n", cs_area, 
250            (scale->el[0])*(scale->el[1])*(double)cs_area);
251   else
252     format("mask area %d pixels\n", cs_area);
253 
254   stack_push((void *)mask, IMRECT, im_free);
255 
256   im_free(reg);
257   im_free(res);
258   return;
259 }
260 
261 
262 
263 Tv_mouse      nmr_masksize_mouse(void)
264 {
265   return (mouse_define(MOUSE_NAME,  "mask size",
266                        LEFT_NAME,   "start",
267                        LEFT_DOWN,    mask_size_start_d,
268                        LEFT_UP,      mask_size_start_u,
269                        RIGHT_NAME,  "next",
270                        RIGHT_DOWN,   mask_size_point_d,
271                        RIGHT_UP,     mask_size_point_u,
272                        MIDDLE_NAME, "size",
273                        MIDDLE_DOWN,  mask_size_show,
274                        NULL));
275 
276 }
277 
278 
279 static void   region_size_show(Tv *tv, Ipos pos)
280 {
281     List            *tv_poly_get();
282   Imrect  *im = NULL, *mask = NULL, *sim = NULL;
283   List  *store = (List *)get_start_el();
284   Vec3    *scale = NULL;
285   int      cs_area = 0;
286   int      i, j, type;
287 
288  if (stack_check_types(IMRECT, NULL) == false)
289     {
290       error("region_size_show: wrong type on stack", warning);
291       return;
292     }
293 
294   sim = (Imrect *) stack_pop(&type);
295 
296   mask = im_alloc(sim->height, sim->width, NULL, char_v);
297   for (i = mask->region->ly; i < mask->region->uy; i++)
298     for (j = mask->region->lx; j < mask->region->ux; j++)
299       IM_CHAR(mask, i, j) = 1;
300   im_poly_crop(mask, roi_poly);
301    
302   if (store != NULL)
303     im = (Imrect *)(store->to);
304   if (im != NULL)
305     scale = (Vec3 *)prop_get(im->props, VOXELS);
306   
307   for (i = mask->region->ly; i < mask->region->uy; i++)
308       for (j = mask->region->lx; j < mask->region->ux; j++)
309         {
310           if (IM_CHAR(mask, i, j) == 1)
311             cs_area++;
312         }
313 
314   stack_push((void *)sim, IMRECT, im_free);
315 
316   if (scale != NULL)
317     format("region area %4.2f mm^2\n", (scale->el[0])*(scale->el[1])*(double)cs_area);
318   else
319     format("region area %d pixels\n", cs_area);
320 
321   im_free(mask);
322 
323   return;
324 }
325 
326 
327 Tv_mouse      nmr_regsize_mouse(void)
328 {
329   return (mouse_define(MOUSE_NAME,  "region size",
330                        LEFT_NAME,   "start",
331                        LEFT_DOWN,    mask_size_start_d,
332                        LEFT_UP,      mask_size_start_u,
333                        RIGHT_NAME,  "next",
334                        RIGHT_DOWN,   mask_size_point_d,
335                        RIGHT_UP,     mask_size_point_u,
336                        MIDDLE_NAME, "size",
337                        MIDDLE_DOWN,  region_size_show,
338                        NULL));
339 
340 }
341 
342 
343 static void   pixel_ft_plot(Tv *tv, Ipos pos)
344 { 
345   Vec2      tv_backproj2();
346 
347   Pl_flow  *plot_data = pl_flow_alloc();
348   Vec2      v = {Vec2_id};
349   Vec3     *scale = NULL;
350   Sequence *seq = NULL;
351   List   *store = (List *)get_start_el();
352   Imrect   *im;
353   Tv       *tv_graph = (Tv *)imcalc_graph_tv_get();
354   float    *flow, *time;
355   int       imptrlx, imptrux, imptrly, imptruy, imptrlz, imptruz;
356   int       length, x, y, k;
357   int       type;
358   float    *row;
359 
360 
361   if (tv == NULL || tv->tv_screen == NULL)
362     return;
363   if (tv_graph == NULL || tv_graph->tv_screen == NULL)
364     return;
365   if ((store == NULL) || (store->to == NULL))
366     return;
367 
368   seq = (Sequence *)get_seq_ptr();
369   im = (Imrect *)(store->to);
370 
371   if ((time = (float *)prop_get(im->props, DYNSTIME)) == NULL)
372     {
373       error("pixel_ft_plot: timing info missing", warning);
374       return;
375     }
376 
377   if ((scale = (Vec3 *)prop_get(im->props, VOXELS)) == NULL)
378     {
379       error("pixel_ft_plot: scale info missing", warning);
380       return;
381     }
382 
383   coreg_slice_init((Vec3 *)NULL);
384   imptrs = coreg_limits(&imptrlz, &imptruz, &imptrly, &imptruy, &imptrlx, 
385                         &imptrux);
386   length = imptruz - imptrlz;    
387   flow = (float *)fvector_alloc(0, length);
388 
389   v = tv_backproj2(tv, pos);
390   x = tina_int(vec2_x(v));
391   y = tina_int(vec2_y(v));
392 
393   for (k = 0; k < length; k++)
394     {
395       row = imptrs[k+imptrlz][y];
396       flow[k] = row[x];
397       flow[k] *= ((scale->el[0])*(scale->el[1])/100);
398     }
399 
400   tv_erase(tv_graph);
401   plot(PL_INIT, PL_TV, tv_graph,
402        PL_AXIS_COLOR, black,
403        PL_X_TEXT, true,
404        PL_Y_TEXT, true,
405        PL_TITLE, "Signal v Time",
406        PL_STYLE, PL_CROSS,
407        PL_COLOR, red,
408        PL_GRAPH_DATA, length, time, flow,
409        PL_PLOT,
410        NULL);
411 
412   plot_data->mask = NULL;
413   plot_data->y1 = flow;
414   plot_data->x = fvector_copy((void *)time, 0, length);
415   plot_data->y1_n2 = plot_data->x_n2 = length;
416   plot_data->y1_n1 = plot_data->x_n1 = 0;
417   set_pl_flow(plot_data);
418   
419   return;
420 }
421 
422 
423 Tv_mouse     nmr_flow_mouse()
424 {
425     return (mouse_define(MOUSE_NAME, "F/T",
426                          LEFT_NAME, "pixel",
427                          LEFT_DOWN, pixel_ft_plot,
428                          NULL));
429 }
430 
431 
432 static void   pixel_ct_plot(Tv *tv, Ipos pos)
433 {
434   float    *conv_st_to_r2(Perfusion *p); 
435   float    *s_2d_pixel_get(void ***imptrs, Vec2 v, Perfusion *p);
436   float     ave_s0_pre_bolus(Perfusion *p);
437   int       find_bolus_time(Perfusion *p);
438   Vec2      tv_backproj2();
439 
440   Pl_flow   *plot_data = pl_flow_alloc();
441   Perfusion *p, *perfusion_alloc();
442   Vec2      v = {Vec2_id};
443   Sequence *seq = NULL;
444   List   *store = (List *)get_start_el();
445   Imrect   *im;
446   Tv       *tv_graph = (Tv *)imcalc_graph_tv_get();
447   float     *r2, *time, *TE;
448   int       imptrlx, imptrux, imptrly, imptruy, imptrlz, imptruz;
449   int       length, x, y, k;
450   int       type;
451   float    *row;
452 
453 
454   if (tv == NULL || tv->tv_screen == NULL)
455     return;
456   if (tv_graph == NULL || tv_graph->tv_screen == NULL)
457     return;
458   if ((store == NULL) || (store->to == NULL))
459     return;
460 
461   seq = (Sequence *)get_seq_ptr();
462   im = (Imrect *)(store->to);
463   if ((time = (float *)prop_get(im->props, DYNSTIME)) == NULL)
464     {
465       error("pixel_ct_plot: timing info missing", warning);
466       return;
467     }
468 
469   if ((TE = (float *)prop_get(im->props, TE_DATA)) == NULL)
470     {
471       error("pixel_ct_plot: echo time info missing", warning);
472       return;
473     }
474 
475   coreg_slice_init((Vec3 *)NULL);
476   imptrs = coreg_limits(&imptrlz, &imptruz, &imptrly, &imptruy, &imptrlx, &imptrux);
477   length = imptruz - imptrlz;    
478   p = perfusion_alloc();
479   p->n1 = imptrlz;
480   p->n2 = imptruz;
481   p->te = *TE;
482 
483   v = tv_backproj2(tv, pos);
484 
485   p->st_1d = s_2d_pixel_get(imptrs, v, p);
486   p->bolus_time = find_bolus_time(p);
487   p->s0_av = ave_s0_pre_bolus(p);
488   p->tscale = time[2]-time[1];
489   r2 = conv_st_to_r2(p);
490 
491   tv_erase(tv_graph);
492   plot(PL_INIT, PL_TV, tv_graph,
493        PL_AXIS_COLOR, black,
494        PL_X_TEXT, true, 
495        PL_Y_TEXT, true, 
496        PL_TITLE, "Conc. v Time",
497        PL_STYLE, PL_CROSS,
498        PL_COLOR, red,
499        PL_GRAPH_DATA, length, time, &r2[imptrlz],
500        PL_PLOT,
501        NULL);
502 
503 
504   plot_data->mask = NULL;
505   plot_data->y1 = &r2[imptrlz];
506   plot_data->x = fvector_copy((void *)time, 0, length);
507   plot_data->y1_n2 = plot_data->x_n2 = length;
508   plot_data->y1_n1 = plot_data->x_n1 = 0;
509   set_pl_flow(plot_data);
510   perfusion_free(p);
511   
512   return;
513 }
514 
515 
516 Tv_mouse     nmr_ctflow_mouse(void)
517 {
518     return (mouse_define(MOUSE_NAME, "C/T",
519                          LEFT_NAME, "pixel",
520                          LEFT_DOWN, pixel_ct_plot,
521                          NULL));
522 }
523 
524 
525 
526 static void   pixel_gfit_plot(Tv *tv, Ipos pos)
527 {
528   void       gamma_fit_pixel(Perfusion *p, Vec2 v, void ***imptrs);
529   Perfusion *perfusion_alloc(void);
530 
531   Perfusion *p = NULL;
532   Vec2       loc = {Vec2_id};  
533   List    *store = (List *)get_start_el();
534   Imrect    *im = NULL;
535   Tv        *tv_g = (Tv *)imcalc_graph_tv();
536   float     *time, *x, *y1, *y2;
537   int        imptrlx, imptrux, imptrly, imptruy, imptrlz, imptruz;
538   void    ***imptrs;
539   int        length;
540   
541   if ((tv_g == NULL) || (tv_g->tv_screen == NULL))
542     return;
543 
544   loc = tv_backproj2(tv, pos);
545   p = perfusion_alloc();
546 
547   im = (Imrect *)(store->to);
548   if ((time = (float *)prop_get(im->props, DYNSTIME)) == NULL)
549     {
550       error("gamma_fit_proc: timing info missing", warning);
551       return;
552     }
553 
554   imptrs = coreg_slice_init((Vec3 *)NULL);
555   gamma_fit_pixel(p, loc, imptrs);
556   imptrs = coreg_limits(&imptrlz, &imptruz, &imptrly, &imptruy, &imptrlx, 
557                         &imptrux);
558 /*  length = (p->st_r2_n2 -  p->st_r2_n1);
559 */
560   length =  imptruz - imptrlz;
561   x = time;
562   if (p->r2 != NULL && p->r2_ther !=NULL)
563   {
564     y1 = &(p->r2[imptrlz]);
565     y2 = &(p->r2_ther[imptrlz]);
566       
567     tv_erase(tv_g);
568     plot(PL_INIT, PL_TV, tv_g,
569          PL_AXIS_COLOR, black,
570          PL_X_TEXT, true, 
571          PL_Y_TEXT, true, 
572          PL_TITLE, "Gamma Fit",
573          PL_STYLE, PL_CROSS,
574          PL_COLOR, red,
575          PL_GRAPH_DATA, length, x, y1,
576          PL_STYLE, PL_CROSS,
577          PL_COLOR, blue,
578          PL_GRAPH_DATA, length, x, y2,
579          PL_STYLE, PL_LINE, 
580          PL_GRAPH_DATA, length, x, y2,
581          PL_PLOT,
582          NULL);
583 
584   }
585   return;
586 }
587 
588 double   pixel_gfit_region(Tv *tv, Ipos pos)
589 {
590   double       gamma_fit_region(Perfusion *p, Vec2 v, void ***imptrs);
591   Perfusion *perfusion_alloc(void);
592 
593   Perfusion *p = NULL;
594   Vec2       loc = {Vec2_id};
595   List    *store = (List *)get_start_el();
596   Imrect    *im = NULL;
597   Tv        *tv_g = (Tv *)imcalc_graph_tv();
598   float     *time, *x, *y1, *y2;
599   int        imptrlx, imptrux, imptrly, imptruy, imptrlz, imptruz;
600   void    ***imptrs;
601   int        length;
602   double     t0;
603  
604 
605   p = perfusion_alloc();
606 
607   im = (Imrect *)(store->to);
608   if ((time = (float *)prop_get(im->props, DYNSTIME)) == NULL)
609     {
610       error("gamma_fit_proc: timing info missing", warning);
611       return(0.0);
612     }
613   imptrs = coreg_slice_init((Vec3 *)NULL);
614   t0 = gamma_fit_region(p, loc, imptrs);
615   imptrs = coreg_limits(&imptrlz, &imptruz, &imptrly, &imptruy, &imptrlx,
616                         &imptrux);
617 /*  length = (p->st_r2_n2 -  p->st_r2_n1);
618 */
619   length =  imptruz - imptrlz;
620   x = time;
621   if (p->r2 != NULL && p->r2_ther !=NULL)
622   {
623     y1 = &(p->r2[imptrlz]);
624     y2 = &(p->r2_ther[imptrlz]);
625 
626     tv_erase(tv_g);
627     plot(PL_INIT, PL_TV, tv_g,
628          PL_AXIS_COLOR, black,
629          PL_X_TEXT, true, 
630          PL_Y_TEXT, true,
631          PL_TITLE, "Gamma Fit",
632          PL_STYLE, PL_CROSS,
633          PL_COLOR, red,
634          PL_GRAPH_DATA, length, x, y1,
635          PL_STYLE, PL_CROSS,
636          PL_COLOR, blue,
637          PL_GRAPH_DATA, length, x, y2,
638          PL_STYLE, PL_LINE,
639          PL_GRAPH_DATA, length, x, y2,
640          PL_PLOT,
641          NULL);
642 
643   }
644   return(t0);
645 }
646 
647 Tv_mouse     nmr_gfit_mouse(void)
648 {
649     return (mouse_define(MOUSE_NAME, "gamma fit",
650                          LEFT_NAME, "pixel",
651                          LEFT_DOWN, pixel_gfit_plot,
652                          NULL));
653 }
654 
655 Tv_mouse     nmr_gfit_region(void)
656 {
657     return (mouse_define(MOUSE_NAME, "gamma region",
658                          LEFT_NAME, "region",
659                          LEFT_DOWN, pixel_gfit_region,
660                          NULL));
661 }
662 

~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~ [ freetext search ] ~ [ file search ] ~

This page was automatically generated by the LXR engine.
Visit the LXR main site for more information.