summaryrefslogtreecommitdiffstats
path: root/gtk
diff options
context:
space:
mode:
authorJohn Stebbins <[email protected]>2018-06-12 12:09:59 -0700
committerJohn Stebbins <[email protected]>2018-06-12 12:09:59 -0700
commit43e589346b065eae3dca53a439ef873e8a271c7a (patch)
treefe1a5f851fa9b8dd982ef5af5122f911acb056b7 /gtk
parent5832b176ce662dc5f1f891c9039f8fa419e1cb2c (diff)
LinGui: change language lists from GtkListBox to GtkTreeView
The GtkTreeView is more flexible and more capable. Languages can be searched for in the GtkTreeView by focusing the widget and typing what you want to find. Double clicking an item in the list will add or remove it from the "selected" languages list in audio and subtitle track selection settings.
Diffstat (limited to 'gtk')
-rw-r--r--gtk/src/audiohandler.c302
-rw-r--r--gtk/src/audiohandler.h2
-rw-r--r--gtk/src/ghb.m416
-rw-r--r--gtk/src/hb-backend.c36
-rw-r--r--gtk/src/hb-backend.h3
-rw-r--r--gtk/src/subtitlehandler.c294
6 files changed, 451 insertions, 202 deletions
diff --git a/gtk/src/audiohandler.c b/gtk/src/audiohandler.c
index d4994463f..68a45ebe8 100644
--- a/gtk/src/audiohandler.c
+++ b/gtk/src/audiohandler.c
@@ -1986,70 +1986,154 @@ audio_def_setting_update(signal_user_data_t *ud, GtkWidget *widget)
}
}
+void
+audio_add_lang_iter(GtkTreeModel *tm, GtkTreeIter *iter, signal_user_data_t *ud)
+{
+ GtkTreeView * selected;
+ GtkTreeStore * selected_ts;
+ GtkTreeIter pos;
+ GtkTreePath * tp;
+ char * lang;
+ int index;
+ const iso639_lang_t * iso_lang;
+ GhbValue * glang, * alang_list;
+ GtkTreeSelection * tsel;
+
+ selected = GTK_TREE_VIEW(GHB_WIDGET(ud->builder, "audio_selected_lang"));
+ selected_ts = GTK_TREE_STORE(gtk_tree_view_get_model(selected));
+ tsel = gtk_tree_view_get_selection(selected);
+
+ // Add to UI selected language list box
+ gtk_tree_model_get(tm, iter, 0, &lang, 1, &index, -1);
+ gtk_tree_store_append(selected_ts, &pos, NULL);
+ gtk_tree_store_set(selected_ts, &pos, 0, lang, 1, index, -1);
+ g_free(lang);
+
+ // Select the item added to the selected list and make it
+ // visible in the scrolled window
+ tp = gtk_tree_model_get_path(GTK_TREE_MODEL(selected_ts), &pos);
+ gtk_tree_selection_select_iter(tsel, &pos);
+ gtk_tree_view_scroll_to_cell(selected, tp, NULL, FALSE, 0, 0);
+ gtk_tree_path_free(tp);
+
+ // Remove from UI available language list box
+ gtk_tree_store_remove(GTK_TREE_STORE(tm), iter);
+
+ // Add to preset language list
+ iso_lang = ghb_iso639_lookup_by_int(index);
+ glang = ghb_string_value_new(iso_lang->iso639_2);
+ alang_list = ghb_dict_get_value(ud->settings, "AudioLanguageList");
+ ghb_array_append(alang_list, glang);
+ ghb_clear_presets_selection(ud);
+}
+
+G_MODULE_EXPORT void
+audio_avail_lang_activated_cb(GtkTreeView *tv, GtkTreePath *tp,
+ GtkTreeViewColumn *column, signal_user_data_t *ud)
+{
+ GtkTreeIter iter;
+ GtkTreeModel * tm = gtk_tree_view_get_model(tv);
+
+ if (gtk_tree_model_get_iter(tm, &iter, tp))
+ {
+ audio_add_lang_iter(tm, &iter, ud);
+ }
+}
+
G_MODULE_EXPORT void
audio_add_lang_clicked_cb(GtkWidget *widget, signal_user_data_t *ud)
{
- GtkListBox *avail = GTK_LIST_BOX(GHB_WIDGET(ud->builder, "audio_avail_lang"));
- GtkListBox *selected = GTK_LIST_BOX(GHB_WIDGET(ud->builder, "audio_selected_lang"));
- GtkListBoxRow *row;
- GtkWidget *label;
+ GtkTreeView * avail;
+ GtkTreeModel * avail_tm;
+ GtkTreeSelection * tsel;
+ GtkTreeIter iter;
- row = gtk_list_box_get_selected_row(avail);
- if (row != NULL)
+ avail = GTK_TREE_VIEW(GHB_WIDGET(ud->builder, "audio_avail_lang"));
+ avail_tm = gtk_tree_view_get_model(avail);
+ tsel = gtk_tree_view_get_selection(avail);
+ if (gtk_tree_selection_get_selected(tsel, NULL, &iter))
{
- int idx;
- const iso639_lang_t *lang;
- GhbValue *glang, *alang_list;
+ audio_add_lang_iter(avail_tm, &iter, ud);
+ }
+}
- // Remove from UI available language list box
- label = gtk_bin_get_child(GTK_BIN(row));
- g_object_ref(G_OBJECT(label));
- gtk_widget_destroy(GTK_WIDGET(row));
- gtk_widget_show(label);
- // Add to UI selected language list box
- gtk_list_box_insert(selected, label, -1);
+void
+audio_remove_lang_iter(GtkTreeModel *tm, GtkTreeIter *iter,
+ signal_user_data_t *ud)
+{
+ GtkTreeView * avail;
+ GtkTreeStore * avail_ts;
+ GtkTreeIter pos, sibling;
+ char * lang;
+ int index;
+ GtkTreePath * tp = gtk_tree_model_get_path(tm, iter);
+ int * ind = gtk_tree_path_get_indices(tp);
+ int row = ind[0];
+ GhbValue * alang_list;
+ GtkTreeSelection * tsel;
+
+ gtk_tree_path_free(tp);
+ avail = GTK_TREE_VIEW(GHB_WIDGET(ud->builder, "audio_avail_lang"));
+ avail_ts = GTK_TREE_STORE(gtk_tree_view_get_model(avail));
+ tsel = gtk_tree_view_get_selection(avail);
- // Add to preset language list
- idx = (intptr_t)g_object_get_data(G_OBJECT(label), "lang_idx");
- lang = ghb_iso639_lookup_by_int(idx);
- glang = ghb_string_value_new(lang->iso639_2);
- alang_list = ghb_dict_get_value(ud->settings, "AudioLanguageList");
- ghb_array_append(alang_list, glang);
- ghb_clear_presets_selection(ud);
+ // Add to UI available language list box
+ gtk_tree_model_get(tm, iter, 0, &lang, 1, &index, -1);
+ if (ghb_find_lang_row(GTK_TREE_MODEL(avail_ts), &sibling, index))
+ {
+ gtk_tree_store_insert_before(avail_ts, &pos, NULL, &sibling);
}
+ else
+ {
+ gtk_tree_store_append(avail_ts, &pos, NULL);
+ }
+ gtk_tree_store_set(avail_ts, &pos, 0, lang, 1, index, -1);
+ g_free(lang);
+
+ // Select the item added to the available list and make it
+ // visible in the scrolled window
+ tp = gtk_tree_model_get_path(GTK_TREE_MODEL(avail_ts), &pos);
+ gtk_tree_selection_select_iter(tsel, &pos);
+ gtk_tree_view_scroll_to_cell(avail, tp, NULL, FALSE, 0, 0);
+ gtk_tree_path_free(tp);
+
+ // Remove from UI selected language list box
+ gtk_tree_store_remove(GTK_TREE_STORE(tm), iter);
+
+ // Remove from preset language list
+ alang_list = ghb_dict_get_value(ud->settings, "AudioLanguageList");
+ ghb_array_remove(alang_list, row);
+ ghb_clear_presets_selection(ud);
}
G_MODULE_EXPORT void
-audio_remove_lang_clicked_cb(GtkWidget *widget, signal_user_data_t *ud)
+audio_selected_lang_activated_cb(GtkTreeView *tv, GtkTreePath *tp,
+ GtkTreeViewColumn *column,
+ signal_user_data_t *ud)
{
+ GtkTreeIter iter;
+ GtkTreeModel * tm = gtk_tree_view_get_model(tv);
- GtkListBox *avail, *selected;
- GtkListBoxRow *row;
- GtkWidget *label;
-
- avail = GTK_LIST_BOX(GHB_WIDGET(ud->builder, "audio_avail_lang"));
- selected = GTK_LIST_BOX(GHB_WIDGET(ud->builder, "audio_selected_lang"));
- row = gtk_list_box_get_selected_row(selected);
- if (row != NULL)
+ if (gtk_tree_model_get_iter(tm, &iter, tp))
{
- gint index;
- GhbValue *alang_list;
-
- index = gtk_list_box_row_get_index(row);
+ audio_remove_lang_iter(tm, &iter, ud);
+ }
+}
- // Remove from UI selected language list box
- label = gtk_bin_get_child(GTK_BIN(row));
- g_object_ref(G_OBJECT(label));
- int idx = (intptr_t)g_object_get_data(G_OBJECT(label), "lang_idx");
- gtk_widget_destroy(GTK_WIDGET(row));
- gtk_widget_show(label);
- // Add to UI available language list box
- gtk_list_box_insert(avail, label, idx);
+G_MODULE_EXPORT void
+audio_remove_lang_clicked_cb(GtkWidget *widget, signal_user_data_t *ud)
+{
+ GtkTreeView * selected;
+ GtkTreeModel * selected_tm;
+ GtkTreeSelection * tsel;
+ GtkTreeIter iter;
- // Remove from preset language list
- alang_list = ghb_dict_get_value(ud->settings, "AudioLanguageList");
- ghb_array_remove(alang_list, index);
- ghb_clear_presets_selection(ud);
+ selected = GTK_TREE_VIEW(GHB_WIDGET(ud->builder, "audio_selected_lang"));
+ selected_tm = gtk_tree_view_get_model(selected);
+ tsel = gtk_tree_view_get_selection(selected);
+ if (gtk_tree_selection_get_selected(tsel, NULL, &iter))
+ {
+ audio_remove_lang_iter(selected_tm, &iter, ud);
}
}
@@ -2297,54 +2381,73 @@ audio_def_encode_setting_changed_cb(GtkWidget *widget, signal_user_data_t *ud)
ghb_clear_presets_selection(ud);
}
-GtkListBoxRow* ghb_find_lang_row(GtkListBox *list_box, int lang_idx)
+gboolean ghb_find_lang_row(GtkTreeModel *model, GtkTreeIter *iter, int lang_idx)
{
- GList *list, *link;
- GtkListBoxRow *result = NULL;
-
- list = link = gtk_container_get_children(GTK_CONTAINER(list_box));
- while (link != NULL)
+ if (gtk_tree_model_get_iter_first(model, iter))
{
- GtkListBoxRow *row = (GtkListBoxRow*)link->data;
- GtkWidget *label = gtk_bin_get_child(GTK_BIN(row));
- int idx = (intptr_t)g_object_get_data(G_OBJECT(label), "lang_idx");
- if (idx == lang_idx)
+ do
{
- result = row;
- break;
- }
- link = link->next;
- }
- g_list_free(list);
-
- return result;
-}
+ gint index;
-static void audio_def_lang_list_clear_cb(GtkWidget *row, gpointer data)
-{
- GtkListBox *avail = (GtkListBox*)data;
- GtkWidget *label = gtk_bin_get_child(GTK_BIN(row));
- g_object_ref(G_OBJECT(label));
- gtk_widget_destroy(GTK_WIDGET(row));
- gtk_widget_show(label);
- int idx = (intptr_t)g_object_get_data(G_OBJECT(label), "lang_idx");
- gtk_list_box_insert(avail, label, idx);
+ gtk_tree_model_get(model, iter, 1, &index, -1);
+ if (index >= lang_idx)
+ {
+ return TRUE;
+ }
+ } while (gtk_tree_model_iter_next(model, iter));
+ }
+ return FALSE;
}
static void
audio_def_selected_lang_list_clear(signal_user_data_t *ud)
{
- GtkListBox *avail, *selected;
- avail = GTK_LIST_BOX(GHB_WIDGET(ud->builder, "audio_avail_lang"));
- selected = GTK_LIST_BOX(GHB_WIDGET(ud->builder, "audio_selected_lang"));
- gtk_container_foreach(GTK_CONTAINER(selected),
- audio_def_lang_list_clear_cb, (gpointer)avail);
+ GtkTreeView * tv;
+ GtkTreeModel * selected_tm;
+ GtkTreeStore * avail_ts;
+ GtkTreeIter iter;
+
+ tv = GTK_TREE_VIEW(GHB_WIDGET(ud->builder, "audio_avail_lang"));
+ avail_ts = GTK_TREE_STORE(gtk_tree_view_get_model(tv));
+ tv = GTK_TREE_VIEW(GHB_WIDGET(ud->builder, "audio_selected_lang"));
+ selected_tm = gtk_tree_view_get_model(tv);
+ if (gtk_tree_model_get_iter_first(selected_tm, &iter))
+ {
+ do
+ {
+ gchar * lang;
+ gint index;
+ GtkTreeIter pos, sibling;
+
+ gtk_tree_model_get(selected_tm, &iter, 0, &lang, 1, &index, -1);
+ if (ghb_find_lang_row(GTK_TREE_MODEL(avail_ts), &sibling, index))
+ {
+ gtk_tree_store_insert_before(avail_ts, &pos, NULL, &sibling);
+ }
+ else
+ {
+ gtk_tree_store_append(avail_ts, &pos, NULL);
+ }
+ gtk_tree_store_set(avail_ts, &pos, 0, lang, 1, index, -1);
+ g_free(lang);
+ } while (gtk_tree_model_iter_next(selected_tm, &iter));
+ }
+ gtk_tree_store_clear(GTK_TREE_STORE(selected_tm));
}
static void
audio_def_lang_list_init(signal_user_data_t *ud)
{
- GhbValue *lang_list;
+ GhbValue * lang_list;
+ GtkTreeView * tv;
+ GtkTreeModel * avail;
+ GtkTreeStore * selected;
+ int ii, count;
+
+ tv = GTK_TREE_VIEW(GHB_WIDGET(ud->builder, "audio_avail_lang"));
+ avail = gtk_tree_view_get_model(tv);
+ tv = GTK_TREE_VIEW(GHB_WIDGET(ud->builder, "audio_selected_lang"));
+ selected = GTK_TREE_STORE(gtk_tree_view_get_model(tv));
// Clear selected languages.
audio_def_selected_lang_list_clear(ud);
@@ -2356,25 +2459,24 @@ audio_def_lang_list_init(signal_user_data_t *ud)
ghb_dict_set(ud->settings, "AudioLanguageList", lang_list);
}
- int ii, count;
count = ghb_array_len(lang_list);
for (ii = 0; ii < count; )
{
- GhbValue *lang_val = ghb_array_get(lang_list, ii);
- int idx = ghb_lookup_lang(lang_val);
+ GhbValue * lang_val = ghb_array_get(lang_list, ii);
+ int idx = ghb_lookup_lang(lang_val);
+ GtkTreeIter iter;
- GtkListBox *avail, *selected;
- GtkListBoxRow *row;
- avail = GTK_LIST_BOX(GHB_WIDGET(ud->builder, "audio_avail_lang"));
- selected = GTK_LIST_BOX(GHB_WIDGET(ud->builder, "audio_selected_lang"));
- row = ghb_find_lang_row(avail, idx);
- if (row)
+ if (ghb_find_lang_row(avail, &iter, idx))
{
- GtkWidget *label = gtk_bin_get_child(GTK_BIN(row));
- g_object_ref(G_OBJECT(label));
- gtk_widget_destroy(GTK_WIDGET(row));
- gtk_widget_show(label);
- gtk_list_box_insert(selected, label, -1);
+ gchar * lang;
+ gint index;
+ GtkTreeIter pos;
+
+ gtk_tree_model_get(avail, &iter, 0, &lang, 1, &index, -1);
+ gtk_tree_store_append(selected, &pos, NULL);
+ gtk_tree_store_set(selected, &pos, 0, lang, 1, index, -1);
+ g_free(lang);
+ gtk_tree_store_remove(GTK_TREE_STORE(avail), &iter);
ii++;
}
else
@@ -2427,10 +2529,12 @@ void ghb_audio_defaults_to_ui(signal_user_data_t *ud)
void ghb_init_audio_defaults_ui(signal_user_data_t *ud)
{
- GtkListBox *list_box;
+ GtkTreeView * tv;
- list_box = GTK_LIST_BOX(GHB_WIDGET(ud->builder, "audio_avail_lang"));
- ghb_init_lang_list_box(list_box);
+ tv = GTK_TREE_VIEW(GHB_WIDGET(ud->builder, "audio_avail_lang"));
+ ghb_init_lang_list(tv, ud);
+ tv = GTK_TREE_VIEW(GHB_WIDGET(ud->builder, "audio_selected_lang"));
+ ghb_init_lang_list_model(tv);
}
G_MODULE_EXPORT void
diff --git a/gtk/src/audiohandler.h b/gtk/src/audiohandler.h
index 45be4df0d..8c60f9e34 100644
--- a/gtk/src/audiohandler.h
+++ b/gtk/src/audiohandler.h
@@ -40,7 +40,7 @@ void ghb_audio_list_refresh_all(signal_user_data_t *ud);
char * ghb_format_quality( const char *prefix, int codec, double quality );
void ghb_init_audio_defaults_ui(signal_user_data_t *ud);
void ghb_audio_defaults_to_ui(signal_user_data_t *ud);
-GtkListBoxRow* ghb_find_lang_row(GtkListBox *list_box, int lang_idx);
+gboolean ghb_find_lang_row(GtkTreeModel *model, GtkTreeIter *iter, int idx);
void ghb_audio_title_change(signal_user_data_t *ud, gboolean title_valid);
void ghb_clear_audio_selection(GtkBuilder *builder);
gboolean ghb_audio_quality_enabled(const GhbValue *asettings);
diff --git a/gtk/src/ghb.m4 b/gtk/src/ghb.m4
index c38eb13a3..c3d061f9a 100644
--- a/gtk/src/ghb.m4
+++ b/gtk/src/ghb.m4
@@ -4265,10 +4265,12 @@ filter_output([
<property name="min_content_height">84</property>
<property name="vexpand">True</property>
<child>
- <object class="GtkListBox" id="audio_avail_lang">
+ <object class="GtkTreeView" id="audio_avail_lang">
<property name="visible">True</property>
+ <property name="headers-visible">False</property>
<property name="can_focus">True</property>
<property name="vexpand">True</property>
+ <signal name="row-activated" handler="audio_avail_lang_activated_cb" swapped="no"/>
</object>
</child>
</object>
@@ -4286,11 +4288,13 @@ filter_output([
<property name="hscrollbar_policy">GTK_POLICY_NEVER</property>
<property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property>
<child>
- <object class="GtkListBox" id="audio_selected_lang">
+ <object class="GtkTreeView" id="audio_selected_lang">
<property name="visible">True</property>
+ <property name="headers-visible">False</property>
<property name="can_focus">True</property>
<property name="tooltip_text" translatable="yes">Create a list of languages you would like to select audio for.
Tracks matching these languages will be selected using the chosen Selection Behavior.</property>
+ <signal name="row-activated" handler="audio_selected_lang_activated_cb" swapped="no"/>
</object>
</child>
</object>
@@ -5078,11 +5082,13 @@ filter_output([
<property name="vexpand">True</property>
<property name="halign">GTK_ALIGN_FILL</property>
<child>
- <object class="GtkListBox" id="subtitle_avail_lang">
+ <object class="GtkTreeView" id="subtitle_avail_lang">
<property name="visible">True</property>
+ <property name="headers-visible">False</property>
<property name="can_focus">True</property>
<property name="vexpand">True</property>
<property name="halign">GTK_ALIGN_FILL</property>
+ <signal name="row-activated" handler="subtitle_avail_lang_activated_cb" swapped="no"/>
</object>
</child>
</object>
@@ -5102,8 +5108,9 @@ filter_output([
<property name="vexpand">True</property>
<property name="halign">GTK_ALIGN_FILL</property>
<child>
- <object class="GtkListBox" id="subtitle_selected_lang">
+ <object class="GtkTreeView" id="subtitle_selected_lang">
<property name="visible">True</property>
+ <property name="headers-visible">False</property>
<property name="can_focus">True</property>
<property name="tooltip_text" translatable="yes">Create a list of languages you would like to select subtitles for.
Tracks matching these languages will be selected using the chosen Selection Behavior.
@@ -5112,6 +5119,7 @@ The first language in this list is your "preferred" language and will be used
for determining subtitle selection settings when there is foreign audio.</property>
<property name="vexpand">True</property>
<property name="halign">GTK_ALIGN_FILL</property>
+ <signal name="row-activated" handler="subtitle_selected_lang_activated_cb" swapped="no"/>
</object>
</child>
</object>
diff --git a/gtk/src/hb-backend.c b/gtk/src/hb-backend.c
index 433e21bfc..8a9ed99b0 100644
--- a/gtk/src/hb-backend.c
+++ b/gtk/src/hb-backend.c
@@ -2899,15 +2899,39 @@ ghb_lookup_combo_option(const gchar *name, const GhbValue *gval)
return result;
}
-void ghb_init_lang_list_box(GtkListBox *list_box)
+void ghb_init_lang_list_model(GtkTreeView *tv)
{
- int ii;
+ GtkTreeViewColumn * column;
+ GtkTreeStore * ts;
+ GtkCellRenderer * lang_cell;
+
+ // Store contains:
+ // 0 - Language string to display
+ // 1 - Index of language in the libhb language list
+ ts = gtk_tree_store_new(2, G_TYPE_STRING, G_TYPE_INT);
+ gtk_tree_view_set_model(tv, GTK_TREE_MODEL(ts));
+
+ lang_cell = gtk_cell_renderer_text_new();
+ column = gtk_tree_view_column_new();
+ gtk_tree_view_column_pack_start(column, lang_cell, FALSE);
+ gtk_tree_view_column_add_attribute(column, lang_cell, "markup", 0);
+ gtk_tree_view_append_column(tv, GTK_TREE_VIEW_COLUMN(column));
+}
+
+void ghb_init_lang_list(GtkTreeView *tv, signal_user_data_t *ud)
+{
+ GtkTreeIter iter;
+ GtkTreeStore * ts;
+ int ii;
+
+ ghb_init_lang_list_model(tv);
+ ts = GTK_TREE_STORE(gtk_tree_view_get_model(tv));
const iso639_lang_t *iso639;
for (iso639 = lang_get_next(NULL), ii = 0; iso639 != NULL;
iso639 = lang_get_next(iso639), ii++)
{
- const char *lang;
+ const char * lang;
if (ii == 0)
{
lang = _("Any");
@@ -2921,10 +2945,8 @@ void ghb_init_lang_list_box(GtkListBox *list_box)
{
lang = iso639->eng_name;
}
- GtkWidget *label = gtk_label_new(lang);
- g_object_set_data(G_OBJECT(label), "lang_idx", (gpointer)(intptr_t)ii);
- gtk_widget_show(label);
- gtk_list_box_insert(list_box, label, -1);
+ gtk_tree_store_append(ts, &iter, NULL);
+ gtk_tree_store_set(ts, &iter, 0, lang, 1, ii, -1);
}
}
diff --git a/gtk/src/hb-backend.h b/gtk/src/hb-backend.h
index 481aafbb2..7ebec5c1a 100644
--- a/gtk/src/hb-backend.h
+++ b/gtk/src/hb-backend.h
@@ -169,7 +169,8 @@ const char* ghb_lookup_filter_name(int filter_id, const char *short_name, int pr
gchar* ghb_get_tmp_dir();
gint ghb_find_closest_audio_samplerate(gint rate);
-void ghb_init_lang_list_box(GtkListBox *list_box);
+void ghb_init_lang_list_model(GtkTreeView *tv);
+void ghb_init_lang_list(GtkTreeView *tv, signal_user_data_t *ud);
void ghb_init_combo_box(GtkComboBox *combo);
void ghb_audio_encoder_opts_set(GtkComboBox *combo);
diff --git a/gtk/src/subtitlehandler.c b/gtk/src/subtitlehandler.c
index 3cf44689f..9297c0968 100644
--- a/gtk/src/subtitlehandler.c
+++ b/gtk/src/subtitlehandler.c
@@ -1329,80 +1329,137 @@ ghb_subtitle_set_pref_lang(GhbValue *settings)
}
}
-G_MODULE_EXPORT void
-subtitle_add_lang_clicked_cb(GtkWidget *widget, signal_user_data_t *ud)
+void
+subtitle_add_lang_iter(GtkTreeModel *tm, GtkTreeIter *iter,
+ signal_user_data_t *ud)
{
- GtkListBox *avail = GTK_LIST_BOX(GHB_WIDGET(ud->builder, "subtitle_avail_lang"));
- GtkListBox *selected = GTK_LIST_BOX(GHB_WIDGET(ud->builder, "subtitle_selected_lang"));
- GtkListBoxRow *row;
- GtkWidget *label;
-
- row = gtk_list_box_get_selected_row(avail);
- if (row != NULL)
- {
- int idx;
- const iso639_lang_t *lang;
- GhbValue *glang, *lang_list;
-
- // Remove from UI available language list box
- label = gtk_bin_get_child(GTK_BIN(row));
- g_object_ref(G_OBJECT(label));
- gtk_widget_destroy(GTK_WIDGET(row));
- gtk_widget_show(label);
- // Add to UI selected language list box
- gtk_list_box_insert(selected, label, -1);
-
- // Add to preset language list
- idx = (intptr_t)g_object_get_data(G_OBJECT(label), "lang_idx");
- lang = ghb_iso639_lookup_by_int(idx);
- glang = ghb_string_value_new(lang->iso639_2);
- lang_list = ghb_dict_get_value(ud->settings, "SubtitleLanguageList");
- if (ghb_array_len(lang_list) == 0)
- {
- subtitle_update_pref_lang(ud, lang);
- }
- ghb_array_append(lang_list, glang);
- ghb_clear_presets_selection(ud);
+ GtkTreeView * selected;
+ GtkTreeStore * selected_ts;
+ GtkTreeIter pos;
+ GtkTreePath * tp;
+ char * lang;
+ int index;
+ const iso639_lang_t * iso_lang;
+ GhbValue * glang, * slang_list;
+ GtkTreeSelection * tsel;
+
+ selected = GTK_TREE_VIEW(GHB_WIDGET(ud->builder, "subtitle_selected_lang"));
+ selected_ts = GTK_TREE_STORE(gtk_tree_view_get_model(selected));
+ tsel = gtk_tree_view_get_selection(selected);
+
+ // Add to UI selected language list box
+ gtk_tree_model_get(tm, iter, 0, &lang, 1, &index, -1);
+ gtk_tree_store_append(selected_ts, &pos, NULL);
+ gtk_tree_store_set(selected_ts, &pos, 0, lang, 1, index, -1);
+ g_free(lang);
+
+ // Select the item added to the selected list and make it
+ // visible in the scrolled window
+ tp = gtk_tree_model_get_path(GTK_TREE_MODEL(selected_ts), &pos);
+ gtk_tree_selection_select_iter(tsel, &pos);
+ gtk_tree_view_scroll_to_cell(selected, tp, NULL, FALSE, 0, 0);
+ gtk_tree_path_free(tp);
+
+ // Remove from UI available language list box
+ gtk_tree_store_remove(GTK_TREE_STORE(tm), iter);
+
+ // Add to preset language list
+ iso_lang = ghb_iso639_lookup_by_int(index);
+ glang = ghb_string_value_new(iso_lang->iso639_2);
+ slang_list = ghb_dict_get_value(ud->settings, "SubtitleLanguageList");
+ if (ghb_array_len(slang_list) == 0)
+ {
+ subtitle_update_pref_lang(ud, iso_lang);
}
+ ghb_array_append(slang_list, glang);
+ ghb_clear_presets_selection(ud);
}
G_MODULE_EXPORT void
-subtitle_remove_lang_clicked_cb(GtkWidget *widget, signal_user_data_t *ud)
+subtitle_avail_lang_activated_cb(GtkTreeView *tv, GtkTreePath *tp,
+ GtkTreeViewColumn *column,
+ signal_user_data_t *ud)
{
+ GtkTreeIter iter;
+ GtkTreeModel * tm = gtk_tree_view_get_model(tv);
- GtkListBox *avail, *selected;
- GtkListBoxRow *row;
- GtkWidget *label;
+ if (gtk_tree_model_get_iter(tm, &iter, tp))
+ {
+ subtitle_add_lang_iter(tm, &iter, ud);
+ }
+}
- avail = GTK_LIST_BOX(GHB_WIDGET(ud->builder, "subtitle_avail_lang"));
- selected = GTK_LIST_BOX(GHB_WIDGET(ud->builder, "subtitle_selected_lang"));
- row = gtk_list_box_get_selected_row(selected);
- if (row != NULL)
+G_MODULE_EXPORT void
+subtitle_add_lang_clicked_cb(GtkWidget *widget, signal_user_data_t *ud)
+{
+ GtkTreeView * avail;
+ GtkTreeModel * avail_tm;
+ GtkTreeSelection * tsel;
+ GtkTreeIter iter;
+
+ avail = GTK_TREE_VIEW(GHB_WIDGET(ud->builder, "subtitle_avail_lang"));
+ avail_tm = gtk_tree_view_get_model(avail);
+ tsel = gtk_tree_view_get_selection(avail);
+ if (gtk_tree_selection_get_selected(tsel, NULL, &iter))
{
- gint index;
- GhbValue *lang_list;
+ subtitle_add_lang_iter(avail_tm, &iter, ud);
+ }
+}
+
+void
+subtitle_remove_lang_iter(GtkTreeModel *tm, GtkTreeIter *iter,
+ signal_user_data_t *ud)
+{
+ GtkTreeView * avail;
+ GtkTreeStore * avail_ts;
+ GtkTreeIter pos, sibling;
+ char * lang;
+ int index;
+ GtkTreePath * tp = gtk_tree_model_get_path(tm, iter);
+ int * ind = gtk_tree_path_get_indices(tp);
+ int row = ind[0];
+ GhbValue * slang_list;
+ GtkTreeSelection * tsel;
+
+ gtk_tree_path_free(tp);
+ avail = GTK_TREE_VIEW(GHB_WIDGET(ud->builder, "subtitle_avail_lang"));
+ avail_ts = GTK_TREE_STORE(gtk_tree_view_get_model(avail));
+ tsel = gtk_tree_view_get_selection(avail);
- index = gtk_list_box_row_get_index(row);
+ // Add to UI available language list box
+ gtk_tree_model_get(tm, iter, 0, &lang, 1, &index, -1);
+ if (ghb_find_lang_row(GTK_TREE_MODEL(avail_ts), &sibling, index))
+ {
+ gtk_tree_store_insert_before(avail_ts, &pos, NULL, &sibling);
+ }
+ else
+ {
+ gtk_tree_store_append(avail_ts, &pos, NULL);
+ }
+ gtk_tree_store_set(avail_ts, &pos, 0, lang, 1, index, -1);
+ g_free(lang);
- // Remove from UI selected language list box
- label = gtk_bin_get_child(GTK_BIN(row));
- g_object_ref(G_OBJECT(label));
- int idx = (intptr_t)g_object_get_data(G_OBJECT(label), "lang_idx");
- gtk_widget_destroy(GTK_WIDGET(row));
- gtk_widget_show(label);
- // Add to UI available language list box
- gtk_list_box_insert(avail, label, idx);
+ // Select the item added to the available list and make it
+ // visible in the scrolled window
+ tp = gtk_tree_model_get_path(GTK_TREE_MODEL(avail_ts), &pos);
+ gtk_tree_selection_select_iter(tsel, &pos);
+ gtk_tree_view_scroll_to_cell(avail, tp, NULL, FALSE, 0, 0);
+ gtk_tree_path_free(tp);
- // Remove from preset language list
- lang_list = ghb_dict_get_value(ud->settings, "SubtitleLanguageList");
- ghb_array_remove(lang_list, index);
+ // Remove from UI selected language list box
+ gtk_tree_store_remove(GTK_TREE_STORE(tm), iter);
- ghb_clear_presets_selection(ud);
+ // Remove from preset language list
+ slang_list = ghb_dict_get_value(ud->settings, "SubtitleLanguageList");
+ ghb_array_remove(slang_list, row);
+ ghb_clear_presets_selection(ud);
- if (ghb_array_len(lang_list) > 0)
+ if (row == 0)
+ {
+ if (ghb_array_len(slang_list) > 0)
{
const iso639_lang_t *lang;
- GhbValue *entry = ghb_array_get(lang_list, 0);
+ GhbValue *entry = ghb_array_get(slang_list, 0);
lang = ghb_iso639_lookup_by_int(ghb_lookup_lang(entry));
subtitle_update_pref_lang(ud, lang);
}
@@ -1413,29 +1470,85 @@ subtitle_remove_lang_clicked_cb(GtkWidget *widget, signal_user_data_t *ud)
}
}
-static void subtitle_def_lang_list_clear_cb(GtkWidget *row, gpointer data)
+G_MODULE_EXPORT void
+subtitle_selected_lang_activated_cb(GtkTreeView *tv, GtkTreePath *tp,
+ GtkTreeViewColumn *column,
+ signal_user_data_t *ud)
{
- GtkListBox *avail = (GtkListBox*)data;
- GtkWidget *label = gtk_bin_get_child(GTK_BIN(row));
- g_object_ref(G_OBJECT(label));
- gtk_widget_destroy(GTK_WIDGET(row));
- gtk_widget_show(label);
- int idx = (intptr_t)g_object_get_data(G_OBJECT(label), "lang_idx");
- gtk_list_box_insert(avail, label, idx);
+ GtkTreeIter iter;
+ GtkTreeModel * tm = gtk_tree_view_get_model(tv);
+
+ if (gtk_tree_model_get_iter(tm, &iter, tp))
+ {
+ subtitle_remove_lang_iter(tm, &iter, ud);
+ }
+}
+
+G_MODULE_EXPORT void
+subtitle_remove_lang_clicked_cb(GtkWidget *widget, signal_user_data_t *ud)
+{
+ GtkTreeView * selected;
+ GtkTreeModel * selected_tm;
+ GtkTreeSelection * tsel;
+ GtkTreeIter iter;
+
+ selected = GTK_TREE_VIEW(GHB_WIDGET(ud->builder,
+ "subtitle_selected_lang"));
+ selected_tm = gtk_tree_view_get_model(selected);
+ tsel = gtk_tree_view_get_selection(selected);
+ if (gtk_tree_selection_get_selected(tsel, NULL, &iter))
+ {
+ subtitle_remove_lang_iter(selected_tm, &iter, ud);
+ }
}
static void subtitle_def_selected_lang_list_clear(signal_user_data_t *ud)
{
- GtkListBox *avail, *selected;
- avail = GTK_LIST_BOX(GHB_WIDGET(ud->builder, "subtitle_avail_lang"));
- selected = GTK_LIST_BOX(GHB_WIDGET(ud->builder, "subtitle_selected_lang"));
- gtk_container_foreach(GTK_CONTAINER(selected),
- subtitle_def_lang_list_clear_cb, (gpointer)avail);
+ GtkTreeView * tv;
+ GtkTreeModel * selected_tm;
+ GtkTreeStore * avail_ts;
+ GtkTreeIter iter;
+
+ tv = GTK_TREE_VIEW(GHB_WIDGET(ud->builder, "subtitle_avail_lang"));
+ avail_ts = GTK_TREE_STORE(gtk_tree_view_get_model(tv));
+ tv = GTK_TREE_VIEW(GHB_WIDGET(ud->builder,
+ "subtitle_selected_lang"));
+ selected_tm = gtk_tree_view_get_model(tv);
+ if (gtk_tree_model_get_iter_first(selected_tm, &iter))
+ {
+ do
+ {
+ char * lang;
+ gint index;
+ GtkTreeIter pos, sibling;
+
+ gtk_tree_model_get(selected_tm, &iter, 0, &lang, 1, &index, -1);
+ if (ghb_find_lang_row(GTK_TREE_MODEL(avail_ts), &sibling, index))
+ {
+ gtk_tree_store_insert_before(avail_ts, &pos, NULL, &sibling);
+ }
+ else
+ {
+ gtk_tree_store_append(avail_ts, &pos, NULL);
+ }
+ gtk_tree_store_set(avail_ts, &pos, 0, lang, 1, index, -1);
+ } while (gtk_tree_model_iter_next(selected_tm, &iter));
+ }
+ gtk_tree_store_clear(GTK_TREE_STORE(selected_tm));
}
static void subtitle_def_lang_list_init(signal_user_data_t *ud)
{
- GhbValue *lang_list;
+ GhbValue * lang_list;
+ GtkTreeView * tv;
+ GtkTreeModel * avail;
+ GtkTreeStore * selected;
+ int ii, count;
+
+ tv = GTK_TREE_VIEW(GHB_WIDGET(ud->builder, "subtitle_avail_lang"));
+ avail = gtk_tree_view_get_model(tv);
+ tv = GTK_TREE_VIEW(GHB_WIDGET(ud->builder, "subtitle_selected_lang"));
+ selected = GTK_TREE_STORE(gtk_tree_view_get_model(tv));
// Clear selected languages.
subtitle_def_selected_lang_list_clear(ud);
@@ -1447,31 +1560,30 @@ static void subtitle_def_lang_list_init(signal_user_data_t *ud)
ghb_dict_set(ud->settings, "SubtitleLanguageList", lang_list);
}
- int ii, count;
count = ghb_array_len(lang_list);
for (ii = 0; ii < count; )
{
- GhbValue *lang_val = ghb_array_get(lang_list, ii);
- int idx = ghb_lookup_lang(lang_val);
+ GhbValue * lang_val = ghb_array_get(lang_list, ii);
+ int idx = ghb_lookup_lang(lang_val);
+ GtkTreeIter iter;
+
if (ii == 0)
{
const iso639_lang_t *lang;
lang = ghb_iso639_lookup_by_int(idx);
subtitle_update_pref_lang(ud, lang);
}
-
- GtkListBox *avail, *selected;
- GtkListBoxRow *row;
- avail = GTK_LIST_BOX(GHB_WIDGET(ud->builder, "subtitle_avail_lang"));
- selected = GTK_LIST_BOX(GHB_WIDGET(ud->builder, "subtitle_selected_lang"));
- row = ghb_find_lang_row(avail, idx);
- if (row)
+ if (ghb_find_lang_row(avail, &iter, idx))
{
- GtkWidget *label = gtk_bin_get_child(GTK_BIN(row));
- g_object_ref(G_OBJECT(label));
- gtk_widget_destroy(GTK_WIDGET(row));
- gtk_widget_show(label);
- gtk_list_box_insert(selected, label, -1);
+ gchar * lang;
+ gint index;
+ GtkTreeIter pos;
+
+ gtk_tree_model_get(avail, &iter, 0, &lang, 1, &index, -1);
+ gtk_tree_store_append(selected, &pos, NULL);
+ gtk_tree_store_set(selected, &pos, 0, lang, 1, index, -1);
+ g_free(lang);
+ gtk_tree_store_remove(GTK_TREE_STORE(avail), &iter);
ii++;
}
else
@@ -1495,10 +1607,12 @@ void ghb_subtitle_defaults_to_ui(signal_user_data_t *ud)
void ghb_init_subtitle_defaults_ui(signal_user_data_t *ud)
{
- GtkListBox *list_box;
+ GtkTreeView * tv;
- list_box = GTK_LIST_BOX(GHB_WIDGET(ud->builder, "subtitle_avail_lang"));
- ghb_init_lang_list_box(list_box);
+ tv = GTK_TREE_VIEW(GHB_WIDGET(ud->builder, "subtitle_avail_lang"));
+ ghb_init_lang_list(tv, ud);
+ tv = GTK_TREE_VIEW(GHB_WIDGET(ud->builder, "subtitle_selected_lang"));
+ ghb_init_lang_list_model(tv);
}
G_MODULE_EXPORT void