Browse Source

Port the pointer-code to xcb

master
Axel Wagner 15 years ago
committed by Michael Stapelberg
parent
commit
0c4b4df75e
  1. 2
      Makefile
  2. 4
      cursors.h
  3. 2
      debian/control
  4. 14
      i3lock.c
  5. 73
      xcb.c
  6. 3
      xcb.h

2
Makefile

@ -11,7 +11,7 @@ CFLAGS += -pipe
CFLAGS += -Wall CFLAGS += -Wall
CFLAGS += -D_GNU_SOURCE CFLAGS += -D_GNU_SOURCE
CFLAGS += $(shell pkg-config --cflags cairo xcb-keysyms xcb-dpms) CFLAGS += $(shell pkg-config --cflags cairo xcb-keysyms xcb-dpms)
LDFLAGS += $(shell pkg-config --libs cairo xcb-keysyms xcb-dpms) LDFLAGS += $(shell pkg-config --libs cairo xcb-keysyms xcb-dpms xcb-image)
LDFLAGS += -lpam LDFLAGS += -lpam
FILES:=$(wildcard *.c) FILES:=$(wildcard *.c)

4
cursors.h

@ -1,3 +1,7 @@
#define CURS_NONE 0
#define CURS_WIN 1
#define CURS_DEFAULT 2
#define curs_invisible_width 8 #define curs_invisible_width 8
#define curs_invisible_height 8 #define curs_invisible_height 8

2
debian/control

@ -3,7 +3,7 @@ Section: utils
Priority: extra Priority: extra
Maintainer: Michael Stapelberg <michael@stapelberg.de> Maintainer: Michael Stapelberg <michael@stapelberg.de>
DM-Upload-Allowed: yes DM-Upload-Allowed: yes
Build-Depends: debhelper (>= 5), libx11-dev, libpam0g-dev, libcairo2-dev, libxcb1-dev, libxcb-dpms0-dev, libxcb-keysyms1-dev Build-Depends: debhelper (>= 5), libx11-dev, libpam0g-dev, libcairo2-dev, libxcb1-dev, libxcb-dpms0-dev, libxcb-keysyms1-dev, libxcb-image0-dev
Standards-Version: 3.8.2 Standards-Version: 3.8.2
Homepage: http://i3.zekjur.net/i3lock/ Homepage: http://i3.zekjur.net/i3lock/

14
i3lock.c

@ -27,6 +27,7 @@
#include "keysym2ucs.h" #include "keysym2ucs.h"
#include "ucs2_to_utf8.h" #include "ucs2_to_utf8.h"
#include "xcb.h" #include "xcb.h"
#include "cursors.h"
static xcb_connection_t *conn; static xcb_connection_t *conn;
static xcb_key_symbols_t *symbols; static xcb_key_symbols_t *symbols;
@ -230,6 +231,8 @@ int main(int argc, char *argv[]) {
xcb_generic_event_t *event; xcb_generic_event_t *event;
xcb_screen_t *scr; xcb_screen_t *scr;
xcb_window_t win; xcb_window_t win;
xcb_cursor_t cursor;
int curs_choice = CURS_NONE;
char o; char o;
int optind = 0; int optind = 0;
struct option longopts[] = { struct option longopts[] = {
@ -279,7 +282,12 @@ int main(int argc, char *argv[]) {
/* TODO: tile image */ /* TODO: tile image */
break; break;
case 'p': case 'p':
/* TODO: cursor */ if (!strcmp(optarg, "win")) {
curs_choice = CURS_WIN;
}
if (!strcmp(optarg, "default")) {
curs_choice = CURS_DEFAULT;
}
break; break;
default: default:
errx(1, "i3lock: Unknown option. Syntax: i3lock [-v] [-n] [-b] [-d] [-i image.png] [-c color] [-t] [-p win|default]\n"); errx(1, "i3lock: Unknown option. Syntax: i3lock [-v] [-n] [-b] [-d] [-i image.png] [-c color] [-t] [-p win|default]\n");
@ -319,7 +327,9 @@ int main(int argc, char *argv[]) {
* ready to handle the expose event immediately afterwards) */ * ready to handle the expose event immediately afterwards) */
win = open_fullscreen_window(conn, scr, color); win = open_fullscreen_window(conn, scr, color);
grab_pointer_and_keyboard(conn, scr); cursor = create_cursor(conn, scr, win, curs_choice);
grab_pointer_and_keyboard(conn, scr, cursor);
if (image_path) if (image_path)
img = cairo_image_surface_create_from_png(image_path); img = cairo_image_surface_create_from_png(image_path);

73
xcb.c

@ -9,6 +9,7 @@
*/ */
#include <xcb/xcb.h> #include <xcb/xcb.h>
#include <xcb/xcb_keysyms.h> #include <xcb/xcb_keysyms.h>
#include <xcb/xcb_image.h>
#include <xcb/dpms.h> #include <xcb/dpms.h>
#include <stdio.h> #include <stdio.h>
#include <stdlib.h> #include <stdlib.h>
@ -17,6 +18,8 @@
#include <assert.h> #include <assert.h>
#include <err.h> #include <err.h>
#include "cursors.h"
static uint32_t get_colorpixel(char *hex) { static uint32_t get_colorpixel(char *hex) {
char strgroups[3][3] = {{hex[0], hex[1], '\0'}, char strgroups[3][3] = {{hex[0], hex[1], '\0'},
{hex[2], hex[3], '\0'}, {hex[2], hex[3], '\0'},
@ -132,7 +135,7 @@ void dpms_turn_off_screen(xcb_connection_t *conn) {
* Repeatedly tries to grab pointer and keyboard (up to 1000 times). * Repeatedly tries to grab pointer and keyboard (up to 1000 times).
* *
*/ */
void grab_pointer_and_keyboard(xcb_connection_t *conn, xcb_screen_t *screen) { void grab_pointer_and_keyboard(xcb_connection_t *conn, xcb_screen_t *screen, xcb_cursor_t cursor) {
xcb_grab_pointer_cookie_t pcookie; xcb_grab_pointer_cookie_t pcookie;
xcb_grab_pointer_reply_t *preply; xcb_grab_pointer_reply_t *preply;
@ -150,7 +153,7 @@ void grab_pointer_and_keyboard(xcb_connection_t *conn, xcb_screen_t *screen) {
XCB_GRAB_MODE_ASYNC, /* pointer events should continue as normal */ XCB_GRAB_MODE_ASYNC, /* pointer events should continue as normal */
XCB_GRAB_MODE_ASYNC, /* keyboard mode */ XCB_GRAB_MODE_ASYNC, /* keyboard mode */
XCB_NONE, /* confine_to = in which window should the cursor stay */ XCB_NONE, /* confine_to = in which window should the cursor stay */
XCB_NONE, /* don’t display a special cursor */ cursor, /* we change the cursor to whatever the user wanted */
XCB_CURRENT_TIME XCB_CURRENT_TIME
); );
@ -164,6 +167,9 @@ void grab_pointer_and_keyboard(xcb_connection_t *conn, xcb_screen_t *screen) {
usleep(50); usleep(50);
} }
if (cursor != XCB_NONE)
xcb_free_cursor(conn, cursor);
while (tries-- > 0) { while (tries-- > 0) {
kcookie = xcb_grab_keyboard( kcookie = xcb_grab_keyboard(
conn, conn,
@ -187,3 +193,66 @@ void grab_pointer_and_keyboard(xcb_connection_t *conn, xcb_screen_t *screen) {
if (tries <= 0) if (tries <= 0)
errx(EXIT_FAILURE, "Cannot grab pointer/keyboard"); errx(EXIT_FAILURE, "Cannot grab pointer/keyboard");
} }
xcb_cursor_t create_cursor(xcb_connection_t *conn, xcb_screen_t *screen, xcb_window_t win, int choice) {
xcb_pixmap_t bitmap;
xcb_pixmap_t mask;
xcb_cursor_t cursor;
unsigned char* curs_bits;
unsigned char* mask_bits;
int curs_w, curs_h;
switch (choice) {
case CURS_NONE:
curs_bits = curs_invisible_bits;
mask_bits = curs_invisible_bits;
curs_w = curs_invisible_width;
curs_h = curs_invisible_height;
break;
case CURS_WIN:
curs_bits = curs_windows_bits;
mask_bits = mask_windows_bits;
curs_w = curs_windows_width;
curs_h = curs_windows_height;
break;
case CURS_DEFAULT:
default:
return XCB_NONE; /* XCB_NONE is xcb's way of saying "don't change the cursor" */
}
bitmap = xcb_create_pixmap_from_bitmap_data(conn,
win,
curs_bits,
curs_w,
curs_h,
1,
screen->white_pixel,
screen->black_pixel,
NULL);
mask = xcb_create_pixmap_from_bitmap_data(conn,
win,
mask_bits,
curs_w,
curs_h,
1,
screen->white_pixel,
screen->black_pixel,
NULL);
cursor = xcb_generate_id(conn);
xcb_create_cursor(conn,
cursor,
bitmap,
mask,
65535,65535,65535,
0,0,0,
0,0);
xcb_free_pixmap(conn, bitmap);
xcb_free_pixmap(conn, mask);
return cursor;
}

3
xcb.h

@ -5,8 +5,9 @@
xcb_visualtype_t *get_root_visual_type(xcb_screen_t *s); xcb_visualtype_t *get_root_visual_type(xcb_screen_t *s);
xcb_window_t open_fullscreen_window(xcb_connection_t *conn, xcb_screen_t *scr, char *color); xcb_window_t open_fullscreen_window(xcb_connection_t *conn, xcb_screen_t *scr, char *color);
void grab_pointer_and_keyboard(xcb_connection_t *conn, xcb_screen_t *screen); void grab_pointer_and_keyboard(xcb_connection_t *conn, xcb_screen_t *screen, xcb_cursor_t cursor);
uint32_t get_mod_mask(xcb_connection_t *conn, xcb_key_symbols_t *symbols, uint32_t keycode); uint32_t get_mod_mask(xcb_connection_t *conn, xcb_key_symbols_t *symbols, uint32_t keycode);
void dpms_turn_off_screen(xcb_connection_t *conn); void dpms_turn_off_screen(xcb_connection_t *conn);
xcb_cursor_t create_cursor(xcb_connection_t *conn, xcb_screen_t *screen, xcb_window_t win, int choice);
#endif #endif

Loading…
Cancel
Save