tUse GtkTreeView in options dialog - vaccinewars - be a doctor and try to vaccinate the world
(HTM) git clone git://src.adamsgaard.dk/vaccinewars
(DIR) Log
(DIR) Files
(DIR) Refs
(DIR) README
(DIR) LICENSE
---
(DIR) commit d01de5ab48d16a145dd0e34df1148b0230a51489
(DIR) parent a2e4409e98b7c8c00b06fe2a29fc655bbef614f6
(HTM) Author: Ben Webb <ben@salilab.org>
Date: Sat, 21 Nov 2020 01:25:41 -0800
Use GtkTreeView in options dialog
Replace all use of the obsolete GtkCList class
in the options dialog with GtkTreeView and
associated classes.
Diffstat:
M src/gui_client/optdialog.c | 446 ++++++++++++++++++-------------
1 file changed, 257 insertions(+), 189 deletions(-)
---
(DIR) diff --git a/src/gui_client/optdialog.c b/src/gui_client/optdialog.c
t@@ -66,15 +66,11 @@ static void UpdateAllLists(void)
GSList *listpt;
for (listpt = clists; listpt; listpt = g_slist_next(listpt)) {
- GtkCList *clist = GTK_CLIST(listpt->data);
-
- if (clist->selection) {
- int row = GPOINTER_TO_INT(clist->selection->data);
-
- if (row >= 0) {
- gtk_clist_unselect_row(clist, row, 0);
- }
- }
+ GtkTreeView *tv = GTK_TREE_VIEW(listpt->data);
+ GtkTreeSelection *treesel = gtk_tree_view_get_selection(tv);
+ /* Force unselection, which should trigger *_sel_changed function to
+ copy widget data into configuration */
+ gtk_tree_selection_unselect_all(treesel);
}
}
t@@ -309,12 +305,19 @@ static void AddStructConfig(GtkWidget *table, int row, gchar *structname,
}
}
-static void swap_rows(GtkCList *clist, gint selrow, gint swaprow,
+static void swap_rows(GtkTreeView *tv, gint selrow, gint swaprow,
gchar *structname)
{
GSList *listpt;
+ GtkTreeIter seliter, swapiter;
+ GtkTreeModel *model = gtk_tree_view_get_model(tv);
+ GtkTreeSelection *treesel = gtk_tree_view_get_selection(tv);
+
+ g_assert(gtk_tree_model_iter_nth_child(model, &seliter, NULL, selrow));
+ g_assert(gtk_tree_model_iter_nth_child(model, &swapiter, NULL, swaprow));
- gtk_clist_unselect_row(clist, selrow, 0);
+ gtk_tree_selection_unselect_iter(treesel, &seliter);
+ gtk_list_store_swap(GTK_LIST_STORE(model), &seliter, &swapiter);
for (listpt = configlist; listpt; listpt = g_slist_next(listpt)) {
struct ConfigWidget *cwid = (struct ConfigWidget *)listpt->data;
t@@ -327,31 +330,57 @@ static void swap_rows(GtkCList *clist, gint selrow, gint swaprow,
cwid->data[selrow] = cwid->data[swaprow];
cwid->data[swaprow] = tmp;
- if (strcmp(gvar->Name, "Name") == 0) {
- gtk_clist_set_text(clist, selrow, 0, cwid->data[selrow]);
- gtk_clist_set_text(clist, swaprow, 0, cwid->data[swaprow]);
- }
}
}
- gtk_clist_select_row(clist, swaprow, 0);
+ gtk_tree_selection_select_iter(treesel, &seliter);
+}
+
+/* Return the index of the currently selected row, or -1 if none is selected.
+ This works only for lists (not trees) with GTK_SELECTION_SINGLE mode */
+static int get_tree_selection_row_index(GtkTreeSelection *treesel,
+ GtkTreeModel **model)
+{
+ int row = -1;
+ GList *selrows = gtk_tree_selection_get_selected_rows(treesel, model);
+ if (selrows) {
+ GtkTreePath *path = selrows->data;
+ gint depth;
+ gint *inds = gtk_tree_path_get_indices_with_depth(path, &depth);
+ g_assert(selrows->next == NULL);
+ g_assert(depth == 1);
+ row = inds[0];
+ }
+ g_list_free_full(selrows, (GDestroyNotify)gtk_tree_path_free);
+ return row;
}
static void list_delete(GtkWidget *widget, gchar *structname)
{
- GtkCList *clist;
- int minlistlength;
+ GtkTreeView *tv;
+ GtkTreeSelection *treesel;
+ GtkTreeModel *model;
+ int minlistlength, nrows, row;
+
+ tv = GTK_TREE_VIEW(g_object_get_data(G_OBJECT(widget), "treeview"));
+ g_assert(tv);
+ treesel = gtk_tree_view_get_selection(tv);
+ row = get_tree_selection_row_index(treesel, &model);
- clist = GTK_CLIST(g_object_get_data(G_OBJECT(widget), "clist"));
- g_assert(clist);
- minlistlength = GPOINTER_TO_INT(g_object_get_data(G_OBJECT(clist),
+ minlistlength = GPOINTER_TO_INT(g_object_get_data(G_OBJECT(model),
"minlistlength"));
+ nrows = gtk_tree_model_iter_n_children(model, NULL);
- if (clist->rows > minlistlength && clist->selection) {
+ if (nrows > minlistlength && row >= 0) {
+ GtkTreeIter iter;
GSList *listpt;
- int row = GPOINTER_TO_INT(clist->selection->data);
+ gboolean valid;
+ /* Prevent selection changed from reading deleted entry */
+ g_object_set_data(G_OBJECT(model), "oldsel", GINT_TO_POINTER(-1));
+ g_assert(gtk_tree_model_iter_nth_child(model, &iter, NULL, row));
+ gtk_tree_selection_unselect_iter(treesel, &iter);
+ valid = gtk_list_store_remove(GTK_LIST_STORE(model), &iter);
- gtk_clist_remove(clist, row);
for (listpt = configlist; listpt; listpt = g_slist_next(listpt)) {
struct ConfigWidget *cwid = (struct ConfigWidget *)listpt->data;
struct GLOBALS *gvar;
t@@ -368,21 +397,31 @@ static void list_delete(GtkWidget *widget, gchar *structname)
cwid->data = g_realloc(cwid->data, sizeof(gchar *) * cwid->maxindex);
}
}
+ if (valid) {
+ gtk_tree_selection_select_iter(treesel, &iter);
+ }
}
}
static void list_new(GtkWidget *widget, gchar *structname)
{
- GtkCList *clist;
+ GtkTreeView *tv;
+ GtkListStore *store;
+ GtkTreeSelection *treesel;
+ GtkTreeIter iter;
int row;
GSList *listpt;
- gchar *text[3];
+ gchar *newname;
- clist = GTK_CLIST(g_object_get_data(G_OBJECT(widget), "clist"));
- g_assert(clist);
+ tv = GTK_TREE_VIEW(g_object_get_data(G_OBJECT(widget), "treeview"));
+ g_assert(tv);
+ treesel = gtk_tree_view_get_selection(tv);
+ store = GTK_LIST_STORE(gtk_tree_view_get_model(tv));
- text[0] = g_strdup_printf(_("New %s"), structname);
- row = gtk_clist_append(clist, text);
+ newname = g_strdup_printf(_("New %s"), structname);
+ gtk_list_store_append(store, &iter);
+ gtk_list_store_set(store, &iter, 0, newname, -1);
+ row = gtk_tree_model_iter_n_children(GTK_TREE_MODEL(store), NULL) - 1;
for (listpt = configlist; listpt; listpt = g_slist_next(listpt)) {
struct ConfigWidget *cwid = (struct ConfigWidget *)listpt->data;
t@@ -394,160 +433,165 @@ static void list_new(GtkWidget *widget, gchar *structname)
g_assert(cwid->maxindex == row + 1);
cwid->data = g_realloc(cwid->data, sizeof(gchar *) * cwid->maxindex);
if (strcmp(gvar->Name, "Name") == 0) {
- cwid->data[row] = g_strdup(text[0]);
+ cwid->data[row] = g_strdup(newname);
} else {
cwid->data[row] = g_strdup("");
}
}
}
- g_free(text[0]);
+ g_free(newname);
- gtk_clist_select_row(clist, row, 0);
+ gtk_tree_selection_select_iter(treesel, &iter);
}
static void list_up(GtkWidget *widget, gchar *structname)
{
- GtkCList *clist;
-
- clist = GTK_CLIST(g_object_get_data(G_OBJECT(widget), "clist"));
- g_assert(clist);
+ GtkTreeView *tv;
+ GtkTreeSelection *treesel;
+ int row;
- if (clist->selection) {
- int row = GPOINTER_TO_INT(clist->selection->data);
+ tv = GTK_TREE_VIEW(g_object_get_data(G_OBJECT(widget), "treeview"));
+ g_assert(tv);
+ treesel = gtk_tree_view_get_selection(tv);
+ row = get_tree_selection_row_index(treesel, NULL);
- if (row > 0) {
- swap_rows(clist, row, row - 1, structname);
- }
+ if (row > 0) {
+ swap_rows(tv, row, row - 1, structname);
}
}
static void list_down(GtkWidget *widget, gchar *structname)
{
- GtkCList *clist;
-
- clist = GTK_CLIST(g_object_get_data(G_OBJECT(widget), "clist"));
- g_assert(clist);
-
- if (clist->selection) {
- int row = GPOINTER_TO_INT(clist->selection->data);
- int numrows = clist->rows;
-
- if (row < numrows - 1 && row >= 0) {
- swap_rows(clist, row, row + 1, structname);
- }
+ GtkTreeView *tv;
+ GtkTreeSelection *treesel;
+ GtkTreeModel *model;
+ int row, nrows;
+
+ tv = GTK_TREE_VIEW(g_object_get_data(G_OBJECT(widget), "treeview"));
+ g_assert(tv);
+ treesel = gtk_tree_view_get_selection(tv);
+ row = get_tree_selection_row_index(treesel, &model);
+ nrows = gtk_tree_model_iter_n_children(model, NULL);
+
+ if (row < nrows - 1 && row >= 0) {
+ swap_rows(tv, row, row + 1, structname);
}
}
-static void list_row_select(GtkCList *clist, gint row, gint column,
- GdkEvent *event, gchar *structname)
+static void list_sel_changed(GtkTreeSelection *treesel, gpointer data)
{
- GSList *listpt;
+ GtkTreeModel *model;
GtkWidget *delbut, *upbut, *downbut;
- int minlistlength;
-
- minlistlength = GPOINTER_TO_INT(g_object_get_data(G_OBJECT(clist),
- "minlistlength"));
- delbut = GTK_WIDGET(g_object_get_data(G_OBJECT(clist), "delete"));
- upbut = GTK_WIDGET(g_object_get_data(G_OBJECT(clist), "up"));
- downbut = GTK_WIDGET(g_object_get_data(G_OBJECT(clist), "down"));
- g_assert(delbut && upbut && downbut);
- gtk_widget_set_sensitive(delbut, clist->rows > minlistlength);
- gtk_widget_set_sensitive(upbut, row > 0);
- gtk_widget_set_sensitive(downbut, row < clist->rows - 1);
-
- for (listpt = configlist; listpt; listpt = g_slist_next(listpt)) {
- struct ConfigWidget *conf = (struct ConfigWidget *)listpt->data;
- struct GLOBALS *gvar;
-
- gvar = &Globals[conf->globind];
-
- if (gvar->NameStruct && strcmp(structname, gvar->NameStruct) == 0) {
- if (gvar->BoolVal) {
- gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(conf->widget),
- conf->data[row] != NULL);
- } else {
- gtk_entry_set_text(GTK_ENTRY(conf->widget), conf->data[row]);
- }
- }
- }
-}
-
-static void list_row_unselect(GtkCList *clist, gint row, gint column,
- GdkEvent *event, gchar *structname)
-{
+ int minlistlength, nrows, row, oldsel;
GSList *listpt;
- GtkWidget *delbut, *upbut, *downbut;
+ gchar *structname = data;
- delbut = GTK_WIDGET(g_object_get_data(G_OBJECT(clist), "delete"));
- upbut = GTK_WIDGET(g_object_get_data(G_OBJECT(clist), "up"));
- downbut = GTK_WIDGET(g_object_get_data(G_OBJECT(clist), "down"));
+ row = get_tree_selection_row_index(treesel, &model);
+ nrows = gtk_tree_model_iter_n_children(model, NULL);
+
+ delbut = GTK_WIDGET(g_object_get_data(G_OBJECT(model), "delete"));
+ upbut = GTK_WIDGET(g_object_get_data(G_OBJECT(model), "up"));
+ downbut = GTK_WIDGET(g_object_get_data(G_OBJECT(model), "down"));
+ oldsel = GPOINTER_TO_INT(g_object_get_data(G_OBJECT(model), "oldsel"));
g_assert(delbut && upbut && downbut);
- gtk_widget_set_sensitive(delbut, FALSE);
- gtk_widget_set_sensitive(upbut, FALSE);
- gtk_widget_set_sensitive(downbut, FALSE);
+ minlistlength = GPOINTER_TO_INT(g_object_get_data(G_OBJECT(model),
+ "minlistlength"));
+ gtk_widget_set_sensitive(delbut, nrows > minlistlength);
+ gtk_widget_set_sensitive(upbut, row > 0);
+ gtk_widget_set_sensitive(downbut, row < nrows - 1);
- for (listpt = configlist; listpt; listpt = g_slist_next(listpt)) {
- struct ConfigWidget *conf = (struct ConfigWidget *)listpt->data;
- struct GLOBALS *gvar;
+ /* Store any edited data from old-selected row */
+ if (oldsel >= 0) {
+ for (listpt = configlist; listpt; listpt = g_slist_next(listpt)) {
+ struct ConfigWidget *conf = (struct ConfigWidget *)listpt->data;
+ struct GLOBALS *gvar;
- gvar = &Globals[conf->globind];
+ gvar = &Globals[conf->globind];
- if (gvar->NameStruct && strcmp(structname, gvar->NameStruct) == 0) {
- g_free(conf->data[row]);
- conf->data[row] = NULL;
+ if (gvar->NameStruct && strcmp(structname, gvar->NameStruct) == 0) {
+ g_free(conf->data[oldsel]);
+ conf->data[oldsel] = NULL;
- if (gvar->BoolVal) {
- if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(conf->widget))) {
- conf->data[row] = g_strdup("1");
+ if (gvar->BoolVal) {
+ if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(conf->widget))) {
+ conf->data[oldsel] = g_strdup("1");
+ }
+ } else {
+ conf->data[oldsel] = gtk_editable_get_chars(
+ GTK_EDITABLE(conf->widget), 0, -1);
+ gtk_entry_set_text(GTK_ENTRY(conf->widget), "");
+ }
+ if (strcmp(gvar->Name, "Name") == 0) {
+ GtkTreeIter ositer;
+ g_assert(gtk_tree_model_iter_nth_child(model, &ositer, NULL, oldsel));
+ gtk_list_store_set(GTK_LIST_STORE(model), &ositer, 0,
+ conf->data[oldsel], -1);
}
- } else {
- conf->data[row] = gtk_editable_get_chars(GTK_EDITABLE(conf->widget),
- 0, -1);
- gtk_entry_set_text(GTK_ENTRY(conf->widget), "");
- }
- if (strcmp(gvar->Name, "Name") == 0) {
- gtk_clist_set_text(clist, row, 0, conf->data[row]);
}
}
}
-}
+ g_object_set_data(G_OBJECT(model), "oldsel", GINT_TO_POINTER(row));
-static void sound_row_select(GtkCList *clist, gint row, gint column,
- GdkEvent *event, gpointer data)
-{
- GtkWidget *entry;
- int globind;
- gchar **text;
+ /* Update widgets with selected row */
+ if (row >= 0) {
+ for (listpt = configlist; listpt; listpt = g_slist_next(listpt)) {
+ struct ConfigWidget *conf = (struct ConfigWidget *)listpt->data;
+ struct GLOBALS *gvar;
- entry = GTK_WIDGET(g_object_get_data(G_OBJECT(clist), "entry"));
- globind = GPOINTER_TO_INT(gtk_clist_get_row_data(clist, row));
- g_assert(globind >=0 && globind < NUMGLOB);
+ gvar = &Globals[conf->globind];
- text = GetGlobalString(globind, 0);
- gtk_entry_set_text(GTK_ENTRY(entry), *text);
+ if (gvar->NameStruct && strcmp(structname, gvar->NameStruct) == 0) {
+ if (gvar->BoolVal) {
+ gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(conf->widget),
+ conf->data[row] != NULL);
+ } else {
+ gtk_entry_set_text(GTK_ENTRY(conf->widget), conf->data[row]);
+ }
+ }
+ }
+ }
}
-static void sound_row_unselect(GtkCList *clist, gint row, gint column,
- GdkEvent *event, gpointer data)
+static void sound_sel_changed(GtkTreeSelection *treesel, gpointer data)
{
+ GtkTreeModel *model;
+ GtkTreeIter iter;
GtkWidget *entry;
- int globind;
- gchar *text, **oldtext;
-
- entry = GTK_WIDGET(g_object_get_data(G_OBJECT(clist), "entry"));
- globind = GPOINTER_TO_INT(gtk_clist_get_row_data(clist, row));
- g_assert(globind >=0 && globind < NUMGLOB);
+ int row, oldsel, globind;
+
+ row = get_tree_selection_row_index(treesel, &model);
+ oldsel = GPOINTER_TO_INT(g_object_get_data(G_OBJECT(model), "oldsel"));
+ entry = GTK_WIDGET(g_object_get_data(G_OBJECT(model), "entry"));
+
+ /* Store any edited data from old-selected row */
+ if (oldsel >= 0) {
+ gchar *text, **oldtext;
+ g_assert(gtk_tree_model_iter_nth_child(model, &iter, NULL, oldsel));
+ gtk_tree_model_get(model, &iter, 2, &globind, -1);
+ g_assert(globind >=0 && globind < NUMGLOB);
+
+ text = gtk_editable_get_chars(GTK_EDITABLE(entry), 0, -1);
+ oldtext = GetGlobalString(globind, 0);
+ g_assert(text && oldtext);
+ if (strcmp(text, *oldtext) != 0) {
+ AssignName(GetGlobalString(globind, 0), text);
+ Globals[globind].Modified = TRUE;
+ }
+ gtk_entry_set_text(GTK_ENTRY(entry), "");
+ g_free(text);
+ }
- text = gtk_editable_get_chars(GTK_EDITABLE(entry), 0, -1);
- oldtext = GetGlobalString(globind, 0);
- g_assert(text && oldtext);
- if (strcmp(text, *oldtext) != 0) {
- AssignName(GetGlobalString(globind, 0), text);
- Globals[globind].Modified = TRUE;
+ g_object_set_data(G_OBJECT(model), "oldsel", GINT_TO_POINTER(row));
+ /* Update new selection */
+ if (row >= 0) {
+ gchar **text;
+ g_assert(gtk_tree_model_iter_nth_child(model, &iter, NULL, row));
+ gtk_tree_model_get(model, &iter, 2, &globind, -1);
+ g_assert(globind >=0 && globind < NUMGLOB);
+ text = GetGlobalString(globind, 0);
+ gtk_entry_set_text(GTK_ENTRY(entry), *text);
}
- gtk_entry_set_text(GTK_ENTRY(entry), "");
- g_free(text);
}
static void BrowseSound(GtkWidget *entry)
t@@ -622,8 +666,12 @@ static void FinishOptDialog(GtkWidget *widget, gpointer data)
static GtkWidget *CreateList(gchar *structname, struct ConfigMembers *members)
{
- GtkWidget *hbox, *vbox, *hbbox, *clist, *scrollwin, *button, *table;
- gchar *titles[3];
+ GtkWidget *hbox, *vbox, *hbbox, *tv, *scrollwin, *button, *table;
+ GtkTreeSelection *treesel;
+ GtkListStore *store;
+ GtkCellRenderer *renderer;
+ GtkTreeIter iter;
+
int ind, minlistlength = 0;
gint i, nummembers;
struct GLOBALS *gvar;
t@@ -650,38 +698,44 @@ static GtkWidget *CreateList(gchar *structname, struct ConfigMembers *members)
vbox = gtk_vbox_new(FALSE, 5);
- titles[0] = structname;
- clist = gtk_scrolled_clist_new_with_titles(1, titles, &scrollwin);
+ tv = gtk_scrolled_tree_view_new(&scrollwin);
+ store = gtk_list_store_new(1, G_TYPE_STRING);
+ gtk_tree_view_set_model(GTK_TREE_VIEW(tv), GTK_TREE_MODEL(store));
+ renderer = gtk_cell_renderer_text_new();
+ gtk_tree_view_insert_column_with_attributes(
+ GTK_TREE_VIEW(tv), -1, structname, renderer, "text", 0, NULL);
+ g_object_unref(store);
+ gtk_tree_view_set_headers_clickable(GTK_TREE_VIEW(tv), FALSE);
- g_signal_connect(G_OBJECT(clist), "select_row",
- G_CALLBACK(list_row_select), structname);
- g_signal_connect(G_OBJECT(clist), "unselect_row",
- G_CALLBACK(list_row_unselect), structname);
- gtk_clist_column_titles_passive(GTK_CLIST(clist));
- gtk_clist_set_selection_mode(GTK_CLIST(clist), GTK_SELECTION_SINGLE);
- gtk_clist_set_auto_sort(GTK_CLIST(clist), FALSE);
+ treesel = gtk_tree_view_get_selection(GTK_TREE_VIEW(tv));
+ g_signal_connect(G_OBJECT(treesel), "changed", G_CALLBACK(list_sel_changed),
+ structname);
+ gtk_tree_selection_set_mode(treesel, GTK_SELECTION_SINGLE);
+ gtk_tree_sortable_set_sort_column_id(GTK_TREE_SORTABLE(store),
+ GTK_TREE_SORTABLE_UNSORTED_SORT_COLUMN_ID, GTK_SORT_ASCENDING);
- clists = g_slist_append(clists, clist);
+ clists = g_slist_append(clists, tv);
for (i = 1; i <= *gvar->MaxIndex; i++) {
- titles[0] = *GetGlobalString(ind, i);
- gtk_clist_append(GTK_CLIST(clist), titles);
+ gtk_list_store_append(store, &iter);
+ gtk_list_store_set(store, &iter, 0, *GetGlobalString(ind, i), -1);
}
gtk_box_pack_start(GTK_BOX(vbox), scrollwin, TRUE, TRUE, 0);
hbbox = gtk_hbox_new(TRUE, 5);
+ g_object_set_data(G_OBJECT(store), "oldsel", GINT_TO_POINTER(-1));
button = gtk_button_new_with_label(_("New"));
- g_object_set_data(G_OBJECT(button), "clist", clist);
+ g_object_set_data(G_OBJECT(button), "treeview", tv);
g_signal_connect(G_OBJECT(button), "clicked",
G_CALLBACK(list_new), structname);
gtk_box_pack_start(GTK_BOX(hbbox), button, TRUE, TRUE, 0);
button = gtk_button_new_with_label(_("Delete"));
gtk_widget_set_sensitive(button, FALSE);
- g_object_set_data(G_OBJECT(button), "clist", clist);
- g_object_set_data(G_OBJECT(clist), "delete", button);
- g_object_set_data(G_OBJECT(clist), "minlistlength",
+ g_object_set_data(G_OBJECT(button), "treeview", tv);
+ g_object_set_data(G_OBJECT(store), "delete", button);
+ g_object_set_data(G_OBJECT(store), "minlistlength",
GINT_TO_POINTER(minlistlength));
g_signal_connect(G_OBJECT(button), "clicked",
G_CALLBACK(list_delete), structname);
t@@ -689,16 +743,16 @@ static GtkWidget *CreateList(gchar *structname, struct ConfigMembers *members)
button = gtk_button_new_with_label(_("Up"));
gtk_widget_set_sensitive(button, FALSE);
- g_object_set_data(G_OBJECT(button), "clist", clist);
- g_object_set_data(G_OBJECT(clist), "up", button);
+ g_object_set_data(G_OBJECT(button), "treeview", tv);
+ g_object_set_data(G_OBJECT(store), "up", button);
g_signal_connect(G_OBJECT(button), "clicked",
G_CALLBACK(list_up), structname);
gtk_box_pack_start(GTK_BOX(hbbox), button, TRUE, TRUE, 0);
button = gtk_button_new_with_label(_("Down"));
gtk_widget_set_sensitive(button, FALSE);
- g_object_set_data(G_OBJECT(button), "clist", clist);
- g_object_set_data(G_OBJECT(clist), "down", button);
+ g_object_set_data(G_OBJECT(button), "treeview", tv);
+ g_object_set_data(G_OBJECT(store), "down", button);
g_signal_connect(G_OBJECT(button), "clicked",
G_CALLBACK(list_down), structname);
gtk_box_pack_start(GTK_BOX(hbbox), button, TRUE, TRUE, 0);
t@@ -720,34 +774,40 @@ static GtkWidget *CreateList(gchar *structname, struct ConfigMembers *members)
return hbox;
}
-static void FillSoundsList(GtkCList *clist)
+static void FillSoundsList(GtkTreeView *tv)
{
- gchar *rowtext[2];
- gint i, row;
+ GtkListStore *store;
+ GtkTreeIter iter;
+ gint i;
+
+ /* Don't update the widget until we're done */
+ store = GTK_LIST_STORE(gtk_tree_view_get_model(tv));
+ g_object_ref(store);
+ gtk_tree_view_set_model(tv, NULL);
- gtk_clist_freeze(clist);
- gtk_clist_clear(clist);
+ gtk_list_store_clear(store);
for (i = 0; i < NUMGLOB; i++) {
if (strlen(Globals[i].Name) > 7
&& strncmp(Globals[i].Name, "Sounds.", 7) == 0) {
- rowtext[0] = &Globals[i].Name[7];
- rowtext[1] = _(Globals[i].Help);
- row = gtk_clist_append(clist, rowtext);
- gtk_clist_set_row_data(clist, row, GINT_TO_POINTER(i));
+ gtk_list_store_append(store, &iter);
+ gtk_list_store_set(store, &iter, 0, &Globals[i].Name[7],
+ 1, _(Globals[i].Help), 2, i, -1);
}
}
- gtk_clist_thaw(clist);
+ gtk_tree_view_set_model(tv, GTK_TREE_MODEL(store));
}
void OptDialog(GtkWidget *widget, gpointer data)
{
GtkWidget *dialog, *notebook, *table, *label, *check, *entry;
- GtkWidget *hbox, *vbox, *vbox2, *hsep, *button, *hbbox, *clist;
+ GtkWidget *hbox, *vbox, *vbox2, *hsep, *button, *hbbox, *tv;
GtkWidget *scrollwin;
GtkAccelGroup *accel_group;
gchar *sound_titles[2];
- int width;
+ GtkCellRenderer *renderer;
+ GtkListStore *store;
+ GtkTreeSelection *treesel;
struct ConfigMembers locmembers[] = {
{ N_("Police presence"), "PolicePresence" },
t@@ -943,16 +1003,27 @@ void OptDialog(GtkWidget *widget, gpointer data)
sound_titles[0] = _("Sound name");
sound_titles[1] = _("Description");
- clist = gtk_scrolled_clist_new_with_titles(2, sound_titles, &scrollwin);
- gtk_clist_column_titles_passive(GTK_CLIST(clist));
- gtk_clist_set_selection_mode(GTK_CLIST(clist), GTK_SELECTION_SINGLE);
- FillSoundsList(GTK_CLIST(clist));
- g_signal_connect(G_OBJECT(clist), "select_row",
- G_CALLBACK(sound_row_select), NULL);
- g_signal_connect(G_OBJECT(clist), "unselect_row",
- G_CALLBACK(sound_row_unselect), NULL);
-
- clists = g_slist_append(clists, clist);
+ tv = gtk_scrolled_tree_view_new(&scrollwin);
+ store = gtk_list_store_new(3, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_INT);
+ g_object_set_data(G_OBJECT(store), "oldsel", GINT_TO_POINTER(-1));
+ gtk_tree_view_set_model(GTK_TREE_VIEW(tv), GTK_TREE_MODEL(store));
+ renderer = gtk_cell_renderer_text_new();
+ gtk_tree_view_insert_column_with_attributes(
+ GTK_TREE_VIEW(tv), -1, sound_titles[0], renderer,
+ "text", 0, NULL);
+ gtk_tree_view_insert_column_with_attributes(
+ GTK_TREE_VIEW(tv), -1, sound_titles[1], renderer,
+ "text", 1, NULL);
+ g_object_unref(store);
+ gtk_tree_view_set_headers_clickable(GTK_TREE_VIEW(tv), FALSE);
+ treesel = gtk_tree_view_get_selection(GTK_TREE_VIEW(tv));
+ gtk_tree_selection_set_mode(treesel, GTK_SELECTION_SINGLE);
+
+ FillSoundsList(GTK_TREE_VIEW(tv));
+ g_signal_connect(G_OBJECT(treesel), "changed",
+ G_CALLBACK(sound_sel_changed), NULL);
+
+ clists = g_slist_append(clists, tv);
gtk_box_pack_start(GTK_BOX(vbox2), scrollwin, TRUE, TRUE, 0);
t@@ -961,7 +1032,7 @@ void OptDialog(GtkWidget *widget, gpointer data)
gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0);
entry = gtk_entry_new();
- g_object_set_data(G_OBJECT(clist), "entry", entry);
+ g_object_set_data(G_OBJECT(store), "entry", entry);
gtk_box_pack_start(GTK_BOX(hbox), entry, TRUE, TRUE, 0);
button = gtk_button_new_with_label(_("Browse..."));
t@@ -1011,7 +1082,4 @@ void OptDialog(GtkWidget *widget, gpointer data)
gtk_container_add(GTK_CONTAINER(dialog), vbox);
gtk_widget_show_all(dialog);
-
- width = gtk_clist_optimal_column_width(GTK_CLIST(clist), 0);
- gtk_clist_set_column_width(GTK_CLIST(clist), 0, width);
}