]> Dogcows Code - chaz/openbox/blobdiff - openbox/menuframe.c
cache pipe menus until the menus close
[chaz/openbox] / openbox / menuframe.c
index 5782b7ac25e8a09890f6f4bd510d9cb5bee367a6..fa9e8e9d9ab1ab59e1c93a9670f2615c663232e2 100644 (file)
@@ -45,6 +45,7 @@ static ObMenuEntryFrame* menu_entry_frame_new(ObMenuEntry *entry,
 static void menu_entry_frame_free(ObMenuEntryFrame *self);
 static void menu_frame_update(ObMenuFrame *self);
 static gboolean menu_entry_frame_submenu_timeout(gpointer data);
+static void menu_frame_hide(ObMenuFrame *self);
 
 static Window createWindow(Window parent, gulong mask,
                            XSetWindowAttributes *attrib)
@@ -498,6 +499,8 @@ static void menu_entry_frame_render(ObMenuEntryFrame *self)
             self->entry->data.normal.icon_width;
         self->a_icon->texture[0].data.rgba.height =
             self->entry->data.normal.icon_height;
+        self->a_icon->texture[0].data.rgba.alpha =
+            self->entry->data.normal.icon_alpha;
         self->a_icon->texture[0].data.rgba.data =
             self->entry->data.normal.icon_data;
         self->a_icon->surface.parent = item_a;
@@ -911,10 +914,13 @@ static gboolean menu_frame_show(ObMenuFrame *self)
 
     if (menu_frame_visible == NULL) {
         /* no menus shown yet */
-        if (!grab_pointer(TRUE, TRUE, OB_CURSOR_POINTER))
+
+        /* grab the pointer in such a way as to pass through "owner events"
+           so that we can get enter/leave notifies in the menu. */
+        if (!grab_pointer(TRUE, FALSE, OB_CURSOR_POINTER))
             return FALSE;
-        if (!grab_keyboard(TRUE)) {
-            grab_pointer(FALSE, TRUE, OB_CURSOR_POINTER);
+        if (!grab_keyboard()) {
+            ungrab_pointer();
             return FALSE;
         }
     }
@@ -932,6 +938,7 @@ static gboolean menu_frame_show(ObMenuFrame *self)
 gboolean menu_frame_show_topmenu(ObMenuFrame *self, gint x, gint y,
                                  gint button)
 {
+    gint px, py;
     guint i;
 
     if (menu_frame_is_visible(self))
@@ -957,14 +964,20 @@ gboolean menu_frame_show_topmenu(ObMenuFrame *self, gint x, gint y,
 
     XMapWindow(ob_display, self->window);
 
+    if (screen_pointer_pos(&px, &py)) {
+        ObMenuEntryFrame *e = menu_entry_frame_under(px, py);
+        if (e && e->frame == self)
+            e->ignore_enters++;
+    }
+
     return TRUE;
 }
 
 gboolean menu_frame_show_submenu(ObMenuFrame *self, ObMenuFrame *parent,
                                  ObMenuEntryFrame *parent_entry)
 {
-    ObMenuEntryFrame *e;
     gint x, y, dx, dy;
+    gint px, py;
 
     if (menu_frame_is_visible(self))
         return TRUE;
@@ -994,14 +1007,16 @@ gboolean menu_frame_show_submenu(ObMenuFrame *self, ObMenuFrame *parent,
 
     XMapWindow(ob_display, self->window);
 
-    if (screen_pointer_pos(&dx, &dy) && (e = menu_entry_frame_under(dx, dy)) &&
-        e->frame == self)
-        ++e->ignore_enters;
+    if (screen_pointer_pos(&px, &py)) {
+        ObMenuEntryFrame *e = menu_entry_frame_under(px, py);
+        if (e && e->frame == self)
+            e->ignore_enters++;
+    }
 
     return TRUE;
 }
 
-void menu_frame_hide(ObMenuFrame *self)
+static void menu_frame_hide(ObMenuFrame *self)
 {
     GList *it = g_list_find(menu_frame_visible, self);
 
@@ -1023,8 +1038,8 @@ void menu_frame_hide(ObMenuFrame *self)
 
     if (menu_frame_visible == NULL) {
         /* last menu shown */
-        grab_pointer(FALSE, TRUE, OB_CURSOR_NONE);
-        grab_keyboard(FALSE);
+        ungrab_pointer();
+        ungrab_keyboard();
     }
 
     XUnmapWindow(ob_display, self->window);
@@ -1043,6 +1058,8 @@ void menu_frame_hide_all()
     }
     if ((it = g_list_last(menu_frame_visible)))
         menu_frame_hide(it->data);
+
+    menu_clear_pipe_caches();
 }
 
 void menu_frame_hide_all_client(ObClient *client)
@@ -1053,6 +1070,8 @@ void menu_frame_hide_all_client(ObClient *client)
         if (f->client == client)
             menu_frame_hide(f);
     }
+
+    menu_clear_pipe_caches();
 }
 
 
@@ -1086,7 +1105,7 @@ ObMenuEntryFrame* menu_entry_frame_under(gint x, gint y)
             ObMenuEntryFrame *e = it->data;
 
             if (RECT_CONTAINS(e->area, x, y)) {
-                ret = e;            
+                ret = e;
                 break;
             }
         }
This page took 0.025241 seconds and 4 git commands to generate.