factor out Gvsp functionality to it's own class
[opengigevision:opengigevision.git] / Gvsp.h
1 #ifndef GVSP_H
2 #define GVSP_H
3
4 #include <arpa/inet.h>
5 #include <vigra/stdimage.hxx>
6 #include <asio.hpp>
7
8 class GvspReader
9 {
10   public:
11     GvspReader(asio::io_service& service, int nPort):
12         m_socket(service, asio::ip::udp::endpoint(asio::ip::udp::v4(), nPort)),
13         m_nCurrPartOfFrame(0),
14         m_nImg(0),
15         m_bRun(false)
16     {
17       StartReceive();
18     }
19
20     void Stop() { m_bRun = false; }
21
22   private:
23     void StartReceive()
24     {
25       m_bRun = true;
26       m_socket.async_receive_from(asio::buffer(m_buff), m_endpoint,
27                                   boost::bind(&GvspReader::RecHandler, this,
28                                               asio::placeholders::error,
29                                               asio::placeholders::bytes_transferred));
30     }
31
32     void RecHandler(const asio::error_code& error, std::size_t nBytes)
33     {
34       if (!error || error == asio::error::message_size)
35       {
36         uint16_t nPartOfFrame = ntohs(((uint16_t*)&m_buff)[3]);
37 //        std::cout << "Got data:" << nBytes << " bytes\tFrame# " << ntohl(((uint32_t*)&m_buff)[0])
38 //                  << "\tPart of frame# " << nPartOfFrame;
39
40         if(m_buff[4] == 0x01)
41         {
42           m_nCurrPartOfFrame = nPartOfFrame;
43           assert(m_nCurrPartOfFrame == 0);
44           uint16_t nWidth = ntohs(((uint16_t*)&m_buff)[13]);
45           uint16_t nHeight = ntohs(((uint16_t*)&m_buff)[15]);
46           std::cout << "\tHeader width: " << nWidth << "\theight: " << nHeight << std::endl;
47           m_img.resize(nWidth, nHeight);
48         }
49         else if(m_buff[4] == 0x03)
50         {
51           if(nPartOfFrame != m_nCurrPartOfFrame+1)
52             std::cout << "\n***Missing Package***" << std::endl;
53
54           m_nCurrPartOfFrame = nPartOfFrame;
55           int nPayloadSize = nBytes-8;
56           std::copy(m_buff.begin()+8, m_buff.begin() + nPayloadSize, m_img.begin()+nPartOfFrame*nPayloadSize);
57 //          std::cout << "\tData size" << nPayloadSize << std::endl;
58         }
59         else if(m_buff[4] == 0x02)
60         {
61           std::cout << "\tFooter" << std::endl;
62           vigra::exportImage(vigra::srcImageRange(m_img), vigra::ImageExportInfo(
63               str(boost::format("%|03|.png") % m_nImg++).c_str()));
64         }
65         else
66           std::cout << "\tUnknown frame" << std::endl;
67
68         if(m_bRun)
69           StartReceive();
70       }
71     }
72
73     asio::ip::udp::socket m_socket;
74     asio::ip::udp::endpoint m_endpoint;
75     boost::array<uint8_t, 2048> m_buff;
76     vigra::BImage m_img;
77     int m_nCurrPartOfFrame;
78     int m_nImg;
79     bool m_bRun;
80 };
81
82
83
84 #endif // GVSP_H