Rename gsheetmodel to psppiresheetmodel
[pspp-builds.git] / lib / gtksheet / gtksheet.c
index 94c56f340473e914f2b7dafac5cd0d1a6cfa6439..977d3bbc1c73f84941c025c7c03bde9f24157811 100644 (file)
@@ -54,7 +54,7 @@
 #include <pango/pango.h>
 #include "gtksheet.h"
 #include <gtksheet/psppire-marshal.h>
-#include "gsheetmodel.h"
+#include "psppire-sheetmodel.h"
 #include <libpspp/misc.h>
 #include <math.h>
 
@@ -91,6 +91,7 @@ static void set_entry_widget_font (GtkSheet *sheet);
 static void gtk_sheet_update_primary_selection (GtkSheet *sheet);
 static void draw_column_title_buttons_range (GtkSheet *sheet, gint first, gint n);
 static void draw_row_title_buttons_range (GtkSheet *sheet, gint first, gint n);
+static void redraw_range (GtkSheet *sheet, GtkSheetRange *range);
 
 
 static void set_row_height (GtkSheet *sheet,
@@ -106,12 +107,12 @@ static GtkStateType gtk_sheet_cell_get_state (GtkSheet *sheet, gint row, gint co
 static inline  void
 dispose_string (const GtkSheet *sheet, gchar *text)
 {
-  GSheetModel *model = gtk_sheet_get_model (sheet);
+  PsppireSheetModel *model = gtk_sheet_get_model (sheet);
 
   if ( ! model )
     return;
 
-  if (g_sheet_model_free_strings (model))
+  if (psppire_sheet_model_free_strings (model))
     g_free (text);
 }
 
@@ -225,12 +226,20 @@ static gboolean
 on_column_boundary (const GtkSheet *sheet, gint x, gint *column)
 {
   gint col;
+  gint pixel;
 
   x += sheet->hadjustment->value;
 
+  if ( x < 0)
+    return FALSE;
+
   col = column_from_xpixel (sheet, x);
 
-  if ( column_from_xpixel (sheet, x - DRAG_WIDTH / 2) < col )
+  pixel = x - DRAG_WIDTH / 2;
+  if (pixel < 0)
+    pixel = 0;
+
+  if ( column_from_xpixel (sheet, pixel) < col )
     {
       *column = col - 1;
       return TRUE;
@@ -249,12 +258,20 @@ static gboolean
 on_row_boundary (const GtkSheet *sheet, gint y, gint *row)
 {
   gint r;
+  gint pixel;
 
   y += sheet->vadjustment->value;
 
+  if ( y < 0)
+    return FALSE;
+
   r = row_from_ypixel (sheet, y);
 
-  if ( row_from_ypixel (sheet, y - DRAG_WIDTH / 2) < r )
+  pixel = y - DRAG_WIDTH / 2;
+  if (pixel < 0)
+    pixel = 0;
+
+  if ( row_from_ypixel (sheet, pixel) < r )
     {
       *row = r - 1;
       return TRUE;
@@ -367,16 +384,9 @@ rectangle_from_range (GtkSheet *sheet, const GtkSheetRange *range,
   r->x = psppire_axis_start_pixel (sheet->haxis, range->col0);
   r->x -= round (sheet->hadjustment->value);
 
-  if ( sheet->row_titles_visible)
-    r->x += sheet->row_title_area.width;
-
-
   r->y = psppire_axis_start_pixel (sheet->vaxis, range->row0);
   r->y -= round (sheet->vadjustment->value);
 
-  if ( sheet->column_titles_visible)
-    r->y += sheet->column_title_area.height;
-
   r->width = psppire_axis_start_pixel (sheet->haxis, range->coli) -
     psppire_axis_start_pixel (sheet->haxis, range->col0) +
     psppire_axis_unit_size (sheet->haxis, range->coli);
@@ -385,6 +395,16 @@ rectangle_from_range (GtkSheet *sheet, const GtkSheetRange *range,
     psppire_axis_start_pixel (sheet->vaxis, range->row0) +
     psppire_axis_unit_size (sheet->vaxis, range->rowi);
 
+  if ( sheet->column_titles_visible)
+    {
+      r->y += sheet->column_title_area.height;
+    }
+
+  if ( sheet->row_titles_visible)
+    {
+      r->x += sheet->row_title_area.width;
+    }
+
   return TRUE;
 }
 
@@ -421,7 +441,7 @@ static void gtk_sheet_forall                         (GtkContainer *container,
                                                  GtkCallback callback,
                                                  gpointer callback_data);
 
-static void gtk_sheet_set_scroll_adjustments    (GtkSheet *sheet,
+static gboolean gtk_sheet_set_scroll_adjustments  (GtkSheet *sheet,
                                                  GtkAdjustment *hadjustment,
                                                  GtkAdjustment *vadjustment);
 
@@ -526,11 +546,6 @@ static void gtk_sheet_real_cell_clear               (GtkSheet *sheet,
                                                  gint column);
 
 
-static void gtk_sheet_row_size_request (GtkSheet *sheet,
-                                       gint row,
-                                       guint *requisition);
-
-
 /* Signals */
 enum
   {
@@ -668,6 +683,21 @@ enum
     PROP_MODEL
   };
 
+static void
+resize_column (GtkSheet *sheet, gint unit, glong size)
+{
+  GtkSheetRange range;
+  range.col0 = unit;
+  range.coli = max_visible_column (sheet);
+  range.row0 = min_visible_row (sheet);
+  range.rowi = max_visible_row (sheet);
+
+  redraw_range (sheet, &range);
+
+  draw_column_title_buttons_range (sheet, range.col0, range.coli);
+}
+
+
 static void
 gtk_sheet_set_horizontal_axis (GtkSheet *sheet, PsppireAxis *a)
 {
@@ -675,11 +705,26 @@ gtk_sheet_set_horizontal_axis (GtkSheet *sheet, PsppireAxis *a)
     g_object_unref (sheet->haxis);
 
   sheet->haxis = a;
+  g_signal_connect_swapped (a, "resize-unit", G_CALLBACK (resize_column), sheet);
 
   if ( sheet->haxis )
     g_object_ref (sheet->haxis);
 }
 
+static void
+resize_row (GtkSheet *sheet, gint unit, glong size)
+{
+  GtkSheetRange range;
+  range.col0 = min_visible_column (sheet);
+  range.coli = max_visible_column (sheet);
+  range.row0 = unit;
+  range.rowi = max_visible_row (sheet);
+
+  redraw_range (sheet, &range);
+
+  draw_row_title_buttons_range (sheet, range.row0, range.rowi);
+}
+
 static void
 gtk_sheet_set_vertical_axis (GtkSheet *sheet, PsppireAxis *a)
 {
@@ -688,6 +733,8 @@ gtk_sheet_set_vertical_axis (GtkSheet *sheet, PsppireAxis *a)
 
   sheet->vaxis = a;
 
+  g_signal_connect_swapped (a, "resize-unit", G_CALLBACK (resize_row), sheet);
+
   if ( sheet->vaxis )
     g_object_ref (sheet->vaxis);
 }
@@ -1096,7 +1143,7 @@ static void
 redraw_range (GtkSheet *sheet, GtkSheetRange *range)
 {
   GdkRectangle rect;
+
   if ( ! GTK_WIDGET_REALIZED (sheet))
     return;
 
@@ -1106,6 +1153,18 @@ redraw_range (GtkSheet *sheet, GtkSheetRange *range)
     {
       GdkRegion *r = gdk_drawable_get_visible_region (sheet->sheet_window);
       gdk_region_get_clipbox (r, &rect);
+
+      if ( sheet->column_titles_visible)
+       {
+         rect.y += sheet->column_title_area.height;
+         rect.height -= sheet->column_title_area.height;
+       }
+
+      if ( sheet->row_titles_visible)
+       {
+         rect.x += sheet->row_title_area.width;
+         rect.width -= sheet->row_title_area.width;
+       }
     }
 
   gdk_window_invalidate_rect (sheet->sheet_window, &rect, FALSE);
@@ -1114,14 +1173,14 @@ redraw_range (GtkSheet *sheet, GtkSheetRange *range)
 
 /* Callback which occurs whenever columns are inserted / deleted in the model */
 static void
-columns_inserted_deleted_callback (GSheetModel *model, gint first_column,
+columns_inserted_deleted_callback (PsppireSheetModel *model, gint first_column,
                                   gint n_columns,
                                   gpointer data)
 {
   GtkSheet *sheet = GTK_SHEET (data);
 
   GtkSheetRange range;
-  gint model_columns = g_sheet_model_get_column_count (model);
+  gint model_columns = psppire_sheet_model_get_column_count (model);
 
 
   /* Need to update all the columns starting from the first column and onwards.
@@ -1149,14 +1208,14 @@ columns_inserted_deleted_callback (GSheetModel *model, gint first_column,
 
 /* Callback which occurs whenever rows are inserted / deleted in the model */
 static void
-rows_inserted_deleted_callback (GSheetModel *model, gint first_row,
+rows_inserted_deleted_callback (PsppireSheetModel *model, gint first_row,
                                gint n_rows, gpointer data)
 {
   GtkSheet *sheet = GTK_SHEET (data);
 
   GtkSheetRange range;
 
-  gint model_rows = g_sheet_model_get_row_count (model);
+  gint model_rows = psppire_sheet_model_get_row_count (model);
 
   /* Need to update all the rows starting from the first row and onwards.
    * Previous rows are unchanged, so don't need to be updated.
@@ -1181,7 +1240,7 @@ rows_inserted_deleted_callback (GSheetModel *model, gint first_row,
   If col0 or coli are negative, then all columns will be updated.
 */
 static void
-range_update_callback (GSheetModel *m, gint row0, gint col0,
+range_update_callback (PsppireSheetModel *m, gint row0, gint col0,
                       gint rowi, gint coli, gpointer data)
 {
   GtkSheet *sheet = GTK_SHEET (data);
@@ -1236,7 +1295,7 @@ range_update_callback (GSheetModel *m, gint row0, gint col0,
  * Returns: the new sheet widget
  */
 GtkWidget *
-gtk_sheet_new (GSheetModel *model)
+gtk_sheet_new (PsppireSheetModel *model)
 {
   GtkWidget *widget = g_object_new (GTK_TYPE_SHEET,
                                    "model", model,
@@ -1254,7 +1313,7 @@ gtk_sheet_new (GSheetModel *model)
  *
  */
 void
-gtk_sheet_set_model (GtkSheet *sheet, GSheetModel *model)
+gtk_sheet_set_model (GtkSheet *sheet, PsppireSheetModel *model)
 {
   g_return_if_fail (GTK_IS_SHEET (sheet));
 
@@ -1367,7 +1426,11 @@ gtk_sheet_show_column_titles (GtkSheet *sheet)
   if (sheet->vadjustment)
     g_signal_emit_by_name (sheet->vadjustment,
                           "value_changed");
+
   size_allocate_global_button (sheet);
+
+  if ( sheet->row_titles_visible)
+    gtk_widget_show (sheet->button);
 }
 
 
@@ -1394,7 +1457,11 @@ gtk_sheet_show_row_titles (GtkSheet *sheet)
   if (sheet->hadjustment)
     g_signal_emit_by_name (sheet->hadjustment,
                           "value_changed");
+
   size_allocate_global_button (sheet);
+
+  if ( sheet->column_titles_visible)
+    gtk_widget_show (sheet->button);
 }
 
 void
@@ -1408,8 +1475,8 @@ gtk_sheet_hide_column_titles (GtkSheet *sheet)
     {
       if (sheet->column_title_window)
        gdk_window_hide (sheet->column_title_window);
-      if (GTK_WIDGET_VISIBLE (sheet->button))
-       gtk_widget_hide (sheet->button);
+
+      gtk_widget_hide (sheet->button);
 
       adjust_scrollbars (sheet);
     }
@@ -1431,8 +1498,7 @@ gtk_sheet_hide_row_titles (GtkSheet *sheet)
       if (sheet->row_title_window)
        gdk_window_hide (sheet->row_title_window);
 
-      if (GTK_WIDGET_VISIBLE (sheet->button))
-       gtk_widget_hide (sheet->button);
+      gtk_widget_hide (sheet->button);
 
       adjust_scrollbars (sheet);
     }
@@ -1474,19 +1540,19 @@ gtk_sheet_moveto (GtkSheet *sheet,
 
 
   if (row >= 0)
-  {
-    gint y =  psppire_axis_start_pixel (sheet->vaxis, row);
+    {
+      gint y =  psppire_axis_start_pixel (sheet->vaxis, row);
 
-    gtk_adjustment_set_value (sheet->vadjustment, y - height * row_align);
-  }
+      gtk_adjustment_set_value (sheet->vadjustment, y - height * row_align);
+    }
 
 
   if (col >= 0)
-  {
-    gint x =  psppire_axis_start_pixel (sheet->haxis, col);
+    {
+      gint x =  psppire_axis_start_pixel (sheet->haxis, col);
 
-    gtk_adjustment_set_value (sheet->hadjustment, x - width * col_align);
-  }
+      gtk_adjustment_set_value (sheet->hadjustment, x - width * col_align);
+    }
 }
 
 
@@ -1508,7 +1574,6 @@ gtk_sheet_select_row (GtkSheet *sheet, gint row)
   sheet->range.rowi = row;
   sheet->range.coli = psppire_axis_unit_count (sheet->haxis) - 1;
   sheet->active_cell.row = row;
-  sheet->active_cell.col = 0;
 
   g_signal_emit (sheet, sheet_signals[SELECT_ROW], 0, row);
   gtk_sheet_real_select_range (sheet, NULL);
@@ -1532,7 +1597,6 @@ gtk_sheet_select_column (GtkSheet *sheet, gint column)
   sheet->range.col0 = column;
   sheet->range.rowi = psppire_axis_unit_count (sheet->vaxis) - 1;
   sheet->range.coli = column;
-  sheet->active_cell.row = 0;
   sheet->active_cell.col = column;
 
   g_signal_emit (sheet, sheet_signals[SELECT_COLUMN], 0, column);
@@ -1603,7 +1667,7 @@ gtk_sheet_get_visible_range (GtkSheet *sheet, GtkSheetRange *range)
 }
 
 
-static void
+static gboolean
 gtk_sheet_set_scroll_adjustments (GtkSheet *sheet,
                                  GtkAdjustment *hadjustment,
                                  GtkAdjustment *vadjustment)
@@ -1613,24 +1677,34 @@ gtk_sheet_set_scroll_adjustments (GtkSheet *sheet,
       if (sheet->vadjustment)
        g_object_unref (sheet->vadjustment);
       sheet->vadjustment = vadjustment;
-      g_object_ref (vadjustment);
 
-      g_signal_connect (sheet->vadjustment, "value_changed",
-                       G_CALLBACK (vadjustment_value_changed),
-                       sheet);
+      if ( vadjustment)
+       {
+         g_object_ref (vadjustment);
+
+         g_signal_connect (sheet->vadjustment, "value_changed",
+                           G_CALLBACK (vadjustment_value_changed),
+                           sheet);
+       }
     }
 
   if ( sheet->hadjustment != hadjustment )
     {
       if (sheet->hadjustment)
        g_object_unref (sheet->hadjustment);
+
       sheet->hadjustment = hadjustment;
-      g_object_ref (hadjustment);
 
-      g_signal_connect (sheet->hadjustment, "value_changed",
-                       G_CALLBACK (hadjustment_value_changed),
-                       sheet);
+      if ( hadjustment)
+       {
+         g_object_ref (hadjustment);
+
+         g_signal_connect (sheet->hadjustment, "value_changed",
+                           G_CALLBACK (hadjustment_value_changed),
+                           sheet);
+       }
     }
+  return TRUE;
 }
 
 static void
@@ -1736,8 +1810,6 @@ gtk_sheet_realize (GtkWidget *widget)
 
   sheet = GTK_SHEET (widget);
 
-  GTK_WIDGET_SET_FLAGS (widget, GTK_REALIZED);
-
   colormap = gtk_widget_get_colormap (widget);
   display = gtk_widget_get_display (widget);
 
@@ -1858,6 +1930,9 @@ gtk_sheet_realize (GtkWidget *widget)
   draw_column_title_buttons (sheet);
 
   gtk_sheet_update_primary_selection (sheet);
+
+
+  GTK_WIDGET_SET_FLAGS (widget, GTK_REALIZED);
 }
 
 static void
@@ -1865,6 +1940,8 @@ create_global_button (GtkSheet *sheet)
 {
   sheet->button = gtk_button_new_with_label (" ");
 
+  GTK_WIDGET_UNSET_FLAGS(sheet->button, GTK_CAN_FOCUS);
+
   g_object_ref_sink (sheet->button);
 
   g_signal_connect (sheet->button,
@@ -1889,7 +1966,6 @@ size_allocate_global_button (GtkSheet *sheet)
   allocation.height = sheet->column_title_area.height;
 
   gtk_widget_size_allocate (sheet->button, &allocation);
-  gtk_widget_show (sheet->button);
 }
 
 static void
@@ -1967,18 +2043,12 @@ gtk_sheet_map (GtkWidget *widget)
          gtk_widget_map (sheet->entry_widget);
        }
 
-      if (GTK_WIDGET_VISIBLE (sheet->button) &&
-         !GTK_WIDGET_MAPPED (sheet->button))
+      if (!GTK_WIDGET_MAPPED (sheet->button))
        {
          gtk_widget_show (sheet->button);
          gtk_widget_map (sheet->button);
        }
 
-      if (GTK_BIN (sheet->button)->child)
-       if (GTK_WIDGET_VISIBLE (GTK_BIN (sheet->button)->child) &&
-           !GTK_WIDGET_MAPPED (GTK_BIN (sheet->button)->child))
-         gtk_widget_map (GTK_BIN (sheet->button)->child);
-
       redraw_range (sheet, NULL);
       change_active_cell (sheet,
                     sheet->active_cell.row,
@@ -2251,7 +2321,7 @@ gtk_sheet_set_cell (GtkSheet *sheet, gint row, gint col,
                    GtkJustification justification,
                    const gchar *text)
 {
-  GSheetModel *model ;
+  PsppireSheetModel *model ;
   gchar *old_text ;
 
   g_return_if_fail (sheet != NULL);
@@ -2265,16 +2335,16 @@ gtk_sheet_set_cell (GtkSheet *sheet, gint row, gint col,
 
   model = gtk_sheet_get_model (sheet);
 
-  old_text = g_sheet_model_get_string (model, row, col);
+  old_text = psppire_sheet_model_get_string (model, row, col);
 
   if (0 != safe_strcmp (old_text, text))
     {
       g_signal_handler_block    (sheet->model, sheet->update_handler_id);
-      g_sheet_model_set_string (model, text, row, col);
+      psppire_sheet_model_set_string (model, text, row, col);
       g_signal_handler_unblock  (sheet->model, sheet->update_handler_id);
     }
 
-  if ( g_sheet_model_free_strings (model))
+  if ( psppire_sheet_model_free_strings (model))
     g_free (old_text);
 }
 
@@ -2304,13 +2374,13 @@ gtk_sheet_cell_clear (GtkSheet *sheet, gint row, gint column)
 static void
 gtk_sheet_real_cell_clear (GtkSheet *sheet, gint row, gint column)
 {
-  GSheetModel *model = gtk_sheet_get_model (sheet);
+  PsppireSheetModel *model = gtk_sheet_get_model (sheet);
 
   gchar *old_text = gtk_sheet_cell_get_text (sheet, row, column);
 
   if (old_text && strlen (old_text) > 0 )
     {
-      g_sheet_model_datum_clear (model, row, column);
+      psppire_sheet_model_datum_clear (model, row, column);
     }
 
   dispose_string (sheet, old_text);
@@ -2319,7 +2389,7 @@ gtk_sheet_real_cell_clear (GtkSheet *sheet, gint row, gint column)
 gchar *
 gtk_sheet_cell_get_text (const GtkSheet *sheet, gint row, gint col)
 {
-  GSheetModel *model;
+  PsppireSheetModel *model;
   g_return_val_if_fail (sheet != NULL, NULL);
   g_return_val_if_fail (GTK_IS_SHEET (sheet), NULL);
 
@@ -2332,7 +2402,7 @@ gtk_sheet_cell_get_text (const GtkSheet *sheet, gint row, gint col)
   if ( !model )
     return NULL;
 
-  return g_sheet_model_get_string (model, row, col);
+  return psppire_sheet_model_get_string (model, row, col);
 }
 
 
@@ -2474,9 +2544,6 @@ gtk_sheet_set_active_cell (GtkSheet *sheet, gint row, gint col)
       col >= psppire_axis_unit_count (sheet->haxis))
     return;
 
-  sheet->active_cell.row = row;
-  sheet->active_cell.col = col;
-
   if (!GTK_WIDGET_REALIZED (GTK_WIDGET (sheet)))
     return;
 
@@ -2652,7 +2719,7 @@ gtk_sheet_show_entry_widget (GtkSheet *sheet)
   gtk_sheet_size_allocate_entry (sheet);
 
   gtk_widget_set_sensitive (GTK_WIDGET (sheet_entry),
-                           g_sheet_model_is_editable (sheet->model,
+                           psppire_sheet_model_is_editable (sheet->model,
                                                       row, col));
   gtk_widget_map (sheet->entry_widget);
 }
@@ -3153,7 +3220,7 @@ gtk_sheet_button_press (GtkWidget *widget,
                     sheet_signals[BUTTON_EVENT_COLUMN], 0,
                     column, event);
 
-      if (g_sheet_model_get_column_sensitivity (sheet->model, column))
+      if (psppire_sheet_model_get_column_sensitivity (sheet->model, column))
        {
          if ( event->type == GDK_2BUTTON_PRESS && event->button == 1)
            g_signal_emit (sheet,
@@ -3166,7 +3233,7 @@ gtk_sheet_button_press (GtkWidget *widget,
                     sheet_signals[BUTTON_EVENT_ROW], 0,
                     row, event);
 
-      if (g_sheet_model_get_row_sensitivity (sheet->model, row))
+      if (psppire_sheet_model_get_row_sensitivity (sheet->model, row))
        {
          if ( event->type == GDK_2BUTTON_PRESS && event->button == 1)
            g_signal_emit (sheet,
@@ -3302,7 +3369,7 @@ gtk_sheet_button_press (GtkWidget *widget,
 
       column = column_from_xpixel (sheet, x);
 
-      if (g_sheet_model_get_column_sensitivity (sheet->model, column))
+      if (psppire_sheet_model_get_column_sensitivity (sheet->model, column))
        {
          veto = gtk_sheet_click_cell (sheet, -1, column);
          gtk_grab_add (GTK_WIDGET (sheet));
@@ -3319,7 +3386,7 @@ gtk_sheet_button_press (GtkWidget *widget,
       y += sheet->vadjustment->value;
 
       row = row_from_ypixel (sheet, y);
-      if (g_sheet_model_get_row_sensitivity (sheet->model, row))
+      if (psppire_sheet_model_get_row_sensitivity (sheet->model, row))
        {
          veto = gtk_sheet_click_cell (sheet, row, -1);
          gtk_grab_add (GTK_WIDGET (sheet));
@@ -3654,17 +3721,17 @@ motion_timeout_callback (gpointer data)
 
   if ( gtk_sheet_get_pixel_info (sheet, x, y, &row, &column) )
     {
-      if (sheet->row_title_under)
+      if (sheet->row_title_under && row >= 0)
        {
-         gchar *text = g_sheet_model_get_row_subtitle (sheet->model, row);
+         gchar *text = psppire_sheet_model_get_row_subtitle (sheet->model, row);
 
          show_subtitle (sheet, row, -1, text);
          g_free (text);
        }
 
-      if (sheet->column_title_under)
+      if (sheet->column_title_under && column >= 0)
        {
-         gchar *text = g_sheet_model_get_column_subtitle (sheet->model,
+         gchar *text = psppire_sheet_model_get_column_subtitle (sheet->model,
                                                           column);
 
          show_subtitle (sheet, -1, column, text);
@@ -4318,7 +4385,6 @@ gtk_sheet_size_allocate (GtkWidget *widget,
   if (sheet->column_titles_visible)
     sheet->row_title_area.y += sheet->column_title_area.height;
 
-
   if (GTK_WIDGET_REALIZED (widget) && sheet->column_titles_visible)
     gdk_window_move_resize (sheet->column_title_window,
                            sheet->column_title_area.x,
@@ -4334,6 +4400,8 @@ gtk_sheet_size_allocate (GtkWidget *widget,
                            sheet->row_title_area.width,
                            sheet->row_title_area.height);
 
+  size_allocate_global_button (sheet);
+
   if (sheet->haxis)
     {
       gint width = sheet->column_title_area.width;
@@ -4401,8 +4469,6 @@ draw_column_title_buttons (GtkSheet *sheet)
 
   if (!GTK_WIDGET_DRAWABLE (sheet)) return;
 
-  size_allocate_global_button (sheet);
-
   draw_column_title_buttons_range (sheet, min_visible_column (sheet), 
                                   max_visible_column (sheet));
 }
@@ -4443,9 +4509,6 @@ draw_row_title_buttons (GtkSheet *sheet)
 
   if (!GTK_WIDGET_DRAWABLE (sheet)) return;
 
-  size_allocate_global_button (sheet);
-
-
   draw_row_title_buttons_range (sheet, min_visible_row (sheet),
                                max_visible_row (sheet));
 }
@@ -4609,6 +4672,8 @@ draw_button (GtkSheet *sheet, GdkWindow *window,
                         allocation.x, allocation.y,
                         allocation.width, allocation.height);
 
+  gtk_widget_ensure_style (sheet->button);
+
   gtk_paint_box (sheet->button->style, window,
                 GTK_STATE_NORMAL, GTK_SHADOW_OUT,
                 &allocation, GTK_WIDGET (sheet->button),
@@ -4728,7 +4793,7 @@ draw_column_title_buttons_range (GtkSheet *sheet, gint first, gint last)
       gboolean is_sensitive = FALSE;
 
       GtkSheetButton *
-       button = g_sheet_model_get_column_button (sheet->model, col);
+       button = psppire_sheet_model_get_column_button (sheet->model, col);
       allocation.y = 0;
       allocation.x = psppire_axis_start_pixel (sheet->haxis, col)
        + CELL_SPACING;
@@ -4736,7 +4801,7 @@ draw_column_title_buttons_range (GtkSheet *sheet, gint first, gint last)
 
       allocation.height = sheet->column_title_area.height;
       allocation.width = psppire_axis_unit_size (sheet->haxis, col);
-      is_sensitive = g_sheet_model_get_column_sensitivity (sheet->model, col);
+      is_sensitive = psppire_sheet_model_get_column_sensitivity (sheet->model, col);
 
       draw_button (sheet, sheet->column_title_window,
                   button, is_sensitive, allocation);
@@ -4777,7 +4842,7 @@ draw_row_title_buttons_range (GtkSheet *sheet, gint first, gint last)
       gboolean is_sensitive = FALSE;
 
       GtkSheetButton *button =
-       g_sheet_model_get_row_button (sheet->model, row);
+       psppire_sheet_model_get_row_button (sheet->model, row);
       allocation.x = 0;
       allocation.y = psppire_axis_start_pixel (sheet->vaxis, row)
        + CELL_SPACING;
@@ -4785,7 +4850,7 @@ draw_row_title_buttons_range (GtkSheet *sheet, gint first, gint last)
 
       allocation.width = sheet->row_title_area.width;
       allocation.height = psppire_axis_unit_size (sheet->vaxis, row);
-      is_sensitive = g_sheet_model_get_row_sensitivity (sheet->model, row);
+      is_sensitive = psppire_sheet_model_get_row_sensitivity (sheet->model, row);
 
       draw_button (sheet, sheet->row_title_window,
                   button, is_sensitive, allocation);
@@ -4884,6 +4949,24 @@ adjust_scrollbars (GtkSheet *sheet)
     }
 }
 
+/* Subtracts the region of WIDGET from REGION */
+static void
+subtract_widget_region (GdkRegion *region, GtkWidget *widget)
+{
+  GdkRectangle rect;
+  GdkRectangle intersect;
+  GdkRegion *region2;
+
+  gdk_region_get_clipbox (region, &rect);
+  gtk_widget_intersect (widget,
+                       &rect,
+                       &intersect);
+
+  region2 = gdk_region_rectangle (&intersect);
+  gdk_region_subtract (region, region2);
+  gdk_region_destroy (region2);
+}
+
 static void
 vadjustment_value_changed (GtkAdjustment *adjustment,
                           gpointer data)
@@ -4900,12 +4983,12 @@ vadjustment_value_changed (GtkAdjustment *adjustment,
   region =
     gdk_drawable_get_visible_region (GDK_DRAWABLE (sheet->sheet_window));
 
+  subtract_widget_region (region, sheet->button);
   gdk_window_begin_paint_region (sheet->sheet_window, region);
 
   draw_sheet_region (sheet, region);
 
   draw_row_title_buttons (sheet);
-  //  size_allocate_global_button (sheet);
   gtk_sheet_draw_active_cell (sheet);
 
   gdk_window_end_paint (sheet->sheet_window);
@@ -4930,12 +5013,12 @@ hadjustment_value_changed (GtkAdjustment *adjustment,
   region =
     gdk_drawable_get_visible_region (GDK_DRAWABLE (sheet->sheet_window));
 
+  subtract_widget_region (region, sheet->button);
   gdk_window_begin_paint_region (sheet->sheet_window, region);
 
   draw_sheet_region (sheet, region);
 
   draw_column_title_buttons (sheet);
-  //  size_allocate_global_button (sheet);
 
   gtk_sheet_draw_active_cell (sheet);
 
@@ -5056,6 +5139,9 @@ set_column_width (GtkSheet *sheet,
   if (column < 0 || column >= psppire_axis_unit_count (sheet->haxis))
     return;
 
+  if ( width <= 0)
+    return;
+
   psppire_axis_resize (sheet->haxis, column, width);
 
   if (GTK_WIDGET_REALIZED (GTK_WIDGET (sheet)))
@@ -5078,6 +5164,9 @@ set_row_height (GtkSheet *sheet,
   if (row < 0 || row >= psppire_axis_unit_count (sheet->vaxis))
     return;
 
+  if (height <= 0)
+    return;
+
   psppire_axis_resize (sheet->vaxis, row, height);
 
   if (GTK_WIDGET_REALIZED (GTK_WIDGET (sheet)) )
@@ -5112,17 +5201,17 @@ gtk_sheet_get_attributes (const GtkSheet *sheet, gint row, gint col,
   attr->border.mask = 0;
   attr->border.color = GTK_WIDGET (sheet)->style->black;
 
-  attr->is_editable = g_sheet_model_is_editable (sheet->model, row, col);
+  attr->is_editable = psppire_sheet_model_is_editable (sheet->model, row, col);
 
   colormap = gtk_widget_get_colormap (GTK_WIDGET (sheet));
-  fg = g_sheet_model_get_foreground (sheet->model, row, col);
+  fg = psppire_sheet_model_get_foreground (sheet->model, row, col);
   if ( fg )
     {
       gdk_colormap_alloc_color (colormap, fg, TRUE, TRUE);
       attr->foreground = *fg;
     }
 
-  bg = g_sheet_model_get_background (sheet->model, row, col);
+  bg = psppire_sheet_model_get_background (sheet->model, row, col);
   if ( bg )
     {
       gdk_colormap_alloc_color (colormap, bg, TRUE, TRUE);
@@ -5130,9 +5219,9 @@ gtk_sheet_get_attributes (const GtkSheet *sheet, gint row, gint col,
     }
 
   attr->justification =
-    g_sheet_model_get_column_justification (sheet->model, col);
+    psppire_sheet_model_get_column_justification (sheet->model, col);
 
-  j = g_sheet_model_get_justification (sheet->model, row, col);
+  j = psppire_sheet_model_get_justification (sheet->model, row, col);
   if (j)
     attr->justification = *j;
 
@@ -5178,7 +5267,7 @@ gtk_sheet_forall (GtkContainer *container,
 }
 
 
-GSheetModel *
+PsppireSheetModel *
 gtk_sheet_get_model (const GtkSheet *sheet)
 {
   g_return_val_if_fail (GTK_IS_SHEET (sheet), NULL);