blob: 9e2c811d52157ffe2fb86e972e7c200fc27b7ec5 [file] [log] [blame]
--- vnc_unixsrc.orig/vncviewer/desktop.c 2004-05-28 13:29:29.000000000 -0400
+++ vnc_unixsrc/vncviewer/desktop.c 2007-01-13 13:59:51.000000000 -0500
@@ -50,6 +50,30 @@
},
};
+void create_image() {
+ image = NULL;
+
+#ifdef MITSHM
+ if (appData.useShm) {
+ image = CreateShmImage();
+ if (!image)
+ appData.useShm = False;
+ }
+#endif
+
+ if (!image) {
+ image = XCreateImage(dpy, vis, visdepth, ZPixmap, 0, NULL,
+ si.framebufferWidth, si.framebufferHeight,
+ BitmapPad(dpy), 0);
+
+ image->data = malloc(image->bytes_per_line * image->height);
+ if (!image->data) {
+ fprintf(stderr,"malloc failed\n");
+ exit(1);
+ }
+ }
+}
+
/*
* DesktopInitBeforeRealization creates the "desktop" widget and the viewport
@@ -82,30 +106,9 @@
for (i = 0; i < 256; i++)
modifierPressed[i] = False;
- image = NULL;
-
-#ifdef MITSHM
- if (appData.useShm) {
- image = CreateShmImage();
- if (!image)
- appData.useShm = False;
- }
-#endif
-
- if (!image) {
- image = XCreateImage(dpy, vis, visdepth, ZPixmap, 0, NULL,
- si.framebufferWidth, si.framebufferHeight,
- BitmapPad(dpy), 0);
-
- image->data = malloc(image->bytes_per_line * image->height);
- if (!image->data) {
- fprintf(stderr,"malloc failed\n");
- exit(1);
- }
- }
+ create_image();
}
-
/*
* DesktopInitAfterRealization does things which require the X windows to
* exist. It creates some GCs and sets the dot cursor.
@@ -460,3 +463,70 @@
break;
}
}
+
+static void reset_image(void) {
+ if (UsingShm()) {
+ ShmCleanup();
+ } else {
+ if (image && image->data) {
+ free(image->data);
+ /* see manpage XDestroyImage may also free data, so we skip and have a tiny leak instead */
+ if (0) XDestroyImage(image);
+ image = NULL;
+ }
+ }
+ create_image();
+ XFlush(dpy);
+}
+
+void ReDoDesktop(void) {
+ int w, h, x, y, dw, dh;
+
+ if (appData.fullScreen) {
+ if (image && image->data) {
+ int len;
+ int h = image->height;
+ int w = image->width;
+ len = image->bytes_per_line * image->height;
+ /* black out window first: */
+ memset(image->data, 0, len);
+ XPutImage(dpy, XtWindow(desktop), gc, image, 0, 0, 0, 0, w, h);
+ XFlush(dpy);
+ }
+ XtResizeWidget(desktop, si.framebufferWidth, si.framebufferHeight, 0);
+ XSync(dpy, False);
+ usleep(100*1000);
+ FullScreenOn();
+ XSync(dpy, False);
+ usleep(100*1000);
+ reset_image();
+ return;
+ }
+
+ dw = appData.wmDecorationWidth;
+ dh = appData.wmDecorationHeight;
+
+ w = si.framebufferWidth;
+ h = si.framebufferHeight;
+
+ if (w + dw >= dpyWidth) {
+ w = dpyWidth - dw;
+ }
+ if (h + dh >= dpyHeight) {
+ h = dpyHeight - dh;
+ }
+
+ XtVaSetValues(toplevel, XtNmaxWidth, w, XtNmaxHeight, h, NULL);
+
+ XtVaSetValues(desktop, XtNwidth, si.framebufferWidth,
+ XtNheight, si.framebufferHeight, NULL);
+
+ x = (dpyWidth - w - dw)/2;
+ y = (dpyHeight - h - dh)/2;
+
+ XtResizeWidget(desktop, si.framebufferWidth, si.framebufferHeight, 0);
+
+ XtConfigureWidget(toplevel, x + dw, y + dh, w, h, 0);
+
+ reset_image();
+}
--- vnc_unixsrc.orig/vncviewer/fullscreen.c 2003-10-09 05:23:49.000000000 -0400
+++ vnc_unixsrc/vncviewer/fullscreen.c 2006-07-27 14:36:06.000000000 -0400
@@ -85,10 +85,13 @@
Dimension oldViewportWidth, oldViewportHeight, clipWidth, clipHeight;
Position viewportX, viewportY;
+ Bool fsAlready = appData.fullScreen, toobig = False;
+
appData.fullScreen = True;
if (si.framebufferWidth > dpyWidth || si.framebufferHeight > dpyHeight) {
+ toobig = True;
XtVaSetValues(viewport, XtNforceBars, True, NULL);
XtVaGetValues(viewport, XtNwidth, &oldViewportWidth,
XtNheight, &oldViewportHeight, NULL);
@@ -129,6 +132,7 @@
reparenting our window to the root. The window manager will get a
ReparentNotify and hopefully clean up its frame window. */
+if (! fsAlready) {
XtVaSetValues(toplevel, XtNoverrideRedirect, True, NULL);
XReparentWindow(dpy, XtWindow(toplevel), DefaultRootWindow(dpy), 0, 0);
@@ -164,10 +168,22 @@
XtManageChild(viewport);
- /* Now we can set "toplevel" to its proper size. */
+} else {
+ XSync(dpy, False);
+}
+ /* Now we can set "toplevel" to its proper size. */
XtResizeWidget(toplevel, toplevelWidth, toplevelHeight, 0);
+if (fsAlready) {
+ XtResizeWidget(viewport, viewportWidth, viewportHeight, 0);
+ if (! toobig) {
+ XtVaSetValues(viewport, XtNforceBars, False, NULL);
+ }
+ XMoveWindow(dpy, XtWindow(viewport), viewportX, viewportY);
+ XSync(dpy, False);
+}
+
/* Set the popup to overrideRedirect too */
XtVaSetValues(popup, XtNoverrideRedirect, True, NULL);
--- vnc_unixsrc.orig/vncviewer/rfbproto.c 2004-03-11 13:14:39.000000000 -0500
+++ vnc_unixsrc/vncviewer/rfbproto.c 2006-07-25 21:51:20.000000000 -0400
@@ -177,6 +177,9 @@
sig_rfbEncodingPointerPos, "Pointer position update");
CapsAdd(encodingCaps, rfbEncodingLastRect, rfbTightVncVendor,
sig_rfbEncodingLastRect, "LastRect protocol extension");
+
+ CapsAdd(encodingCaps, rfbEncodingNewFBSize, rfbTightVncVendor,
+ sig_rfbEncodingNewFBSize, "New FB size protocol extension");
}
@@ -729,6 +732,7 @@
Bool requestCompressLevel = False;
Bool requestQualityLevel = False;
Bool requestLastRectEncoding = False;
+ Bool requestNewFBSizeEncoding = True;
spf.type = rfbSetPixelFormat;
spf.format = myFormat;
@@ -806,6 +810,10 @@
if (se->nEncodings < MAX_ENCODINGS && requestLastRectEncoding) {
encs[se->nEncodings++] = Swap32IfLE(rfbEncodingLastRect);
}
+
+ if (se->nEncodings < MAX_ENCODINGS && requestNewFBSizeEncoding) {
+ encs[se->nEncodings++] = Swap32IfLE(rfbEncodingNewFBSize);
+ }
}
else {
if (SameMachine(rfbsock)) {
@@ -849,6 +857,7 @@
}
encs[se->nEncodings++] = Swap32IfLE(rfbEncodingLastRect);
+ encs[se->nEncodings++] = Swap32IfLE(rfbEncodingNewFBSize);
}
len = sz_rfbSetEncodingsMsg + se->nEncodings * 4;
@@ -1038,6 +1047,16 @@
}
continue;
}
+ if (rect.encoding == rfbEncodingNewFBSize) {
+ fprintf(stderr,"New Size: %dx%d at (%d, %d)\n",
+ rect.r.w, rect.r.h, rect.r.x, rect.r.y);
+ si.framebufferWidth = rect.r.w;
+ si.framebufferHeight = rect.r.h;
+ fprintf(stderr, "si: %d %d\n", si.framebufferWidth, si.framebufferHeight);
+ ReDoDesktop();
+
+ continue;
+ }
if ((rect.r.x + rect.r.w > si.framebufferWidth) ||
(rect.r.y + rect.r.h > si.framebufferHeight))
--- vnc_unixsrc.orig/vncviewer/shm.c 2000-06-11 08:00:53.000000000 -0400
+++ vnc_unixsrc/vncviewer/shm.c 2006-07-26 23:30:42.000000000 -0400
@@ -41,6 +41,10 @@
}
}
+Bool UsingShm() {
+ return needShmCleanup;
+}
+
static int
ShmCreationXErrorHandler(Display *dpy, XErrorEvent *error)
{
--- vnc_unixsrc.orig/vncviewer/vncviewer.h 2004-03-11 13:14:40.000000000 -0500
+++ vnc_unixsrc/vncviewer/vncviewer.h 2006-07-26 23:31:25.000000000 -0400
@@ -162,6 +162,8 @@
extern void CopyDataToScreen(char *buf, int x, int y, int width, int height);
extern void SynchroniseScreen();
+extern void ReDoDesktop();
+
/* dialogs.c */
extern void ServerDialogDone(Widget w, XEvent *event, String *params,
@@ -243,6 +245,7 @@
extern XImage *CreateShmImage();
extern void ShmCleanup();
+extern Bool UsingShm();
/* sockets.c */
--- vnc_unixsrc.orig/vncviewer/vncviewer.c 2004-01-13 09:22:05.000000000 -0500
+++ vnc_unixsrc/vncviewer/vncviewer.c 2006-07-27 19:00:25.000000000 -0400
@@ -57,6 +57,11 @@
}
}
+ if (argc > 1 && strstr(argv[1], "-h") == argv[1]) {
+ usage();
+ return 0;
+ }
+
/* Call the main Xt initialisation function. It parses command-line options,
generating appropriate resource specs, and makes a connection to the X
display. */