diff --git a/src/file.c b/src/file.c index 3844abf..c10fb6f 100644 --- a/src/file.c +++ b/src/file.c @@ -7,7 +7,7 @@ #include "file.h" #include "stringhelper.h" -static void run_alsactl( +void run_alsactl( struct alsa_card *card, char *cmd, char *fn diff --git a/src/file.h b/src/file.h index f7253b7..088147d 100644 --- a/src/file.h +++ b/src/file.h @@ -3,6 +3,10 @@ #include +// Forward declaration of struct alsa_card +struct alsa_card; + void activate_load(GSimpleAction *action, GVariant *parameter, gpointer data); void activate_save(GSimpleAction *action, GVariant *parameter, gpointer data); void activate_sim(GSimpleAction *action, GVariant *parameter, gpointer data); +void run_alsactl(struct alsa_card *card, char *cmd, char *fn); diff --git a/src/window-routing.c b/src/window-routing.c index 5e7031b..59a36c4 100644 --- a/src/window-routing.c +++ b/src/window-routing.c @@ -9,6 +9,28 @@ #include "widget-boolean.h" #include "window-mixer.h" #include "window-routing.h" +#include "file.h" + +// Function to list .state files in .focusrite directory +static GList* list_state_files(const char *directory) { + GDir *dir; + const gchar *filename; + GList *file_list = NULL; + + dir = g_dir_open(directory, 0, NULL); + if (!dir) { + return NULL; + } + + while ((filename = g_dir_read_name(dir))) { + if (g_str_has_suffix(filename, ".state")) { + file_list = g_list_prepend(file_list, g_strdup(filename)); + } + } + + g_dir_close(dir); + return file_list; +} // clear all the routing sinks static void routing_preset_clear(struct alsa_card *card) { @@ -117,6 +139,13 @@ static void routing_preset( routing_preset_preamp(card); } else if (strcmp(s, "stereo_out") == 0) { routing_preset_stereo_out(card); + } else { + // Load the .state file + const char *focusrite_dir = g_build_path(G_DIR_SEPARATOR_S, g_get_home_dir(), ".focusrite", NULL); + char *filepath = g_build_filename(focusrite_dir, s, NULL); + run_alsactl(card, "restore", filepath); + g_free((gchar*)focusrite_dir); + g_free(filepath); } } @@ -128,6 +157,35 @@ static GtkWidget *make_preset_menu_button(struct alsa_card *card) { g_menu_append(menu, "Preamp", "routing.preset('preamp')"); g_menu_append(menu, "Stereo Out", "routing.preset('stereo_out')"); + // Add separator + g_menu_append_section(menu, NULL, G_MENU_MODEL(g_menu_new())); + + // Add .state files from .focusrite directory + const char *focusrite_dir = g_build_path(G_DIR_SEPARATOR_S, g_get_home_dir(), ".focusrite", NULL); + GList *state_files = list_state_files(focusrite_dir); + for (GList *l = state_files; l != NULL; l = l->next) { + gchar *basename = g_path_get_basename(l->data); + + // Remove the .state extension for the label + gchar *label = g_strdup(basename); + gchar *dot = g_strrstr(label, ".state"); + if (dot) { + *dot = '\0'; // Truncate the string at the .state position + } + + // Keep the full basename with the extension for the action + gchar *action = g_strdup_printf("routing.preset('%s')", basename); + + g_menu_append(menu, label, action); + + g_free(label); + g_free(action); + g_free(basename); + g_free(l->data); + } + g_list_free(state_files); + g_free((gchar*)focusrite_dir); + GtkWidget *button = gtk_menu_button_new(); gtk_widget_set_halign(button, GTK_ALIGN_CENTER); gtk_widget_set_valign(button, GTK_ALIGN_CENTER);