]> Creatis software - clitk.git/blob - vv/vvSlicer.cxx
1de1738c030f39925a49c96fe740945d07bea407
[clitk.git] / vv / vvSlicer.cxx
1 /*=========================================================================
2   Program:   vv                     http://www.creatis.insa-lyon.fr/rio/vv
3
4   Authors belong to: 
5   - University of LYON              http://www.universite-lyon.fr/
6   - Léon Bérard cancer center       http://oncora1.lyon.fnclcc.fr
7   - CREATIS CNRS laboratory         http://www.creatis.insa-lyon.fr
8
9   This software is distributed WITHOUT ANY WARRANTY; without even
10   the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
11   PURPOSE.  See the copyright notices for more information.
12
13   It is distributed under dual licence
14
15   - BSD        See included LICENSE.txt file
16   - CeCILL-B   http://www.cecill.info/licences/Licence_CeCILL-B_V1-en.html
17   ======================================================================-====*/
18
19 #include "vvSlicer.h"
20 #include "vvImage.h"
21 #include "vvSlicerManagerCommand.h"
22 #include "vvGlyphSource.h"
23 #include "vvGlyph2D.h"
24 #include "vvImageMapToWLColors.h"
25
26 #include <vtkTextProperty.h>
27 #include <vtkTextActor.h>
28 #include <vtkTextSource.h>
29 #include <vtkActor2D.h>
30 #include <vtkCursor2D.h>
31 #include <vtkPolyDataMapper2D.h>
32 #include <vtkProperty2D.h>
33 #include <vtkCornerAnnotation.h>
34 #include <vtkImageMapToWindowLevelColors.h>
35 #include <vtkImageData.h>
36 #include <vtkImageActor.h>
37 #include <vvBlendImageActor.h>
38 #include <vtkToolkits.h>
39 #include <vtkObjectFactory.h>
40 #include <vtkPointData.h>
41 #include <vtkDataArray.h>
42 #include <vtkFloatArray.h>
43 #include <vtkClipPolyData.h>
44 #include <vtkGlyph3D.h>
45 #include <vtkMath.h>
46 #include <vtkCursor3D.h>
47 #include <vtkProperty.h>
48 #include <vtkLight.h>
49 #include <vtkLightCollection.h>
50 #include <vtkScalarBarActor.h>
51 #include <vtkLookupTable.h>
52
53 #include <vtkRenderer.h>
54 #include <vtkRendererCollection.h>
55 #include <vtkRenderWindow.h>
56 #include <vtkRenderWindowInteractor.h>
57 #include <vtkCamera.h>
58 #include <vtkCallbackCommand.h>
59 #include <vtkCommand.h>
60 #include <vtkPolyDataMapper.h>
61 #include <vtkBox.h>
62
63 #include <vtkExtractVOI.h>
64 #include <vtkSphereSource.h>
65 #include <vtkCutter.h>
66 #include <vtkAssignAttribute.h>
67 #include <vtkImageAccumulate.h>
68 #include <vtkImageReslice.h>
69
70 vtkCxxRevisionMacro(vvSlicer, "DummyRevision");
71 vtkStandardNewMacro(vvSlicer);
72
73 //------------------------------------------------------------------------------
74 vvSlicer::vvSlicer()
75 {
76   mImage = NULL;
77   mCurrentTSlice = 0;
78   mUseReducedExtent = false;
79
80   mCurrent[0] = -VTK_DOUBLE_MAX;
81   mCurrent[1] = -VTK_DOUBLE_MAX;
82   mCurrent[2] = -VTK_DOUBLE_MAX;
83
84   mCursor[0] = -VTK_DOUBLE_MAX;
85   mCursor[1] = -VTK_DOUBLE_MAX;
86   mCursor[2] = -VTK_DOUBLE_MAX;
87   mCursor[3] = -VTK_DOUBLE_MAX;
88
89   mSubSampling = 5;
90   mScale = 1;
91   mVFLog = 0;
92   mVFWidth = 1;
93
94   std::string text = "F1 = sagital; F2 = coronal; F3 = axial\n";
95   text += "F5 = horizontal flip; F6 = vertical flip\n\n";
96   text += "0,1,2,3,4,5 : preset windowing\n";
97   text += "6,7,8,9 : preset colormap\n";
98   text += "z : local windowing\n";
99   text += "r : reset view\n";
100   text += "l : reload image\n";
101   text += "f : fly to mouse position\n";
102   text += "g : go to cross hair position\n\n";
103   text += "Up,down : change slice\n";
104   text += "Left,right : change tenporal slice\n\n";
105   text += "Scrollbar (or w/x) : zoom in/out\n";
106   text += "left button : synchronize all views\n";
107   text += "middle button : grab image\n";
108   text += "right button : change windowing\n";
109
110   crossCursor = vtkCursor2D::New();
111   crossCursor->AllOff();
112   crossCursor->AxesOn();
113   crossCursor->SetTranslationMode(1);
114   crossCursor->SetRadius(2);
115
116   pdm = vtkPolyDataMapper2D::New();
117   pdm->SetInput(crossCursor->GetOutput());
118
119   pdmA = vtkActor2D::New();
120   pdmA->SetMapper(pdm);
121   pdmA->GetProperty()->SetColor(255,10,212);
122   pdmA->SetVisibility(0);
123   pdmA->SetPickable(0);
124
125   ca = vtkCornerAnnotation::New();
126   ca->GetTextProperty()->SetColor(255,10,212);
127   ca->SetVisibility(1);
128   mFileName = "";
129
130   mVF = NULL;
131   mOverlay = NULL;
132   mFusion = NULL;
133   mLandmarks = NULL;
134
135   legend = vtkSmartPointer<vtkScalarBarActor>::New();
136   //legend->SetTitle("test!");
137   legend->SetPosition(0.82,0.18);
138   legend->SetWidth(0.1);
139   legend->SetVisibility(0);
140   legend->SetLabelFormat("%.1f");
141   this->GetRenderer()->AddActor(legend);
142
143   this->WindowLevel->Delete();
144   this->WindowLevel = vvImageMapToWLColors::New();
145   this->InstallPipeline();
146   
147 }
148 //------------------------------------------------------------------------------
149
150
151 //------------------------------------------------------------------------------
152 vtkImageMapToWindowLevelColors* vvSlicer::GetOverlayMapper() {
153   return mOverlayMapper.GetPointer();
154 }
155 //------------------------------------------------------------------------------
156
157
158 //------------------------------------------------------------------------------
159 vvBlendImageActor* vvSlicer::GetOverlayActor() {
160   return mOverlayActor.GetPointer();
161 }
162 //------------------------------------------------------------------------------
163
164
165 //------------------------------------------------------------------------------
166 vtkImageMapToWindowLevelColors* vvSlicer::GetFusionMapper() {
167   return mFusionMapper.GetPointer();
168 }
169 //------------------------------------------------------------------------------
170
171     
172 //------------------------------------------------------------------------------
173 vtkImageActor* vvSlicer::GetFusionActor() {
174   return mFusionActor.GetPointer();
175 }
176 //------------------------------------------------------------------------------
177
178
179 //------------------------------------------------------------------------------
180 vtkActor* vvSlicer::GetVFActor() {
181   return mVFActor.GetPointer();
182 }
183 //------------------------------------------------------------------------------
184
185
186 //------------------------------------------------------------------------------
187 vtkCornerAnnotation* vvSlicer::GetAnnotation() {
188   return ca.GetPointer();
189 }
190 //------------------------------------------------------------------------------
191
192
193 //------------------------------------------------------------------------------
194 void vvSlicer::EnableReducedExtent(bool b) {
195   mUseReducedExtent = b;
196 }
197 //------------------------------------------------------------------------------
198
199
200 //------------------------------------------------------------------------------
201 void vvSlicer::SetReducedExtent(int * ext) {
202   mReducedExtent = ext;
203 }
204 //------------------------------------------------------------------------------
205
206
207 //------------------------------------------------------------------------------
208 void vvSlicer::AddContour(vvMesh::Pointer contour,bool propagate)
209 {
210
211   mSurfaceCutActors.push_back(new vvMeshActor());
212   if (propagate)
213     mSurfaceCutActors.back()->Init(contour,mCurrentTSlice,mVF);
214   else
215     mSurfaceCutActors.back()->Init(contour,mCurrentTSlice);
216   mSurfaceCutActors.back()->SetSlicingOrientation(SliceOrientation);
217   this->GetRenderer()->AddActor(mSurfaceCutActors.back()->GetActor());
218
219   SetContourSlice();
220 }
221 //------------------------------------------------------------------------------
222
223
224 //------------------------------------------------------------------------------
225 void vvSlicer::ToggleContourSuperposition()
226 {
227   for (std::vector<vvMeshActor*>::iterator i=mSurfaceCutActors.begin();
228        i!=mSurfaceCutActors.end();i++)
229     (*i)->ToggleSuperposition();
230 }
231 //------------------------------------------------------------------------------
232
233
234 //------------------------------------------------------------------------------
235 void vvSlicer::SetCursorColor(int r,int g, int b)
236 {
237   pdmA->GetProperty()->SetColor(r,g,b);
238 }
239 //------------------------------------------------------------------------------
240
241
242 //------------------------------------------------------------------------------
243 void vvSlicer::SetCursorVisibility(bool s)
244 {
245   pdmA->SetVisibility(s);
246 }
247 //------------------------------------------------------------------------------
248
249
250 //------------------------------------------------------------------------------
251 bool vvSlicer::GetCursorVisibility()
252 {
253   return pdmA->GetVisibility();
254 }
255 //------------------------------------------------------------------------------
256
257
258 //------------------------------------------------------------------------------
259 vvSlicer::~vvSlicer()
260 {
261   for (std::vector<vvMeshActor*>::iterator i=mSurfaceCutActors.begin();
262        i!=mSurfaceCutActors.end();i++)
263     delete (*i);
264 }
265 //------------------------------------------------------------------------------
266
267
268 //------------------------------------------------------------------------------
269 void vvSlicer::SetCurrentPosition(double x, double y, double z, int t)
270 {
271   mCurrent[0] = x;
272   mCurrent[1] = y;
273   mCurrent[2] = z;
274   mCurrentTSlice = t;
275 }
276 //------------------------------------------------------------------------------
277
278
279 //------------------------------------------------------------------------------
280 void vvSlicer::SetImage(vvImage::Pointer image)
281 {
282   if (image->GetVTKImages().size())
283     {
284       mImage = image;
285       this->Superclass::SetInput(image->GetVTKImages()[0]);
286
287       // Prevent crash when reload -> change slice if outside extent
288       int extent[6];
289       this->GetInput()->GetWholeExtent(extent);
290       if (SliceOrientation == 0) {
291         if (Slice >= extent[1]) {
292           Slice = (extent[1]-extent[0])/2.0;
293         }
294       }
295       if (SliceOrientation == 1) {
296         if (Slice >= extent[3]) {
297           Slice = (extent[3]-extent[2])/2.0;
298         }
299       }
300       if (SliceOrientation == 2) {
301         if (Slice >= extent[5]) {
302           Slice = (extent[5]-extent[4])/2.0;
303         }
304       }
305
306       this->UpdateDisplayExtent();
307       mCurrentTSlice = 0;
308       ca->SetText(0,mFileName.c_str());
309     }
310 }
311 //------------------------------------------------------------------------------
312
313
314 //------------------------------------------------------------------------------
315 void vvSlicer::SetOverlay(vvImage::Pointer overlay)
316 {
317   if (overlay->GetVTKImages().size())
318     {
319       mOverlay = overlay;
320
321       if (!mOverlayMapper)
322         mOverlayMapper = vtkImageMapToWindowLevelColors::New();
323       mOverlayMapper->SetInput(overlay->GetVTKImages()[0]);
324
325       if (!mOverlayActor)
326         {
327           mOverlayActor = vvBlendImageActor::New();
328           mOverlayActor->SetInput(mOverlayMapper->GetOutput());
329           mOverlayActor->SetPickable(0);
330           mOverlayActor->SetVisibility(false);
331           mOverlayActor->SetOpacity(0.5);
332           this->UpdateDisplayExtent();
333         }
334
335       //stupid but necessary : the Overlay need to be rendered before fusion
336       if (mFusionActor)
337         {
338           this->GetRenderer()->RemoveActor(mFusionActor);
339           this->GetRenderer()->AddActor(mOverlayActor);
340           this->GetRenderer()->AddActor(mFusionActor);
341         }
342       else
343         this->GetRenderer()->AddActor(mOverlayActor);
344
345       //Synchronize slice
346       SetTSlice(mCurrentTSlice);
347     }
348 }
349 //------------------------------------------------------------------------------
350
351
352 //------------------------------------------------------------------------------
353 void vvSlicer::SetFusion(vvImage::Pointer fusion)
354 {
355   if (fusion->GetVTKImages().size())
356     {
357       mFusion = fusion;
358
359       if (!mFusionMapper)
360         mFusionMapper = vtkImageMapToWindowLevelColors::New();
361       mFusionMapper->SetInput(fusion->GetVTKImages()[0]);
362
363       if (!mFusionActor)
364         {
365           mFusionActor = vtkImageActor::New();
366           mFusionActor->SetInput(mFusionMapper->GetOutput());
367           mFusionActor->SetPickable(0);
368           mFusionActor->SetVisibility(false);
369           mFusionActor->SetOpacity(0.7);
370           this->UpdateDisplayExtent();
371           this->GetRenderer()->AddActor(mFusionActor);
372         }
373
374       //Synchronize slice
375       SetTSlice(mCurrentTSlice);
376     }
377 }
378 //------------------------------------------------------------------------------
379
380
381 //------------------------------------------------------------------------------
382 void vvSlicer::SetActorVisibility(const std::string& actor_type, int overlay_index ,bool vis)
383 {
384   if (actor_type == "vector")
385     {
386       this->mVFActor->SetVisibility(vis);
387     }
388   if (actor_type == "overlay")
389     {
390       this->mOverlayActor->SetVisibility(vis);
391     }
392   if (actor_type == "fusion")
393     {
394       this->mFusionActor->SetVisibility(vis);
395     }
396   if (actor_type == "contour")
397     this->mSurfaceCutActors[overlay_index]->GetActor()->SetVisibility(vis);
398   UpdateDisplayExtent();
399 }
400 //------------------------------------------------------------------------------
401
402
403 //------------------------------------------------------------------------------
404 void vvSlicer::SetVF(vvImage::Pointer vf)
405 {
406   if (vf->GetVTKImages().size())
407     {
408       mVF = vf;
409
410       if (!mAAFilter)
411         {
412           mAAFilter=vtkAssignAttribute::New();
413           mVOIFilter = vtkExtractVOI::New();
414           mVOIFilter->SetSampleRate(mSubSampling,mSubSampling,mSubSampling);
415         }
416       mVOIFilter->SetInput(vf->GetVTKImages()[0]);
417       mAAFilter->SetInput(mVOIFilter->GetOutput());
418       ///This tells VTK to use the scalar (pixel) data of the image to draw the little arrows
419       mAAFilter->Assign(vtkDataSetAttributes::SCALARS, vtkDataSetAttributes::VECTORS, vtkAssignAttribute::POINT_DATA);
420
421       if (!mArrow)
422         mArrow = vvGlyphSource::New();
423       mArrow->SetGlyphTypeToSpecificArrow();
424       mArrow->SetScale(mScale);
425       mArrow->FilledOff();
426
427       // Glyph the gradient vector (with arrows)
428       if (!mGlyphFilter)
429         mGlyphFilter = vvGlyph2D::New();
430       mGlyphFilter->SetInput(mAAFilter->GetOutput());
431       mGlyphFilter->SetSource(mArrow->GetOutput());
432       mGlyphFilter->ScalingOn();
433       mGlyphFilter->SetScaleModeToScaleByVector();
434       mGlyphFilter->OrientOn();
435       mGlyphFilter->SetVectorModeToUseVector();
436       mGlyphFilter->SetColorModeToColorByVector();
437
438       if (!mVFMapper)
439         mVFMapper = vtkPolyDataMapper::New();
440       //mVFMapper->SetInputConnection(mGlyphFilter->GetOutputPort());
441       mVFMapper->SetInput(mGlyphFilter->GetOutput());
442       mVFMapper->ImmediateModeRenderingOn();
443
444       if (!mVFActor)
445         mVFActor = vtkActor::New();
446       mVFActor->SetMapper(mVFMapper);
447       mVFActor->SetPickable(0);
448       mVFActor->GetProperty()->SetLineWidth(mVFWidth);
449       this->UpdateDisplayExtent();
450       this->GetRenderer()->AddActor(mVFActor);
451
452       //Synchronize slice
453       SetTSlice(mCurrentTSlice);
454     }
455 }
456 //------------------------------------------------------------------------------
457
458
459 //------------------------------------------------------------------------------
460 void vvSlicer::SetLandmarks(vvLandmarks* landmarks)
461 {
462   mLandmarks = landmarks;
463   if (landmarks)
464     {
465
466       if (!mCross)
467         mCross = vtkCursor3D::New();
468       mCross->SetFocalPoint(0.0,0.0,0.0);
469       mCross->SetModelBounds(-10,10,-10,10,-10,10);
470       mCross->AllOff();
471       mCross->AxesOn();
472
473       if (!mLandGlyph)
474         mLandGlyph = vtkGlyph3D::New();
475       mLandGlyph->SetSource(mCross->GetOutput());
476       mLandGlyph->SetInput(landmarks->GetOutput());
477       //mLandGlyph->SetIndexModeToScalar();
478       mLandGlyph->SetRange(0,1);
479       mLandGlyph->ScalingOff();
480
481       mLandGlyph->SetColorModeToColorByScalar();
482
483       if (!mClipBox)
484         mClipBox = vtkBox::New();
485       if (!mLandClipper)
486         mLandClipper = vtkClipPolyData::New();
487       mLandClipper->InsideOutOn();
488       mLandClipper->SetInput(mLandGlyph->GetOutput());
489       mLandClipper->SetClipFunction(mClipBox);
490
491       if (!mLandMapper)
492         mLandMapper = vtkPolyDataMapper::New();
493       mLandMapper->SetInputConnection(mLandClipper->GetOutputPort());
494       //mLandMapper->ScalarVisibilityOff();
495
496       if (!mLandActor)
497         mLandActor = vtkActor::New();
498       mLandActor->SetMapper(mLandMapper);
499       mLandActor->GetProperty()->SetColor(255,10,212);
500       mLandActor->SetPickable(0);
501       mLandActor->SetVisibility(true);
502       this->UpdateDisplayExtent();
503       this->GetRenderer()->AddActor(mLandActor);
504     }
505 }
506 //------------------------------------------------------------------------------
507
508 //------------------------------------------------------------------------------
509 //FIXME: this function leaks memory, we should fix it someday :)
510 void vvSlicer::RemoveActor(const std::string& actor_type, int overlay_index)
511 {
512   if (actor_type == "vector")
513     {
514       Renderer->RemoveActor(mVFActor);
515       mGlyphFilter=NULL;
516       mVF = NULL;
517       mArrow = NULL;
518       mAAFilter=NULL;
519       mVOIFilter = NULL;
520       mVFMapper = NULL;
521       mVFActor = NULL;
522     }
523   if (actor_type == "overlay")
524     {
525       Renderer->RemoveActor(mOverlayActor);
526       mOverlay = NULL;
527       mOverlayActor = NULL;
528       mOverlayMapper = NULL;
529     }
530   if (actor_type == "fusion")
531     {
532       Renderer->RemoveActor(mFusionActor);
533       mFusion = NULL;
534       mFusionActor = NULL;
535       mFusionMapper = NULL;
536     }
537   if (actor_type == "contour")
538     {
539       Renderer->RemoveActor(this->mSurfaceCutActors[overlay_index]->GetActor());
540       mSurfaceCutActors.erase(mSurfaceCutActors.begin()+overlay_index);
541     }
542 }
543 //------------------------------------------------------------------------------
544
545
546 //------------------------------------------------------------------------------
547 void vvSlicer::SetVFSubSampling(int sub)
548 {
549   if (mVOIFilter)
550     {
551       mVOIFilter->SetSampleRate(mSubSampling,mSubSampling,mSubSampling);
552       mSubSampling = sub;
553     }
554   UpdateDisplayExtent();
555   Render();
556 }
557 //------------------------------------------------------------------------------
558
559
560 //------------------------------------------------------------------------------
561 void vvSlicer::SetVFScale(int scale)
562 {
563   mScale = scale;
564   if (mArrow)
565     mArrow->SetScale(mScale);
566   UpdateDisplayExtent();
567   Render();
568 }
569 //------------------------------------------------------------------------------
570
571 //------------------------------------------------------------------------------
572 void vvSlicer::SetVFWidth(int width)
573 {
574   mVFWidth = width;
575   if (mVFActor)
576     mVFActor->GetProperty()->SetLineWidth(mVFWidth);
577   UpdateDisplayExtent();
578   Render();
579 }
580 //------------------------------------------------------------------------------
581
582
583 //------------------------------------------------------------------------------
584 void vvSlicer::SetVFLog(int log)
585 {
586   mVFLog = log;
587   if (mGlyphFilter)
588     {
589       mGlyphFilter->SetUseLog(mVFLog);
590       mGlyphFilter->Modified();
591     }
592   UpdateDisplayExtent();
593   Render();
594 }
595 //------------------------------------------------------------------------------
596
597
598 //------------------------------------------------------------------------------
599 void vvSlicer::SetTSlice(int t)
600 {
601   if (t < 0)
602     t = 0;
603   else if ((unsigned int)t >= mImage->GetVTKImages().size())
604     t = mImage->GetVTKImages().size() -1;
605
606   if (mCurrentTSlice == t) return;
607
608   mCurrentTSlice = t;
609   this->SetInput(mImage->GetVTKImages()[t]);
610   if (mVF && mVFActor->GetVisibility())
611     {
612       if (mVF->GetVTKImages().size() > (unsigned int)mCurrentTSlice)
613         mVOIFilter->SetInput(mVF->GetVTKImages()[mCurrentTSlice]);
614     }
615   if (mOverlay && mOverlayActor->GetVisibility())
616     {
617       if (mOverlay->GetVTKImages().size() > (unsigned int)mCurrentTSlice)
618         mOverlayMapper->SetInput(mOverlay->GetVTKImages()[mCurrentTSlice]);
619     }
620   if (mFusion && mFusionActor->GetVisibility())
621     {
622       if (mFusion->GetVTKImages().size() > (unsigned int)mCurrentTSlice)
623         mFusionMapper->SetInput(mFusion->GetVTKImages()[mCurrentTSlice]);
624     }
625   if (mSurfaceCutActors.size() > 0)
626     for (std::vector<vvMeshActor*>::iterator i=mSurfaceCutActors.begin();
627          i!=mSurfaceCutActors.end();i++)
628       (*i)->SetTimeSlice(mCurrentTSlice);
629   UpdateDisplayExtent();
630 }
631 //------------------------------------------------------------------------------
632
633
634 //------------------------------------------------------------------------------
635 int vvSlicer::GetTSlice()
636 {
637   return mCurrentTSlice;
638 }
639 //------------------------------------------------------------------------------
640
641
642 //------------------------------------------------------------------------------
643 void vvSlicer::SetSliceOrientation(int orientation)
644 {
645   //if 2D image, force to watch in Axial View
646   int extent[6];
647   this->GetInput()->GetWholeExtent(extent);
648   if (extent[5]-extent[4] <= 2)
649     orientation=2;
650
651   if (orientation < vtkImageViewer2::SLICE_ORIENTATION_YZ ||
652       orientation > vtkImageViewer2::SLICE_ORIENTATION_XY)
653     {
654       vtkErrorMacro("Error - invalid slice orientation " << orientation);
655       return;
656     }
657
658   this->SliceOrientation = orientation;
659     
660   // Update the viewer
661   int *range = this->GetSliceRange();
662   if (range)
663     this->Slice = static_cast<int>((range[0] + range[1]) * 0.5);
664
665   this->UpdateOrientation();
666   this->UpdateDisplayExtent();
667
668   if (this->Renderer && this->GetInput())
669     {
670       double scale = this->Renderer->GetActiveCamera()->GetParallelScale();
671       this->Renderer->ResetCamera();
672       this->Renderer->GetActiveCamera()->SetParallelScale(scale);
673     }
674
675   SetContourSlice();
676 }
677 //----------------------------------------------------------------------------
678
679
680 //----------------------------------------------------------------------------
681 int * vvSlicer::GetExtent() {
682   int *w_ext;
683   if (mUseReducedExtent) {
684     w_ext = mReducedExtent;
685   }
686   else w_ext = GetInput()->GetWholeExtent();
687   return w_ext;
688 }
689 //----------------------------------------------------------------------------
690
691
692 //----------------------------------------------------------------------------
693 int vvSlicer::GetOrientation() {
694   return this->SliceOrientation;
695 }
696 //----------------------------------------------------------------------------
697
698
699 //----------------------------------------------------------------------------
700 void vvSlicer::UpdateDisplayExtent()
701 {
702   vtkImageData *input = this->GetInput();
703   if (!input || !this->ImageActor)
704     {
705       return;
706     }
707   input->UpdateInformation();
708   int *w_ext;// = input->GetWholeExtent();
709
710   if (mUseReducedExtent) {
711     w_ext = mReducedExtent;
712   }
713   else w_ext = input->GetWholeExtent();
714
715   switch (this->SliceOrientation)
716     {
717     case vtkImageViewer2::SLICE_ORIENTATION_XY:
718       this->ImageActor->SetDisplayExtent(
719                                          w_ext[0], w_ext[1], w_ext[2], w_ext[3], this->Slice, this->Slice);
720       if (mVF && mVFActor->GetVisibility())
721         {
722           int vfExtent[6];
723           ComputeVFDisplayedExtent(w_ext[0], w_ext[1], w_ext[2], w_ext[3], this->Slice, this->Slice,vfExtent);
724           mVOIFilter->SetVOI(vfExtent);
725           mGlyphFilter->SetOrientation(1,1,0);
726           mVFMapper->Update();
727           // put the vector field between the image and the camera
728           if (Renderer->GetActiveCamera()->GetPosition()[2] > this->Slice)
729             mVFActor->SetPosition(0,0,ImageActor->GetBounds()[5]+2);
730           else
731             mVFActor->SetPosition(0,0,ImageActor->GetBounds()[4]-2);
732         }
733       if (mOverlay && mOverlayActor->GetVisibility())
734         {
735           int overExtent[6];
736           ComputeOverlayDisplayedExtent(w_ext[0], w_ext[1], w_ext[2], w_ext[3], this->Slice, this->Slice,overExtent);
737           mOverlayActor->SetDisplayExtent(overExtent);
738           if (Renderer->GetActiveCamera()->GetPosition()[2] > this->Slice)
739             mOverlayActor->SetPosition(0,0,1);
740           else
741             mOverlayActor->SetPosition(0,0,-1);
742         }
743       if (mFusion && mFusionActor->GetVisibility())
744         {
745           int fusExtent[6];
746           ComputeFusionDisplayedExtent(w_ext[0], w_ext[1], w_ext[2], w_ext[3], this->Slice, this->Slice,fusExtent);
747           mFusionActor->SetDisplayExtent(fusExtent);
748           if (Renderer->GetActiveCamera()->GetPosition()[2] > this->Slice)
749             mFusionActor->SetPosition(0,0,1.5);
750           else
751             mFusionActor->SetPosition(0,0,-1.5);
752         }
753       if (mLandActor)
754         {
755           if (mClipBox)
756             {
757               double bounds [6];
758               bounds[0] = ImageActor->GetBounds()[0];
759               bounds[1] = ImageActor->GetBounds()[1];
760               bounds[2] = ImageActor->GetBounds()[2];
761               bounds[3] = ImageActor->GetBounds()[3];
762               bounds[4] = ImageActor->GetBounds()[4]-(0.9/this->GetInput()->GetSpacing()[2]);
763               bounds[5] = ImageActor->GetBounds()[5]+(0.9/this->GetInput()->GetSpacing()[2]);
764               mClipBox->SetBounds(bounds);
765               UpdateLandmarks();
766             }
767           if (Renderer->GetActiveCamera()->GetPosition()[2] > this->Slice)
768             mLandActor->SetPosition(0,0,1.5);
769           else
770             mLandActor->SetPosition(0,0,-1.5);
771         }
772       break;
773
774     case vtkImageViewer2::SLICE_ORIENTATION_XZ:
775       this->ImageActor->SetDisplayExtent(
776                                          w_ext[0], w_ext[1], this->Slice, this->Slice, w_ext[4], w_ext[5]);
777       if (mVF && mVFActor->GetVisibility())
778         {
779           int vfExtent[6];
780           ComputeVFDisplayedExtent(w_ext[0], w_ext[1], this->Slice, this->Slice, w_ext[4], w_ext[5],vfExtent);
781           mVOIFilter->SetVOI(vfExtent);
782           mGlyphFilter->SetOrientation(1,0,1);
783           mVFMapper->Update();
784           // put the vector field between the image aSpacingnd the camera
785           if (Renderer->GetActiveCamera()->GetPosition()[1] > this->Slice)
786             mVFActor->SetPosition(0,ImageActor->GetBounds()[3]+2,0);
787           else
788             mVFActor->SetPosition(0,ImageActor->GetBounds()[2]-2,0);
789         }
790       if (mOverlay && mOverlayActor->GetVisibility())
791         {
792           int overExtent[6];
793           ComputeOverlayDisplayedExtent(w_ext[0], w_ext[1], this->Slice, this->Slice, w_ext[4], w_ext[5],overExtent);
794           mOverlayActor->SetDisplayExtent(overExtent);
795           if (Renderer->GetActiveCamera()->GetPosition()[1] > this->Slice)
796             mOverlayActor->SetPosition(0,1,0);
797           else
798             mOverlayActor->SetPosition(0,-1,0);
799         }
800       if (mFusion && mFusionActor->GetVisibility())
801         {
802           int fusExtent[6];
803           ComputeFusionDisplayedExtent(w_ext[0], w_ext[1], this->Slice, this->Slice, w_ext[4], w_ext[5],fusExtent);
804           mFusionActor->SetDisplayExtent(fusExtent);
805           if (Renderer->GetActiveCamera()->GetPosition()[1] > this->Slice)
806             mFusionActor->SetPosition(0,1.5,0);
807           else
808             mFusionActor->SetPosition(0,-1.5,0);
809         }
810       if (mLandActor)
811         {
812           if (mClipBox)
813             {
814               double bounds [6];
815               bounds[0] = ImageActor->GetBounds()[0];
816               bounds[1] = ImageActor->GetBounds()[1];
817               bounds[2] = ImageActor->GetBounds()[2]-(0.5/this->GetInput()->GetSpacing()[1]);
818               bounds[3] = ImageActor->GetBounds()[3]+(0.5/this->GetInput()->GetSpacing()[1]);
819               bounds[4] = ImageActor->GetBounds()[4];
820               bounds[5] = ImageActor->GetBounds()[5];
821               mClipBox->SetBounds(bounds);
822               UpdateLandmarks();
823             }
824           if (Renderer->GetActiveCamera()->GetPosition()[1] > this->Slice)
825             mLandActor->SetPosition(0,1.5,0);
826           else
827             mLandActor->SetPosition(0,-1.5,0);
828         }
829       break;
830
831     case vtkImageViewer2::SLICE_ORIENTATION_YZ:
832       this->ImageActor->SetDisplayExtent(
833                                          this->Slice, this->Slice, w_ext[2], w_ext[3], w_ext[4], w_ext[5]);
834       if (mVF && mVFActor->GetVisibility())
835         {
836           int vfExtent[6];
837           ComputeVFDisplayedExtent(this->Slice, this->Slice, w_ext[2], w_ext[3], w_ext[4], w_ext[5],vfExtent);
838           mVOIFilter->SetVOI(vfExtent);
839           mGlyphFilter->SetOrientation(0,1,1);
840           mVFMapper->Update();
841           // put the vector field between the image and the camera
842           if (Renderer->GetActiveCamera()->GetPosition()[0] > this->Slice)
843             mVFActor->SetPosition(ImageActor->GetBounds()[1]+2,0,0);
844           else
845             mVFActor->SetPosition(ImageActor->GetBounds()[0]-2,0,0);
846         }
847       if (mOverlay && mOverlayActor->GetVisibility())
848         {
849           int overExtent[6];
850           ComputeOverlayDisplayedExtent(this->Slice, this->Slice, w_ext[2], w_ext[3], w_ext[4], w_ext[5],overExtent);
851           mOverlayActor->SetDisplayExtent(overExtent);
852           if (Renderer->GetActiveCamera()->GetPosition()[0] > this->Slice)
853             mOverlayActor->SetPosition(1,0,0);
854           else
855             mOverlayActor->SetPosition(-1,0,0);
856         }
857       if (mFusion && mFusionActor->GetVisibility())
858         {
859           int fusExtent[6];
860           ComputeFusionDisplayedExtent(this->Slice, this->Slice, w_ext[2], w_ext[3], w_ext[4], w_ext[5],fusExtent);
861           mFusionActor->SetDisplayExtent(fusExtent);
862           if (Renderer->GetActiveCamera()->GetPosition()[0] > this->Slice)
863             mFusionActor->SetPosition(1.5,0,0);
864           else
865             mFusionActor->SetPosition(-1.5,0,0);
866         }
867       if (mLandActor)
868         {
869           if (mClipBox)
870             {
871               double bounds [6];
872               bounds[0] = ImageActor->GetBounds()[0]-(0.5/this->GetInput()->GetSpacing()[0]);
873               bounds[1] = ImageActor->GetBounds()[1]+(0.5/this->GetInput()->GetSpacing()[0]);
874               bounds[2] = ImageActor->GetBounds()[2];
875               bounds[3] = ImageActor->GetBounds()[3];
876               bounds[4] = ImageActor->GetBounds()[4];
877               bounds[5] = ImageActor->GetBounds()[5];
878               mClipBox->SetBounds(bounds);
879               UpdateLandmarks();
880             }
881           if (Renderer->GetActiveCamera()->GetPosition()[0] > this->Slice)
882             mLandActor->SetPosition(1.5,0,0);
883           else
884             mLandActor->SetPosition(-1.5,0,0);
885         }
886       break;
887     }
888
889   // Figure out the correct clipping range
890
891   if (this->Renderer)
892     {
893       if (this->InteractorStyle &&
894           this->InteractorStyle->GetAutoAdjustCameraClippingRange())
895         {
896           this->Renderer->ResetCameraClippingRange();
897         }
898       else
899         {
900           vtkCamera *cam = this->Renderer->GetActiveCamera();
901           if (cam)
902             {
903               double bounds[6];
904               this->ImageActor->GetBounds(bounds);
905               double spos = (double)bounds[this->SliceOrientation * 2];
906               double cpos = (double)cam->GetPosition()[this->SliceOrientation];
907               double range = fabs(spos - cpos);
908               double *spacing = input->GetSpacing();
909               double avg_spacing =
910                 ((double)spacing[0] + (double)spacing[1] + (double)spacing[2]) / 3.0;
911               cam->SetClippingRange(
912                                     range - avg_spacing * 3.0, range + avg_spacing * 3.0);
913             }
914         }
915     }
916 }
917 //----------------------------------------------------------------------------
918
919
920 //----------------------------------------------------------------------------
921 void vvSlicer::ComputeVFDisplayedExtent(int x1,int x2,int y1,int y2,int z1,int z2,int vfExtent[6])
922 {
923   vtkImageData* image=this->GetInput();
924   vfExtent[0] = (( image->GetOrigin()[0] + x1*image->GetSpacing()[0] ) - mVF->GetOrigin()[0]) /
925     mVF->GetSpacing()[0];
926   vfExtent[1] = (( image->GetOrigin()[0] + x2*image->GetSpacing()[0] ) - mVF->GetOrigin()[0]) /
927     mVF->GetSpacing()[0];
928   vfExtent[2] = (( image->GetOrigin()[1] + y1*image->GetSpacing()[1] ) - mVF->GetOrigin()[1]) /
929     mVF->GetSpacing()[1];
930   vfExtent[3] = (( image->GetOrigin()[1] + y2*image->GetSpacing()[1] ) - mVF->GetOrigin()[1]) /
931     mVF->GetSpacing()[1];
932   vfExtent[4] = (( image->GetOrigin()[2] + z1*image->GetSpacing()[2] ) - mVF->GetOrigin()[2]) /
933     mVF->GetSpacing()[2];
934   vfExtent[5] = (( image->GetOrigin()[2] + z2*image->GetSpacing()[2] ) - mVF->GetOrigin()[2]) /
935     mVF->GetSpacing()[2];
936
937   ClipDisplayedExtent(vfExtent,mVOIFilter->GetInput()->GetWholeExtent());
938 }
939 //----------------------------------------------------------------------------
940
941
942 //----------------------------------------------------------------------------
943 void vvSlicer::ComputeOverlayDisplayedExtent(int x1,int x2,int y1,int y2,int z1,int z2,int overExtent[6])
944 {
945   vtkImageData* image=this->GetInput();
946   overExtent[0] = (( image->GetOrigin()[0] + x1*image->GetSpacing()[0] ) - mOverlay->GetOrigin()[0]) /
947     mOverlay->GetSpacing()[0];
948   overExtent[1] = (( image->GetOrigin()[0] + x2*image->GetSpacing()[0] ) - mOverlay->GetOrigin()[0]) /
949     mOverlay->GetSpacing()[0];
950   overExtent[2] = (( image->GetOrigin()[1] + y1*image->GetSpacing()[1] ) - mOverlay->GetOrigin()[1]) /
951     mOverlay->GetSpacing()[1];
952   overExtent[3] = (( image->GetOrigin()[1] + y2*image->GetSpacing()[1] ) - mOverlay->GetOrigin()[1]) /
953     mOverlay->GetSpacing()[1];
954   overExtent[4] = (( image->GetOrigin()[2] + z1*image->GetSpacing()[2] ) - mOverlay->GetOrigin()[2]) /
955     mOverlay->GetSpacing()[2];
956   overExtent[5] = (( image->GetOrigin()[2] + z2*image->GetSpacing()[2] ) - mOverlay->GetOrigin()[2]) /
957     mOverlay->GetSpacing()[2];
958   ClipDisplayedExtent(overExtent, mOverlayMapper->GetInput()->GetWholeExtent());
959 }
960 //----------------------------------------------------------------------------
961
962
963 //----------------------------------------------------------------------------
964 void vvSlicer::ComputeFusionDisplayedExtent(int x1,int x2,int y1,int y2,int z1,int z2,int fusExtent[6])
965 {
966   vtkImageData* image=this->GetInput();
967   fusExtent[0] = (( image->GetOrigin()[0] + x1*image->GetSpacing()[0] ) - mFusion->GetOrigin()[0]) /
968     mFusion->GetSpacing()[0];
969   fusExtent[1] = (( image->GetOrigin()[0] + x2*image->GetSpacing()[0] ) - mFusion->GetOrigin()[0]) /
970     mFusion->GetSpacing()[0];
971   fusExtent[2] = (( image->GetOrigin()[1] + y1*image->GetSpacing()[1] ) - mFusion->GetOrigin()[1]) /
972     mFusion->GetSpacing()[1];
973   fusExtent[3] = (( image->GetOrigin()[1] + y2*image->GetSpacing()[1] ) - mFusion->GetOrigin()[1]) /
974     mFusion->GetSpacing()[1];
975   fusExtent[4] = (( image->GetOrigin()[2] + z1*image->GetSpacing()[2] ) - mFusion->GetOrigin()[2]) /
976     mFusion->GetSpacing()[2];
977   fusExtent[5] = (( image->GetOrigin()[2] + z2*image->GetSpacing()[2] ) - mFusion->GetOrigin()[2]) /
978     mFusion->GetSpacing()[2];
979   ClipDisplayedExtent(fusExtent, mFusionMapper->GetInput()->GetWholeExtent());
980 }
981 //----------------------------------------------------------------------------
982
983
984 //----------------------------------------------------------------------------
985 void vvSlicer::ClipDisplayedExtent(int extent[6], int refExtent[6])
986 {
987   bool out = false;
988   int maxBound = 6;
989
990   //2D overlay on 3D image specific case
991   if (refExtent[4] == refExtent[5])
992     {
993       maxBound = 4;
994       extent[4] = refExtent[4];
995       extent[5] = refExtent[5];
996     }
997
998   for (int i = 0; i < maxBound; i = i+2)
999     {
1000       //if we are totally outside the image
1001       if ( extent[i] > refExtent[i+1] || extent[i+1] < refExtent[i] )
1002         {
1003           out = true;
1004           break;
1005         }
1006       //crop to the limit of the image
1007       extent[i] = (extent[i] > refExtent[i]) ? extent[i] : refExtent[i];
1008       extent[i] = (extent[i] < refExtent[i+1]) ? extent[i] : refExtent[i+1];
1009       extent[i+1] = (extent[i+1] > refExtent[i]) ? extent[i+1] : refExtent[i];
1010       extent[i+1] = (extent[i+1] < refExtent[i+1]) ? extent[i+1] : refExtent[i+1];
1011     }
1012   if (out)
1013     for (int i = 0; i < maxBound; i = i+2)
1014       {
1015         extent[i] = refExtent[i];
1016         extent[i+1] = refExtent[i];
1017       }
1018 }
1019 //----------------------------------------------------------------------------
1020
1021
1022 //----------------------------------------------------------------------------
1023 void vvSlicer::UpdateOrientation()
1024 {
1025   // Set the camera position
1026   vtkCamera *cam = this->Renderer ? this->Renderer->GetActiveCamera() : NULL;
1027   if (cam)
1028     {
1029       switch (this->SliceOrientation)
1030         {
1031         case vtkImageViewer2::SLICE_ORIENTATION_XY:
1032           cam->SetFocalPoint(0,0,0);
1033           cam->SetPosition(0,0,-1); // -1 if medical ?
1034           cam->SetViewUp(0,-1,0);
1035           break;
1036
1037         case vtkImageViewer2::SLICE_ORIENTATION_XZ:
1038           cam->SetFocalPoint(0,0,0);
1039           cam->SetPosition(0,-1,0); // 1 if medical ?
1040           cam->SetViewUp(0,0,1);
1041           break;
1042
1043         case vtkImageViewer2::SLICE_ORIENTATION_YZ:
1044           cam->SetFocalPoint(0,0,0);
1045           cam->SetPosition(-1,0,0); // -1 if medical ?
1046           cam->SetViewUp(0,0,1);
1047           break;
1048         }
1049     }
1050 }
1051 //----------------------------------------------------------------------------
1052
1053
1054 //----------------------------------------------------------------------------
1055 void vvSlicer::SetOpacity(double s)
1056 {
1057   this->GetImageActor()->SetOpacity(s);
1058 }
1059 //----------------------------------------------------------------------------
1060
1061
1062 //----------------------------------------------------------------------------
1063 void vvSlicer::SetRenderWindow(int orientation, vtkRenderWindow * rw)
1064 {
1065   this->Superclass::SetRenderWindow(rw);
1066   this->SetupInteractor(rw->GetInteractor());
1067   ca->SetImageActor(this->GetImageActor());
1068   ca->SetWindowLevel(this->GetWindowLevel());
1069   ca->SetText(2, "<slice>");
1070   ca->SetText(3, "<window>\n<level>");
1071
1072   double bounds[6];
1073   double max = 65000;
1074
1075   bounds[0] = -max;
1076   bounds[1] = max;
1077   bounds[2] = -max;
1078   bounds[3] = max;
1079   bounds[4] = -max;
1080   bounds[5] = max;
1081
1082   crossCursor->SetModelBounds(bounds);
1083   this->GetRenderer()->AddActor(pdmA);
1084   this->GetRenderer()->AddActor(ca);
1085   this->GetRenderer()->ResetCamera();
1086
1087   //this is just a mapping between the labeling of the orientations presented to the user and
1088   //the one used by vtk
1089   SetSliceOrientation(2-(orientation%3));
1090   ResetCamera();
1091 }
1092 //----------------------------------------------------------------------------
1093
1094
1095 //----------------------------------------------------------------------------
1096 void vvSlicer::ResetCamera()
1097 {
1098   if (this->GetInput())
1099     {
1100       double* input_bounds=this->GetInput()->GetBounds();
1101       double bmax=input_bounds[1]-input_bounds[0];
1102       if (bmax < input_bounds[3]-input_bounds[2]) bmax=input_bounds[3]-input_bounds[2];
1103       if (bmax < input_bounds[5]-input_bounds[4]) bmax=input_bounds[5]-input_bounds[4];
1104       this->GetRenderer()->ResetCamera();
1105       this->GetRenderer()->GetActiveCamera()->SetParallelScale(bmax/2);
1106     }
1107 }
1108 //----------------------------------------------------------------------------
1109
1110
1111 //----------------------------------------------------------------------------
1112 void vvSlicer::SetDisplayMode(bool i)
1113 {
1114   this->GetImageActor()->SetVisibility(i);
1115   this->GetAnnotation()->SetVisibility(i);
1116   this->GetRenderer()->SetDraw(i);
1117   if (mLandActor)
1118     mLandActor->SetVisibility(i);
1119   pdmA->SetVisibility(i);
1120   if (i)
1121     UpdateDisplayExtent();
1122 }
1123 //----------------------------------------------------------------------------
1124
1125
1126 //----------------------------------------------------------------------------
1127 void vvSlicer::FlipHorizontalView()
1128 {
1129   vtkCamera *cam = this->Renderer ? this->Renderer->GetActiveCamera() : NULL;
1130   if (cam)
1131     {
1132       double *position = cam->GetPosition();
1133       switch (this->SliceOrientation)
1134         {
1135         case vtkImageViewer2::SLICE_ORIENTATION_XY:
1136           cam->SetPosition(position[0],position[1],-position[2]);
1137           break;
1138
1139         case vtkImageViewer2::SLICE_ORIENTATION_XZ:
1140           cam->SetPosition(position[0],-position[1],position[2]);
1141           break;
1142
1143         case vtkImageViewer2::SLICE_ORIENTATION_YZ:
1144           cam->SetPosition(-position[0],position[1],position[2]);
1145           break;
1146         }
1147       this->Renderer->ResetCameraClippingRange();
1148       this->UpdateDisplayExtent();
1149     }
1150 }
1151 //----------------------------------------------------------------------------
1152
1153
1154 //----------------------------------------------------------------------------
1155 void vvSlicer::FlipVerticalView()
1156 {
1157   vtkCamera *cam = this->Renderer ? this->Renderer->GetActiveCamera() : NULL;
1158   if (cam)
1159     {
1160       FlipHorizontalView();
1161       double *viewup = cam->GetViewUp();
1162       cam->SetViewUp(-viewup[0],-viewup[1],-viewup[2]);
1163       this->UpdateDisplayExtent();
1164     }
1165 }
1166 //----------------------------------------------------------------------------
1167
1168
1169 //----------------------------------------------------------------------------
1170 void vvSlicer::SetColorWindow(double window)
1171 {
1172   vtkLookupTable* LUT = static_cast<vtkLookupTable*>(this->GetWindowLevel()->GetLookupTable());
1173   if ( LUT )
1174     {
1175       double level = this->GetWindowLevel()->GetLevel();
1176       LUT->SetTableRange(level-fabs(window)/4,level+fabs(window)/4);
1177       LUT->Build();
1178     }
1179   this->vtkImageViewer2::SetColorWindow(window);
1180 }
1181 //----------------------------------------------------------------------------
1182
1183
1184 //----------------------------------------------------------------------------
1185 void vvSlicer::SetColorLevel(double level)
1186 {
1187   vtkLookupTable* LUT = static_cast<vtkLookupTable*>(this->GetWindowLevel()->GetLookupTable());
1188   if ( LUT )
1189     {
1190       double window = this->GetWindowLevel()->GetWindow();
1191       LUT->SetTableRange(level-fabs(window)/4,level+fabs(window)/4);
1192       LUT->Build();
1193     }
1194   this->vtkImageViewer2::SetColorLevel(level);
1195 }
1196 //----------------------------------------------------------------------------
1197
1198 //----------------------------------------------------------------------------
1199 // Returns the min an the max value in a 41x41 region around the mouse pointer
1200 void vvSlicer::GetExtremasAroundMousePointer(double & min, double & max)
1201 {
1202   //Get mouse pointer position in view coordinates
1203   double fLocalExtents[6];
1204   for(int i=0; i<3; i++)
1205     {
1206       fLocalExtents[i*2  ] = mCurrent[i];
1207       fLocalExtents[i*2+1] = mCurrent[i];
1208     }
1209   this->Renderer->WorldToView(fLocalExtents[0], fLocalExtents[2], fLocalExtents[4]);
1210   this->Renderer->WorldToView(fLocalExtents[1], fLocalExtents[3], fLocalExtents[5]);
1211   for(int i=0; i<3; i++)
1212     {
1213       if (i!=SliceOrientation) //SR: assumes that SliceOrientation is valid in ViewCoordinates (???)
1214         {
1215               fLocalExtents[i*2  ] -= 0.2;
1216               fLocalExtents[i*2+1] += 0.2;
1217         }
1218     }
1219   this->Renderer->ViewToWorld(fLocalExtents[0], fLocalExtents[2], fLocalExtents[4]);
1220   this->Renderer->ViewToWorld(fLocalExtents[1], fLocalExtents[3], fLocalExtents[5]);
1221
1222   //Convert to image pixel coordinates (rounded)
1223   int iLocalExtents[6];
1224   for(int i=0; i<3; i++)
1225     {
1226       fLocalExtents[i*2  ] = (fLocalExtents[i*2  ] - this->GetInput()->GetOrigin()[i])/this->GetInput()->GetSpacing()[i];
1227       fLocalExtents[i*2+1] = (fLocalExtents[i*2+1] - this->GetInput()->GetOrigin()[i])/this->GetInput()->GetSpacing()[i];
1228     
1229       iLocalExtents[i*2  ] = lrint(fLocalExtents[i*2  ]);
1230       iLocalExtents[i*2+1] = lrint(fLocalExtents[i*2+1]);
1231
1232       if(iLocalExtents[i*2  ]>iLocalExtents[i*2+1])
1233           std::swap(iLocalExtents[i*2], iLocalExtents[i*2+1]);
1234     }
1235
1236   vtkSmartPointer<vtkExtractVOI> voiFilter = vtkExtractVOI::New();
1237   voiFilter->SetInput(this->GetInput());
1238   voiFilter->SetVOI(iLocalExtents);
1239   voiFilter->Update();
1240   if (!voiFilter->GetOutput()->GetNumberOfPoints())
1241     {
1242       min = 0;
1243       max = 0;
1244       return;
1245     }
1246
1247   vtkSmartPointer<vtkImageAccumulate> accFilter = vtkImageAccumulate::New();
1248   accFilter->SetInput(voiFilter->GetOutput());
1249   accFilter->Update();
1250   
1251   min = *(accFilter->GetMin());
1252   max = *(accFilter->GetMax());
1253 }
1254 //----------------------------------------------------------------------------
1255
1256 //----------------------------------------------------------------------------
1257 void vvSlicer::Render()
1258 {
1259   //  DD("vvSlicer::Render");
1260   // DD(SliceOrientation);
1261   if (this->GetWindowLevel()->GetLookupTable() && !this->mOverlay && !this->mFusion)
1262     {
1263       legend->SetLookupTable(this->GetWindowLevel()->GetLookupTable());
1264       legend->SetVisibility(1);
1265     }
1266   else legend->SetVisibility(0);
1267
1268   if (ca->GetVisibility())
1269     {
1270       std::string worldPos = "";
1271       std::stringstream world1;
1272       std::stringstream world2;
1273       std::stringstream world3;
1274       world1 << (int)mCurrent[0];
1275       world2 << (int)mCurrent[1];
1276       world3 << (int)mCurrent[2];
1277       double X = (mCurrent[0] - this->GetInput()->GetOrigin()[0])/this->GetInput()->GetSpacing()[0];
1278       double Y = (mCurrent[1] - this->GetInput()->GetOrigin()[1])/this->GetInput()->GetSpacing()[1];
1279       double Z = (mCurrent[2] - this->GetInput()->GetOrigin()[2])/this->GetInput()->GetSpacing()[2];
1280
1281       if (pdmA->GetVisibility())
1282         {
1283           double x = mCursor[0];
1284           double y = mCursor[1];
1285           double z = mCursor[2];
1286           double xCursor = (x - this->GetInput()->GetOrigin()[0])/this->GetInput()->GetSpacing()[0];
1287           double yCursor = (y - this->GetInput()->GetOrigin()[1])/this->GetInput()->GetSpacing()[1];
1288           double zCursor = (z - this->GetInput()->GetOrigin()[2])/this->GetInput()->GetSpacing()[2];
1289
1290           if (xCursor >= this->GetImageActor()->GetDisplayExtent()[0] &&
1291               xCursor < this->GetImageActor()->GetDisplayExtent()[1]+1 &&
1292               yCursor >= this->GetImageActor()->GetDisplayExtent()[2] &&
1293               yCursor < this->GetImageActor()->GetDisplayExtent()[3]+1 &&
1294               zCursor >= this->GetImageActor()->GetDisplayExtent()[4] &&
1295               zCursor < this->GetImageActor()->GetDisplayExtent()[5]+1 )
1296             {
1297               vtkRenderer * renderer = this->Renderer;
1298
1299               renderer->WorldToView(x,y,z);
1300               renderer->ViewToNormalizedViewport(x,y,z);
1301               renderer->NormalizedViewportToViewport(x,y);
1302               renderer->ViewportToNormalizedDisplay(x,y);
1303               renderer->NormalizedDisplayToDisplay(x,y);
1304               crossCursor->SetFocalPoint(x,y,z);
1305             }
1306           else
1307             crossCursor->SetFocalPoint(-1,-1,z);
1308         }
1309
1310       if (X >= this->GetInput()->GetWholeExtent()[0] &&
1311           X <= this->GetInput()->GetWholeExtent()[1] &&
1312           Y >= this->GetInput()->GetWholeExtent()[2] &&
1313           Y <= this->GetInput()->GetWholeExtent()[3] &&
1314           Z >= this->GetInput()->GetWholeExtent()[4] &&
1315           Z <= this->GetInput()->GetWholeExtent()[5])
1316         {
1317           std::stringstream pixel1;
1318           std::stringstream pixel2;
1319           std::stringstream pixel3;
1320           std::stringstream temps;
1321           pixel1 << (int)X;
1322           pixel2 << (int)Y;
1323           pixel3 << (int)Z;
1324           temps << mCurrentTSlice;
1325           double value = this->GetInput()->GetScalarComponentAsDouble(lrint(X),
1326                                                                       lrint(Y),
1327                                                                       lrint(Z),0);
1328
1329           std::stringstream val;
1330           val << value;
1331           worldPos += "data value : " + val.str();
1332           worldPos += "\n mm : " + world1.str() + " " + world2.str() + " " + 
1333             world3.str() + " " + temps.str();
1334           worldPos += "\n pixel : " + pixel1.str() + " " + pixel2.str() + " " + 
1335             pixel3.str() + " " + temps.str();
1336         }
1337       ca->SetText(1,worldPos.c_str());
1338     }
1339   if (mOverlay && mOverlayActor->GetVisibility())
1340     {
1341       mOverlayMapper->SetWindow(this->GetColorWindow());
1342       mOverlayMapper->SetLevel(this->GetColorLevel());
1343       mOverlayMapper->Update();
1344     }
1345   if (mLandMapper)
1346     UpdateLandmarks();
1347   //this->Superclass::Render();
1348   this->GetRenderWindow()->Render();
1349 }
1350 //----------------------------------------------------------------------------
1351
1352
1353 //----------------------------------------------------------------------------
1354 void vvSlicer::UpdateCursorPosition()
1355 {
1356   if (this->GetImageActor()->GetVisibility())
1357     {
1358       pdmA->SetVisibility(true);
1359       mCursor[0] = mCurrent[0];
1360       mCursor[1] = mCurrent[1];
1361       mCursor[2] = mCurrent[2];
1362       mCursor[3] = mCurrentTSlice;
1363     }
1364 }
1365 //----------------------------------------------------------------------------
1366
1367
1368 //----------------------------------------------------------------------------
1369 void vvSlicer::UpdateLandmarks()
1370 {
1371   vtkPolyData *pd = static_cast<vtkPolyData*>(mLandClipper->GetInput());
1372   if (pd->GetPoints())
1373     {
1374       mLandGlyph->SetRange(0,1);
1375       mLandGlyph->Modified();
1376       mLandGlyph->Update();
1377
1378       mClipBox->Modified();
1379       mLandClipper->Update();
1380       mLandMapper->Update();
1381     }
1382
1383 }
1384 //----------------------------------------------------------------------------
1385
1386
1387 //----------------------------------------------------------------------------
1388 void vvSlicer::SetSlice(int slice)
1389 {
1390   int *range = this->GetSliceRange();
1391   if (range)
1392     {
1393       if (slice < range[0])
1394         {
1395           slice = range[0];
1396         }
1397       else if (slice > range[1])
1398         {
1399           slice = range[1];
1400         }
1401     }
1402
1403   if (this->Slice == slice)
1404     {
1405       return;
1406     }
1407
1408   this->Slice = slice;
1409   SetContourSlice();
1410   this->Modified();
1411   this->UpdateDisplayExtent();
1412
1413   //  DD("SetSlice de slicer = Render");
1414
1415   // Seems to work without this line
1416   //  this->Render();
1417 }
1418 //----------------------------------------------------------------------------
1419
1420
1421 //----------------------------------------------------------------------------
1422 void vvSlicer::SetContourSlice()
1423 {
1424   if (mSurfaceCutActors.size() > 0)
1425     for (std::vector<vvMeshActor*>::iterator i=mSurfaceCutActors.begin();
1426          i!=mSurfaceCutActors.end();i++)
1427       (*i)->SetCutSlice((this->Slice)*this->GetImage()->GetSpacing()[this->SliceOrientation]+
1428                         this->GetImage()->GetOrigin()[this->SliceOrientation]);
1429 }
1430 //----------------------------------------------------------------------------
1431
1432
1433 //----------------------------------------------------------------------------
1434 void vvSlicer::ForceUpdateDisplayExtent()
1435 {
1436   this->UpdateDisplayExtent();
1437 }
1438 //----------------------------------------------------------------------------
1439
1440
1441 //----------------------------------------------------------------------------
1442 int* vvSlicer::GetDisplayExtent()
1443 {
1444   return this->GetImageActor()->GetDisplayExtent();
1445 }
1446 //----------------------------------------------------------------------------
1447
1448
1449 //----------------------------------------------------------------------------
1450 void vvSlicer::PrintSelf(ostream& os, vtkIndent indent)
1451 {
1452   this->Superclass::PrintSelf(os, indent);
1453 }
1454 //----------------------------------------------------------------------------
1455
1456
1457    
1458    
1459
1460
1461