Index: src/keybindings.c
===================================================================
RCS file: /cvs/gnome/metacity/src/keybindings.c,v
retrieving revision 1.102
diff -u -u -r1.102 keybindings.c
--- src/keybindings.c	22 Sep 2004 19:15:26 -0000	1.102
+++ src/keybindings.c	30 Sep 2004 00:35:08 -0000
@@ -2624,11 +2624,14 @@
                       XEvent         *event,
                       MetaKeyBinding *binding)
 {
-  if (window)
-    {
-      if (window->has_resize_func)
-        meta_window_fill_vertical (window);
-    }
+     if (window)
+	  if (window->has_resize_func)
+	  {
+	       if (window->maximized_vertically)
+		    meta_window_unfill_vertical(window);
+	       else
+		    meta_window_fill_vertical (window);
+	  }
 }
 
 static void
@@ -2638,11 +2641,14 @@
                        XEvent         *event,
                        MetaKeyBinding *binding)
 {
-  if (window)
-    {
-      if (window->has_resize_func)
-        meta_window_fill_horizontal (window);
-    }
+     if (window)
+	  if (window->has_resize_func)
+	  {
+	       if (window->maximized_horizontally)
+		    meta_window_unfill_horizontal(window);
+	       else
+		    meta_window_fill_horizontal (window);
+	  }
 }
 
 static gboolean
Index: src/window.c
===================================================================
RCS file: /cvs/gnome/metacity/src/window.c,v
retrieving revision 1.345
diff -u -u -r1.345 window.c
--- src/window.c	15 Sep 2004 15:54:51 -0000	1.345
+++ src/window.c	30 Sep 2004 00:35:09 -0000
@@ -435,6 +435,8 @@
   window->user_has_move_resized = FALSE;
   
   window->maximized = FALSE;
+  window->maximized_vertically = FALSE;
+  window->maximized_horizontally = FALSE;
   window->maximize_after_placement = FALSE;
   window->fullscreen = FALSE;
   window->on_all_workspaces = FALSE;
@@ -1944,13 +1946,15 @@
 {
   meta_topic (META_DEBUG_WINDOW_OPS,
               "Maximizing %s\n", window->desc);
-  
+
   if (saved_rect != NULL)
     window->saved_rect = *saved_rect;
   else
     meta_window_save_rect (window);
-  
+
   window->maximized = TRUE;
+  window->maximized_horizontally = TRUE;
+  window->maximized_vertically = TRUE;
   
   recalc_window_features (window);
   set_net_wm_state (window);
@@ -1989,6 +1993,8 @@
                   "Unmaximizing %s\n", window->desc);
       
       window->maximized = FALSE;
+      window->maximized_vertically = FALSE;
+      window->maximized_horizontally = FALSE;
 
       /* When we unmaximize, if we're doing a mouse move also we could
        * get the window suddenly jumping to the upper left corner of
@@ -1998,7 +2004,7 @@
       if (meta_grab_op_is_moving (window->display->grab_op) &&
           window->display->grab_window == window)
         {
-          window->display->grab_anchor_window_pos = window->saved_rect;
+	   window->display->grab_anchor_window_pos = window->saved_rect;
         }
 
       meta_window_move_resize (window,
@@ -2905,15 +2911,15 @@
   if (!window->has_maximize_func)
     return;
   
-  meta_window_get_outer_rect (window, &rect);
-
-  if ( rect.x >= work_area->x &&
-       rect.y >= work_area->y &&
-       (((work_area->width - work_area->x) - rect.width) <
-        window->size_hints.width_inc) &&
-       (((work_area->height - work_area->y) - rect.height) <
-        window->size_hints.height_inc) )
-    meta_window_maximize (window);
+  if ( ( rect.x >= work_area->x &&
+	 rect.y >= work_area->y &&
+	 (((work_area->width - work_area->x) - rect.width) <
+	  window->size_hints.width_inc) &&
+	 (((work_area->height - work_area->y) - rect.height) <
+	  window->size_hints.height_inc) )
+       || (window->maximized_horizontally && window->maximized_vertically)
+       )
+       meta_window_maximize (window);
 }
 
 void
@@ -2934,14 +2940,50 @@
   
   if (window->frame != NULL)
     {
-      x += window->frame->child_x;
-      w -= (window->frame->child_x + window->frame->right_width);
+	 x += window->frame->child_x;
+	 w -= (window->frame->child_x + window->frame->right_width);
     }
   
+  window->saved_rect.x = window->rect.x;
+  window->saved_rect.width = window->rect.width;
+  if(window->frame)
+       window->saved_rect.x += window->frame->rect.x;
+
+  window->maximized_horizontally = TRUE;
+
+  if(window->maximized_vertically) {
+       /* need to maximize, not just resize horizontally */
+       window->maximized = TRUE;
+  }
+
   meta_window_move_resize (window, TRUE,
                            x, y, w, h);
 
-  check_maximize_to_work_area (window, &work_area);
+//  check_maximize_to_work_area (window, &work_area);
+}
+
+void
+meta_window_unfill_horizontal (MetaWindow  *window)
+{
+  if (window->maximized_horizontally)
+    {
+      window->maximized_horizontally = FALSE;
+
+      if(window->maximized) {
+	   /* undo all the maximization stuff as well, at the next update */
+	   window->maximized = FALSE;
+      }    
+
+      meta_window_move_resize (window,
+                               TRUE,
+                               window->saved_rect.x,
+                               window->user_rect.y,
+                               window->saved_rect.width,
+                               window->user_rect.height);
+
+      recalc_window_features (window);
+      set_net_wm_state (window);
+    }
 }
 
 void
@@ -2966,10 +3008,44 @@
       h -= (window->frame->child_y + window->frame->bottom_height);
     }
   
+  window->saved_rect.y = window->rect.y;
+  window->saved_rect.height = window->rect.height;
+  if(window->frame)
+       window->saved_rect.y += window->frame->rect.y;
+
+  window->maximized_vertically = TRUE;
+
+  if(window->maximized_horizontally) {
+       /* need to maximize, not just resize vertically */
+       window->maximized = TRUE;
+  }
+
   meta_window_move_resize (window, TRUE,
                            x, y, w, h);
 
-  check_maximize_to_work_area (window, &work_area);
+//  check_maximize_to_work_area (window, &work_area);
+}
+
+void
+meta_window_unfill_vertical (MetaWindow  *window)
+{
+  if (window->maximized_vertically)
+    {
+      window->maximized_vertically = FALSE;
+
+      if(window->maximized)
+	   window->maximized = FALSE;
+
+      meta_window_move_resize (window,
+                               TRUE,
+                               window->user_rect.x,
+                               window->saved_rect.y,
+                               window->user_rect.width,
+                               window->saved_rect.height);
+
+      recalc_window_features (window);
+      set_net_wm_state (window);
+    }
 }
 
 static guint move_resize_idle = 0;
Index: src/window.h
===================================================================
RCS file: /cvs/gnome/metacity/src/window.h,v
retrieving revision 1.107
diff -u -u -r1.107 window.h
--- src/window.h	19 Aug 2004 02:05:24 -0000	1.107
+++ src/window.h	30 Sep 2004 00:35:09 -0000
@@ -110,6 +110,12 @@
   guint maximized : 1;
   guint maximize_after_placement : 1;
 
+  /* Whether we're maximized vertically */
+  guint maximized_vertically : 1;
+
+  /* Whether we're maximized horizontally */
+  guint maximized_horizontally : 1;
+
   /* Whether we're shaded */
   guint shaded : 1;
 
@@ -383,7 +389,10 @@
 
 
 void        meta_window_fill_horizontal     (MetaWindow  *window);
+void        meta_window_unfill_horizontal (MetaWindow  *window);
+
 void        meta_window_fill_vertical       (MetaWindow  *window);
+void        meta_window_unfill_vertical (MetaWindow  *window);
 
 /* This recalcs the window/frame size, and recalcs the frame
  * size/contents as well.
