Skip to content

Wizard Step Registration

Register custom steps in the campaign creation wizard from your add-on plugin.

Call Igcf_Campaign_Form_Registry::register_step() during the init action. The first argument is a unique slug; the second is a configuration array:

add_action( 'init', function() {
Igcf_Campaign_Form_Registry::register_step(
'verification',
array(
'label' => __( 'Verification', 'igcf-verification' ),
'priority' => 30,
'template' => 'campaign-form/step-verification',
'fields' => array(
'id_document' => array( 'required' => true ),
),
'visible' => true,
'has_form' => true,
)
);
} );

The slug must be unique across all plugins. It becomes part of the wizard URL (#step-verification) and is used as the key in completion state lookups.

Parameter Type Default Description
label string '' Translatable label shown in the wizard sidebar and step heading.
priority int 50 Ordering weight. Lower values appear first.
template string '' Template name passed to igcf_get_template().
fields array array() Field definitions for completion tracking (see below).
visible bool|callable true Whether the step is shown. Can be a boolean or a callable that returns a boolean.
has_form bool true Whether the wizard wraps the template in a <form> with Save Draft / Next buttons.

The fields array tells the registry which fields to check for completion tracking. Each key is a field identifier, and its value is a configuration array with a required entry:

'fields' => array(
'id_document' => array( 'required' => true ),
'phone_number' => array( 'required' => false ),
),

The required value can be a boolean or a callable. A callable receives the campaign WP_Post object and must return a boolean:

'fields' => array(
'tax_id' => array(
'required' => function( $campaign ) {
$goal = get_post_meta( $campaign->ID, '_igcf_goal', true );
// Only require tax ID for campaigns above $10,000.
return (float) $goal > 10000;
},
),
),

When evaluating completion, the registry reads field values using the following logic:

  1. title maps to the campaign’s post_title.
  2. description maps to the campaign’s post_content.
  3. All other keys are read from post meta with the _igcf_ prefix (e.g., field key goal reads _igcf_goal).

Create a PHP template file that igcf_get_template() can locate. The default location is:

src/plugins/your-addon/public/views/campaign-form/step-verification.php

The template receives an $igcf_args array. Use the igcf_locate_template filter to tell the template loader where to find your add-on’s templates:

add_filter( 'igcf_locate_template', function( $located, $template_name, $template_file ) {
if ( 0 === strpos( $template_name, 'campaign-form/step-verification' ) ) {
$addon_path = MY_ADDON_DIR . 'public/views/' . $template_file;
if ( file_exists( $addon_path ) ) {
return $addon_path;
}
}
return $located;
}, 10, 3 );

Themes can override your template by placing a copy at:

wp-content/themes/your-theme/ignition-crowdfunding/campaign-form/step-verification.php

See Template Overrides for details on the lookup order.

The has_form parameter controls how the wizard renders your step.

When has_form is true (the default), the wizard wraps your template inside a <form> element and automatically adds Save Draft and Next buttons (or the final submit button on the last step). Your template only needs to render the form fields. Data is submitted as a standard form POST. The last-step submit button is filterable via igcf_campaign_form_submit_button — core publishes the campaign, while an add-on such as Ignition Platform Mode relabels it “Submit for Review”.

When has_form is false, the wizard renders your template without a <form> wrapper and without any buttons. Your step is responsible for managing its own data persistence, typically through REST API calls with JavaScript. The core Rewards step uses this approach:

Igcf_Campaign_Form_Registry::register_step(
'rewards',
array(
'label' => __( 'Rewards', 'ignition-crowdfunding' ),
'priority' => 20,
'template' => 'campaign-form/step-rewards',
'fields' => array(),
'visible' => 'igcf_is_reward_levels_enabled',
'has_form' => false,
)
);

Use has_form => false when your step needs dynamic UI interactions (drag-and-drop, inline editing, AJAX-driven lists) that don’t fit a traditional form submission model.

Use the visible parameter to show or hide a step based on runtime conditions. Pass a callable that returns a boolean:

Igcf_Campaign_Form_Registry::register_step(
'verification',
array(
'label' => __( 'Verification', 'igcf-verification' ),
'priority' => 30,
'template' => 'campaign-form/step-verification',
'fields' => array(
'id_document' => array( 'required' => true ),
),
'visible' => function() {
return get_option( 'igcf_require_creator_verification', false );
},
)
);

You can also pass a named function reference:

'visible' => 'igcf_verification_is_required',

When a step is hidden, it does not appear in the wizard sidebar or navigation. Its fields are excluded from completion state calculations for the review step.

Steps with an empty fields array are also excluded from completion tracking — they show no badge or checkmark in the progress bar. Only steps with at least one required field participate in completion indicators.

Steps are sorted by priority (ascending). Steps with equal priority maintain their insertion order.

The core plugin registers three steps:

Step Priority
Details 10
Rewards 20
Review 99

Add-ons should use priorities in the 30–89 range to place steps between Rewards and Review. Some suggested conventions:

Range Intended use
30–39 Content steps (media, story sections)
40–49 Financial steps (budget, milestones)
50–59 Compliance steps (verification, legal)
60–89 Other custom steps

The registry’s get_field_value() method reads field values from post meta using the _igcf_ prefix convention. For example, field key id_document is read from _igcf_id_document meta.

If your add-on stores data in custom tables or uses a different meta prefix, the built-in completion tracking will not find the values. In that case you have two options:

  1. Recommended: Store wizard-related fields using the _igcf_ meta prefix so completion tracking works automatically.
  2. Alternative: Register the step with an empty fields array and handle completion state in your own UI.

This example registers a “Verification” step that requires the campaign creator to upload an ID document before submitting the campaign.

<?php
/**
* Plugin Name: IGCF Verification Add-on
* Description: Adds a verification step to the campaign creation wizard.
*/
define( 'IGCF_VERIFY_DIR', plugin_dir_path( __FILE__ ) );
// Register the wizard step.
add_action( 'init', function() {
Igcf_Campaign_Form_Registry::register_step(
'verification',
array(
'label' => __( 'Verification', 'igcf-verification' ),
'priority' => 50,
'template' => 'campaign-form/step-verification',
'fields' => array(
'id_document' => array( 'required' => true ),
),
'visible' => function() {
return get_option( 'igcf_require_creator_verification', false );
},
'has_form' => true,
)
);
} );
// Register template location.
add_filter( 'igcf_locate_template', function( $located, $template_name, $template_file ) {
if ( 'campaign-form/step-verification' === $template_name ) {
$path = IGCF_VERIFY_DIR . 'public/views/' . $template_file;
if ( file_exists( $path ) ) {
return $path;
}
}
return $located;
}, 10, 3 );

Create public/views/campaign-form/step-verification.php in your add-on:

<?php
/**
* Verification step template.
*
* @var array $igcf_args Template arguments.
*/
// Exit if accessed directly.
if ( ! defined( 'ABSPATH' ) ) {
exit;
}
$campaign_id = isset( $igcf_args['campaign_id'] ) ? $igcf_args['campaign_id'] : 0;
$id_document = get_post_meta( $campaign_id, '_igcf_id_document', true );
?>
<div class="igcf-verification-step">
<p><?php esc_html_e( 'Upload a government-issued ID to verify your identity.', 'igcf-verification' ); ?></p>
<label for="igcf-id-document">
<?php esc_html_e( 'ID Document', 'igcf-verification' ); ?>
<span class="igcf-required">*</span>
</label>
<input
type="hidden"
name="id_document"
id="igcf-id-document-value"
value="<?php echo esc_attr( $id_document ); ?>"
/>
<button type="button" class="igcf-verification-step__upload wp-element-button" id="igcf-upload-id">
<?php esc_html_e( 'Select File', 'igcf-verification' ); ?>
</button>
<?php if ( $id_document ) : ?>
<p class="igcf-verification-step__status">
<?php esc_html_e( 'Document uploaded.', 'igcf-verification' ); ?>
</p>
<?php endif; ?>
</div>

When the creator fills in the id_document field and saves, the value is stored as _igcf_id_document post meta. The registry’s completion tracking automatically verifies the field is non-empty before allowing submission.