aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--epan/prefs-int.h4
-rw-r--r--epan/prefs.c101
-rw-r--r--epan/prefs.h8
-rw-r--r--gtk/prefs_dlg.c92
4 files changed, 167 insertions, 38 deletions
diff --git a/epan/prefs-int.h b/epan/prefs-int.h
index 547ae36742..7603049fc7 100644
--- a/epan/prefs-int.h
+++ b/epan/prefs-int.h
@@ -30,9 +30,9 @@ struct pref_module {
const char *name; /* name of module */
const char *title; /* title of module (displayed in preferences list) */
const char *description;/* Description of module (displayed in preferences notebook) */
- gboolean is_subtree; /* if TRUE, this has other modules, not preferences, under it */
void (*apply_cb)(void); /* routine to call when preferences applied */
- GList *prefs; /* list of its preferences or submodules */
+ GList *prefs; /* list of its preferences */
+ GList *submodules; /* list of its submodules */
int numprefs; /* number of non-obsolete preferences */
gboolean prefs_changed; /* if TRUE, a preference has changed since we last checked */
gboolean obsolete; /* if TRUE, this is a module that used to
diff --git a/epan/prefs.c b/epan/prefs.c
index 309d876567..2dd47070a1 100644
--- a/epan/prefs.c
+++ b/epan/prefs.c
@@ -51,6 +51,7 @@
#include <epan/uat-int.h>
/* Internal functions */
+static module_t *find_subtree(module_t *parent, const char *name);
static module_t *prefs_register_module_or_subtree(module_t *parent,
const char *name, const char *title, const char *description, gboolean is_subtree,
void (*apply_cb)(void));
@@ -166,13 +167,27 @@ prefs_register_module_or_subtree(module_t *parent, const char *name,
const char *p;
guchar c;
+ /* this module may have been created as a subtree item previously */
+ if(module = find_subtree(parent, title)) {
+ /* the module is currently a subtree */
+ module->name = name;
+ module->apply_cb = apply_cb;
+ module->description = description;
+
+ if(prefs_find_module(name) == NULL)
+ modules = g_list_insert_sorted(modules, module,
+ module_compare_name);
+
+ return module;
+ }
+
module = g_malloc(sizeof (module_t));
module->name = name;
module->title = title;
module->description = description;
- module->is_subtree = is_subtree;
module->apply_cb = apply_cb;
module->prefs = NULL; /* no preferences, to start */
+ module->submodules = NULL; /* no submodules, to start */
module->numprefs = 0;
module->prefs_changed = FALSE;
module->obsolete = FALSE;
@@ -238,7 +253,7 @@ prefs_register_module_or_subtree(module_t *parent, const char *name,
/*
* It goes into the list for this module.
*/
- parent->prefs = g_list_insert_sorted(parent->prefs, module,
+ parent->submodules = g_list_insert_sorted(parent->submodules, module,
module_compare_title);
}
@@ -271,6 +286,59 @@ prefs_register_protocol(int id, void (*apply_cb)(void))
proto_get_protocol_name(id), apply_cb);
}
+
+module_t *
+prefs_register_protocol_subtree(const char *subtree, int id, void (*apply_cb)(void))
+{
+ protocol_t *protocol;
+ module_t *subtree_module;
+ module_t *new_module;
+ char *sep = NULL, *ptr = NULL;
+ char *csubtree = NULL;
+
+ /*
+ * Have we yet created the "Protocols" subtree?
+ */
+ if (protocols_module == NULL) {
+ /*
+ * No. Do so.
+ */
+ protocols_module = prefs_register_subtree(NULL, "Protocols", NULL);
+ }
+
+ subtree_module = protocols_module;
+
+ if(subtree) {
+ /* take a copy of the buffer */
+ ptr = csubtree = g_strdup(subtree);
+
+ while(ptr && *ptr) {
+
+ if((sep = strchr(ptr, '/')))
+ *sep++ = '\0';
+
+ if(!(new_module = find_subtree(subtree_module, ptr))) {
+ /* create it */
+ new_module = prefs_register_subtree(subtree_module, ptr, NULL);
+ }
+
+ subtree_module = new_module;
+ ptr = sep;
+
+ }
+
+ /* g_free(csubtree); */
+
+ }
+
+ protocol = find_protocol_by_id(id);
+ return prefs_register_module(subtree_module,
+ proto_get_protocol_filter_name(id),
+ proto_get_protocol_short_name(protocol),
+ proto_get_protocol_name(id), apply_cb);
+}
+
+
/*
* Register that a protocol used to have preferences but no longer does,
* by creating an "obsolete" module for it.
@@ -322,6 +390,27 @@ prefs_find_module(const char *name)
return (module_t *) list_entry->data;
}
+static gint
+subtree_match(gconstpointer a, gconstpointer b)
+{
+ const module_t *module = a;
+ const char *title = b;
+
+ return strcmp(title, module->title);
+}
+
+static module_t *
+find_subtree(module_t *parent, const char *name)
+{
+ GList *list_entry;
+
+ list_entry = g_list_find_custom(parent ? parent->submodules : top_level_modules,
+ name, subtree_match);
+ if (list_entry == NULL)
+ return NULL; /* no such module */
+ return (module_t *) list_entry->data;
+}
+
/*
* Call a callback function, with a specified argument, for each module
* in a list of modules. If the list is NULL, searches the top-level
@@ -1306,13 +1395,7 @@ read_prefs_file(const char *pf_path, FILE *pf, pref_set_pair_cb pref_set_pair_fc
}
break;
case IN_VAL:
- if (got_c != '#') {
- g_string_append_c(cur_val, (gchar) got_c);
- } else {
- while (isspace((guchar)cur_val->str[cur_val->len]) && cur_val->len > 0)
- g_string_truncate(cur_val, cur_val->len - 1);
- state = IN_SKIP;
- }
+ g_string_append_c(cur_val, (gchar) got_c);
break;
}
}
diff --git a/epan/prefs.h b/epan/prefs.h
index 52e1adeff0..230361eea1 100644
--- a/epan/prefs.h
+++ b/epan/prefs.h
@@ -195,6 +195,14 @@ extern module_t *prefs_register_subtree(module_t *parent, const char *title,
extern module_t *prefs_register_protocol(int id, void (*apply_cb)(void));
/*
+ * Register that a protocol has preferences and group it under a single
+ * subtree
+ */
+#define PREFERENCE_GROUPING
+extern module_t *prefs_register_protocol_subtree(const char *subtree, int id,
+ void (*apply_cb)(void));
+
+/*
* Register that a protocol used to have preferences but no longer does,
* by creating an "obsolete" module for it.
*/
diff --git a/gtk/prefs_dlg.c b/gtk/prefs_dlg.c
index da16a45ed5..55e2a1e60a 100644
--- a/gtk/prefs_dlg.c
+++ b/gtk/prefs_dlg.c
@@ -127,6 +127,8 @@ struct ct_struct {
gboolean is_protocol;
};
+static gint blank_page = 0;
+
static guint
pref_exists(pref_t *pref _U_, gpointer user_data _U_)
{
@@ -277,7 +279,7 @@ module_prefs_show(module_t *module, gpointer user_data)
/*
* Is this module a subtree, with modules underneath it?
*/
- if (!module->is_subtree) {
+ if (!module->submodules) {
/*
* No.
* Does it have any preferences (other than possibly obsolete ones)?
@@ -299,25 +301,24 @@ module_prefs_show(module_t *module, gpointer user_data)
strcpy(label_str, module->title);
#if GTK_MAJOR_VERSION < 2
ct_node = gtk_ctree_insert_node(GTK_CTREE(cts->tree), cts->node, NULL,
- &label_ptr, 5, NULL, NULL, NULL, NULL, !module->is_subtree,
+ &label_ptr, 5, NULL, NULL, NULL, NULL, !module->submodules,
FALSE);
#else
model = GTK_TREE_STORE(gtk_tree_view_get_model(GTK_TREE_VIEW(cts->tree)));
- if (module->is_subtree)
- gtk_tree_store_append(model, &iter, NULL);
- else
- gtk_tree_store_append(model, &iter, &cts->iter);
+ if (module->submodules && !cts->iter.stamp)
+ gtk_tree_store_append(model, &iter, NULL);
+ else
+ gtk_tree_store_append(model, &iter, &cts->iter);
#endif
/*
* Is this a subtree?
*/
- if (module->is_subtree) {
+ if (module->submodules) {
/*
* Yes.
*/
- /* Note that there's no page attached to this item */
#if GTK_MAJOR_VERSION < 2
gtk_ctree_node_set_row_data(GTK_CTREE(cts->tree), ct_node,
GINT_TO_POINTER(-1));
@@ -336,10 +337,15 @@ module_prefs_show(module_t *module, gpointer user_data)
#endif
if (module == protocols_module)
child_cts.is_protocol = TRUE;
- prefs_module_list_foreach(module->prefs, module_prefs_show, &child_cts);
- } else {
+ prefs_module_list_foreach(module->submodules, module_prefs_show, &child_cts);
+
+ /* keep the page count right */
+ cts->page = child_cts.page;
+
+ }
+ if(module->prefs) {
/*
- * No. Create a notebook page for it.
+ * Has preferences. Create a notebook page for it.
*/
/* Scrolled window */
@@ -383,10 +389,21 @@ module_prefs_show(module_t *module, gpointer user_data)
OBJECT_SET_DATA(frame, E_PAGE_ITER_KEY, gtk_tree_iter_copy(&iter));
#endif
- cts->page++;
+ cts->page++;
/* Show 'em what we got */
gtk_widget_show_all(main_sw);
+ } else {
+ /* show the blank page */
+
+#if GTK_MAJOR_VERSION < 2
+ gtk_ctree_node_set_row_data(GTK_CTREE(cts->tree), ct_node,
+ GINT_TO_POINTER(blank_page));
+#else
+ gtk_tree_store_set(model, &iter, 0, label_str, 1, blank_page, -1);
+#endif
+
+
}
return 0;
@@ -434,8 +451,10 @@ prefs_nb_page_add(GtkWidget *notebook, const gchar *title, GtkWidget *page, cons
frame = gtk_frame_new(title);
gtk_widget_show(frame);
- gtk_container_add(GTK_CONTAINER(frame), page);
- OBJECT_SET_DATA(prefs_w, page_key, page);
+ if(page) {
+ gtk_container_add(GTK_CONTAINER(frame), page);
+ OBJECT_SET_DATA(prefs_w, page_key, page);
+ }
gtk_notebook_append_page (GTK_NOTEBOOK(notebook), frame, NULL);
return frame;
@@ -518,6 +537,7 @@ prefs_cb(GtkWidget *w _U_, gpointer dummy _U_)
#else
store = gtk_tree_store_new(2, G_TYPE_STRING, G_TYPE_INT);
cts.tree = tree_view_new(GTK_TREE_MODEL(store));
+ cts.iter.stamp = 0; /* mark this as the toplevel */
OBJECT_SET_DATA(prefs_w, E_PREFSW_TREE_KEY, cts.tree);
gtk_tree_view_set_headers_visible(GTK_TREE_VIEW(cts.tree), FALSE);
selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(cts.tree));
@@ -545,6 +565,11 @@ prefs_cb(GtkWidget *w _U_, gpointer dummy _U_)
cts.page = 0;
+ /* Blank Page */
+ strcpy(label_str, "(No Specific Preferences)");
+ prefs_nb_page_add(prefs_nb, label_str, NULL, NULL);
+ blank_page = cts.page++;
+
/* GUI prefs */
strcpy(label_str, "User Interface");
prefs_nb_page_add(prefs_nb, label_str, gui_prefs_show(), E_GUI_PAGE_KEY);
@@ -1673,9 +1698,31 @@ module_search_properties(module_t *module, gpointer user_data)
p->module = module;
return 1; /* stops the search */
}
+
+ if(module->submodules)
+ return prefs_module_list_foreach(module->submodules, module_search_properties, p);
+
return 0;
}
+#if GTK_MAJOR_VERSION >= 2
+static void
+tree_expand_row(GtkTreeModel *model, GtkTreeView *tree_view, GtkTreeIter *iter)
+{
+ GtkTreeIter parent;
+ GtkTreePath *path;
+
+ /* expand the parent first */
+ if(gtk_tree_model_iter_parent(model, &parent, iter))
+ tree_expand_row(model, tree_view, &parent);
+
+ path = gtk_tree_model_get_path(model, iter);
+ gtk_tree_view_expand_row(tree_view, path, FALSE);
+ /*expand_tree(tree_view, &parent, NULL, NULL);*/
+
+ gtk_tree_path_free(path);
+}
+#endif
/* select a node in the tree view */
/* XXX - this is almost 100% copied from byte_view_select() in proto_draw.c,
@@ -1691,8 +1738,7 @@ tree_select_node(GtkWidget *tree, prefs_tree_iter *iter)
GtkTreeIter local_iter = *iter;
GtkTreeView *tree_view = GTK_TREE_VIEW(tree);
GtkTreeModel *model;
- GtkTreePath *first_path, *path;
- GtkTreeIter parent;
+ GtkTreePath *first_path;
#endif
#if GTK_MAJOR_VERSION < 2
@@ -1718,17 +1764,9 @@ tree_select_node(GtkWidget *tree, prefs_tree_iter *iter)
/* Expand our field's row */
first_path = gtk_tree_model_get_path(model, &local_iter);
- gtk_tree_view_expand_row(tree_view, first_path, FALSE);
- /*expand_tree(tree_view, &iter, NULL, NULL);*/
- /* ... and its parents */
- while (gtk_tree_model_iter_parent(model, &parent, &local_iter)) {
- path = gtk_tree_model_get_path(model, &parent);
- gtk_tree_view_expand_row(tree_view, path, FALSE);
- /*expand_tree(tree_view, &parent, NULL, NULL);*/
- local_iter = parent;
- gtk_tree_path_free(path);
- }
+ /* expand from the top down */
+ tree_expand_row(model, tree_view, &local_iter);
/* select our field's row */
gtk_tree_selection_select_path(gtk_tree_view_get_selection(tree_view),
@@ -1774,7 +1812,7 @@ properties_cb(GtkWidget *w, gpointer dummy)
XXX - should we just associate protocols with modules directly? */
p.title = title;
p.module = NULL;
- prefs_module_list_foreach(protocols_module->prefs, module_search_properties,
+ prefs_module_list_foreach(protocols_module->submodules, module_search_properties,
&p);
if (p.module == NULL) {
/* We didn't find it - that protocol probably has no preferences. */