--- gtk+-2.6.4/gtk/gtkcheckbutton.c	2004-08-09 19:59:51.000000000 +0300
+++ gtk+-2.6.4/gtk/gtkcheckbutton.c	2005-04-06 16:19:36.317017336 +0300
@@ -31,27 +31,44 @@
 #include "gtklabel.h"
 
 
-#define INDICATOR_SIZE     13
+#define INDICATOR_SIZE     24
 #define INDICATOR_SPACING  2
 
+/* maJiK numbers for indicator */
+#define INDICATOR_SIDE_PADDING 5
+#define FOCUS_TOP_PADDING 7
+#define FOCUS_DOWN_PADDING 1 
+
+/* spacing to take account of the 1 pixel 
+   transparency of the widgetfocus.png 
+*/
+#define HILDON_SPACING 1 
+ 
+#define TOGGLE_ON_CLICK "toggle-on-click"
 
-static void gtk_check_button_class_init          (GtkCheckButtonClass *klass);
-static void gtk_check_button_init                (GtkCheckButton      *check_button);
-static void gtk_check_button_size_request        (GtkWidget           *widget,
-						  GtkRequisition      *requisition);
-static void gtk_check_button_size_allocate       (GtkWidget           *widget,
-						  GtkAllocation       *allocation);
-static gint gtk_check_button_expose              (GtkWidget           *widget,
-						  GdkEventExpose      *event);
-static void gtk_check_button_paint               (GtkWidget           *widget,
-						  GdkRectangle        *area);
-static void gtk_check_button_draw_indicator      (GtkCheckButton      *check_button,
-						  GdkRectangle        *area);
-static void gtk_real_check_button_draw_indicator (GtkCheckButton      *check_button,
-						  GdkRectangle        *area);
+static void gtk_check_button_class_init   (GtkCheckButtonClass *klass);
+static void gtk_check_button_init         (GtkCheckButton     *check_button);
+static void gtk_check_button_size_request (GtkWidget         *widget,
+					   GtkRequisition    *requisition);
+static void gtk_check_button_size_allocate (GtkWidget         *widget,
+					    GtkAllocation     *allocation);
+static gint gtk_check_button_expose        (GtkWidget         *widget,
+					    GdkEventExpose    *event);
+static void gtk_check_button_paint         (GtkWidget        *widget,
+					    GdkRectangle     *area);
+static void gtk_check_button_draw_indicator (GtkCheckButton   *check_button,
+					     GdkRectangle     *area);
+static void gtk_real_check_button_draw_indicator 
+                                             (GtkCheckButton *check_button,
+					      GdkRectangle   *area);
 
-static GtkToggleButtonClass *parent_class = NULL;
+static void gtk_check_button_calc_indicator_size( GtkCheckButton *button, 
+                                                  GdkRectangle *rect );
+
+static void gtk_check_button_clicked (GtkButton *button);
+static void gtk_check_button_update_state (GtkButton *button);
 
+static GtkToggleButtonClass *parent_class = NULL;
 
 GType
 gtk_check_button_get_type (void)
@@ -85,32 +102,36 @@
 gtk_check_button_class_init (GtkCheckButtonClass *class)
 {
   GtkWidgetClass *widget_class;
-  
+  GtkButtonClass *button_class;
+
   widget_class = (GtkWidgetClass*) class;
+  button_class = (GtkButtonClass*) class;
   parent_class = g_type_class_peek_parent (class);
   
   widget_class->size_request = gtk_check_button_size_request;
   widget_class->size_allocate = gtk_check_button_size_allocate;
   widget_class->expose_event = gtk_check_button_expose;
 
+  button_class->clicked = gtk_check_button_clicked;
+
   class->draw_indicator = gtk_real_check_button_draw_indicator;
 
   gtk_widget_class_install_style_property (widget_class,
 					   g_param_spec_int ("indicator_size",
-							     P_("Indicator Size"),
-							     P_("Size of check or radio indicator"),
-							     0,
-							     G_MAXINT,
-							     INDICATOR_SIZE,
-							     G_PARAM_READABLE));
+				               P_("Indicator Size"),
+                       P_("Size of check or radio indicator"),
+                       0,
+                       G_MAXINT,
+                       INDICATOR_SIZE,
+                       G_PARAM_READABLE));
   gtk_widget_class_install_style_property (widget_class,
 					   g_param_spec_int ("indicator_spacing",
-							     P_("Indicator Spacing"),
-							     P_("Spacing around check or radio indicator"),
-							     0,
-							     G_MAXINT,
-							     INDICATOR_SPACING,
-							     G_PARAM_READABLE));
+					             P_("Indicator Spacing"),
+                       P_("Spacing around check or radio indicator"),
+                       0,
+                       G_MAXINT,
+                       INDICATOR_SPACING,
+                       G_PARAM_READABLE));
 }
 
 static void
@@ -148,7 +169,8 @@
 GtkWidget*
 gtk_check_button_new_with_mnemonic (const gchar *label)
 {
-  return g_object_new (GTK_TYPE_CHECK_BUTTON, "label", label, "use_underline", TRUE, NULL);
+  return g_object_new (GTK_TYPE_CHECK_BUTTON, "label", label, 
+                                              "use_underline", TRUE, NULL);
 }
 
 
@@ -163,39 +185,70 @@
   
   if (GTK_WIDGET_DRAWABLE (widget))
     {
-      gint border_width;
-      gint interior_focus;
-      gint focus_width;
-      gint focus_pad;
-	  
+      gint border_width = 0;
+      gint interior_focus = 0;
+      gint focus_width = 0;
+      gint focus_pad = 0;
+      gint indicator_size = 0;
+      gint indicator_spacing = 0;
+      
       gtk_widget_style_get (widget,
 			    "interior-focus", &interior_focus,
 			    "focus-line-width", &focus_width,
 			    "focus-padding", &focus_pad,
+			    "indicator-size", &indicator_size,
+			    "indicator-spacing", &indicator_spacing,
 			    NULL);
-
-      gtk_check_button_draw_indicator (check_button, area);
       
       border_width = GTK_CONTAINER (widget)->border_width;
+      
+      /* Hildon: change the focus so that it draws around the entire
+       * widget - including both the indicator *and* the label 
+       */
       if (GTK_WIDGET_HAS_FOCUS (widget))
 	{
 	  GtkWidget *child = GTK_BIN (widget)->child;
 	  
+	  int w = indicator_size + 2 * indicator_spacing + 
+	          2 * (focus_width + focus_pad);
+	  int h = indicator_size + 2 * indicator_spacing + 
+	          2 * (focus_width + focus_pad) + 2 * HILDON_SPACING
+	          - FOCUS_TOP_PADDING;
+	  int x = widget->allocation.x;
+	  int y = widget->allocation.y + (widget->allocation.height - h)/2 
+	          + FOCUS_DOWN_PADDING;
+	  
+	  if (gtk_widget_get_direction(widget) == GTK_TEXT_DIR_RTL)
+	    x = widget->allocation.x + widget->allocation.width - 
+	      (2 * HILDON_SPACING) - (indicator_size + 2) - 
+	      (indicator_spacing + 2);	  
+
 	  if (interior_focus && child && GTK_WIDGET_VISIBLE (child))
-	    gtk_paint_focus (widget->style, widget->window, GTK_WIDGET_STATE (widget),
-			     NULL, widget, "checkbutton",
-			     child->allocation.x - focus_width - focus_pad,
-			     child->allocation.y - focus_width - focus_pad,
-			     child->allocation.width + 2 * (focus_width + focus_pad),
-			     child->allocation.height + 2 * (focus_width + focus_pad));
+	    {
+	      if (gtk_widget_get_direction(widget) == GTK_TEXT_DIR_RTL)
+		{
+		  /* Move the "x" to the left, and enlarge the width, 
+		     both accounting for the child 
+                   */               
+		  x += - child->allocation.width - HILDON_SPACING - 
+		    (widget->style->xthickness);
+		  w += child->allocation.width + HILDON_SPACING + 
+		    (widget->style->xthickness);
+		} else {
+		  w = child->allocation.x + child->allocation.width + 
+		    2 * widget->style->xthickness - x;
+		}
+		  
+	      gtk_paint_focus (widget->style, widget->window, 
+			       GTK_WIDGET_STATE (widget),
+			       NULL, widget, "checkbutton", x, y, w, h);
+	    }
 	  else
-	    gtk_paint_focus (widget->style, widget->window, GTK_WIDGET_STATE (widget), 
-			     NULL, widget, "checkbutton",
-			     border_width + widget->allocation.x,
-			     border_width + widget->allocation.y,
-			     widget->allocation.width - 2 * border_width,
-			     widget->allocation.height - 2 * border_width);
+	    gtk_paint_focus (widget->style, widget->window, 
+                             GTK_WIDGET_STATE (widget), 
+			     NULL, widget, "checkbutton", x, y, w, h);
 	}
+      gtk_check_button_draw_indicator (check_button, area);
     }
 }
 
@@ -205,10 +258,10 @@
 			     gint           *indicator_spacing)
 {
   GtkWidget *widget =  GTK_WIDGET (check_button);
-
+  
   if (indicator_size)
     gtk_widget_style_get (widget, "indicator_size", indicator_size, NULL);
-
+  
   if (indicator_spacing)
     gtk_widget_style_get (widget, "indicator_spacing", indicator_spacing, NULL);
 }
@@ -233,7 +286,7 @@
 			    "focus-line-width", &focus_width,
 			    "focus-padding", &focus_pad,
 			    NULL);
- 
+
       requisition->width = border_width * 2;
       requisition->height = border_width * 2;
 
@@ -246,15 +299,19 @@
 	  GtkRequisition child_requisition;
 	  
 	  gtk_widget_size_request (child, &child_requisition);
-
-	  requisition->width += child_requisition.width + indicator_spacing;
+	  
+	  requisition->width += child_requisition.width + 
+	    2 * widget->style->xthickness;
 	  requisition->height += child_requisition.height;
+	  requisition->width += 2 * widget->style->xthickness;
 	}
       
-      requisition->width += (indicator_size + indicator_spacing * 2 + 2 * (focus_width + focus_pad));
+      requisition->width += (indicator_size + indicator_spacing * 2 + 
+			     2 * (focus_width + focus_pad));
       
       temp = indicator_size + indicator_spacing * 2;
-      requisition->height = MAX (requisition->height, temp) + 2 * (focus_width + focus_pad);
+      requisition->height = MAX (requisition->height, temp) + 
+	2 * (focus_width + focus_pad);
     }
   else
     (* GTK_WIDGET_CLASS (parent_class)->size_request) (widget, requisition);
@@ -280,45 +337,59 @@
       gint focus_width;
       gint focus_pad;
       
-      _gtk_check_button_get_props (check_button, &indicator_size, &indicator_spacing);
+      _gtk_check_button_get_props (check_button, 
+				   &indicator_size, &indicator_spacing);
       gtk_widget_style_get (widget,
 			    "focus-line-width", &focus_width,
 			    "focus-padding", &focus_pad,
 			    NULL);
-						    
+
       widget->allocation = *allocation;
       if (GTK_WIDGET_REALIZED (widget))
 	gdk_window_move_resize (button->event_window,
 				allocation->x, allocation->y,
 				allocation->width, allocation->height);
       
-      if (GTK_BIN (button)->child && GTK_WIDGET_VISIBLE (GTK_BIN (button)->child))
+      if (GTK_BIN (button)->child && 
+	  GTK_WIDGET_VISIBLE (GTK_BIN (button)->child))
 	{
 	  GtkRequisition child_requisition;
  	  gint border_width = GTK_CONTAINER (widget)->border_width;
-
-	  gtk_widget_get_child_requisition (GTK_BIN (button)->child, &child_requisition);
+	  
+	  gtk_widget_get_child_requisition (GTK_BIN (button)->child, 
+                                            &child_requisition);
  
-	  child_allocation.width = MIN (child_requisition.width,
+	  child_allocation.width = MIN (
+					child_requisition.width,
 					allocation->width -
-					((border_width + focus_width + focus_pad) * 2
-					 + indicator_size + indicator_spacing * 3));
-	  child_allocation.width = MAX (child_allocation.width, 1);
+					((border_width + focus_width + 
+					  focus_pad) * 2
+					 - 2 * widget->style->xthickness + 
+					 indicator_size + 
+					 indicator_spacing * 2 ) );
 
+	  child_allocation.width = MAX (child_allocation.width, 1);
+	  
 	  child_allocation.height = MIN (child_requisition.height,
-					 allocation->height - (border_width + focus_width + focus_pad) * 2);
+					 allocation->height - 
+					 (border_width + focus_width + 
+					  focus_pad) * 2);
 	  child_allocation.height = MAX (child_allocation.height, 1);
 	  
-	  child_allocation.x = (border_width + indicator_size + indicator_spacing * 3 +
-				widget->allocation.x + focus_width + focus_pad);
+	  child_allocation.x = (border_width + indicator_size + 
+				indicator_spacing * 2 +
+				widget->style->xthickness + 
+				widget->allocation.x + 
+				focus_width + focus_pad); 
 	  child_allocation.y = widget->allocation.y +
-		  (allocation->height - child_allocation.height) / 2;
-
+	    (allocation->height - child_allocation.height) / 2;
+	  
 	  if (gtk_widget_get_direction (widget) == GTK_TEXT_DIR_RTL)
-	    child_allocation.x = allocation->x + allocation->width
-	      - (child_allocation.x - allocation->x + child_allocation.width);
+	    child_allocation.x = allocation->x + allocation->width - 
+	      (child_allocation.x - allocation->x + child_allocation.width);
 	  
-	  gtk_widget_size_allocate (GTK_BIN (button)->child, &child_allocation);
+	  gtk_widget_size_allocate (GTK_BIN (button)->child, 
+				    &child_allocation);
 	}
     }
   else
@@ -375,45 +446,33 @@
 				      GdkRectangle   *area)
 {
   GtkWidget *widget;
-  GtkWidget *child;
   GtkButton *button;
   GtkToggleButton *toggle_button;
   GtkStateType state_type;
   GtkShadowType shadow_type;
-  gint x, y;
-  gint indicator_size;
-  gint indicator_spacing;
-  gint focus_width;
-  gint focus_pad;
-  gboolean interior_focus;
+  
+  GdkRectangle indicator = {0, 0, 0, 0};
   
   if (GTK_WIDGET_DRAWABLE (check_button))
     {
       widget = GTK_WIDGET (check_button);
       button = GTK_BUTTON (check_button);
       toggle_button = GTK_TOGGLE_BUTTON (check_button);
-  
-      gtk_widget_style_get (widget, "interior_focus", &interior_focus,
-			    "focus-line-width", &focus_width, 
-			    "focus-padding", &focus_pad, NULL);
-
-      _gtk_check_button_get_props (check_button, &indicator_size, &indicator_spacing);
-
-      x = widget->allocation.x + indicator_spacing + GTK_CONTAINER (widget)->border_width;
-      y = widget->allocation.y + (widget->allocation.height - indicator_size) / 2;
-
-      child = GTK_BIN (check_button)->child;
-      if (!interior_focus || !(child && GTK_WIDGET_VISIBLE (child)))
-	x += focus_width + focus_pad;      
-
+      gtk_check_button_calc_indicator_size( check_button, &indicator );
+      
+      /* move indicator to root coordinates */
+      indicator.x += widget->allocation.x;
+      indicator.y += widget->allocation.y;
+      
       if (toggle_button->inconsistent)
 	shadow_type = GTK_SHADOW_ETCHED_IN;
       else if (toggle_button->active)
 	shadow_type = GTK_SHADOW_IN;
       else
 	shadow_type = GTK_SHADOW_OUT;
-
-      if (button->activate_timeout || (button->button_down && button->in_button))
+      
+      if (button->activate_timeout || 
+	  (button->button_down && button->in_button))
 	state_type = GTK_STATE_ACTIVE;
       else if (button->in_button)
 	state_type = GTK_STATE_PRELIGHT;
@@ -422,32 +481,107 @@
       else
 	state_type = GTK_STATE_NORMAL;
       
-      if (gtk_widget_get_direction (widget) == GTK_TEXT_DIR_RTL)
-	x = widget->allocation.x + widget->allocation.width - (indicator_size + x - widget->allocation.x);
+      /* Hildon change. We want to draw active image always when we have
+       * focus. */
+      if (GTK_WIDGET_HAS_FOCUS (widget))
+	state_type = GTK_STATE_ACTIVE;
 
-      if (GTK_WIDGET_STATE (toggle_button) == GTK_STATE_PRELIGHT)
+      if (gtk_widget_get_direction (widget) == GTK_TEXT_DIR_RTL)
 	{
-	  GdkRectangle restrict_area;
-	  GdkRectangle new_area;
-	      
-	  restrict_area.x = widget->allocation.x + GTK_CONTAINER (widget)->border_width;
-	  restrict_area.y = widget->allocation.y + GTK_CONTAINER (widget)->border_width;
-	  restrict_area.width = widget->allocation.width - (2 * GTK_CONTAINER (widget)->border_width);
-	  restrict_area.height = widget->allocation.height - (2 * GTK_CONTAINER (widget)->border_width);
+	  indicator.x = widget->allocation.x + widget->allocation.width 
+	    - (indicator.width + indicator.x - widget->allocation.x);
 	  
-	  if (gdk_rectangle_intersect (area, &restrict_area, &new_area))
-	    {
-	      gtk_paint_flat_box (widget->style, widget->window, GTK_STATE_PRELIGHT,
-				  GTK_SHADOW_ETCHED_OUT, 
-				  area, widget, "checkbutton",
-				  new_area.x, new_area.y,
-				  new_area.width, new_area.height);
-	    }
 	}
 
       gtk_paint_check (widget->style, widget->window,
 		       state_type, shadow_type,
 		       area, widget, "checkbutton",
-		       x, y, indicator_size, indicator_size);
+		       indicator.x, indicator.y, 
+		       indicator.width, indicator.height);
+    }
+}
+
+
+/* calculates the size and position of the indicator
+ * relative to the origin of the check button.
+ */
+static void gtk_check_button_calc_indicator_size( GtkCheckButton *button, 
+						  GdkRectangle *rect )
+{
+  gint indicator_size;
+  gint indicator_spacing;
+  gint focus_width;
+  gint focus_pad;
+  gboolean interior_focus;
+  GtkWidget *child; 
+  GtkWidget *widget = GTK_WIDGET(button);
+  
+    
+  gtk_widget_style_get (widget, "interior_focus", &interior_focus,
+			"focus-line-width", &focus_width, 
+			"focus-padding", &focus_pad, 
+			"indicator-size", &indicator_size,
+			"indicator-spacing", &indicator_spacing,
+			NULL
+			);
+  
+
+  /* HILDON: We want the indicator to be positioned according to the spec.
+   *
+   * NOTE: INDICATOR_SIDE_PADDING and INDICATOR_TOP_PADDING 
+   * are maJiKal numbers that make the indicator to be drawn 
+   * to correct coordinates, 1337 \o/
+   */
+  rect->x = INDICATOR_SIDE_PADDING;
+  rect->y = ( widget->allocation.height - indicator_size ) / 2;
+  
+  /* Hildon: we always add space for the focus */
+  rect->x += focus_width + focus_pad;      
+
+  child = GTK_BIN (widget)->child;
+  if (interior_focus && child && GTK_WIDGET_VISIBLE (child))
+    {
+      rect->y += HILDON_SPACING;      
     }
+  
+  rect->width = indicator_size;
+  rect->height = indicator_size;
 }
+
+static void
+gtk_check_button_clicked (GtkButton *button)
+{
+  GtkToggleButton *toggle_button = GTK_TOGGLE_BUTTON (button);
+
+  toggle_button->active = !toggle_button->active;
+  gtk_toggle_button_toggled (toggle_button);
+  
+  gtk_check_button_update_state (button);
+  
+  g_object_notify (G_OBJECT (toggle_button), "active");
+}
+
+static void
+gtk_check_button_update_state (GtkButton *button)
+{
+  GtkToggleButton *toggle_button = GTK_TOGGLE_BUTTON (button);
+  gboolean depressed;
+  GtkStateType new_state;
+  
+  if (toggle_button->inconsistent)
+    depressed = FALSE;
+  else if (button->in_button && button->button_down)
+    depressed = TRUE;
+  else
+    depressed = toggle_button->active;
+      
+  if (button->in_button && 
+      (!button->button_down || toggle_button->draw_indicator))
+    new_state = GTK_STATE_PRELIGHT;
+  else
+    new_state = depressed ? GTK_STATE_ACTIVE : GTK_STATE_NORMAL;
+  
+  _gtk_button_set_depressed (button, depressed); 
+  gtk_widget_set_state (GTK_WIDGET (toggle_button), new_state);
+}
+