From cfda8297cc4432a77e3f7e8679753a908e9f5759 Mon Sep 17 00:00:00 2001 From: Paul Buetow Date: Tue, 21 Jul 2026 18:39:47 +0300 Subject: enhance: wire up GEGL image filters (a cycle / s save) + fix export bugs The enhancer module existed (GEGL presets: Auto-fix, Brightness, Contrast, Saturation, Warm, Cool, Sharpen, Denoise) but was never connected to the app and GEGL was never initialized. Wire it up: - app.c: gegl_init() once in GApplication::startup (GEGL-gated). - enhancer.c: add enhancer_load(GFile) -> GeglBuffer (gegl:load) and enhancer_buffer_to_texture(GeglBuffer) -> GdkTexture (RGBA8 -> GdkMemoryTexture) for the live preview bridge. - enhancer_export: pick the saver from the output extension (jpg/png/webp) instead of always gegl:jpg-save (ju0 - was writing JPEG bytes into .png); verify the save actually produced a non-empty newer file instead of trusting g_file_test(EXISTS) on a pre-existing path (ku0 - false success). - window.c: win.enhance (a) cycles the active preset and previews it on the current image (switches to large view, loads via GEGL, applies, shows the texture); win.enhance-save (s) exports -enhanced. with the active preset, never overwriting the original. Preview resets on navigation; the title shows the active preset. - shortcuts.c: a -> win.enhance, s -> win.enhance-save; ? overlay Enhance group. - tests: test_enhancer gains load_and_to_texture, export_format (PNG/JPEG signature checks), export_real_success (ku0 - parent-missing and pre-existing-directory both return FALSE). LSAN suppressions cover GEGL's jpg-load plugin leak. test_shortcut full-table updated (25 rows). Synchronous apply (may briefly block on large images) and a navigate-away dirty prompt are deliberately out of scope for v1. --- src/app.c | 15 +++++++++++++++ 1 file changed, 15 insertions(+) (limited to 'src/app.c') diff --git a/src/app.c b/src/app.c index 587feb7..4bd351b 100644 --- a/src/app.c +++ b/src/app.c @@ -18,6 +18,10 @@ #include +#if GGAZE_HAVE_GEGL +#include +#endif + struct _GgazeApp { AdwApplication parent_instance; }; @@ -40,6 +44,16 @@ ggaze_app_activate(GApplication *p_app) { gtk_window_present(GTK_WINDOW(p_win)); } +static void +ggaze_app_startup(GApplication *p_app) { + G_APPLICATION_CLASS(ggaze_app_parent_class)->startup(p_app); +#if GGAZE_HAVE_GEGL + /* Init GEGL once before any window is created (before the first enhance + * call). Idempotent if already initialised. */ + gegl_init(NULL, NULL); +#endif +} + static void ggaze_app_open(GApplication *p_app, GFile **p_files, gint n_files, const gchar *c_hint) { @@ -62,6 +76,7 @@ ggaze_app_init(GgazeApp *p_app) { static void ggaze_app_class_init(GgazeAppClass *p_klass) { GApplicationClass *p_app_class = G_APPLICATION_CLASS(p_klass); + p_app_class->startup = ggaze_app_startup; p_app_class->activate = ggaze_app_activate; p_app_class->open = ggaze_app_open; } -- cgit v1.2.3