xcursor: add new cursor infra

Signed-off-by: Julien Danjou <julien@danjou.info>
This commit is contained in:
Julien Danjou 2008-11-13 11:02:19 +01:00
parent f2eab39776
commit 3cf79072cd
7 changed files with 89 additions and 117 deletions

View File

@ -41,6 +41,7 @@
#include "screen.h" #include "screen.h"
#include "common/version.h" #include "common/version.h"
#include "common/atoms.h" #include "common/atoms.h"
#include "common/xcursor.h"
#include "config.h" #include "config.h"
awesome_t globalconf; awesome_t globalconf;
@ -454,17 +455,6 @@ main(int argc, char **argv)
globalconf.font = draw_font_new("sans 8"); globalconf.font = draw_font_new("sans 8");
/* init cursors */
globalconf.cursor[CurNormal] = xutil_cursor_new(globalconf.connection, XUTIL_CURSOR_LEFT_PTR);
globalconf.cursor[CurResize] = xutil_cursor_new(globalconf.connection, XUTIL_CURSOR_SIZING);
globalconf.cursor[CurResizeH] = xutil_cursor_new(globalconf.connection, XUTIL_CURSOR_DOUBLE_ARROW_HORIZ);
globalconf.cursor[CurResizeV] = xutil_cursor_new(globalconf.connection, XUTIL_CURSOR_DOUBLE_ARROW_VERT);
globalconf.cursor[CurMove] = xutil_cursor_new(globalconf.connection, XUTIL_CURSOR_FLEUR);
globalconf.cursor[CurTopRight] = xutil_cursor_new(globalconf.connection, XUTIL_CURSOR_TOP_RIGHT_CORNER);
globalconf.cursor[CurTopLeft] = xutil_cursor_new(globalconf.connection, XUTIL_CURSOR_TOP_LEFT_CORNER);
globalconf.cursor[CurBotRight] = xutil_cursor_new(globalconf.connection, XUTIL_CURSOR_BOTTOM_RIGHT_CORNER);
globalconf.cursor[CurBotLeft] = xutil_cursor_new(globalconf.connection, XUTIL_CURSOR_BOTTOM_LEFT_CORNER);
for(colors_nbr = 0; colors_nbr < 2; colors_nbr++) for(colors_nbr = 0; colors_nbr < 2; colors_nbr++)
xcolor_init_reply(colors_reqs[colors_nbr]); xcolor_init_reply(colors_reqs[colors_nbr]);
@ -485,7 +475,7 @@ main(int argc, char **argv)
| XCB_EVENT_MASK_ENTER_WINDOW | XCB_EVENT_MASK_LEAVE_WINDOW | XCB_EVENT_MASK_ENTER_WINDOW | XCB_EVENT_MASK_LEAVE_WINDOW
| XCB_EVENT_MASK_STRUCTURE_NOTIFY | XCB_EVENT_MASK_STRUCTURE_NOTIFY
| XCB_EVENT_MASK_PROPERTY_CHANGE, | XCB_EVENT_MASK_PROPERTY_CHANGE,
globalconf.cursor[CurNormal] xcursor_new(globalconf.connection, XC_left_ptr)
}; };
xcb_change_window_attributes(globalconf.connection, xcb_change_window_attributes(globalconf.connection,

View File

@ -19,12 +19,13 @@
* *
*/ */
#include <X11/cursorfont.h> /* CURSORFONT */
#include <X11/Xlibint.h>
#include "common/xcursor.h" #include "common/xcursor.h"
#include "common/util.h" #include "common/util.h"
static char const * const xcursor[] = static char const * const xcursor_font[] =
{ {
[XC_X_cursor] = "X_cursor", [XC_X_cursor] = "X_cursor",
[XC_arrow] = "arrow", [XC_arrow] = "arrow",
@ -109,11 +110,12 @@ static char const * const xcursor[] =
* \param s The string. * \param s The string.
*/ */
uint16_t uint16_t
xcursor_fromstr(const char *s) xcursor_font_fromstr(const char *s)
{ {
for(int i = 0; i < ssizeof(xcursor); i++) if(s)
if(!a_strcmp(s, xcursor[i])) for(int i = 0; i < countof(xcursor_font); i++)
return i; if(xcursor_font[i] && !a_strcmp(s, xcursor_font[i]))
return i;
return 0; return 0;
} }
@ -121,11 +123,43 @@ xcursor_fromstr(const char *s)
* \param c The cursor. * \param c The cursor.
*/ */
const char * const char *
xcursor_tostr(uint16_t c) xcursor_font_tostr(uint16_t c)
{ {
if(c < ssizeof(xcursor)) if(c < countof(xcursor_font))
return xcursor[c]; return xcursor_font[c];
return NULL; return NULL;
} }
/** Equivalent to 'XCreateFontCursor()', error are handled by the
* default current error handler.
* \param conn The connection to the X server.
* \param cursor_font Type of cursor to use.
* \return Allocated cursor font.
*/
xcb_cursor_t
xcursor_new(xcb_connection_t *conn, uint16_t cursor_font)
{
static xcb_font_t font = XCB_NONE;
static xcb_cursor_t xcursor[countof(xcursor_font)];
/* Get the font for the cursor */
if(!font)
{
font = xcb_generate_id(conn);
xcb_open_font(conn, font, sizeof(CURSORFONT) - 1, CURSORFONT);
}
if(!xcursor[cursor_font])
{
xcursor[cursor_font] = xcb_generate_id(conn);
xcb_create_glyph_cursor(conn, xcursor[cursor_font], font, font,
cursor_font, cursor_font + 1,
0, 0, 0,
65535, 65535, 65535);
}
return xcursor[cursor_font];
}
// vim: filetype=c:expandtab:shiftwidth=4:tabstop=8:softtabstop=4:encoding=utf-8:textwidth=80 // vim: filetype=c:expandtab:shiftwidth=4:tabstop=8:softtabstop=4:encoding=utf-8:textwidth=80

View File

@ -22,10 +22,12 @@
#ifndef AWESOME_COMMON_XCURSORS_H #ifndef AWESOME_COMMON_XCURSORS_H
#define AWESOME_COMMON_XCURSORS_H #define AWESOME_COMMON_XCURSORS_H
#include <stdint.h> #include <X11/cursorfont.h>
#include <xcb/xcb.h>
uint16_t xcursor_fromstr(const char *); uint16_t xcursor_font_fromstr(const char *);
const char * xcursor_tostr(uint16_t); const char * xcursor_font_tostr(uint16_t);
xcb_cursor_t xcursor_new(xcb_connection_t *, uint16_t);
#endif #endif
// vim: filetype=c:expandtab:shiftwidth=4:tabstop=8:softtabstop=4:encoding=utf-8:textwidth=80 // vim: filetype=c:expandtab:shiftwidth=4:tabstop=8:softtabstop=4:encoding=utf-8:textwidth=80

View File

@ -25,9 +25,6 @@
#include <xcb/xcb_atom.h> #include <xcb/xcb_atom.h>
#include <xcb/xcb_icccm.h> #include <xcb/xcb_icccm.h>
/* CURSORFONT */
#include <X11/Xlibint.h>
#include "common/xutil.h" #include "common/xutil.h"
#include "common/atoms.h" #include "common/atoms.h"
@ -395,34 +392,6 @@ xutil_button_fromint(int button)
return 0; return 0;
} }
/** Equivalent to 'XCreateFontCursor()', error are handled by the
* default current error handler.
* \param conn The connection to the X server.
* \param cursor_font Type of cursor to use.
* \return Allocated cursor font.
*/
xcb_cursor_t
xutil_cursor_new(xcb_connection_t *conn, uint16_t cursor_font)
{
static xcb_font_t font = XCB_NONE;
xcb_cursor_t cursor;
/* Get the font for the cursor */
if(!font)
{
font = xcb_generate_id(conn);
xcb_open_font(conn, font, sizeof(CURSORFONT) - 1, CURSORFONT);
}
cursor = xcb_generate_id(conn);
xcb_create_glyph_cursor(conn, cursor, font, font,
cursor_font, cursor_font + 1,
0, 0, 0,
65535, 65535, 65535);
return cursor;
}
/** Convert a root window a physical screen ID. /** Convert a root window a physical screen ID.
* \param connection The connection to the X server. * \param connection The connection to the X server.
* \param root Root window. * \param root Root window.

View File

@ -34,17 +34,6 @@
#define XUTIL_MASK_CLEAN(mask) (mask & ~(globalconf.numlockmask | XCB_MOD_MASK_LOCK)) #define XUTIL_MASK_CLEAN(mask) (mask & ~(globalconf.numlockmask | XCB_MOD_MASK_LOCK))
/* See http://tronche.com/gui/x/xlib/appendix/b/ for values */
#define XUTIL_CURSOR_FLEUR 52
#define XUTIL_CURSOR_LEFT_PTR 68
#define XUTIL_CURSOR_SIZING 120
#define XUTIL_CURSOR_BOTTOM_LEFT_CORNER 12
#define XUTIL_CURSOR_BOTTOM_RIGHT_CORNER 14
#define XUTIL_CURSOR_TOP_LEFT_CORNER 134
#define XUTIL_CURSOR_TOP_RIGHT_CORNER 136
#define XUTIL_CURSOR_DOUBLE_ARROW_HORIZ 108
#define XUTIL_CURSOR_DOUBLE_ARROW_VERT 116
/* X error codes */ /* X error codes */
/* Everything's okay */ /* Everything's okay */
@ -112,7 +101,6 @@ typedef struct
bool xutil_error_init(const xcb_generic_error_t *, xutil_error_t *); bool xutil_error_init(const xcb_generic_error_t *, xutil_error_t *);
xcb_keysym_t xutil_key_mask_fromstr(const char *, size_t); xcb_keysym_t xutil_key_mask_fromstr(const char *, size_t);
unsigned int xutil_button_fromint(int); unsigned int xutil_button_fromint(int);
xcb_cursor_t xutil_cursor_new(xcb_connection_t *, uint16_t);
static inline void static inline void
xutil_error_wipe(xutil_error_t *err) xutil_error_wipe(xutil_error_t *err)

80
mouse.c
View File

@ -28,6 +28,7 @@
#include "layouts/floating.h" #include "layouts/floating.h"
#include "layouts/tile.h" #include "layouts/tile.h"
#include "layouts/magnifier.h" #include "layouts/magnifier.h"
#include "common/xcursor.h"
#define MOUSEMASK (XCB_EVENT_MASK_BUTTON_PRESS \ #define MOUSEMASK (XCB_EVENT_MASK_BUTTON_PRESS \
| XCB_EVENT_MASK_BUTTON_RELEASE \ | XCB_EVENT_MASK_BUTTON_RELEASE \
@ -356,21 +357,18 @@ mouse_query_pointer_root(int *s, int *x, int *y, uint16_t *mask)
/** Grab the Pointer. /** Grab the Pointer.
* \param window The window grabbed. * \param window The window grabbed.
* \param cursor The cursor to display (see struct.h CurNormal, CurResize, etc). * \param cursor The cursor to display.
* \return True on success, false if an error occured. * \return True on success, false if an error occured.
*/ */
static bool static bool
mouse_grab_pointer(xcb_window_t window, size_t cursor) mouse_grab_pointer(xcb_window_t window, xcb_cursor_t cursor)
{ {
xcb_grab_pointer_cookie_t grab_ptr_c; xcb_grab_pointer_cookie_t grab_ptr_c;
xcb_grab_pointer_reply_t *grab_ptr_r; xcb_grab_pointer_reply_t *grab_ptr_r;
if(cursor >= CurLast)
cursor = CurNormal;
grab_ptr_c = xcb_grab_pointer_unchecked(globalconf.connection, false, window, grab_ptr_c = xcb_grab_pointer_unchecked(globalconf.connection, false, window,
MOUSEMASK, XCB_GRAB_MODE_ASYNC, XCB_GRAB_MODE_ASYNC, MOUSEMASK, XCB_GRAB_MODE_ASYNC, XCB_GRAB_MODE_ASYNC,
window, globalconf.cursor[cursor], XCB_CURRENT_TIME); window, cursor, XCB_CURRENT_TIME);
grab_ptr_r = xcb_grab_pointer_reply(globalconf.connection, grab_ptr_c, NULL); grab_ptr_r = xcb_grab_pointer_reply(globalconf.connection, grab_ptr_c, NULL);
if(!grab_ptr_r) if(!grab_ptr_r)
@ -497,7 +495,7 @@ mouse_client_move(client_t *c, int snap, bool infobox)
|| c->type == WINDOW_TYPE_DESKTOP || c->type == WINDOW_TYPE_DESKTOP
|| c->type == WINDOW_TYPE_SPLASH || c->type == WINDOW_TYPE_SPLASH
|| c->type == WINDOW_TYPE_DOCK || c->type == WINDOW_TYPE_DOCK
|| !mouse_grab_pointer(root, CurMove)) || !mouse_grab_pointer(root, xcursor_new(globalconf.connection, XC_fleur)))
return; return;
if(infobox && (client_isfloating(c) || layout == layout_floating)) if(infobox && (client_isfloating(c) || layout == layout_floating))
@ -592,7 +590,7 @@ mouse_client_resize_floating(client_t *c, corner_t corner, bool infobox)
int mouse_x = 0, mouse_y = 0; int mouse_x = 0, mouse_y = 0;
/* the infobox */ /* the infobox */
simple_window_t sw; simple_window_t sw;
size_t cursor = CurResize; xcb_cursor_t cursor;
int top, bottom, left, right; int top, bottom, left, right;
/* do not resize fixed client */ /* do not resize fixed client */
@ -620,17 +618,17 @@ mouse_client_resize_floating(client_t *c, corner_t corner, bool infobox)
switch(corner) switch(corner)
{ {
default: default:
cursor = CurTopLeft; cursor = xcursor_new(globalconf.connection, XC_top_left_corner);
break; break;
case TopRightCorner: case TopRightCorner:
cursor = CurTopRight; cursor = xcursor_new(globalconf.connection, XC_top_right_corner);
break; break;
case BottomLeftCorner: case BottomLeftCorner:
cursor = CurBotLeft; cursor = xcursor_new(globalconf.connection, XC_bottom_left_corner);
break; break;
case BottomRightCorner: case BottomRightCorner:
cursor = CurBotRight; cursor = xcursor_new(globalconf.connection, XC_bottom_right_corner);
break; break;
} }
/* grab the pointer */ /* grab the pointer */
@ -667,13 +665,13 @@ mouse_client_resize_floating(client_t *c, corner_t corner, bool infobox)
switch(corner) switch(corner)
{ {
default: cursor = CurTopLeft; break; default: cursor = xcursor_new(globalconf.connection, XC_top_left_corner); break;
case TopRightCorner: cursor = CurTopRight; break; case TopRightCorner: cursor = xcursor_new(globalconf.connection, XC_top_right_corner); break;
case BottomLeftCorner: cursor = CurBotLeft; break; case BottomLeftCorner: cursor = xcursor_new(globalconf.connection, XC_bottom_left_corner); break;
case BottomRightCorner: cursor = CurBotRight; break; case BottomRightCorner: cursor = xcursor_new(globalconf.connection, XC_bottom_right_corner); break;
} }
xcb_change_active_pointer_grab(globalconf.connection, globalconf.cursor[cursor], xcb_change_active_pointer_grab(globalconf.connection, cursor,
XCB_CURRENT_TIME, MOUSEMASK); XCB_CURRENT_TIME, MOUSEMASK);
} }
@ -744,7 +742,7 @@ mouse_client_resize_tiled(client_t *c)
layout_t *layout; layout_t *layout;
int mouse_x = 0, mouse_y = 0; int mouse_x = 0, mouse_y = 0;
size_t cursor = CurResize; xcb_cursor_t cursor;
screen = xutil_screen_get(globalconf.connection, c->phys_screen); screen = xutil_screen_get(globalconf.connection, c->phys_screen);
tag = tags_get_current(c->screen)[0]; tag = tags_get_current(c->screen)[0];
@ -761,22 +759,22 @@ mouse_client_resize_tiled(client_t *c)
if(layout == layout_tile) if(layout == layout_tile)
{ {
mouse_x = area.x + area.width * tag->mwfact; mouse_x = area.x + area.width * tag->mwfact;
cursor = CurResizeH; cursor = xcursor_new(globalconf.connection, XC_bottom_right_corner);
} }
else if(layout == layout_tileleft) else if(layout == layout_tileleft)
{ {
mouse_x = area.x + area.width * (1. - tag->mwfact); mouse_x = area.x + area.width * (1. - tag->mwfact);
cursor = CurResizeH; cursor = xcursor_new(globalconf.connection, XC_sb_h_double_arrow);
} }
else if(layout == layout_tilebottom) else if(layout == layout_tilebottom)
{ {
mouse_y = area.y + area.height * tag->mwfact; mouse_y = area.y + area.height * tag->mwfact;
cursor = CurResizeV; cursor = xcursor_new(globalconf.connection, XC_sb_v_double_arrow);
} }
else if(layout == layout_tiletop) else if(layout == layout_tiletop)
{ {
mouse_y = area.y + area.height * (1. - tag->mwfact); mouse_y = area.y + area.height * (1. - tag->mwfact);
cursor = CurResizeV; cursor = xcursor_new(globalconf.connection, XC_sb_v_double_arrow);
} }
else else
return; return;
@ -842,7 +840,7 @@ mouse_client_resize_magnified(client_t *c, bool infobox)
/* mouse position */ /* mouse position */
int mouse_x = 0, mouse_y = 0; int mouse_x = 0, mouse_y = 0;
/* cursor while grabbing */ /* cursor while grabbing */
size_t cursor = CurResize; xcb_cursor_t cursor;
corner_t corner = AutoCorner; corner_t corner = AutoCorner;
/* current tag */ /* current tag */
tag_t *tag; tag_t *tag;
@ -876,17 +874,17 @@ mouse_client_resize_magnified(client_t *c, bool infobox)
switch(corner) switch(corner)
{ {
default: default:
cursor = CurTopLeft; cursor = xcursor_new(globalconf.connection, XC_top_left_corner);
break; break;
case TopRightCorner: case TopRightCorner:
cursor = CurTopRight; cursor = xcursor_new(globalconf.connection, XC_top_right_corner);
break; break;
case BottomLeftCorner: case BottomLeftCorner:
cursor = CurBotLeft; cursor = xcursor_new(globalconf.connection, XC_bottom_left_corner);
break; break;
case BottomRightCorner: case BottomRightCorner:
cursor = CurBotRight; cursor = xcursor_new(globalconf.connection, XC_bottom_right_corner);
break; break;
} }
/* grab pointer */ /* grab pointer */

View File

@ -50,13 +50,6 @@ typedef enum
WIBOX_TYPE_TITLEBAR WIBOX_TYPE_TITLEBAR
} wibox_type_t; } wibox_type_t;
/** Cursors */
enum
{
CurNormal, CurResize, CurResizeH, CurResizeV, CurMove,
CurTopLeft, CurTopRight, CurBotLeft, CurBotRight, CurLast
};
typedef struct button_t button_t; typedef struct button_t button_t;
typedef struct widget_t widget_t; typedef struct widget_t widget_t;
typedef struct widget_node_t widget_node_t; typedef struct widget_node_t widget_node_t;
@ -314,8 +307,6 @@ struct awesome_t
unsigned int capslockmask; unsigned int capslockmask;
/** Check for XRandR extension */ /** Check for XRandR extension */
bool have_randr; bool have_randr;
/** Cursors */
xcb_cursor_t cursor[CurLast];
/** Clients list */ /** Clients list */
client_t *clients; client_t *clients;
/** Embedded windows */ /** Embedded windows */