/* PSPPIRE - a graphical user interface for PSPP.
- Copyright (C) 2006, 2007, 2010, 2011, 2012, 2013, 2015, 2016 Free Software Foundation
+ Copyright (C) 2006, 2007, 2010, 2011, 2012, 2013, 2015, 2016,
+ 2021 Free Software Foundation
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
#include <gtk/gtk.h>
-#include <libpspp/copyleft.h>
-#include <libpspp/version.h>
-#include "help-menu.h"
-#include <libpspp/message.h>
+#include "libpspp/cast.h"
+#include "libpspp/copyleft.h"
+#include "libpspp/message.h"
+#include "libpspp/version.h"
+#include "ui/gui/executor.h"
+#include "ui/gui/help-menu.h"
+#include "ui/gui/psppire-data-window.h"
#include "gl/configmake.h"
#include "gl/relocatable.h"
/* Try to open html documentation uri via the default
browser on the operating system */
#ifdef __APPLE__
-#define HTMLOPENARGV {"open", 0, 0}
+#define HTMLOPENAPP "open"
#elif _WIN32
-#define HTMLOPENARGV {"wscript", 0, 0}
+#define HTMLOPENAPP "wscript"
#else
-#define HTMLOPENARGV {"xdg-open", 0, 0}
+#define HTMLOPENAPP "xdg-open"
#endif
static const gchar *artists[] = { "Bastián Díaz", "Hugo Alejandro", NULL};
+/* Opening the htmluri in windows via cmd /start uri opens
+ the windows command shell for a moment. The alternative is
+ to start a script via wscript. This will not be visible*/
+#ifdef _WIN32
+static gboolean
+open_windows_help (const gchar *helpuri, GError **err)
+{
+ SHELLEXECUTEINFOA info;
+ memset (&info, 0, sizeof (info));
+
+ info.cbSize = sizeof (info);
+ info.fMask = SEE_MASK_FLAG_NO_UI;
+ info.lpVerb = "open";
+ info.lpFile = helpuri;
+ info.nShow = SW_SHOWNORMAL;
+
+ BOOL ret = ShellExecuteExA (&info);
+
+ if (ret)
+ return TRUE;
+
+ /* Contrary to what the microsoft documentation indicates, ShellExecuteExA does
+ not seem to setLastError. So we have to deal with errors ourselves here. */
+ const char *msg = 0;
+ switch (GPOINTER_TO_INT (info.hInstApp))
+ {
+ case SE_ERR_FNF:
+ msg = "File not found";
+ break;
+ case SE_ERR_PNF:
+ msg = "Path not found";
+ break;
+ case SE_ERR_ACCESSDENIED:
+ msg = "Access denied";
+ break;
+ case SE_ERR_OOM:
+ msg = "Out of memory";
+ break;
+ case SE_ERR_DLLNOTFOUND:
+ msg = "Dynamic-link library not found";
+ break;
+ case SE_ERR_SHARE:
+ msg = "Cannot share an open file";
+ break;
+ case SE_ERR_ASSOCINCOMPLETE:
+ msg = "File association information not complete";
+ break;
+ case SE_ERR_DDETIMEOUT:
+ msg = "DDE operation timed out";
+ break;
+ case SE_ERR_DDEFAIL:
+ msg = "DDE operation failed";
+ break;
+ case SE_ERR_DDEBUSY:
+ msg = "DDE operation is busy";
+ break;
+ case SE_ERR_NOASSOC:
+ msg = "File association not available";
+ break;
+ default:
+ msg = "Unknown error";
+ break;
+ }
+
+ *err = g_error_new_literal (g_quark_from_static_string ("pspp-help-error"),
+ 0,
+ msg);
+
+ return FALSE;
+}
+
+static gboolean
+on_activate_link (GtkAboutDialog *label,
+ gchar *uri,
+ gpointer user_data)
+{
+ return open_windows_help (uri, NULL);
+}
+#endif
+
+static void
+about_system_info (GtkMenuItem *mmm, GtkWindow *parent)
+{
+ execute_const_syntax_string (psppire_default_data_window (), "SHOW SYSTEM.");
+}
+
static void
about_new (GtkMenuItem *mmm, GtkWindow *parent)
{
GtkWidget *about = gtk_about_dialog_new ();
- gtk_about_dialog_set_logo_icon_name (GTK_ABOUT_DIALOG (about), "pspp");
+#ifdef _WIN32
+ /* The default handler for Windows doesn't appear to work. */
+ g_signal_connect (about, "activate-link", G_CALLBACK (on_activate_link), parent);
+#endif
- gtk_window_set_icon_name (GTK_WINDOW (about), "pspp");
+ gtk_about_dialog_set_logo_icon_name (GTK_ABOUT_DIALOG (about), "org.gnu.pspp");
+
+ gtk_window_set_icon_name (GTK_WINDOW (about), "org.gnu.pspp");
gtk_about_dialog_set_website (GTK_ABOUT_DIALOG (about), PACKAGE_URL);
/* TRANSLATORS: Do not translate this string. Instead, put the names of the people
who have helped in the translation. */
_("translator-credits")
- );
+);
gtk_window_set_transient_for (GTK_WINDOW (about), parent);
}
-/* Opening the htmluri in windows via cmd /start uri opens
- the windows command shell for a moment. The alternative is
- to start a script via wscript. This will not be visible*/
-#ifdef _WIN32
-static gboolean open_windows_help (const gchar *helpuri,
- GError **err)
-{
- gchar *vbsfilename = NULL;
- gchar *vbs = NULL;
- gboolean result;
- vbsfilename = g_build_filename (g_get_tmp_dir (),
- "pspp-help-open.vbs",
- NULL);
- vbs = g_strdup_printf("CreateObject(\"WScript.Shell\").Run \"%s\"",
- helpuri);
- result = g_file_set_contents (vbsfilename,
- vbs,
- strlen(vbs),
- err);
- g_free (vbs);
- if (!result)
- goto error;
-
- gchar *argv[] = {"wscript",vbsfilename,0};
-
- result = g_spawn_async (NULL, argv,
- NULL, G_SPAWN_SEARCH_PATH,
- NULL, NULL, NULL, err);
- error:
- g_free (vbsfilename);
- return result;
-}
-#endif
/* Open the manual at PAGE with the following priorities
First: local yelp help system
void
online_help (const char *page)
{
- GError *err = NULL;
GError *htmlerr = NULL;
- gchar *argv[3] = { "yelp", 0, 0};
- gchar *htmlargv[3] = HTMLOPENARGV;
gchar *htmlfilename = NULL;
gchar *htmlfullname = NULL;
gchar *htmluri = NULL;
if (page == NULL)
{
- argv[1] = g_strdup_printf ("file://%s", relocate (DOCDIR "/pspp.xml"));
htmlfilename = g_strdup ("index.html");
}
else
gchar **tokens = NULL;
const int maxtokens = 5;
int idx ;
- argv[1] = g_strdup_printf ("file://%s#%s",
- relocate (DOCDIR "/pspp.xml"), page);
/* The page will be translated to the htmlfilename
page htmlfilename
GRAPH#SCATTERPLOT SCATTERPLOT.html
htmlfilename);
g_free (htmlfullname);
g_free (htmlfilename);
- htmlargv[1] = htmluri;
- /* The following **SHOULD** work but it does not on 28.5.2016
- g_app_info_launch_default_for_uri (htmluri, NULL, &err);
- osx: wine is started to launch the uri...
- windows: not so bad, but the first access does not work*/
-
- if (! (g_spawn_async (NULL, argv,
- NULL, G_SPAWN_SEARCH_PATH,
- NULL, NULL, NULL, &err) ||
#ifdef _WIN32
- open_windows_help (htmluri, &htmlerr))
+ bool ok = open_windows_help (htmluri, &htmlerr);
#else
- g_spawn_async (NULL, htmlargv,
- NULL, G_SPAWN_SEARCH_PATH,
- NULL, NULL, NULL, &htmlerr))
+ gchar *htmlargv[3] = {CONST_CAST (char *, HTMLOPENAPP), htmluri, 0};
+ bool ok = g_spawn_async (NULL, htmlargv,
+ NULL, G_SPAWN_SEARCH_PATH,
+ NULL, NULL, NULL, &htmlerr);
#endif
- )
+ if (!ok)
{
- msg (ME, _("Cannot open reference manual via yelp: %s. "
- "Cannot open via html: %s "
+ msg (ME, _("Cannot open via html: %s "
"with uri: %s "
"The PSSP manual is also available at %s"),
- err->message,
htmlerr->message,
htmluri,
PACKAGE_URL "documentation.html");
}
- g_free (argv[1]);
g_free (htmluri);
- g_clear_error (&err);
g_clear_error (&htmlerr);
}
GtkWidget *menu = gtk_menu_new ();
GtkWidget *help_about = gtk_menu_item_new_with_mnemonic (_("_About"));
+ GtkWidget *help_system_info = gtk_menu_item_new_with_mnemonic (_("_System Information"));
GtkWidget *help_ref = gtk_menu_item_new_with_mnemonic (_("_Reference Manual"));
GtkAccelGroup *accel_group = gtk_accel_group_new ();
GTK_ACCEL_VISIBLE);
gtk_menu_attach (GTK_MENU (menu), help_ref, 0, 1, 0, 1);
- gtk_menu_attach (GTK_MENU (menu), help_about, 0, 1, 1, 2);
+ gtk_menu_attach (GTK_MENU (menu), help_system_info, 0, 1, 1, 2);
+ gtk_menu_attach (GTK_MENU (menu), help_about, 0, 1, 2, 3);
g_signal_connect (help_about, "activate", G_CALLBACK (about_new), toplevel);
+ g_signal_connect (help_system_info, "activate", G_CALLBACK (about_system_info), toplevel);
g_signal_connect (help_ref, "activate", G_CALLBACK (reference_manual), NULL);
g_object_set (menuitem, "submenu", menu, NULL);
gtk_widget_show_all (menuitem);
+ g_object_unref (accel_group);
+
return menuitem;
}