summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/frame.c98
-rw-r--r--src/frame.h4
-rw-r--r--src/frames.c125
-rw-r--r--src/frames.h60
-rw-r--r--src/main.c11
-rwxr-xr-xsrc/run-metacity.sh2
-rw-r--r--src/screen.c24
-rw-r--r--src/theme.c3
-rw-r--r--src/uislave/frames.c125
-rw-r--r--src/uislave/frames.h60
-rw-r--r--src/window.c6
-rw-r--r--src/window.h2
12 files changed, 481 insertions, 39 deletions
diff --git a/src/frame.c b/src/frame.c
index 789509c..fd23b67 100644
--- a/src/frame.c
+++ b/src/frame.c
@@ -47,6 +47,9 @@ struct _MetaFrameActionGrab
static void clear_tip (MetaFrame *frame);
+static guint draw_handler = 0;
+static GSList *draw_pending = NULL;
+
static void
meta_frame_init_info (MetaFrame *frame,
MetaFrameInfo *info)
@@ -93,26 +96,6 @@ meta_frame_init_info (MetaFrame *frame,
info->current_control_state = META_STATE_PRELIGHT;
}
-static void
-pango_hack_start (MetaDisplay *display)
-{
- if (display->server_grab_count > 0)
- {
- meta_verbose ("Pango workaround, ungrabbing server\n");
- XUngrabServer (display->xdisplay);
- }
-}
-
-static void
-pango_hack_end (MetaDisplay *display)
-{
- if (display->server_grab_count > 0)
- {
- meta_verbose ("Pango workaround, regrabbing server\n");
- XGrabServer (display->xdisplay);
- }
-}
-
void
meta_frame_calc_geometry (MetaFrame *frame,
int child_width, int child_height,
@@ -140,7 +123,10 @@ meta_frame_calc_geometry (MetaFrame *frame,
info.height = child_height;
if (!frame->theme_acquired)
- frame->theme_data = window->screen->engine->acquire_frame (&info);
+ {
+ frame->theme_data = window->screen->engine->acquire_frame (&info);
+ frame->theme_acquired = TRUE;
+ }
geom.left_width = 0;
geom.right_width = 0;
@@ -152,10 +138,8 @@ meta_frame_calc_geometry (MetaFrame *frame,
geom.shape_mask = None;
- pango_hack_start (frame->window->display);
window->screen->engine->fill_frame_geometry (&info, &geom,
frame->theme_data);
- pango_hack_end (frame->window->display);
*geomp = geom;
}
@@ -191,7 +175,7 @@ set_background_color (MetaFrame *frame)
{
XSetWindowAttributes attrs;
- attrs.background_pixel = None;
+ attrs.background_pixel = frame->bg_pixel;
XChangeWindowAttributes (frame->window->display->xdisplay,
frame->xwindow,
CWBackPixel,
@@ -226,6 +210,9 @@ meta_window_ensure_frame (MetaWindow *window)
frame->bg_pixel = 0;
frame->mapped = FALSE;
+
+ frame->edges_exposed = FALSE;
+ frame->title_exposed = FALSE;
attrs.event_mask = EVENT_MASK;
@@ -283,6 +270,11 @@ meta_window_destroy_frame (MetaWindow *window)
frame = window->frame;
+ if (frame->title_exposed || frame->edges_exposed)
+ {
+ draw_pending = g_slist_remove (draw_pending, frame);
+ }
+
if (frame->tooltip_timeout)
clear_tip (frame);
@@ -403,12 +395,10 @@ meta_frame_draw_now (MetaFrame *frame,
info.drawable = p;
info.xoffset = - x;
info.yoffset = - y;
- pango_hack_start (frame->window->display);
+
frame->window->screen->engine->expose_frame (&info,
0, 0, width, height,
frame->theme_data);
- pango_hack_end (frame->window->display);
-
XCopyArea (frame->window->display->xdisplay,
p, frame->xwindow,
@@ -419,13 +409,51 @@ meta_frame_draw_now (MetaFrame *frame,
XFreePixmap (frame->window->display->xdisplay,
p);
+
+ frame->title_exposed = FALSE;
+ frame->edges_exposed = FALSE;
+}
+
+static gboolean
+draw_idle (gpointer data)
+{
+ GSList *tmp;
+
+ tmp = draw_pending;
+ while (tmp != NULL)
+ {
+ int yoffset;
+ MetaFrame *frame;
+
+ frame = tmp->data;
+
+ yoffset = 0;
+ if (!frame->title_exposed)
+ yoffset += frame->child_y;
+
+ meta_frame_draw_now (frame, 0, yoffset,
+ frame->rect.width,
+ frame->rect.height - yoffset);
+ tmp = tmp->next;
+ }
+ g_slist_free (draw_pending);
+ draw_pending = NULL;
+
+ draw_handler = 0;
+ return FALSE;
}
void
meta_frame_queue_draw (MetaFrame *frame)
{
- /* FIXME, actually queue */
- meta_frame_draw_now (frame, 0, 0, -1, -1);
+ if (draw_handler == 0)
+ draw_handler = g_idle_add (draw_idle, NULL);
+
+ if (!(frame->title_exposed || frame->edges_exposed))
+ draw_pending = g_slist_prepend (draw_pending, frame);
+
+ frame->title_exposed = TRUE;
+ frame->edges_exposed = TRUE;
}
static void
@@ -938,11 +966,13 @@ meta_frame_event (MetaFrame *frame,
case KeymapNotify:
break;
case Expose:
- meta_frame_draw_now (frame,
- event->xexpose.x,
- event->xexpose.y,
- event->xexpose.width,
- event->xexpose.height);
+ {
+ gboolean title_was_exposed = frame->title_exposed;
+ meta_frame_queue_draw (frame);
+ if (!title_was_exposed &&
+ event->xexpose.y > frame->child_y)
+ frame->title_exposed = FALSE;
+ }
break;
case GraphicsExpose:
break;
diff --git a/src/frame.h b/src/frame.h
index 83cfda3..314d1c2 100644
--- a/src/frame.h
+++ b/src/frame.h
@@ -63,6 +63,10 @@ struct _MetaFrame
guint theme_acquired : 1;
guint mapped : 1;
+
+ /* world's lamest expose compression */
+ guint edges_exposed : 1;
+ guint title_exposed : 1;
};
void meta_window_ensure_frame (MetaWindow *window);
diff --git a/src/frames.c b/src/frames.c
new file mode 100644
index 0000000..0904e09
--- /dev/null
+++ b/src/frames.c
@@ -0,0 +1,125 @@
+/* Metacity window frame manager widget */
+
+/*
+ * Copyright (C) 2001 Havoc Pennington
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation; either version 2 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+ * 02111-1307, USA.
+ */
+
+#include "frames.h"
+
+static void meta_frames_class_init (MetaFramesClass *klass);
+static void meta_frames_init (MetaFrames *frames);
+static void meta_frames_destroy (GtkObject *object);
+static void meta_frames_finalize (GObject *object);
+static void meta_frames_style_set (GtkWidget *widget,
+ GtkStyle *prev_style);
+
+static GtkWidgetClass *parent_class = NULL;
+static guint signals[LAST_SIGNAL];
+
+GtkType
+meta_frames_get_type (void)
+{
+ static GtkType frames_type = 0;
+
+ if (!frames_type)
+ {
+ static const GtkTypeInfo frames_info =
+ {
+ "MetaFrames",
+ sizeof (MetaFrames),
+ sizeof (MetaFramesClass),
+ (GtkClassInitFunc) meta_frames_class_init,
+ (GtkObjectInitFunc) meta_frames_init,
+ /* reserved_1 */ NULL,
+ /* reserved_2 */ NULL,
+ (GtkClassInitFunc) NULL,
+ };
+
+ frames_type = gtk_type_unique (GTK_TYPE_WIDGET, &frames_info);
+ }
+
+ return frames_type;
+}
+
+static void
+meta_frames_class_init (MetaFramesClass *class)
+{
+ GObjectClass *gobject_class;
+ GtkObjectClass *object_class;
+ GtkWidgetClass *widget_class;
+
+ gobject_class = G_OBJECT_CLASS (class);
+ object_class = (GtkObjectClass*) class;
+ widget_class = (GtkWidgetClass*) class;
+
+ parent_class = g_type_class_peek_parent (class);
+
+ gobject_class->finalize = meta_frames_finalize;
+ object_class->destroy = meta_frames_destroy;
+
+ widget_class->style_set = meta_frames_style_set;
+
+ gtk_widget_class_install_style_property (widget_class,
+ g_param_spec_int ("slider_width",
+ _("Slider Width"),
+ _("Width of scrollbar or scale thumb"),
+ 0,
+ G_MAXINT,
+ 14,
+ G_PARAM_READABLE));
+
+}
+
+static void
+meta_frames_init (MetaFrames *frames)
+{
+ GTK_WINDOW (frames)->type = GTK_WINDOW_POPUP;
+}
+
+static void
+meta_frames_destroy (GtkObject *object)
+{
+
+
+}
+
+static void
+meta_frames_finalize (GObject *object)
+{
+
+
+}
+
+void
+meta_frames_manage_window (MetaFrames *frames,
+ GdkWindow *window)
+{
+ g_return_if_fail (GDK_IS_WINDOW (window));
+
+ gdk_window_set_user_data (window, frames);
+
+ gdk_window_set_events (window,
+ GDK_EXPOSURE_MASK |
+ GDK_POINTER_MOTION_MASK |
+ GDK_POINTER_MOTION_HINT_MASK |
+ GDK_BUTTON_PRESS_MASK |
+ GDK_BUTTON_RELEASE_MASK |
+ GDK_STRUCTURE_MASK);
+}
+
+
diff --git a/src/frames.h b/src/frames.h
new file mode 100644
index 0000000..c9c2583
--- /dev/null
+++ b/src/frames.h
@@ -0,0 +1,60 @@
+/* Metacity window frame manager widget */
+
+/*
+ * Copyright (C) 2001 Havoc Pennington
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation; either version 2 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+ * 02111-1307, USA.
+ */
+
+#ifndef META_FRAMES_H
+#define META_FRAMES_H
+
+#include <gtk/gtk.h>
+
+/* This is one widget that manages all the window frames
+ * as subwindows.
+ */
+
+#define META_TYPE_FRAMES (meta_frames_get_type ())
+#define META_FRAMES(obj) (META_CHECK_CAST ((obj), META_TYPE_FRAMES, MetaFrames))
+#define META_FRAMES_CLASS(klass) (META_CHECK_CLASS_CAST ((klass), META_TYPE_FRAMES, MetaFramesClass))
+#define META_IS_FRAMES(obj) (META_CHECK_TYPE ((obj), META_TYPE_FRAMES))
+#define META_IS_FRAMES_CLASS(klass) (META_CHECK_CLASS_TYPE ((klass), META_TYPE_FRAMES))
+#define META_FRAMES_GET_CLASS(obj) (META_CHECK_GET_CLASS ((obj), META_TYPE_FRAMES, MetaFramesClass))
+
+typedef struct _MetaFrames MetaFrames;
+typedef struct _MetaFramesClass MetaFramesClass;
+
+struct _MetaFrames
+{
+ GtkWindow parent_instance;
+
+};
+
+struct _MetaFramesClass
+{
+ GtkWindowClass parent_class;
+
+};
+
+GType meta_frames_get_type (void) G_GNUC_CONST;
+
+MetaFrames *meta_frames_new (void);
+
+void meta_frames_manage_window (MetaFrames *frames,
+ GdkWindow *window);
+
+#endif
diff --git a/src/main.c b/src/main.c
index a71ac08..e111d6e 100644
--- a/src/main.c
+++ b/src/main.c
@@ -39,6 +39,7 @@ main (int argc, char **argv)
{
struct sigaction act;
sigset_t empty_mask;
+ char *display_name;
sigemptyset (&empty_mask);
act.sa_handler = SIG_IGN;
@@ -57,6 +58,16 @@ main (int argc, char **argv)
g_type_init (0); /* grumble */
meta_errors_init ();
+
+ if (g_getenv ("METACITY_DISPLAY"))
+ {
+ meta_verbose ("Using METACITY_DISPLAY %s\n",
+ g_getenv ("METACITY_DISPLAY"));
+ display_name =
+ g_strconcat ("DISPLAY=", g_getenv ("METACITY_DISPLAY"), NULL);
+ putenv (display_name);
+ /* DO NOT FREE display_name, putenv() sucks */
+ }
if (!meta_display_open (NULL))
meta_exit (META_EXIT_ERROR);
diff --git a/src/run-metacity.sh b/src/run-metacity.sh
index cef1d71..611d94a 100755
--- a/src/run-metacity.sh
+++ b/src/run-metacity.sh
@@ -29,5 +29,5 @@ if test -z "$ONLY_WM"; then
fi
if test -z "$ONLY_SETUP"; then
- METACITY_UISLAVE_DIR=./uislave DISPLAY=:1 exec unst libtool --mode=execute $DEBUG ./metacity
+ METACITY_UISLAVE_DIR=./uislave METACITY_DISPLAY=:1 exec unst libtool --mode=execute $DEBUG ./metacity
fi
diff --git a/src/screen.c b/src/screen.c
index 5374b00..f6029c5 100644
--- a/src/screen.c
+++ b/src/screen.c
@@ -194,6 +194,9 @@ meta_screen_new (MetaDisplay *display,
screen);
screen->stack = meta_stack_new (screen);
+
+ /* hack pango to get its coverage window */
+ meta_screen_get_pango_context (screen, NULL, PANGO_DIRECTION_LTR);
meta_verbose ("Added screen %d ('%s') root 0x%lx\n",
screen->number, screen->screen_name, screen->xroot);
@@ -354,7 +357,26 @@ meta_screen_get_pango_context (MetaScreen *screen,
* are honored.
*/
pango_context_set_base_dir (ctx, direction);
- pango_context_set_font_description (ctx, desc);
+
+ if (desc == NULL)
+ {
+ desc = pango_font_description_from_string ("Sans 12");
+ pango_context_set_font_description (ctx, desc);
+ pango_font_description_free (desc);
+ }
+ else
+ {
+ pango_context_set_font_description (ctx, desc);
+ }
+
+ {
+ /* Make Pango grab server now not later */
+ PangoLayout *hack;
+ hack = pango_layout_new (ctx);
+ pango_layout_set_text (hack, "foo", -1);
+ pango_layout_get_extents (hack, NULL, NULL);
+ g_object_unref (G_OBJECT (hack));
+ }
screen->pango_context = ctx;
}
diff --git a/src/theme.c b/src/theme.c
index c80c2a3..76d104b 100644
--- a/src/theme.c
+++ b/src/theme.c
@@ -601,7 +601,8 @@ default_expose_frame (MetaFrameInfo *info,
draw_current_control_bg (info, &fgeom);
- if (fgeom.title_rect.width > 0 && fgeom.title_rect.height > 0)
+ if (y < fgeom.top_height &&
+ fgeom.title_rect.width > 0 && fgeom.title_rect.height > 0)
{
int layout_y;
MetaRectangle clip;
diff --git a/src/uislave/frames.c b/src/uislave/frames.c
new file mode 100644
index 0000000..0904e09
--- /dev/null
+++ b/src/uislave/frames.c
@@ -0,0 +1,125 @@
+/* Metacity window frame manager widget */
+
+/*
+ * Copyright (C) 2001 Havoc Pennington
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation; either version 2 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+ * 02111-1307, USA.
+ */
+
+#include "frames.h"
+
+static void meta_frames_class_init (MetaFramesClass *klass);
+static void meta_frames_init (MetaFrames *frames);
+static void meta_frames_destroy (GtkObject *object);
+static void meta_frames_finalize (GObject *object);
+static void meta_frames_style_set (GtkWidget *widget,
+ GtkStyle *prev_style);
+
+static GtkWidgetClass *parent_class = NULL;
+static guint signals[LAST_SIGNAL];
+
+GtkType
+meta_frames_get_type (void)
+{
+ static GtkType frames_type = 0;
+
+ if (!frames_type)
+ {
+ static const GtkTypeInfo frames_info =
+ {
+ "MetaFrames",
+ sizeof (MetaFrames),
+ sizeof (MetaFramesClass),
+ (GtkClassInitFunc) meta_frames_class_init,
+ (GtkObjectInitFunc) meta_frames_init,
+ /* reserved_1 */ NULL,
+ /* reserved_2 */ NULL,
+ (GtkClassInitFunc) NULL,
+ };
+
+ frames_type = gtk_type_unique (GTK_TYPE_WIDGET, &frames_info);
+ }
+
+ return frames_type;
+}
+
+static void
+meta_frames_class_init (MetaFramesClass *class)
+{
+ GObjectClass *gobject_class;
+ GtkObjectClass *object_class;
+ GtkWidgetClass *widget_class;
+
+ gobject_class = G_OBJECT_CLASS (class);
+ object_class = (GtkObjectClass*) class;
+ widget_class = (GtkWidgetClass*) class;
+
+ parent_class = g_type_class_peek_parent (class);
+
+ gobject_class->finalize = meta_frames_finalize;
+ object_class->destroy = meta_frames_destroy;
+
+ widget_class->style_set = meta_frames_style_set;
+
+ gtk_widget_class_install_style_property (widget_class,
+ g_param_spec_int ("slider_width",
+ _("Slider Width"),
+ _("Width of scrollbar or scale thumb"),
+ 0,
+ G_MAXINT,
+ 14,
+ G_PARAM_READABLE));
+
+}
+
+static void
+meta_frames_init (MetaFrames *frames)
+{
+ GTK_WINDOW (frames)->type = GTK_WINDOW_POPUP;
+}
+
+static void
+meta_frames_destroy (GtkObject *object)
+{
+
+
+}
+
+static void
+meta_frames_finalize (GObject *object)
+{
+
+
+}
+
+void
+meta_frames_manage_window (MetaFrames *frames,
+ GdkWindow *window)
+{
+ g_return_if_fail (GDK_IS_WINDOW (window));
+
+ gdk_window_set_user_data (window, frames);
+
+ gdk_window_set_events (window,
+ GDK_EXPOSURE_MASK |
+ GDK_POINTER_MOTION_MASK |
+ GDK_POINTER_MOTION_HINT_MASK |
+ GDK_BUTTON_PRESS_MASK |
+ GDK_BUTTON_RELEASE_MASK |
+ GDK_STRUCTURE_MASK);
+}
+
+
diff --git a/src/uislave/frames.h b/src/uislave/frames.h
new file mode 100644
index 0000000..c9c2583
--- /dev/null
+++ b/src/uislave/frames.h
@@ -0,0 +1,60 @@
+/* Metacity window frame manager widget */
+
+/*
+ * Copyright (C) 2001 Havoc Pennington
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation; either version 2 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+ * 02111-1307, USA.
+ */
+
+#ifndef META_FRAMES_H
+#define META_FRAMES_H
+
+#include <gtk/gtk.h>
+
+/* This is one widget that manages all the window frames
+ * as subwindows.
+ */
+
+#define META_TYPE_FRAMES (meta_frames_get_type ())
+#define META_FRAMES(obj) (META_CHECK_CAST ((obj), META_TYPE_FRAMES, MetaFrames))
+#define META_FRAMES_CLASS(klass) (META_CHECK_CLASS_CAST ((klass), META_TYPE_FRAMES, MetaFramesClass))
+#define META_IS_FRAMES(obj) (META_CHECK_TYPE ((obj), META_TYPE_FRAMES))
+#define META_IS_FRAMES_CLASS(klass) (META_CHECK_CLASS_TYPE ((klass), META_TYPE_FRAMES))
+#define META_FRAMES_GET_CLASS(obj) (META_CHECK_GET_CLASS ((obj), META_TYPE_FRAMES, MetaFramesClass))
+
+typedef struct _MetaFrames MetaFrames;
+typedef struct _MetaFramesClass MetaFramesClass;
+
+struct _MetaFrames
+{
+ GtkWindow parent_instance;
+
+};
+
+struct _MetaFramesClass
+{
+ GtkWindowClass parent_class;
+
+};
+
+GType meta_frames_get_type (void) G_GNUC_CONST;
+
+MetaFrames *meta_frames_new (void);
+
+void meta_frames_manage_window (MetaFrames *frames,
+ GdkWindow *window);
+
+#endif
diff --git a/src/window.c b/src/window.c
index ab8dd92..b68b2a7 100644
--- a/src/window.c
+++ b/src/window.c
@@ -324,7 +324,11 @@ meta_window_free (MetaWindow *window)
window->border_width);
meta_error_trap_pop (window->display);
-
+
+ g_free (window->sm_client_id);
+ g_free (window->role);
+ g_free (window->res_class);
+ g_free (window->res_name);
g_free (window->title);
g_free (window->desc);
g_free (window);
diff --git a/src/window.h b/src/window.h
index c5d0d91..b4c5a12 100644
--- a/src/window.h
+++ b/src/window.h
@@ -127,7 +127,7 @@ struct _MetaWindow
*/
guint user_has_resized : 1;
guint user_has_moved : 1;
-
+
/* Number of UnmapNotify that are caused by us, if
* we get UnmapNotify with none pending then the client
* is withdrawing the window.