Index: nautilus-zoom-control.c
===================================================================
RCS file: /cvs/gnome/nautilus/src/nautilus-zoom-control.c,v
retrieving revision 1.74
diff -u -r1.74 nautilus-zoom-control.c
--- nautilus-zoom-control.c	9 Sep 2002 17:21:36 -0000	1.74
+++ nautilus-zoom-control.c	13 Oct 2002 20:52:28 -0000
@@ -19,7 +19,8 @@
  * along with this program; if not, write to the Free Software
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
  *
- * Author: Andy Hertzfeld <andy@eazel.com>
+ * Author: Andy Hertzfeld <andy@eazel.com>,
+ * 	   Jan Arne Petersen <jpetersen@uni-bonn.de>
  *
  * This is the zoom control for the location bar
  *
@@ -32,18 +33,18 @@
 #include <libgnome/gnome-i18n.h>
 #include <eel/eel-accessibility.h>
 #include <eel/eel-glib-extensions.h>
-#include <eel/eel-graphic-effects.h>
 #include <eel/eel-gtk-extensions.h>
 #include <gtk/gtkaccessible.h>
 #include <gtk/gtkmenu.h>
 #include <gtk/gtkradiomenuitem.h>
 #include <gtk/gtkbindings.h>
+#include <gtk/gtklabel.h>
+#include <gtk/gtkbutton.h>
+#include <gtk/gtkhbox.h>
+#include <gtk/gtkimage.h>
+#include <gtk/gtkarrow.h>
 #include <gdk/gdkkeysyms.h>
 #include <libgnome/gnome-macros.h>
-#include <libnautilus-private/nautilus-file-utilities.h>
-#include <libnautilus-private/nautilus-global-preferences.h>
-#include <libnautilus-private/nautilus-marshal.h>
-#include <libnautilus-private/nautilus-theme.h>
 #include <math.h>
 #include <stdlib.h>
 #include <string.h>
@@ -57,15 +58,6 @@
 	LAST_SIGNAL
 };
 
-typedef enum {
-	PRELIGHT_NONE,
-	PRELIGHT_MINUS,
-	PRELIGHT_CENTER,
-	PRELIGHT_PLUS
-} PrelightMode;
-
-#define	GAP_WIDTH 2
-
 struct NautilusZoomControlDetails {
 	float zoom_level;
 	float min_zoom_level;	 
@@ -74,19 +66,15 @@
 	gboolean has_max_zoom_level;
 	GList *preferred_zoom_levels;
 
-	int y_offset;
-	GdkPixbuf *zoom_body_image;
-	GdkPixbuf *zoom_decrement_image;
-	GdkPixbuf *zoom_increment_image;
-	GdkPixbuf *number_strip;
-	PrelightMode prelight_mode;
+	GtkTooltips *tooltips;
 
-	PangoLayout *layout;
+	GtkLabel *zoom_label;
+	GtkButton *zoom_out_button;
+	GtkButton *zoom_in_button;
 
 	gboolean marking_menu_items;
 };
 
-
 static guint signals[LAST_SIGNAL];
 
 static gpointer accessible_parent_class;
@@ -109,11 +97,10 @@
 	N_("Try to fit in window"),
 };
 
-static void nautilus_zoom_control_load_images   (NautilusZoomControl      *zoom_control);
-static void nautilus_zoom_control_unload_images (NautilusZoomControl      *zoom_control);
-static void nautilus_zoom_control_theme_changed (gpointer                  user_data);
+static GType	nautilus_zoom_control_accessible_get_type (void);
+static GtkMenu *create_zoom_menu 			  (NautilusZoomControl *zoom_control,
+							   GtkToggleButton *zoom_button);
 
-static GType nautilus_zoom_control_accessible_get_type (void);
 
 /* button assignments */
 #define CONTEXTUAL_MENU_BUTTON 3
@@ -126,374 +113,245 @@
 static void
 nautilus_zoom_control_finalize (GObject *object)
 {
-	eel_preferences_remove_callback (NAUTILUS_PREFERENCES_THEME,
-					 nautilus_zoom_control_theme_changed,
-					 object);
+	NautilusZoomControl *zoom_control;
 
-	nautilus_zoom_control_unload_images (NAUTILUS_ZOOM_CONTROL (object));
+	zoom_control = NAUTILUS_ZOOM_CONTROL (object);
+	
+	if (zoom_control->details->tooltips != NULL) {
+		g_object_unref (G_OBJECT (zoom_control->details->tooltips));
+		zoom_control->details->tooltips = NULL;
+	}
 
-	eel_g_list_free_deep (NAUTILUS_ZOOM_CONTROL (object)->details->preferred_zoom_levels);
-	g_free (NAUTILUS_ZOOM_CONTROL (object)->details);
+	eel_g_list_free_deep (zoom_control->details->preferred_zoom_levels);
+	g_free (zoom_control->details);
 
 	G_OBJECT_CLASS (parent_class)->finalize (object);
 }
 
-static int
-get_zoom_width (NautilusZoomControl *zoom_control)
-{
-	int total_width;
-	total_width = gdk_pixbuf_get_width (zoom_control->details->zoom_increment_image);
-	total_width += GAP_WIDTH;
-	total_width += gdk_pixbuf_get_width (zoom_control->details->zoom_body_image);
-	total_width += GAP_WIDTH;
-	total_width += gdk_pixbuf_get_width (zoom_control->details->zoom_decrement_image);
-	return total_width;
-}
-
 static void
-nautilus_zoom_control_instance_init (NautilusZoomControl *zoom_control)
+menu_position_under (GtkMenu *menu,
+		     int *x, 
+		     int *y,
+		     gboolean *push_in,
+		     gpointer user_data)
 {
-	GTK_WIDGET_SET_FLAGS (zoom_control, GTK_CAN_FOCUS);
-	GTK_WIDGET_UNSET_FLAGS (zoom_control, GTK_NO_WINDOW);
+	GtkWidget *widget;
 
-	gtk_widget_add_events (GTK_WIDGET (zoom_control), 
-			       GDK_BUTTON_PRESS_MASK
-			       | GDK_BUTTON_RELEASE_MASK
-			       | GDK_POINTER_MOTION_MASK);
-	
-	zoom_control->details = g_new0 (NautilusZoomControlDetails, 1);
-	
-	zoom_control->details->zoom_level = 1.0;
-	zoom_control->details->min_zoom_level = 0.0;
-	zoom_control->details->max_zoom_level = 2.0;
-	zoom_control->details->has_min_zoom_level = TRUE;
-	zoom_control->details->has_max_zoom_level = TRUE;
+	g_return_if_fail (GTK_IS_BUTTON (user_data));
+	g_return_if_fail (GTK_WIDGET_NO_WINDOW (user_data));
 
-	nautilus_zoom_control_load_images (zoom_control);
-	
-	gtk_widget_set_size_request (GTK_WIDGET (zoom_control),
-				     get_zoom_width (zoom_control), -1);
-
-	eel_preferences_add_callback (NAUTILUS_PREFERENCES_THEME,
-				      nautilus_zoom_control_theme_changed,
-				      zoom_control);
-}
+	widget = GTK_WIDGET (user_data);
 
-/* allocate a new zoom control */
-GtkWidget *
-nautilus_zoom_control_new (void)
-{
-	return gtk_widget_new (nautilus_zoom_control_get_type (), NULL);
+	gdk_window_get_origin (widget->window, x, y);
+	
+	*x += widget->allocation.x;
+	*y += widget->allocation.y + widget->allocation.height;
+	
+	*push_in = FALSE;
 }
 
-/* handler for handling theme changes */
-static void
-nautilus_zoom_control_theme_changed (gpointer user_data)
+static gboolean
+zoom_button_press_cb (GtkWidget *widget,
+		      GdkEventButton *event,
+		      gpointer user_data)
 {
 	NautilusZoomControl *zoom_control;
 
 	zoom_control = NAUTILUS_ZOOM_CONTROL (user_data);
-	gtk_widget_hide (GTK_WIDGET (zoom_control));
-	nautilus_zoom_control_load_images (zoom_control);
-	gtk_widget_show (GTK_WIDGET (zoom_control));	
-}
-
-static int
-get_zoom_offset (const char *property)
-{
-	char *num_str;
-	int result;
-	
-	result = 0;
-	num_str = nautilus_theme_get_theme_data ("zoom_control", property);
-	if (num_str != NULL) {
-		result = atoi (num_str);
-		g_free (num_str);
-	}
-
-	return result;
-}
-
-/* draw the current zoom percentage, using a custom number strip if one is available, or
-   using the ordinary text routines otherwise */
-static void
-draw_number (GtkWidget *widget, GdkRectangle *box)
-{
-	char buffer[8];
-	char *cur_char;
-	int x, y, percent; 
-	int char_height, char_width, char_offset;
-	int num_v_offset, num_h_offset;
-	NautilusZoomControl *zoom_control;
-	GdkPixbuf *number_pixbuf;
-	PangoRectangle logical_rect;
-
-	zoom_control = NAUTILUS_ZOOM_CONTROL (widget);
 	
-	num_v_offset = get_zoom_offset ("number_v_2_offset");
-	num_h_offset = get_zoom_offset ("number_h_offset");
+	if ((event->type == GDK_BUTTON_PRESS) && event->button == 1) {
+		gtk_widget_grab_focus (widget);
 		
-	percent = floor ((100.0 * zoom_control->details->zoom_level) + .5);
-	g_snprintf (buffer, 8, "%d", percent);
-	
-	if (zoom_control->details->number_strip != NULL) {
-		number_pixbuf = zoom_control->details->number_strip;
-		if (zoom_control->details->prelight_mode == PRELIGHT_CENTER) {
-			number_pixbuf = eel_create_spotlight_pixbuf (number_pixbuf);
-		}
-		
-		char_width = get_zoom_offset ("digit_width");
-		if (char_width <= 0) {
-			char_width = gdk_pixbuf_get_width (number_pixbuf) / 10;
-		}
-		char_height = gdk_pixbuf_get_height (number_pixbuf);
+		gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (widget), TRUE);
+		gtk_menu_popup (create_zoom_menu (zoom_control, 
+					          GTK_TOGGLE_BUTTON (widget)),
+				NULL, NULL, menu_position_under, widget,
+				event->button, event->time);
 
-		x = box->x + num_h_offset + ((box->width - char_width * strlen (buffer)) >> 1);  
-		y = box->y + num_v_offset + ((box->height - char_height) >> 1);
-
-		cur_char = &buffer[0];		
-		while (*cur_char) {
-			char_offset = (*cur_char++ - '0') * char_width;
-			gdk_pixbuf_render_to_drawable_alpha (number_pixbuf,
-							     widget->window, 
-							     char_offset, 0, x, y,
-							     char_width,
-							     char_height,
-							     GDK_PIXBUF_ALPHA_BILEVEL, 128, GDK_RGB_DITHER_MAX,
-							     0, 0);
-			x += char_width;
-		}
-	
-		if (number_pixbuf != zoom_control->details->number_strip) {
-			g_object_unref (number_pixbuf);
-		}
-	} else {
-		pango_layout_set_text (zoom_control->details->layout, buffer, -1);
-		pango_layout_get_pixel_extents (zoom_control->details->layout, NULL, &logical_rect);
-
-		x = box->x + num_h_offset + (box->width - logical_rect.width)  / 2;
-		y = box->y + num_v_offset + (box->height - logical_rect.height) / 2;
-
-		gtk_paint_layout (widget->style,
-				  widget->window,
-				  GTK_WIDGET_STATE (widget),
-				  FALSE,
-				  box,
-				  widget,
-				  "zoom_control",
-				  x, y,
-				  zoom_control->details->layout);
-	}
-}
-
-/* utilities to simplify drawing */
-static void
-draw_pixbuf (GdkPixbuf *pixbuf, GdkDrawable *drawable, int x, int y)
-{
-	gdk_pixbuf_render_to_drawable_alpha (pixbuf, drawable, 0, 0, x, y,
-					     gdk_pixbuf_get_width (pixbuf),
-					     gdk_pixbuf_get_height (pixbuf),
-					     GDK_PIXBUF_ALPHA_BILEVEL, 128, GDK_RGB_DITHER_MAX,
-					     0, 0);
-}
-
-static void
-draw_pixbuf_with_prelight (NautilusZoomControl *zoom_control, GdkPixbuf *pixbuf, int x_pos, int y_pos, PrelightMode mode)
-{
-	GdkPixbuf *temp_pixbuf;
-	temp_pixbuf = pixbuf;
-	if (zoom_control->details->prelight_mode == mode) {
-		temp_pixbuf = eel_create_spotlight_pixbuf (temp_pixbuf);
-	}
-	draw_pixbuf (temp_pixbuf, GTK_WIDGET (zoom_control)->window, x_pos, y_pos + zoom_control->details->y_offset);
-	if (pixbuf != temp_pixbuf) {
-		g_object_unref (temp_pixbuf);
+		return TRUE;
 	}
-
+	return FALSE;
 }
 
-/* draw the zoom control image into the passed-in rectangle */
-
-static void
-draw_zoom_control_image (GtkWidget *widget, GdkRectangle *box)
+static gboolean
+zoom_button_key_press_cb (GtkWidget *widget,
+			  GdkEventKey *event,
+			  gpointer user_data)
 {
 	NautilusZoomControl *zoom_control;
-	int offset, width, height;
-		
-	zoom_control = NAUTILUS_ZOOM_CONTROL (widget);
 
-	/* draw the decrement symbol if necessary, complete with prelighting */
-	if (nautilus_zoom_control_can_zoom_out (zoom_control)) {
-		draw_pixbuf_with_prelight (zoom_control, zoom_control->details->zoom_decrement_image,
-					   box->x, box->y, PRELIGHT_MINUS);
-	} else {
-		width  = gdk_pixbuf_get_width (zoom_control->details->zoom_decrement_image);
-		height = gdk_pixbuf_get_height (zoom_control->details->zoom_decrement_image);		
-		
-		/* Clear the symbol area to get the default widget background */
-		gdk_window_clear_area (widget->window,
-				       box->x,
-				       box->y + zoom_control->details->y_offset,
-				       width,
-				       height);
+	zoom_control = NAUTILUS_ZOOM_CONTROL (user_data);
+
+	if (event->keyval == GDK_space ||
+	    event->keyval == GDK_KP_Space ||
+	    event->keyval == GDK_Return ||
+	    event->keyval == GDK_KP_Enter) {
+		gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (widget), TRUE);
+		gtk_menu_popup (create_zoom_menu (zoom_control, 
+					          GTK_TOGGLE_BUTTON (widget)),
+				NULL, NULL, menu_position_under, widget,
+				1, event->time);
+		return TRUE;
 	}
 	
-	offset = gdk_pixbuf_get_width (zoom_control->details->zoom_decrement_image) + GAP_WIDTH;
-	/* draw the body image, prelighting if necessary */
-	draw_pixbuf_with_prelight (zoom_control, zoom_control->details->zoom_body_image,
-				   box->x + offset, box->y, PRELIGHT_CENTER);
-	
-	offset += gdk_pixbuf_get_width (zoom_control->details->zoom_body_image) + GAP_WIDTH;
-	
-	/* draw the increment symbol if necessary, complete with prelighting */
-	if (nautilus_zoom_control_can_zoom_in (zoom_control)) {
-		draw_pixbuf_with_prelight (zoom_control, zoom_control->details->zoom_increment_image,
-					   box->x + offset, box->y, PRELIGHT_PLUS);
-	} else {
-		width  = gdk_pixbuf_get_width (zoom_control->details->zoom_increment_image);
-		height = gdk_pixbuf_get_height (zoom_control->details->zoom_increment_image);		
-
-		/* Clear the symbol area to get the default widget background */
-		gdk_window_clear_area (widget->window,
-				       box->x + offset,
-				       box->y + zoom_control->details->y_offset,
-				       width,
-				       height);
-	}
+	return FALSE;
 }
 
-/* handle expose events */
-
-static int
-nautilus_zoom_control_expose (GtkWidget *widget, GdkEventExpose *event)
+static void
+zoom_out_button_clicked (GtkButton *button,
+			 NautilusZoomControl *zoom_control)
 {
-	GdkRectangle box;
-	g_return_val_if_fail (widget != NULL, FALSE);
-	g_return_val_if_fail (NAUTILUS_IS_ZOOM_CONTROL (widget), FALSE);
-
-	box.x = 0; box.y = 0;
-	box.width = widget->allocation.width;
-	box.height = widget->allocation.height;
-
-	draw_zoom_control_image (widget, &box);	
-	draw_number (widget, &box);
-	
-	if (GTK_WIDGET_HAS_FOCUS (widget)) {
-		gtk_paint_focus (widget->style,
-				 widget->window,
-				 GTK_WIDGET_STATE (widget),
-				 &event->area,
-				 widget,
-				 "nautilus-zoom-control",
-				 box.x, box.y,
-				 box.width, box.height);
-	}		 
-
-	return FALSE;
+	g_signal_emit (G_OBJECT (zoom_control), signals[ZOOM_OUT], 0);
 }
 
-/* set the prelight mode and redraw as necessary */
 static void
-nautilus_zoom_control_set_prelight_mode (NautilusZoomControl *zoom_control, PrelightMode mode)
+zoom_in_button_clicked (GtkButton *button,
+			NautilusZoomControl *zoom_control)
 {
-	if (mode != zoom_control->details->prelight_mode) {
-		zoom_control->details->prelight_mode = mode;		
-		gtk_widget_queue_draw (GTK_WIDGET (zoom_control));	
-	}
-	
+	g_signal_emit (G_OBJECT (zoom_control), signals[ZOOM_IN], 0);
 }
 
-/* routines to load the images used to draw the control */
+/* handle mouse wheel scrolls */
 
-/* load or reload the images from the current theme */
+static gboolean
+zoom_button_scroll_event_cb (GtkWidget *widget,
+			     GdkEventScroll *event,
+			     NautilusZoomControl *zoom_control)
+{
+	switch (event->direction) {
+		case GDK_SCROLL_UP :
+			if (nautilus_zoom_control_can_zoom_in (zoom_control)) {
+				g_signal_emit (zoom_control, signals[ZOOM_IN], 0);
+			}
+			return TRUE;
+		case GDK_SCROLL_DOWN :
+			if (nautilus_zoom_control_can_zoom_out (zoom_control)) {
+				g_signal_emit (zoom_control, signals[ZOOM_OUT], 0);
+			}
+			return TRUE;
+		default :
+			return FALSE;
+	}
+}
 
 static void
-nautilus_zoom_control_unload_images (NautilusZoomControl *zoom_control)
+nautilus_zoom_control_instance_init (NautilusZoomControl *zoom_control)
 {
-	if (zoom_control->details->zoom_body_image) {
-		g_object_unref (zoom_control->details->zoom_body_image);
-		zoom_control->details->zoom_body_image = NULL;
-	}
+	GtkHBox *hbox, *zoom_hbox;
+	GtkArrow *arrow;
+	GtkToggleButton *zoom_button;
+	PangoAttrList *attr_list;
+	PangoAttribute *attr;
 	
-	if (zoom_control->details->zoom_decrement_image) {
-		g_object_unref (zoom_control->details->zoom_decrement_image);
-		zoom_control->details->zoom_decrement_image = NULL;
-	}
+	zoom_control->details = g_new0 (NautilusZoomControlDetails, 1);
 	
-	if (zoom_control->details->zoom_increment_image) {
-		g_object_unref (zoom_control->details->zoom_increment_image);
-		zoom_control->details->zoom_increment_image = NULL;
-	}
-
-	if (zoom_control->details->number_strip != NULL) {
-		g_object_unref (zoom_control->details->number_strip);
-		zoom_control->details->number_strip = NULL;
-	}
+	zoom_control->details->zoom_level = 1.0;
+	zoom_control->details->min_zoom_level = 0.0;
+	zoom_control->details->max_zoom_level = 2.0;
+	zoom_control->details->has_min_zoom_level = TRUE;
+	zoom_control->details->has_max_zoom_level = TRUE;
 
-	if (zoom_control->details->layout != NULL) {
-		g_object_unref (zoom_control->details->layout);
-		zoom_control->details->layout = NULL;
-	}
-}
+	zoom_control->details->tooltips = gtk_tooltips_new ();
+	g_object_ref (zoom_control->details->tooltips);
+        gtk_object_sink (GTK_OBJECT (zoom_control->details->tooltips));
+
+	zoom_control->details->zoom_label = g_object_new (GTK_TYPE_LABEL,
+							  "label", "100%",
+							  NULL);
+
+	attr_list = pango_attr_list_new ();
+	attr = pango_attr_weight_new (PANGO_WEIGHT_BOLD);
+	attr->start_index = 0;
+	attr->end_index = G_MAXINT;
+	pango_attr_list_insert (attr_list, attr);
+	gtk_label_set_attributes (zoom_control->details->zoom_label,
+				  attr_list);
+	pango_attr_list_unref (attr_list);
+
+	arrow = g_object_new (GTK_TYPE_ARROW,
+			      "arrow-type", GTK_ARROW_DOWN,
+			      "shadow-type", GTK_SHADOW_NONE,
+			      NULL);
+
+	zoom_hbox = g_object_new (GTK_TYPE_HBOX,
+				  "spacing", 0,
+				  NULL);
+ 
+	gtk_box_pack_start (GTK_BOX (zoom_hbox), 
+			    GTK_WIDGET (zoom_control->details->zoom_label),
+			    FALSE, FALSE, 0);
+	gtk_box_pack_end (GTK_BOX (zoom_hbox), GTK_WIDGET (arrow),
+			  FALSE, FALSE, 0);
+	
+	zoom_button = g_object_new (GTK_TYPE_TOGGLE_BUTTON,
+				    "relief", GTK_RELIEF_NONE,
+				    NULL);
+
+	g_signal_connect (G_OBJECT (zoom_button),
+			  "button_press_event",
+			  G_CALLBACK (zoom_button_press_cb),
+			  zoom_control);
+	g_signal_connect (G_OBJECT (zoom_button),
+			  "key_press_event",
+			  G_CALLBACK (zoom_button_key_press_cb),
+			  zoom_control);
+	g_signal_connect (G_OBJECT (zoom_button),
+			  "scroll_event",
+			  G_CALLBACK (zoom_button_scroll_event_cb),
+			  zoom_control);
+
+	gtk_container_add (GTK_CONTAINER (zoom_button),
+			   GTK_WIDGET (zoom_hbox));
+
+	zoom_control->details->zoom_out_button = g_object_new (GTK_TYPE_BUTTON,
+							       "relief", GTK_RELIEF_NONE,
+							       NULL);
+	g_signal_connect (G_OBJECT (zoom_control->details->zoom_out_button),
+			  "clicked",
+			  G_CALLBACK (zoom_out_button_clicked),
+			  zoom_control);
+	gtk_tooltips_set_tip (zoom_control->details->tooltips,
+			      GTK_WIDGET (zoom_control->details->zoom_out_button),
+			      _("Show the contents in less detail"), NULL);
+	gtk_container_add (GTK_CONTAINER (zoom_control->details->zoom_out_button),
+			   gtk_image_new_from_stock (GTK_STOCK_ZOOM_OUT,
+				   		     GTK_ICON_SIZE_BUTTON));
+
+	zoom_control->details->zoom_in_button = g_object_new (GTK_TYPE_BUTTON,
+							      "relief", GTK_RELIEF_NONE,
+							      NULL);
+	g_signal_connect (G_OBJECT (zoom_control->details->zoom_in_button),
+			  "clicked",
+			  G_CALLBACK (zoom_in_button_clicked),
+			  zoom_control);
+	gtk_tooltips_set_tip (zoom_control->details->tooltips,
+			      GTK_WIDGET (zoom_control->details->zoom_in_button),
+			      _("Show the contents in more detail"), NULL);
+	gtk_container_add (GTK_CONTAINER (zoom_control->details->zoom_in_button),
+			   gtk_image_new_from_stock (GTK_STOCK_ZOOM_IN,
+				   		     GTK_ICON_SIZE_BUTTON));
+
+	hbox = g_object_new (GTK_TYPE_HBOX,
+			     "spacing", 0,
+			     NULL);
+
+	gtk_box_pack_start (GTK_BOX (hbox), GTK_WIDGET (zoom_control->details->zoom_out_button),
+			    FALSE, FALSE, 0);
+	gtk_box_pack_start (GTK_BOX (hbox), GTK_WIDGET (zoom_button),
+			    FALSE, FALSE, 0);
+	gtk_box_pack_start (GTK_BOX (hbox), GTK_WIDGET (zoom_control->details->zoom_in_button),
+			    FALSE, FALSE, 0);
 
-static GdkPixbuf*
-load_themed_image (const char *file_name)
-{
-	GdkPixbuf *pixbuf;
-	char *image_path;
-	
-	image_path = nautilus_theme_get_image_path (file_name);
-	if (image_path) {
-		pixbuf = gdk_pixbuf_new_from_file (image_path, NULL);
-		g_free (image_path);
-		return pixbuf;
-	}
-	return NULL;
-}
+	gtk_container_add (GTK_CONTAINER (zoom_control), GTK_WIDGET (hbox));
 
-static void
-nautilus_zoom_control_update_offsets (NautilusZoomControl *zoom_control)
-{
-	zoom_control->details->y_offset = (
-		GTK_WIDGET (zoom_control)->allocation.height -
-		gdk_pixbuf_get_height (zoom_control->details->zoom_body_image)) >> 1;
+	gtk_widget_show_all (GTK_WIDGET (hbox));
 }
 
-static void
-nautilus_zoom_control_load_images (NautilusZoomControl *zoom_control)
+/* allocate a new zoom control */
+GtkWidget *
+nautilus_zoom_control_new (void)
 {
-	PangoContext *context;
-	PangoFontDescription *font_desc;
-	char *font_name;
-
-	nautilus_zoom_control_unload_images (zoom_control);
-
-	zoom_control->details->zoom_body_image = load_themed_image ("zoom_body.png");
-	zoom_control->details->zoom_decrement_image = load_themed_image ("decrement.png");
-	zoom_control->details->zoom_increment_image = load_themed_image ("increment.png");
-
-	zoom_control->details->number_strip = load_themed_image ("number_strip.png");
-
-	if (zoom_control->details->number_strip == NULL) {
-		context = gtk_widget_get_pango_context (GTK_WIDGET (zoom_control));
-		zoom_control->details->layout = pango_layout_new (context);
-		
-		font_name = nautilus_theme_get_theme_data ("zoom", "font_name");
-		if (font_name == NULL) {
-			font_name = g_strdup ("Mono 9");
-		}
-
-		font_desc = pango_font_description_from_string (font_name);
-		if (font_desc != NULL) {
-			pango_layout_set_font_description (zoom_control->details->layout,
-							   font_desc);
-		}
-
-		pango_font_description_free (font_desc);
-		g_free (font_name);
-	}
-
-	nautilus_zoom_control_update_offsets (zoom_control);
+	return gtk_widget_new (nautilus_zoom_control_get_type (), NULL);
 }
 
 /* routines to create and handle the zoom menu */
@@ -579,15 +437,47 @@
 	return GTK_RADIO_MENU_ITEM (menu_item);
 }
 
+static void
+menu_deactivate_callback (GtkWidget *widget,
+			  GtkToggleButton *zoom_button)
+{
+	gtk_toggle_button_set_active (zoom_button, FALSE);
+}
+
+static void
+default_zoom_menu_callback (GtkMenuItem *item,
+			    NautilusZoomControl *zoom_control)
+{
+	g_signal_emit (zoom_control, signals[ZOOM_TO_FIT], 0);
+}
+
 static GtkMenu *
-create_zoom_menu (NautilusZoomControl *zoom_control)
+create_zoom_menu (NautilusZoomControl *zoom_control,
+		  GtkToggleButton *zoom_button)
 {
 	GtkMenu *menu;
+	GtkWidget *default_item, *separator_item;
 	GtkRadioMenuItem *previous_item;
 	GList *node;
 
 	menu = GTK_MENU (gtk_menu_new ());
 
+	g_signal_connect (G_OBJECT (menu), "deactivate",
+			  G_CALLBACK (menu_deactivate_callback),
+			  zoom_button);
+
+	default_item = gtk_image_menu_item_new_with_mnemonic (_("Normal Si_ze"));
+	gtk_image_menu_item_set_image (GTK_IMAGE_MENU_ITEM (default_item),
+				       gtk_image_new_from_stock (GTK_STOCK_ZOOM_100,
+					       			 GTK_ICON_SIZE_MENU));
+	g_signal_connect (G_OBJECT (default_item), "activate",
+			  G_CALLBACK (default_zoom_menu_callback), zoom_control);
+	gtk_widget_show_all (default_item);
+	gtk_menu_shell_append (GTK_MENU_SHELL (menu), default_item);
+	separator_item = gtk_separator_menu_item_new ();
+	gtk_widget_show (separator_item);
+	gtk_menu_shell_append (GTK_MENU_SHELL (menu), separator_item);
+
 	previous_item = NULL;
 	for (node = zoom_control->details->preferred_zoom_levels; node != NULL; node = node->next) {
 		previous_item = create_zoom_menu_item
@@ -596,63 +486,6 @@
 	
 	return menu;  
 }
-  
-/* handle button presses */
-
-static gboolean
-nautilus_zoom_control_button_press_event (GtkWidget *widget, GdkEventButton *event)
-{
-	NautilusZoomControl *zoom_control;
-	int width, center;
-	
-	zoom_control = NAUTILUS_ZOOM_CONTROL (widget);
-
-	if (event->type != GDK_BUTTON_PRESS) {
-		return FALSE;
-	}
-
-	gtk_widget_grab_focus (widget);
-
-	/* check for the context menu button and handle by creating and showing the menu */  
-	if (event->button == CONTEXTUAL_MENU_BUTTON) {
-		eel_pop_up_context_menu (create_zoom_menu (zoom_control), 
-					 EEL_DEFAULT_POPUP_MENU_DISPLACEMENT, 
-					 EEL_DEFAULT_POPUP_MENU_DISPLACEMENT, 
-					 event);
-		return TRUE;
- 	}
-	
-	width = widget->allocation.width;
-	center = width >> 1;
-	if ((event->x < (width / 3)) && nautilus_zoom_control_can_zoom_out (zoom_control)) {
-		g_signal_emit (widget, signals[ZOOM_OUT], 0);			
-	} else if ((event->x > ((2 * width) / 3)) && nautilus_zoom_control_can_zoom_in (zoom_control)) {
-		g_signal_emit (widget, signals[ZOOM_IN], 0);			
-	} else if ((event->x >= (center - (width >> 3))) && (event->x <= (center + (width >> 3)))) {
-		g_signal_emit (widget, signals[ZOOM_TO_FIT], 0);			
-	}
-
-	/* We don't change our state (to reflect the new zoom) here. The zoomable will
-	 * call back with the new level. Actually, the callback goes to the view-frame
-	 * containing the zoomable which, in turn, emits zoom_level_changed, which
-	 * someone (e.g. nautilus_window) picks up and handles by calling into us -
-	 * nautilus_zoom_control_set_zoom_level.
-	 */	  
-  
-	return TRUE;
-}
-
-/* handle setting the prelight mode */
-
-/* handle enter, leave and motion events to maintain the prelight state */
-
-static gboolean
-nautilus_zoom_control_leave_notify (GtkWidget *widget,
-			 	    GdkEventCrossing *event)
-{
-	nautilus_zoom_control_set_prelight_mode (NAUTILUS_ZOOM_CONTROL (widget), PRELIGHT_NONE);
-  	return FALSE;
-}
 
 static AtkObject *
 nautilus_zoom_control_get_accessible (GtkWidget *widget)
@@ -671,52 +504,6 @@
 	return eel_accessibility_set_atk_object_return (widget, accessible);
 }
 
-static gboolean
-nautilus_zoom_control_motion_notify (GtkWidget *widget, GdkEventMotion *event)
-{
-	int x, y, x_offset;
-	int width, center;
-	NautilusZoomControl *zoom_control;
-	PrelightMode mode;
-	
-	zoom_control = NAUTILUS_ZOOM_CONTROL (widget);
-	
-	gtk_widget_get_pointer (widget, &x, &y);
-	
-	x_offset = x ;
-	width = widget->allocation.width;
-	center = width >> 1;
-
-	mode = PRELIGHT_NONE;
-	if ((x_offset < (width / 3)) && nautilus_zoom_control_can_zoom_out (zoom_control)) {
-		mode = PRELIGHT_MINUS;		
-	} else if ((x_offset > ((2 * width) / 3)) && nautilus_zoom_control_can_zoom_in (zoom_control)) {
-		mode = PRELIGHT_PLUS;
-	} else if ((x_offset >= (center - (width >> 3))) && (x_offset <= (center + (width >> 3)))) {
-		mode = PRELIGHT_CENTER;
-	}
-
-	nautilus_zoom_control_set_prelight_mode (zoom_control, mode);
-	
-	return FALSE;
-}
-
-
-/* handle setting the size */
-static void
-nautilus_zoom_control_size_allocate (GtkWidget *widget, GtkAllocation *allocation)
-{
-	NautilusZoomControl *zoom_control;
-
-	zoom_control = NAUTILUS_ZOOM_CONTROL (widget);
-
-	GTK_WIDGET_CLASS (parent_class)->size_allocate (widget, allocation);
-	
-	widget->allocation.width = get_zoom_width (zoom_control);
-   	widget->allocation.height = allocation->height;
-	nautilus_zoom_control_update_offsets (zoom_control);
-}
-
 static void
 nautilus_zoom_control_change_value (NautilusZoomControl *zoom_control, 
 				    GtkScrollType scroll)
@@ -740,8 +527,20 @@
 void
 nautilus_zoom_control_set_zoom_level (NautilusZoomControl *zoom_control, float zoom_level)
 {
+	gchar buffer[9];
+	gint percent;
+
 	zoom_control->details->zoom_level = zoom_level;
-	gtk_widget_queue_draw (GTK_WIDGET (zoom_control));
+
+	/* update zoom label */
+	percent = floor ((100.0 * zoom_control->details->zoom_level) + .5);
+	g_snprintf (buffer, 9, "%d%%", percent);
+	gtk_label_set_text (zoom_control->details->zoom_label, buffer);
+
+	gtk_widget_set_sensitive (GTK_WIDGET (zoom_control->details->zoom_out_button),
+				  nautilus_zoom_control_can_zoom_out (zoom_control));
+	gtk_widget_set_sensitive (GTK_WIDGET (zoom_control->details->zoom_in_button),
+				  nautilus_zoom_control_can_zoom_in (zoom_control));
 }
 
 void
@@ -821,13 +620,8 @@
 
 	widget_class = GTK_WIDGET_CLASS (class);
 	
-	widget_class->button_press_event = nautilus_zoom_control_button_press_event;
-	widget_class->expose_event = nautilus_zoom_control_expose;
-	widget_class->motion_notify_event = nautilus_zoom_control_motion_notify;
-	widget_class->size_allocate = nautilus_zoom_control_size_allocate;
-  	widget_class->leave_notify_event = nautilus_zoom_control_leave_notify;
 	widget_class->get_accessible = nautilus_zoom_control_get_accessible;
-	
+
 	class->change_value = nautilus_zoom_control_change_value;
 
 	signals[ZOOM_IN] =
