1 /* PSPPIRE - a graphical user interface for PSPP.
2 Copyright (C) 2007 Free Software Foundation
4 This program is free software: you can redistribute it and/or modify
5 it under the terms of the GNU General Public License as published by
6 the Free Software Foundation, either version 3 of the License, or
7 (at your option) any later version.
9 This program is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 GNU General Public License for more details.
14 You should have received a copy of the GNU General Public License
15 along with this program. If not, see <http://www.gnu.org/licenses/>. */
19 #include <libpspp/i18n.h>
20 #include "dialog-common.h"
22 #include "psppire-var-ptr.h"
27 /* Append the names of selected variables to STRING.
28 TREEVIEW is the treeview containing the variables.
29 COLUMN is the column in the treeview containing the variables.
30 DICT is the dictionary for those variables.
33 append_variable_names (GString *string,
34 PsppireDict *dict, GtkTreeView *treeview, gint column)
39 GtkTreeModel *list_store =
40 gtk_tree_view_get_model (treeview);
42 if ( gtk_tree_model_get_iter_first (list_store, &iter) )
47 struct variable *var = NULL;
48 GtkTreePath *path = gtk_tree_model_get_path (list_store, &iter);
50 gtk_tree_model_get_value (list_store, &iter, column, &value);
52 /* FIXME: G_TYPE_INT should be deprecated.
53 As well as being simpler, it'd be unecessary to pass dict */
54 if ( G_VALUE_TYPE (&value) == G_TYPE_INT )
55 var = psppire_dict_get_variable (dict, g_value_get_int (&value));
57 else if ( G_VALUE_TYPE (&value) == PSPPIRE_VAR_PTR_TYPE)
58 var = g_value_get_boxed (&value);
61 g_critical ("Unsupported type \"%s\", in variable name treeview.",
62 G_VALUE_TYPE_NAME (&value));
64 g_value_unset (&value);
66 g_string_append (string, " ");
67 g_string_append (string, var_get_name (var));
69 gtk_tree_path_free (path);
72 while (gtk_tree_model_iter_next (list_store, &iter));
81 get_selected_variable (GtkTreeModel *treemodel,
88 GtkTreePath *path = gtk_tree_model_get_path (treemodel, iter);
90 gtk_tree_model_get_value (treemodel, iter, 0, &value);
92 gtk_tree_path_free (path);
94 var = psppire_dict_get_variable (dict, g_value_get_int (&value));
96 g_value_unset (&value);
104 /* A (*GtkTreeCellDataFunc) function.
105 This function expects TREEMODEL to hold G_TYPE_INT. The ints it holds
106 are the indices of the variables in the dictionary, which DATA points to.
107 It renders the name of the variable into CELL.
110 cell_var_name (GtkTreeViewColumn *tree_column,
111 GtkCellRenderer *cell,
112 GtkTreeModel *tree_model,
116 PsppireDict *dict = data;
117 struct variable *var;
120 var = get_selected_variable (tree_model, iter, dict);
122 name = recode_string (UTF8, psppire_dict_encoding (dict),
123 var_get_name (var), -1);
124 g_object_set (cell, "text", name, NULL);
130 /* Set a model for DEST, which is an GtkListStore of g_int's
131 whose values are the indices into DICT */
133 set_dest_model (GtkTreeView *dest, PsppireDict *dict)
135 GtkTreeViewColumn *col;
136 GtkListStore *dest_list = gtk_list_store_new (1, G_TYPE_INT);
137 GtkCellRenderer *renderer = gtk_cell_renderer_text_new ();
139 gtk_tree_view_set_model (GTK_TREE_VIEW (dest), GTK_TREE_MODEL (dest_list));
141 col = gtk_tree_view_column_new_with_attributes ("Var",
147 gtk_tree_view_column_set_cell_data_func (col, renderer,
151 /* FIXME: make this a value in terms of character widths */
152 g_object_set (col, "min-width", 100, NULL);
154 gtk_tree_view_column_set_sizing (col, GTK_TREE_VIEW_COLUMN_FIXED);
156 gtk_tree_view_append_column (GTK_TREE_VIEW (dest), col);
161 /* Returns FALSE if the variables represented by the union of the rows
162 currently selected by SOURCE widget, and contents of the DEST
163 widget, are of different types.
165 In other words, this function when passed as the argument to
166 psppire_selector_set_allow, ensures that the selector selects only
167 string variables, or only numeric variables, not a mixture.
170 homogeneous_types (GtkWidget *source, GtkWidget *dest)
174 gboolean retval = TRUE;
176 GtkTreeModel *model = gtk_tree_view_get_model (GTK_TREE_VIEW (source));
179 GtkTreeSelection *selection;
180 enum val_type type = -1;
183 while (GTK_IS_TREE_MODEL_FILTER (model))
185 model = gtk_tree_model_filter_get_model (GTK_TREE_MODEL_FILTER (model));
188 dict = PSPPIRE_DICT (model);
190 selection = gtk_tree_view_get_selection (GTK_TREE_VIEW (source));
192 list = gtk_tree_selection_get_selected_rows (selection, &model);
194 /* Iterate through the selection of the source treeview */
195 for (l = list; l ; l = l->next)
197 GtkTreePath *path = l->data;
200 gtk_tree_model_filter_convert_path_to_child_path (GTK_TREE_MODEL_FILTER (model), path);
202 gint *idx = gtk_tree_path_get_indices (fpath);
204 const struct variable *v = psppire_dict_get_variable (dict, idx[0]);
206 gtk_tree_path_free (fpath);
210 if ( var_get_type (v) != type )
217 type = var_get_type (v);
220 g_list_foreach (list, (GFunc) gtk_tree_path_free, NULL);
223 if ( retval == FALSE )
226 /* now deal with the dest widget */
227 model = gtk_tree_view_get_model (GTK_TREE_VIEW (dest));
229 for (ok = gtk_tree_model_get_iter_first (model, &iter);
231 ok = gtk_tree_model_iter_next (model, &iter))
234 const struct variable *v;
235 gtk_tree_model_get (model, &iter, 0, &idx, -1);
237 v = psppire_dict_get_variable (dict, idx);
241 if ( var_get_type (v) != type )
248 type = var_get_type (v);
257 /* Returns true iff the variable selected by SOURCE is numeric */
259 numeric_only (GtkWidget *source, GtkWidget *dest)
261 gboolean retval = TRUE;
263 GtkTreeModel *model = gtk_tree_view_get_model (GTK_TREE_VIEW (source));
266 GtkTreeSelection *selection;
269 while (GTK_IS_TREE_MODEL_FILTER (model))
271 model = gtk_tree_model_filter_get_model (GTK_TREE_MODEL_FILTER (model));
274 dict = PSPPIRE_DICT (model);
276 selection = gtk_tree_view_get_selection (GTK_TREE_VIEW (source));
278 list = gtk_tree_selection_get_selected_rows (selection, &model);
280 /* Iterate through the selection of the source treeview */
281 for (l = list; l ; l = l->next)
283 GtkTreePath *path = l->data;
284 GtkTreePath *fpath = gtk_tree_model_filter_convert_path_to_child_path
285 (GTK_TREE_MODEL_FILTER (model), path);
287 gint *idx = gtk_tree_path_get_indices (fpath);
289 const struct variable *v = psppire_dict_get_variable (dict, idx[0]);
291 gtk_tree_path_free (fpath);
293 if ( var_is_alpha (v))
300 g_list_foreach (list, (GFunc) gtk_tree_path_free, NULL);