All the information you need in one place

How to track custom events with JavaScript?

Nelio A/B Testing comes with a set of built-in conversion actions that should satisfy the needs of most users. For example, there’s built-in conversion actions to track when a visitor visits a certain page on your site, clicks on a certain element or link, submits a form, or purchases a WooCommerce product.

However, there might be certain scenarios that aren’t covered by any of these conversion actions. If you have such need, you can use a Custom Event conversion action, which basically lets you programmatically trigger a conversion action via JavaScript whenever you want.

Example: Time on Page (basic)

Assume, for example, that you want to trigger a conversion if, and only if, a visitor has stayed on the tested page for at least 30 seconds. To do so, all you have to do is add a Custom Event conversion action in your test and set its Custom Event Name property to something like, for instance, time-30s.

Then, we need to create a custom JavaScript snippet that triggers the conversion at the right time. A script like the following would do the trick:

setTimeout( function() {
  nab.trigger( 'time-30s' );
}, 30000 );

As you can see, the previous script sets a timeout that will run an anonymous function in 30,000ms. The anonymous function will use Nelio A/B Testing’s nab.trigger method to trigger a custom event conversion using the name we defined in our test (time-30s). And that’s it!

Please notice you’ll need to add the previous snippet to your tested page and its variant. To do so, you can use an HTML block (if you’re using Gutenberg) within a script tag:

<script type="text/javascript">
  setTimeout( function() {
    nab.trigger( 'time-30s' );
  }, 30000 );

Example: Time on Page (advanced)

As you may have already noticed, conversions in Nelio A/B Testing are binary. That is, they either occurred or didn’t. This means that it’s easy to track if a visitor was on your tested page for at least 30 seconds (they either did or didn’t), but it’s impossible to track which variant is better at keeping your visitors engaged, regardless of how long they stay on the page.

To overcome this limitation there’s a workaround that might help you. The idea is pretty simple: you need to create a test with multiple goals, each with a single custom conversion action. Each goal will then implement the previous solution, the only difference being the time thresholds they use. For example, let’s say we add four goals:

  1. Goal 1: custom conversion action named time-10s
  2. Goal 2: custom conversion action named time-30s
  3. Goal 3: custom conversion action named time-60s
  4. Goal 4: custom conversion action named time-90s

And the following snippet:

setTimeout( function() {
  nab.trigger( 'time-10s' );
}, 10000 );
setTimeout( function() {
  nab.trigger( 'time-30s' );
}, 30000 );
setTimeout( function() {
  nab.trigger( 'time-60s' );
}, 60000 );
setTimeout( function() {
  nab.trigger( 'time-90s' );
}, 90000 );

Or, if you fancy a shorter version:

[ 10, 30, 60, 90 ].forEach(
  ( threshold ) => setTimeout(
    () => nab.trigger( `time-${ threshold }s` ),
    threshold * 1000

With such a setup, we’d trigger conversion actions at 10, 30, 60, and 90 seconds. Since each conversion action is defined in its own goal, Nelio A/B Testing would be able to tell us the conversion rates at each time threshold. This means we’d be able to know, for each variant, how many visitors stayed for at least 10 seconds if we look at goal 1. If we then switch to goal 2, we’d know how many visitors stayed for at least 30 seconds. And so on.

Example: Scroll

Another common scenario that you might be interested in tracking is how much have your visitors scrolled down your tested page. This information is available to subscribers as Scrollmaps in the Heatmap section of your variants, but it can’t be used as a conversion action per se.

If you want the page scroll to be your conversion event, you’ll need to implement a similar approach to the one we used in the previous example. That is, create several goals with one custom event:

  1. Goal 1: custom conversion action named scroll-30
  2. Goal 2: custom conversion action named scroll-50
  3. Goal 3: custom conversion action named scroll-75
  4. Goal 4: custom conversion action named scroll-100

and then trigger each custom event at the appropriate time:

( function() {
  [ 30, 50, 75, 100 ].forEach(
    ( threshold ) => document.addEventListener( 'scroll', () => {
      const bottom = window.pageYOffset + window.innerHeight;
      const scroll = 100 * bottom / document.body.clientHeight;
      if ( scroll >= threshold ) {
        nab.trigger( `scroll-${ threshold }` );
    } )
} )();

Notice the code is almost identical to the one we used in the previous example, the only difference being how the custom event is triggered (in this particular instance, we use addEventListener to listen to the scroll event and thus compute how far down we’ve come).