PlusLib  2.9.0
Software library for tracked ultrasound image acquisition, calibration, and processing.
vtkPlusGetPolydataCommand.cxx
Go to the documentation of this file.
1 /*=Plus=header=begin======================================================
2 Program: Plus
3 Copyright (c) Laboratory for Percutaneous Surgery. All rights reserved.
4 See License.txt for details.
5 =========================================================Plus=header=end*/
6 
7 // Local includes
8 #include "PlusConfigure.h"
9 #include "vtkPlusDataCollector.h"
11 
12 // VTK includes
13 #include <vtkOBJReader.h>
14 #include <vtkPLYReader.h>
15 #include <vtkPolyData.h>
16 #include <vtkPolyDataReader.h>
17 #include <vtkSTLReader.h>
18 
19 namespace
20 {
21  static const std::string GET_POLYDATA = "GetPolydata";
22 }
23 
25 
26 //----------------------------------------------------------------------------
28  : PolydataId("")
29 {
30 
31 }
32 
33 //----------------------------------------------------------------------------
35 {
36 }
37 
38 //----------------------------------------------------------------------------
39 void vtkPlusGetPolydataCommand::PrintSelf(ostream& os, vtkIndent indent)
40 {
41  this->Superclass::PrintSelf(os, indent);
42 }
43 
44 //----------------------------------------------------------------------------
46 {
47  // Get filename from attribute
48  if (aConfig->GetAttribute("FileName") != nullptr)
49  {
50  this->PolydataId = aConfig->GetAttribute("FileName");
51  }
52  else if (this->MetaData.find("FileName") != this->MetaData.end())
53  {
54  this->PolydataId = this->MetaData["FileName"].second;
55  }
56  else
57  {
58  LOG_ERROR("Unable to find FileName attribute or metadata in " << this->GetName() << " command.");
59  return PLUS_FAIL;
60  }
61 
62  return Superclass::ReadConfiguration(aConfig);
63 }
64 
65 //----------------------------------------------------------------------------
67 {
68  if (this->GetPolydataId().empty())
69  {
70  LOG_ERROR("PolydataId not set when WriteConfiguration was called.");
71  return PLUS_FAIL;
72  }
73  aConfig->SetAttribute("FileName", this->GetPolydataId().c_str());
74 
75  return Superclass::WriteConfiguration(aConfig);
76 }
77 
78 //----------------------------------------------------------------------------
79 void vtkPlusGetPolydataCommand::GetCommandNames(std::list<std::string>& cmdNames)
80 {
81  cmdNames.clear();
82  cmdNames.push_back(GET_POLYDATA);
83 }
84 
85 //----------------------------------------------------------------------------
86 std::string vtkPlusGetPolydataCommand::GetDescription(const std::string& commandName)
87 {
88  std::string desc;
89  if (commandName.empty() || igsioCommon::IsEqualInsensitive(commandName, GET_POLYDATA))
90  {
91  desc += GET_POLYDATA;
92  desc += "Acquire the polydata.";
93  }
94  return desc;
95 }
96 
97 //----------------------------------------------------------------------------
99 {
100  SetName(GET_POLYDATA);
101 }
102 
103 //----------------------------------------------------------------------------
105 {
106  std::string baseMessage = std::string("vtkPlusGetPolydataCommand ") + (!this->Name.empty() ? this->Name : "(undefined)")
107  + ", device: (" + (this->GetPolydataId().empty() ? "(undefined)" : this->GetPolydataId()) + ")";
108 
109  std::string errorString;
110  if (igsioCommon::IsEqualInsensitive(this->Name, GET_POLYDATA))
111  {
112  if (this->ExecutePolydataReply(errorString) != PLUS_SUCCESS)
113  {
114  return PLUS_FAIL;
115  }
116  return PLUS_SUCCESS;
117  }
118  this->QueueCommandResponse(PLUS_FAIL, baseMessage + " Failed. See error message.", std::string("Unknown command name: ") + this->Name);
119  return PLUS_FAIL;
120 }
121 
122 //----------------------------------------------------------------------------
124 {
125  bool loaded(false);
126 
127  vtkSmartPointer<vtkPolyDataReader> reader = vtkSmartPointer<vtkPolyDataReader>::New();
128 
129  std::string finalFileName(this->PolydataId);
130  if (vtksys::SystemTools::FileExists(this->PolydataId))
131  {
132  reader->SetFileName(this->PolydataId.c_str());
133  }
134  else
135  {
136  if (vtkPlusConfig::GetInstance()->FindModelPath(this->PolydataId, finalFileName) == PLUS_SUCCESS)
137  {
138  reader->SetFileName(finalFileName.c_str());
139  }
140  else
141  {
142  LOG_ERROR("Unable to locate file with name " << this->PolydataId);
143  this->QueueCommandResponse(PLUS_FAIL, "Command failed.", std::string("Unable to locate file with name ") + this->PolydataId);
144  return PLUS_FAIL;
145  }
146  }
147 
148  vtkSmartPointer<vtkAbstractPolyDataReader> polyReader = vtkSmartPointer<vtkSTLReader>::New();
149  if (!reader->IsFilePolyData())
150  {
151  reader = nullptr; // This flags later code to recognize that it's not a .vtk file
152  polyReader->SetFileName(finalFileName.c_str());
153  polyReader->Update();
154  if (polyReader->GetOutput() == nullptr)
155  {
156  polyReader = vtkSmartPointer<vtkOBJReader>::New();
157  polyReader->SetFileName(finalFileName.c_str());
158  polyReader->Update();
159  if (polyReader->GetOutput() == nullptr)
160  {
161  polyReader = vtkSmartPointer<vtkPLYReader>::New();
162  polyReader->SetFileName(finalFileName.c_str());
163  polyReader->Update();
164  if (polyReader->GetOutput() == nullptr)
165  {
166  LOG_ERROR("Unrecognized polydata file type: " << this->PolydataId);
167  this->QueueCommandResponse(PLUS_FAIL, "Command failed.", std::string("Unrecognized polydata file type: ") + this->PolydataId);
168  return PLUS_FAIL;
169  }
170  }
171  }
172  }
173  else
174  {
175  reader->Update();
176  }
177 
178  auto errorCode = (reader == nullptr ? polyReader->GetErrorCode() : reader->GetErrorCode());
179  vtkPolyData* polyData = (reader == nullptr ? polyReader->GetOutput() : reader->GetOutput());
180  if (errorCode != 0)
181  {
182  std::stringstream ss;
183  ss << "Reader threw error: " << errorCode;
184  this->QueueCommandResponse(PLUS_FAIL, "PlusServer", ss.str());
185  }
186  else if (polyData != nullptr)
187  {
188  vtkSmartPointer<vtkPlusCommandPolydataResponse> response = vtkSmartPointer<vtkPlusCommandPolydataResponse>::New();
189  response->SetClientId(this->ClientId);
190  response->SetPolyDataName(this->GetPolydataId());
191  response->SetPolyData(polyData);
192  response->SetRespondWithCommandMessage(this->RespondWithCommandMessage);
193  this->CommandResponseQueue.push_back(response);
194 
195  std::string name = vtksys::SystemTools::GetFilenameName(this->PolydataId);
196  this->QueueCommandResponse(PLUS_SUCCESS, name, "Command succeeded.");
197  return PLUS_SUCCESS;
198  }
199 
200  this->QueueCommandResponse(PLUS_FAIL, "Unable to load polydata.");
201  return PLUS_FAIL;
202 }
virtual void GetCommandNames(std::list< std::string > &cmdNames)
virtual void PrintSelf(ostream &os, vtkIndent indent)
virtual PlusStatus WriteConfiguration(vtkXMLDataElement *aConfig)
std::string Name
const char ** errorString
Definition: phidget22.h:1270
igsioStatus PlusStatus
Definition: PlusCommon.h:40
virtual PlusStatus ReadConfiguration(vtkXMLDataElement *aConfig)
virtual void PrintSelf(ostream &os, vtkIndent indent)
PlusStatus ExecutePolydataReply(std::string &outErrorString)
virtual std::string GetDescription(const std::string &commandName)
#define PLUS_FAIL
Definition: PlusCommon.h:43
static vtkPlusConfig * GetInstance()
#define PLUS_SUCCESS
Definition: PlusCommon.h:44
bool RespondWithCommandMessage
igtl::MessageBase::MetaDataMap MetaData
void QueueCommandResponse(PlusStatus status, const std::string &message, const std::string &error="", const igtl::MessageBase::MetaDataMap *metaData=nullptr)
PlusStatus FindModelPath(const std::string &aModelPath, std::string &aFoundAbsolutePath)
This command is used to answer the OpenIGTLink message GET_POLYDATA. GET_POLYDATA returns the request...
virtual PlusStatus WriteConfiguration(vtkXMLDataElement *aConfig)
vtkStandardNewMacro(vtkPlusGetPolydataCommand)
PlusCommandResponseList CommandResponseQueue
virtual PlusStatus ReadConfiguration(vtkXMLDataElement *aConfig)