You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

SMsgWriter.h 6.7KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177
  1. /* Copyright (C) 2002-2005 RealVNC Ltd. All Rights Reserved.
  2. *
  3. * This is free software; you can redistribute it and/or modify
  4. * it under the terms of the GNU General Public License as published by
  5. * the Free Software Foundation; either version 2 of the License, or
  6. * (at your option) any later version.
  7. *
  8. * This software is distributed in the hope that it will be useful,
  9. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  10. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  11. * GNU General Public License for more details.
  12. *
  13. * You should have received a copy of the GNU General Public License
  14. * along with this software; if not, write to the Free Software
  15. * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,
  16. * USA.
  17. */
  18. //
  19. // SMsgWriter - class for writing RFB messages on the server side.
  20. //
  21. #ifndef __RFB_SMSGWRITER_H__
  22. #define __RFB_SMSGWRITER_H__
  23. #include <rdr/types.h>
  24. #include <rfb/encodings.h>
  25. #include <rfb/Encoder.h>
  26. #include <rfb/PixelBuffer.h>
  27. namespace rdr { class OutStream; }
  28. namespace rfb {
  29. class PixelFormat;
  30. class ConnParams;
  31. class ImageGetter;
  32. class ColourMap;
  33. class Region;
  34. class UpdateInfo;
  35. class JpegEncoder;
  36. class WriteSetCursorCallback {
  37. public:
  38. virtual void writeSetCursorCallback() = 0;
  39. };
  40. class SMsgWriter {
  41. public:
  42. virtual ~SMsgWriter();
  43. // writeServerInit() must only be called at the appropriate time in the
  44. // protocol initialisation.
  45. virtual void writeServerInit()=0;
  46. // Methods to write normal protocol messages
  47. // writeSetColourMapEntries() writes a setColourMapEntries message, using
  48. // the given ColourMap object to lookup the RGB values of the given range
  49. // of colours.
  50. virtual void writeSetColourMapEntries(int firstColour, int nColours,
  51. ColourMap* cm);
  52. // writeBell() and writeServerCutText() do the obvious thing.
  53. virtual void writeBell();
  54. virtual void writeServerCutText(const char* str, int len);
  55. // setupCurrentEncoder() should be called before each framebuffer update,
  56. // prior to calling getNumRects() or writeFramebufferUpdateStart().
  57. void setupCurrentEncoder();
  58. // getNumRects() computes the number of sub-rectangles that will compose a
  59. // given rectangle, for current encoder.
  60. int getNumRects(const Rect &r);
  61. // writeSetDesktopSize() on a V3 writer won't actually write immediately,
  62. // but will write the relevant pseudo-rectangle as part of the next update.
  63. virtual bool writeSetDesktopSize()=0;
  64. virtual bool writeSetDesktopName()=0;
  65. // Like setDesktopSize, we can't just write out a setCursor message
  66. // immediately on a V3 writer. Instead of calling writeSetCursor()
  67. // directly, you must call cursorChange(), and then invoke writeSetCursor()
  68. // in response to the writeSetCursorCallback() callback. For a V3 writer
  69. // this will happen when the next update is sent.
  70. virtual void cursorChange(WriteSetCursorCallback* cb)=0;
  71. virtual void writeSetCursor(int width, int height, const Point& hotspot,
  72. void* data, void* mask)=0;
  73. virtual void writeSetXCursor(int width, int height, int hotspotX,
  74. int hotspotY, void* data, void* mask)=0;
  75. // needFakeUpdate() returns true when an immediate update is needed in
  76. // order to flush out setDesktopSize or setCursor pseudo-rectangles to the
  77. // client.
  78. virtual bool needFakeUpdate();
  79. // writeFramebufferUpdate() writes a framebuffer update using the given
  80. // UpdateInfo and ImageGetter. On a V3 writer this may have
  81. // pseudo-rectangles for setDesktopSize and setCursor added to it, and so
  82. // may invoke writeSetCursorCallback().
  83. //
  84. // FIXME: This function is not used because it incorrectly computes
  85. // the number of rectangles if the Tight encoder is used.
  86. /*
  87. virtual void writeFramebufferUpdate(const UpdateInfo& ui, ImageGetter* ig,
  88. Region* updatedRegion);
  89. */
  90. // writeRects() accepts an UpdateInfo (changed & copied regions) and an
  91. // ImageGetter to fetch pixels from. It then calls writeCopyRect() and
  92. // writeRect() as appropriate. writeFramebufferUpdateStart() must be used
  93. // before the first writeRects() call and writeFrameBufferUpdateEnd() after
  94. // the last one. It returns the actual region sent to the client, which
  95. // may be smaller than the update passed in.
  96. virtual void writeRects(const UpdateInfo& update, ImageGetter* ig,
  97. Region* updatedRegion);
  98. // To construct a framebuffer update you can call
  99. // writeFramebufferUpdateStart(), followed by a number of writeCopyRect()s
  100. // and writeRect()s, finishing with writeFramebufferUpdateEnd(). If you
  101. // know the exact number of rectangles ahead of time you can specify it to
  102. // writeFramebufferUpdateStart() which can be more efficient.
  103. virtual void writeFramebufferUpdateStart(int nRects)=0;
  104. virtual void writeFramebufferUpdateStart()=0;
  105. virtual void writeFramebufferUpdateEnd()=0;
  106. // writeRect() tries to write the given rectangle. If it is unable to
  107. // write the whole rectangle it returns false and sets actual to the actual
  108. // rectangle which was updated.
  109. virtual bool writeRect(const Rect& r, ImageGetter* ig, Rect* actual);
  110. virtual bool writeRect(const Rect& r, unsigned int encoding,
  111. ImageGetter* ig, Rect* actual);
  112. virtual void writeCopyRect(const Rect& r, int srcX, int srcY);
  113. virtual bool canUseJpegEncoder(PixelBuffer *pb) const;
  114. virtual void writeJpegRect(PixelBuffer *pb, const Rect& r);
  115. virtual void startRect(const Rect& r, unsigned int enc)=0;
  116. virtual void endRect()=0;
  117. ConnParams* getConnParams() { return cp; }
  118. rdr::OutStream* getOutStream() { return os; }
  119. rdr::U8* getImageBuf(int required, int requested=0, int* nPixels=0);
  120. int bpp();
  121. int getUpdatesSent() { return updatesSent; }
  122. int getRectsSent(int encoding) { return rectsSent[encoding]; }
  123. int getBytesSent(int encoding) { return bytesSent[encoding]; }
  124. int getRawBytesEquivalent() { return rawBytesEquivalent; }
  125. int imageBufIdealSize;
  126. protected:
  127. SMsgWriter(ConnParams* cp, rdr::OutStream* os);
  128. virtual void startMsg(int type)=0;
  129. virtual void endMsg()=0;
  130. ConnParams* cp;
  131. rdr::OutStream* os;
  132. Encoder* encoders[encodingMax+1];
  133. JpegEncoder* jpegEncoder;
  134. int lenBeforeRect;
  135. unsigned int currentEncoding;
  136. int updatesSent;
  137. int bytesSent[encodingMax+1];
  138. int rectsSent[encodingMax+1];
  139. int rawBytesEquivalent;
  140. // FIXME: Gather statistics for JpegEncoder as well.
  141. rdr::U8* imageBuf;
  142. int imageBufSize;
  143. };
  144. }
  145. #endif