Tip: Interacting with the actual .NET Control Add-in controls

The control add-in framework in NAV 2013 is great, because apart from allowing you to put a custom Windows Forms control on the page, it also allows you to interact with it through properties, methods, and events. In my classes I typically create a custom text box control that exposes a property to set the background color on the text box. It only takes adding a property of type Color, decorating it with the ApplicationVisible attribute, and you are ready to play.

However, if you want to enable setting all properties or invoking all of the methods the control supports, you could start wrapping the internal control into new ApplicationVisible properties and methods. There is no end to this.

Even though this is an incredibly simple concept, it just never crossed my mind: why not exposing the whole control as an ApplicationVisible property – this would in turn enable you to access the whole control, all its properties and methods (unfortunately, not the events – the delegates are still not supported in C/AL) without having to write a single additional line of code.

I give full credit here to my friend John who gave me thins hint. Thanks, John!

Here’s a practical example: you have a custom button control add-in that looks more or less like this:

image

Why not appending this little piece of code (marked green):

image

It costs nothing, but it allows you to do things like this:

image

Or like this:

image

Or, why not, like this:

image

Even though the C/AL Symbol Menu will not give you access to any of the inner control directly, all the members are still there for you to access.

Again, as I said – you can’t subscribe to events. This is one of those limitations of .NET Interoperability I wrote about last year that I hope get sorted out at some point in future.

However Smile However… an idea has just crossed my mind and I’ll keep fingers crossed that I have enough time to try it out. If it works out, my next blog post will explain just that – subscribing to just about any event the inner control exposes.

Vjeko

Vjeko has been writing code for living since 1995, and he has shared his knowledge and experience in presentations, articles, blogs, and elsewhere since 2002. Hopelessly curious, passionate about technology, avid language learner no matter human or computer.

This Post Has 13 Comments

  1. Peter Tijsma

    Again, great post!
    I can see again new possibilities coming up in our ISV product 🙂

    Really smart!

    Thanks,

    1. Vjeko

      Thanks, Peter! 🙂 I should just send you a monthly idea-royalty bill 😛

      1. Peter Tijsma

        🙂

        Now you just only need to update your drag-n-drop control blog with some additional info 😉

        1. Vjeko

          Who knows, who knows…

  2. Nikolai L'Estrange

    The interesting bit is when you realise you don’t want to give access to the actual .NET Button object because you know Developers will play… (e.g. you know if they change the Image or the Size they will break it).

    It took me far too long to figure out that a simple wrapper class will do this nicely. The wrapper class should take the Button in the constructor and expose functions for each property of Button you are happy for people to change. This also allows you to make some read-only (by only implementing the get {})

    1. Vjeko

      @Nikolai: I don’t quite agree with you. The whole control framework is in place to allow you to develop controls that are not natively supported by RTC. The “developer” from your statement is in fact – you. It is you who is developing the control in C# so that you can enable yourself to access it in C/AL – and you should make your life in C/AL easier. It’s much easier to expose the whole control as a property, rather than expose a new property and then redeploy the control when you need it. Also – if it’s not you for whom you are developing, then I still don’t agree that “developers could break it” is a good enough reason. Developers can break anything anyway, should we prevent them from changing, say, CU12, or CU90, or something? If you ask me – controls have properties and methods precisely so that developers use them – and by making them accessible to C/AL with less hassle, less typing, less human error, and less manual work around deployment, you are playing along the design goals for those controls. If there are any properties and methods that are not intended to be used by developers, they are marked private and are already inaccessible; everything else should be accessible.

      1. Nikolai L'Estrange

        Mostly I agree Vjeko, and with an actual Button control I would do it your way.

        I mostly put that comment as a tip for when you develop more complex controls, if you don’t have the option of setting some properties as private (e.g. I’ve made a few WPF controls – they usually need to have public properties or they just don’t display) or you want to have a “clean” API to give to your other developers (and you don’t want to write a manual for them 😉

        That’s sort of my role at the moment, I’m the .NET control guy… Your blog helps me enormously btw 🙂

        1. Vjeko

          Thanks, Nikolai 🙂 I see your point. It mostly depends on your role and your target audience. If you are developing an add-in for a project that you are also working on (this may include a vertical solution that includes your add-on) then it makes sense to expose as much as possible to C/AL and make it easily accessible. If you are developing components, and you sell those components out of project implementations or vertical solutions (something extremely rare in NAV world) – then you might want to hide stuff to help yourself in supporting, and to avoid writing manuals 🙂

  3. Justinas

    Hi, Vjeko,

    it’s nice to subscribe to any event, but.. Is it possible to pass from NAV to Add-In the type of a text-box? For example if you wan’t to use add-in with a text-box on NAV field of type Text, you have to inherit “IValueControlAddInDefinition”, for Integer you go with Int32 in the , and so on.

    How to avoid creating the same add-in for every type?

    1. Vjeko

      Hi Justinas, you just took away the surprise factor from my next post, because that’s exactly what my next post will be about 🙂

  4. Meik

    Hi Vjeko, This is a really nice Tip. Is this also possible in NAV 2017 or NAV 2018? Do you know what I need to change so it is working in one of them? I get the Button but I can´t insert
    “CurrPage.Button.Button.Text := ‘Click me Now’;”

    I can insert “CurrPage.GLN.Button.Text := ‘Click me Now’;”(instead of button the fieldname where I have put the Add-In) but It doesn´t change anything in the application.

    Thank you.

    1. Vjeko

      Well, I certainly don’t know this by heart. Didn’t try it under 2017 or 2018. You shouldn’t be using .NET control add-ins under 2017 or 2018 anyway. JavaScript control add-ins are the way to go.

Leave a Reply