1#include <stdint.h> 2#include <stdio.h> 3#include <stdlib.h> 4 5#include <X11/Xutil.h> /* for XDestroyImage */ 6 7#include "test.h" 8 9static void fill_rect(struct test_display *t, 10 Picture p, 11 XRenderPictFormat *format, 12 int use_window, int tx, int ty, 13 uint8_t op, int x, int y, int w, int h, 14 int mask_x, int mask_y, int mask_w, int mask_h, 15 uint8_t red, uint8_t green, uint8_t blue, uint8_t alpha) 16{ 17 Drawable tmp; 18 Pixmap pixmask; 19 XRenderColor c; 20 Picture src, mask; 21 22 if (use_window) { 23 XSetWindowAttributes attr; 24 25 attr.override_redirect = 1; 26 tmp = XCreateWindow(t->dpy, DefaultRootWindow(t->dpy), 27 tx, ty, 28 w, h, 29 0, format->depth, 30 InputOutput, 31 DefaultVisual(t->dpy, 32 DefaultScreen(t->dpy)), 33 CWOverrideRedirect, &attr); 34 XMapWindow(t->dpy, tmp); 35 } else 36 tmp = XCreatePixmap(t->dpy, DefaultRootWindow(t->dpy), 37 w, h, format->depth); 38 39 pixmask = XCreatePixmap(t->dpy, DefaultRootWindow(t->dpy), w, h, 8); 40 mask = XRenderCreatePicture(t->dpy, pixmask, 41 XRenderFindStandardFormat(t->dpy, PictStandardA8), 42 0, NULL); 43 c.red = c.green = c.blue = c.alpha = 0; 44 XRenderFillRectangle(t->dpy, PictOpSrc, mask, &c, 45 0, 0, w, h); 46 c.red = c.green = c.blue = c.alpha = 0xffff; 47 XRenderFillRectangle(t->dpy, PictOpSrc, mask, &c, 48 mask_x, mask_y, mask_w, mask_h); 49 50 src = XRenderCreatePicture(t->dpy, tmp, format, 0, NULL); 51 c.red = red * alpha; 52 c.green = green * alpha; 53 c.blue = blue * alpha; 54 c.alpha = alpha << 8 | alpha; 55 XRenderFillRectangle(t->dpy, PictOpSrc, src, &c, 0, 0, w, h); 56 57 XRenderComposite(t->dpy, op, src, mask, p, 0, 0, 0, 0, x, y, w, h); 58 59 XRenderFreePicture(t->dpy, src); 60 if (use_window) 61 XDestroyWindow(t->dpy, tmp); 62 else 63 XFreePixmap(t->dpy, tmp); 64 65 XRenderFreePicture(t->dpy, mask); 66 XFreePixmap(t->dpy, pixmask); 67} 68 69static void clear(struct test_display *dpy, struct test_target *tt) 70{ 71 XRenderColor render_color = {0}; 72 XRenderFillRectangle(dpy->dpy, PictOpClear, tt->picture, &render_color, 73 0, 0, tt->width, tt->height); 74} 75 76static void rect_tests(struct test *t, int reps, int sets, enum target target, int use_window) 77{ 78 struct test_target out, ref; 79 int r, s; 80 printf("Testing area fills (%s, using %s source): ", 81 test_target_name(target), use_window ? "window" : "pixmap"); 82 fflush(stdout); 83 84 test_target_create_render(&t->out, target, &out); 85 clear(&t->out, &out); 86 87 test_target_create_render(&t->ref, target, &ref); 88 clear(&t->ref, &ref); 89 90 for (s = 0; s < sets; s++) { 91 for (r = 0; r < reps; r++) { 92 int x, y, w, h; 93 int mask_x, mask_y, mask_w, mask_h; 94 int tmpx, tmpy; 95 uint8_t red = rand(); 96 uint8_t green = rand(); 97 uint8_t blue = rand(); 98 uint8_t alpha = rand(); 99 int try = 50; 100 101 do { 102 x = rand() % (out.width - 1); 103 y = rand() % (out.height - 1); 104 w = 1 + rand() % (out.width - x - 1); 105 h = 1 + rand() % (out.height - y - 1); 106 tmpx = w == out.width ? 0 : rand() % (out.width - w); 107 tmpy = h == out.height ? 0 : rand() % (out.height - h); 108 } while (((tmpx+w > x && tmpx < x+w) || 109 (tmpy+h > y && tmpy < y+h)) && 110 --try); 111 112 mask_x = (rand() % (2*w)) - w; 113 mask_y = (rand() % (2*h)) - h; 114 mask_w = rand() % w; 115 mask_h = rand() % h; 116 117 if (try) { 118 fill_rect(&t->out, out.picture, out.format, 119 use_window, tmpx, tmpy, 120 PictOpSrc, x, y, w, h, 121 mask_x, mask_y, mask_w, mask_h, 122 red, green, blue, alpha); 123 fill_rect(&t->ref, ref.picture, ref.format, 124 use_window, tmpx, tmpy, 125 PictOpSrc, x, y, w, h, 126 mask_x, mask_y, mask_w, mask_h, 127 red, green, blue, alpha); 128 } 129 } 130 131 test_compare(t, 132 out.draw, out.format, 133 ref.draw, ref.format, 134 0, 0, out.width, out.height, 135 ""); 136 } 137 138 printf("passed [%d iterations x %d]\n", reps, sets); 139 140 test_target_destroy_render(&t->out, &out); 141 test_target_destroy_render(&t->ref, &ref); 142} 143 144int main(int argc, char **argv) 145{ 146 struct test test; 147 int i; 148 149 test_init(&test, argc, argv); 150 151 for (i = 0; i <= DEFAULT_ITERATIONS; i++) { 152 int reps = REPS(i), sets = SETS(i); 153 enum target t; 154 155 for (t = TARGET_FIRST; t <= TARGET_LAST; t++) { 156 rect_tests(&test, reps, sets, t, 0); 157 if (t != PIXMAP) 158 rect_tests(&test, reps, sets, t, 1); 159 } 160 } 161 162 return 0; 163} 164