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/>. */
18 /* This file is a rubbish bin where stuff gets put when it doesn't seem to
23 #include "psppire-syntax-window.h"
25 #include <glib-object.h>
29 #include "message-dialog.h"
30 #include <data/format.h>
31 #include <data/data-in.h>
32 #include <data/data-out.h>
33 #include <data/dictionary.h>
34 #include <data/casereader-provider.h>
35 #include <libpspp/message.h>
37 #include <libpspp/i18n.h>
42 #include <data/settings.h>
44 #include <language/command.h>
45 #include <data/lazy-casereader.h>
46 #include <data/procedure.h>
47 #include <language/lexer/lexer.h>
48 #include "psppire-data-store.h"
49 #include <output/manager.h>
50 #include "psppire-output-window.h"
56 /* Formats a value according to FORMAT
57 The returned string must be freed when no longer required */
59 value_to_text (union value v, struct fmt_spec format)
63 s = g_new (gchar, format.w + 1);
64 data_out (&v, &format, s);
74 text_to_value (const gchar *text, union value *v,
75 struct fmt_spec format)
79 if ( format.type != FMT_A)
81 if ( ! text ) return FALSE;
84 const gchar *s = text;
92 if ( !*s) return FALSE;
97 ok = data_in (ss_cstr (text), LEGACY_NATIVE, format.type, 0, 0, 0,
98 v, fmt_var_width (&format));
106 get_widget_assert (GladeXML *xml, const gchar *name)
112 w = glade_xml_get_widget (xml, name);
115 g_critical ("Widget \"%s\" could not be found\n", name);
120 /* Converts a string in the pspp locale to utf-8.
121 The return value must be freed when no longer required*/
123 pspp_locale_to_utf8 (const gchar *text, gssize len, GError **err)
125 return recode_string (CONV_PSPP_TO_UTF8, text, len);
128 #define _(msgid) gettext (msgid)
129 #define N_(msgid) msgid
137 dialog = gtk_message_dialog_new (NULL,
141 _("Sorry. The help system hasn't yet "
142 "been implemented."));
143 gtk_dialog_run (GTK_DIALOG (dialog));
144 gtk_widget_destroy (dialog);
148 connect_help (GladeXML *xml)
150 GList *helps = glade_xml_get_widget_prefix (xml, "help_button_");
153 for ( i = g_list_first (helps); i ; i = g_list_next (i))
154 g_signal_connect (GTK_WIDGET (i->data), "clicked", give_help, 0);
162 reference_manual (GtkMenuItem *menu, gpointer data)
165 if ( ! g_spawn_command_line_async ("yelp info:pspp", &err) )
167 msg (ME, _("Cannot open reference manual: %s"), err->message);
169 g_clear_error (&err);
173 extern struct dataset *the_dataset;
174 extern struct source_stream *the_source_stream;
175 extern PsppireDataStore *the_data_store;
177 /* Lazy casereader callback function used by execute_syntax. */
178 static struct casereader *
179 create_casereader_from_data_store (void *data_store_)
181 PsppireDataStore *data_store = data_store_;
182 return psppire_data_store_get_reader (data_store);
186 execute_syntax (struct getl_interface *sss)
189 gboolean retval = TRUE;
191 struct casereader *reader;
194 unsigned long int lazy_serial;
196 /* When the user executes a number of snippets of syntax in a
197 row, none of which read from the active file, the GUI becomes
198 progressively less responsive. The reason is that each syntax
199 execution encapsulates the active file data in another
200 datasheet layer. The cumulative effect of having a number of
201 layers of datasheets wastes time and space.
203 To solve the problem, we use a "lazy casereader", a wrapper
204 around the casereader obtained from the data store, that
205 only actually instantiates that casereader when it is
206 needed. If the data store casereader is never needed, then
207 it is reused the next time syntax is run, without wrapping
208 it in another layer. */
209 value_cnt = psppire_data_store_get_value_count (the_data_store);
210 case_cnt = psppire_data_store_get_case_count (the_data_store);
211 reader = lazy_casereader_create (value_cnt, case_cnt,
212 create_casereader_from_data_store,
213 the_data_store, &lazy_serial);
214 proc_set_active_file_data (the_dataset, reader);
216 g_return_val_if_fail (proc_has_active_file (the_dataset), FALSE);
218 lexer = lex_create (the_source_stream);
220 getl_append_source (the_source_stream, sss, GETL_BATCH, ERRMODE_CONTINUE);
224 enum cmd_result result = cmd_parse (lexer, the_dataset);
226 if ( cmd_result_is_failure (result))
229 if ( source_stream_current_error_mode (the_source_stream)
234 if ( result == CMD_EOF || result == CMD_FINISH)
238 getl_abort_noninteractive (the_source_stream);
242 psppire_dict_replace_dictionary (the_data_store->dict,
243 dataset_dict (the_dataset));
245 reader = proc_extract_active_file_data (the_dataset);
246 if (!lazy_casereader_destroy (reader, lazy_serial))
247 psppire_data_store_set_reader (the_data_store, reader);
251 psppire_output_window_reload ();
258 /* Create a deep copy of SRC */
260 clone_list_store (const GtkListStore *src)
262 GtkTreeIter src_iter;
265 const gint n_cols = gtk_tree_model_get_n_columns (GTK_TREE_MODEL (src));
266 GType *types = g_malloc (sizeof (*types) * n_cols);
271 for (i = 0 ; i < n_cols; ++i )
272 types[i] = gtk_tree_model_get_column_type (GTK_TREE_MODEL (src), i);
274 dest = gtk_list_store_newv (n_cols, types);
276 for (ok = gtk_tree_model_get_iter_first (GTK_TREE_MODEL (src),
279 ok = gtk_tree_model_iter_next (GTK_TREE_MODEL (src), &src_iter))
281 GtkTreeIter dest_iter;
282 gtk_list_store_append (dest, &dest_iter);
284 for (i = 0 ; i < n_cols; ++i )
288 gtk_tree_model_get_value (GTK_TREE_MODEL (src), &src_iter, i, &val);
289 gtk_list_store_set_value (dest, &dest_iter, i, &val);
291 g_value_unset (&val);
305 paste_syntax_in_new_window (const gchar *syntax)
307 GtkWidget *se = psppire_syntax_window_new ();
309 gtk_text_buffer_insert_at_cursor (PSPPIRE_SYNTAX_WINDOW (se)->buffer, syntax, -1);
311 gtk_widget_show (se);