summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMichel Dänzer <michel.daenzer@amd.com>2016-06-28 17:22:47 +0900
committerAdam Jackson <ajax@redhat.com>2016-07-19 13:13:36 -0400
commit65c5eab6000f108762b7ef6b63869525222ff99d (patch)
tree41010ba10f84569071e36993179ab4644f43545a
parentc0b02ce45f48450d2896a424dc1eb9a2827ed4c5 (diff)
dix: Work around non-premultiplied ARGB cursor data
Some games incorrectly use non-premultiplied ARGB cursor data, presumably because that's what Windows uses. On some hardware (and with SWcursor), this breaks areas of the cursor which are supposed to be transparent (and presumably also translucent areas, but that's less noticeable). This change checks for pixels with alpha == 0 and any non-alpha component != 0. If any such pixel is found, the data is assumed to be non-premultiplied and fixed up by multiplying the RGB components with the alpha component. Bugzilla: https://bugs.freedesktop.org/show_bug.cgi?id=92309 Signed-off-by: Michel Dänzer <michel.daenzer@amd.com> Reviewed-by: Alex Deucher <alexander.deucher@amd.com> (cherry picked from commit 401a8d6e1379133863e3271374dc21850d0d3cab)
-rw-r--r--dix/cursor.c23
1 files changed, 23 insertions, 0 deletions
diff --git a/dix/cursor.c b/dix/cursor.c
index e45945619..25d676779 100644
--- a/dix/cursor.c
+++ b/dix/cursor.c
@@ -288,6 +288,29 @@ AllocARGBCursor(unsigned char *psrcbits, unsigned char *pmaskbits,
goto error;
*ppCurs = pCurs;
+
+ if (argb) {
+ size_t i, size = bits->width * bits->height;
+
+ for (i = 0; i < size; i++) {
+ if ((argb[i] & 0xff000000) == 0 && (argb[i] & 0xffffff) != 0) {
+ /* ARGB data doesn't seem pre-multiplied, fix it */
+ for (i = 0; i < size; i++) {
+ CARD32 a, ar, ag, ab;
+
+ a = argb[i] >> 24;
+ ar = a * ((argb[i] >> 16) & 0xff) / 0xff;
+ ag = a * ((argb[i] >> 8) & 0xff) / 0xff;
+ ab = a * (argb[i] & 0xff) / 0xff;
+
+ argb[i] = a << 24 | ar << 16 | ag << 8 | ab;
+ }
+
+ break;
+ }
+ }
+ }
+
return Success;
error: