summaryrefslogtreecommitdiff
path: root/tools/virtual.c
diff options
context:
space:
mode:
authorChris Wilson <chris@chris-wilson.co.uk>2013-09-02 21:19:24 +0100
committerChris Wilson <chris@chris-wilson.co.uk>2013-09-02 21:19:24 +0100
commit5fed6e24996eb0fcfeec19341ce4103e7e7eb2d8 (patch)
tree11e4bc47018e40cce05f31b5abf85657b828e060 /tools/virtual.c
parentb955622cc25ab12305a572901a8ed0f23896dab3 (diff)
intel-virtual-output: Perform pixel type conversion from XfixesCursorImage
For whatever reason, Xfixes uses "unsigned long" in its protocol definition for the cursor pixels. Signed-off-by: Chris Wilson <chris@chris-wilson.co.uk>
Diffstat (limited to 'tools/virtual.c')
-rw-r--r--tools/virtual.c55
1 files changed, 39 insertions, 16 deletions
diff --git a/tools/virtual.c b/tools/virtual.c
index 120d9e85..27d80e85 100644
--- a/tools/virtual.c
+++ b/tools/virtual.c
@@ -88,6 +88,8 @@ struct display {
Cursor invisible_cursor;
Cursor visible_cursor;
+ XcursorImage cursor_image;
+ int cursor_serial;
int cursor_x;
int cursor_y;
int cursor_moved;
@@ -1001,26 +1003,47 @@ static Cursor display_load_invisible_cursor(struct display *display)
return XCreatePixmapCursor(display->dpy, bitmap, bitmap, &black, &black, 0, 0);
}
-static void display_load_visible_cursor(struct display *display, XFixesCursorImage *cur)
+static Cursor display_get_visible_cursor(struct display *display)
{
- XcursorImage image;
+ if (display->cursor_serial != display->cursor_image.size) {
+ DBG(("%s updating cursor\n", DisplayString(display->dpy)));
+
+ if (display->visible_cursor)
+ XFreeCursor(display->dpy, display->visible_cursor);
- memset(&image, 0, sizeof(image));
- image.width = cur->width;
- image.height = cur->height;
- image.size = image.width;
- if (image.height > image.size)
- image.size = image.height;
- image.xhot = cur->xhot;
- image.yhot = cur->yhot;
- image.pixels = (void *)cur->pixels;
+ display->visible_cursor = XcursorImageLoadCursor(display->dpy, &display->cursor_image);
+ display->cursor_serial = display->cursor_image.size;
+ }
+
+ return display->visible_cursor;
+}
+
+static void display_load_visible_cursor(struct display *display, XFixesCursorImage *cur)
+{
+ unsigned long *src; /* XXX deep sigh */
+ XcursorPixel *dst;
+ unsigned n;
+
+ if (cur->width != display->cursor_image.width ||
+ cur->height != display->cursor_image.height)
+ display->cursor_image.pixels = realloc(display->cursor_image.pixels,
+ 4 * cur->width * cur->height);
+ if (display->cursor_image.pixels == NULL)
+ return;
- if (display->visible_cursor)
- XFreeCursor(display->dpy, display->visible_cursor);
+ display->cursor_image.width = cur->width;
+ display->cursor_image.height = cur->height;
+ display->cursor_image.xhot = cur->xhot;
+ display->cursor_image.yhot = cur->yhot;
+ display->cursor_image.size++;
- DBG(("%s updating cursor\n", DisplayString(display->dpy)));
- display->visible_cursor = XcursorImageLoadCursor(display->dpy, &image);
+ n = cur->width*cur->height;
+ src = cur->pixels;
+ dst = display->cursor_image.pixels;
+ while (n--)
+ *dst++ = *src++;
+ DBG(("%s marking cursor changed\n", DisplayString(display->dpy)));
display->cursor_moved++;
display->cursor_visible += display->cursor != display->invisible_cursor;
}
@@ -1058,7 +1081,7 @@ static void display_flush_cursor(struct display *display)
cursor = None;
if (display->cursor_visible)
- cursor = display->visible_cursor;
+ cursor = display_get_visible_cursor(display);
if (cursor == None)
cursor = display->invisible_cursor;
if (cursor != display->cursor) {