X-Git-Url: https://pintos-os.org/cgi-bin/gitweb.cgi?a=blobdiff_plain;f=src%2Fui%2Fgui%2Fpspp-sheet-view-column.c;h=a11acf7e3565a67d3e9a733815df002ccd012864;hb=20f28c180d171a2f0e707c274b249d90f8d903e0;hp=88a624dd448915d4a6ea6bb440eaf7353d6a745c;hpb=3bc8bee4dbb8a204fb61b0dfe97c4468899dd1c3;p=pspp diff --git a/src/ui/gui/pspp-sheet-view-column.c b/src/ui/gui/pspp-sheet-view-column.c index 88a624dd44..a11acf7e35 100644 --- a/src/ui/gui/pspp-sheet-view-column.c +++ b/src/ui/gui/pspp-sheet-view-column.c @@ -44,6 +44,7 @@ #include "ui/gui/psppire-marshal.h" #include "ui/gui/pspp-sheet-selection.h" +#include "ui/gui/pspp-widget-facade.h" #define P_(STRING) STRING #define GTK_PARAM_READABLE G_PARAM_READABLE|G_PARAM_STATIC_NAME|G_PARAM_STATIC_NICK|G_PARAM_STATIC_BLURB @@ -71,7 +72,8 @@ enum PROP_QUICK_EDIT, PROP_SELECTED, PROP_SELECTABLE, - PROP_ROW_HEAD + PROP_ROW_HEAD, + PROP_TABBABLE }; enum @@ -139,7 +141,7 @@ static GList *pspp_sheet_view_column_cell_layout_get_cells (GtkCellLayout /* Button handling code */ static void pspp_sheet_view_column_create_button (PsppSheetViewColumn *tree_column); -static void pspp_sheet_view_column_update_button (PsppSheetViewColumn *tree_column); +void pspp_sheet_view_column_update_button (PsppSheetViewColumn *tree_column); /* Button signal handlers */ static gint pspp_sheet_view_column_button_event (GtkWidget *widget, @@ -425,6 +427,14 @@ pspp_sheet_view_column_class_init (PsppSheetViewColumnClass *class) P_("If true, this column is a \"row head\", equivalent to a column head. If rectangular selection is enabled, then shift+click and control+click in the column select row ranges and toggle row selection, respectively. The column should ordinarily include a button cell; clicking on the button will select the row (and deselect all other rows)."), FALSE, GTK_PARAM_READWRITE)); + + g_object_class_install_property (object_class, + PROP_TABBABLE, + g_param_spec_boolean ("tabbable", + P_("Tabbable"), + P_("If true, Tab and Shift+Tab visit this column. If false, Tab and Shift+Tab skip this column."), + TRUE, + GTK_PARAM_READWRITE)); } static void @@ -467,6 +477,7 @@ pspp_sheet_view_column_init (PsppSheetViewColumn *tree_column) tree_column->selected = FALSE; tree_column->selectable = TRUE; tree_column->row_head = FALSE; + tree_column->tabbable = TRUE; tree_column->sort_order = GTK_SORT_ASCENDING; tree_column->show_sort_indicator = FALSE; tree_column->property_changed_signal = 0; @@ -479,6 +490,7 @@ pspp_sheet_view_column_init (PsppSheetViewColumn *tree_column) tree_column->use_resized_width = FALSE; tree_column->title = g_strdup (""); tree_column->quick_edit = TRUE; + tree_column->need_button = FALSE; } static void @@ -619,6 +631,11 @@ pspp_sheet_view_column_set_property (GObject *object, g_value_get_boolean (value)); break; + case PROP_TABBABLE: + pspp_sheet_view_column_set_tabbable (tree_column, + g_value_get_boolean (value)); + break; + default: G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); break; @@ -737,6 +754,11 @@ pspp_sheet_view_column_get_property (GObject *object, pspp_sheet_view_column_get_row_head (tree_column)); break; + case PROP_TABBABLE: + g_value_set_boolean (value, + pspp_sheet_view_column_get_tabbable (tree_column)); + break; + default: G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); break; @@ -1035,7 +1057,7 @@ pspp_sheet_view_column_create_button (PsppSheetViewColumn *tree_column) pspp_sheet_view_column_update_button (tree_column); } -static void +void pspp_sheet_view_column_update_button (PsppSheetViewColumn *tree_column) { gint sort_column_id = -1; @@ -1045,6 +1067,7 @@ pspp_sheet_view_column_update_button (PsppSheetViewColumn *tree_column) GtkWidget *current_child; GtkArrowType arrow_type = GTK_ARROW_NONE; GtkTreeModel *model; + gboolean can_focus; if (tree_column->tree_view) model = pspp_sheet_view_get_model (PSPP_SHEET_VIEW (tree_column->tree_view)); @@ -1052,7 +1075,8 @@ pspp_sheet_view_column_update_button (PsppSheetViewColumn *tree_column) model = NULL; /* Create a button if necessary */ - if (tree_column->visible && + if (tree_column->need_button && + tree_column->visible && tree_column->button == NULL && tree_column->tree_view && gtk_widget_get_realized (tree_column->tree_view)) @@ -1061,10 +1085,10 @@ pspp_sheet_view_column_update_button (PsppSheetViewColumn *tree_column) if (! tree_column->button) return; - hbox = GTK_BIN (tree_column->button)->child; + hbox = gtk_bin_get_child (GTK_BIN (tree_column->button)); alignment = tree_column->alignment; arrow = tree_column->arrow; - current_child = GTK_BIN (alignment)->child; + current_child = gtk_bin_get_child (GTK_BIN (alignment)); /* Set up the actual button */ gtk_alignment_set (GTK_ALIGNMENT (alignment), tree_column->xalign, @@ -1187,23 +1211,18 @@ pspp_sheet_view_column_update_button (PsppSheetViewColumn *tree_column) gdk_window_hide (tree_column->window); } } - - if (tree_column->reorderable || tree_column->clickable) - { - gtk_widget_set_can_focus (tree_column->button, TRUE); - } - else + + can_focus = pspp_sheet_view_column_can_focus (tree_column); + gtk_widget_set_can_focus (tree_column->button, can_focus); + if (!can_focus && gtk_widget_has_focus (tree_column->button)) { - gtk_widget_set_can_focus (tree_column->button, FALSE); - if (gtk_widget_has_focus (tree_column->button)) - { - GtkWidget *toplevel = gtk_widget_get_toplevel (tree_column->tree_view); - if (gtk_widget_is_toplevel (toplevel)) - { - gtk_window_set_focus (GTK_WINDOW (toplevel), NULL); - } - } + GtkWidget *toplevel = gtk_widget_get_toplevel (tree_column->tree_view); + if (gtk_widget_is_toplevel (toplevel)) + { + gtk_window_set_focus (GTK_WINDOW (toplevel), NULL); + } } + /* Queue a resize on the assumption that we always want to catch all changes * and columns don't change all that often. */ @@ -1367,8 +1386,13 @@ on_pspp_sheet_view_column_button_clicked (PsppSheetViewColumn *column) if (pspp_sheet_selection_get_mode (selection) == PSPP_SHEET_SELECTION_RECTANGLE) { pspp_sheet_selection_select_all (selection); - pspp_sheet_selection_unselect_all_columns (selection); - pspp_sheet_selection_select_column (selection, column); + if (pspp_sheet_view_column_get_row_head (column)) + pspp_sheet_selection_select_all_columns (selection); + else + { + pspp_sheet_selection_unselect_all_columns (selection); + pspp_sheet_selection_select_column (selection, column); + } sheet_view->priv->anchor_column = column; return TRUE; } @@ -1539,6 +1563,9 @@ _pspp_sheet_view_column_realize_button (PsppSheetViewColumn *column) g_return_if_fail (PSPP_IS_SHEET_VIEW (tree_view)); g_return_if_fail (gtk_widget_get_realized (GTK_WIDGET (tree_view))); g_return_if_fail (tree_view->priv->header_window != NULL); + if (!column->need_button || !column->button) + return; + g_return_if_fail (column->button != NULL); gtk_widget_set_parent_window (column->button, tree_view->priv->header_window); @@ -1557,7 +1584,7 @@ _pspp_sheet_view_column_realize_button (PsppSheetViewColumn *column) GDK_POINTER_MOTION_HINT_MASK | GDK_KEY_PRESS_MASK); attributes_mask = GDK_WA_CURSOR | GDK_WA_X | GDK_WA_Y; - attr.cursor = gdk_cursor_new_for_display (gdk_drawable_get_display (tree_view->priv->header_window), + attr.cursor = gdk_cursor_new_for_display (gdk_window_get_display (tree_view->priv->header_window), GDK_SB_H_DOUBLE_ARROW); attr.y = 0; attr.width = TREE_VIEW_DRAG_WIDTH; @@ -1577,11 +1604,12 @@ void _pspp_sheet_view_column_unrealize_button (PsppSheetViewColumn *column) { g_return_if_fail (column != NULL); - g_return_if_fail (column->window != NULL); - - gdk_window_set_user_data (column->window, NULL); - gdk_window_destroy (column->window); - column->window = NULL; + if (column->window != NULL) + { + gdk_window_set_user_data (column->window, NULL); + gdk_window_destroy (column->window); + column->window = NULL; + } } void @@ -1604,7 +1632,8 @@ _pspp_sheet_view_column_set_tree_view (PsppSheetViewColumn *column, g_assert (column->tree_view == NULL); column->tree_view = GTK_WIDGET (tree_view); - pspp_sheet_view_column_create_button (column); + if (column->need_button) + pspp_sheet_view_column_create_button (column); column->property_changed_signal = g_signal_connect_swapped (tree_view, @@ -2334,7 +2363,7 @@ pspp_sheet_view_column_set_title (PsppSheetViewColumn *tree_column, * Return value: the title of the column. This string should not be * modified or freed. **/ -G_CONST_RETURN gchar * +const gchar * pspp_sheet_view_column_get_title (PsppSheetViewColumn *tree_column) { g_return_val_if_fail (PSPP_IS_SHEET_VIEW_COLUMN (tree_column), NULL); @@ -2360,7 +2389,7 @@ pspp_sheet_view_column_set_expand (PsppSheetViewColumn *tree_column, { g_return_if_fail (PSPP_IS_SHEET_VIEW_COLUMN (tree_column)); - expand = expand?TRUE:FALSE; + expand = !!expand; if (tree_column->expand == expand) return; tree_column->expand = expand; @@ -2541,10 +2570,11 @@ pspp_sheet_view_column_set_reorderable (PsppSheetViewColumn *tree_column, /* if (reorderable) pspp_sheet_view_column_set_clickable (tree_column, TRUE);*/ - if (tree_column->reorderable == (reorderable?TRUE:FALSE)) + reorderable = !!reorderable; + if (tree_column->reorderable == reorderable) return; - tree_column->reorderable = (reorderable?TRUE:FALSE); + tree_column->reorderable = reorderable; pspp_sheet_view_column_update_button (tree_column); g_object_notify (G_OBJECT (tree_column), "reorderable"); } @@ -2581,7 +2611,7 @@ pspp_sheet_view_column_set_quick_edit (PsppSheetViewColumn *tree_column, quick_edit = !!quick_edit; if (tree_column->quick_edit != quick_edit) { - tree_column->quick_edit = (quick_edit?TRUE:FALSE); + tree_column->quick_edit = quick_edit; g_object_notify (G_OBJECT (tree_column), "quick-edit"); } } @@ -2625,7 +2655,7 @@ pspp_sheet_view_column_set_selected (PsppSheetViewColumn *tree_column, if (tree_column->tree_view != NULL) gtk_widget_queue_draw (GTK_WIDGET (tree_column->tree_view)); - tree_column->selected = (selected?TRUE:FALSE); + tree_column->selected = selected; g_object_notify (G_OBJECT (tree_column), "selected"); sheet_view = PSPP_SHEET_VIEW (pspp_sheet_view_column_get_tree_view ( @@ -2670,7 +2700,7 @@ pspp_sheet_view_column_set_selectable (PsppSheetViewColumn *tree_column, { if (tree_column->tree_view != NULL) gtk_widget_queue_draw (GTK_WIDGET (tree_column->tree_view)); - tree_column->selectable = (selectable?TRUE:FALSE); + tree_column->selectable = selectable; g_object_notify (G_OBJECT (tree_column), "selectable"); } } @@ -2709,7 +2739,7 @@ pspp_sheet_view_column_set_row_head (PsppSheetViewColumn *tree_column, row_head = !!row_head; if (tree_column->row_head != row_head) { - tree_column->row_head = (row_head?TRUE:FALSE); + tree_column->row_head = row_head; g_object_notify (G_OBJECT (tree_column), "row_head"); } } @@ -2731,6 +2761,44 @@ pspp_sheet_view_column_get_row_head (PsppSheetViewColumn *tree_column) } +/** + * pspp_sheet_view_column_set_tabbable: + * @tree_column: A #PsppSheetViewColumn + * @tabbable: If true, the column is "tabbable", meaning that Tab and Shift+Tab + * in the sheet visit this column. If false, Tab and Shift+Tab skip this + * column. + **/ +void +pspp_sheet_view_column_set_tabbable (PsppSheetViewColumn *tree_column, + gboolean tabbable) +{ + g_return_if_fail (PSPP_IS_SHEET_VIEW_COLUMN (tree_column)); + + tabbable = !!tabbable; + if (tree_column->tabbable != tabbable) + { + tree_column->tabbable = tabbable; + g_object_notify (G_OBJECT (tree_column), "tabbable"); + } +} + +/** + * pspp_sheet_view_column_get_tabbable: + * @tree_column: A #PsppSheetViewColumn + * + * Returns %TRUE if the column is tabbable. + * + * Return value: %TRUE if the column is tabbable. + **/ +gboolean +pspp_sheet_view_column_get_tabbable (PsppSheetViewColumn *tree_column) +{ + g_return_val_if_fail (PSPP_IS_SHEET_VIEW_COLUMN (tree_column), FALSE); + + return tree_column->tabbable; +} + + /** * pspp_sheet_view_column_set_sort_column_id: * @tree_column: a #PsppSheetViewColumn @@ -4262,3 +4330,64 @@ _gtk_cell_layout_buildable_add_child (GtkBuildable *buildable, g_return_if_fail (iface->pack_start != NULL); iface->pack_start (GTK_CELL_LAYOUT (buildable), GTK_CELL_RENDERER (child), FALSE); } + +void +pspp_sheet_view_column_size_request (PsppSheetViewColumn *tree_column, + GtkRequisition *request) +{ + GtkWidget *base = GTK_WIDGET (tree_column->tree_view); + GtkRequisition label_req; + GtkRequisition align_req; + GtkRequisition arrow_req; + GtkRequisition hbox_req; + GtkStyle **button_style; + + if (tree_column->button) + { + gtk_widget_size_request (tree_column->button, request); + return; + } + + facade_label_get_size_request (0, 0, base, tree_column->title, &label_req); + facade_alignment_get_size_request (0, 0, 0, 0, 0, &label_req, &align_req); + facade_arrow_get_size_request (0, 0, &arrow_req); + + facade_hbox_get_base_size_request (0, 2, 2, &hbox_req); + facade_hbox_add_child_size_request (0, &arrow_req, 0, &hbox_req); + facade_hbox_add_child_size_request (0, &align_req, 0, &hbox_req); + + button_style = &PSPP_SHEET_VIEW (tree_column->tree_view)->priv->button_style; + if (*button_style == NULL) + { + *button_style = facade_get_style (base, GTK_TYPE_BUTTON, 0); + g_object_ref (*button_style); + } + facade_button_get_size_request (0, base, *button_style, &hbox_req, request); +} + +void +pspp_sheet_view_column_size_allocate (PsppSheetViewColumn *tree_column, + GtkAllocation *allocation) +{ + tree_column->allocation = *allocation; + if (tree_column->button) + gtk_widget_size_allocate (tree_column->button, allocation); +} + +gboolean +pspp_sheet_view_column_can_focus (PsppSheetViewColumn *tree_column) +{ + return tree_column->reorderable || tree_column->clickable; +} + +void +pspp_sheet_view_column_set_need_button (PsppSheetViewColumn *tree_column, + gboolean need_button) +{ + if (tree_column->need_button != need_button) + { + tree_column->need_button = need_button; + pspp_sheet_view_column_update_button (tree_column); + _pspp_sheet_view_column_realize_button (tree_column); + } +}