4

I'm trying to detect wether a screensaver is running or not.

Here's the code that I've got so far:

/* LDFLAGS='-L/usr/X11R6/lib/ -lX11 -lXext -lXss' make xidle */
#include <stdio.h>
#include <X11/Xlib.h>
#include <X11/Xutil.h>
#include <X11/extensions/scrnsaver.h>

int
main(int argc, char *argv[])
{
    XScreenSaverInfo info;
    Display *dpy = XOpenDisplay(NULL);

    if(NULL == dpy) {
        fprintf(stderr, "failed to open display\n");
        return 1;
    }

    int a = 0;
    int b = 0;
    XScreenSaverQueryExtension(dpy, &a, &b);
    printf("%d %d\n", a, b);

    XScreenSaverQueryInfo(dpy, RootWindow(dpy, DefaultScreen(dpy)), &info);
    printf("%d %d %d %d\n", info.state, info.til_or_since, info.idle, info.kind);
    return 0;
}

But info.state is always 3 (ScreenSaverDisabled). I've tested this with xscreensaver and gnome-screensaver.

Here is some example output:

92 0
3 0 9903 0

It's the same with a running screensaver or without (except info.idle of course).

Additional info:

$ X -version
X.Org X Server 1.13.0
Release Date: 2012-09-05
X Protocol Version 11, Revision 0

Window Manager: i3

Distribution: Arch Linux

EDIT: With the help of [this][1] I've created an xcb version, which also doesn't work. To exclude errors in my testing procedure, here it is: I have this code running in an endless loop while I have xscreensaver running in the background. And to actually activate the screensaver I use xscreensaver-command --activate

#include <stdlib.h>
#include <stdio.h>
#include <xcb/xcb.h>
#include <xcb/screensaver.h>

static xcb_connection_t * connection;
static xcb_screen_t * screen;

/**
 * Connects to the X server (via xcb) and gets the screen
 */
void magic_begin () {
    connection = xcb_connect (NULL, NULL);
    screen = xcb_setup_roots_iterator (xcb_get_setup (connection)).data;
}

/**
 * Asks X for the time the user has been idle
 * @returns idle time in milliseconds
 */
unsigned long magic_get_state () {
    xcb_screensaver_query_info_cookie_t cookie;
    xcb_screensaver_query_info_reply_t *info;

    cookie = xcb_screensaver_query_info (connection, screen->root);
    info = xcb_screensaver_query_info_reply (connection, cookie, NULL);

    int state = info->state;

    return state;
}

int main(int arc, char *argv[])
{
    magic_begin();
    int state = magic_get_state();
    printf("state: %d\n", state);
}


[1]: http://stackoverflow.com/questions/9049087/with-x11-how-can-i-get-the-users-time-away-from-keyboard-while-ignoring-cert
knopwob
  • 61
  • 6
  • looks OK to me and works for my ubuntu/virtualbox: https://gist.github.com/4142683 – Andrey Sidorov Nov 25 '12 at 06:55
  • Which version of Ubuntu are you using? And how exactly did you test it? I've tried it with ubuntu 10.04 and it didn't work either. I'm running xscreensaver and after that xscreensaver-command --activate. – knopwob Nov 28 '12 at 18:51
  • Ubuntu 12.04, ssh'ed to virtual box and watched output until screensaver is enabled by timeout – Andrey Sidorov Nov 29 '12 at 00:19

1 Answers1

2

I went to the xorg irc channel and was told that at least xscreensaver doesn't use the extension I use.

knopwob
  • 61
  • 6