Plicatibu
Plicatibu

Reputation: 1722

How to know which window has focus and how to change it?

I would like to know how can I ask X11 which windows has the focus. And if for any reason my own application (that may be visible or not) got the focus I want be able to let the former windows get the focus again.

For instance, my application is running with many others (e.g. firefox, gvim, nautilus, ...)

Suppose that at first firefox has focus and that the user clicked on my app which now has the focus. I want that my application put the focus on firefox again.

Does anyone knows how to achieve this? Books recommendations would be very nice.

Upvotes: 20

Views: 23570

Answers (4)

John P
John P

Reputation: 1581

I recommend an application called XDoTool. It supports quite a lot of queries, controls, and even hooks.

> xdotool getwindowfocus               # 29360135
> xdotool getwindowfocus getwindowpid  # 12988
> xdotool getwindowfocus getwindowname # tilda
> xdotool getwindowfocus behave '%@' blur getmouselocation
#      or focus, mouse-enter, etc.
x:514 y:317 screen:0 window:56623121
x:271 y:26 screen:0 window:56623121
...

Commands like behave accept a callback, which can be built-in like getmouselocation or external like exec notify-send 'focused window', exec zsh myscript.zsh, etc., however you want to use it.

Edit - you can focus using xdotool windowfocus [options] [window], as in xdotool search --class firefox windowfocus. In my case this causes errors because Firefox shows up as a couple dozen 'windows', but all have the same PID; it works given the right ID. Hopefully that's a start.

Edit 2 - the 'window ID' is the decimal representation of the window pointer, e.g. from xprop:

> xprop -root _NET_ACTIVE_WINDOW
_NET_ACTIVE_WINDOW(WINDOW): window id # 0x1c00007, 0x0
> xdotool getwindowfocus
29360135
> printf '%d\n' '0x1c00007'
29360135

Upvotes: 13

Neale Pickett
Neale Pickett

Reputation: 306

You probably want the XGetInputFocus call.

Window focused;
int revert_to;

XGetInputFocus(dpy, &focused, &revert_to);

In this snippet, focused will be the window with current input focus, getting keyboard events and mouse button presses.

This will work even if the window manager does not set the _NET_ACTIVE_WINDOW property on the root window, as specified by EWMH. A few window managers, such as dwm and my 9wm, don't set this.

Upvotes: 12

Marten
Marten

Reputation: 1156

Take a look at the _NET_ACTIVE_WINDOW value of the root window which is set by most modern window managers:

xprop -root _NET_ACTIVE_WINDOW

This value can, of course, be obtained using Xlib library calls.

Upvotes: 24

Aiden Bell
Aiden Bell

Reputation: 28386

Use this XQueryTree to find the currently active, or top-most window.

Here is a function, when given a display, it will find the current window in focus:

static Window
GetCurrWindow(d)
Display *d;
{
Window foo;
Window win;
int bar;

    do{
    (void) XQueryPointer(d, DefaultRootWindow(d), &foo, &win,
        &bar, &bar, &bar, &bar, &bar);
    } while(win <= 0);


#ifdef VROOT
    {
    int n;
    Window *wins;
    XWindowAttributes xwa;

    (void) fputs("=xwa=", stdout);

    /* do{  */
        XQueryTree(d, win, &foo, &foo, &wins, &n);
    /* } while(wins <= 0); */
    bar=0;
    while(--n >= 0) {
        XGetWindowAttributes(d, wins[n], &xwa);
        if( (xwa.width * xwa.height) > bar) {
        win = wins[n];
        bar = xwa.width * xwa.height;
        }
        n--;
    }
    XFree(wins);
    }
#endif
    return(win);
}

http://tronche.com/gui/x/xlib/window-information/XQueryTree.html

I found the source:

http://examples.oreilly.com/networksa/tools/xsnoop.c

Good Luck

Upvotes: 7

Related Questions