【问题标题】:Incorrect color encoding in Remote Framebuffer server远程帧缓冲区服务器中的颜色编码不正确
【发布时间】:2016-06-21 02:46:42
【问题描述】:

我正在研究一个使用“RAW”像素编码的 RFB 服务器的简单实现。我使用 TightVNC 作为我的桌面客户端。我的代码工作到客户端能够请求整个“桌面”,即 640x480 像素。我的测试图案在形状方面绘制正确,但颜色错误。

我尝试使用每个像素 8 位:每个字节中编码为 RRRGGGBB 的三个红色、三个绿色和两个蓝色。

我的 ServerInit 数据包包含此像素编码规范...

//all of these 13 fields are unsigned chars...

si.pf.bits_per_pixel = 8;
si.pf.depth = 8;
si.pf.big_endian_flag = 0;
si.pf.true_colour_flag = 1;

si.pf.red_max_hi = 0;
si.pf.red_max_lo = 7;    // 3 bits
si.pf.green_max_hi = 0;
si.pf.green_max_lo = 7;  // 3 bits
si.pf.blue_max_hi = 0;
si.pf.blue_max_lo = 3;   // 2 bits

si.pf.red_shift = 5;     // >>>>>RRR
si.pf.green_shift = 2;   // >>RRRGGG
si.pf.blue_shift = 0;    // RRRGGGBB

//remaining fields are omitted

整个结构是这样定义的:

typedef struct
{
  uchar bits_per_pixel;
  uchar depth;
  uchar big_endian_flag;
  uchar true_colour_flag;

  uchar red_max_hi;
  uchar red_max_lo;
  uchar green_max_hi;
  uchar green_max_lo;
  uchar blue_max_hi;
  uchar blue_max_lo;

  uchar red_shift;
  uchar green_shift;
  uchar blue_shift;

  uchar padding0;
  uchar padding1;
  uchar padding2;
}tPixelFormat;

现在,如果我用0xe0(二进制111 000 00)填充我的桌面图像,那么我希望这会被解释为纯鲜红色。但它显示为浅蓝色(好像 8 个单独的位被向后解释!)。我的测试图案的形状是正确的,因为我在顶角绘制了几个白色像素(白色显然是二进制111 111 11)。

我不明白这一点。我相信我已经遵循了 RFB 规范中描述的算法和编码...http://vncdotool.readthedocs.org/en/latest/rfbproto.html#serverinit

我做错了什么?

【问题讨论】:

  • 字节序不适用于 RAW 格式,因为每个像素只有一个字节,所以在使用 8 位/像素时。提供的代码中的 16 位值 (_hi/_lo) 应该是大端格式。
  • 在规格中 red-max green-max blue-maxU16。您写道,您的结构长 13 个字节。另一件事:结构是否包装好?你确定对齐吗?发布结构定义。
  • 我在问题中添加了结构定义。 Wireshark的解码器

标签: c encoding bitmap rfb-protocol


【解决方案1】:

Wireshark 来救援!解决了。​​

事实证明,客户端发送了一个我没有看到的 SetPixelFormat 请求,代码忽略了它,显然服务器被授权通过更改其输出格式来响应请求。

解决方法是通过硬编码客户要求的值,从一开始就简单地为客户提供它想要的东西。此时客户端不再发送该请求,因为它对服务器现在从一开始就发出的内容感到满意。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-03-02
    • 2012-03-06
    • 1970-01-01
    • 1970-01-01
    • 2013-06-19
    相关资源
    最近更新 更多