24
24
#include <stdlib.h>
25
25
#include <string.h>
27
#include <OpenGL/gl.h>
29
#include "gtkshorts.h"
33
#include "shortcuts.h"
30
34
#include "dialog.h"
31
37
#include "interface.h"
38
#include "gui_image.h"
40
extern struct sysenv_pak sysenv;
42
#define MANUAL_FILE "gdis.manual"
44
GtkTextTag *help_tag_bold, *help_tag_italic, *help_tag_invisible, *help_tag_fixed;
46
/**********************/
47
/* add a single topic */
48
/**********************/
49
void help_topic_new(gchar *topic, gchar *text)
54
g_hash_table_insert(sysenv.manual, g_strdup(topic), g_strdup(text));
56
g_hash_table_insert(sysenv.manual, g_strdup(topic), "<empty>\n");
59
g_hash_table_insert(sysenv.manual, "error", "manual file was probably not found\n");
62
/**************************************************/
63
/* load the help file and process the manual text */
64
/**************************************************/
68
gchar *filename, *line, *topic;
72
/* hash table with topic label as the key */
73
sysenv.manual = g_hash_table_new(g_str_hash, g_str_equal);
75
/* open the manual file for scanning */
76
filename = g_build_filename(sysenv.gdis_path, MANUAL_FILE, NULL);
77
printf("scanning: %s\n", filename);
78
scan = scan_new(filename);
82
help_topic_new(NULL, NULL);
86
/* process the manual file */
88
buffer = g_string_new(NULL);
89
line = scan_get_line(scan);
90
while (!scan_complete(scan))
92
if (g_strncasecmp(line, "%topic ", 7) == 0)
94
/* add any old data */
95
if (topic && buffer->len)
97
help_topic_new(topic, buffer->str);
98
buffer = g_string_set_size(buffer, 0);
101
/* remove trailing <cr> */
102
n = strlen(&line[7]);
103
topic = g_strndup(&line[7], n-1);
107
/* append everything that's not a topic to the current buffer */
109
g_string_append(buffer, line);
112
line = scan_get_line(scan);
115
/* done - add the last topic found */
117
help_topic_new(topic, buffer->str);
119
g_string_free(buffer, TRUE);
125
/**********************/
126
/* add a single entry */
127
/**********************/
128
void gui_help_populate(gpointer key, gpointer value, gpointer data)
132
GtkListStore *list = data;
134
gtk_list_store_append(list, &iter);
135
gtk_list_store_set(list, &iter, 0, topic, -1);
138
/****************************************/
139
/* fill out the available manual topics */
140
/****************************************/
141
void gui_help_refresh(GtkListStore *list)
143
g_assert(sysenv.manual != NULL);
145
gtk_list_store_clear(list);
146
g_hash_table_foreach(sysenv.manual, gui_help_populate, list);
149
/*********************************************/
150
/* process and display appropriate help text */
151
/*********************************************/
152
void gui_help_topic_show(GtkTextBuffer *buffer, gchar *source)
154
gint i, j, n, start, stop;
159
/* initialize help tags */
161
help_tag_bold = gtk_text_buffer_create_tag(buffer,
163
"weight", PANGO_WEIGHT_BOLD,
166
if (!help_tag_italic)
167
help_tag_italic = gtk_text_buffer_create_tag(buffer,
169
"style", PANGO_STYLE_ITALIC,
172
/* invisible tag not implemented as of GTK 2.2 */
174
if (!help_tag_invisible)
175
help_tag_invisible = gtk_text_buffer_create_tag(buffer,
182
/* FIXME - hack due to above */
183
if (!help_tag_invisible)
185
GdkColor white = {0, 65535, 65535, 65535};
186
help_tag_invisible = gtk_text_buffer_create_tag(buffer,
195
help_tag_fixed = gtk_text_buffer_create_tag(buffer,
202
tag_bold = gtk_text_buffer_create_tag(buffer, "bold", "style", PANGO_WEIGHT_OBLIQUE, NULL);
205
gtk_text_buffer_set_text(buffer, source, -1);
212
/* search for special tags */
213
if (source[i] == '\\')
215
/* process the tag */
220
/* make the tag invisible */
221
gtk_text_buffer_get_iter_at_offset(buffer, &a, i);
222
gtk_text_buffer_get_iter_at_offset(buffer, &b, i+3);
223
gtk_text_buffer_apply_tag(buffer, help_tag_invisible, &a, &b);
225
/* apply the bold tag to the rest of the line */
227
for (j=i+3 ; j<n ; j++)
229
if (source[j] == '\n')
237
gtk_text_buffer_get_iter_at_offset(buffer, &b, stop);
238
gtk_text_buffer_apply_tag(buffer, help_tag_bold, &a, &b);
244
/* make the tag invisible */
245
gtk_text_buffer_get_iter_at_offset(buffer, &a, i);
246
gtk_text_buffer_get_iter_at_offset(buffer, &b, i+3);
247
gtk_text_buffer_apply_tag(buffer, help_tag_invisible, &a, &b);
249
/* apply the bold tag to the rest of the line */
251
for (j=i+3 ; j<n ; j++)
253
if (source[j] == '\n')
261
gtk_text_buffer_get_iter_at_offset(buffer, &b, stop);
262
gtk_text_buffer_apply_tag(buffer, help_tag_italic, &a, &b);
266
/* fixed width font */
268
/* make the tag invisible */
269
gtk_text_buffer_get_iter_at_offset(buffer, &a, i);
270
gtk_text_buffer_get_iter_at_offset(buffer, &b, i+3);
271
gtk_text_buffer_apply_tag(buffer, help_tag_invisible, &a, &b);
273
/* apply the fixed tag to the rest of the line */
275
for (j=i+3 ; j<n ; j++)
277
if (source[j] == '\n')
285
gtk_text_buffer_get_iter_at_offset(buffer, &b, stop);
286
gtk_text_buffer_apply_tag(buffer, help_tag_fixed, &a, &b);
292
/* get the picture label code */
294
for (j=i+3 ; j<n ; j++)
296
if (source[j] == ' ' || source[j] == '\n')
306
gtk_text_buffer_get_iter_at_offset(buffer, &a, i);
307
gtk_text_buffer_get_iter_at_offset(buffer, &b, stop);
308
gtk_text_buffer_apply_tag(buffer, help_tag_invisible, &a, &b);
310
/* CURRENT - delete one char to compensate? */
311
gtk_text_buffer_get_iter_at_offset(buffer, &b, i+1);
312
gtk_text_buffer_delete(buffer, &a, &b);
314
/* insert the pixbuf - counts as one character in the text buffer */
315
text = g_strndup(&source[i+3], stop-i-3);
316
pixbuf = image_table_lookup(text);
317
gtk_text_buffer_insert_pixbuf(buffer, &a, pixbuf);
327
/***************************/
328
/* topic selection handler */
329
/***************************/
330
void gui_help_topic_selected(GtkTreeSelection *selection, gpointer data)
334
GtkTreeModel *treemodel;
335
GtkTextBuffer *buffer;
337
/* record selection as the active entry */
338
if (gtk_tree_selection_get_selected(selection, &treemodel, &iter))
340
gtk_tree_model_get(treemodel, &iter, 0, &topic, -1);
341
text = g_hash_table_lookup(sysenv.manual, topic);
342
buffer = gtk_text_view_get_buffer(GTK_TEXT_VIEW(data));
343
gui_help_topic_show(buffer, text);
347
/*******************************/
348
/* topic list sorting primitve */
349
/*******************************/
350
gint help_sort_topics(GtkTreeModel *treemodel, GtkTreeIter *a, GtkTreeIter *b, gpointer data)
354
gtk_tree_model_get(treemodel, a, 0, &str1, -1);
355
gtk_tree_model_get(treemodel, b, 0, &str2, -1);
357
return(strcasecmp(str1, str2));
360
/****************************/
361
/* display a manual browser */
362
/****************************/
363
void gui_help_dialog(void)
40
GtkWidget *window, *notebook, *hbox, *vbox, *frame, *label;
41
GString *buff, *title;
367
GtkTreeViewColumn *c;
369
GtkTreeSelection *select;
370
GtkWidget *window, *swin, *hbox, *tree, *view;
44
dialog = dialog_request(ABOUT, "About", NULL, NULL, NULL);
373
dialog = dialog_request(MANUAL, "Manual", NULL, NULL, NULL);
47
376
window = dialog_window(dialog);
48
gtk_window_set_position(GTK_WINDOW(window), GTK_WIN_POS_CENTER);
50
/* notebook display */
51
hbox = gtk_hbox_new(FALSE,0);
52
gtk_box_pack_start(GTK_BOX(GTK_DIALOG(window)->vbox), hbox, TRUE, TRUE, 10);
53
notebook = gtk_notebook_new();
54
gtk_notebook_set_tab_pos(GTK_NOTEBOOK(notebook), GTK_POS_TOP);
55
gtk_container_add(GTK_CONTAINER(hbox), notebook);
58
buff = g_string_new(NULL);
59
title = g_string_new(NULL);
61
/* fill out the pages in the notebook */
62
for (doc=0 ; doc<LAST ; doc++)
67
g_string_assign(title,"GDIS");
68
g_string_sprintf(buff,"GDIS version %4.2f.%d\n\n",VERSION,PATCH);
69
g_string_append(buff,"The GTK Display Interface for Structures\n\n");
70
g_string_append(buff,"(c) 2004 by Sean Fleming\n");
71
g_string_append(buff,"sean@power.curtin.edu.au\n\n");
72
g_string_append(buff,"http://gdis.sourceforge.net\n\n");
73
g_string_append(buff,"Additional programming:\n\n");
74
g_string_append(buff,"Andrew Rohl\n");
75
g_string_append(buff,"andrew@power.curtin.edu.au\n\n");
76
g_string_append(buff,"Current development of this project is supported by the\n");
77
g_string_append(buff,"Western Australian Premier's Research Fellowship.\n");
80
g_string_assign(title,"SgInfo");
81
g_string_sprintf(buff,"Space Group information lookup.\n\n");
82
g_string_append(buff,"(c) 1994-96 by Ralf W. Grosse-Kunstleve.\n\n");
83
g_string_append(buff,"rwgk@laplace.csb.yale.edu\n\n");
86
g_string_assign(title,"Symmetry");
87
g_string_sprintf(buff,"Brute force symmetry analyzer\n\n");
88
g_string_append(buff,"(c) 1996 Sergei Pachkovsky\n\n");
89
g_string_append(buff,"patchkov@chem.ucalgary.ca\n\n");
90
g_string_append(buff,"http://www.cobalt.chem.ucalgary.ca/ps/\n\n");
93
g_string_assign(title,"CDD");
94
g_string_sprintf(buff,"CDD uses the double description method to compute\n");
95
g_string_append(buff,"the vertices and extreme rays of a polyhedron.\n");
96
g_string_append(buff,"It is utilized in calculating crystal habits.\n\n");
97
g_string_append(buff,"(c) 1997 by Komei Fukuda\n\n");
98
g_string_append(buff,"fukuda@ifor.math.ethz.ch\n\n");
99
g_string_append(buff,"http://www.ifor.math.ethz.ch/~fukuda/cdd_home/cdd.html\n\n");
102
g_string_assign(title,"GPeriodic");
103
g_string_sprintf(buff,"Shows the periodic table of elements.\n\n");
104
g_string_append(buff,"(c) 1999 by Kyle R. Burton\n\n");
105
g_string_append(buff,"mortis@voicenet.com\n\n");
106
g_string_append(buff,"http://www.voicenet.com/~mortis\n");
107
g_string_append(buff,"http://gperiodic.seul.org\n\n");
108
g_string_append(buff,"Contributing authors:\n");
109
g_string_append(buff,"a.w.peters@ieee.org,\n");
110
g_string_append(buff,"khazuada@univ-littoral.fr,\n");
111
g_string_append(buff,"mrivera@cable.net.co,\n");
112
g_string_append(buff,"chris@koeln.ccc.de,\n");
113
g_string_append(buff,"lalo@linuxcenter.com.br\n");
114
g_string_append(buff,"koen_kooi@hotmail.com\n\n");
377
gtk_window_set_default_size(GTK_WINDOW(window), 800, 500);
379
/* split pane display */
380
hbox = gtk_hbox_new(FALSE, 0);
381
gtk_box_pack_start(GTK_BOX(GTK_DIALOG(window)->vbox), hbox, TRUE, TRUE, 1);
383
/* left pane - topics browser */
384
swin = gtk_scrolled_window_new(NULL, NULL);
385
gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(swin),
386
GTK_POLICY_NEVER, GTK_POLICY_NEVER);
387
gtk_box_pack_start(GTK_BOX(hbox), swin, FALSE, TRUE, 0);
390
list = gtk_list_store_new(1, G_TYPE_STRING);
391
tree = gtk_tree_view_new_with_model(GTK_TREE_MODEL(list));
392
gtk_scrolled_window_add_with_viewport(GTK_SCROLLED_WINDOW(swin), tree);
393
r = gtk_cell_renderer_text_new();
394
c = gtk_tree_view_column_new_with_attributes(" ", r, "text", 0, NULL);
395
gtk_tree_view_append_column(GTK_TREE_VIEW(tree), c);
396
gtk_tree_view_set_headers_visible(GTK_TREE_VIEW(tree), FALSE);
398
/* auto sort the topic list */
399
gtk_tree_sortable_set_default_sort_func(GTK_TREE_SORTABLE(GTK_TREE_MODEL(list)),
400
help_sort_topics, NULL, NULL);
401
gtk_tree_sortable_set_sort_column_id(GTK_TREE_SORTABLE(GTK_TREE_MODEL(list)),
402
GTK_TREE_SORTABLE_DEFAULT_SORT_COLUMN_ID,
405
/* set the width of the topics pane */
406
gtk_widget_set_size_request(swin, 15*sysenv.gtk_fontsize, -1);
408
/* right pane - text */
409
swin = gtk_scrolled_window_new(NULL, NULL);
410
gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(swin),
411
GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC);
412
gtk_box_pack_start(GTK_BOX(hbox), swin, TRUE, TRUE, 0);
413
view = gtk_text_view_new();
414
gtk_text_view_set_editable(GTK_TEXT_VIEW(view), FALSE);
415
gtk_container_add(GTK_CONTAINER(swin), view);
417
/* configure the text viewing area */
418
gtk_text_view_set_wrap_mode(GTK_TEXT_VIEW(view), GTK_WRAP_WORD);
419
/* NB: GTK_JUSTIFY_FILL was not supported at the time this was written */
421
gtk_text_view_set_justification(GTK_TEXT_VIEW(view), GTK_JUSTIFY_FILL);
423
gtk_text_view_set_left_margin(GTK_TEXT_VIEW(view), PANEL_SPACING);
424
gtk_text_view_set_right_margin(GTK_TEXT_VIEW(view), PANEL_SPACING);
426
/* NB: these are associated with the text buffer and must be reallocated each */
427
/* time a new text buffer is created */
429
help_tag_italic=NULL;
430
help_tag_invisible=NULL;
433
/* topic selection handler */
434
select = gtk_tree_view_get_selection(GTK_TREE_VIEW(tree));
435
gtk_tree_selection_set_mode(select, GTK_SELECTION_SINGLE);
436
g_signal_connect(G_OBJECT(select), "changed",
437
G_CALLBACK(gui_help_topic_selected),
440
/* terminating button */
441
gui_stock_button(GTK_STOCK_CLOSE, dialog_destroy, dialog,
442
GTK_DIALOG(window)->action_area);
444
/* populate the manual page */
445
gui_help_refresh(list);
447
/* expose the dialog */
448
gtk_widget_show_all(window);
117
455
g_string_assign(title,"OpenGL");
118
456
g_string_sprintf(buff,"GL_RENDERER %s\n", glGetString(GL_RENDERER));
119
457
g_string_sprintfa(buff,"GL_VERSION %s\n", glGetString(GL_VERSION));
120
458
g_string_sprintfa(buff,"GL_VENDOR %s\n", glGetString(GL_VENDOR));
123
g_string_assign(title,"POVRay");
124
g_string_sprintf(buff,"The Persistence Of Vision Raytracer\n\n");
125
g_string_append(buff,"http://www.povray.org\n\n");
126
g_string_append(buff,"GDIS acts only as a GUI to POVRay.\n\n");
127
g_string_append(buff,"A working version of POVRay must be installed\n");
128
g_string_append(buff,"on your system in order to render molecules.\n");
131
g_string_assign(title,"GULP");
132
g_string_sprintf(buff,"The General Utility Lattice Program\n\n");
133
g_string_append(buff,"(c) Julian Gale\n\n");
134
g_string_append(buff,"j.gale@curtin.edu.au\n\n");
135
g_string_append(buff,"http://gulp.curtin.edu.au/\n\n");
136
g_string_append(buff,"GDIS acts only as a GUI to GULP.\n\n");
137
g_string_append(buff,"A working version of GULP must be installed on\n");
138
g_string_append(buff,"your system in order to run energy calculations.\n");
141
g_string_assign(title,"Babel");
142
g_string_sprintf(buff,"A coordinate file interconversion program\n\n");
143
g_string_append(buff,"(c) 1992-1996 Pat Walters and Matt Stahl\n\n");
144
g_string_append(buff,"babel@mercury.aichem.arizona.edu\n\n");
145
g_string_append(buff,"http://smog.com/chem/babel/\n\n");
146
g_string_append(buff,"GDIS acts only as a GUI to Babel.\n\n");
147
g_string_append(buff,"A working version of Babel must be installed on\n");
148
g_string_append(buff,"your system in order to load certain filetypes.\n");
154
/* frame each page */
155
frame = gtk_frame_new (title->str);
156
gtk_container_set_border_width (GTK_CONTAINER (frame), 10);
157
/* put in a vbox to get a border around the text */
158
vbox = gtk_vbox_new(TRUE,0);
159
gtk_container_add (GTK_CONTAINER (frame), vbox);
160
gtk_container_set_border_width (GTK_CONTAINER(GTK_BOX(vbox)), 10);
161
/* add the title & text */
162
label = gtk_label_new (buff->str);
163
gtk_container_add(GTK_CONTAINER(GTK_BOX(vbox)), label);
164
label = gtk_label_new (title->str);
165
gtk_notebook_append_page (GTK_NOTEBOOK (notebook), frame, label);
168
/* starting page - GDIS, of course */
169
gtk_notebook_set_page(GTK_NOTEBOOK(notebook), 0);
171
/* terminating button */
172
gtksh_stock_button(GTK_STOCK_CLOSE, dialog_destroy, dialog,
173
GTK_DIALOG(window)->action_area);
176
/* show the dialog */
177
gtk_widget_show_all(window);
180
g_string_free(buff, TRUE);
181
g_string_free(title, TRUE);