Merge commit 'origin/stable'
[pspp-builds.git] / src / ui / gui / psppire.c
index a7b22037b868e7d523726c8f80faab41ebe1acc8..1cd7ee803c736a740b373a53b035c7dcef6bd90a 100644 (file)
 
 #include <config.h>
 
-#include <locale.h>
+#include <libpspp/i18n.h>
 #include <assert.h>
 #include <libintl.h>
 #include <gsl/gsl_errno.h>
 
+#include <xalloc.h>
+#include <argp.h>
+#include <ui/command-line.h>
 #include "relocatable.h"
 
-#include "data-editor.h"
+#include "psppire-data-window.h"
 #include "psppire.h"
+#include "widgets.h"
 
+#include <libpspp/getl.h>
 #include <unistd.h>
 #include <data/casereader.h>
 #include <data/datasheet.h>
 #include <libpspp/version.h>
 #include <output/output.h>
 #include <output/journal.h>
+#include <language/syntax-string-source.h>
 
 #include <gtk/gtk.h>
-#include <glade/glade.h>
 #include "psppire-dict.h"
 #include "psppire-var-store.h"
 #include "psppire-data-store.h"
-#include "helper.h"
+#include "executor.h"
 #include "message-dialog.h"
+#include <ui/syntax-gen.h>
+
+#include "psppire-window-register.h"
+#include "psppire-output-window.h"
+
+#include <data/sys-file-reader.h>
+#include <data/por-file-reader.h>
 
-#include "output-viewer.h"
+#include <ui/source-init-opts.h>
 
+GtkRecentManager *the_recent_mgr = 0;
 PsppireDataStore *the_data_store = 0;
 PsppireVarStore *the_var_store = 0;
 
@@ -57,32 +70,28 @@ static void create_icon_factory (void);
 struct source_stream *the_source_stream ;
 struct dataset * the_dataset = NULL;
 
+static GtkWidget *the_data_window;
 
 static void
 replace_casereader (struct casereader *s)
 {
-  PsppireCaseFile *pcf = psppire_case_file_new (s);
-
-  psppire_data_store_set_case_file (the_data_store, pcf);
+  psppire_data_store_set_reader (the_data_store, s);
 }
 
 #define _(msgid) gettext (msgid)
 #define N_(msgid) msgid
 
 
+
+
 void
-initialize (void)
+initialize (struct command_line_processor *clp, int argc, char **argv)
 {
   PsppireDict *dictionary = 0;
 
-  /* gtk_init messes with the locale.
-     So unset the bits we want to control ourselves */
-  setlocale (LC_NUMERIC, "C");
-
-  bindtextdomain (PACKAGE, relocate (locale_dir));
-
+  i18n_init ();
 
-  glade_init ();
+  preregister_widgets ();
 
   gsl_set_error_handler_off ();
   fn_init ();
@@ -134,7 +143,19 @@ initialize (void)
   journal_enable ();
   textdomain (PACKAGE);
 
-  new_data_window (NULL, NULL);
+
+  the_recent_mgr = gtk_recent_manager_get_default ();
+
+  the_data_window = psppire_data_window_new ();
+
+  command_line_processor_replace_aux (clp, &post_init_argp, the_source_stream);
+  command_line_processor_replace_aux (clp, &non_option_argp, the_source_stream);
+
+  command_line_processor_parse (clp, argc, argv);
+
+  execute_syntax (create_syntax_string_source (""));
+
+  gtk_widget_show (the_data_window);
 }
 
 
@@ -145,9 +166,28 @@ de_initialize (void)
   message_dialog_done ();
   settings_done ();
   outp_done ();
+  i18n_done ();
 }
 
 
+static void
+func (gpointer key, gpointer value, gpointer data)
+{
+  gboolean rv;
+  PsppireWindow *window = PSPPIRE_WINDOW (value);
+
+  g_signal_emit_by_name (window, "delete-event", 0, &rv);
+}
+
+void
+psppire_quit (void)
+{
+  PsppireWindowRegister *reg = psppire_window_register_new ();
+  psppire_window_register_foreach (reg, func, NULL);
+
+  gtk_main_quit ();
+}
+
 
 struct icon_info
 {
@@ -209,11 +249,11 @@ create_icon_factory (void)
 
 
     gtk_stock_add (items, 2);
-    gtk_icon_factory_add (factory, "pspp-stock-reset", 
+    gtk_icon_factory_add (factory, "pspp-stock-reset",
                          gtk_icon_factory_lookup_default (GTK_STOCK_REFRESH)
                          );
 
-    gtk_icon_factory_add (factory, "pspp-stock-select", 
+    gtk_icon_factory_add (factory, "pspp-stock-select",
                          gtk_icon_factory_lookup_default (GTK_STOCK_INDEX)
                          );
   }
@@ -221,3 +261,93 @@ create_icon_factory (void)
   gtk_icon_factory_add_default (factory);
 }
 
+\f
+
+static error_t
+parse_non_options (int key, char *arg, struct argp_state *state)
+{
+  struct source_stream *ss = state->input;
+
+  if ( NULL == ss )
+    return 0;
+
+  switch (key)
+    {
+    case ARGP_KEY_ARG:
+      {
+       gchar *filename = NULL;
+       gchar *utf8 = NULL;
+       const gchar *local_encoding = NULL;
+       gsize written = -1;
+       const gboolean local_is_utf8 = g_get_charset (&local_encoding);
+
+       /* There seems to be no Glib function to convert from local encoding
+          to filename encoding.  Therefore it has to be done in two steps:
+          the intermediate encoding is UTF8.
+
+          Either step could fail.  However, in many cases the file can still
+          be loaded even if the conversion fails. So in those cases, after showing
+          a warning, we simply copy the locally encoded filename to the destination
+          and hope for the best.
+       */
+
+       if ( local_is_utf8)
+         {
+           utf8 = xstrdup (arg);
+         }
+       else
+         {
+           GError *err = NULL;
+           utf8 = g_locale_to_utf8 (arg, -1, NULL, &written, &err);
+           if ( NULL == utf8)
+             {
+               g_warning ("Cannot convert filename from local encoding \"%s\" to UTF-8: %s",
+                          local_encoding,
+                          err->message);
+               g_clear_error (&err);
+             }
+         }
+
+       if ( NULL != utf8)
+         {
+           GError *err = NULL;
+           filename = g_filename_from_utf8 (utf8, written, NULL, NULL, &err);
+           if ( NULL == filename)
+             {
+               g_warning ("Cannot convert filename from UTF8 to filename encoding: %s",
+                          err->message);
+               g_clear_error (&err);
+             }
+         }
+
+       g_free (utf8);
+
+       if ( filename == NULL)
+         filename = xstrdup (arg);
+
+       psppire_window_load (PSPPIRE_WINDOW (the_data_window), filename);
+
+       g_free (filename);
+       break;
+      }
+    default:
+      return ARGP_ERR_UNKNOWN;
+    }
+  return 0;
+}
+
+
+const struct argp non_option_argp = {NULL, parse_non_options, 0, 0, 0, 0, 0};
+
+
+const char *
+output_file_name (void)
+{
+  const char *dir = default_output_path ();
+  static char *filename = NULL;
+
+  if ( NULL == filename )
+    filename = xasprintf ("%s%s", dir, OUTPUT_FILE_NAME);
+
+  return filename;
+}