Added a new backend API, zoitechat_import_gtk3_theme_archive(const char *archive_path, GError **error), and exposed it in the common header so GTK setup code can call a shared import path instead of inlining extraction logic.

Updated the GTK3 import callback in setup.c to:

    open a file chooser titled Import GTK3 Theme ZIP,

    enforce a ZIP-focused chooser filter (*.zip, *.ZIP),

    call the new backend function,

    show success/failure dialogs through setup_theme_show_message,

    refresh the GTK3 theme list immediately after successful import.

Updated the GTK3 section button label to Import GTK3 Theme ZIP and added/used new translatable strings for the new button text and import messages.
This commit is contained in:
2026-02-26 00:16:05 -07:00
parent 4aeb5b5697
commit 4354aaa57a
3 changed files with 85 additions and 28 deletions

View File

@@ -330,6 +330,75 @@ cleanup:
return ok;
}
gboolean
zoitechat_import_gtk3_theme_archive (const char *archive_path, GError **error)
{
char *theme_root;
char *basename;
char *dot;
char *dest_dir;
char *argv[] = {"unzip", "-o", (char *)archive_path, "-d", NULL, NULL};
int status = 0;
gboolean ok;
if (!archive_path)
{
g_set_error (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT,
_("No GTK3 theme archive specified."));
return FALSE;
}
theme_root = g_build_filename (g_get_home_dir (), ".themes", NULL);
basename = g_path_get_basename (archive_path);
if (!basename || basename[0] == '\0')
{
g_free (theme_root);
g_free (basename);
g_set_error (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT,
_("Failed to determine GTK3 theme name."));
return FALSE;
}
dot = strrchr (basename, '.');
if (dot)
*dot = '\0';
dest_dir = g_build_filename (theme_root, basename, NULL);
if (g_mkdir_with_parents (dest_dir, 0700) != 0)
{
g_set_error (error, G_FILE_ERROR, g_file_error_from_errno (errno),
_("Failed to create GTK3 theme directory."));
g_free (dest_dir);
g_free (basename);
g_free (theme_root);
return FALSE;
}
argv[4] = dest_dir;
ok = g_spawn_sync (NULL, argv, NULL, G_SPAWN_SEARCH_PATH, NULL, NULL,
NULL, NULL, &status, error);
if (!ok)
{
g_free (dest_dir);
g_free (basename);
g_free (theme_root);
return FALSE;
}
if (!g_spawn_check_exit_status (status, error))
{
g_free (dest_dir);
g_free (basename);
g_free (theme_root);
return FALSE;
}
g_free (dest_dir);
g_free (basename);
g_free (theme_root);
return TRUE;
}
gboolean
zoitechat_import_theme (const char *path, GError **error)
{

View File

@@ -31,6 +31,7 @@
gboolean zoitechat_theme_path_from_arg (const char *arg, char **path_out);
gboolean zoitechat_import_theme (const char *path, GError **error);
gboolean zoitechat_import_gtk3_theme_archive (const char *archive_path, GError **error);
gboolean zoitechat_apply_theme (const char *theme_name, GError **error);
#ifdef USE_OPENSSL

View File

@@ -2109,22 +2109,24 @@ setup_theme_gtk3_import_cb (GtkWidget *button, gpointer user_data)
{
setup_theme_ui *ui = user_data;
GtkWidget *dialog;
GtkFileFilter *filter;
gint response;
char *archive_path;
char *basename;
char *dot;
char *dest_root;
char *dest_dir;
char *argv[] = {"unzip", "-o", NULL, "-d", NULL, NULL};
GError *error = NULL;
int status = 0;
dialog = gtk_file_chooser_dialog_new (_("Import GTK3 Theme"), GTK_WINDOW (setup_window),
dialog = gtk_file_chooser_dialog_new (_("Import GTK3 Theme ZIP"), GTK_WINDOW (setup_window),
GTK_FILE_CHOOSER_ACTION_OPEN,
_ ("_Cancel"), GTK_RESPONSE_CANCEL,
_ ("_Open"), GTK_RESPONSE_ACCEPT,
NULL);
filter = gtk_file_filter_new ();
gtk_file_filter_set_name (filter, _("ZIP archives"));
gtk_file_filter_add_pattern (filter, "*.zip");
gtk_file_filter_add_pattern (filter, "*.ZIP");
gtk_file_chooser_add_filter (GTK_FILE_CHOOSER (dialog), filter);
gtk_file_chooser_set_filter (GTK_FILE_CHOOSER (dialog), filter);
response = gtk_dialog_run (GTK_DIALOG (dialog));
if (response != GTK_RESPONSE_ACCEPT)
{
@@ -2138,38 +2140,23 @@ setup_theme_gtk3_import_cb (GtkWidget *button, gpointer user_data)
if (!archive_path)
return;
basename = g_path_get_basename (archive_path);
dot = strrchr (basename, '.');
if (dot)
*dot = '\0';
dest_root = g_build_filename (g_get_home_dir (), ".themes", NULL);
g_mkdir_with_parents (dest_root, 0700);
dest_dir = g_build_filename (dest_root, basename, NULL);
g_mkdir_with_parents (dest_dir, 0700);
argv[2] = archive_path;
argv[4] = dest_dir;
if (!g_spawn_sync (NULL, argv, NULL, G_SPAWN_SEARCH_PATH, NULL, NULL,
NULL, NULL, &status, &error)
|| !g_spawn_check_exit_status (status, &error))
if (!zoitechat_import_gtk3_theme_archive (archive_path, &error))
{
setup_theme_show_message (GTK_MESSAGE_ERROR,
error ? error->message : _("Failed to import GTK3 theme archive."));
error ? error->message : _("Failed to import GTK3 theme ZIP archive."));
g_clear_error (&error);
}
else
{
gtk_label_set_text (GTK_LABEL (ui->gtk3_status_label), _("GTK3 theme imported. Select it and click Apply GTK3 Theme."));
setup_theme_populate_gtk3 (ui);
gtk_label_set_text (GTK_LABEL (ui->gtk3_status_label), _("GTK3 theme ZIP imported successfully."));
setup_theme_show_message (GTK_MESSAGE_INFO, _("GTK3 theme ZIP imported successfully."));
}
g_free (dest_dir);
g_free (dest_root);
g_free (basename);
g_free (archive_path);
}
static void
setup_theme_gtk3_apply_cb (GtkWidget *button, gpointer user_data)
{
@@ -2280,7 +2267,7 @@ setup_create_theme_page (void)
g_signal_connect (G_OBJECT (ui->gtk3_combo), "changed",
G_CALLBACK (setup_theme_gtk3_selection_changed), ui);
ui->gtk3_import_button = gtk_button_new_with_mnemonic (_("_Import GTK3 Theme"));
ui->gtk3_import_button = gtk_button_new_with_mnemonic (_("_Import GTK3 Theme ZIP"));
gtk_box_pack_start (GTK_BOX (button_box), ui->gtk3_import_button, FALSE, FALSE, 0);
g_signal_connect (G_OBJECT (ui->gtk3_import_button), "clicked",
G_CALLBACK (setup_theme_gtk3_import_cb), ui);