...
This commit is contained in:
parent
46d224f5ae
commit
b1d438922a
48
HACKING
Normal file
48
HACKING
Normal file
@ -0,0 +1,48 @@
|
||||
|
||||
The script src/run-metacity.sh is useful to hack on the window manager.
|
||||
It runs metacity in an Xnest. e.g.:
|
||||
CLIENTS=3 ./run-metacity.sh
|
||||
or
|
||||
DEBUG=memprof ./run-metacity.sh
|
||||
or whatever.
|
||||
|
||||
src/window.c is where all the guts of the window manager live. This is
|
||||
basically the only remotely scary file.
|
||||
|
||||
src/frames.c is the GtkWidget that handles drawing window frames.
|
||||
|
||||
src/core.h defines the interface used by the GTK portion of the window
|
||||
manager to talk to the other portions. There's some cruft in here
|
||||
that's unused, since nearly all window operations have moved out of
|
||||
this file so frameless apps can have window operations.
|
||||
|
||||
src/ui.h defines the interface the plain Xlib portion of the window
|
||||
manager uses to talk to the GTK portion.
|
||||
|
||||
Files that include gdk.h or gtk.h are not supposed to include
|
||||
display.h or window.h or other core files.
|
||||
|
||||
Files in the core (display.[hc], window.[hc]) are not supposed to
|
||||
include gdk.h or gtk.h.
|
||||
|
||||
When hacking, remember that you can have multiple screens. The code is
|
||||
also written to support multiple displays, but this is useless, since
|
||||
you can just run two copies of the WM. Also, an XKillClient() or
|
||||
shutdown on any display causes Xlib to exit the app, so it would be
|
||||
broken. So the multi-display thing is mostly just for code
|
||||
cleanliness. Multi-screen on the other hand is important for some
|
||||
people.
|
||||
|
||||
Remember that strings stored in X properties are not in UTF-8, and
|
||||
they have to end up in UTF-8 before we try putting them through Pango.
|
||||
|
||||
If you make any X request involving a client window, you have to
|
||||
meta_error_trap_push() around the call; this is not necessary for
|
||||
X requests on the frame windows.
|
||||
|
||||
Remember that not all windows have frames, and window->frame can
|
||||
be NULL.
|
||||
|
||||
The code could use cleanup in a lot of places, feel free to do so.
|
||||
|
||||
|
@ -1,3 +1,4 @@
|
||||
|
||||
SUBDIRS=src
|
||||
|
||||
EXTRA_DIST=HACKING
|
||||
|
2
README
2
README
@ -23,6 +23,8 @@ sometime probably.
|
||||
Feel free to send patches too; Metacity is really small and simple, so
|
||||
if you find a bug or want to add a feature it should be pretty easy.
|
||||
|
||||
See the HACKING file for some notes on hacking Metacity.
|
||||
|
||||
METACITY FEATURES
|
||||
===
|
||||
|
||||
|
@ -1555,24 +1555,26 @@ meta_display_grab_window_buttons (MetaDisplay *display,
|
||||
meta_warning ("Failed to grab button %d with Mod1Mask for frame 0x%lx error code %d\n",
|
||||
i, xwindow, result);
|
||||
|
||||
#if 1
|
||||
/* This is just for debugging, since I end up moving
|
||||
* the Xnest otherwise ;-)
|
||||
*/
|
||||
meta_error_trap_push (display);
|
||||
result = XGrabButton (display->xdisplay, i, ControlMask,
|
||||
xwindow, False,
|
||||
ButtonPressMask | ButtonReleaseMask |
|
||||
PointerMotionMask | PointerMotionHintMask,
|
||||
GrabModeAsync, GrabModeAsync,
|
||||
False, None);
|
||||
XSync (display->xdisplay, False);
|
||||
result = meta_error_trap_pop (display);
|
||||
|
||||
if (result != Success)
|
||||
meta_warning ("Failed to grab button %d with ControlMask for frame 0x%lx error code %d\n",
|
||||
i, xwindow, result);
|
||||
#endif
|
||||
|
||||
if (g_getenv ("METACITY_DEBUG_BUTTON_GRABS"))
|
||||
{
|
||||
/* This is just for debugging, since I end up moving
|
||||
* the Xnest otherwise ;-)
|
||||
*/
|
||||
meta_error_trap_push (display);
|
||||
result = XGrabButton (display->xdisplay, i, ControlMask,
|
||||
xwindow, False,
|
||||
ButtonPressMask | ButtonReleaseMask |
|
||||
PointerMotionMask | PointerMotionHintMask,
|
||||
GrabModeAsync, GrabModeAsync,
|
||||
False, None);
|
||||
XSync (display->xdisplay, False);
|
||||
result = meta_error_trap_pop (display);
|
||||
|
||||
if (result != Success)
|
||||
meta_warning ("Failed to grab button %d with ControlMask for frame 0x%lx error code %d\n",
|
||||
i, xwindow, result);
|
||||
}
|
||||
|
||||
++i;
|
||||
}
|
||||
|
@ -185,6 +185,11 @@ find_next_cascade (MetaWindow *window,
|
||||
|
||||
/* Find the leftmost, then topmost, empty area on the workspace
|
||||
* that can contain the new window.
|
||||
*
|
||||
* Cool feature to have: if we can't fit the current window size,
|
||||
* try shrinking the window (within geometry constraints). But
|
||||
* beware windows such as Emacs with no sane minimum size, we
|
||||
* don't want to create a 1x1 Emacs.
|
||||
*/
|
||||
static gboolean
|
||||
find_first_fit (MetaWindow *window,
|
||||
@ -196,7 +201,7 @@ find_first_fit (MetaWindow *window,
|
||||
int *new_x,
|
||||
int *new_y)
|
||||
{
|
||||
|
||||
/* FIXME */
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -525,6 +525,10 @@ set_clone_restart_commands (void)
|
||||
|
||||
SmcSetProperties (session_connection, 3, props);
|
||||
|
||||
g_free (prop1.vals);
|
||||
g_free (prop2.vals);
|
||||
g_free (prop3.vals);
|
||||
|
||||
g_free (session_file);
|
||||
}
|
||||
|
||||
|
84
src/window.c
84
src/window.c
@ -70,13 +70,22 @@ static gboolean process_property_notify (MetaWindow *window,
|
||||
static void meta_window_show (MetaWindow *window);
|
||||
static void meta_window_hide (MetaWindow *window);
|
||||
|
||||
static void meta_window_move_resize_internal (MetaWindow *window,
|
||||
gboolean is_configure_request,
|
||||
int resize_gravity,
|
||||
int root_x_nw,
|
||||
int root_y_nw,
|
||||
int w,
|
||||
int h);
|
||||
static void adjust_for_gravity (MetaWindow *window,
|
||||
MetaFrameGeometry *fgeom,
|
||||
gboolean coords_assume_border,
|
||||
int x,
|
||||
int y,
|
||||
int *xp,
|
||||
int *yp);
|
||||
static void meta_window_move_resize_internal (MetaWindow *window,
|
||||
gboolean is_configure_request,
|
||||
gboolean do_gravity_adjust,
|
||||
int resize_gravity,
|
||||
int root_x_nw,
|
||||
int root_y_nw,
|
||||
int w,
|
||||
int h);
|
||||
|
||||
|
||||
void meta_window_move_resize_now (MetaWindow *window);
|
||||
|
||||
@ -446,7 +455,7 @@ meta_window_new (MetaDisplay *display, Window xwindow,
|
||||
* passing TRUE for is_configure_request, ICCCM says
|
||||
* initial map is handled same as configure request
|
||||
*/
|
||||
meta_window_move_resize_internal (window, TRUE,
|
||||
meta_window_move_resize_internal (window, TRUE, FALSE,
|
||||
NorthWestGravity,
|
||||
window->size_hints.x,
|
||||
window->size_hints.y,
|
||||
@ -522,7 +531,7 @@ meta_window_apply_session_info (MetaWindow *window,
|
||||
* indeed valid, so we know we'll go right back to one.
|
||||
*/
|
||||
while (window->workspaces)
|
||||
meta_workspace_remove_window (window->workspaces->next->data, window);
|
||||
meta_workspace_remove_window (window->workspaces->data, window);
|
||||
|
||||
tmp = spaces;
|
||||
while (tmp != NULL)
|
||||
@ -543,6 +552,32 @@ meta_window_apply_session_info (MetaWindow *window,
|
||||
g_slist_free (spaces);
|
||||
}
|
||||
}
|
||||
|
||||
if (info->geometry_set)
|
||||
{
|
||||
int x, y, w, h;
|
||||
|
||||
window->placed = TRUE; /* don't do placement algorithms later */
|
||||
|
||||
x = info->rect.x;
|
||||
y = info->rect.y;
|
||||
|
||||
w = window->size_hints.base_width +
|
||||
info->rect.width * window->size_hints.width_inc;
|
||||
h = window->size_hints.base_height +
|
||||
info->rect.height * window->size_hints.height_inc;
|
||||
|
||||
/* Force old gravity, ignoring anything now set */
|
||||
window->size_hints.win_gravity = info->gravity;
|
||||
|
||||
meta_verbose ("Restoring pos %d,%d size %d x %d for %s\n",
|
||||
x, y, w, h, window->desc);
|
||||
|
||||
meta_window_move_resize_internal (window,
|
||||
FALSE, TRUE,
|
||||
NorthWestGravity,
|
||||
x, y, w, h);
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
@ -1020,7 +1055,7 @@ meta_window_unshade (MetaWindow *window)
|
||||
|
||||
|
||||
/* returns values suitable for meta_window_move */
|
||||
void
|
||||
static void
|
||||
adjust_for_gravity (MetaWindow *window,
|
||||
MetaFrameGeometry *fgeom,
|
||||
gboolean coords_assume_border,
|
||||
@ -1155,6 +1190,8 @@ adjust_for_gravity (MetaWindow *window,
|
||||
static void
|
||||
meta_window_move_resize_internal (MetaWindow *window,
|
||||
gboolean is_configure_request,
|
||||
/* only relevant if !is_configure_request */
|
||||
gboolean do_gravity_adjust,
|
||||
int resize_gravity,
|
||||
int root_x_nw,
|
||||
int root_y_nw,
|
||||
@ -1233,7 +1270,7 @@ meta_window_move_resize_internal (MetaWindow *window,
|
||||
frame_size_dy = 0;
|
||||
}
|
||||
|
||||
if (is_configure_request)
|
||||
if (is_configure_request || do_gravity_adjust)
|
||||
{
|
||||
adjust_for_gravity (window,
|
||||
window->frame ? &fgeom : NULL,
|
||||
@ -1424,7 +1461,7 @@ meta_window_resize (MetaWindow *window,
|
||||
|
||||
meta_window_get_position (window, &x, &y);
|
||||
|
||||
meta_window_move_resize_internal (window, FALSE,
|
||||
meta_window_move_resize_internal (window, FALSE, FALSE,
|
||||
NorthWestGravity,
|
||||
x, y, w, h);
|
||||
}
|
||||
@ -1434,7 +1471,7 @@ meta_window_move (MetaWindow *window,
|
||||
int root_x_nw,
|
||||
int root_y_nw)
|
||||
{
|
||||
meta_window_move_resize_internal (window, FALSE,
|
||||
meta_window_move_resize_internal (window, FALSE, FALSE,
|
||||
NorthWestGravity,
|
||||
root_x_nw, root_y_nw,
|
||||
window->rect.width,
|
||||
@ -1448,7 +1485,7 @@ meta_window_move_resize (MetaWindow *window,
|
||||
int w,
|
||||
int h)
|
||||
{
|
||||
meta_window_move_resize_internal (window, FALSE,
|
||||
meta_window_move_resize_internal (window, FALSE, FALSE,
|
||||
NorthWestGravity,
|
||||
root_x_nw, root_y_nw,
|
||||
w, h);
|
||||
@ -1464,7 +1501,7 @@ meta_window_resize_with_gravity (MetaWindow *window,
|
||||
|
||||
meta_window_get_position (window, &x, &y);
|
||||
|
||||
meta_window_move_resize_internal (window, FALSE,
|
||||
meta_window_move_resize_internal (window, FALSE, FALSE,
|
||||
gravity,
|
||||
x, y, w, h);
|
||||
}
|
||||
@ -1579,6 +1616,21 @@ meta_window_get_gravity_position (MetaWindow *window,
|
||||
*root_y = y;
|
||||
}
|
||||
|
||||
void
|
||||
meta_window_get_geometry (MetaWindow *window,
|
||||
int *x,
|
||||
int *y,
|
||||
int *width,
|
||||
int *height)
|
||||
{
|
||||
meta_window_get_gravity_position (window, x, y);
|
||||
|
||||
*width = (window->rect.width - window->size_hints.base_width) /
|
||||
window->size_hints.width_inc;
|
||||
*height = (window->rect.height - window->size_hints.base_height) /
|
||||
window->size_hints.height_inc;
|
||||
}
|
||||
|
||||
void
|
||||
meta_window_get_outer_rect (MetaWindow *window,
|
||||
MetaRectangle *rect)
|
||||
@ -1874,7 +1926,7 @@ meta_window_configure_request (MetaWindow *window,
|
||||
window->size_hints.width = width;
|
||||
window->size_hints.height = height;
|
||||
|
||||
meta_window_move_resize_internal (window, TRUE,
|
||||
meta_window_move_resize_internal (window, TRUE, FALSE,
|
||||
NorthWestGravity,
|
||||
window->size_hints.x,
|
||||
window->size_hints.y,
|
||||
|
@ -257,6 +257,14 @@ void meta_window_get_position (MetaWindow *window,
|
||||
void meta_window_get_gravity_position (MetaWindow *window,
|
||||
int *x,
|
||||
int *y);
|
||||
/* Get geometry for saving in the session; x/y are gravity
|
||||
* position, and w/h are in resize inc above the base size.
|
||||
*/
|
||||
void meta_window_get_geometry (MetaWindow *window,
|
||||
int *x,
|
||||
int *y,
|
||||
int *width,
|
||||
int *height);
|
||||
void meta_window_get_outer_rect (MetaWindow *window,
|
||||
MetaRectangle *rect);
|
||||
void meta_window_delete (MetaWindow *window,
|
||||
|
Loading…
Reference in New Issue
Block a user