MDrivenWiki
Log in

UIOverride

From MDrivenWiki
UIOverride

Working with MDriven viewmodels you expect the UI to be created by the MDriven logic for the given platform. This handles the standard grids, edits and picklists. But ever so often you want to be able to inject other controls and bind these to the data instead.

You can replace the whole page/dialog/form but many times you will suffice with just injecting one or a few things into the standard UI.

To do this you check the "Content override" checkbox on the viewmodel column that is the root of your data for the override control. This will signal just as grey rectangle in the designer.

Two new properties will show up in the propetry inspector: ContentOverrideType and ContentOverrideDesignTimePath. These are properties to point out a c# assembly that can render the control in design time. This is totally optional - and you do not need to do this in order to use the UIOverride on runtime. If you want to find out how to use it read more here: Custom controls in ViewModel aided Views

To get the UIOverride to work in runtime we need to do different things per target platform. All platforms support the UIOverride - but the used control must support the platform.

Platform What you need to do
WPF std MDriven Framework Implement IExternalWECPOFUIComponent, read more here
MDriven Turnkey WPF Currently you must implement the HandleContentOverride and merge your control with existing view
MDriven Turnkey AngularJS
  • Add AngularUIOverride tagged value on viewmodel column
  • set the value to a file containing your control <yourcontrol>.cshtml
  • Make sure the file exists on the server under EXT_OverridePages
  • Make sure your control gets a name that is unique to your existing views in the app - or else the control will be picked up as a complete view override as well.
MDriven Turnkey MVC <Same instructions as for Angular> but the cshtml must now be razor and your page must be set to use MVC

In the following video tutorial the example of UIOverride, ContentOverride - creating and injecting your own controls in MDriven Turnkey generated UI is given in more practical way to faciliate your user experience.

To make your experience more comfortable, we set the main tags mentioned in the video to the right bar menu of this mini player. Choose the interesting subtitle on the list and immediately get to the exact theme navigation-itemplace in the video. Now you can pick any topic to be instructed without watching the whole video.

content override checkbox wpf turnkey fat client look angular UI override control implementation tagged value data change reaction / mutation observer pattern matching

In WPF-Turnkey-Fatclient you go like this:

    static WindowWecpofTest()
    {
      ViewMetaBase.ContentOverride += HandleContentOverride;
    }
    public static void HandleContentOverride(object sender, ContentOverrideEventArgs args)
    {
      if (args.ViewName == "UIOverride" && args.Owner== "UIOverride" && args.Name== "NumberOfLeaves")
      {
        args.ContinueWithOrg = false;
        ExampleUIOverrideTest myOverride = new ExampleUIOverrideTest();
        Grid.SetColumn(myOverride, args.X);
        Grid.SetRow(myOverride, args.Y);
        Grid.SetColumnSpan(myOverride, args.Colspan);
        Grid.SetRowSpan(myOverride, args.Rowspan);
        Binding b = new Binding("NumberOfLeaves");
        myOverride.SetBinding(ExampleUIOverrideTest.NumberOfLeafsProperty,b);
        (args.StreamCli.TargetForUI as Grid).Children.Add(myOverride);
      }
    }

In WPF-Turnkey-Fatclient you will likely work in Visual Studio having full access to the Turnkey client code. Your controls are then compiled and delivered along with the application-client.

In MDrivenTurnkey for AngualarJS you may not and need not to have access to the Visual Studio at all.

Instead you signal in the ContentOverride column’s tagged value what the cshtml is named:
ContentOverride.png
The important TaggedValue is AngularUIOverride and the file location should be <YourSite>\Views\EXT_OverridePages\AFlowerCtrlPartial.cshtml

In Angular you have access to data from the scope-variable named “data”. This is one example on how to bind:

<h1>Control has access to data Im telling the truth! {{data.NumberOfLeaves}}</h1>

In my example ctrl I wanted to call a javascript everytime my data changed. Maybe there are other ways to accomplish this but I added a MutationObserver to a div that shows my data:

    var MutationObserver = window.MutationObserver ||window.WebKitMutationObserver;
    var myObserver = new MutationObserver(mutationHandler);
    var obsConfig = {
      childList: true,
      subtree: true};
    $(document).ready(function () {
      console.info("INIT mutationHandler");
      myObserver.observe(this, obsConfig);
      myObserver.observe(document.getElementById("TriggerToRedraw"), obsConfig);
    });
       function mutationHandler(mutationRecords) {
      console.info("mutationHandler:");
      var str = $("#TriggerToRedraw")[0].innerHTML;
      console.log("numleaves:" + str);
      var numleaves = Number(str);
      drawStar(100, 100, numleaves, 30, 15);

         };

Whenever the MutationObserver finds a “Mutation” on my div it will call the script with new content of that div.