Official tutorials on GIMP plug-ins and GEGL filters development

Cross-posting this from other media where GIMP may have an official presence since I believe it’s important we get as much feedback as possible before release.

So in the last few days, I’ve started writing tutorials on writing various kinds of programmatic extensions for GIMP, i.e. plug-ins but also filters. It is not finished work. I will likely add more sections, or more parts in existing sections, and I’m sure I will tweak text as I read again and again.

People who know me also know I have a hard time writing concisely (and for a good tutorial, I believe it needs to be both concise and detailed at times, in the same time, which is something hard to achieve! I worked quite hard already on current text and structure!).

Anyway as I know there are quite some people in this forum interested in plug-in developments, here are the 2 tutorials:

Still work-in-progress (both) but I welcome feedbacks! Thanks! :hugs:

P.S.: note that the feedback is not only about the docs, but also about issues in the API itself. If you notice issues when trying to make your plug-in and it feels that the problem is that something is not ideal in the API, we want to hear from it. We likely won’t do major restructuration before 3.0.0, yet we are still able to do some logic fixes here and there.

4 Likes

For GEGL filters “How to write a filter” you can take from Liam’s blog who cited what I was doing.

Hope this helps.

1 Like

Back in 2024 I wrote a simple GEGL graph that I figured could be the user’s first GEGL meta operation akin to a hello world for GEGL

The meta operation is this

id=1 add aux=[ ref=1 saturation scale=2 ]
hue-chroma lightness=-29

in .c format, and the user has to fill out the ??? areas with help from gegl.org. You can check it out as in my opinion it makes a better “hello world” for GEGL meta ops.

.c file below

/* This file is an image processing operation for GEGL
 *
 * GEGL is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 3 of the License, or (at your option) any later version.
 *
 * GEGL is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with GEGL; if not, see <https://www.gnu.org/licenses/>.
 *
 * Copyright 2006 Øyvind Kolås <pippin@gimp.org>
 * 2024 (gimpchat username here) with Beaver's help - Vibrance Saturation Effect.

This is a guide on how to make a very simple GEGL Plugin. Which is literally saturation on the "addition blend mode" with a lighting property. It is inspired by GMIC's "vibrance" filter"

THIS IS THE GRAPH THAT WE WILL TURN INTO A PLUGIN 

id=1 add aux=[ ref=1 saturation scale=2 ]
hue-chroma lightness=-29
 */

#include "config.h"
#include <glib/gi18n-lib.h>

#ifdef GEGL_PROPERTIES

/*This is where Vibrances saturation GUI aspect goes

I gave it the correct parmaters in value_range and ui_range but you
the user has to give it the property_name and a slider name. Note if you are paying very close attention you will realize I intentionally limited the ui and value range that these filters
are capable of for the same of simplicity.*/

property_double (propertynamecorresponding, _("Name this slider"), 0.0)
   description (_("description"))
   value_range (0.0, 5.0)
   ui_range    (0.0, 5.0)

/*This is where Lightness slider goes

I gave it the correct parmaters in value_range and ui_range but you
the user has to give it the property_name and a slider name. */

property_double (propertynamecorresponding2, _("Name this slider"), 0.0)
   description (_("description"))
   value_range (-20.0, 10.0)
   ui_range    (-20.0, 10.0)

#else

#define GEGL_OP_META
#define GEGL_OP_NAME     vibrance
#define GEGL_OP_C_SOURCE vibrance.c

#include "gegl-op.h"

/* This GEGL node list needs to include three seperate names of your choice So far it only contains "???" as substitutes for the following operations.
"1. gegl saturation"  "2. gegl hue chroma"  3. gegl add . 

The goal is to give these operations names  three unique names of your choice while listing their true GEGL operation name. 
"*input" and "*output" which is the default read image from gimp and render image from gimp are already done. */

static void attach (GeglOperation *operation)
{
  GeglNode *gegl = operation->node;
  GeglNode *input, *???, *???, *???,  *output;



  input    = gegl_node_get_input_proxy (gegl, "input");
  output   = gegl_node_get_output_proxy (gegl, "output");


/*you can find this filters operation name here https://gegl.org/operations/gegl-hue-chroma*/
  ??? = gegl_node_new_child (gegl,
                                  "operation", "gegl:???",
                                  NULL);

/*you can find this filters operation name here https://gegl.org/operations/gegl-saturation.html*/
  ??? = gegl_node_new_child (gegl,
                                  "operation", "gegl:???",
                                  NULL);

/*you can find this blend modes operation name here https://gegl.org/operations/gegl-add.html*/
  ??? = gegl_node_new_child (gegl,
                                  "operation", "gegl:???",
                                  NULL);

/*This is the literal GEGL Graph. The goal is to recreate the GEGL syntax

id=1 add aux=[ ref=1 saturation scale=2 ]
hue-chroma lightness=-9

in a way the .c file understands. input and output are already done and I actually did one step because in this case "id=1" is the first input (the bookmark) and
the second input is "ref=1" which is the image called. */

  gegl_node_link_many (input, ???, ???, output, NULL);
  gegl_node_link_many (input, ???,  NULL);
  gegl_node_connect_from (???, "aux", ???, "output");

/*the property name is what you wrote on lines 38 and 48.

??? is the name you assigned to filters "hue chroma" and "saturation"

once again, the original property name can be found here listed after the |
https://gegl.org/operations/gegl-saturation.html

https://gegl.org/operations/gegl-hue-chroma (its the third one that has to do with light)
*/                              
 gegl_operation_meta_redirect (operation, "saturationpropertynameyougave", ???, "property_name_of_gegl:saturation"); 
 gegl_operation_meta_redirect (operation, "lightnesspropertynameyougave", ???, "property_name_of_gegl:hue-chromas_light"); 

}

static void
gegl_op_class_init (GeglOpClass *klass)
{
  GeglOperationClass *operation_class;

  operation_class = GEGL_OPERATION_CLASS (klass);

  operation_class->attach = attach;
/*enter a name space like john:vibrance and then enter your plugins name and description. Do not use the names (gegl:, gimp: or svg:)*/
  gegl_operation_class_set_keys (operation_class,
    "name",        "namespace:vibrance",
    "title",       _("My New GEGL Plugin's name"),
/*mash number buttons for reference hash*/
    "reference-hash", "23489234jkfg8932ac",
    "description", _("Template for GEGL Plugins"),
/*If you want to put your plugin in the menu of Gimp 2.99.16+ add a copy of the name here.*/
    "gimp:menu-path", "<Image>/Filters/Menu_for_my_plugin",
    "gimp:menu-label", _("Menu Plugin Name..."),
    NULL);
}

#endif