diff --git a/gtk/gtk.symbols b/gtk/gtk.symbols
index 167936d..7298967 100644
--- a/gtk/gtk.symbols
+++ b/gtk/gtk.symbols
@@ -544,6 +544,7 @@ gtk_button_box_set_layout
 #if IN_HEADER(__GTK_BUTTON_H__)
 #if IN_FILE(__GTK_BUTTON_C__)
 gtk_button_clicked
+gtk_button_depress
 #ifndef GTK_DISABLE_DEPRECATED
 gtk_button_enter
 #endif
diff --git a/gtk/gtkbutton.c b/gtk/gtkbutton.c
index 5b328ae..681ca47 100644
--- a/gtk/gtkbutton.c
+++ b/gtk/gtkbutton.c
@@ -127,7 +127,6 @@ static gint gtk_button_enter_notify (GtkWidget * widget,
 				     GdkEventCrossing * event);
 static gint gtk_button_leave_notify (GtkWidget * widget,
 				     GdkEventCrossing * event);
-static void gtk_real_button_pressed (GtkButton * button);
 static void gtk_real_button_released (GtkButton * button);
 static void gtk_real_button_clicked (GtkButton * button);
 static void gtk_real_button_activate  (GtkButton          *button);
@@ -206,7 +205,7 @@ gtk_button_class_init (GtkButtonClass *klass)
   container_class->child_type = gtk_button_child_type;
   container_class->add = gtk_button_add;
 
-  klass->pressed = gtk_real_button_pressed;
+  klass->pressed = gtk_button_depress;
   klass->released = gtk_real_button_released;
   klass->clicked = NULL;
   klass->enter = gtk_button_update_state;
@@ -332,7 +331,8 @@ gtk_button_class_init (GtkButtonClass *klass)
    *
    * Emitted when the button is pressed.
    * 
-   * Deprecated: 2.8: Use the #GtkWidget::button-press-event signal.
+   * Deprecated: 2.8: Use the #GtkWidget::button-press-event signal and
+   * gtk_button_depress().
    */ 
   button_signals[PRESSED] =
     g_signal_new (I_("pressed"),
@@ -364,7 +364,8 @@ gtk_button_class_init (GtkButtonClass *klass)
    * GtkButton::clicked:
    * @button: the object that received the signal
    *
-   * Emitted when the button has been activated (pressed and released).
+   * Emitted when the button has been activated (pressed and released)
+   * with the first mouse button.
    */ 
   button_signals[CLICKED] =
     g_signal_new (I_("clicked"),
@@ -1609,13 +1610,18 @@ static gboolean
 gtk_button_button_release (GtkWidget      *widget,
 			   GdkEventButton *event)
 {
-  GtkButton *button;
+  GtkButton *button = GTK_BUTTON (widget);
 
   if (event->button == 1)
     {
-      button = GTK_BUTTON (widget);
       gtk_button_released (button);
     }
+  else if (button->button_down)
+    {
+      button->button_down = FALSE;
+      if (!button->activate_timeout)
+        gtk_button_update_state (button);
+    }
 
   return TRUE;
 }
@@ -1701,9 +1707,28 @@ gtk_button_leave_notify (GtkWidget        *widget,
   return FALSE;
 }
 
-static void
-gtk_real_button_pressed (GtkButton *button)
+/**
+ * gtk_button_depress:
+ * @button: a #GtkButton
+ *
+ * Presses the button, so that it is drawn pressed and behaves
+ * as if it were pressed.
+ *
+ * This function can be used to trigger click behavior if
+ * the middle or right button is pressed, from a signal
+ * callback in GtkWidget::button-press-event. By default,
+ * only the first button reacts to presses.
+ *
+ * Note that this may not work if the pointer device is
+ * configured to scroll with the middle button as well.
+ *
+ * Since: 2.22
+ **/
+void
+gtk_button_depress (GtkButton *button)
 {
+  g_return_if_fail (GTK_IS_BUTTON (button));
+
   if (button->activate_timeout)
     return;
   
diff --git a/gtk/gtkbutton.h b/gtk/gtkbutton.h
index 7a67ddc..471eba4 100644
--- a/gtk/gtkbutton.h
+++ b/gtk/gtkbutton.h
@@ -98,6 +98,7 @@ void           gtk_button_pressed           (GtkButton      *button);
 void           gtk_button_released          (GtkButton      *button);
 #endif
 void           gtk_button_clicked           (GtkButton      *button);
+void           gtk_button_depress           (GtkButton      *button);
 #ifndef GTK_DISABLE_DEPRECATED
 void           gtk_button_enter             (GtkButton      *button);
 void           gtk_button_leave             (GtkButton      *button);
diff --git a/tests/testgtk.c b/tests/testgtk.c
index ba57dc4..139539c 100644
--- a/tests/testgtk.c
+++ b/tests/testgtk.c
@@ -13825,6 +13825,18 @@ struct {
 };
 int nbuttons = sizeof (buttons) / sizeof (buttons[0]);
 
+static gboolean
+my_button_hack (GtkWidget      *button,
+                GdkEventButton *event,
+                gpointer        data)
+{
+  if (event->button == 3)
+    gtk_button_depress (GTK_BUTTON (button));
+  else if (event->button == 2)
+    g_signal_emit_by_name (button, "pressed", 0);
+  return FALSE;
+}
+
 void
 create_main_window (void)
 {
@@ -13902,6 +13914,8 @@ create_main_window (void)
 			  NULL);
       else
         gtk_widget_set_sensitive (button, FALSE);
+      g_signal_connect (button, "button-press-event",
+                        G_CALLBACK (my_button_hack), NULL);
       gtk_box_pack_start (GTK_BOX (box2), button, TRUE, TRUE, 0);
     }
 
