systray: Separate reparenting from embedding

This commit is contained in:
o9000 2015-07-16 20:20:23 +02:00
parent 9933399dc4
commit c606a1a35a
3 changed files with 69 additions and 2 deletions

View file

@ -609,6 +609,58 @@ gboolean reparent_icon(TrayWindow *traywin)
if (traywin->reparented) if (traywin->reparented)
return TRUE; return TRUE;
// Watch for the icon trying to resize itself / closing again
XSync(server.dsp, False);
error = FALSE;
XErrorHandler old = XSetErrorHandler(window_error_handler);
if (systray_profile)
fprintf(stderr, "XSelectInput(server.dsp, traywin->win, StructureNotifyMask)\n");
XSelectInput(server.dsp, traywin->win, StructureNotifyMask | PropertyChangeMask);
XSync(server.dsp, False);
XSetErrorHandler(old);
if (error != FALSE) {
fprintf(stderr, RED "systray %d: cannot embed icon for window %lu (%s) parent %lu pid %d\n" RESET, __LINE__, traywin->win, traywin->name, traywin->parent, traywin->pid);
remove_icon(traywin);
return FALSE;
}
// Reparent
if (systray_profile)
fprintf(stderr, "XSync(server.dsp, False)\n");
XSync(server.dsp, False);
error = FALSE;
old = XSetErrorHandler(window_error_handler);
if (systray_profile)
fprintf(stderr, "XReparentWindow(server.dsp, traywin->win, traywin->parent, 0, 0)\n");
XWithdrawWindow(server.dsp, traywin->win, server.screen);
XReparentWindow(server.dsp, traywin->win, traywin->parent, 0, 0);
if (systray_profile)
fprintf(stderr, "XMoveResizeWindow(server.dsp, traywin->win = %ld, 0, 0, traywin->width = %d, traywin->height = %d)\n", traywin->win, traywin->width, traywin->height);
XMoveResizeWindow(server.dsp, traywin->win, 0, 0, traywin->width, traywin->height);
XSync(server.dsp, False);
XSetErrorHandler(old);
if (error != FALSE) {
fprintf(stderr, RED "systray %d: cannot embed icon for window %lu (%s) parent %lu pid %d\n" RESET, __LINE__, traywin->win, traywin->name, traywin->parent, traywin->pid);
remove_icon(traywin);
return FALSE;
}
traywin->reparented = 1;
if (systray_profile)
fprintf(stderr, "[%f] %s:%d win = %lu (%s)\n", profiling_get_time(), __FUNCTION__, __LINE__, traywin->win, traywin->name);
return TRUE;
}
gboolean embed_icon(TrayWindow *traywin)
{
if (systray_profile)
fprintf(stderr, "[%f] %s:%d win = %lu (%s)\n", profiling_get_time(), __FUNCTION__, __LINE__, traywin->win, traywin->name);
if (traywin->embedded)
return TRUE;
Panel* panel = systray.area.panel; Panel* panel = systray.area.panel;
// Watch for the icon trying to resize itself / closing again // Watch for the icon trying to resize itself / closing again
@ -617,7 +669,7 @@ gboolean reparent_icon(TrayWindow *traywin)
XErrorHandler old = XSetErrorHandler(window_error_handler); XErrorHandler old = XSetErrorHandler(window_error_handler);
if (systray_profile) if (systray_profile)
fprintf(stderr, "XSelectInput(server.dsp, traywin->win, StructureNotifyMask)\n"); fprintf(stderr, "XSelectInput(server.dsp, traywin->win, StructureNotifyMask)\n");
XSelectInput(server.dsp, traywin->win, StructureNotifyMask); XSelectInput(server.dsp, traywin->win, StructureNotifyMask | PropertyChangeMask);
XSync(server.dsp, False); XSync(server.dsp, False);
XSetErrorHandler(old); XSetErrorHandler(old);
if (error != FALSE) { if (error != FALSE) {
@ -741,7 +793,7 @@ gboolean reparent_icon(TrayWindow *traywin)
fprintf(stderr, "XSync(server.dsp, False)\n"); fprintf(stderr, "XSync(server.dsp, False)\n");
XSync(server.dsp, False); XSync(server.dsp, False);
traywin->reparented = 1; traywin->embedded = 1;
if (systray_profile) if (systray_profile)
fprintf(stderr, "[%f] %s:%d win = %lu (%s)\n", profiling_get_time(), __FUNCTION__, __LINE__, traywin->win, traywin->name); fprintf(stderr, "[%f] %s:%d win = %lu (%s)\n", profiling_get_time(), __FUNCTION__, __LINE__, traywin->win, traywin->name);

View file

@ -50,6 +50,7 @@ typedef struct
struct timespec time_last_render; struct timespec time_last_render;
int num_fast_renders; int num_fast_renders;
int reparented; int reparented;
int embedded;
char *name; char *name;
} TrayWindow; } TrayWindow;
@ -85,6 +86,8 @@ void stop_net();
void net_message(XClientMessageEvent *e); void net_message(XClientMessageEvent *e);
gboolean add_icon(Window id); gboolean add_icon(Window id);
gboolean reparent_icon(TrayWindow *traywin);
gboolean embed_icon(TrayWindow *traywin);
void remove_icon(TrayWindow *traywin); void remove_icon(TrayWindow *traywin);
void refresh_systray_icons(); void refresh_systray_icons();

View file

@ -1287,12 +1287,24 @@ start:
break; break;
case ReparentNotify: case ReparentNotify:
fprintf(stderr, "ReparentNotify\n");
if (!systray_enabled) if (!systray_enabled)
break; break;
panel = (Panel*)systray.area.panel; panel = (Panel*)systray.area.panel;
if (e.xany.window == panel->main_win) // reparented to us if (e.xany.window == panel->main_win) // reparented to us
break; break;
// FIXME: 'reparent to us' badly detected => disabled // FIXME: 'reparent to us' badly detected => disabled
for (it = systray.list_icons; it; it = g_slist_next(it)) {
TrayWindow *traywin = (TrayWindow*)it->data;
if (traywin->win == e.xreparent.window) {
fprintf(stderr, "win\n");
if (traywin->parent == e.xreparent.parent) {
fprintf(stderr, "parent\n");
embed_icon(traywin);
}
break;
}
}
break; break;
case UnmapNotify: case UnmapNotify:
case DestroyNotify: case DestroyNotify: