[genius] Fri Sep 05 01:52:10 2014 Jiri (George) Lebl <jirka 5z com>
- From: George Lebl <jirka src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [genius] Fri Sep 05 01:52:10 2014 Jiri (George) Lebl <jirka 5z com>
- Date: Fri, 5 Sep 2014 06:52:32 +0000 (UTC)
commit 1308ac19e1b4ddc8380c4901df132f923fc3ad9b
Author: Jiri (George) Lebl <jiri lebl gmail com>
Date: Fri Sep 5 01:52:16 2014 -0500
Fri Sep 05 01:52:10 2014 Jiri (George) Lebl <jirka 5z com>
* tutors/*: add a simple strange-attractor tutorial
* src/tutors.[ch], src/gnome-genius.c: add a tutorials menu
to load same programs, Right now really simple, eventually should
have submenus, and have to figure out translation
ChangeLog | 8 ++
Makefile.am | 2 +-
configure.in | 1 +
src/Makefile.am | 2 +
src/gnome-genius.c | 121 ++++++++++++++++++++++------
src/graphing.c | 4 +
src/tutors.c | 182 ++++++++++++++++++++++++++++++++++++++++++
src/tutors.h | 34 ++++++++
tutors/Makefile.am | 6 ++
tutors/strange-attractor.gel | 57 +++++++++++++
10 files changed, 390 insertions(+), 27 deletions(-)
---
diff --git a/ChangeLog b/ChangeLog
index 9b8073d..3aea396 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,11 @@
+Fri Sep 05 01:52:10 2014 Jiri (George) Lebl <jirka 5z com>
+
+ * tutors/*: add a simple strange-attractor tutorial
+
+ * src/tutors.[ch], src/gnome-genius.c: add a tutorials menu
+ to load same programs, Right now really simple, eventually should
+ have submenus, and have to figure out translation
+
Tue Sep 02 10:12:42 2014 Jiri (George) Lebl <jirka 5z com>
* help/C/genius.xml: minor fixes
diff --git a/Makefile.am b/Makefile.am
index a5a8ee5..09b28e9 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -1,4 +1,4 @@
-SUBDIRS = ve gtkextra src pixmaps lib po help
+SUBDIRS = ve gtkextra src pixmaps tutors lib po help
mimeinfodir = $(datadir)/mime-info
mimeinfo_DATA = genius.keys genius.mime
diff --git a/configure.in b/configure.in
index 8370d0c..a63f53b 100644
--- a/configure.in
+++ b/configure.in
@@ -282,6 +282,7 @@ lib/symbolic/Makefile
lib/commutative_algebra/Makefile
ve/Makefile
gtkextra/Makefile
+tutors/Makefile
pixmaps/Makefile
pixmaps/32x32/Makefile
pixmaps/48x48/Makefile
diff --git a/src/Makefile.am b/src/Makefile.am
index 392546a..e33026b 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -75,6 +75,8 @@ gnome_genius_SOURCES = \
parseutil.c \
inter.c \
inter.h \
+ tutors.c \
+ tutors.h \
plugin.c \
plugin.h \
plugread.c \
diff --git a/src/gnome-genius.c b/src/gnome-genius.c
index b859164..882d4d0 100644
--- a/src/gnome-genius.c
+++ b/src/gnome-genius.c
@@ -47,6 +47,7 @@
#include "graphing.h"
#include "plugin.h"
+#include "tutors.h"
#include "inter.h"
#include "binreloc.h"
@@ -255,13 +256,15 @@ static void actually_open_help (const char *id);
static void fork_helper_setup_comm (void);
-static void new_program (const char *filename);
+static void new_program (const char *filename,
+ gboolean tutor);
static GtkActionEntry entries[] = {
{ "FileMenu", NULL, N_("_File") }, /* name, stock id, label */
{ "EditMenu", NULL, N_("_Edit") }, /* name, stock id, label */
{ "CalculatorMenu", NULL, N_("_Calculator") }, /* name, stock id, label */
{ "PluginsMenu", NULL, N_("P_lugins") }, /* name, stock id, label */
+ { "TutorialsMenu", NULL, N_("_Tutorials") }, /* name, stock id, label */
{ "ProgramsMenu", NULL, N_("_Programs") }, /* name, stock id, label */
{ "SettingsMenu", NULL, N_("_Settings") }, /* name, stock id, label */
{ "HelpMenu", NULL, N_("_Help") }, /* name, stock id, label */
@@ -418,6 +421,12 @@ static GtkActionEntry entries[] = {
"No Plugins", "",
"No Plugins",
NULL },
+ /* Kind of a placeholder for empty menu,
+ * FIXME: probably a bad hack */
+ { "NoTutorial", NULL,
+ "No Tutorials", "",
+ "No Tutorials",
+ NULL },
};
static guint n_entries = G_N_ELEMENTS (entries);
@@ -465,6 +474,9 @@ static const gchar *ui_info =
" <separator/>"
" <menuitem action='Plot'/>"
" </menu>"
+" <menu action='TutorialsMenu'>"
+" <menuitem action='NoTutorial'/>"
+" </menu>"
" <menu action='PluginsMenu'>"
" <menuitem action='NoPlugin'/>"
" </menu>"
@@ -554,7 +566,6 @@ simple_menu_item_select_cb (GtkMenuItem *item, gpointer data)
if (message) {
gtk_statusbar_push (GTK_STATUSBAR (genius_window_statusbar), 0 /* context */,
message);
- g_free (message);
}
}
@@ -648,7 +659,7 @@ file_open_recent (GtkRecentChooser *chooser, gpointer data)
uri = gtk_recent_info_get_uri (item);
- new_program (uri);
+ new_program (uri, FALSE);
gtk_recent_info_unref (item);
}
@@ -3439,9 +3450,11 @@ file_is_writable (const char *fname)
+/* if tutor, filename is a filename and not a uri */
static void
-new_program (const char *filename)
+new_program (const char *filename, gboolean tutor)
{
+ char *contents;
static int cnt = 1;
GtkWidget *tv;
GtkWidget *sw;
@@ -3542,7 +3555,7 @@ new_program (const char *filename)
G_CALLBACK (move_cursor),
p);
- if (filename == NULL) {
+ if (filename == NULL || tutor) {
GFile* file;
char *d = g_get_current_dir ();
char *n = g_strdup_printf (_("Program_%d.gel"), cnt);
@@ -3559,7 +3572,6 @@ new_program (const char *filename)
p->vname = g_strdup_printf (_("Program %d"), cnt);
cnt++;
} else {
- char *contents;
recent_add (filename);
p->name = g_strdup (filename);
if (file_exists (filename)) {
@@ -3569,31 +3581,40 @@ new_program (const char *filename)
p->readonly = FALSE;
contents = g_strdup ("");
}
- if (contents != NULL &&
- g_utf8_validate (contents, -1, NULL)) {
- GtkTextIter iter;
+ p->vname = g_path_get_basename (p->name);
+ p->real_file = TRUE;
+ }
+
+ if (tutor && filename != NULL) {
+ contents = NULL;
+ g_file_get_contents (filename, &contents, NULL, NULL);
+ }
+
+ if (contents != NULL &&
+ g_utf8_validate (contents, -1, NULL)) {
+ GtkTextIter iter;
#ifdef HAVE_GTKSOURCEVIEW
- gtk_source_buffer_begin_not_undoable_action
- (GTK_SOURCE_BUFFER (buffer));
+ gtk_source_buffer_begin_not_undoable_action
+ (GTK_SOURCE_BUFFER (buffer));
#endif
- gtk_text_buffer_get_iter_at_offset (buffer, &iter, 0);
- gtk_text_buffer_insert_with_tags_by_name
- (buffer, &iter, contents, -1, "foo", NULL);
+ gtk_text_buffer_get_iter_at_offset (buffer, &iter, 0);
+ gtk_text_buffer_insert_with_tags_by_name
+ (buffer, &iter, contents, -1, "foo", NULL);
#ifdef HAVE_GTKSOURCEVIEW
- gtk_source_buffer_end_not_undoable_action
- (GTK_SOURCE_BUFFER (buffer));
+ gtk_source_buffer_end_not_undoable_action
+ (GTK_SOURCE_BUFFER (buffer));
#endif
- g_free (contents);
- } else {
+ g_free (contents);
+ } else {
+ if (filename != NULL && ! tutor) {
char *s = g_strdup_printf (_("Cannot open %s"), filename);
genius_display_error (NULL, s);
g_free (s);
- if (contents != NULL)
- g_free (contents);
}
- p->vname = g_path_get_basename (p->name);
- p->real_file = TRUE;
+ if (contents != NULL)
+ g_free (contents);
}
+
/* the label will change after the set_current_page */
p->label = gtk_label_new (p->vname);
p->mlabel = gtk_label_new (p->vname);
@@ -3635,7 +3656,7 @@ new_program (const char *filename)
static void
new_callback (GtkWidget *menu_item, gpointer data)
{
- new_program (NULL);
+ new_program (NULL, FALSE);
}
static void
@@ -3658,7 +3679,7 @@ really_open_cb (GtkFileChooser *fs, int response, gpointer data)
g_free (last_dir);
last_dir = gtk_file_chooser_get_current_folder (fs);
- new_program (s);
+ new_program (s, FALSE);
gtk_widget_destroy (GTK_WIDGET (fs));
}
@@ -4543,6 +4564,12 @@ catch_interrupts (GtkWidget *w, GdkEvent *e)
}
static void
+open_tutor_cb (GtkWidget *w, GelTutorial * tut)
+{
+ new_program (tut->file, TRUE);
+}
+
+static void
open_plugin_cb (GtkWidget *w, GelPlugin * plug)
{
gel_open_plugin (plug);
@@ -4897,7 +4924,7 @@ loadup_files_from_cmdline (int argc, char *argv[])
g_object_unref (file);
- new_program (uri);
+ new_program (uri, FALSE);
g_free (uri);
}
@@ -4918,7 +4945,7 @@ drag_data_received (GtkWidget *widget, GdkDragContext *context,
uris = gtk_selection_data_get_uris (selection_data);
for (uri = uris[i]; uri != NULL; i++, uri = uris[i]) {
- new_program (uri);
+ new_program (uri, FALSE);
}
g_strfreev (uris);
}
@@ -4965,6 +4992,7 @@ main (int argc, char *argv[])
GtkWidget *w;
char *file;
int plugin_count = 0;
+ int tutor_count = 0;
gboolean give_no_lib_error_after_init = FALSE;
arg0 = g_strdup (argv[0]);
@@ -5138,12 +5166,53 @@ main (int argc, char *argv[])
G_CALLBACK (update_term_geometry), NULL);
gtk_widget_hide (gtk_ui_manager_get_widget (genius_ui, "/MenuBar/PluginsMenu"));
+ gtk_widget_hide (gtk_ui_manager_get_widget (genius_ui, "/MenuBar/TutorialsMenu"));
/* Show the window now before going on with the
* setup */
gtk_widget_show_now (genius_window);
check_events ();
+ gel_read_tutor_list ();
+
+ if (gel_tutor_list != NULL) {
+ GSList *li;
+ int i;
+ GtkWidget *menu = gtk_menu_item_get_submenu (GTK_MENU_ITEM (gtk_ui_manager_get_widget
(genius_ui, "/MenuBar/TutorialsMenu")));
+
+ for (i = 0, li = gel_tutor_list;
+ li != NULL;
+ li = li->next, i++) {
+ GtkWidget *item;
+ GelTutorial *tut = li->data;
+ char *s;
+
+ s = g_strconcat (tut->category, ": ", tut->name, NULL);
+ item = gtk_menu_item_new_with_label (s);
+ g_free (s);
+
+ g_signal_connect (item, "select",
+ G_CALLBACK (simple_menu_item_select_cb),
+ tut->name);
+ g_signal_connect (item, "deselect",
+ G_CALLBACK (simple_menu_item_deselect_cb),
+ tut->name);
+ gtk_widget_show (item);
+ g_signal_connect (G_OBJECT (item), "activate",
+ G_CALLBACK (open_tutor_cb), tut);
+ gtk_menu_shell_append (GTK_MENU_SHELL (menu), item);
+ tutor_count ++;
+ }
+ }
+
+ /* if no tutorials, hide the menu */
+ if (tutor_count == 0) {
+ gtk_widget_hide (gtk_ui_manager_get_widget (genius_ui, "/MenuBar/TutorialsMenu"));
+ } else {
+ gtk_widget_show (gtk_ui_manager_get_widget (genius_ui, "/MenuBar/TutorialsMenu"));
+ gtk_widget_hide (gtk_ui_manager_get_widget (genius_ui, "/MenuBar/TutorialsMenu/NoTutorial"));
+ }
+
gel_read_plugin_list ();
if (gel_plugin_list != NULL) {
diff --git a/src/graphing.c b/src/graphing.c
index c0beba3..4e18100 100644
--- a/src/graphing.c
+++ b/src/graphing.c
@@ -2291,6 +2291,10 @@ ensure_window (gboolean do_window_present)
gtk_widget_show_all (menubar);
plot_canvas = gtk_plot_canvas_new (WIDTH, HEIGHT, 1.0);
+ g_signal_connect (G_OBJECT (plot_canvas),
+ "destroy",
+ G_CALLBACK (gtk_widget_destroyed),
+ &plot_canvas);
GTK_PLOT_CANVAS_UNSET_FLAGS (GTK_PLOT_CANVAS (plot_canvas),
GTK_PLOT_CANVAS_DND_FLAGS);
g_signal_connect (G_OBJECT (plot_canvas), "select_region",
diff --git a/src/tutors.c b/src/tutors.c
new file mode 100644
index 0000000..4075723
--- /dev/null
+++ b/src/tutors.c
@@ -0,0 +1,182 @@
+/* GENIUS Calculator
+ * Copyright (C) 1997-2014 Jiri (George) Lebl
+ *
+ * Author: Jiri (George) Lebl
+ *
+ * This file is part of Genius.
+ *
+ * Genius is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+#include "config.h"
+
+#include <stdlib.h>
+#include <dirent.h>
+#include <unistd.h>
+#include <signal.h>
+#include <glob.h>
+#include <stdio.h>
+#include <string.h>
+#include <math.h>
+#include <time.h>
+#include <glib.h>
+#include <gmodule.h>
+#include <readline/readline.h>
+#include <readline/history.h>
+#include <readline/tilde.h>
+
+#include <vicious.h>
+
+#include "calc.h"
+#include "eval.h"
+#include "util.h"
+#include "dict.h"
+#include "compil.h"
+
+#include "mpwrap.h"
+
+#include "parse.h"
+
+#include "tutors.h"
+
+#include "binreloc.h"
+
+GSList *gel_tutor_list = NULL;
+
+static GHashTable *opened = NULL;
+static GHashTable *info = NULL;
+
+static GelTutorial *
+gel_readtutor (const char *dir_name, const char *file_name)
+{
+ char *f = g_build_filename (ve_sure_string (dir_name),
+ ve_sure_string (file_name), NULL);
+ FILE *fp;
+ char buf[512];
+ char *name;
+ char *cat;
+ char *s;
+ GelTutorial *tut = NULL;
+
+ fp = fopen (f, "r");
+
+ if (fp == NULL) {
+ g_free (f);
+ return NULL;
+ }
+
+ if (fgets (buf, sizeof (buf), fp) == NULL) {
+ g_free (f);
+ fclose (fp);
+ return NULL;
+ }
+
+ s = strchr (buf, ':');
+ if (s != NULL) {
+ cat = g_strdup (g_strstrip(s+1));
+ } else {
+ g_free (f);
+ fclose (fp);
+ return NULL;
+ }
+
+ if (fgets (buf, sizeof (buf), fp) == NULL) {
+ g_free (f);
+ g_free (cat);
+ fclose (fp);
+ return NULL;
+ }
+
+ s = strchr (buf, ':');
+ if (s != NULL) {
+ name = g_strdup (g_strstrip (s+1));
+ } else {
+ g_free (f);
+ g_free (cat);
+ fclose (fp);
+ return NULL;
+ }
+
+ fclose (fp);
+
+ tut = g_new (GelTutorial, 1);
+ tut->category = cat;
+ tut->name = name;
+ tut->file = f;
+
+ return tut;
+}
+
+static void
+free_tutor(GelTutorial *tut)
+{
+ g_free (tut->category);
+ g_free (tut->name);
+ g_free (tut->file);
+ g_free (tut);
+}
+
+static void
+read_tutors_from_dir (const char *dir_name)
+{
+ DIR *dir;
+ struct dirent *dent;
+
+ dir = opendir (dir_name);
+ if (dir == NULL) {
+ return;
+ }
+ while((dent = readdir (dir)) != NULL) {
+ char *p;
+ GelTutorial *tut;
+ if(dent->d_name[0] == '.' &&
+ (dent->d_name[1] == '\0' ||
+ (dent->d_name[1] == '.' &&
+ dent->d_name[2] == '\0')))
+ continue;
+ p = strrchr(dent->d_name,'.');
+ if(!p || strcmp(p,".gel")!=0)
+ continue;
+ tut = gel_readtutor (dir_name, dent->d_name);
+ if (tut != NULL) {
+ gel_tutor_list = g_slist_prepend (gel_tutor_list, tut);
+ }
+ }
+ closedir (dir);
+}
+
+void
+gel_read_tutor_list (void)
+{
+ char *dir_name;
+ char *datadir;
+
+ /*free the previous list*/
+ g_slist_foreach (gel_tutor_list, (GFunc)free_tutor, NULL);
+ g_slist_free (gel_tutor_list);
+ gel_tutor_list = NULL;
+
+ datadir = gbr_find_data_dir (DATADIR);
+ dir_name = g_build_filename (datadir, "genius", "tutors", NULL);
+ g_free (datadir);
+ read_tutors_from_dir (dir_name);
+ g_free (dir_name);
+
+ dir_name = g_build_filename (g_get_home_dir (),
+ ".genius", "tutors", NULL);
+ read_tutors_from_dir (dir_name);
+ g_free (dir_name);
+
+ /* FIXME: should do more */
+ gel_tutor_list = g_slist_reverse (gel_tutor_list);
+}
diff --git a/src/tutors.h b/src/tutors.h
new file mode 100644
index 0000000..f7b15ca
--- /dev/null
+++ b/src/tutors.h
@@ -0,0 +1,34 @@
+/* GENIUS Calculator
+ * Copyright (C) 1997-2014 Jiri (George) Lebl
+ *
+ * Author: Jiri (George) Lebl
+ *
+ * This file is part of Genius.
+ *
+ * Genius is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef TUTOR_H__
+#define TUTOR_H__
+
+typedef struct _GelTutorial {
+ char *category;
+ char *name;
+ char *file;
+} GelTutorial;
+
+void gel_read_tutor_list(void);
+extern GSList *gel_tutor_list;
+
+#endif /* PLUGIN_H__ */
diff --git a/tutors/Makefile.am b/tutors/Makefile.am
new file mode 100644
index 0000000..4fbcf63
--- /dev/null
+++ b/tutors/Makefile.am
@@ -0,0 +1,6 @@
+tutordir = \
+ $(datadir)/genius/tutors/
+tutor_DATA = \
+ strange-attractor.gel
+EXTRA_DIST = \
+ $(tutor_DATA)
diff --git a/tutors/strange-attractor.gel b/tutors/strange-attractor.gel
new file mode 100644
index 0000000..248508d
--- /dev/null
+++ b/tutors/strange-attractor.gel
@@ -0,0 +1,57 @@
+# Category: Differential Equations
+# Name: Strange Attractor (Duffing's equation)
+#
+# Creates a strange attractor by strobing the forced Duffing
+# equation
+#
+
+# The Duffing equation (converted to an ODE system)
+# x_1' = x_2, x_2' = -0.05x_2 - x_1^3 + 7.5cos(t)
+#
+function duf(t,x) = [x@(2),-0.05*x@(2)-(x@(1))^3+7.5*cos(t)];
+
+# Strobe period
+strobe = 2*pi;
+
+# Initial time
+t = 0.0;
+
+# Steps to use in RungeKutta for each strobe
+steps = 25;
+
+# Number of points to compute
+ptnum = 5000;
+
+#initial position
+x = [0.0,0.0];
+
+LinePlotDrawLegends = false;
+
+points = null;
+
+k = 1;
+for j=1 to ptnum do (
+ x = RungeKutta(duf,t,x,t+strobe,steps);
+ t = t+strobe;
+
+ # only plot points from the 100th on
+ if (j > 100) then (
+ points@(k,) = x;
+ increment k;
+
+ # every 500 point display intermediate picture
+ if j % 500 == 0 then (
+ DisplayVariables(`j);
+ PlotCanvasFreeze ();
+ LinePlotClear ();
+ LinePlotDrawPoints (points, "color", "blue", "window", "fit");
+ PlotCanvasThaw ();
+ )
+ )
+);
+
+# Display final picture
+PlotCanvasFreeze ();
+LinePlotClear ();
+LinePlotDrawPoints (points, "color", "blue", "window", "fit");
+PlotCanvasThaw ();
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]