afzal@cui.unige.ch (Afzal Ballim) (11/19/90)
Subject: OpenWindows 2.0 Xlib ClipRectangle bug Hi, I have noticed what may be a problem with the OpenWindows 2.0 server in using clip rectangles in (at least) Unsorted mode. I have tried to isolate the problem but haven't had time to track it down, and it may be a problem with my reasoning rather than the server. Anyway, I include a program below that seems to demonstrate it. The program should move a rectangular block around an octogone over a background pixmap. With the MIT R4 sample server on my monochrome Sun-4 workstation this works fine. However, on the same machine running Open Windows 2.0 it fails to redraw certain portions of the background pixmap. It appears that when copying with clip rectangles in unsorted mode, if two rectangles overlap then something goes wrong with the dimensions. I would appreciate anyone either confirming this problem, or telling me what I'm doing wrong. I'd additionally like to know if this fails on other servers. +------------------------------CUT HERE------------------------------+ #! /bin/sh # This is a shell archive. Remove anything before this line, then unpack # it by saving it into a file and typing "sh file". To overwrite existing # files, type "sh file -c". You can also feed this as standard input via # unshar, or by typing "sh <file", e.g.. If this archive is complete, you # will see the following message at the end: # "End of shell archive." # Contents: probNBM.c # Wrapped by afzal@issun3 on Mon Nov 19 11:52:49 1990 PATH=/bin:/usr/bin:/usr/ucb ; export PATH if test -f 'probNBM.c' -a "${1}" != "-c" ; then echo shar: Will not clobber existing file \"'probNBM.c'\" else echo shar: Extracting \"'probNBM.c'\" \(4360 characters\) sed "s/^X//" >'probNBM.c' <<'END_OF_FILE' X X#include <stdio.h> X#include <X11/Xlib.h> X#include <X11/Xutil.h> X X/* border width */ X#define BDW 4 X X/* the overlap region for trying things out */ X#define OVX 155 X#define OVY 135 X#define OVW 128 X#define OVH 128 X XDisplay *mydisplay; X Xstatic int dx[] = { X1,0,-1,-1,-1,0,1,1 X}; X Xstatic int dy[]= { X-1,-1,-1,0,1,1,1,0 X}; X X/* don't do things until window is mapped */ Xexpose_wait() X{ X XEvent e; X X while (1) X { XNextEvent(mydisplay,&e); X if (e.type == Expose) return; X } X} X X Xmain(argc, argv) Xint argc; Xchar *argv[]; X{ X/* declarations */ XWindow mywindow; XXGCValues gcvalues; XGC copygc, clipgc; XXSizeHints hints; Xint myscreen; Xunsigned long foreground,background; XPixmap bg, db; Xint i,j,k,l,del_x,del_y; /* :-) */ Xint cur_x,cur_y; XXRectangle rectangles[4]; Xint which; X X/* Initialisation */ X Xmydisplay = XOpenDisplay(""); Xmyscreen = DefaultScreen(mydisplay); X X/* pixel values */ Xforeground = BlackPixel(mydisplay,myscreen); Xbackground = WhitePixel(mydisplay,myscreen); X X/* hints */ Xhints.x = 200; hints.y = 300; Xhints.width = 480; hints.height = 320; X Xhints.flags = PPosition | PSize; X X/* make a window */ X Xmywindow = XCreateSimpleWindow(mydisplay, X DefaultRootWindow(mydisplay), X hints.x,hints.y,hints.width,hints.height, X BDW,foreground,background); XXSetStandardProperties(mydisplay,mywindow,"Clip test","Clip test", X None,argv,argc,&hints); X XXSelectInput(mydisplay,mywindow,ExposureMask); X X/* make the GCs */ X Xgcvalues.foreground= foreground; Xgcvalues.background= background; Xclipgc = XCreateGC(mydisplay,mywindow,GCBackground|GCForeground,&gcvalues); Xgcvalues.function = GXcopy; Xcopygc = XCreateGC(mydisplay,mywindow,GCBackground|GCForeground|GCFunction,&gcvalues); X X/* raise window */ XXMapRaised(mydisplay,mywindow); Xexpose_wait(); X X/* make the bg */ Xbg = XCreatePixmap(mydisplay,mywindow, X 480,320,foreground,background, X DefaultDepth(mydisplay,myscreen)); X X/* fill bg */ X X XFillRectangle(mydisplay,bg,copygc,0,0,480,320); X XSetFunction(mydisplay,copygc,GXxor); X XSetForeground(mydisplay,copygc,foreground^background); X for (i=0;i<480;i++) XDrawLine(mydisplay,bg,copygc,0,0,i,319); X for (i=0;i<320;i++) XDrawLine(mydisplay,bg,copygc,0,0,479,i); X XSetFunction(mydisplay,copygc,GXcopy); X X/* make the double buffer */ Xdb = XXCreatePixmap(mydisplay,mywindow,512,480,DefaultDepth(mydisplay,myscreen)); X X/* set up the rectangle */ Xcur_x=cur_y=rectangles[1].x=rectangles[1].y=rectangles[3].x=rectangles[3].y=240; Xrectangles[1].width=rectangles[1].height=rectangles[3].width=rectangles[3].height=32; X Xrectangles[0].x=rectangles[2].x=OVX; Xrectangles[0].y=rectangles[2].y=OVY; Xrectangles[0].width=rectangles[2].width=OVW; Xrectangles[0].height=rectangles[2].height=OVH; X Xwhich=0; X X/* copy background to screen */ XXCopyArea(mydisplay,bg,db, X copygc,0,0,512,480,0,0); XXCopyArea(mydisplay,db,mywindow, X copygc,0,0,512,480,0,0); XXFlush(mydisplay); X X X/* main loop, don't care about events */ X/* do the rounds 10 times */ Xfor (i=0;i<10;i++) X for((j=0,del_x=dx[0],del_y=dy[0]);j<8; X (++j,del_x=dx[j],del_y=dy[j])) X /* make the rectangle blit around an octogon */ X for (k=0;k<50;k++) { X /* this looks weird, but is written this way to emulate X the program which turned up this problem */ X /* update the db by drawing from the bg */ X#ifdef DEBUG X printf("bg %d, blit %d, ",which,which+1); X#endif X XCopyArea(mydisplay,bg,db,copygc, X OVX,OVY,OVW,OVH,rectangles[which].x,rectangles[which].y); X XCopyArea(mydisplay,bg,db,copygc, X rectangles[which+1].x,rectangles[which+1].y, X 32,32,rectangles[which+1].x,rectangles[which+1].y); X X /* now draw the new */ X which=(which+2)%4; X cur_x += del_x; cur_y+=del_y; X rectangles[which+1].x = cur_x; X rectangles[which+1].y = cur_y; X XFillRectangle(mydisplay,db,copygc, X rectangles[which+1].x,rectangles[which+1].y, X 32,32); X X /* update the window */ X XSetClipRectangles(mydisplay,clipgc, X 0,0,rectangles,4,Unsorted); X XCopyArea(mydisplay,db,mywindow,clipgc, X 0,0,512,480,0,0); X#ifdef DEBUG X printf(" bg %d, blit %d\n",which,which+1); X#endif X for(l=0;l<4;l++) X#ifdef DEBUG X printf("rectangle %d = [ %d , %d , %d , %d ]\n",l, X rectangles[l].x,rectangles[l].y, X rectangles[l].width,rectangles[l].height); X printf("\n"); X#endif X XFlush(mydisplay);} X X XXFreeGC(mydisplay,copygc); XXDestroyWindow(mydisplay,mywindow); XXCloseDisplay(mydisplay); Xexit(0); X X} X END_OF_FILE if test 4360 -ne `wc -c <'probNBM.c'`; then echo shar: \"'probNBM.c'\" unpacked with wrong size! fi # end of 'probNBM.c' fi echo shar: End of shell archive. exit 0 +------------------------------END CUT-------------------------------+ Afzal Ballim |EAN,BITNET,EARN,MHS,X.400: afzal@divsun.unige.ch ISSCO, University of Geneva |UUCP: mcvax!cernvax!cui!divsun.unige.ch!afzal 54 route des Acacias |JANET: afzal%divsun.unige.ch@uk.ac.ean-relay CH-1227 GENEVA,Switzerland |CSNET,ARPA: afzal%divsun.unige.ch@relay.cs.net
naughton@wind.Eng.Sun.COM (Patrick Naughton) (11/20/90)
This is indeed a bug (bugid 1046988) and it is fixed in the next version... In article <3773@cui.unige.ch>, afzal@cui.unige.ch (Afzal Ballim) writes: |> Subject: OpenWindows 2.0 Xlib ClipRectangle bug |> |> |> Hi, I have noticed what may be a problem with the OpenWindows 2.0 server in |> using clip rectangles in (at least) Unsorted mode. I have tried to isolate |> the problem but haven't had time to track it down, and it may be a problem |> with my reasoning rather than the server. Anyway, I include a program below |> that seems to demonstrate it. The program should move a rectangular block |> around an octogone over a background pixmap. With the MIT R4 sample server |> on my monochrome Sun-4 workstation this works fine. However, on the same |> machine running Open Windows 2.0 it fails to redraw certain portions of the |> background pixmap. |> |> It appears that when copying with clip rectangles in unsorted mode, if |> two rectangles overlap then something goes wrong with the dimensions. |> |> I would appreciate anyone either confirming this problem, or telling me what |> I'm doing wrong. I'd additionally like to know if this fails on other servers. |> <code deleted> -Patrick -- ______________________________________________________________________ Patrick J. Naughton ARPA: naughton@sun.com Windows and Graphics Group UUCP: ...!sun!naughton Sun Microsystems, Inc. AT&T: (415) 336 - 1080