Configuration: FreeBSD 4.5 - XFree86 4.2.0 - ATI Radeon VE
Problem: If a polygon which is being filled with a stipple intersects a
clip region, the fill fails and paints the clipped region black.
Diagnosing:
1) rectangles do not seem to suffer from this problem
2) solid(non-stipple) fills do not seem to exhibit the problem
3) if NoAccel is turned on, the problem goes away
How to repeat:
Attached is a program which draws 8 square polygons, 4 of which are not
clipped, 4 of which are. The rightmost polygons should all fail. If they
don't, please let me know.
I will be happy to provide any other logs or configuration information
required as this was a real pain to hunt down.
Thanks,
-a
#include <X11/Xlib.h>
#define stipple_bitmap_width 16
#define stipple_bitmap_height 16
static unsigned char stipple_bitmap_bits[] = {
0x33, 0x33, 0x66, 0x66, 0xcc, 0xcc, 0x99, 0x99, 0x33, 0x33, 0x66, 0x66,
0xcc, 0xcc, 0x99, 0x99, 0x33, 0x33, 0x66, 0x66, 0xcc, 0xcc, 0x99, 0x99,
0x33, 0x33, 0x66, 0x66, 0xcc, 0xcc, 0x99, 0x99};
Display *display;
int screen_num;
static char *progname;
int main(int argc, char **argv)
{
Window win;
Pixmap stippleBitmap;
char *display_name = NULL;
GC gc0,gc1,gc2,gc3;
unsigned long valuemask = 0;
XGCValues values;
XEvent event;
Colormap defaultColormap;
XColor red,green,blue,black,white,junk;
XRectangle clipRects[1] = {{400,50,400,400}};
XPoint rb[5] = {{0,0},{100,0},{100,100},{0,100},{0,0}};
XPoint r[8][5];
int i,j,k;
for(i=0; i<8; i++)
{
for(j=0; j<6; j++)
{
r[i][j].x = rb[j].x + i*100 + i*2;
r[i][j].y = rb[j].y;
}
}
progname = argv[0];
if ((display=XOpenDisplay(display_name)) == NULL)
{
printf("Failed to open display\n");
exit(-1);
}
win = XCreateSimpleWindow(display, RootWindow(display, screen_num),
0, 0, 800, 150, 0, BlackPixel(display, screen_num),
WhitePixel(display, screen_num));
screen_num = DefaultScreen(display);
stippleBitmap = XCreateBitmapFromData(display, win, stipple_bitmap_bits,
stipple_bitmap_width, stipple_bitmap_height);
XSelectInput(display, win, ExposureMask | KeyPressMask);
defaultColormap = DefaultColormap(display, screen_num);
XAllocNamedColor(display, defaultColormap, "red", &red, &junk);
XAllocNamedColor(display, defaultColormap, "green", &green, &junk);
XAllocNamedColor(display, defaultColormap, "blue", &blue, &junk);
XAllocNamedColor(display, defaultColormap, "black", &black, &junk);
XAllocNamedColor(display, defaultColormap, "white", &white, &junk);
values.foreground = red.pixel;
values.background = green.pixel;
values.fill_style = FillStippled;
values.stipple = stippleBitmap;
valuemask = GCForeground | GCBackground | GCFillStyle | GCStipple;
gc0 = XCreateGC(display, win, valuemask, &values);
XMapWindow(display, win);
while(1)
{
XNextEvent(display, &event);
switch (event.type)
{
case Expose:
/* Draw something */
for(i=0; i<4; i++)
{
XFillPolygon(display, win, gc0, r[i], 5, Convex, CoordModeOrigin);
}
XSetClipRectangles(display, gc0, 0, 0, clipRects, 1, Unsorted);
for(i=4; i<8; i++)
{
XFillPolygon(display, win, gc0, r[i], 5, Convex, CoordModeOrigin);
}
break;
case KeyPress:
XFreeGC(display, gc0);
XCloseDisplay(display);
exit(-1);
break;
default:
break;
}
}
}