PlusLib  2.9.0
Software library for tracked ultrasound image acquisition, calibration, and processing.
vtkPlusUltravioletPCOUVCam.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 
6 Developed by ULL & IACTEC-IAC group
7 =========================================================Plus=header=end*/
8 
9 // Local includes
10 #include "PlusConfigure.h"
11 #include "vtkPlusChannel.h"
12 #include "vtkPlusDataSource.h"
14 
15 // VTK includes
16 #include <vtkImageData.h>
17 #include <vtkObjectFactory.h>
18 
19 // PCOUV
20 #include "pco_err.h"
21 #include "sc2_SDKStructures.h"
22 #include "SC2_SDKAddendum.h"
23 #include "SC2_CamExport.h"
24 #include "SC2_Defs.h"
25 
26 //----------------------------------------------------------------------------
27 
29 
30 //----------------------------------------------------------------------------
32 {
34  this->StartThreadForInternalUpdates = true;
35 }
36 
37 //----------------------------------------------------------------------------
39 {
40 }
41 
42 //----------------------------------------------------------------------------
43 void vtkPlusUltravioletPCOUVCam::PrintSelf(ostream& os, vtkIndent indent)
44 {
45  this->Superclass::PrintSelf(os, indent);
46  os << indent << "UltravioletPCOUVCam: PCO Ultraviolet Camera" << std::endl;
47 }
48 
49 //-----------------------------------------------------------------------------
50 PlusStatus vtkPlusUltravioletPCOUVCam::ReadConfiguration(vtkXMLDataElement* rootConfigElement)
51 {
52  XML_FIND_DEVICE_ELEMENT_REQUIRED_FOR_READING(deviceConfig, rootConfigElement);
53  LOG_DEBUG("Configure PCO Ultaviolet");
54 
55  const char* ExposureTimeString = deviceConfig->GetAttribute("ExposureTime");
56  const char* TimeBaseExposureString = deviceConfig->GetAttribute("TimeBaseExposure");
57  if (ExposureTimeString)
58  {
59  this->dwExposure = std::atoi(ExposureTimeString);
60  }
61  else
62  {
63  this->dwExposure = -1;
64  }
65 
66  if (TimeBaseExposureString)
67  {
68  this->wTimeBaseExposure = std::atoi(TimeBaseExposureString);
69  }
70  else
71  {
72  this->wTimeBaseExposure = -1;
73  }
74 
75  LOG_DEBUG("PCO Ultaviolet: ExposureTime = " << this->dwExposure << " TimeBaseExposure = " << this->wTimeBaseExposure);
76 
77  return PLUS_SUCCESS;
78 }
79 
80 //-----------------------------------------------------------------------------
81 PlusStatus vtkPlusUltravioletPCOUVCam::WriteConfiguration(vtkXMLDataElement* rootConfigElement)
82 {
83  XML_FIND_DEVICE_ELEMENT_REQUIRED_FOR_WRITING(deviceConfig, rootConfigElement);
84  return PLUS_SUCCESS;
85 }
86 
87 //----------------------------------------------------------------------------
89 {
90  if (freeze)
91  {
92  this->Disconnect();
93  }
94  else
95  {
96  this->Connect();
97  }
98  return PLUS_SUCCESS;
99 }
100 
101 //----------------------------------------------------------------------------
103 {
104  PCO_Description strDescription;
105  PCO_CameraType strCamType;
106  int iRet;
107  DWORD CameraWarning, CameraError, CameraStatus;
109  WORD RecordingState;
110  DWORD auxDelay;
111  DWORD auxExposure;
112  WORD auxTimeBaseDelay;
113  WORD auxTimeBaseExposure;
114 
115  this->cam = nullptr;
116 
117  iRet = PCO_OpenCamera(&(this->cam), 0);
118  if (iRet != PCO_NOERROR)
119  {
120  LOG_ERROR("PCO Ultraviolet: camera not detected.");
121  return PLUS_FAIL;
122  }
123  else {
124  LOG_DEBUG("PCO Ultraviolet: camera found.");
125  }
126  strDescription.wSize = sizeof(PCO_Description);
127  iRet = PCO_GetCameraDescription(this->cam, &strDescription);
128 
129  iRet = PCO_GetRecordingState(this->cam, &RecordingState);
130  if (RecordingState)
131  {
132  iRet = PCO_SetRecordingState(this->cam, 0);
133  }
134 
135  iRet = PCO_GetDelayExposureTime(this->cam, &(auxDelay), &(auxExposure), &(auxTimeBaseDelay), &(auxTimeBaseExposure));
136 
137  this->dwDelay = auxDelay;
138  if (this->dwExposure == -1) {
139  this->dwExposure = auxExposure;
140  }
141  this->wTimeBaseDelay = auxTimeBaseDelay;
142  if (this->wTimeBaseExposure == -1) {
143  this->wTimeBaseExposure = auxTimeBaseExposure;
144  }
145 
146  if ((iRet = PCO_SetDelayExposureTime(this->cam, this->dwDelay, this->dwExposure, this->wTimeBaseDelay, this->wTimeBaseExposure)) != 0) {
147  LOG_ERROR("PCO Ultraviolet: SetExposureTime (PCO_SetDelayExposureTime) failed with errorcode " << iRet);
148  return PLUS_FAIL;
149  }
150 
151  // Arm Camera before next Set...
152  iRet = PCO_ArmCamera(this->cam);
153 
154  iRet = PCO_GetCameraHealthStatus(this->cam, &CameraWarning, &CameraError, &CameraStatus);
155  if (CameraError != 0)
156  {
157  LOG_ERROR("PCO Ultraviolet: Camera has error status " << CameraError);
158  iRet = PCO_CloseCamera(this->cam);
159  return PLUS_FAIL;
160  }
161 
162  strCamType.wSize = sizeof(PCO_CameraType);
163  iRet = PCO_GetCameraType(this->cam, &strCamType);
164  if (iRet != PCO_NOERROR)
165  {
166  LOG_ERROR("PCO Ultraviolet: PCO_GetCameraType failed with errorcode " << iRet);
167  iRet = PCO_CloseCamera(this->cam);
168  return PLUS_FAIL;
169  }
170 
171  if (strCamType.wInterfaceType == INTERFACE_CAMERALINK)
172  {
173  PCO_SC2_CL_TRANSFER_PARAM cl_par;
174  iRet = PCO_GetTransferParameter(this->cam, (void*)&cl_par, sizeof(PCO_SC2_CL_TRANSFER_PARAM));
175  LOG_DEBUG("PCO Ultraviolet Camlink Settings: Baudrate=" << cl_par.baudrate << ", Clockfreq=" << cl_par.ClockFrequency << ", Dataformat=" << cl_par.DataFormat << ", Transmit=" << cl_par.Transmit);
176  }
177 
178  iRet = PCO_GetSizes(this->cam, &(this->XResAct), &(this->YResAct), &(this->XResMax), &(this->YResMax));
179  bufsize = (this->XResAct) * (this->YResAct) * sizeof(WORD);
180 
181  this->pImgBuf = nullptr;
182  this->BufNum = -1;
183 
184  iRet = PCO_AllocateBuffer(this->cam, &this->BufNum, this->bufsize, &(this->pImgBuf), &(this->BufEvent));
185  iRet = PCO_SetImageParameters(this->cam, this->XResAct, this->YResAct, IMAGEPARAMETERS_READ_FROM_SEGMENTS, NULL, 0);
186  return PLUS_SUCCESS;
187 }
188 
189 //----------------------------------------------------------------------------
191 {
192  int iRet;
193  iRet = PCO_CloseCamera(this->cam);
194  this->pImgBuf = nullptr;
195  return PLUS_SUCCESS;
196 }
197 
198 //----------------------------------------------------------------------------
200 {
201  int iRet;
202 
203  if (this->cam == nullptr)
204  {
205  LOG_ERROR("vtkPlusUltravioletPCOUVCam::InternalUpdate Unable to read date");
206  return PLUS_SUCCESS;
207  }
208 
209  iRet = PCO_SetRecordingState(this->cam, 1);
210 
211  iRet = PCO_GetImageEx(this->cam, 1, 0, 0, this->BufNum, this->XResAct, this->YResAct, 16);
212  if (iRet != PCO_NOERROR)
213  {
214  LOG_ERROR("vtkPlusUltravioletPCOUVCam::InternalUpdate Unable to receive frame");
215  return PLUS_SUCCESS;
216  }
217 
218  vtkPlusDataSource* aSource(nullptr);
219  if (this->GetFirstActiveOutputVideoSource(aSource) == PLUS_FAIL || aSource == nullptr)
220  {
221  LOG_ERROR("Unable to grab a video source. Skipping frame.");
222  return PLUS_FAIL;
223  }
224 
225  if (aSource->GetNumberOfItems() == 0)
226  {
227  // Init the buffer with the metadata from the first frame
228  aSource->SetImageType(US_IMG_BRIGHTNESS);
229  aSource->SetPixelType(VTK_UNSIGNED_SHORT);
230  aSource->SetNumberOfScalarComponents(1);
231  aSource->SetInputFrameSize(this->XResAct, this->YResAct, 1);
232  }
233 
234  // Add the frame to the stream buffer
235  FrameSizeType frameSize = { static_cast<unsigned int>(this->XResAct), static_cast<unsigned int>(this->YResAct), 1 };
236  if (aSource->AddItem(this->pImgBuf, aSource->GetInputImageOrientation(), frameSize, VTK_UNSIGNED_SHORT, 1, US_IMG_BRIGHTNESS, 0, this->FrameNumber) == PLUS_FAIL)
237  {
238  return PLUS_FAIL;
239  }
240 
241  this->FrameNumber++;
242 
243  return PLUS_SUCCESS;
244 }
245 
246 //----------------------------------------------------------------------------
248 {
249  if (this->OutputChannels.size() > 1)
250  {
251  LOG_WARNING("vtkPlusUltravioletPCOUVCam is expecting one output channel and there are " << this->OutputChannels.size() << " channels. First output channel will be used.");
252  }
253 
254  if (this->OutputChannels.empty())
255  {
256  LOG_ERROR("No output channels defined for vtkPlusUltravioletPCOUVCam. Cannot proceed.");
257  this->CorrectlyConfigured = false;
258  return PLUS_FAIL;
259  }
260  return PLUS_SUCCESS;
261 }
virtual void PrintSelf(ostream &os, vtkIndent indent) VTK_OVERRIDE
#define XML_FIND_DEVICE_ELEMENT_REQUIRED_FOR_WRITING(deviceConfig, rootConfigElement)
virtual PlusStatus InternalDisconnect() VTK_OVERRIDE
igsioStatus PlusStatus
Definition: PlusCommon.h:40
unsigned short WORD
Definition: ATC3DGm.h:450
PlusStatus SetInputFrameSize(unsigned int x, unsigned int y, unsigned int z)
virtual PlusStatus AddItem(vtkImageData *frame, US_IMAGE_ORIENTATION usImageOrientation, US_IMAGE_TYPE imageType, long frameNumber, double unfilteredTimestamp=UNDEFINED_TIMESTAMP, double filteredTimestamp=UNDEFINED_TIMESTAMP, const igsioFieldMapType *customFields=NULL)
bool RequireImageOrientationInConfiguration
PlusStatus SetImageType(US_IMAGE_TYPE imageType)
#define PLUS_FAIL
Definition: PlusCommon.h:43
PlusStatus WriteConfiguration(vtkXMLDataElement *config)
PlusStatus SetPixelType(igsioCommon::VTKScalarPixelType pixelType)
virtual PlusStatus Disconnect()
unsigned long DWORD
Definition: ATC3DGm.h:451
PlusStatus GetFirstActiveOutputVideoSource(vtkPlusDataSource *&aVideoSource)
unsigned long FrameNumber
#define PLUS_SUCCESS
Definition: PlusCommon.h:44
PlusStatus ReadConfiguration(vtkXMLDataElement *config)
virtual PlusStatus InternalConnect() VTK_OVERRIDE
Class for interfacing an PCO Ultraviolet capture device and recording frames into a Plus buffer.
virtual PlusStatus Connect()
#define XML_FIND_DEVICE_ELEMENT_REQUIRED_FOR_READING(deviceConfig, rootConfigElement)
virtual US_IMAGE_ORIENTATION GetInputImageOrientation()
bool StartThreadForInternalUpdates
virtual void PrintSelf(ostream &os, vtkIndent indent) VTK_OVERRIDE
ChannelContainer OutputChannels
PlusStatus SetNumberOfScalarComponents(unsigned int numberOfScalarComponents)
vtkStandardNewMacro(vtkPlusUltravioletPCOUVCam)
virtual int GetNumberOfItems()
bool CorrectlyConfigured
Interface to a 3D positioning tool, video source, or generalized data stream.