durandalsingle-page-applicationdurandal-2.0durandal-navigation

Durandal router - how to define view as modal in routes definition


How can I declare view to be opened as modal directly on click?

My route's definition is:

var routes = [
    { route: '', moduleId: 'home', title: 'My Apps', nav: true },
    { route: 'aboutus', moduleId: 'aboutus', title: 'About Us', nav: true },
    { route: 'help', moduleId: 'help', title: 'Help', nav: true },
    { route: 'faq', moduleId: 'faq', title: 'FAQ', nav: true },
    { route: 'contactus', moduleId: 'contactus', title: 'Contact', nav: true }
];

I want to open 'contactus' module as modal dialog on a current screen - don't want to navigate to another view.

Have no idea how to acomplish that. Many thanks for suggestions.


Solution

    1. Create Custom modal
    2. Use Compose binding
    3. Modifed router on shell view and model

    create custom modal

    CustomModal.html

    <div class="modal-content messageBox">
        <div class="modal-header">
            Custom modal example
        </div>
        <div class="modal-content">
            <div data-bind="compose: $root.moduleId"></div>
        </div>
        <div class="modal-footer">
           <button class="btn btn-primary" data-bind="click: ok">Ok</button>
        </div>
    </div>
    

    CustomModal.js

    define(['plugins/dialog', 'knockout'], function (dialog, ko) {
    
        var customModal = function(moduleId)
        {
           this.moduleId = moduleId;
        };
    
        customModal.prototype.ok = function()
        {
           dialog.close(this);
        };
    
        customModal.show = function(moduleId)
        {
           return dialog.show(new customModal(moduleId));
        };
    
        return customModal;
    });
    

    and then, modified shell.js and shell.html

    shell.js

    define(['plugins/router', '../customModal'], function(router, customModal)
    { 
       var modified_routes = [
         // Normal route configuration
         { route: '', moduleId: 'home', title: 'My Apps', nav: true },
         { route: 'aboutus', moduleId: 'aboutus', title: 'About Us', nav: true },
    
         // Modified route configuration, included add-on property
         { 
           route: 'contactus', 
           moduleId: 'contactus', 
           title: 'Contact', 
           nav: true, 
           showOnModal: true // add-on property
         }
       ];
    
       return {
          showModal: function(data)
          {
             customModal.show(data.moduleId);
          },
          activate: function()
          {
             router.map(modified_routes).buildNavigationModel().activate();
          }
       }  
    });
    

    shell.html

    <ul class="nav navbar-nav" data-bind="foreach: router.navigationModel">
        <li>
             <!-- ko if: ! showOnModal -->
             <a data-bind="attr: { href: hash }"><span data-bind="text: title"></span></a>
             <!-- /ko -->
    
             <!-- ko if: showOnModal -->
             <a data-bind="click: $root.showModal"><span data-bind="text: title"></span></a>
             <!-- /ko -->
        </li>
    </ul>