Back to index

easystroke  0.5.5.1
Classes | Public Types | Public Member Functions | Public Attributes | Static Public Attributes | Private Member Functions | Private Attributes | Friends
Grabber Class Reference

#include <grabber.h>

Collaboration diagram for Grabber:
Collaboration graph
[legend]

List of all members.

Classes

struct  XiDevice

Public Types

enum  State { NONE, BUTTON, SELECT, RAW }
enum  GrabState { GrabNo, GrabYes, GrabRaw }
typedef std::map< XID,
boost::shared_ptr< XiDevice > > 
DeviceMap

Public Member Functions

XiDeviceget_xi_dev (int id)
 Grabber ()
 ~Grabber ()
bool handle (XEvent &ev)
void queue_suspend ()
void queue_resume ()
void new_device (XIDeviceInfo *)
bool is_grabbed (guint b)
bool is_instant (guint b)
bool is_click_hold (guint b)
void hierarchy_changed (XIHierarchyEvent *)
int get_default_button ()
void unminimize ()

Public Attributes

Children children
int opcode
int event
int error
Out< std::string > * current_class

Static Public Attributes

static const char * state_name [4] = { "None", "Button", "Select", "Raw" }

Private Member Functions

bool init_xi ()
void set ()
void grab_xi (bool)
void grab_xi_devs (GrabState)
void update_excluded ()
void grab (State s)
void suspend ()
void resume ()
void update ()

Private Attributes

DeviceMap xi_devs
State current
State grabbed
bool xi_grabbed
GrabState xi_devs_grabbed
int suspended
bool active
Cursor cursor_select
ButtonInfo grabbed_button
std::vector< ButtonInfobuttons

Friends

class Handler
class StrokeHandler
class Button
class Prefs

Detailed Description

Definition at line 56 of file grabber.h.


Member Typedef Documentation

typedef std::map<XID, boost::shared_ptr<XiDevice> > Grabber::DeviceMap

Definition at line 85 of file grabber.h.


Member Enumeration Documentation

Enumerator:
GrabNo 
GrabYes 
GrabRaw 

Definition at line 64 of file grabber.h.

Enumerator:
NONE 
BUTTON 
SELECT 
RAW 

Definition at line 63 of file grabber.h.


Constructor & Destructor Documentation

Definition at line 225 of file grabber.cc.

                 : children(ROOT) {
       current = BUTTON;
       suspended = 0;
       suspend();
       active = true;
       grabbed = NONE;
       xi_grabbed = false;
       xi_devs_grabbed = GrabNo;
       grabbed_button.button = 0;
       grabbed_button.state = 0;
       cursor_select = XCreateFontCursor(dpy, XC_crosshair);
       init_xi();
       prefs.excluded_devices.connect(new IdleNotifier(sigc::mem_fun(*this, &Grabber::update)));
       prefs.button.connect(new IdleNotifier(sigc::mem_fun(*this, &Grabber::update)));
       current_class = fun2(&get_wm_class, current_app_window, stroke_app);
       current_class->connect(new IdleNotifier(sigc::mem_fun(*this, &Grabber::update)));
       disabled.connect(new IdleNotifier(sigc::mem_fun(*this, &Grabber::set)));
       update();
       resume();
}

Here is the call graph for this function:

Definition at line 246 of file grabber.cc.

                  {
       XFreeCursor(dpy, cursor_select);
}

Member Function Documentation

int Grabber::get_default_button ( ) [inline]

Definition at line 127 of file grabber.h.

{ return grabbed_button.button; }

Here is the caller graph for this function:

Definition at line 411 of file grabber.cc.

                                           {
       DeviceMap::iterator i = xi_devs.find(id);
       return i == xi_devs.end() ? NULL : i->second.get();
}

Here is the caller graph for this function:

void Grabber::grab ( State  s) [inline, private]

Definition at line 107 of file grabber.h.

{ current = s; set(); }

Here is the caller graph for this function:

void Grabber::grab_xi ( bool  grab) [private]

Definition at line 436 of file grabber.cc.

                               {
       if (!xi_grabbed == !grab)
              return;
       xi_grabbed = grab;
       for (DeviceMap::iterator i = xi_devs.begin(); i != xi_devs.end(); ++i)
              if (i->second->active)
                     for (std::vector<ButtonInfo>::iterator j = buttons.begin(); j != buttons.end(); j++)
                            i->second->grab_button(*j, grab);
}

Here is the call graph for this function:

Here is the caller graph for this function:

void Grabber::grab_xi_devs ( GrabState  grab) [private]

Definition at line 457 of file grabber.cc.

                                         {
       if (xi_devs_grabbed == grab)
              return;
       xi_devs_grabbed = grab;
       for (DeviceMap::iterator i = xi_devs.begin(); i != xi_devs.end(); ++i)
              i->second->grab_device(grab);
}

Here is the call graph for this function:

Here is the caller graph for this function:

bool Grabber::handle ( XEvent &  ev) [inline]

Definition at line 114 of file grabber.h.

{ return children.handle(ev); }

Here is the call graph for this function:

Here is the caller graph for this function:

void Grabber::hierarchy_changed ( XIHierarchyEvent *  event)

Definition at line 312 of file grabber.cc.

                                                       {
       for (int i = 0; i < event->num_info; i++) {
              XIHierarchyInfo *info = event->info + i;
              if (info->flags & XISlaveAdded) {
                     int n;
                     XIDeviceInfo *dev_info = XIQueryDevice(dpy, info->deviceid, &n);
                     if (!dev_info)
                            return;
                     new_device(dev_info);
                     XIFreeDeviceInfo(dev_info);
                     update_excluded();
                     win->prefs_tab->update_device_list();
              } else if (info->flags & XISlaveRemoved) {
                     if (verbosity >= 1)
                            printf("Device %d removed.\n", info->deviceid);
                     xi_devs.erase(info->deviceid);
                     win->prefs_tab->update_device_list();
                     if (current_dev && current_dev->dev == info->deviceid)
                            current_dev = NULL;
              } else if (info->flags & (XISlaveAttached | XISlaveDetached)) {
                     DeviceMap::iterator i = xi_devs.find(info->deviceid);
                     if (i == xi_devs.end())
                            return;
                     i->second->master = info->attachment;
              }
       }
}

Here is the call graph for this function:

Here is the caller graph for this function:

bool Grabber::init_xi ( ) [private]

Definition at line 250 of file grabber.cc.

                      {
       /* XInput Extension available? */
       int major = 2, minor = 0;
       if (!XQueryExtension(dpy, "XInputExtension", &opcode, &event, &error) ||
                     XIQueryVersion(dpy, &major, &minor) == BadRequest ||
                     major < 2) {
              printf("Error: This version of easystroke needs an XInput 2.0-aware X server.\n"
                            "Please downgrade to easystroke 0.4.x or upgrade your X server to 1.7.\n");
              exit(EXIT_FAILURE);
       }

       int n;
       XIDeviceInfo *info = XIQueryDevice(dpy, XIAllDevices, &n);
       if (!info) {
              printf("Warning: No XInput devices available\n");
              return false;
       }

       current_dev = NULL;

       for (int i = 0; i < n; i++)
              new_device(info + i);
       XIFreeDeviceInfo(info);
       prefs.excluded_devices.connect(new IdleNotifier(sigc::mem_fun(*this, &Grabber::update_excluded)));
       update_excluded();
       xi_grabbed = false;
       set();

       if (!xi_devs.size()) {
              printf("Error: No suitable XInput devices found\n");
              exit(EXIT_FAILURE);
       }

       // TODO: Proximity
       device_mask.deviceid = XIAllDevices;
       device_mask.mask = device_mask_data;
       device_mask.mask_len = sizeof(device_mask_data);
       memset(device_mask.mask, 0, device_mask.mask_len);
       XISetMask(device_mask.mask, XI_ButtonPress);
       XISetMask(device_mask.mask, XI_ButtonRelease);
       XISetMask(device_mask.mask, XI_Motion);

       raw_mask.deviceid = XIAllDevices;
       raw_mask.mask = raw_mask_data;
       raw_mask.mask_len = sizeof(raw_mask_data);
       memset(raw_mask.mask, 0, raw_mask.mask_len);
       XISetMask(raw_mask.mask, XI_ButtonPress);
       XISetMask(raw_mask.mask, XI_ButtonRelease);
       XISetMask(raw_mask.mask, XI_RawMotion);

       XIEventMask global_mask;
       unsigned char data[2] = { 0, 0 };
       global_mask.deviceid = XIAllDevices;
       global_mask.mask = data;
       global_mask.mask_len = sizeof(data);
       XISetMask(global_mask.mask, XI_HierarchyChanged);

       XISelectEvents(dpy, ROOT, &global_mask, 1);

       return true;
}

Here is the call graph for this function:

Here is the caller graph for this function:

bool Grabber::is_click_hold ( guint  b)

Definition at line 508 of file grabber.cc.

                                   {
       for (std::vector<ButtonInfo>::iterator i = buttons.begin(); i != buttons.end(); i++)
              if (i->button == b && i->click_hold)
                     return true;
       return false;
}

Here is the caller graph for this function:

bool Grabber::is_grabbed ( guint  b)

Definition at line 494 of file grabber.cc.

                                {
       for (std::vector<ButtonInfo>::iterator i = buttons.begin(); i != buttons.end(); i++)
              if (i->button == b)
                     return true;
       return false;
}
bool Grabber::is_instant ( guint  b)

Definition at line 501 of file grabber.cc.

                                {
       for (std::vector<ButtonInfo>::iterator i = buttons.begin(); i != buttons.end(); i++)
              if (i->button == b && i->instant)
                     return true;
       return false;
}

Here is the caller graph for this function:

void Grabber::new_device ( XIDeviceInfo *  info)

Definition at line 361 of file grabber.cc.

                                           {
       if (info->use == XIMasterPointer || info->use == XIMasterKeyboard)
              return;

       if (is_xtest_device(info->deviceid))
              return;

       for (int j = 0; j < info->num_classes; j++)
              if (info->classes[j]->type == ButtonClass) {
                     XiDevice *xi_dev = new XiDevice(this, info);
                     xi_devs[info->deviceid].reset(xi_dev);
                     return;
              }
}

Here is the call graph for this function:

Here is the caller graph for this function:

void Grabber::queue_resume ( ) [inline]

Definition at line 118 of file grabber.h.

{ queue(sigc::mem_fun(*this, &Grabber::resume)); }

Here is the call graph for this function:

Here is the caller graph for this function:

void Grabber::queue_suspend ( ) [inline]

Definition at line 117 of file grabber.h.

{ queue(sigc::mem_fun(*this, &Grabber::suspend)); }

Here is the call graph for this function:

Here is the caller graph for this function:

void Grabber::resume ( ) [inline, private]

Definition at line 109 of file grabber.h.

{ if (suspended) suspended--; set(); }

Here is the caller graph for this function:

void Grabber::set ( ) [private]

Definition at line 465 of file grabber.cc.

                  {
       bool act = !suspended && ((active && !disabled.get()) || (current != NONE && current != BUTTON));
       grab_xi(act && current != SELECT);
       if (!act)
              grab_xi_devs(GrabNo);
       else if (current == NONE)
              grab_xi_devs(GrabYes);
       else if (current == RAW)
              grab_xi_devs(GrabRaw);
       else
              grab_xi_devs(GrabNo);
       State old = grabbed;
       grabbed = act ? current : NONE;
       if (old == grabbed)
              return;
       if (verbosity >= 2)
              printf("grabbing: %s\n", state_name[grabbed]);

       if (old == SELECT)
              XUngrabPointer(dpy, CurrentTime);

       if (grabbed == SELECT) {
              int code = XGrabPointer(dpy, ROOT, False, ButtonPressMask,
                            GrabModeAsync, GrabModeAsync, ROOT, cursor_select, CurrentTime);
              if (code != GrabSuccess)
                     throw GrabFailedException(code);
       }
}

Here is the call graph for this function:

Here is the caller graph for this function:

void Grabber::suspend ( ) [inline, private]

Definition at line 108 of file grabber.h.

{ suspended++; set(); }

Here is the caller graph for this function:

Definition at line 214 of file grabber.cc.

                         {
       if (minimized.empty())
              return;
       Window w;
       unsigned int n;
       minimized.pop(n, w);
       activate(w, CurrentTime);
}

Here is the call graph for this function:

Here is the caller graph for this function:

void Grabber::update ( ) [private]

Definition at line 522 of file grabber.cc.

                     {
       std::map<std::string, RButtonInfo>::const_iterator i = prefs.exceptions.ref().find(current_class->get());
       active = true;
       ButtonInfo bi = prefs.button.ref();
       if (i != prefs.exceptions.ref().end()) {
              if (i->second)
                     bi = *i->second;
              else
                     active = false;
       }
       const ActionListDiff *a = stroke_app.get();
       if (!a)
              a = actions.get_action_list(current_class->get());
       if (active && actions.get_root()->size_rec() && !a->count_actions())
              active = false;
       const std::vector<ButtonInfo> &extra = prefs.extra_buttons.ref();
       if (grabbed_button == bi && buttons.size() == extra.size() + 1 &&
                     std::equal(extra.begin(), extra.end(), ++buttons.begin())) {
              set();
              return;
       }
       suspend();
       grabbed_button = bi;
       buttons.clear();
       buttons.reserve(extra.size() + 1);
       buttons.push_back(bi);
       for (std::vector<ButtonInfo>::const_iterator i = extra.begin(); i != extra.end(); ++i)
              if (!i->overlap(bi))
                     buttons.push_back(*i);
       resume();
}

Here is the call graph for this function:

Here is the caller graph for this function:

void Grabber::update_excluded ( ) [private]

Definition at line 340 of file grabber.cc.

                              {
       suspend();
       for (DeviceMap::iterator i = xi_devs.begin(); i != xi_devs.end(); ++i)
              i->second->active = !prefs.excluded_devices.ref().count(i->second->name);
       resume();
}

Here is the call graph for this function:

Here is the caller graph for this function:


Friends And Related Function Documentation

friend class Button [friend]

Definition at line 59 of file grabber.h.

friend class Handler [friend]

Definition at line 57 of file grabber.h.

friend class Prefs [friend]

Definition at line 60 of file grabber.h.

friend class StrokeHandler [friend]

Definition at line 58 of file grabber.h.


Member Data Documentation

bool Grabber::active [private]

Definition at line 96 of file grabber.h.

std::vector<ButtonInfo> Grabber::buttons [private]

Definition at line 99 of file grabber.h.

Definition at line 62 of file grabber.h.

Definition at line 92 of file grabber.h.

Out<std::string>* Grabber::current_class

Definition at line 115 of file grabber.h.

Cursor Grabber::cursor_select [private]

Definition at line 97 of file grabber.h.

Definition at line 86 of file grabber.h.

Definition at line 86 of file grabber.h.

Definition at line 92 of file grabber.h.

Definition at line 98 of file grabber.h.

Definition at line 86 of file grabber.h.

const char * Grabber::state_name = { "None", "Button", "Select", "Raw" } [static]

Definition at line 65 of file grabber.h.

int Grabber::suspended [private]

Definition at line 95 of file grabber.h.

Definition at line 91 of file grabber.h.

Definition at line 94 of file grabber.h.

bool Grabber::xi_grabbed [private]

Definition at line 93 of file grabber.h.


The documentation for this class was generated from the following files: