00001
00002
00003
00004 #include "vtkActor.h"
00005 #include "vtkAppendFilter.h"
00006 #include "vtkCamera.h"
00007 #include "vtkCallbackCommand.h"
00008 #include "vtkCellArray.h"
00009 #include "vtkCylinderSource.h"
00010 #include "vtkClosePolyData.h"
00011 #include "vtkCommand.h"
00012 #include "vtkDoubleArray.h"
00013 #include "vtkExtractVOI.h"
00014 #include "vtkImageReader.h"
00015 #include "vtkImageViewer.h"
00016 #include "vtkImageViewer2.h"
00017 #include "vtkImageToStructuredPoints.h"
00018 #include "vtkImageThreshold.h"
00019 #include "vtkImageWriter.h"
00020 #include "vtkImageClip.h"
00021 #include "vtkImageResample.h"
00022 #include "vtkImageReslice.h"
00023 #include "vtkImageResample.h"
00024 #include "vtkImageThreshold.h"
00025 #include "vtkImageCast.h"
00026 #include "vtkImageData.h"
00027 #include "vtkMath.h"
00028 #include "vtkMarchingCubes.h"
00029 #include "vtkObjectFactory.h"
00030 #include "vtkPolyDataMapper.h"
00031 #include "vtkRenderer.h"
00032 #include "vtkRenderWindow.h"
00033 #include "vtkRenderWindowInteractor.h"
00034 #include "vtkPolyDataConnectivityFilter.h"
00035 #include "vtkProperty.h"
00036 #include "vtkPriorityQueue.h"
00037 #include "vtkPoints.h"
00038 #include "vtkPolyData.h"
00039 #include "vtkPolyDataMapper.h"
00040 #include "vtkPolyDataWriter.h"
00041 #include "vtkPolyDataReader.h"
00042 #include "vtkPointData.h"
00043 #include "vtkSphereSource.h"
00044 #include "vtkSTLWriter.h"
00045 #include "vtkStripper.h"
00046 #include "vtkTriangleFilter.h"
00047 #include "vtkTransform.h"
00048
00049 #include "wxPathologyWidget_01.h"
00050 #include "kernel/vtkOtsuSphereSource.h"
00051 #include <wx/splitter.h>
00052
00053
00054
00055
00056
00057
00058
00059 wxPathologyWidget_01::wxPathologyWidget_01(wxWindow *parent, marInterface* mar)
00060 : wxPanel( parent, -1)
00061 {
00062
00063
00064 _mar = mar;
00065 wxBoxSizer *sizer = new wxBoxSizer(wxVERTICAL );
00066 wxSplitterWindow *pnlSplitter = new wxSplitterWindow( this , -1);
00067 wxPanel *viewPanel = CreateViewPanel(pnlSplitter);
00068 wxPanel *controlPanel = CreateControlPanel(pnlSplitter);
00069
00070 sizer -> Add( pnlSplitter ,1,wxGROW ,0);
00071 pnlSplitter -> SetMinimumPaneSize( 150 );
00072 pnlSplitter -> SplitVertically( viewPanel, controlPanel, 600 );
00073 this -> SetSizer(sizer);
00074
00075
00076
00077
00078 stlInterna = NULL;
00079 stlExterna = NULL;
00080 stlImageData = NULL;
00081 workingDir = NULL;
00082
00083
00084 p1SphereSource = NULL;
00085 p1Mapper = NULL;
00086 p1Actor = NULL;
00087
00088 p2SphereSource = NULL;
00089 p2Mapper = NULL;
00090 p2Actor = NULL;
00091
00092 patSphereSource = NULL;
00093 patMapper = NULL;
00094 patActor = NULL;
00095
00096
00097 pathologyFrame = NULL;
00098
00099 patImageData = NULL;
00100 voiFilter = NULL;
00101 cubesFilter = NULL;
00102 dataMapper = NULL;
00103 dataActor = NULL;
00104
00105 outlineFilter = NULL;
00106 outlineMapper = NULL;
00107 outlineActor = NULL;
00108
00109
00110 p3SphereSource = NULL;
00111 p3Mapper = NULL;
00112 p3Actor = NULL;
00113
00114
00115 }
00116
00117 wxPathologyWidget_01::~wxPathologyWidget_01(){
00118
00119 }
00120
00121 wxPanel* wxPathologyWidget_01::CreateViewPanel(wxWindow *parent)
00122 {
00123 wxPanel *panel = new wxPanel(parent,-1);
00124 wxBoxSizer *sizer = new wxBoxSizer(wxVERTICAL);
00125 _maracasSurfaceWidget = new wxSurfaceWidget(panel);
00126 sizer->Add(_maracasSurfaceWidget , 1, wxEXPAND, 0);
00127 panel->SetSizer(sizer);
00128 panel->SetAutoLayout(true);
00129 panel->SetSize(400,400);
00130 panel->Layout();
00131 return panel;
00132 }
00133
00134 wxPanel* wxPathologyWidget_01::CreateControlPanel(wxWindow *parent)
00135 {
00136 wxPanel *panel = new wxPanel(parent,-1);
00137 wxFlexGridSizer *sizer = new wxFlexGridSizer(2);
00138
00139
00140
00141
00142 sizer->Add(new wxStaticText(panel,-1,_T(" ")));
00143 sizer->Add(new wxStaticText(panel,-1,_T(" ")));
00144 sizer->Add(new wxStaticText(panel,-1,_T(" - - - PATHOLOGY EXTRACTION - - - ")));
00145 sizer->Add(new wxStaticText(panel,-1,_T(" ")));
00146 wxButton *btnP1 = new wxButton(panel,-1,_T("Set P1"));
00147 wxButton *btnP2 = new wxButton(panel,-1,_T("Set P2"));
00148 wxButton *btnPat = new wxButton(panel,-1,_T("Set Region"));
00149 wxButton *btnExtract = new wxButton(panel,-1,_T("Extract Region"));
00150 wxButton *btnAxis = new wxButton(panel,-1, _T("Axis"));
00151 sizer->Add(btnP1);
00152 sizer->Add(btnP2);
00153 sizer->Add(btnPat);sizer->Add(new wxStaticText(panel,-1,_T(" ")));
00154 sizer->Add(btnExtract);sizer->Add(new wxStaticText(panel,-1,_T(" ")));
00155
00156 patSliderOpacity = new wxSlider( panel, -1, 50 , 0, 100, wxDefaultPosition, wxDefaultSize, wxSL_HORIZONTAL | wxSL_LABELS );
00157 sizer->Add(new wxStaticText(panel, -1,_T("Opacity Pathological VOI")));
00158 sizer->Add(patSliderOpacity);
00159 patSliderMarchingCubes = new wxSlider( panel, -1, 254 , 0, 1000, wxDefaultPosition, wxDefaultSize, wxSL_HORIZONTAL | wxSL_LABELS );
00160 sizer->Add(new wxStaticText(panel, -1,_T(" Marching Cubes Level Pathological VOI")));
00161 sizer->Add(patSliderMarchingCubes);
00162 sizer->Add(btnAxis);sizer->Add(new wxStaticText(panel,-1,_T(" ")));
00163
00164
00165
00166
00167
00168
00169 sizer->Add(new wxStaticText(panel,-1,_T(" ")));
00170 sizer->Add(new wxStaticText(panel,-1,_T(" ")));
00171 sizer->Add(new wxStaticText(panel,-1,_T(" - - - STL Diego - - - ")));
00172 sizer->Add(new wxStaticText(panel,-1,_T(" ")));
00173 stlSliderDeltaGauss = new wxSlider( panel, -1, 100 , 0, 300 , wxDefaultPosition, wxDefaultSize, wxSL_HORIZONTAL | wxSL_LABELS );
00174 stlSliderMarchingCubes= new wxSlider( panel, -1, 128 , 0, 256 , wxDefaultPosition, wxDefaultSize, wxSL_HORIZONTAL | wxSL_LABELS );
00175
00176 sizer->Add(new wxStaticText(panel,-1,_T(" Delta Gauss")));
00177 sizer->Add(stlSliderDeltaGauss);
00178
00179 sizer->Add(new wxStaticText(panel,-1,_T(" Marching Cubes Level")));
00180 sizer->Add(stlSliderMarchingCubes);
00181
00182 stlSliderOpacityInternal = new wxSlider(panel, -1, 100,0,100, wxDefaultPosition, wxDefaultSize, wxSL_HORIZONTAL | wxSL_LABELS);
00183 stlSliderOpacityExternal = new wxSlider(panel, -1, 100,0,100, wxDefaultPosition, wxDefaultSize, wxSL_HORIZONTAL | wxSL_LABELS);
00184
00185 sizer->Add(new wxStaticText(panel, -1,_T(" Opacity STL Internal")));
00186 sizer->Add(stlSliderOpacityInternal);
00187
00188 sizer->Add(new wxStaticText(panel, -1,_T(" Opacity STL External")));
00189 sizer->Add(stlSliderOpacityExternal);
00190
00191 wxButton *btnFileSTL = new wxButton(panel,-1,_T("Generate STL files"));
00192 sizer->Add(btnFileSTL);
00193 sizer->Add(new wxStaticText(panel,-1,_T(" ")));
00194
00195
00196
00197
00198
00199
00200
00201
00202
00203
00204 panel->SetSizer(sizer);
00205 panel->SetAutoLayout(true);
00206 panel->SetSize(400,600);
00207 panel->Layout();
00208
00209
00210
00211 Connect(btnP1->GetId(),wxEVT_COMMAND_BUTTON_CLICKED, (wxObjectEventFunction) &wxPathologyWidget_01::OnBtnSetP1);
00212 Connect(btnP2->GetId(),wxEVT_COMMAND_BUTTON_CLICKED, (wxObjectEventFunction) &wxPathologyWidget_01::OnBtnSetP2);
00213 Connect(btnPat->GetId(),wxEVT_COMMAND_BUTTON_CLICKED,(wxObjectEventFunction) &wxPathologyWidget_01::OnBtnSetPat);
00214 Connect(btnExtract->GetId(),wxEVT_COMMAND_BUTTON_CLICKED,(wxObjectEventFunction) &wxPathologyWidget_01::OnBtnExtractPat);
00215 Connect(patSliderOpacity->GetId(), wxEVT_COMMAND_SLIDER_UPDATED , (wxObjectEventFunction) &wxPathologyWidget_01::OnChangePatOpacity);
00216 Connect(patSliderMarchingCubes->GetId(), wxEVT_COMMAND_SLIDER_UPDATED , (wxObjectEventFunction) &wxPathologyWidget_01::OnChangePatMarchingCubes);
00217 Connect(btnAxis->GetId(), wxEVT_COMMAND_BUTTON_CLICKED , (wxObjectEventFunction) &wxPathologyWidget_01::OnBtnExtractAxis);
00218
00219
00220
00221
00222
00223
00224 Connect(btnFileSTL->GetId() , wxEVT_COMMAND_BUTTON_CLICKED , (wxObjectEventFunction) &wxPathologyWidget_01::OnBtnFileSTL );
00225 Connect(stlSliderDeltaGauss->GetId() , wxEVT_SCROLL_THUMBRELEASE , (wxObjectEventFunction) &wxPathologyWidget_01::OnChangeSTLGaussLevel );
00226 Connect(stlSliderMarchingCubes->GetId() , wxEVT_SCROLL_THUMBRELEASE , (wxObjectEventFunction) &wxPathologyWidget_01::OnChangeSTLMarchingCubesLevel);
00227 Connect(stlSliderOpacityInternal->GetId(), wxEVT_COMMAND_SLIDER_UPDATED , (wxObjectEventFunction) &wxPathologyWidget_01::OnOpacitySTLInternal);
00228 Connect(stlSliderOpacityExternal->GetId(), wxEVT_COMMAND_SLIDER_UPDATED , (wxObjectEventFunction) &wxPathologyWidget_01::OnOpacitySTLExternal);
00229
00230
00231
00232
00233
00234
00235 return panel;
00236 }
00237
00238 void wxPathologyWidget_01::Refresh()
00239 {
00240 _maracasSurfaceWidget->GetVtk3DSurfaceWidget()->Render();
00241 }
00242
00243
00244 void wxPathologyWidget_01::ConfigureVTK()
00245 {
00246 wxBusyCursor wait;
00247
00248 vtkImageData *imagedata = _mar->_experiment->getDynData( )->getVolume( )->castVtk();
00249
00250 _maracasSurfaceWidget->ShowMARACASData( _mar );
00251
00252
00253 this->ConfigureSTL();
00254 this->ConfigurePathologyExtraction();
00255
00256 }
00257
00258
00259 void wxPathologyWidget_01::ConfigureVTK(vtkImageData *imagedata, int x, int y, int z, double param){
00260
00261 this->px = x;
00262 this->py = y;
00263 this->pz = z;
00264
00265 wxBusyCursor wait;
00266 _maracasSurfaceWidget->ShowMARACASData( _mar );
00267
00268
00269
00270 this->ConfigureMPR();
00271 this->ConfigureSTL();
00272 this->ConfigurePathologyExtraction();
00273 }
00274
00275
00276
00277
00278
00279
00280
00281
00282
00283
00284
00285
00286
00287
00288 void wxPathologyWidget_01::ConfigureMPR(){
00289
00290 mprSphereSource = vtkSphereSource::New();
00291 mprMapper = vtkPolyDataMapper::New();
00292 mprActor = vtkActor::New();
00293
00294 mprMapper->SetInput(mprSphereSource->GetOutput());
00295 mprActor->SetMapper(mprMapper);
00296 mprActor->PickableOff( );
00297
00298 mprSphereSource->SetCenter(this->px,this->py,this->pz);
00299 mprSphereSource->SetRadius(2.5);
00300
00301 mprActor->GetProperty()->SetColor( 1.0, 0.0, 0.0 );
00302 vtkRenderer *ren = _maracasSurfaceWidget->GetVtk3DSurfaceWidget()->GetRenderer();
00303 ren->AddActor(mprActor);
00304
00305 }
00306
00307
00308
00309
00310
00311
00312
00313
00314
00315
00316
00317 void wxPathologyWidget_01::ConfigureSTL()
00318 {
00319 stlExterna = vtkPolyData::New();
00320 stlInterna = vtkPolyData::New();
00321
00322 dsm1 = vtkPolyDataMapper ::New();
00323 dsm1->SetInput (stlInterna);
00324 dsm1->ScalarVisibilityOff();
00325
00326 actorInternal = vtkActor::New();
00327 actorInternal->SetMapper (dsm1);
00328 actorInternal->GetProperty()->SetColor (0,1,0);
00329
00330 dsm2 = vtkPolyDataMapper ::New();
00331 dsm2->SetInput (stlExterna);
00332 dsm2->ScalarVisibilityOff();
00333
00334 actorExternal= vtkActor::New();
00335 actorExternal->SetMapper (dsm2);
00336 actorExternal->GetProperty()->SetRepresentationToWireframe();
00337 vtkRenderer *ren = _maracasSurfaceWidget->GetVtk3DSurfaceWidget()->GetRenderer();
00338 ren->AddActor(actorInternal);
00339 ren->AddActor(actorExternal);
00340
00341 stlExtractor = new vtkSTLExtractor();
00342 }
00343
00344 void wxPathologyWidget_01::generateSTLSurfaces()
00345 {
00346 stlExtractor->setVolume(stlImageData);
00347 stlExtractor->setSigmaLevel(stlDeltaGaussLevel);
00348 stlExtractor->setMarchingCubesLevel(stlMarchingCubesLevel);
00349 stlExtractor->calculate();
00350
00351 stlInterna->DeepCopy(stlExtractor->getInnerSurface());
00352 stlExterna->DeepCopy(stlExtractor->getOuterSurface());
00353 }
00354
00355
00356 void wxPathologyWidget_01::OnOpacitySTLExternal(wxScrollEvent& event){
00357 double value = ((double)stlSliderOpacityExternal->GetValue())/100;
00358 actorExternal->GetProperty( )->SetOpacity( value );
00359 Refresh();
00360 }
00361
00362
00363 void wxPathologyWidget_01::OnOpacitySTLInternal(wxScrollEvent& event){
00364 double value = ((double)stlSliderOpacityInternal->GetValue())/100;
00365 actorInternal->GetProperty( )->SetOpacity( value );
00366 Refresh();
00367 }
00368
00369 void wxPathologyWidget_01::OnBtnFileSTL(wxCommandEvent& event)
00370 {
00371 wxBusyCursor wait;
00372 wxString dirSTL = _mar->_parameters->getStringParam(
00373 marParameters::e_installation_directory );
00374 dirSTL = ( dirSTL == _T("NO_DIRECTORY") ) ? wxGetHomeDir( ) : dirSTL;
00375 wxDirDialog dialog( this, _T("Choose a directory..."), ( !dirSTL.IsEmpty( ) )?
00376 dirSTL: wxGetHomeDir( ) );
00377
00378 if( dialog.ShowModal( ) == wxID_OK )
00379 {
00380
00381
00382
00383
00384
00385 const char* fileprefix = "c:\\Creatis\\";
00386 std::string prefix = fileprefix;
00387
00388
00389
00390
00391 vtkTriangleFilter *filtro = vtkTriangleFilter::New();
00392 filtro->SetInput(stlInterna);
00393 vtkPolyDataConnectivityFilter *pdcf = vtkPolyDataConnectivityFilter::New();
00394 pdcf->SetInput( filtro->GetOutput() );
00395 vtkClosePolyData *cpd = vtkClosePolyData::New();
00396 cpd->SetInput( pdcf->GetOutput() );
00397
00398
00399 cpd->Update();
00400 vtkSTLWriter *writerI = vtkSTLWriter::New();
00401 writerI->SetInput( cpd->GetOutput() );
00402 prefix = fileprefix;
00403 prefix += "internal.stl";
00404 writerI->SetFileName(prefix.c_str());
00405 writerI->SetFileTypeToASCII();
00406 writerI->Write();
00407 writerI->Delete();
00408
00409
00410 filtro->SetInput(stlExterna);
00411 cpd->Update();
00412 vtkSTLWriter *writerE = vtkSTLWriter::New();
00413 writerE->SetInput( cpd->GetOutput() );
00414 prefix = fileprefix;
00415 prefix += "external.stl";
00416 writerE->SetFileName( prefix.c_str() );
00417 writerE->SetFileTypeToASCII();
00418 writerE->Write();
00419 writerE->Delete();
00420
00421 filtro->Delete();
00422 cpd->Delete();
00423 pdcf->Delete();
00424 }
00425
00426
00427 _mar->_parameters->setStringParam( marParameters::e_installation_directory, dialog.GetPath( ) );
00428 _mar->saveParameters( );
00429 }
00430
00431
00432 void wxPathologyWidget_01::OnChangeSTLGaussLevel(wxScrollEvent& event)
00433 {
00434 stlDeltaGaussLevel = ((double)stlSliderDeltaGauss->GetValue())/100;
00435 generateSTLSurfaces();
00436 Refresh();
00437 }
00438
00439
00440 void wxPathologyWidget_01::OnChangeSTLMarchingCubesLevel(wxScrollEvent& event)
00441 {
00442 stlMarchingCubesLevel = ((double)stlSliderMarchingCubes->GetValue());
00443 generateSTLSurfaces();
00444 Refresh();
00445
00446 }
00447
00448
00449
00450
00451
00452
00453
00454
00455
00456
00457
00458 double GetDistanciaEuclideana(double* a, double* b){
00459 return sqrt(((a[0]-b[0])*(a[0]-b[0]))+((a[1]-b[1])*(a[1]-b[1]))+((a[2]-b[2])*(a[2]-b[2])));
00460 }
00461
00462
00463 double GetValorPromedio(vtkImageData *data){
00464 int ext[6];
00465 int i, j, k;
00466 int numVoxels = 0;
00467 double promedio = 0;
00468 double valor;
00469
00470
00471 data->GetExtent(ext);
00472
00473
00474 for(i=ext[0];i<=ext[1];i++){
00475 for(j=ext[2];j<=ext[3];j++){
00476 for(k=ext[4];k<=ext[5];k++){
00477 valor =data->GetScalarComponentAsDouble(i,j,k,0);
00478 promedio += valor;
00479 numVoxels++;
00480 }
00481 }
00482 }
00483 return (double)promedio/(double)numVoxels;
00484 }
00485
00486
00487 void wxPathologyWidget_01::ConfigurePathologyExtraction()
00488 {
00489 }
00490
00491 void wxPathologyWidget_01::generatePathologySurface(){
00492
00493 }
00494
00495
00496 void wxPathologyWidget_01::OnBtnSetP1(wxCommandEvent &event){
00497 vtk3DSurfaceWidget *sw = _maracasSurfaceWidget->GetVtk3DSurfaceWidget();
00498
00499 if(p1Actor){
00500 sw->GetRenderer()->RemoveActor(p1Actor);
00501 }
00502
00503
00504 sw->GetSphereCenter(p1Center);
00505
00506 p1SphereSource = vtkSphereSource::New();
00507 p1Mapper = vtkPolyDataMapper::New();
00508 p1Actor = vtkActor::New();
00509
00510 p1Mapper->SetInput(p1SphereSource->GetOutput());
00511 p1Actor->SetMapper(p1Mapper);
00512 p1Actor->PickableOff( );
00513
00514 p1SphereSource->SetCenter(p1Center[0],p1Center[1],p1Center[2]);
00515 p1SphereSource->SetRadius(0.5);
00516
00517 p1Actor->GetProperty()->SetColor( 0.0, 1.0, 0.0);
00518
00519 sw->GetRenderer()->AddActor(p1Actor);
00520 Refresh();
00521
00522 }
00523
00524 void wxPathologyWidget_01::OnBtnSetP2(wxCommandEvent &event){
00525
00526 vtk3DSurfaceWidget *sw = _maracasSurfaceWidget->GetVtk3DSurfaceWidget();
00527
00528
00529 if(p2Actor){
00530 sw->GetRenderer()->RemoveActor(p1Actor);
00531 }
00532
00533 sw->GetSphereCenter(p2Center);
00534
00535 p2SphereSource = vtkSphereSource::New();
00536 p2Mapper = vtkPolyDataMapper::New();
00537 p2Actor = vtkActor::New();
00538
00539 p2Mapper->SetInput(p2SphereSource->GetOutput());
00540 p2Actor->SetMapper(p2Mapper);
00541 p2Actor->PickableOff( );
00542
00543 p2SphereSource->SetCenter(p2Center[0],p2Center[1],p2Center[2]);
00544 p2SphereSource->SetRadius(0.5);
00545
00546 p2Actor->GetProperty()->SetColor( 0.0, 1.0, 0.0);
00547
00548 sw->GetRenderer()->AddActor(p2Actor);
00549 Refresh();
00550 }
00551
00552
00553
00554
00555 void wxPathologyWidget_01::OnBtnSetPat(wxCommandEvent &event){
00556
00557 if (p2SphereSource == NULL || p1SphereSource == NULL){
00558 return;
00559 }
00560
00561 vtk3DSurfaceWidget *sw = _maracasSurfaceWidget->GetVtk3DSurfaceWidget();
00562
00563 if(patActor){
00564 sw->GetRenderer()->RemoveActor(patActor);
00565 }
00566
00567
00568 double centro[3];
00569
00570
00571 centro[0] = (p1Center[0] + p2Center[0]) / 2;
00572 centro[1] = (p1Center[1] + p2Center[1]) / 2;
00573 centro[2] = (p1Center[2] + p2Center[2]) / 2;
00574
00575 patSphereSource = vtkSphereSource::New();
00576 patMapper = vtkPolyDataMapper::New();
00577 patActor = vtkActor::New();
00578
00579 patMapper->SetInput(patSphereSource->GetOutput());
00580 patActor->SetMapper(patMapper);
00581
00582
00583 patSphereSource->SetCenter(centro[0],centro[1],centro[2]);
00584 patSphereSource->SetRadius(GetDistanciaEuclideana(p1Center,p2Center));
00585
00586 patActor->GetProperty()->SetColor( 0.15, 0.75, 0.15 );
00587 patActor->PickableOff( );
00588 patActor->GetProperty( )->SetOpacity(0.15);
00589
00590 sw->GetRenderer()->AddActor(patActor);
00591 Refresh();
00592 }
00593
00594
00595
00596
00597 void wxPathologyWidget_01::OnBtnExtractPat(wxCommandEvent &event){
00598
00599
00600
00601 vtkRenderer* renderer = _maracasSurfaceWidget->GetVtk3DSurfaceWidget()->GetRenderer();
00602
00603
00604
00605 vtkImageData* originalData = vtkImageData::New();
00606 originalData->DeepCopy(_mar->_experiment->getDynData()->getVolume()->castVtk());
00607
00608 double spacing[3];
00609 originalData->GetSpacing(spacing);
00610
00611 int extend[6];
00612 originalData->GetExtent(extend);
00613
00614
00615
00616
00617
00618
00619
00620 double p1crem[3], p2crem[3];
00621
00622 p1crem[0] = p1Center[0] / spacing[0];
00623 p1crem[1] = p1Center[1] / spacing[1];
00624 p1crem[2] = p1Center[2] / spacing[2];
00625
00626 p2crem[0] = p2Center[0] / spacing[0];
00627 p2crem[1] = p2Center[1] / spacing[1];
00628 p2crem[2] = p2Center[2] / spacing[2];
00629
00630
00631
00632
00633
00634
00635
00636 double radio = GetDistanciaEuclideana(p1crem,p2crem) / 2;
00637 double centro[3];
00638
00639 centro[0] = (p1crem[0] + p2crem[0]) / 2;
00640 centro[1] = (p1crem[1] + p2crem[1]) / 2;
00641 centro[2] = (p1crem[2] + p2crem[2]) / 2;
00642
00643
00644
00645
00646
00647 double lowX = centro[0] - (2*radio);
00648 double highX = centro[0] + (2*radio);
00649 double lowY = centro[1] - (2*radio);
00650 double highY = centro[1] + (2*radio);
00651 double lowZ = centro[2] - (2*radio);
00652 double highZ = centro[2] + (2*radio);
00653
00654
00655
00656
00657
00658
00659 voiFilter = vtkExtractVOI::New();
00660 voiFilter->SetInput(originalData);
00661 voiFilter->SetVOI((int)lowX, (int)highX, (int)lowY, (int)highY, (int)lowZ, (int)highZ);
00662 voiFilter->Update();
00663 patImageData = vtkImageData::New();
00664 patImageData->DeepCopy(voiFilter->GetOutput());
00665
00666
00667
00668
00669
00670
00671 vtkOtsuSphereSource *otsu = new vtkOtsuSphereSource();
00672 thresholdOTSU = otsu->calculateOptimalThreshold(patImageData);
00673
00674
00675
00676
00677
00678
00679 patMCLevel = 128.0;
00680 cubesFilter = vtkMarchingCubes::New();
00681 cubesFilter->SetInput(otsu->getImageForSegmentation());
00682 cubesFilter->SetValue(0,patMCLevel);
00683 cubesFilter->SetNumberOfContours(1);
00684
00685
00686
00687
00688
00689 polyUnico = vtkPolyDataConnectivityFilter::New();
00690 polyUnico->SetInput(cubesFilter->GetOutput());
00691 polyUnico->SetExtractionModeToLargestRegion();
00692
00693 stripper = vtkStripper::New();
00694 stripper->SetInput(polyUnico->GetOutput());
00695
00696
00697
00698
00699
00700
00701 dataMapper = vtkPolyDataMapper::New();
00702 dataMapper->SetInput(stripper->GetOutput());
00703 dataMapper->ScalarVisibilityOff();
00704
00705
00706
00707
00708
00709
00710 dataActor = vtkActor::New();
00711 dataActor->SetMapper(dataMapper);
00712 dataActor->SetPosition(lowX*spacing[0],lowY*spacing[1],lowZ*spacing[2]);
00713 dataActor->GetProperty()->SetOpacity(patOpacityLevel);
00714 dataActor->GetProperty()->SetColor( 0.20, 0.20, 1.0 );
00715 dataActor->GetProperty()->SetRepresentationToWireframe();
00716
00717 renderer->AddActor(dataActor);
00718
00719
00720
00721 outlineFilter = vtkOutlineFilter::New();
00722 outlineFilter->SetInput(voiFilter->GetOutput());
00723
00724 vtkPolyDataMapper* outlineMapper = vtkPolyDataMapper::New();
00725 outlineMapper->SetInput(outlineFilter->GetOutput());
00726
00727 if(outlineActor){
00728 renderer->RemoveActor(outlineActor);
00729 }
00730
00731 if(patActor){
00732 renderer->RemoveActor(patActor);
00733 }
00734
00735 if(p3Actor){
00736 renderer->RemoveActor(p3Actor);
00737 }
00738
00739
00740 outlineActor = vtkActor::New();
00741 outlineActor->SetMapper(outlineMapper);
00742 outlineActor->GetProperty()->SetOpacity(1);
00743
00744
00745
00746
00747
00748
00749
00750
00751
00752
00753
00754
00755
00756
00757
00758
00759
00760
00761
00762 Refresh();
00763 }
00764
00765
00766 void wxPathologyWidget_01::OnChangePatOpacity(wxScrollEvent& event){
00767 patOpacityLevel = ((double)patSliderOpacity->GetValue())/100.0;
00768 dataActor->GetProperty( )->SetOpacity(patOpacityLevel);
00769 Refresh();
00770 }
00771
00772 void wxPathologyWidget_01::OnChangePatMarchingCubes(wxScrollEvent& event){
00773 patMCLevel = ((double)patSliderMarchingCubes->GetValue());
00774 cubesFilter->SetValue(0,patMCLevel);
00775 cubesFilter->Update();
00776 Refresh();
00777 }
00778
00779
00780
00781
00782
00783 double GetDistanciaAPolydata(double* punto, vtkPoints* centers){
00784 double distancia = 0.0;
00785 double minima = 1e100;
00786 double vertice[3];
00787 int N = centers->GetNumberOfPoints();
00788
00789 for(int i = 0; i < N; i++){
00790 centers->GetPoint(i,vertice);
00791 distancia = sqrt(((punto[0]-vertice[0])*(punto[0]-vertice[0]))+((punto[1]-vertice[1])*(punto[1]-vertice[1]))+((punto[2]-vertice[2])*(punto[2]-vertice[2])));
00792
00793 if (distancia < minima){
00794 minima = distancia;
00795 }
00796 }
00797 return minima;
00798 }
00799
00800
00801 double GetProductoPunto(double* vectorA, double* vectorB){
00802 return (vectorA[0]*vectorB[0] + vectorA[1]*vectorB[1] + vectorA[2]*vectorB[2]);
00803 }
00804
00805
00806 double GetNormaVector(double* vector){
00807 return sqrt(GetProductoPunto(vector, vector));
00808 }
00809
00810
00811 void GetVector(double* p0, double* p1, double* resultado){
00812
00813 resultado[0] = p1[0] - p0[0];
00814 resultado[1] = p1[1] - p0[1];
00815 resultado[2] = p1[2] - p0[2];
00816
00817 }
00818
00819
00820 void VectorUnitario(double *v){
00821 double norma = GetNormaVector(v);
00822 v[0] = v[0] / norma;
00823 v[1] = v[1] / norma;
00824 v[2] = v[2] / norma;
00825 }
00826
00827
00828 void GetNormalCelda(double* p0, double* p1, double* p2, double* normal){
00829
00830 double U[3],V[3];
00831 GetVector(p1,p2,U);
00832 GetVector(p1,p0,V);
00833
00834
00835 normal[0] = (U[1]*V[2])-(U[2]*V[1]);
00836 normal[1] = -((U[0]*V[2])-(U[2]*V[0]));
00837 normal[2] = (U[0]*V[1])-(U[1]*V[0]);
00838 VectorUnitario(normal);
00839 }
00840
00841 void GetNormal(vtkPoints* puntosCelda, double* normal){
00842 double p0[3], p1[3], p2[3];
00843
00844 puntosCelda->GetPoint(0, p0);
00845 puntosCelda->GetPoint(1, p1);
00846 puntosCelda->GetPoint(2, p2);
00847
00848 GetNormalCelda(p0,p1,p2, normal);
00849 }
00850
00851
00852
00853 int GetClosestCellOnPolyData(double* punto, vtkPoints* centers){
00854 double distancia = 0.0;
00855 double minima = 1e100;
00856 int ID = -1;
00857 double vertice[3];
00858 int N = centers->GetNumberOfPoints();
00859
00860 for(int i = 0; i < N; i++){
00861 centers->GetPoint(i,vertice);
00862 distancia = sqrt(((punto[0]-vertice[0])*(punto[0]-vertice[0]))+((punto[1]-vertice[1])*(punto[1]-vertice[1]))+((punto[2]-vertice[2])*(punto[2]-vertice[2])));
00863
00864 if (distancia < minima){
00865 minima = distancia;
00866 ID = i;
00867 }
00868 }
00869
00870
00871 return ID;
00872 }
00873
00874 double GetProjectionOnNormal(double* vector, double* normal){
00875 double pp = GetProductoPunto(vector, normal);
00876 double vv = GetNormaVector(normal);
00877 double pr = pp / vv;
00878 return pr;
00879 }
00880
00881
00882
00883
00884
00885 void wxPathologyWidget_01::OnBtnExtractAxis(wxCommandEvent& event){
00886
00887
00888
00889
00890
00891
00892 vtkRenderer* renderer = _maracasSurfaceWidget->GetVtk3DSurfaceWidget()->GetRenderer();
00893
00894
00895
00896
00897 int extentOriginal[6];
00898 this->patImageData->GetExtent(extentOriginal);
00899
00900
00901
00902
00903
00904
00905 int factor = 1;
00906 double resampling = 1.0/(double)factor;
00907
00908
00909
00910
00911
00912 vtkImageResample* resamplingFilter = vtkImageResample::New();
00913 resamplingFilter->SetAxisOutputSpacing(0,resampling);
00914 resamplingFilter->SetAxisOutputSpacing(1,resampling);
00915 resamplingFilter->SetAxisOutputSpacing(2,resampling);
00916 resamplingFilter->ReleaseDataFlagOff();
00917 resamplingFilter->SetInput(patImageData);
00918 resamplingFilter->SetInterpolationModeToCubic();
00919 resamplingFilter->Update();
00920
00921
00922
00923
00924 vtkImageData* imagenRemuestreada = resamplingFilter->GetOutput();
00925 imagenRemuestreada->ReleaseDataFlagOff();
00926
00927
00928
00929
00930
00931
00932
00933 this->isoBinaria = vtkImageData::New();
00934 this->isoBinaria->CopyStructure(resamplingFilter->GetOutput());
00935 this->isoBinaria->SetScalarTypeToDouble();
00936
00937
00938
00939
00940
00941 int extentBinaria[6];
00942 this->isoBinaria->GetExtent(extentBinaria);
00943 int *dim = isoBinaria->GetDimensions();
00944
00945
00946
00947
00948
00949 int eX, eY, eZ, idpoint;
00950 double *ptr = NULL;
00951
00952 FILE* logger = freopen("tests.txt","w",stdout);
00953
00954
00955
00956 for(eX = extentBinaria[0]; eX <= extentBinaria[1]; eX++){
00957 for(eY = extentBinaria[2]; eY <= extentBinaria[3]; eY++){
00958 for (eZ = extentBinaria[4]; eZ <= extentBinaria[5]; eZ++){
00959 idpoint = isoBinaria->FindPoint(eX, eY, eZ);
00960 ptr = (double *)isoBinaria->GetScalarPointer(eX,eY,eZ);
00961 *ptr = 0;
00962 }
00963 }
00964 }
00965
00966
00967
00968
00969
00970 vtkPolyData *polyData= stripper->GetOutput();
00971
00972
00973 vtkPoints *puntosPolyData = polyData->GetPoints();
00974 vtkPointData *pointData = polyData->GetPointData();
00975
00976 vtkPolyDataWriter* writePoly = vtkPolyDataWriter::New();
00977 writePoly->SetFileName("poly.vtk");
00978 writePoly->SetInput(polyData);
00979 writePoly->Write();
00980
00981
00982
00983
00984
00985
00986 int numVertices = puntosPolyData->GetNumberOfPoints();
00987
00988
00989
00990 int j;
00991 double vertice[3];
00992
00993
00994
00995
00996
00997
00998
00999
01000
01001
01002
01003
01004
01005
01006
01007 vtkPolyDataNormals* polyNormalsFilter = vtkPolyDataNormals::New();
01008 polyNormalsFilter->SetInput(polyData);
01009 polyNormalsFilter->SplittingOn();
01010 polyNormalsFilter->ConsistencyOn();
01011 polyNormalsFilter->NonManifoldTraversalOn();
01012 polyNormalsFilter->ComputeCellNormalsOn();
01013 polyNormalsFilter->Update();
01014
01015
01016 vtkPolyData* polyDataConNormales = polyNormalsFilter->GetOutput();
01017
01018
01019
01020
01021
01022 vtkCellCenters* cellCentersFilter = vtkCellCenters::New();
01023 cellCentersFilter->SetInput(polyDataConNormales);
01024 cellCentersFilter->VertexCellsOn();
01025 cellCentersFilter->Update();
01026
01027 vtkPolyData* polydataCenters = cellCentersFilter->GetOutput();
01028 vtkPoints* polyCenterPoints = polydataCenters->GetPoints();
01029
01030 vtkPoints* puntosCelda = NULL;
01031 vtkIdList* lista = NULL;
01032 vtkCell* celda = NULL;
01033 double normal[3];
01034 int numCeldas = polyCenterPoints->GetNumberOfPoints();
01035
01036
01037 vtkPoints *normales = vtkPoints::New();
01038
01039 int i;
01040 for(i = 0; i < numCeldas ; i++){
01041
01042 polyCenterPoints->GetPoint(i,vertice);
01043
01044 celda = polyDataConNormales->GetCell(i);
01045 puntosCelda = celda->GetPoints();
01046 GetNormal(puntosCelda, normal);
01047 normales->InsertPoint(i, normal);
01048
01049
01050 lista = celda->GetPointIds();
01051 for(j = 0; j < lista->GetNumberOfIds(); j++){
01052 int idPunto = lista->GetId(j);
01053 puntosCelda->GetPoint(j, vertice);
01054
01055 }
01056
01057 }
01058
01059
01060
01061
01062
01063
01064
01065 double spacing[3];
01066 patImageData->GetSpacing(spacing);
01067
01068 double p1crem[3], p2crem[3];
01069
01070 p1crem[0] = p1Center[0] / spacing[0];
01071 p1crem[1] = p1Center[1] / spacing[1];
01072 p1crem[2] = p1Center[2] / spacing[2];
01073
01074 p2crem[0] = p2Center[0] / spacing[0];
01075 p2crem[1] = p2Center[1] / spacing[1];
01076 p2crem[2] = p2Center[2] / spacing[2];
01077
01078
01079
01080
01081
01082
01083
01084 double radio = GetDistanciaEuclideana(p1crem,p2crem) / 2;
01085 double centro[3];
01086
01087 centro[0] = (p1crem[0] + p2crem[0]) / 2;
01088 centro[1] = (p1crem[1] + p2crem[1]) / 2;
01089 centro[2] = (p1crem[2] + p2crem[2]) / 2;
01090
01091
01092
01093
01094
01095 double lowX = centro[0] - (2*radio);
01096 double highX = centro[0] + (2*radio);
01097 double lowY = centro[1] - (2*radio);
01098 double highY = centro[1] + (2*radio);
01099 double lowZ = centro[2] - (2*radio);
01100 double highZ = centro[2] + (2*radio);
01101
01102
01103
01104
01105
01106 int numeroPuntos = dim[0] * dim[1] * dim[2];
01107
01108
01109 int sem[3];
01110
01111
01112 sem[0] = (int)(p2Center[0]-(lowX*spacing[0]));
01113 sem[1] = (int)(p2Center[1]-(lowY*spacing[1]));
01114 sem[2] = (int)(p2Center[2]-(lowZ*spacing[2]));
01115
01116
01117 int idSemilla = isoBinaria->FindPoint(sem[0],sem[1],sem[2]);
01118
01119 if (idSemilla == -1) return;
01120
01121 int graphSize = (extentBinaria[1]-extentBinaria[0]) * (extentBinaria[3]-extentBinaria[2])*(extentBinaria[5]-extentBinaria[4]);
01122
01123
01124 vtkPriorityQueue *colaEvaluacion = vtkPriorityQueue::New();
01125
01126 colaEvaluacion->Allocate(graphSize);
01127
01128 colaEvaluacion->Insert(0, idSemilla);
01129
01130 vtkFloatingPointType prioridad;
01131
01132 int longitudCola = colaEvaluacion->GetNumberOfItems();
01133
01134
01135 int vecinoID = -1;
01136
01137 int puntoID = -1;
01138
01139 double* coordsVecino;
01140
01141 double* coordsPunto;
01142
01143 int cont=0;
01144
01145 vtkPoints *resultado = vtkPoints::New();
01146
01147 int premiere = 1;
01148
01149
01150 double centroCelda[3], vectorInterno[3], vectorNormal[3];
01151
01152 while(longitudCola > 0){
01153
01154
01155
01156
01157
01158 puntoID = colaEvaluacion->Pop(0,prioridad);
01159
01160 coordsPunto = isoBinaria->GetPoint(puntoID);
01161
01162
01163 ptr = (double *)isoBinaria->GetScalarPointer((int)(coordsPunto[0]*factor), (int)(coordsPunto[1]*factor), (int)(coordsPunto[2]*factor));
01164 *ptr = 255.0;
01165
01166 if(premiere == 1){
01167 vtkImageWriter* writeImage = vtkImageWriter::New();
01168 writeImage->SetInput(isoBinaria);
01169 writeImage->SetFileName("sem.vtk");
01170 writeImage->Write();
01171 premiere = 0;
01172 }
01173
01174 resultado->InsertPoint(cont, coordsPunto);
01175 cont++;
01176
01177
01178
01179
01180
01181
01182 int vk,vj,vi;
01183 for(vk = -1; vk<2; vk++) {
01184 for(vj = -1; vj<2; vj++) {
01185 for(vi = -1; vi<2; vi++) {
01186
01187 vecinoID = puntoID + (vk * dim[1]*dim[0]) + (vj * dim[0]) + vi;
01188
01189 if( vecinoID >= 0 && vecinoID < numeroPuntos && vecinoID != 0 && vecinoID != puntoID ) {
01190
01191 coordsVecino = isoBinaria->GetPoint(vecinoID);
01192
01193
01194 ptr = (double *)isoBinaria->GetScalarPointer((int)(coordsVecino[0]*factor),(int)(coordsVecino[1]*factor),(int)(coordsVecino[2]*factor));
01195
01196
01197
01198
01199 if (*ptr == 0){
01200
01201
01202 int normalID = GetClosestCellOnPolyData(coordsVecino, polyCenterPoints);
01203
01204
01205 polyCenterPoints->GetPoint(normalID,centroCelda);
01206 normales->GetPoint(normalID, vectorNormal);
01207
01208 GetVector(coordsVecino, centroCelda, vectorInterno);
01209 VectorUnitario(vectorInterno);
01210
01211 double projection = GetProjectionOnNormal(vectorInterno, vectorNormal);
01212 ptr = (double *)isoBinaria->GetScalarPointer((int)(coordsVecino[0]*factor),(int)(coordsVecino[1]*factor),(int)(coordsVecino[2]*factor));
01213
01214 if (projection > 0){
01215
01216
01217
01218
01219
01220
01221 colaEvaluacion->Insert(prioridad,vecinoID);
01222
01223 } else {
01224
01225
01226
01227
01228
01229
01230 *ptr = 0;
01231 }
01232 }
01233
01234 }
01235 }
01236 }
01237 }
01238
01239 longitudCola = colaEvaluacion->GetNumberOfItems();
01240 }
01241 colaEvaluacion->Delete();
01242
01243
01244
01245
01246
01247
01248 this->isoDistance = vtkImageEuclideanDistance::New();
01249 this->isoDistance->SetInput(this->isoBinaria);
01250 this->isoDistance->InitializeOn();
01251 this->isoDistance->Update();
01252 vtkImageData *imDistancias = isoDistance->GetOutput();
01253
01254
01255
01256
01257
01258 this->dijkstraFilter = vtkDijkstraImageData::New();
01259 this->dijkstraFilter->SetInput(isoDistance->GetOutput());
01260
01261 int idA = (int)isoBinaria->FindPoint(p1Center[0],p1Center[1], p1Center[2]);
01262 int idB = (int)isoBinaria->FindPoint(p2Center[0],p2Center[1], p2Center[2]);
01263
01264 dijkstraFilter->SourceID = idA;
01265 dijkstraFilter->SinkID = idB;
01266 dijkstraFilter->Update();
01267
01268 caminoMapper = vtkPolyDataMapper::New();
01269 caminoMapper->SetInput(dijkstraFilter->GetOutput());
01270 caminoMapper->ScalarVisibilityOff();
01271
01272 renderer->RemoveActor(dataActor);
01273
01274
01275
01276
01277 vtkIdList *camino = dijkstraFilter->GetShortestPathIdList();
01278
01279 int size = camino->GetNumberOfIds();
01280 double coords[3];
01281
01282
01283 for(i=0;i < size;i++){
01284 int pointId = camino->GetId(i);
01285 isoBinaria->GetPoint(pointId, coords);
01286 double scalar = imagenRemuestreada->GetPointData()->GetScalars()->GetTuple1(pointId);
01287
01288
01289
01290
01291 vtkSphereSource *_nodo = vtkSphereSource::New();
01292 _nodo->SetCenter(coords[0],coords[1],coords[2]);
01293 _nodo->SetRadius(0.2);
01294
01295 vtkPolyDataMapper *_mapper = vtkPolyDataMapper::New();
01296 _mapper->SetInput(_nodo->GetOutput());
01297
01298
01299 vtkActor *_actor = vtkActor::New();
01300 _actor->GetProperty()->SetColor( 0.8, 0.2, 0.3);
01301 _actor->SetMapper(_mapper);
01302 _actor->PickableOff( );
01303
01304 renderer->AddActor(_actor);
01305
01306
01307 }
01308
01309
01310 }
01311
01312
01313
01314
01315
01316