Intro
The topic of the Nintex Form Events has been covered before, most notably in the document located here: https://community.nintex.com/docs/DOC-1217
However, there are a few shortcomings and errors with this document undoubtedly because the Official SDK Documentation Help Page contains a lot of erroneous information (https://help.nintex.com/en-us/sdks/sdk2013/FormSDK/Topics/SDK_NF_CON_NF_Events.htm):
Though it would be easy to make an almost identical Blog or Document containing the corrected information, I wanted to take the time to delve a little deeper into how Nintex Forms fires its custom Events and the options it presents to you as a developer.
I should also take this time to get one of the bigger caveats of this blog out of the way. This is mainly for the Classic Forms and not the Responsive Forms. While I will get into how you can utilize them in the Responsive Forms, it's a HUGE hassle and ultimately isn't supported by Nintex... sadly. Until that is the case, it won't be particularly useful to that environment . Actually, scratch that. No time to get into how to do this for Responsive Forms without making this a giant book. Sorry Responsive Users.
All that aside… let’s get into it!
Brief Events Refresher
For the uninitiated, an event could be thought of as a notification. While Events are not a native part of the JavaScript Language, they ARE a part of the API presented to us by web browsers (specifically the DOM api), and because Nintex Forms are presented to us via the web browser, we have access to all of those events.
The special thing about Events is that you, as a developer, get to choose when you would like to or not like to pay attention, or ‘handle’, the event in question. Some of these exposed events may be familiar to you already. Most people who have done a little JavaScript have probably used or seen the ‘onclick’ event, the ‘change’ event, or the ‘blur’ event to name a few.
When you handle an event, such as ‘onclick’, you are saying to the browser, “Whenever someone clicks *some* element, I want to execute a chunk of code”.
Fundamentally it is this simple, but to learn more in depth please read: Introduction to events - Learn web development | MDN
Nintex Form "Events" Primer
That being said, the 'Events' exposed to us in Nintex Forms are not like the events exposed to us by the DOM api / Web Browser. Instead, Nintex Forms Events are more like checkpoints. With a normal native event, you can call any of the exposed functionality built around them to alter the way that event is handled (see: Event.stopPropagation() - Web APIs | MDN). Nintex Form Events are actually called linearly just like any other function / expression, by the code that is executed whenever you interact with the Form in some meaningful way.
You could think of the flow how Nintex Form Events work as being
Native DOM Event (like "onclick") =>
Nintex Forms Processing Functions =>
Nintex Forms 'Starting Event' =>
Any Code That Was Passed Into That Particular "Event's" Collection =>
Continuation of Nintex Forms Processing Functions =>
Nintex Forms 'Outro Event' =>
That Was Passed Into That Particular "Event's" Collection =>
Done
To give a more specific example, let's look at how the Add New Row button works on a Repeating Section.
- User "CLICKS" on the Add New Row image.
- This initiates / emits the (native) "onclick" event.
- When the Form was rendered, an Event Handler was setup on the form to handle this specific 'click' event on this specific image / link. The handler is as follows (courtesy of Nintex):
formFillerDivCurrent.on('click', '.nf-repeater-addrow-link', function(event) {
var addrowImage = NWF$(this);
var thisRepeaterControl = NWF$(NWF$(addrowImage.closest('.nf-repeater'))o0]);
NWF.FormFiller.Functions.BulkCalculationExecution = true;
NWF.FormFiller.Functions.UseServerValueForCalculations = true;
NWF.FormFiller.Functions.AddNewRepeaterRow(thisRepeaterControl, formFillerDivCurrent);
NWF.FormFiller.Functions.BulkCalculationExecution = false;
NWF.FormFiller.Functions.UseServerValueForCalculations = false;
NWF.FormFiller.Functions.ProcessDeferredCalculations();
});
This handler is set to fire when you have clicked on an element that has the class "nf-repeater-addrow-link" and, after executing a few functions, eventually executes the AddNewRepeaterRow() function.
- Inside of the AddNewRepeaterRow function lay all of the code to generate a brand new Repeater Row for you!
If you were to look at the entire AddNewRepeaterRow function as a whole, it would look a lot like:{
AddNewRepeaterRow: function(thisRepeaterControl, formFillerDivCurrent) {
var newRepeaterRow;
var heightIncrease;
NWF.FormFiller.Events.ExecuteRepeaterRowAdding(thisRepeaterControl);
/*
LOTS OF CODE DOING LOTS OF FUN REPEATING SECTION STUFF HERE
*/
NWF.FormFiller.Events.ExecuteRepeaterRowAdded(newRepeaterRow);
}
}
You'll notice that *around* the code where all of the 'fun repeating section stuff' happens are two lines of code that may seem familiar.
Specifically they are the lines:NWF.FormFiller.Events.ExecuteRepeaterRowAdding(thisRepeaterControl);
And:
NWF.FormFiller.Events.ExecuteRepeaterRowAdded(newRepeaterRow);
You may have also noticed that these Executed "events" are named in a particular way. This is the typical* layout of Nintex Form Events. Usually there is an "Intro" call that invokes things at the very beginning of something BEFORE it has even started, and an "Outro" call that invokes your code at the very END of whatever the main function's purpose was.
In this case the Intro 'event' can be thought of as the RepeaterRowAdding, while the Outro 'event' can be thought of as RepeaterRowAdded.
When RepeaterRowAdding is invoked...
- Any function that you have passed into the NWF.FormFiller.Events.RegisterRepeaterRowAdding() function, will be executed.
For instance, if I had the following code in the Custom Javascript section of the Form Settings (Classic Forms):NWF.FormFiller.Events.RegisterRepeaterRowAdding(function(){
console.log("The Row Hasn't Been Created Yet!");
});
Then once the ExecuteRepeaterRowAdding function was called during the AddNewReapeaterRow function, you would see the message "The Row Hasn't Been Created Yet!" in the console window of your browser!
- The Same things will happen with the ExecuteRepeaterRowAdded function. Any number of functions that you have passed using the NWF.FormFiller.Events.RegisterRepeaterRowAdded() function will be executed at this time.
For instance, if I had the following code in the Custom Javascript section of the Form Settings (Classic Forms):NWF.FormFiller.Events.RegisterRepeaterRowAdded(function(){
console.log("The Row Has Been Totally Created!");
});
Much like before, you would see the console message "The Row Has Been Totally Created!" after the new Repeater Row had been added to the form.
- With everything finished, the other remainder code executes and the user is none the wiser!
Now that you understand how these work a bit more intricately, let's take a look at a list of all the available Nintex Form Events we have available to us!
Available Form Events
Below is a list of every available Nintex Forms Event that will fire during the course of Form Initialization (loading) stage when you load up a form. Any arguments passed to the Event Function has been noted as a comment inside of the code example, along with a few console outputs to help you see exactly what is happening.
(Note 1: A few terms I use in here are things like "inner-control" or "outermost filler div". If you are unfamiliar with how Nintex Forms generates its HTML for the controls, it can typically be thought of as:
<div class="nf-filler-control aka:OUTER CONTROL">
<div class="nf-filler-control-border">
<div class="nf-filler-control-inner">
<div class="something-sometimes">
<probably your INNER CONTROL(S)/>
</div>
</div>
</div>
</div>
This is an terrible exaggeration, but anytime that you seem me write something like NWF$(outermost filler div); you know that the jquery object that is returned to you is referencing the outermost layer of the target control and NOT the innermost element which contains that actual VALUE of that control)
(Note 2: You'll notice that I have used colors for the names of the below events. The key is as follows:
Red: Indicates that the event is fired only ONCE during the loading of the Form, and never again.
Blue: Indicates that the event is fired MULTIPLE TIMES, but ONLY during the loading of the Form and never after.
Plum: Indicates that the event is fired both during the Form Load, and during the Normal Runtime of the Form after the user is able to interact with it.)
Lime: Indicates that the event is fired after the Form has been Loaded during Normal Runtime only!)
RegisterBeforeReady: This is the first Nintex Form event that fires AFTER all of the custom JavaScript has been loaded into the Form (Classic). This event will ONLY fire ONCE during a Forms Initialization.
NWF.FormFiller.Events.RegisterBeforeReady(function () {
console.log("Executing 'RegisterBeforeReady' ");
/* argumentsl0] === undefined */
});
RegisterControlProcessing: This event fires any time a Form Control is being processed during the initial generation of the Form. As far as I know, this is the only time this event fires.
NWF.FormFiller.Events.RegisterControlProcessing(function () {
console.log("Executing 'RegisterControlProcessing' ");
console.log("Processing Control: " + arguments/0].closest(".nf-filler-control").attr("data-controlname"));
/* arguments/0] === NWF$(inner-control) */
});
RegisterControlProcessed: This event fires any time a Form Control has completed processing during the initial generation of the Form. As far as I know, this is the only time this event fires.
NWF.FormFiller.Events.RegisterControlProcessed(function () {
console.log("Executing 'RegisterControlProcessed' ");
console.log("Processed Control: " + arguments0].fillerDiv.attr("data-controlname"));
/* argumentse0] === {
fillerDiv: NWF$(outermost filler div),
formControl: fillerDiv.children().children().children(),
formFillerDivCurrent: NWF$("#formFillerDiv")
}; */
});
RegisterControlHeightChangePropagating: This event fires any time a Form Control has to adjust its height because of something other than a Rule, and subsequently pushes that height change to every Form Container, eventually ending with a resize of the Form Canvas itself. When a Form is initializing, the Repeating Section will typically fire this as it generates its hidden 'root' row, and then again for it's 1st visible row.
NWF.FormFiller.Events.RegisterControlHeightChangePropagating(function () {
console.log("Executing 'RegisterControlHeightChangePropagating' ");
console.log("Height Change Propagating For: " + arguments.0].attr("data-controlname"));
/* arguments/0] === NWF$(outermost filler div); */
});
RegisterControlHeightChangePropagated: This event fires after all of the Control's Siblings have been repositioned, and its Parent Containers and Canvas have been resized. This follows the RegisterControlHeightChangePropagating event.
NWF.FormFiller.Events.RegisterControlHeightChangePropagated(function () {
console.log("Executing 'RegisterControlHeightChangePropagated' ");
console.log("Height Change Propagated For: " + arguments0].attr("data-controlname"));
/* arguments<0] === NWF$(outermost filler div); */
});