C++ rosserial发布传感器\u msgs/来自windows的图像

C++ rosserial发布传感器\u msgs/来自windows的图像,c++,windows,image,kinect,ros,C++,Windows,Image,Kinect,Ros,我正在使用windows和kinect v1传感器的sdk进行一个项目。目标是通过ros从kinect发送彩色图像, 我不知道该怎么办。现在我正在使用该消息发布RGB值。这是我目前掌握的代码: img.header.stamp = nh->now(); img.header.frame_id = "kinect1_ref"; img.height = height; img.width = width; img.encoding =

我正在使用windows和kinect v1传感器的sdk进行一个项目。目标是通过ros从kinect发送彩色图像,

我不知道该怎么办。现在我正在使用该消息发布RGB值。这是我目前掌握的代码:

    img.header.stamp = nh->now();
    img.header.frame_id = "kinect1_ref";
    img.height = height;
    img.width = width;        
    img.encoding = "rgb8";
    img.is_bigendian = false;
    img.step = width*3;

    BYTE* start = (BYTE*) lockedRect.pBits;
    img.data = new uint8_t[width*3*height];



    long it;
    for (int y = 0; y < height; ++y) {
        for (int x = 0; x < width; ++x) {
            const BYTE* curr = start + (x + width*y)*4;
            for(int n=0; n<3; n++){
                it = y*width*3 + x*3 + n;
                img.data[it] =  (uint8_t) curr[2-n];
            }
        }
    }   
    pub->publish(&img);

这里没有写序列化和反序列化这两种方法,但我实际上不知道它们是如何工作的。

我想知道这是如何编译的
img.data
是一个
std::vector
。话虽如此,请尝试以下方法:

img.header.stamp = nh->now();
img.header.frame_id = "kinect1_ref";
img.height = height;
img.width = width;        
img.encoding = "rgb8";
img.is_bigendian = false;
img.step = width * 3;

BYTE* start = (BYTE*) lockedRect.pBits;
img.data.resize(img.step * height);

long it;
for (int y = 0; y < height; ++y) {
    for (int x = 0; x < width; ++x) {
        const BYTE* curr = start + (x + width*y)*4;
        for(int n=0; n<3; n++){
            it = y*width*3 + x*3 + n;
            img.data[it] =  (uint8_t) curr[2-n];
        }
    }
}   
pub->publish(&img);
img.header.stamp=nh->now();
img.header.frame\u id=“kinect1\u ref”;
img.height=高度;
img.width=宽度;
img.encoding=“rgb8”;
img.is_bigendian=false;
img.step=宽度*3;
字节*开始=(字节*)lockedRect.pBits;
img.data.resize(img.step*高度);
长此以往;
对于(int y=0;y
更新


我发现了有关
rosserial_windows
限制中使用的协议的这些信息。虽然您指定了高度、宽度和步长,但是序列化对于这些消息变量来说是不可知的。我似乎还必须在
data_lendth
中指定数组的长度。但问题在于此eason最大数组长度限制为
uint8\u t

任何数组类型T[]的数组长度都需要设置变量T_length。这意味着您不能在不更改协议的情况下超过
uint8_T
限制


一个解决方案是将图像分割成255字节的自定义消息并对其进行索引。你必须将图像数据放在接收器端,从数据中创建一个传感器图像并发布。

我想知道这对你来说是如何编译的。
img.data
是一个
std::vector
是:

img.header.stamp = nh->now();
img.header.frame_id = "kinect1_ref";
img.height = height;
img.width = width;        
img.encoding = "rgb8";
img.is_bigendian = false;
img.step = width * 3;

BYTE* start = (BYTE*) lockedRect.pBits;
img.data.resize(img.step * height);

long it;
for (int y = 0; y < height; ++y) {
    for (int x = 0; x < width; ++x) {
        const BYTE* curr = start + (x + width*y)*4;
        for(int n=0; n<3; n++){
            it = y*width*3 + x*3 + n;
            img.data[it] =  (uint8_t) curr[2-n];
        }
    }
}   
pub->publish(&img);
img.header.stamp=nh->now();
img.header.frame\u id=“kinect1\u ref”;
img.height=高度;
img.width=宽度;
img.encoding=“rgb8”;
img.is_bigendian=false;
img.step=宽度*3;
字节*开始=(字节*)lockedRect.pBits;
img.data.resize(img.step*高度);
长此以往;
对于(int y=0;y
更新


我发现了有关
rosserial_windows
限制中使用的协议的这些信息。虽然您指定了高度、宽度和步长,但是序列化对于这些消息变量来说是不可知的。我似乎还必须在
data_lendth
中指定数组的长度。但问题在于此eason最大数组长度限制为
uint8\u t

任何数组类型T[]的数组长度都需要设置变量T_length。这意味着您不能在不更改协议的情况下超过
uint8_T
限制


一个解决方案是将图像分割成255字节的自定义消息并编制索引。你必须将图像数据放在接收器端,从数据中创建一个sensor_msgs::image并发布该图像。

首先,多亏了cassinaj,我认为解决方案将是他提出的答案。我将添加我为处于相同情况的人找到的一些信息

rosserial中数组的限制由
uint8_t
给出,在大多数ros发行版中,该限制最大为255字节。但是,该问题已在本文中进行了评论,其中建议将该值增加到
uint32_t
。因此,如果您从r在Jade中,数据的长度应为
uint32\u t
。这是图像消息的生成代码:

  class Image : public ros::Msg
  {
  public:
    std_msgs::Header header;
    uint32_t height;
    uint32_t width;
    const char* encoding;
    uint8_t is_bigendian;
    uint32_t step;
    uint32_t data_length;
    uint8_t st_data;
    uint8_t * data;
  Image():
    header(),
    height(0),
    width(0),
    encoding(""),
    is_bigendian(0),
    step(0),
    data_length(0), data(NULL)
{
}
 virtual int serialize(unsigned char *outbuffer) const
 virtual int deserialize(unsigned char *inbuffer)
我本来希望现在一切正常,但出现了另一个问题。尽管数组的长度可能是一个高值,但rosserial消息的缓冲区仍然被限制在一个低值。我猜是协议本身受到了限制。然后,我无法发送整个图像消息,即480x640xRGB,但我可以使用它根据我的测试,将图像的一部分(8x8xRGB)还原。这最终成功了,我在rviz中可视化了图像,没有任何问题

因此,正如cassinaj所建议的那样,一种解决方案是将所有数据分成若干部分,然后在接收器端将它们全部放在一起。这应该是可行的,尽管听起来很痛苦(如果我将图像分成8x8部分,一个图像大约需要4800条消息!)

出于这个原因,我尝试使用win_ros(适用于windows的ros),以便通过ros本身发送来自kinect的所有数据。遗憾的是,rosserial具有这些限制,因为它非常易于使用和实现


如果有人还有什么要补充的,或者我遗漏了什么,请告诉我。任何帮助都是非常感谢的!

首先,感谢卡西纳吉,我认为解决方案应该是他提出的答案。不过,我要补充一些我为处于相同情况的人找到的信息

rosserial中数组的限制由
uint8_t
给出,在大多数ros发行版中,该限制最大为255字节。但是,该问题已在本文中进行了评论,其中建议将该值增加到
uint32_t
。因此,如果您从r在Jade中,数据的长度应为
uint32\u t
。这是图像消息的生成代码:

  class Image : public ros::Msg
  {
  public:
    std_msgs::Header header;
    uint32_t height;
    uint32_t width;
    const char* encoding;
    uint8_t is_bigendian;
    uint32_t step;
    uint32_t data_length;
    uint8_t st_data;
    uint8_t * data;
  Image():
    header(),
    height(0),
    width(0),
    encoding(""),
    is_bigendian(0),
    step(0),
    data_length(0), data(NULL)
{
}
 virtual int serialize(unsigned char *outbuffer) const
 virtual int deserialize(unsigned char *inbuffer)
我本来希望现在一切正常,但出现了另一个问题。尽管数组的长度可能是一个很高的值,但rosserial的缓冲区