Developer documentation

Node parameters

You can add parameters to your algorithm by creating a property with a getter and setter. Then you annotate the getter and setter with the same @JIPipeParameter keys. You should also add an @JIPipeDocumentation annotation to either the getter or setter.

Parameters are automatically serialized and deserialized.

  • Your setter can return a boolean. If the output is true, JIPipe considers the value as valid. If false, the JIPipe UI re-loads a valid value via the getter.
  • Please make sure that your parameter key is unique. Only one getter and one setter should have the same key.
  • Not all data types are supported. Data types are registered into JIPipe and available via JIPipeUIParametertypeRegistry.getInstance(). In a later tutorial we show how to register custom data types. JIPipe supports common primitives like boolean, int, float, double, String, and all enum data types.

Example code: parameter

// ... see previous tutorials
public class MyAlgorithm extends JIPipeIteratingAlgorithm {

    private float roundness = 0.5f;

    // ... see previous tutorials

    @JIPipeParameter("roundness")
    @JIPipeDocumentation(name = "Roundness", description = "Value within [0, 1]")
    public float getRoundness() {
        return roundness;
    }

    @JIPipeParameter("roundness")
    public boolean setRoundness(float roundness)  { // void or boolean return values are supported
        if(roundness < 0 || roundness > 1)
            return false; // Reject this value
        this.roundness = roundness;
    }

}

Changing parameter values from code

The following part is only important if you want to update parameter values that should be reflected in the UI.

When a user sets a parameter within the UI, it goes through an instance of JIPipeParameterAccess. This object is responsible for triggering the required events to notify the UI.

If you set a parameter setter via code, you will notice that any open parameter UI does not respond to this change – due to the absence of the JIPipeParameterCollection.ParameterChangedEvent.

Use the provided triggerParameterChange(key) function to trigger the appropriate parameter change event for a parameter. Alternatively, you can use the setParameter(key, value) method to set parameters.

MyAlgorithm algorithm = new MyAlgorithm(...);

// This will NOT update the UI
algorithm.setRoundness(1.0f);

// Either trigger the event manually
algorithm.setRoundness(1.0f);
algorithm.triggerParameterChange("roundness");

// Or just use the setParameter() function
algorithm.setParameter("roundness", 1.0f);

You can also read parameters via their key using getParameter()

MyAlgorithm algorithm = new MyAlgorithm(...);
algorithm.getParameter("roundness", Float.class) // Returns 1.0 

Parameter settings

Some parameter types have different styles or other settings that can change the behavior of the parameter editor UI. An example is StringParameterSettings that allows to change between single-line and multi-line editors.

Sub-parameters

Any JIPipeParameterCollection allows (nested) sub-parameters.

To create a sub-parameter create a getter to an JIPipeParameterCollection and annotate it with @JIPipeParameter. The key provided with the annotation should be an unique parameter key. The parameters in the sub-parameter instance are automatically displayed as new group in the parameter editor.

@JIPipeDocumentation(name = "Gaussian filter")
@JIPipeParameter(value = "gaussian-algorithm")
public GaussianBlur2DAlgorithm getGaussianAlgorithm() {
    return gaussianAlgorithm;
}

The @JIPipeParameter annotation allows you to determine various properties, like if the sub-parameter should be collapsed or hidden by default.

Please do not forget to listen for the ParameterStructureChangedEvent and pass it to the algorithm’s event bus. Otherwise there can be issues with the extension builder. You can use the registerSubParameter() method in the constructor and copy constructor as a shortcut.

Conditional parameter visibility

Each parameter collection (including nodes) allow the conditional display of parameters or sub-parameters. To setup this display, override the isParameterUIVisible method. There are two overloads, one for displaying or hiding single parameters, and one for controlling the display of sub-parameters.

// Example for conditional showing/hidding of single parameters
 @Override
public boolean isParameterUIVisible(JIPipeParameterTree tree, JIPipeParameterAccess access) {
    if (access.getKey().equals("mode"))
        return true;
    if (mode == Mode.Automatic) {
        return !access.getKey().equals("custom-name");
    } else {
        if (access.getKey().equals("ignore-missing-metadata"))
            return true;
        if (access.getKey().equals("missing-string"))
            return true;
        return access.getKey().equals("custom-name");
    }
} 

// Example for sub-parameters
@Override
public boolean isParameterUIVisible(JIPipeParameterTree tree, JIPipeParameterCollection subParameter) {
    if(!scaleToModelSize && subParameter == getScale2DAlgorithm()) {
        return false;
    }
    return super.isParameterUIVisible(tree, subParameter);
}

Use triggerParameterUIChange() to trigger an update of the UI in the setter function if you have dependencies between parameters. This will work for parameters and parameter groups.

User-defined parameters

If you want to make it possible for users to create custom parameters, create an JIPipeDynamicParameterCollection as sub-parameter. You can control the list of allowed parameter types and other settings.

// Field that initializes the dynamic parameter collection with all supported parameter types
private JIPipeDynamicParameterCollection scriptParameters = new JIPipeDynamicParameterCollection(true,
            JIPipe.getParameterTypes().getRegisteredParameters().values());
            
public MyClass() {
    registerSubParameter(scriptParameters);
}

public MyClass(MyClass other) {
    this.scriptParameters = new JIPipeDynamicParameterCollection(other.scriptParameters);
    registerSubParameter(scriptParameters);
}

@JIPipeDocumentation(name = "Script parameters")
@JIPipeParameter(value = "script-parameters", persistence = JIPipeParameterPersistence.Object) // Important: Set persistence
public JIPipeDynamicParameterCollection getScriptParameters() {
    return scriptParameters;
}
  • Do not forget to deep-copy the JIPipeDynamicParameterCollection. The class has a copy constructor for such an operation.
  • Please do not forget to listen for the ParameterStructureChangedEvent and pass it to the algorithm’s event bus. Otherwise there can be issues with the extension builder. JIPipeAlgorithm comes with a pre-made function registerSubParameters() that should be called in the constructors.
  • We recommend setting the persistence of the getter to JIPipeParameterPersistence.Object. Otherwise, JIPipe will have issues with de-serializing the parameter and lose all settings.

Custom parameter collections

You can inherit from JIPipeCustomParameterCollection to define all parameters manually without the need for an JIPipeDynamicParameterCollection or annotations.