00001 
00010 #include <EDDSourceLib/inc/EDDImageDataSource.h>
00011 #include <EDDSourceLib/inc/EDDMsgLoop.h>
00012 #include <proto/EDDImageDataMsg.h>
00013 #include <stdio.h>
00014 #include <stdlib.h>
00015 #include <string.h>
00016 
00017 #if defined(WIN32)
00018 #define snprintf sprintf_s
00019 #else
00020 using namespace std;
00021 #endif
00022 
00023 static char* maFields[] =
00024 {
00025     "DESC",
00026     "X",
00027     "Y",
00028     "Z"
00029 };
00030         
00031 tcEDDImageDataSource::tcEDDImageDataSource(char* apDesc)
00032 : tcEDDDataSource()
00033 , mnImageNo(0)
00034 , mpOutputBuffer(0)
00035 , mnOutputBufferLen(0)
00036 {
00037     
00038     strncpy(maDescription, apDesc, gnMaxStringLen);
00039     snprintf(maXLabel, gnMaxStringLen, "X");    
00040     snprintf(maYLabel, gnMaxStringLen, "Y");    
00041     snprintf(maZLabel, gnMaxStringLen, "Z"); 
00042        
00043     
00044     RegisterWithMsgLoop();
00045 }
00046         
00047 tcEDDImageDataSource::~tcEDDImageDataSource(void)
00048 {
00049     UnRegisterWithMsgLoop();
00050     if (NULL != mpOutputBuffer)
00051     {
00052         delete [] mpOutputBuffer;
00053     }
00054 }
00055         
00056 int 
00057 tcEDDImageDataSource::HandleMsg(tsEDDMsgHdr* apMsg)
00058 {
00059     int rv = EDDMSG_OK;
00060     switch(apMsg->mnMsgId)
00061     {
00062         case EDDMSGID_SOURCEDESCREQMSG:
00063             {
00064                 char* maDescData[4];
00065                 maDescData[0] = maDescription;
00066                 maDescData[1] = maXLabel;
00067                 maDescData[2] = maYLabel;
00068                 maDescData[3] = maZLabel;
00069                 SendSourceDescMsg(maFields, maDescData, 4);
00070             }
00071             break;
00072         default:
00073             rv = EDDMSG_UNHANDLED;
00074             break;
00075     }
00076     return rv;
00077 }
00078 
00079 void 
00080 tcEDDImageDataSource::BuildOutputBuffer(void)
00081 {
00082     int maxlen = tcEDDMsgLoop::GetInstance()->GetMaxMessageLen(mnSourceId);
00083     if (maxlen < 0) maxlen = 1400;
00084     if (mnOutputBufferLen < maxlen)
00085     {
00086         mnOutputBufferLen = maxlen;
00087         if (NULL != mpOutputBuffer)
00088         {
00089             delete [] mpOutputBuffer;
00090         }
00091         mpOutputBuffer = new char[mnOutputBufferLen];
00092     }
00093 }
00094 
00095 void
00096 tcEDDImageDataSource::SendImageDescriptor(uint16_t anRows, uint16_t anCols, uint8_t anType, uint8_t anFlags)
00097 {
00098     tsEDDImageDescMsg* lpDescMsg = (tsEDDImageDescMsg*)mpOutputBuffer;
00099     
00100     lpDescMsg->mnImageNumber = mnImageNo;
00101     lpDescMsg->mnImageType   = anType;
00102     lpDescMsg->mnNumRows     = anRows;
00103     lpDescMsg->mnNumCols     = anCols;
00104     lpDescMsg->mnFlags       = anFlags;
00105     lpDescMsg->mnOffset[0]   = 0.0;
00106     lpDescMsg->mnOffset[1]   = 0.0;
00107     lpDescMsg->mnScale[0]    = 1.0;
00108     lpDescMsg->mnScale[1]    = 1.0;
00109     BuildHeader(&lpDescMsg->msHeader, EDDMSGID_IMAGEDESCMSG, sizeof(tsEDDImageDescMsg));
00110     tcEDDMsgLoop::GetInstance()->SendMsg(&lpDescMsg->msHeader);
00111 
00112 }
00113 
00114 int 
00115 tcEDDImageDataSource::SendSparseImageData(uint16_t anDefault, uint16_t anRows, uint16_t anCols,
00116                                               uint32_t* apImageOffset, uint16_t* apValue, uint16_t anNumPts,
00117                                               uint8_t anType)
00118 {
00119     return SendSparseData((void*)&anDefault, anRows, anCols, apImageOffset, apValue, anNumPts, sizeof(uint16_t), anType);
00120 }                                             
00121 
00122 int 
00123 tcEDDImageDataSource::SendSparseImageData(uint8_t anDefault, uint16_t anRows, uint16_t anCols,
00124                                               uint32_t* apImageOffset, uint8_t* apValue, uint16_t anNumPts,
00125                                               uint8_t anType)
00126 {
00127     return SendSparseData((void*)&anDefault, anRows, anCols, apImageOffset, apValue, anNumPts, sizeof(uint8_t), anType);    
00128 }                                            
00129 
00130 int
00131 tcEDDImageDataSource::SendSparseData(void* apDefault, uint16_t anRows, uint16_t anCols,
00132                                          uint32_t* apImageOffset, void* apValue, uint16_t anNumPts,
00133                                          int WordSizeBytes, uint8_t anType)
00134 {
00135     int rv = 0;
00136     
00137     
00138     if (!IsSubscribed())
00139     {
00140        return rv;
00141     }
00142 
00143     BuildOutputBuffer();
00144     
00145     
00146     SendImageDescriptor(anRows, anCols, anType, EDDIMGFLAGS_SPARSE);
00147 
00148     
00149     unsigned int MaxPixelsPerMsg = (mnOutputBufferLen-sizeof(tsEDDImageMsg)-WordSizeBytes) / (WordSizeBytes+sizeof(uint32_t));
00150     unsigned int pixels_sent = 0;
00151     while(pixels_sent < anNumPts)
00152     {
00153         tsEDDImageMsg* lpImageMsg    = (tsEDDImageMsg*)mpOutputBuffer;
00154         lpImageMsg->mnTotalPixels    = anNumPts;
00155         lpImageMsg->mnImageNumber    = mnImageNo;
00156         if (anNumPts-pixels_sent > MaxPixelsPerMsg)
00157         {
00158             lpImageMsg->mnNumPixels  = MaxPixelsPerMsg;
00159             lpImageMsg->mnStartPixel = pixels_sent;
00160         }
00161         else
00162         {
00163             lpImageMsg->mnNumPixels  = anNumPts-pixels_sent;
00164             lpImageMsg->mnStartPixel = anNumPts;
00165         }
00166         char* lpData = (char*)(lpImageMsg+1);
00167         
00168         memcpy(lpData, apImageOffset+pixels_sent, sizeof(uint32_t)*lpImageMsg->mnNumPixels);
00169         lpData += sizeof(uint32_t)*lpImageMsg->mnNumPixels;
00170         
00171         memcpy(lpData, (char*)apValue+pixels_sent*WordSizeBytes, WordSizeBytes*lpImageMsg->mnNumPixels);
00172         lpData += WordSizeBytes*lpImageMsg->mnNumPixels;
00173         
00174         memcpy(lpData, apDefault, WordSizeBytes);
00175         BuildHeader(&lpImageMsg->msHeader, EDDMSGID_IMAGEMSG, 
00176                     sizeof(tsEDDImageMsg)+WordSizeBytes*(1+lpImageMsg->mnNumPixels)+lpImageMsg->mnNumPixels*sizeof(uint32_t));
00177         tcEDDMsgLoop::GetInstance()->SendMsg(&lpImageMsg->msHeader);
00178         pixels_sent += lpImageMsg->mnNumPixels;
00179     }
00180     mnImageNo++;
00181         
00182     return rv;    
00183     
00184 }                                        
00185 
00186 int 
00187 tcEDDImageDataSource::SendImageData(uint8_t* apData, uint16_t anRows, uint16_t anCols, uint8_t anType)
00188 {
00189     return Send3DData(apData, anRows, anCols, sizeof(uint8_t), anType); 
00190 }
00191 
00192 int 
00193 tcEDDImageDataSource::SendImageData(uint16_t* apData, uint16_t anRows, uint16_t anCols, uint8_t anType)
00194 {   
00195     return Send3DData(apData, anRows, anCols, sizeof(uint16_t), anType); 
00196 }
00197 
00198 int
00199 tcEDDImageDataSource::Send3DData(void* apData, uint16_t anRows, uint16_t anCols, int WordSizeBytes, uint8_t anDataType)
00200 {
00201     int rv = 0;
00202     
00203     
00204     if (!IsSubscribed())
00205     {
00206        return rv;
00207     }
00208 
00209     BuildOutputBuffer();
00210     
00211     
00212     SendImageDescriptor(anRows, anCols, anDataType, 0);
00213     
00214     
00215     unsigned int MaxPixelsPerMsg = (mnOutputBufferLen-sizeof(tsEDDImageMsg)) / WordSizeBytes;
00216     unsigned int pixels_sent = 0;
00217     unsigned int total_pixels = anRows*anCols;
00218     while(pixels_sent < total_pixels)
00219     {
00220         tsEDDImageMsg* lpImageMsg    = (tsEDDImageMsg*)mpOutputBuffer;
00221         lpImageMsg->mnTotalPixels    = total_pixels;
00222         lpImageMsg->mnStartPixel     = pixels_sent;
00223         lpImageMsg->mnImageNumber    = mnImageNo;
00224         if (total_pixels-pixels_sent > MaxPixelsPerMsg)
00225         {
00226             lpImageMsg->mnNumPixels = MaxPixelsPerMsg;
00227         }
00228         else
00229         {
00230             lpImageMsg->mnNumPixels = total_pixels-pixels_sent;
00231         }
00232         void *lpData = (void*)(lpImageMsg+1);
00233         memcpy(lpData, (char*)apData+pixels_sent*WordSizeBytes, lpImageMsg->mnNumPixels*WordSizeBytes);
00234         BuildHeader(&lpImageMsg->msHeader, EDDMSGID_IMAGEMSG, 
00235                     sizeof(tsEDDImageMsg)+WordSizeBytes*lpImageMsg->mnNumPixels);
00236         tcEDDMsgLoop::GetInstance()->SendMsg(&lpImageMsg->msHeader);
00237         pixels_sent += lpImageMsg->mnNumPixels;
00238     }
00239     mnImageNo++;
00240         
00241     return rv;
00242     
00243 }
00244         
00245 int 
00246 tcEDDImageDataSource::SetLabel(teAxis aeAxis, char* apLabel)
00247 {
00248     char* lpPtr;
00249     switch (aeAxis)
00250     {
00251         case eeX:
00252             lpPtr = &maXLabel[0];
00253             break;
00254         case eeY:
00255             lpPtr = &maYLabel[0];
00256             break;
00257         case eeZ:
00258         default:
00259             lpPtr = &maZLabel[0];
00260             break;
00261     }
00262     strncpy(lpPtr, apLabel, gnMaxStringLen);
00263     return 0;
00264 }
00265 
00266 int 
00267 tcEDDImageDataSource::SetDescription(char* apDesc)
00268 {
00269     strncpy(maDescription, apDesc, gnMaxStringLen);
00270     return 0;
00271 }