AX 7. How to override form data source field methods without overlaying.

It is a common customization task to override standard form data source field methods like jumpRef(), modified() or  validate().

Recommended approach in AX 7 is to avoid overlaying and use extensions as much as possible. To achieve this new events were introduced. However on form data source field level we have only 3 available events:

SalesTable

We can try to use form controls instead of form data source fields but this approach has several cons:

  • User can add new control using form personalization and this control won’t support overridden logic. It could be critical if you are restricting field lookup values or adding validations.
  • One form could have several controls that refers to one data source field so you have to duplicate your code.
  • Number of delegates are limited as well. Microsoft will add more later 🙂

For example we want to add custom jumpRef() and validate() methods to itemId field on sales order form. To achieve this we have to either overlay it or use next approach.

First of all we will create class to handle method overrides.

/// <summary>
/// Handles events raised by <c>SalesTable</c> form.
/// </summary>
public class SalesTableEventHandler
{
    /// <summary>
    /// Post event handler for <c>SalesTable</c> <c>SalesLine</c> Initialized event.
    /// </summary>
    /// <param name=“_sender”></param>
    /// <param name=“_e”></param>
    [FormDataSourceEventHandler(formDataSourceStr(SalesTable, SalesLine), FormDataSourceEventType::Initialized)]
    public static void SalesLine_OnInitialized(FormDataSource _sender, FormDataSourceEventArgs _e)
    {
        var overrides = SalesTableFormExtensionOverrides::construct();

        _sender.object(fieldNum(SalesLine, ItemId)).registerOverrideMethod(methodStr(FormDataObject, jumpRef),
            methodStr(SalesTableFormExtensionOverrides, itemId_OnJumpRef), overrides);

        _sender.object(fieldNum(SalesLine, ItemId)).registerOverrideMethod(methodStr(FormDataObject, validate),
            methodStr(SalesTableFormExtensionOverrides, itemId_OnValidate), overrides);
    }
}

Then we will create new event handler class and subscribe to OnInitialized event of SalesLine data source.

/// <summary>
/// Contains methods which are used to override <c>SalesLine</c> data source field methods.
/// </summary>
public class SalesTableFormExtensionOverrides
{
    protected void new()
    {
    }

    /// <summary>
    /// Constructs a new instance of <c>SalesTableFormExtensionOverrides</c> class.
    /// </summary>
    /// <returns>
    /// A <c>SalesTableFormExtensionOverrides</c> class.
    /// </returns>
    public static SalesTableFormExtensionOverrides construct()
    {
        return new SalesTableFormExtensionOverrides();
    }

    /// <summary>
    /// Provides the open main table functionality for an item.
    /// </summary>
    /// <param name ="_targetField"> The <c>FormDataObject</c> where the jumpRef is triggered.</param>
    public void itemId_OnJumpRef(FormDataObject _targetField)
    {
        InventTable::jumpRefItemId(_targetField.getValue(), OpenMode::Edit);
    }

    /// <summary>
    /// Checks whether <c>ItemId</c> is valid.
    /// </summary>
    /// <param name = "_targetField"> The <c>FormDataObject</c> where the Validate is triggered.</param>
    public boolean itemId_OnValidate(FormDataObject _targetField)
    {
        //emulate super() call. Comment out to skip.
        boolean ret = _targetField.validate();

        if (ret)
        {
            //custom validation here.
        }

        return ret;
    }
}

That’s all. Using this approach you can override any data source field method.

Advertisements

7 thoughts on “AX 7. How to override form data source field methods without overlaying.

  1. AlexOnDAX September 19, 2016 / 9:54 pm

    Your upper and lower blocks of code appear to be switched. Great blog though.

    • ievgensaxblog September 19, 2016 / 10:31 pm

      Thanks Alex.
      It makes sense to create class before using it but I hope everyone got an idea behind.

  2. Hek December 5, 2016 / 11:44 am

    Hi. Great post. But I’ve found out that that doesn’t work for lookup method on datasource field

  3. paivi February 23, 2017 / 10:05 am

    Hi,

    Overriding validate method works fine except in case when a validated (new) field value is not valid. The new value stays on a form though the validate method returns false. In AX2012 an original value is restored. I tried targetField.restore method but it didn’t help. Any idea how this could work?

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s