From bb779745f45c917099fde31c4cea8bb6d6bc6f7d Mon Sep 17 00:00:00 2001
From: rathnor <rathnor>
Date: Wed, 28 Apr 2004 13:04:06 +0000
Subject: add apps file matching on role. Includes new textProperty property on
 FbWindow.

---
 ChangeLog            |  5 +++++
 src/ClientPattern.cc | 11 ++++++++++-
 src/ClientPattern.hh |  4 ++--
 src/FbTk/FbWindow.cc | 30 +++++++++++++++++++++++++++++-
 src/FbTk/FbWindow.hh |  6 ++++--
 5 files changed, 50 insertions(+), 6 deletions(-)

diff --git a/ChangeLog b/ChangeLog
index 8a7f45c..bc98ae0 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,10 @@
 (Format: Year/Month/Day)
 Changes for 0.9.10:
+*04/04/28:
+  * Add apps file matching on WM_WINDOW_ROLE (Simon)
+    - use "role=string". Particularly useful for gaim windows
+      [app] (role=buddy_list) ...
+    ClientPattern.hh/cc FbWindow.hh/cc
 *04/04/27:
   * Fix up several toolbar theme items and alignments (Simon)
     - big improvement in look/compatibility of older styles
diff --git a/src/ClientPattern.cc b/src/ClientPattern.cc
index f41ccb0..2fba185 100644
--- a/src/ClientPattern.cc
+++ b/src/ClientPattern.cc
@@ -20,12 +20,13 @@
 // FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
 // DEALINGS IN THE SOFTWARE.
 
-// $Id: ClientPattern.cc,v 1.6 2003/12/17 01:19:39 fluxgen Exp $
+// $Id: ClientPattern.cc,v 1.7 2004/04/28 13:04:06 rathnor Exp $
 
 #include "ClientPattern.hh"
 #include "RegExp.hh"
 #include "StringUtil.hh"
 #include "WinClient.hh"
+#include "FbTk/App.hh"
 
 // use GNU extensions
 #ifndef _GNU_SOURCE
@@ -110,6 +111,8 @@ ClientPattern::ClientPattern(const char *str):
                     prop = CLASS;
                 } else if (strcasecmp(memstr.c_str(), "title") == 0) {
                     prop = TITLE;
+                } else if (strcasecmp(memstr.c_str(), "role") == 0) {
+                    prop = ROLE;
                 } else {
                     had_error = pos + match.find_first_of('(') + 1;
                     break;
@@ -186,6 +189,8 @@ std::string ClientPattern::toString() const {
         case TITLE:
             pat.append("title=");
             break;
+        case ROLE:
+            pat.append("role=");
         }
 
         pat.append((*it)->orig);
@@ -246,6 +251,10 @@ std::string ClientPattern::getProperty(WinProperty prop, const WinClient &client
     case NAME:
         return client.getWMClassName();
         break;
+    case ROLE:
+        Atom wm_role = XInternAtom(FbTk::App::instance()->display(), "WM_WINDOW_ROLE", False);
+        return client.textProperty(wm_role);
+        break;
     }
     return client.getWMClassName();
 }
diff --git a/src/ClientPattern.hh b/src/ClientPattern.hh
index 7e89511..2357a24 100644
--- a/src/ClientPattern.hh
+++ b/src/ClientPattern.hh
@@ -21,7 +21,7 @@
 // FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
 // DEALINGS IN THE SOFTWARE.
 
-// $Id: ClientPattern.hh,v 1.2 2003/06/13 12:02:00 fluxgen Exp $
+// $Id: ClientPattern.hh,v 1.3 2004/04/28 13:04:06 rathnor Exp $
 
 #ifndef CLIENTPATTERN_HH
 #define CLIENTPATTERN_HH
@@ -53,7 +53,7 @@ public:
     /// @return a string representation of this pattern
     std::string toString() const;
 
-    enum WinProperty { TITLE, CLASS, NAME };
+    enum WinProperty { TITLE, CLASS, NAME, ROLE };
 
     /// Does this client match this pattern?
     bool match(const WinClient &win) const;
diff --git a/src/FbTk/FbWindow.cc b/src/FbTk/FbWindow.cc
index 195eeea..47e1399 100644
--- a/src/FbTk/FbWindow.cc
+++ b/src/FbTk/FbWindow.cc
@@ -19,7 +19,7 @@
 // FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
 // DEALINGS IN THE SOFTWARE.
 
-// $Id: FbWindow.cc,v 1.31 2004/01/21 20:07:41 fluxgen Exp $
+// $Id: FbWindow.cc,v 1.32 2004/04/28 13:04:06 rathnor Exp $
 
 #include "FbWindow.hh"
 
@@ -32,6 +32,7 @@
 #include "config.h"
 #endif // HAVE_CONFIG_H
 
+#include <X11/Xutil.h>
 #include <X11/Xatom.h>
 
 #include <cassert>
@@ -342,6 +343,33 @@ void FbWindow::reparent(const FbWindow &parent, int x, int y) {
     updateGeometry();
 }
 
+std::string FbWindow::textProperty(Atom property) const {
+    XTextProperty text_prop;
+    char ** stringlist;
+    int count;
+    std::string ret;
+
+    if (XGetTextProperty(s_display, window(), &text_prop, property) == 0)
+        return "";
+
+    if (text_prop.value == 0 || text_prop.nitems == 0)
+        return "";
+
+    if (text_prop.encoding != XA_STRING) {
+        // still returns a "StringList" despite the different name
+        if (XmbTextPropertyToTextList(s_display, &text_prop, &stringlist, &count) == 0 || count == 0)
+            return "";
+    } else {
+        if (XTextPropertyToStringList(&text_prop, &stringlist, &count) == 0 || count == 0)
+            return "";
+
+    }
+
+    ret = stringlist[0];
+    XFreeStringList(stringlist);
+    return ret;
+}
+
 bool FbWindow::property(Atom property,
                         long long_offset, long long_length,
                         bool do_delete,
diff --git a/src/FbTk/FbWindow.hh b/src/FbTk/FbWindow.hh
index d44e36f..045356f 100644
--- a/src/FbTk/FbWindow.hh
+++ b/src/FbTk/FbWindow.hh
@@ -19,7 +19,7 @@
 // FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
 // DEALINGS IN THE SOFTWARE.
 
-// $Id: FbWindow.hh,v 1.28 2004/01/21 20:22:26 fluxgen Exp $
+// $Id: FbWindow.hh,v 1.29 2004/04/28 13:04:06 rathnor Exp $
 
 #ifndef FBTK_FBWINDOW_HH
 #define FBTK_FBWINDOW_HH
@@ -28,7 +28,7 @@
 
 #include <X11/Xlib.h>
 #include <memory>
-
+#include <string>
 
 namespace FbTk {
 
@@ -135,6 +135,8 @@ public:
                         unsigned char *data,
                         int nelements);
 
+    std::string textProperty(Atom property) const;
+
     /// @return parent FbWindow
     const FbWindow *parent() const { return m_parent; }
     /// @return real X window
-- 
cgit v0.11.2