aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
Diffstat (limited to 'x11-wm/compiz/files/compiz-quinn-r1.patch')
-rw-r--r--x11-wm/compiz/files/compiz-quinn-r1.patch1813
1 files changed, 1813 insertions, 0 deletions
diff --git a/x11-wm/compiz/files/compiz-quinn-r1.patch b/x11-wm/compiz/files/compiz-quinn-r1.patch
new file mode 100644
index 0000000..d0582ce
--- /dev/null
+++ b/x11-wm/compiz/files/compiz-quinn-r1.patch
@@ -0,0 +1,1813 @@
+--- ./gnome/window-decorator/gnome-window-decorator.c.old 2006-03-25 22:14:23.871947208 -0500
++++ ./gnome/window-decorator/gnome-window-decorator.c 2006-03-25 07:29:45.000000000 -0500
+@@ -64,7 +64,7 @@
+ #define BOTTOM_SPACE 14
+
+ #define ICON_SPACE 20
+-#define BUTTON_SPACE 52
++#define BUTTON_SPACE 70
+
+ typedef struct _extents {
+ gint left;
+@@ -73,6 +73,8 @@
+ gint bottom;
+ } extents;
+
++#define FAKE_WINDOW_ACTION_HELP (1 << 20)
++
+ #define GRAVITY_WEST (0)
+ #define GRAVITY_EAST (1 << 0)
+ #define GRAVITY_NORTH (0)
+@@ -656,6 +658,8 @@
+ static Atom wm_move_resize_atom;
+ static Atom restack_window_atom;
+ static Atom select_window_atom;
++static Atom net_wm_context_help_atom;
++static Atom wm_protocols_atom;
+
+ #define C(name) { 0, XC_ ## name }
+
+@@ -685,10 +689,11 @@
+ { 10, 21, -8, 6, 0, 1, 1, 0 },
+ { 2, 17, 10, 10, 1, 1, 0, 0 }
+ }
+-}, bpos[3] = {
++}, bpos[4] = {
+ { -10, 6, 16, 16, 1, 0, 0, 0 },
+ { -26, 6, 16, 16, 1, 0, 0, 0 },
+- { -42, 6, 16, 16, 1, 0, 0, 0 }
++ { -42, 6, 16, 16, 1, 0, 0, 0 },
++ { -58, 6, 16, 16, 1, 0, 0, 0 },
+ };
+
+ typedef struct _decor_color {
+@@ -702,8 +707,8 @@
+
+ typedef struct _decor {
+ Window event_windows[3][3];
+- Window button_windows[3];
+- guint button_states[3];
++ Window button_windows[4];
++ guint button_states[4];
+ GdkPixmap *pixmap;
+ GdkPixmap *buffer_pixmap;
+ GdkGC *gc;
+@@ -1089,6 +1094,26 @@
+ }
+
+ static void
++ draw_help_button (decor_t *d,
++ cairo_t *cr,
++ double s)
++{
++ cairo_rel_move_to (cr,0.0,6.0);
++
++ cairo_rel_line_to (cr,0.0,3.0);
++ cairo_rel_line_to (cr,4.5,0.0);
++ cairo_rel_line_to (cr,0.0,4.5);
++ cairo_rel_line_to (cr,3.0,0.0);
++ cairo_rel_line_to (cr,0.0,-4.5);
++ cairo_rel_line_to (cr,4.5,0.0);
++ cairo_rel_line_to (cr,0.0,-3.0);
++ cairo_rel_line_to (cr,-4.5,0.0);
++ cairo_rel_line_to (cr,0.0,-4.5);
++ cairo_rel_line_to (cr,-3.0,0.0);
++ cairo_rel_line_to (cr,0.0,4.5);
++ cairo_close_path (cr);
++}
++static void
+ draw_close_button (decor_t *d,
+ cairo_t *cr,
+ double s)
+@@ -1412,9 +1437,45 @@
+
+ cairo_stroke (cr);
+
++ if (d->actions & FAKE_WINDOW_ACTION_HELP)
++ {
++ button_state_offsets (d->width - RIGHT_SPACE - BUTTON_SPACE + 3.0,
++ titlebar_height / 2 + 3.0,
++ d->button_states[3], &x, &y, &sx, &sy);
++
++ if (d->active)
++ {
++ gdk_cairo_set_source_color_alpha (cr,
++ &style->fg[GTK_STATE_NORMAL],
++ alpha);
++ cairo_move_to (cr, sx, sy);
++ draw_help_button (d, cr, 3.0);
++ cairo_fill (cr);
++
++ if (d->button_states[3] & IN_EVENT_WINDOW)
++ cairo_set_source_rgb (cr, 1.0, 1.0, 1.0);
++ else
++ cairo_set_source_rgba (cr, color.r, color.g, color.b, 0.95);
++
++ cairo_move_to (cr, x, y);
++ draw_help_button (d, cr, 3.0);
++ cairo_fill (cr);
++ }
++ else
++ {
++ gdk_cairo_set_source_color_alpha (cr,
++ &style->fg[GTK_STATE_NORMAL],
++ alpha * 0.75);
++ cairo_move_to (cr, x, y);
++ draw_help_button (d, cr, 3.0);
++ cairo_fill (cr);
++ }
++ }
++
++
+ if (d->actions & WNCK_WINDOW_ACTION_CLOSE)
+ {
+- button_state_offsets (d->width - RIGHT_SPACE - BUTTON_SPACE + 39.0,
++ button_state_offsets (d->width - RIGHT_SPACE - BUTTON_SPACE + 57.0,
+ titlebar_height / 2 + 3.0,
+ d->button_states[0], &x, &y, &sx, &sy);
+
+@@ -1449,7 +1510,7 @@
+
+ if (d->actions & WNCK_WINDOW_ACTION_MAXIMIZE)
+ {
+- button_state_offsets (d->width - RIGHT_SPACE - BUTTON_SPACE + 21.0,
++ button_state_offsets (d->width - RIGHT_SPACE - BUTTON_SPACE + 39.0,
+ titlebar_height / 2 + 3.0,
+ d->button_states[1], &x, &y, &sx, &sy);
+
+@@ -1504,7 +1565,7 @@
+
+ if (d->actions & WNCK_WINDOW_ACTION_MINIMIZE)
+ {
+- button_state_offsets (d->width - RIGHT_SPACE - BUTTON_SPACE + 3.0,
++ button_state_offsets (d->width - RIGHT_SPACE - BUTTON_SPACE + 21.0,
+ titlebar_height / 2 + 3.0,
+ d->button_states[2], &x, &y, &sx, &sy);
+
+@@ -2249,12 +2310,13 @@
+ }
+ }
+
+- for (i = 0; i < 3; i++)
++ for (i = 0; i < 4; i++)
+ {
+- static guint button_actions[3] = {
++ static guint button_actions[4] = {
+ WNCK_WINDOW_ACTION_CLOSE,
+ WNCK_WINDOW_ACTION_MAXIMIZE,
+- WNCK_WINDOW_ACTION_MINIMIZE
++ WNCK_WINDOW_ACTION_MINIMIZE,
++ FAKE_WINDOW_ACTION_HELP
+ };
+
+ if (d->actions & button_actions[i])
+@@ -2403,7 +2465,46 @@
+ {
+ decor_t *d = g_object_get_data (G_OBJECT (win), "decor");
+
++ /* code to check for context help protocol */
++ Atom actual;
++ int result, format;
++ unsigned long n, left;
++ unsigned long offset;
++ unsigned char *data;
++ Window id = wnck_window_get_xid (win);
++ Display *xdisplay;
++ GdkDisplay *gdkdisplay;
++ //GdkScreen *screen;
++ //Window xroot;
++ //XEvent ev;
++
++ gdkdisplay = gdk_display_get_default ();
++ xdisplay = GDK_DISPLAY_XDISPLAY (gdkdisplay);
++ //screen = gdk_display_get_default_screen (gdkdisplay);
++ //xroot = RootWindowOfScreen (gdk_x11_screen_get_xscreen (screen));
++
+ d->actions = wnck_window_get_actions (win);
++
++ left=1;
++ offset=0;
++ while(left)
++ {
++ result = XGetWindowProperty (xdisplay, id, wm_protocols_atom,
++ offset, 1L, FALSE, XA_ATOM, &actual, &format,
++ &n, &left, &data);
++ offset++;
++ if (result == Success && n && data)
++ {
++ Atom a;
++
++ memcpy (&a, data, sizeof (Atom));
++ XFree ((void *) data);
++ if (a == net_wm_context_help_atom)
++ {
++ d->actions |= FAKE_WINDOW_ACTION_HELP;
++ }
++ }
++ }
+ }
+
+ static gboolean
+@@ -2501,7 +2602,7 @@
+
+ attr.event_mask |= ButtonReleaseMask;
+
+- for (i = 0; i < 3; i++)
++ for (i = 0; i < 4; i++)
+ {
+ d->button_windows[i] =
+ XCreateWindow (xdisplay,
+@@ -2524,7 +2625,7 @@
+ GINT_TO_POINTER (d->event_windows[i][j]),
+ GINT_TO_POINTER (xid));
+
+- for (i = 0; i < 3; i++)
++ for (i = 0; i < 4; i++)
+ g_hash_table_insert (frame_table,
+ GINT_TO_POINTER (d->button_windows[i]),
+ GINT_TO_POINTER (xid));
+@@ -2813,6 +2914,7 @@
+ if (d->decorated)
+ {
+ update_window_decoration_actions (win);
++ update_event_windows (win);
+ queue_decor_draw (d);
+ }
+ }
+@@ -3356,6 +3458,74 @@
+ }
+
+ static void
++ send_help_message (WnckWindow * win)
++{
++ Display *xdisplay;
++ GdkDisplay *gdkdisplay;
++ //GdkScreen *screen;
++ Window id;
++ XEvent ev;
++
++ gdkdisplay = gdk_display_get_default ();
++ xdisplay = GDK_DISPLAY_XDISPLAY (gdkdisplay);
++ //screen = gdk_display_get_default_screen (gdkdisplay);
++ //xroot = RootWindowOfScreen (gdk_x11_screen_get_xscreen (screen));
++ id=wnck_window_get_xid(win);
++
++ ev.xclient.type = ClientMessage;
++ //ev.xclient.display = xdisplay;
++
++ //ev.xclient.serial = 0;
++ //ev.xclient.send_event = TRUE;
++
++ ev.xclient.window = id;
++ ev.xclient.message_type = wm_protocols_atom;
++ ev.xclient.data.l[0] = net_wm_context_help_atom;
++ ev.xclient.data.l[1] = 0L;
++ ev.xclient.format = 32;
++
++ XSendEvent (xdisplay, id, FALSE,
++ 0L,
++ &ev);
++
++ XSync (xdisplay, FALSE);
++}
++
++static void
++ help_button_event (WnckWindow *win,
++ XEvent *xevent)
++{
++ decor_t *d = g_object_get_data (G_OBJECT (win), "decor");
++ guint state = d->button_states[3];
++
++ handle_tooltip_event (win, xevent, state, "Context Help");
++
++ switch (xevent->type) {
++ case ButtonPress:
++ d->button_states[3] |= PRESSED_EVENT_WINDOW;
++ break;
++ case ButtonRelease:
++ if (d->button_states[3] == (PRESSED_EVENT_WINDOW | IN_EVENT_WINDOW))
++ send_help_message (win);
++
++ d->button_states[3] &= ~PRESSED_EVENT_WINDOW;
++ break;
++ case EnterNotify:
++ d->button_states[3] |= IN_EVENT_WINDOW;
++ if (wnck_window_is_active (win))
++ tooltip_start_delay ("Context Help");
++ break;
++ case LeaveNotify:
++ if (xevent->xcrossing.mode != NotifyGrab)
++ d->button_states[3] &= ~IN_EVENT_WINDOW;
++ break;
++ }
++
++ if (state != d->button_states[3])
++ queue_decor_draw (d);
++}
++
++static void
+ top_left_event (WnckWindow *win,
+ XEvent *xevent)
+ {
+@@ -3393,6 +3563,145 @@
+ action_menu_mapped = FALSE;
+ }
+
++static void minimize_callback(GtkWidget * menuItem, WnckWindow * win)
++{
++ wnck_window_minimize(win);
++}
++
++static void maximize_callback(GtkWidget * menuItem, WnckWindow * win)
++{
++ if (wnck_window_is_maximized(win))
++ {
++ wnck_window_unmaximize(win);
++ }
++ else
++ {
++ wnck_window_maximize(win);
++ }
++}
++
++static void above_callback(GtkWidget * menuItem, WnckWindow * win)
++{
++ if (wnck_window_is_above(win))
++ {
++ wnck_window_unmake_above(win);
++ }
++ else
++ {
++ wnck_window_make_above(win);
++ }
++}
++
++#define _NET_WM_STATE_REMOVE 0 /* remove/unset property */
++#define _NET_WM_STATE_ADD 1 /* add/set property */
++#define _NET_WM_STATE_TOGGLE 2 /* toggle property */
++
++static void pin_callback(GtkWidget * menuItem, WnckWindow * win)
++{
++ XEvent xev;
++ Display *xdisplay;
++ GdkDisplay *gdkdisplay;
++ GdkScreen *screen;
++ Window xroot;
++
++ gdkdisplay = gdk_display_get_default ();
++ xdisplay = GDK_DISPLAY_XDISPLAY (gdkdisplay);
++ screen = gdk_display_get_default_screen (gdkdisplay);
++ xroot = RootWindowOfScreen (gdk_x11_screen_get_xscreen (screen));
++
++ xev.xclient.type = ClientMessage;
++ xev.xclient.serial = 0;
++ xev.xclient.send_event = TRUE;
++ xev.xclient.window = wnck_window_get_xid(win);
++ xev.xclient.message_type = XInternAtom(xdisplay,"_NET_WM_STATE",FALSE);
++ xev.xclient.format=32;
++ xev.xclient.data.l[1]=XInternAtom(xdisplay,"_NET_WM_STATE_STICKY",FALSE);
++ xev.xclient.data.l[2]=0;
++ xev.xclient.data.l[3]=0;
++ xev.xclient.data.l[4]=0;
++ //wnck_window_pin(win);
++ unsigned long data[2];
++ if (wnck_window_is_pinned(win))
++ {
++ data[0] = 0;
++ xev.xclient.data.l[0]=_NET_WM_STATE_REMOVE;
++ }
++ else
++ {
++ data[0] = 0xFFFFFFFF;
++ xev.xclient.data.l[0]=_NET_WM_STATE_ADD;
++ }
++ XSendEvent(xdisplay,xroot,FALSE,
++ SubstructureRedirectMask | SubstructureNotifyMask, &xev);
++ XChangeProperty (xdisplay, wnck_window_get_xid(win),
++ XInternAtom(xdisplay,"_NET_WM_DESKTOP",FALSE),
++ XA_CARDINAL, 32, PropModeReplace,
++ (unsigned char *) data, 1);
++
++}
++
++static void close_callback(GtkWidget * menuItem, WnckWindow * win)
++{
++ wnck_window_close(win,0);
++}
++
++static void trans_callback(GtkWidget * menuItem, WnckWindow * win)
++{
++ Display *xdisplay;
++ GdkDisplay *gdkdisplay;
++ gdkdisplay = gdk_display_get_default ();
++ xdisplay = GDK_DISPLAY_XDISPLAY (gdkdisplay);
++ //screen = gdk_display_get_default_screen (gdkdisplay);
++ //xroot = RootWindowOfScreen (gdk_x11_screen_get_xscreen (screen));
++ XDeleteProperty (xdisplay, wnck_window_get_xid(win),
++ XInternAtom(xdisplay,"_NET_WM_WINDOW_OPACITY",FALSE));
++}
++
++static GtkWidget * comp_create_window_action_menu (WnckWindow *win)
++{
++ decor_t *d = g_object_get_data (G_OBJECT (win), "decor");
++ GtkWidget * menuItem;
++ GtkWidget * menu = gtk_menu_new();
++
++ menuItem=gtk_menu_item_new_with_label("Minimize");
++ g_signal_connect(G_OBJECT(menuItem),"activate",G_CALLBACK(minimize_callback),win);
++ gtk_widget_set_sensitive(menuItem,d->actions & WNCK_WINDOW_ACTION_MINIMIZE);
++ gtk_menu_shell_append(GTK_MENU_SHELL(menu),menuItem);
++
++ menuItem=gtk_check_menu_item_new_with_label("Maximize");
++ gtk_check_menu_item_set_active(GTK_CHECK_MENU_ITEM(menuItem),wnck_window_is_maximized(win));
++ g_signal_connect(G_OBJECT(menuItem),"toggled",G_CALLBACK(maximize_callback),win);
++ gtk_widget_set_sensitive(menuItem,d->actions & WNCK_WINDOW_ACTION_MAXIMIZE);
++ gtk_menu_shell_append(GTK_MENU_SHELL(menu),menuItem);
++
++ menuItem=gtk_check_menu_item_new_with_label("On Top");
++ gtk_check_menu_item_set_active(GTK_CHECK_MENU_ITEM(menuItem),wnck_window_is_above(win));
++ g_signal_connect(G_OBJECT(menuItem),"toggled",G_CALLBACK(above_callback),win);
++ gtk_menu_shell_append(GTK_MENU_SHELL(menu),menuItem);
++
++ menuItem=gtk_check_menu_item_new_with_label("On All Workspaces");
++ gtk_check_menu_item_set_active(GTK_CHECK_MENU_ITEM(menuItem),wnck_window_is_pinned(win));
++ g_signal_connect(G_OBJECT(menuItem),"toggled",G_CALLBACK(pin_callback),win);
++ gtk_menu_shell_append(GTK_MENU_SHELL(menu),menuItem);
++
++ menuItem=gtk_menu_item_new_with_label("Reset Transparency");
++ g_signal_connect(G_OBJECT(menuItem),"activate",G_CALLBACK(trans_callback),win);
++ gtk_widget_set_sensitive(menuItem,d->actions & WNCK_WINDOW_ACTION_MINIMIZE);
++ gtk_menu_shell_append(GTK_MENU_SHELL(menu),menuItem);
++
++ menuItem=gtk_separator_menu_item_new();
++ gtk_menu_shell_append(GTK_MENU_SHELL(menu),menuItem);
++
++ menuItem=gtk_menu_item_new_with_label("Close");
++ gtk_widget_set_sensitive(menuItem,d->actions & WNCK_WINDOW_ACTION_CLOSE);
++ g_signal_connect(G_OBJECT(menuItem),"activate",G_CALLBACK(close_callback),win);
++ gtk_menu_shell_append(GTK_MENU_SHELL(menu),menuItem);
++
++ gtk_widget_show_all(menu);
++
++ return menu;
++}
++
+ static void
+ title_event (WnckWindow *win,
+ XEvent *xevent)
+@@ -3443,7 +3752,8 @@
+ if (action_menu)
+ gtk_object_destroy (GTK_OBJECT (action_menu));
+
+- action_menu = wnck_create_window_action_menu (win);
++ //action_menu = wnck_create_window_action_menu (win);
++ action_menu = comp_create_window_action_menu (win);
+
+ gtk_menu_set_screen (GTK_MENU (action_menu), screen);
+
+@@ -3578,10 +3888,11 @@
+ { left_event, title_event, right_event },
+ { bottom_left_event, bottom_event, bottom_right_event }
+ };
+- static event_callback button_callback[3] = {
++ static event_callback button_callback[4] = {
+ close_button_event,
+ max_button_event,
+- min_button_event
++ min_button_event,
++ help_button_event
+ };
+ decor_t *d = g_object_get_data (G_OBJECT (win), "decor");
+
+@@ -3594,7 +3905,7 @@
+ if (d->event_windows[i][j] == xevent->xany.window)
+ (*callback[i][j]) (win, xevent);
+
+- for (i = 0; i < 3; i++)
++ for (i = 0; i < 4; i++)
+ if (d->button_windows[i] == xevent->xany.window)
+ (*button_callback[i]) (win, xevent);
+ }
+@@ -4000,6 +4311,8 @@
+ restack_window_atom = XInternAtom (xdisplay, "_NET_RESTACK_WINDOW", FALSE);
+ select_window_atom = XInternAtom (xdisplay, "_SWITCH_SELECT_WINDOW",
+ FALSE);
++ wm_protocols_atom = XInternAtom (xdisplay, "WM_PROTOCOLS", FALSE);
++ net_wm_context_help_atom = XInternAtom (xdisplay, "_NET_WM_CONTEXT_HELP", FALSE);
+
+ for (i = 0; i < 3; i++)
+ {
+--- ./plugins/Makefile.am.old 2006-02-12 17:00:50.000000000 -0500
++++ ./plugins/Makefile.am 2006-03-26 00:44:54.000000000 -0500
+@@ -1,3 +1,15 @@
++libtrailfocus_la_LDFLAGS = -module -avoid-version -no-undefined
++libtrailfocus_la_LIBADD = @COMPIZ_LIBS@
++libtrailfocus_la_SOURCES = trailfocus.c
++
++libtransset_la_LDFLAGS = -module -avoid-version -no-undefined
++libtransset_la_LIBADD = @COMPIZ_LIBS@
++libtransset_la_SOURCES = transset.c
++
++libopaquefocus_la_LDFLAGS = -module -avoid-version -no-undefined
++libopaquefocus_la_LIBADD = @COMPIZ_LIBS@
++libopaquefocus_la_SOURCES = opaquefocus.c
++
+ libfade_la_LDFLAGS = -module -avoid-version -no-undefined
+ libfade_la_LIBADD = @COMPIZ_LIBS@
+ libfade_la_SOURCES = fade.c
+@@ -66,6 +78,9 @@
+ moduledir = $(plugindir)
+
+ module_LTLIBRARIES = \
++ libtrailfocus.la \
++ libtransset.la \
++ libopaquefocus.la \
+ libfade.la \
+ libcube.la \
+ librotate.la \
+--- ./plugins/minimize.c.old 2006-03-16 12:50:08.000000000 -0500
++++ ./plugins/minimize.c 2006-03-26 00:58:09.000000000 -0500
+@@ -26,6 +26,7 @@
+ #include <X11/Xatom.h>
+
+ #include <stdlib.h>
++#include <stdio.h>
+ #include <string.h>
+ #include <math.h>
+
+@@ -41,6 +42,8 @@
+ #define MIN_TIMESTEP_MAX 50.0f
+ #define MIN_TIMESTEP_PRECISION 0.1f
+
++#define FAKE_ICON_SIZE 4
++
+ static char *winType[] = {
+ "Toolbar",
+ "Utility",
+@@ -61,7 +64,9 @@
+ #define MIN_SCREEN_OPTION_SPEED 0
+ #define MIN_SCREEN_OPTION_TIMESTEP 1
+ #define MIN_SCREEN_OPTION_WINDOW_TYPE 2
+-#define MIN_SCREEN_OPTION_NUM 3
++#define MIN_SCREEN_OPTION_ON_CREATE 3
++#define MIN_SCREEN_OPTION_CENTER 4
++#define MIN_SCREEN_OPTION_NUM 5
+
+ typedef struct _MinScreen {
+ int windowPrivateIndex;
+@@ -81,6 +86,8 @@
+ unsigned int wMask;
+
+ int moreAdjust;
++ Bool scaleInNewWindows;
++ Bool scaleFromCenter;
+ } MinScreen;
+
+ typedef struct _MinWindow {
+@@ -95,6 +102,7 @@
+ int state, newState;
+
+ int unmapCnt;
++ int destroyCnt;
+ } MinWindow;
+
+ #define GET_MIN_DISPLAY(d) \
+@@ -119,6 +127,19 @@
+
+ #define NUM_OPTIONS(s) (sizeof ((s)->opt) / sizeof (CompOption))
+
++static Bool getMousePointerXY(CompScreen * s, short * x, short * y)
++{
++ Window w1,w2;
++ int xp,yp,xj,yj;
++ unsigned int m;
++ if (XQueryPointer(s->display->display,s->root,&w1,&w2,&xj,&yj,&xp,&yp,&m))
++ {
++ *x=xp;
++ *y=yp;
++ return TRUE;
++ }
++ return FALSE;
++}
+ static CompOption *
+ minGetScreenOptions (CompScreen *screen,
+ int *count)
+@@ -164,7 +185,20 @@
+ ms->wMask = compWindowTypeMaskFromStringList (&o->value);
+ return TRUE;
+ }
+- default:
++ break;
++ case MIN_SCREEN_OPTION_ON_CREATE:
++ if (compSetBoolOption (o, value))
++ {
++ ms->scaleInNewWindows=o->value.b;
++ return TRUE;
++ }
++ case MIN_SCREEN_OPTION_CENTER:
++ if (compSetBoolOption (o, value))
++ {
++ ms->scaleFromCenter=o->value.b;
++ return TRUE;
++ }
++ default:
+ break;
+ }
+
+@@ -210,8 +244,22 @@
+ o->value.list.value[i].s = strdup (winType[i]);
+ o->rest.s.string = windowTypeString;
+ o->rest.s.nString = nWindowTypeString;
+-
+ ms->wMask = compWindowTypeMaskFromStringList (&o->value);
++
++ o = &ms->opt[MIN_SCREEN_OPTION_ON_CREATE];
++ o->name = "zoom_created_windows";
++ o->shortDesc = "Zoom Created Windows";
++ o->longDesc = "Zooms created windows in from cursor/center";
++ o->type = CompOptionTypeBool;
++ o->value.b = TRUE;
++
++ o = &ms->opt[MIN_SCREEN_OPTION_CENTER];
++ o->name = "zoom_created_windows_from_center";
++ o->shortDesc = "Zoom Created Windows from Center";
++ o->longDesc = "Zooms created windows in from center instead of cursor";
++ o->type = CompOptionTypeBool;
++ o->value.b = FALSE;
++
+ }
+
+ static Bool
+@@ -286,7 +334,7 @@
+
+ MIN_WINDOW (w);
+
+- if (mw->newState == IconicState)
++ if (mw->newState == IconicState || mw->newState == WithdrawnState)
+ {
+ x1 = mw->icon.x;
+ y1 = mw->icon.y;
+@@ -357,6 +405,11 @@
+ mw->ty = y1 - w->attrib.y;
+ mw->xScale = xScale;
+ mw->yScale = yScale;
++ if (mw->destroyCnt)
++ {
++ destroyWindow(w);
++ mw->destroyCnt--;
++ }
+
+ return 0;
+ }
+@@ -531,6 +584,20 @@
+ }
+ }
+ break;
++ case DestroyNotify:
++ w = findWindowAtDisplay (d, event->xunmap.window);
++ if (w)
++ {
++ MIN_SCREEN(w->screen);
++ if (ms->wMask & w->type)
++ {
++ MIN_WINDOW(w);
++ mw->destroyCnt++;
++ w->destroyRefCnt++;
++ addWindowDamage(w);
++ }
++ }
++ break;
+ case UnmapNotify:
+ w = findWindowAtDisplay (d, event->xunmap.window);
+ if (w)
+@@ -564,13 +631,45 @@
+ else /* X -> Withdrawn */
+ {
+ MIN_WINDOW (w);
+-
+- if (mw->state == IconicState)
+- {
+- (*w->screen->setWindowScale) (w, 1.0f, 1.0f);
+- mw->state = NormalState;
+- }
+- }
++ if (ms->wMask & w->type)
++ {
++ if (mw->state == IconicState)
++ {
++ (*w->screen->setWindowScale) (w, 1.0f, 1.0f);
++ mw->state = NormalState;
++ }
++ mw->state = NormalState;
++ mw->newState = WithdrawnState;
++ //let's zoom windows on hide
++ if (getMousePointerXY(w->screen,&mw->icon.x,&mw->icon.y) && ms->scaleInNewWindows && (ms->wMask & w->type))
++ {
++ //mw->icon.x=w->attrib.x+(w->attrib.width/2-16);
++ //mw->icon.y=w->attrib.y+(w->attrib.height/2-16);
++ mw->icon.width=FAKE_ICON_SIZE;
++ mw->icon.height=FAKE_ICON_SIZE;
++ mw->icon.x-=FAKE_ICON_SIZE/2;
++ mw->icon.y-=FAKE_ICON_SIZE/2;
++ if (ms->scaleFromCenter)
++ {
++ mw->icon.x = w->attrib.x+w->attrib.width/2-FAKE_ICON_SIZE/2;
++ mw->icon.y = w->attrib.y+w->attrib.height/2-FAKE_ICON_SIZE/2;
++ }
++ //mw->tx=w->attrib.x-mw->icon.x;
++ //mw->ty=w->attrib.y-mw->icon.y;
++ //mw->tx=w->attrib.width/2-16;
++ //mw->ty=w->attrib.height/2-16;
++ //mw->xScale=-(32.0/w->attrib.width);
++ //mw->yScale=-(32.0/w->attrib.height);
++ mw->adjust=TRUE;
++ ms->moreAdjust=TRUE;
++ mw->unmapCnt++;
++ w->unmapRefCnt++;
++ addWindowDamage (w);
++
++ //fprintf(stderr,"We should have it.\n");
++ }
++ }
++ }
+ }
+ default:
+ break;
+@@ -619,6 +718,35 @@
+ }
+ }
+ }
++ else if (mw->state!=NormalState)
++ {
++ if (getMousePointerXY(w->screen,&mw->icon.x,&mw->icon.y) && ms->scaleInNewWindows)
++ {
++ //mw->icon.x=w->attrib.x+(w->attrib.width/2-16);
++ //mw->icon.y=w->attrib.y+(w->attrib.height/2-16);
++ mw->icon.width=FAKE_ICON_SIZE;
++ mw->icon.height=FAKE_ICON_SIZE;
++ mw->icon.x-=FAKE_ICON_SIZE/2;
++ mw->icon.y-=FAKE_ICON_SIZE/2;
++ if (ms->scaleFromCenter)
++ {
++ mw->icon.x = w->attrib.x+w->attrib.width/2-FAKE_ICON_SIZE/2;
++ mw->icon.y = w->attrib.y+w->attrib.height/2-FAKE_ICON_SIZE/2;
++ }
++ mw->tx=mw->icon.x-w->attrib.x;
++ mw->ty=mw->icon.y-w->attrib.y;
++ //mw->tx=w->attrib.width/2-16;
++ //mw->ty=w->attrib.height/2-16;
++ mw->xScale=((float)FAKE_ICON_SIZE)/w->attrib.width;
++ mw->yScale=((float)FAKE_ICON_SIZE)/w->attrib.height;
++ mw->state=IconicState; // we're doing this as a hack, it may not be necessary
++ mw->newState=NormalState;
++ mw->adjust=TRUE;
++ ms->moreAdjust=TRUE;
++ addWindowDamage (w);
++ //fprintf(stderr,"We should have it.\n");
++ }
++ }
+
+ mw->newState = NormalState;
+ }
+@@ -638,7 +766,7 @@
+ MIN_SCREEN (w->screen);
+ MIN_WINDOW (w);
+
+- if (mw->unmapCnt)
++ if (mw->unmapCnt || mw->destroyCnt)
+ return FALSE;
+
+ UNWRAP (ms, w->screen, focusWindow);
+@@ -712,6 +840,8 @@
+
+ ms->speed = MIN_SPEED_DEFAULT;
+ ms->timestep = MIN_TIMESTEP_DEFAULT;
++ ms->scaleInNewWindows = TRUE;
++ ms->scaleFromCenter = FALSE;
+
+ minScreenInitOptions (ms);
+
+@@ -764,11 +894,44 @@
+ mw->xScaleVelocity = mw->yScaleVelocity = 1.0f;
+
+ mw->unmapCnt = 0;
++ mw->destroyCnt = 0;
+
+ mw->state = mw->newState = minGetWindowState (w);
+
+ w->privates[ms->windowPrivateIndex].ptr = mw;
+
++ /* use a 'virtual' icon of 32x32 at mpx-16,mpy-16 */
++ /* TODO consider changing this to a configurable thing somnehow */
++ if (w->type & ms->wMask && ms->scaleInNewWindows && mw->state==NormalState)
++ {
++ if (getMousePointerXY(w->screen,&mw->icon.x,&mw->icon.y))
++ {
++ //mw->icon.x=w->attrib.x+(w->attrib.width/2-16);
++ //mw->icon.y=w->attrib.y+(w->attrib.height/2-16);
++ mw->icon.width=FAKE_ICON_SIZE;
++ mw->icon.height=FAKE_ICON_SIZE;
++ mw->icon.x-=FAKE_ICON_SIZE/2;
++ mw->icon.y-=FAKE_ICON_SIZE/2;
++ if (ms->scaleFromCenter)
++ {
++ mw->icon.x = w->attrib.x+w->attrib.width/2-FAKE_ICON_SIZE/2;
++ mw->icon.y = w->attrib.y+w->attrib.height/2-FAKE_ICON_SIZE/2;
++ }
++ mw->tx=mw->icon.x-w->attrib.x;
++ mw->ty=mw->icon.y-w->attrib.y;
++ //mw->tx=w->attrib.width/2-16;
++ //mw->ty=w->attrib.height/2-16;
++ mw->xScale=((float)FAKE_ICON_SIZE)/w->attrib.width;
++ mw->yScale=((float)FAKE_ICON_SIZE)/w->attrib.height;
++ mw->state=IconicState; // we're doing this as a hack, it may not be necessary
++ mw->newState=NormalState;
++ mw->adjust=TRUE;
++ ms->moreAdjust=TRUE;
++ addWindowDamage (w);
++ //fprintf(stderr,"We should have it.\n");
++ }
++ }
++
+ return TRUE;
+ }
+
+--- ./plugins/move.c.old 2006-03-14 11:30:48.000000000 -0500
++++ ./plugins/move.c 2006-03-26 08:43:29.000000000 -0500
+@@ -26,6 +26,8 @@
+ #include <stdio.h>
+ #include <stdlib.h>
+ #include <string.h>
++#include <time.h>
++#include <math.h>
+
+ #include <X11/cursorfont.h>
+
+@@ -37,6 +39,12 @@
+ #define MOVE_TERMINATE_BUTTON_DEFAULT Button1
+ #define MOVE_TERMINATE_MODIFIERS_DEFAULT CompReleaseMask
+
++#define MOVE_SCREEN_OPTION_EDGEFLIP_TIMEBASED_DEFAULT FALSE
++#define MOVE_SCREEN_OPTION_EDGEFLIP_RATIOBASED_DEFAULT FALSE
++#define MOVE_SCREEN_OPTION_EDGEFLIP_TIME_DEFAULT 3.0f
++#define MOVE_SCREEN_OPTION_EDGEFLIP_RATIO_DEFAULT 90.0f
++#define MOVE_SCREEN_OPTION_EDGEFLIP_CONTINOUS_DRAG_DEFAULT FALSE
++
+ struct _MoveKeys {
+ char *name;
+ int dx;
+@@ -62,12 +70,23 @@
+ KeyCode key[NUM_KEYS];
+ } MoveDisplay;
+
+-#define MOVE_SCREEN_OPTION_INITIATE 0
+-#define MOVE_SCREEN_OPTION_TERMINATE 1
+-#define MOVE_SCREEN_OPTION_NUM 2
++#define MOVE_SCREEN_OPTION_INITIATE 0
++#define MOVE_SCREEN_OPTION_TERMINATE 1
++#define MOVE_SCREEN_OPTION_MOVING_OPACITY_LEVEL 2
++#define MOVE_SCREEN_OPTION_EDGEFLIP_TIMEBASED 3
++#define MOVE_SCREEN_OPTION_EDGEFLIP_RATIOBASED 4
++#define MOVE_SCREEN_OPTION_EDGEFLIP_TIME 5
++#define MOVE_SCREEN_OPTION_EDGEFLIP_RATIO 6
++#define MOVE_SCREEN_OPTION_EDGEFLIP_CONTINOUS_DRAG 7
++#define MOVE_SCREEN_OPTION_NUM 8
+
+ typedef struct _MoveScreen {
+ CompOption opt[MOVE_SCREEN_OPTION_NUM];
++
++ PreparePaintScreenProc preparePaintScreen;
++ DonePaintScreenProc donePaintScreen;
++ PaintScreenProc paintScreen;
++ SetScreenOptionForPluginProc setScreenOptionForPlugin;
+
+ int grabIndex;
+
+@@ -75,6 +94,23 @@
+
+ int prevPointerX;
+ int prevPointerY;
++ GLushort savedOpacity;
++ int movingOpacityLevel;
++ time_t FirstEdgeContact;
++ float acceleration;
++ float speed;
++ float timestep;
++
++ GLfloat xrot, xVelocity;
++ GLfloat baseXrot;
++
++ Bool moving;
++ GLfloat moveTo;
++ XPoint savedPointer;
++ Bool grabbed;
++ Bool rotateLeft;
++
++ float prevInvisibleRatio;
+ } MoveScreen;
+
+ #define GET_MOVE_DISPLAY(d) \
+@@ -129,6 +165,29 @@
+ if (compSetBindingOption (o, value))
+ return TRUE;
+ break;
++ case MOVE_SCREEN_OPTION_MOVING_OPACITY_LEVEL:
++ if(compSetIntOption(o, value))
++ {
++ ms->movingOpacityLevel = o->value.i;
++ return TRUE;
++ }
++ break;
++ case MOVE_SCREEN_OPTION_EDGEFLIP_TIMEBASED:
++ case MOVE_SCREEN_OPTION_EDGEFLIP_RATIOBASED:
++ case MOVE_SCREEN_OPTION_EDGEFLIP_CONTINOUS_DRAG:
++ if (compSetBoolOption (o, value))
++ {
++ return TRUE;
++ }
++ break;
++ case MOVE_SCREEN_OPTION_EDGEFLIP_TIME:
++ case MOVE_SCREEN_OPTION_EDGEFLIP_RATIO:
++ if (compSetFloatOption (o, value))
++ {
++ return TRUE;
++ }
++ break;
++
+ default:
+ break;
+ }
+@@ -159,8 +218,209 @@
+ o->value.bind.type = CompBindingTypeButton;
+ o->value.bind.u.button.modifiers = MOVE_TERMINATE_MODIFIERS_DEFAULT;
+ o->value.bind.u.button.button = MOVE_TERMINATE_BUTTON_DEFAULT;
++
++ o = &ms->opt[MOVE_SCREEN_OPTION_MOVING_OPACITY_LEVEL];
++ o->name = "moving_window_opacity_level";
++ o->shortDesc = "Opacity level of moving windows";
++ o->longDesc = "Opacity level of moving windows";
++ o->type = CompOptionTypeInt;
++ o->value.i = 20;
++ o->rest.i.min = 25;
++ o->rest.i.max = 100;
++ ms->movingOpacityLevel = 20;
++
++ o = &ms->opt[MOVE_SCREEN_OPTION_EDGEFLIP_TIMEBASED];
++ o->name = "edgeflip_timebased";
++ o->shortDesc = "Edge flipping on time basis";
++ o->longDesc = "Flip to next viewport when dragging window to the edge for a certain time";
++ o->type = CompOptionTypeBool;
++ o->value.b = MOVE_SCREEN_OPTION_EDGEFLIP_TIMEBASED_DEFAULT;
++
++ o = &ms->opt[MOVE_SCREEN_OPTION_EDGEFLIP_TIME];
++ o->name = "edgeflip_time";
++ o->shortDesc = "Time before edge flipping";
++ o->longDesc = "Time before edge flipping (in seconds)";
++ o->type = CompOptionTypeFloat;
++ o->value.f = MOVE_SCREEN_OPTION_EDGEFLIP_TIME_DEFAULT;
++ o->rest.f.min = 0.1f;
++ o->rest.f.max = 255.0f;
++ o->rest.f.precision = 0.1f;
++
++ o = &ms->opt[MOVE_SCREEN_OPTION_EDGEFLIP_RATIOBASED];
++ o->name = "edgeflip_ratiobased";
++ o->shortDesc = "Edge flipping on time basis";
++ o->longDesc = "Flip to next viewport when dragging window to the edge for a certain time";
++ o->type = CompOptionTypeBool;
++ o->value.b = MOVE_SCREEN_OPTION_EDGEFLIP_RATIOBASED_DEFAULT;
++
++ o = &ms->opt[MOVE_SCREEN_OPTION_EDGEFLIP_RATIO];
++ o->name = "edgeflip_ratio";
++ o->shortDesc = "Ratio of the window's width that has to be out of the screen";
++ o->longDesc = "Ratio of the window's width that has to be out of the screen";
++ o->type = CompOptionTypeFloat;
++ o->value.f = MOVE_SCREEN_OPTION_EDGEFLIP_RATIO_DEFAULT;
++ o->rest.f.min = 0.0f;
++ o->rest.f.max = 100.0f;
++ o->rest.f.precision = 0.1f;
++
++ o = &ms->opt[MOVE_SCREEN_OPTION_EDGEFLIP_CONTINOUS_DRAG];
++ o->name = "edgeflip_continous_drag";
++ o->shortDesc = "Drag windows continously";
++ o->longDesc = "When dragging windows to another desktop, behave like one infinite desktop";
++ o->type = CompOptionTypeBool;
++ o->value.b = MOVE_SCREEN_OPTION_EDGEFLIP_CONTINOUS_DRAG_DEFAULT;
++
++}
++
++static int
++ adjustVelocity (MoveScreen *ms,
++ int size)
++{
++ float xrot, adjust, amount;
++
++ if (ms->moving)
++ {
++ xrot = ms->moveTo + (ms->xrot + ms->baseXrot);
++ }
++ else
++ {
++ xrot = ms->xrot;
++ if (ms->xrot < -180.0f / size)
++ xrot = 360.0f / size + ms->xrot;
++ else if (ms->xrot > 180.0f / size)
++ xrot = ms->xrot - 360.0f / size;
++ }
++
++ adjust = -xrot * 0.05f * ms->acceleration;
++ amount = fabs (xrot);
++ if (amount < 10.0f)
++ amount = 10.0f;
++ else if (amount > 30.0f)
++ amount = 30.0f;
++
++ ms->xVelocity = (amount * ms->xVelocity + adjust) / (amount + 2.0f);
++
++ return (fabs (xrot) < 0.1f && fabs (ms->xVelocity) < 0.2f);
++}
++
++static void
++ movePreparePaintScreen (CompScreen *s,
++ int msSinceLastPaint)
++{
++ MOVE_SCREEN (s);
++
++ if (ms->moving)
++ {
++ int steps;
++ float amount, chunk;
++
++ amount = msSinceLastPaint * 0.05f * ms->speed;
++ steps = amount / (0.5f * ms->timestep);
++ if (!steps) steps = 1;
++ chunk = amount / (float) steps;
++
++ while (steps--)
++ {
++ ms->xrot += ms->xVelocity * chunk;
++
++ if (ms->xrot > 360.0f / s->size)
++ {
++ ms->baseXrot += 360.0f / s->size;
++ ms->xrot -= 360.0f / s->size;
++ }
++ else if (ms->xrot < 0.0f)
++ {
++ ms->baseXrot -= 360.0f / s->size;
++ ms->xrot += 360.0f / s->size;
++ }
++
++ if (adjustVelocity (ms, s->size))
++ {
++ ms->xVelocity = 0.0f;
++
++ float xrot;
++ int tx;
++
++ xrot = ms->baseXrot + ms->xrot;
++ if (xrot < 0.0f)
++ tx = (s->size * xrot / 360.0f) - 0.5f;
++ else
++ tx = (s->size * xrot / 360.0f) + 0.5f;
++
++ moveScreenViewport (s, tx, TRUE);
++
++ ms->xrot = 0.0f;
++ ms->baseXrot = ms->moveTo = 0.0f;
++ ms->moving = FALSE;
++ ms->prevPointerX += s->workArea.width*(ms->rotateLeft?1:-1);
++ ms->FirstEdgeContact = -1;
++
++ if (ms->opt[MOVE_SCREEN_OPTION_EDGEFLIP_CONTINOUS_DRAG].value.b)
++ XWarpPointer(s->display->display,None,s->root,0,0,0,0,
++ ms->prevPointerX,ms->prevPointerY);
++ else
++ XWarpPointer(s->display->display, None, None, 0, 0, 0, 0, 0, 0);
++
++ break;
++ }
++ }
++
++ }
++
++ UNWRAP (ms, s, preparePaintScreen);
++ (*s->preparePaintScreen) (s, msSinceLastPaint);
++ WRAP (ms, s, preparePaintScreen, movePreparePaintScreen);
++}
++
++static void
++ moveDonePaintScreen (CompScreen *s)
++{
++ MOVE_SCREEN (s);
++
++ if (ms->moving)
++ {
++ if (ms->xVelocity)
++ damageScreen (s);
++ }
++ UNWRAP (ms, s, donePaintScreen);
++ (*s->donePaintScreen) (s);
++ WRAP (ms, s, donePaintScreen, moveDonePaintScreen);
++}
++
++static Bool
++ movePaintScreen (CompScreen *s,
++ const ScreenPaintAttrib *sAttrib,
++ Region region,
++ unsigned int mask)
++{
++ Bool status;
++
++ MOVE_SCREEN (s);
++
++ if (ms->moving)
++ {
++ ScreenPaintAttrib sa = *sAttrib;
++
++ sa.xRotate += ms->baseXrot + ms->xrot;
++
++ mask &= ~PAINT_SCREEN_REGION_MASK;
++ mask |= PAINT_SCREEN_TRANSFORMED_MASK;
++
++ UNWRAP (ms, s, paintScreen);
++ status = (*s->paintScreen) (s, &sa, region, mask);
++ WRAP (ms, s, paintScreen, movePaintScreen);
++ }
++ else
++ {
++ UNWRAP (ms, s, paintScreen);
++ status = (*s->paintScreen) (s, sAttrib, region, mask);
++ WRAP (ms, s, paintScreen, movePaintScreen);
++ }
++
++ return status;
+ }
+
++
+ static void
+ moveInitiate (CompWindow *w,
+ int x,
+@@ -197,6 +457,13 @@
+ (w->screen->windowGrabNotify) (w, x, y, state,
+ CompWindowGrabMoveMask |
+ CompWindowGrabButtonMask);
++ ms->savedOpacity=getWindowProp32(w->screen->display,w->id,
++ w->screen->display->winOpacityAtom,
++ w->paint.opacity);
++ w->paint.opacity = getWindowProp32(w->screen->display,w->id,
++ w->screen->display->winOpacityAtom,
++ (GLushort)(OPAQUE*
++ ms->movingOpacityLevel/100.0));
+ }
+
+ static void
+@@ -206,7 +473,10 @@
+
+ if (md->w)
+ {
++
+ MOVE_SCREEN (md->w->screen);
++
++ md->w->paint.opacity=ms->savedOpacity;
+
+ (md->w->screen->windowUngrabNotify) (md->w);
+
+@@ -233,6 +503,10 @@
+ {
+ CompWindow *w;
+ int pointerDx, pointerDy;
++ if (ms->moving)
++ {
++ return;
++ }
+
+ MOVE_DISPLAY (s->display);
+
+@@ -242,7 +516,7 @@
+ pointerDy = yRoot - ms->prevPointerY;
+ ms->prevPointerX = xRoot;
+ ms->prevPointerY = yRoot;
+-
++
+ if (w->type & CompWindowTypeFullscreenMask)
+ {
+ pointerDx = pointerDy = 0;
+@@ -276,8 +550,83 @@
+ }
+ }
+
++ /* after all window moving is done, check for edge flipping */
++ /* NOTE:
++ Since we move the window anyway, the window positions used here
++ are already the positions after the movement (always +pointerDx). */
++ if (!(md->w->state & CompWindowStateStickyMask))
++ {
++ int rotateValue = 0;
++ if (ms->opt[MOVE_SCREEN_OPTION_EDGEFLIP_TIMEBASED].value.b)
++ {
++ if ((xRoot <= s->workArea.x) || (xRoot >= s->workArea.width - 1))
++ {
++ if (ms->FirstEdgeContact == -1)
++ ms->FirstEdgeContact = time(NULL);
++ if (difftime(time(NULL), ms->FirstEdgeContact) >=
++ ms->opt[MOVE_SCREEN_OPTION_EDGEFLIP_TIME].value.f)
++ {
++ ms->FirstEdgeContact = time(NULL);
++
++ rotateValue = (xRoot <= s->workArea.x) ? 1 : -1;
++
++ pointerDx = -rotateValue;
++ }
++ }
++ else if (ms->FirstEdgeContact != -1)
++ ms->FirstEdgeContact = -1;
++ }
++
++ if ((rotateValue == 0) &&
++ (ms->opt[MOVE_SCREEN_OPTION_EDGEFLIP_RATIOBASED].value.b))
++ {
++ int windowWidth;
++ int visibleWidth;
++ float invisibleRatio;
++
++ windowWidth = visibleWidth = w->attrib.width;
++ if ((w->attrib.x + pointerDx) <= s->workArea.x)
++ visibleWidth = ((w->attrib.x + pointerDx) + windowWidth) -
++ s->workArea.x;
++ else if (((w->attrib.x + pointerDx) + windowWidth) >=
++ s->workArea.width - 1)
++ visibleWidth = (s->workArea.x + s->workArea.width) -
++ (w->attrib.x + pointerDx);
++
++ invisibleRatio = 1.0f - (visibleWidth / (float)windowWidth);
++ if ((invisibleRatio >=
++ ms->opt[MOVE_SCREEN_OPTION_EDGEFLIP_RATIO].value.f / 100.0f))
++ {
++ if ((ms->prevInvisibleRatio < 0.0001f) ||
++ ((ms->prevInvisibleRatio - invisibleRatio) >= 0.02f))
++ {
++ ms->prevInvisibleRatio = invisibleRatio;
++
++ rotateValue =
++ ((w->attrib.x + pointerDx) <= s->workArea.x) ? 1 : -1;
++ }
++ }
++ else
++ ms->prevInvisibleRatio = 0.0f;
++ }
++
++ if (rotateValue != 0)
++ {
++ ms->moving = TRUE;
++ ms->moveTo += (360.0f / s->size) * -rotateValue;
++ ms->rotateLeft=rotateValue==1;
++
++ moveWindow(md->w, pointerDx, pointerDy, TRUE);
++
++ damageScreen(s);
++ return;
++ }
++ }
++
+ if (pointerDx || pointerDy)
++ {
+ moveWindow (md->w, pointerDx, pointerDy, TRUE);
++ }
+ }
+ }
+
+@@ -469,6 +818,56 @@
+ free (md);
+ }
+
++static void
++ moveUpdateRotateOptions (CompScreen *s)
++{
++ CompPlugin *p;
++
++ MOVE_SCREEN (s);
++
++ p = findActivePlugin ("rotate");
++ if (p && p->vTable->getScreenOptions)
++ {
++ CompOption *options, *option;
++ int nOptions;
++
++ options = (*p->vTable->getScreenOptions) (s, &nOptions);
++ option = compFindOption (options, nOptions, "speed", 0);
++ if (option)
++ ms->speed = option->value.f;
++ option = compFindOption (options, nOptions, "acceleration", 0);
++ if (option)
++ ms->acceleration = option->value.f;
++ option = compFindOption (options, nOptions, "timestep", 0);
++ if (option)
++ ms->timestep = option->value.f;
++ }
++}
++
++static Bool
++ moveSetScreenOptionForPlugin (CompScreen *s,
++ char *plugin,
++ char *name,
++ CompOptionValue *value)
++{
++ Bool status;
++
++ MOVE_SCREEN (s);
++
++ UNWRAP (ms, s, setScreenOptionForPlugin);
++ status = (*s->setScreenOptionForPlugin) (s, plugin, name, value);
++ WRAP (ms, s, setScreenOptionForPlugin, moveSetScreenOptionForPlugin);
++
++ if (status && strcmp (plugin, "rotate") == 0 && strcmp (name, "speed") == 0)
++ moveUpdateRotateOptions (s);
++ if (status && strcmp (plugin, "rotate") == 0 && strcmp (name, "acceleration") == 0)
++ moveUpdateRotateOptions (s);
++ if (status && strcmp (plugin, "rotate") == 0 && strcmp (name, "timestep") == 0)
++ moveUpdateRotateOptions (s);
++
++ return status;
++}
++
+ static Bool
+ moveInitScreen (CompPlugin *p,
+ CompScreen *s)
+@@ -485,6 +884,17 @@
+
+ ms->prevPointerX = 0;
+ ms->prevPointerY = 0;
++
++ ms->xrot = 0.0f;
++ ms->xVelocity = 0.0f;
++
++ ms->baseXrot = 0.0f;
++
++ ms->moving = FALSE;
++ ms->moveTo = 0.0f;
++
++ ms->FirstEdgeContact = -1;
++ ms->prevInvisibleRatio = 0.0f;
+
+ moveScreenInitOptions (ms, s->display->display);
+
+@@ -493,6 +903,13 @@
+ addScreenBinding (s, &ms->opt[MOVE_SCREEN_OPTION_INITIATE].value.bind);
+
+ s->privates[md->screenPrivateIndex].ptr = ms;
++
++ WRAP (ms, s, preparePaintScreen, movePreparePaintScreen);
++ WRAP (ms, s, donePaintScreen, moveDonePaintScreen);
++ WRAP (ms, s, paintScreen, movePaintScreen);
++ WRAP (ms, s, setScreenOptionForPlugin, moveSetScreenOptionForPlugin);
++
++ moveUpdateRotateOptions (s);
+
+ return TRUE;
+ }
+@@ -523,6 +940,10 @@
+ freeDisplayPrivateIndex (displayPrivateIndex);
+ }
+
++CompPluginDep moveDeps[] = {
++ { CompPluginRuleAfter, "rotate" }
++};
++
+ CompPluginVTable moveVTable = {
+ "move",
+ "Move Window",
+@@ -539,7 +960,7 @@
+ 0, /* SetDisplayOption */
+ moveGetScreenOptions,
+ moveSetScreenOption,
+- NULL,
++ moveDeps,
+ 0
+ };
+
+--- ./plugins/rotate.c.old 2006-03-02 17:39:54.000000000 -0500
++++ ./plugins/rotate.c 2006-03-25 07:19:05.000000000 -0500
+@@ -1089,7 +1089,7 @@
+ rotateFiniDisplay,
+ rotateInitScreen,
+ rotateFiniScreen,
+- 0, /* InitWindow */
++ 0 , /* InitWindow */
+ 0, /* FiniWindow */
+ 0, /* GetDisplayOptions */
+ 0, /* SetDisplayOption */
+diff -ru /usr/portage/distfiles/cvs-src/compiz/plugins/scale.c ./plugins/scale.c
+--- ./plugins/scale.c.old 2006-03-17 08:16:31.000000000 -0500
++++ ./plugins/scale.c 2006-03-26 01:27:05.000000000 -0500
+@@ -50,6 +50,12 @@
+ #define SCALE_TERMINATE_KEY_DEFAULT "F12"
+ #define SCALE_TERMINATE_MODIFIERS_DEFAULT CompPressMask
+
++#define SCALE_CURRENT_INITIATE_KEY_DEFAULT "F11"
++#define SCALE_CURRENT_INITIATE_MODIFIERS_DEFAULT CompPressMask
++
++#define SCALE_CURRENT_TERMINATE_KEY_DEFAULT "F11"
++#define SCALE_CURRENT_TERMINATE_MODIFIERS_DEFAULT CompPressMask
++
+ #define SCALE_NEXT_WINDOW_KEY_DEFAULT "Right"
+ #define SCALE_NEXT_WINDOW_MODIFIERS_DEFAULT CompPressMask
+
+@@ -74,6 +80,8 @@
+ #define SCALE_OPACITY_MIN 0
+ #define SCALE_OPACITY_MAX 100
+
++#define SCALE_USE_CLASS_DEFAULT FALSE
++
+ static char *winType[] = {
+ "Toolbar",
+ "Utility",
+@@ -106,7 +114,10 @@
+ #define SCALE_SCREEN_OPTION_WINDOW_TYPE 7
+ #define SCALE_SCREEN_OPTION_DARKEN_BACK 8
+ #define SCALE_SCREEN_OPTION_OPACITY 9
+-#define SCALE_SCREEN_OPTION_NUM 10
++#define SCALE_SCREEN_OPTION_CURRENT_INITIATE 10
++#define SCALE_SCREEN_OPTION_CURRENT_TERMINATE 11
++#define SCALE_SCREEN_OPTION_USE_CLASS 12
++#define SCALE_SCREEN_OPTION_NUM 13
+
+ typedef struct _ScaleScreen {
+ int windowPrivateIndex;
+@@ -150,6 +161,10 @@
+
+ Bool darkenBack;
+ GLushort opacity;
++
++ Bool onlyCurrent;
++ Bool useClass;
++ CompWindow * currentWindow;
+ } ScaleScreen;
+
+ typedef struct _ScaleWindow {
+@@ -229,6 +244,16 @@
+ return TRUE;
+ }
+ break;
++ case SCALE_SCREEN_OPTION_CURRENT_INITIATE:
++ if (addScreenBinding (screen, &value->bind))
++ {
++ removeScreenBinding (screen, &o->value.bind);
++
++ if (compSetBindingOption (o, value))
++ return TRUE;
++ }
++ break;
++ case SCALE_SCREEN_OPTION_CURRENT_TERMINATE:
+ case SCALE_SCREEN_OPTION_TERMINATE:
+ case SCALE_SCREEN_OPTION_NEXT_WINDOW:
+ if (compSetBindingOption (o, value))
+@@ -261,7 +286,13 @@
+ ss->darkenBack = o->value.b;
+ return TRUE;
+ }
+- case SCALE_SCREEN_OPTION_OPACITY:
++ case SCALE_SCREEN_OPTION_USE_CLASS:
++ if (compSetBoolOption (o, value))
++ {
++ ss->useClass = o->value.b;
++ return TRUE;
++ }
++ case SCALE_SCREEN_OPTION_OPACITY:
+ if (compSetIntOption (o, value))
+ {
+ ss->opacity = (OPAQUE * o->value.i) / 100;
+@@ -319,6 +350,28 @@
+ XKeysymToKeycode (display,
+ XStringToKeysym (SCALE_TERMINATE_KEY_DEFAULT));
+
++ o = &ss->opt[SCALE_SCREEN_OPTION_CURRENT_INITIATE];
++ o->name = "initiate_current";
++ o->shortDesc = "Initiate Current";
++ o->longDesc = "Layout and start transforming windows (current app only)";
++ o->type = CompOptionTypeBinding;
++ o->value.bind.type = CompBindingTypeKey;
++ o->value.bind.u.key.modifiers = SCALE_CURRENT_INITIATE_MODIFIERS_DEFAULT;
++ o->value.bind.u.key.keycode =
++ XKeysymToKeycode (display,
++ XStringToKeysym (SCALE_CURRENT_INITIATE_KEY_DEFAULT));
++
++ o = &ss->opt[SCALE_SCREEN_OPTION_CURRENT_TERMINATE];
++ o->name = "terminate_current";
++ o->shortDesc = "Terminate Current";
++ o->longDesc = "Return from current-app scale view";
++ o->type = CompOptionTypeBinding;
++ o->value.bind.type = CompBindingTypeKey;
++ o->value.bind.u.key.modifiers = SCALE_CURRENT_TERMINATE_MODIFIERS_DEFAULT;
++ o->value.bind.u.key.keycode =
++ XKeysymToKeycode (display,
++ XStringToKeysym (SCALE_CURRENT_TERMINATE_KEY_DEFAULT));
++
+ o = &ss->opt[SCALE_SCREEN_OPTION_NEXT_WINDOW];
+ o->name = "next_window";
+ o->shortDesc = "Next Window";
+@@ -380,6 +433,14 @@
+ o->value.i = SCALE_OPACITY_DEFAULT;
+ o->rest.i.min = SCALE_OPACITY_MIN;
+ o->rest.i.max = SCALE_OPACITY_MAX;
++
++ o = &ss->opt[SCALE_SCREEN_OPTION_USE_CLASS];
++ o->name = "use_class";
++ o->shortDesc = "Use WM_CLASS for only-current";
++ o->longDesc = "Use WM_CLASS to find out wether a window should be scaled in only-current";
++ o->type = CompOptionTypeBool;
++ o->value.b = SCALE_USE_CLASS_DEFAULT;
++
+ }
+
+ static Bool
+@@ -442,7 +503,19 @@
+
+ if (w->state & CompWindowStateSkipPagerMask)
+ return FALSE;
++
++ if (ss->onlyCurrent)
++ {
++ if (!ss->useClass && (w->clientLeader != ss->currentWindow->clientLeader))
++ return FALSE;
++ if (ss->useClass && (strcmp(w->resClass,ss->currentWindow->resClass)!=0))
++ return FALSE;
++ }
+
++ if (!(ss->currentWindow))
++ return TRUE;
++ if (ss->onlyCurrent && ss->currentWindow != w)
++ restackWindowBelow(w,ss->currentWindow);
+ return TRUE;
+ }
+
+@@ -834,7 +907,7 @@
+ }
+
+ static void
+-scaleInitiate (CompScreen *s)
++scaleInitiate (CompScreen *s, Bool CurrentOnly)
+ {
+ SCALE_SCREEN (s);
+ SCALE_DISPLAY (s->display);
+@@ -850,6 +923,11 @@
+ if (!sd->lastActiveNum)
+ sd->lastActiveNum = s->activeNum - 1;
+
++ ss->onlyCurrent=CurrentOnly;
++ if (CurrentOnly)
++ {
++ ss->currentWindow=findWindowAtDisplay(s->display,s->display->activeWindow);
++ }
+ if (layoutThumbs (s))
+ {
+ ss->state = SCALE_STATE_OUT;
+@@ -864,6 +942,8 @@
+ {
+ SCALE_DISPLAY (s->display);
+ SCALE_SCREEN (s);
++ ss->currentWindow=0;
++ ss->onlyCurrent=FALSE;
+
+ if (ss->grabIndex)
+ {
+@@ -1026,14 +1106,18 @@
+ state = ss->state;
+
+ if (EV_KEY (&ss->opt[SCALE_SCREEN_OPTION_INITIATE], event))
+- scaleInitiate (s);
++ scaleInitiate (s,FALSE);
++
++ if (EV_KEY (&ss->opt[SCALE_SCREEN_OPTION_CURRENT_INITIATE], event))
++ scaleInitiate (s,TRUE);
+
+ if (ss->grabIndex &&
+ EV_KEY (&ss->opt[SCALE_SCREEN_OPTION_NEXT_WINDOW], event))
+ scaleNextWindow (s);
+
+- if (state == ss->state &&
+- (EV_KEY (&ss->opt[SCALE_SCREEN_OPTION_TERMINATE], event) ||
++ if (state == ss->state &&
++ (EV_KEY (&ss->opt[SCALE_SCREEN_OPTION_TERMINATE], event) ||
++ EV_KEY (&ss->opt[SCALE_SCREEN_OPTION_CURRENT_TERMINATE], event) ||
+ (event->type == KeyPress &&
+ event->xkey.keycode == s->escapeKeyCode)))
+ scaleTerminate (s);
+@@ -1062,7 +1146,10 @@
+ }
+
+ if (EV_BUTTON (&ss->opt[SCALE_SCREEN_OPTION_INITIATE], event))
+- scaleInitiate (s);
++ scaleInitiate (s,FALSE);
++
++ if (EV_BUTTON (&ss->opt[SCALE_SCREEN_OPTION_CURRENT_INITIATE], event))
++ scaleInitiate (s,TRUE);
+
+ if (ss->grabIndex &&
+ EV_BUTTON (&ss->opt[SCALE_SCREEN_OPTION_NEXT_WINDOW], event))
+@@ -1071,7 +1158,10 @@
+ if (state == ss->state &&
+ EV_BUTTON (&ss->opt[SCALE_SCREEN_OPTION_TERMINATE], event))
+ scaleTerminate (s);
+- }
++ if (state == ss->state &&
++ EV_BUTTON (&ss->opt[SCALE_SCREEN_OPTION_CURRENT_TERMINATE], event))
++ scaleTerminate (s);
++ }
+ break;
+ case MotionNotify:
+ s = findScreenAtDisplay (d, event->xmotion.root);
+@@ -1194,6 +1284,8 @@
+ ss->grabIndex = 0;
+
+ ss->state = SCALE_STATE_NONE;
++
++ ss->useClass = SCALE_USE_CLASS_DEFAULT;
+
+ ss->slots = 0;
+ ss->slotsSize = 0;
+@@ -1211,10 +1303,13 @@
+ ss->speed = SCALE_SPEED_DEFAULT;
+ ss->timestep = SCALE_TIMESTEP_DEFAULT;
+ ss->opacity = (OPAQUE * SCALE_OPACITY_DEFAULT) / 100;
++ ss->onlyCurrent = FALSE;
++ ss->currentWindow = 0;
+
+ scaleScreenInitOptions (ss, s->display->display);
+
+ addScreenBinding (s, &ss->opt[SCALE_SCREEN_OPTION_INITIATE].value.bind);
++ addScreenBinding (s, &ss->opt[SCALE_SCREEN_OPTION_CURRENT_INITIATE].value.bind);
+
+ WRAP (ss, s, preparePaintScreen, scalePreparePaintScreen);
+ WRAP (ss, s, donePaintScreen, scaleDonePaintScreen);
+--- ./plugins/switcher.c.old 2006-03-17 05:06:52.000000000 -0500
++++ ./plugins/switcher.c 2006-03-23 01:54:36.000000000 -0500
+@@ -92,6 +92,7 @@
+
+ Atom selectWinAtom;
+ } SwitchDisplay;
++#define SWITCH_ALL_DESKTOPS_DEFAULT TRUE
+
+ #define SWITCH_SCREEN_OPTION_INITIATE 0
+ #define SWITCH_SCREEN_OPTION_TERMINATE 1
+@@ -105,7 +106,8 @@
+ #define SWITCH_SCREEN_OPTION_BRIGHTNESS 9
+ #define SWITCH_SCREEN_OPTION_OPACITY 10
+ #define SWITCH_SCREEN_OPTION_BRINGTOFRONT 11
+-#define SWITCH_SCREEN_OPTION_NUM 12
++#define SWITCH_SCREEN_OPTION_ALL_DESKTOPS 12
++#define SWITCH_SCREEN_OPTION_NUM 13
+
+ typedef struct _SwitchScreen {
+ PreparePaintScreenProc preparePaintScreen;
+@@ -292,6 +294,10 @@
+ ss->bringToFront = o->value.b;
+ return TRUE;
+ }
++ break;
++ case SWITCH_SCREEN_OPTION_ALL_DESKTOPS:
++ if (compSetBoolOption (o, value))
++ return TRUE;
+ default:
+ break;
+ }
+@@ -425,6 +431,15 @@
+ o->longDesc = "Bring selected window to front";
+ o->type = CompOptionTypeBool;
+ o->value.b = SWITCH_BRINGTOFRONT_DEFAULT;
++
++
++ o = &ss->opt[SWITCH_SCREEN_OPTION_ALL_DESKTOPS];
++ o->name = "all_dekstops";
++ o->shortDesc = "All Desktops";
++ o->longDesc = "Switch between windows on all virtual desktops";
++ o->type = CompOptionTypeBool;
++ o->value.b = SWITCH_ALL_DESKTOPS_DEFAULT;
++
+ }
+
+ static void
+@@ -441,6 +456,7 @@
+ static Bool
+ isSwitchWin (CompWindow *w)
+ {
++ int workspaceX, winRealX, winWorkspace;
+ SWITCH_SCREEN (w->screen);
+
+ if (!w->mapNum || w->attrib.map_state != IsViewable)
+@@ -454,6 +470,17 @@
+
+ if (w->state & CompWindowStateSkipPagerMask)
+ return FALSE;
++
++ if (!ss->opt[SWITCH_SCREEN_OPTION_ALL_DESKTOPS].value.b)
++ {
++ /* only switch between windows in the current workspace
++ Tiago Sousa <mirage@kaotik.org> */
++ workspaceX = w->screen->width * w->screen->x;
++ winRealX = w->serverX + workspaceX;
++ winWorkspace = floor((double)winRealX / (double)w->screen->width);
++ if (winWorkspace != w->screen->x)
++ return FALSE;
++ }
+
+ return TRUE;
+ }
+@@ -726,6 +753,7 @@
+ Visual *visual;
+ Atom mwmHintsAtom;
+ MwmHints mwmHints;
++ Atom type;
+
+ visual = findArgbVisual (dpy, s->screenNum);
+ if (!visual)
+@@ -779,6 +807,13 @@
+ XInternAtom (dpy, "_NET_WM_STATE", 0),
+ XA_ATOM, 32, PropModeReplace,
+ (unsigned char *) state, nState);
++
++ type = XInternAtom (dpy, "_NET_WM_WINDOW_TYPE_SPLASH", 0);
++ XChangeProperty (dpy, ss->popupWindow,
++ XInternAtom (dpy, "_NET_WM_WINDOW_TYPE", 0),
++ XA_ATOM, 32, PropModeReplace,
++ (unsigned char *) &type, 1);
++
+ }
+
+ if (!ss->grabIndex)
+--- ./src/screen.c.old 2006-03-20 12:21:23.000000000 -0500
++++ ./src/screen.c 2006-03-26 00:33:59.000000000 -0500
+@@ -137,6 +137,12 @@
+ screen->display->desktopGeometryAtom,
+ XA_CARDINAL, 32, PropModeReplace,
+ (unsigned char *) data, 2);
++
++ /*data[0] = size;
++ XChangeProperty (screen->display->display, screen->root,
++ screen->display->numberOfDesktopsAtom,
++ XA_CARDINAL, 32, PropModeReplace,
++ (unsigned char *) data, 1);*/
+
+ screen->size = size;
+ }
+@@ -2505,6 +2511,11 @@
+ s->display->desktopViewportAtom,
+ XA_CARDINAL, 32, PropModeReplace,
+ (unsigned char *) data, 2);
++ /*data [0] = s->x;
++ XChangeProperty (s->display->display, s->root,
++ s->display->currentDesktopAtom,
++ XA_CARDINAL, 32, PropModeReplace,
++ (unsigned char *) data, 1);*/
+ }
+ }
+ }
+--- ./src/window.c.old 2006-03-20 09:47:25.000000000 -0500
++++ ./src/window.c 2006-03-25 07:30:25.000000000 -0500
+@@ -489,22 +489,21 @@
+ switch (w->type) {
+ case CompWindowTypeFullscreenMask:
+ case CompWindowTypeNormalMask:
+- actions |=
+- CompWindowActionMinimizeMask |
+- CompWindowActionMaximizeHorzMask |
+- CompWindowActionMaximizeVertMask |
+- CompWindowActionFullscreenMask;
+- /* fall-through */
+ case CompWindowTypeDialogMask:
+ case CompWindowTypeModalDialogMask:
+ case CompWindowTypeUtilMask:
+- case CompWindowTypeToolbarMask:
+- actions |=
+- CompWindowActionMoveMask |
+- CompWindowActionResizeMask |
+- CompWindowActionStickMask |
+- CompWindowActionCloseMask;
++ actions =
++ CompWindowActionMaximizeHorzMask |
++ CompWindowActionMaximizeVertMask |
++ CompWindowActionFullscreenMask |
++ CompWindowActionMoveMask |
++ CompWindowActionResizeMask |
++ CompWindowActionStickMask |
++ CompWindowActionMinimizeMask |
++ CompWindowActionCloseMask;
++ /* All actions should be available on windows that aren't "special" */
+ break;
++ case CompWindowTypeToolbarMask:
+ case CompWindowTypeMenuMask:
+ case CompWindowTypeSplashMask:
+ case CompWindowTypeDesktopMask:
+@@ -514,6 +513,13 @@
+ break;
+ }
+
++ if (w->sizeHints.min_width==w->sizeHints.max_width && w->sizeHints.min_height==w->sizeHints.max_height)
++ {
++ /* according to the docs, THIS is how we should tell if these actions should be restricted */
++ actions &= ~(CompWindowActionResizeMask | CompWindowActionMaximizeHorzMask |
++ CompWindowActionMaximizeVertMask | CompWindowActionFullscreenMask);
++ }
++
+ if (actions != w->actions)
+ {
+ w->actions = actions;