DevExtreme jQuery - Built-in Layouts

In most cases, you do not have to define layouts yourself. The framework comes with a set of predefined layouts. You can find them in the DevExtreme zip archive or in the folder where you have installed DevExtreme, which is C:\Program Files (x86)\DevExpress 17.2\DevExtreme\Sources\Lib\layouts by default. A folder with layouts is added to the project template as well. So you don't have to add them manually.

As you can see in the layouts folder, each layout is represented by a set of three files.

  • .html
    Includes HTML layout templates for different devices.
  • .css
    Includes CSS rules specific for different devices.
  • .js
    Contains a layout controller that shows a view using the layout template that is appropriate for the device on which the application is running.

Before using predefined layouts, find out which content placeholders and command containers are available in their device-specific versions. This information will be required when defining views and mapping the commands that are added to these views.

Below you will find details about each of the predefined layouts. In addition, you will learn how to use layout sets to specify which layouts should be used in your application and when.

Navbar Layout

The Navbar layout is available for all platforms supported by the framework. This layout is characterized by the presence of a navigation control on a view. The navigation control is global navigation that provides access to the root views of the application.

iOS

NavBar iOS

NOTE
If you place a command in the 'ios-view-footer' command container, add the 'view-footer' content placeholder to your view as well. In this instance, the dxContent component with the 'ios-view-footer' command container defined in the layout will be rendered to the 'view-footer' content placeholder of your view.

Links:

HTML
<link rel="dx-template" type="text/html" href="layouts/NavBar/NavbarLayout.html" />
<script type="text/javascript" src="layouts/NavBar/NavbarLayout.js"></script>
<link rel="stylesheet" type="text/css" href="layouts/NavBar/NavbarLayout.css" />

Android

NavBar Android

Links:

HTML
<link rel="dx-template" type="text/html" href="layouts/NavBar/NavbarLayout.html" />
<script type="text/javascript" src="layouts/NavBar/NavbarLayout.js"></script>
<link rel="stylesheet" type="text/css" href="layouts/NavBar/NavbarLayout.css" />

Windows Phone

NavBar Windows 8

Links:

NOTE
The NavBar layout for Windows Phone requires links to the PivotLayout and SimpleLayout files in addition to the NavBar layout files.
HTML
<link rel="dx-template" type="text/html" href="layouts/NavBar/NavbarLayout.html" />
<script type="text/javascript" src="layouts/NavBar/NavbarLayout.js"></script>
<link rel="stylesheet" type="text/css" href="layouts/NavBar/NavbarLayout.css" />

<link rel="stylesheet" type="text/css" href="layouts/Pivot/PivotLayout.css" />
<link rel="dx-template" type="text/html" href="layouts/Pivot/PivotLayout.html"/>
<script type="text/javascript" src="layouts/Pivot/PivotLayout.js"></script>

<link rel="stylesheet" type="text/css" href="layouts/Simple/SimpleLayout.css" />
<link rel="dx-template" type="text/html" href="layouts/Simple/SimpleLayout.html"/>
<script type="text/javascript" src="layouts/Simple/SimpleLayout.js"></script>

Generic

NavBar Generic

NOTE
If you place a command in the 'generic-view-footer' command container, add the 'view-footer' content placeholder to your view as well. In this instance, the dxContent component with the 'generic-view-footer' command container defined in the layout will be rendered to the 'view-footer' content placeholder of your view.

Links:

HTML
<link rel="dx-template" type="text/html" href="layouts/NavBar/NavbarLayout.html" />
<script type="text/javascript" src="layouts/NavBar/NavbarLayout.js"></script>
<link rel="stylesheet" type="text/css" href="layouts/NavBar/NavbarLayout.css" />

Pivot Layout

The Pivot layout is available for Windows Phone 8 applications. This layout is characterized by the presence of a pivot control on a view. The pivot control is a global navigation that provides access to the root views of the application.

Pivot

Links:

HTML
<link rel="dx-template" type="text/html" href="layouts/Pivot/PivotLayout.html" />
<script type="text/javascript" src="layouts/Pivot/PivotLayout.js"></script>
<link rel="stylesheet" type="text/css" href="layouts/Pivot/PivotLayout.css" />

SlideOut Layout

The SlideOut layout is available for all the platforms supported by the framework. This layout is characterized by its slide-out menu that is hidden behind the main screen. This menu can be revealed by a click on the top left corner menu icon. The slide-out menu represents a global navigation that provides access to the root views of the application.

iOS

SlideOut iOS

SlideOut iOS

NOTE
If you place a command to the 'ios-view-footer' command container, add the 'view-footer' content placeholder to your view as well. In this instance, the dxContent component with the 'ios-view-footer' command container defined in the layout will be rendered to the 'view-footer' content placeholder of your view.

Links:

HTML
<link rel="dx-template" type="text/html" href="layouts/SlideOut/SlideOutLayout.html" />
<script type="text/javascript" src="layouts/SlideOut/SlideOutLayout.js"></script>
<link rel="stylesheet" type="text/css" href="layouts/SlideOut/SlideOutLayout.css" />

Android

SlideOut Android

Links:

HTML
<link rel="dx-template" type="text/html" href="layouts/SlideOut/SlideOutLayout.html" />
<script type="text/javascript" src="layouts/SlideOut/SlideOutLayout.js"></script>
<link rel="stylesheet" type="text/css" href="layouts/SlideOut/SlideOutLayout.css" />

Windows Phone 8

SlideOut Windows Phone 8

Links:

HTML
<link rel="dx-template" type="text/html" href="layouts/SlideOut/SlideOutLayout.html" />
<script type="text/javascript" src="layouts/SlideOut/SlideOutLayout.js"></script>
<link rel="stylesheet" type="text/css" href="layouts/SlideOut/SlideOutLayout.css" />

Generic

SlideOut Generic

SlideOut Generic

NOTE
If you place a command in the 'generic-view-footer' command container, add the 'view-footer' content placeholder to your view as well. In this instance, the dxContent component with the 'generic-view-footer' command container defined in the layout will be rendered to the 'view-footer' content placeholder of your view.

Links:

HTML
<link rel="dx-template" type="text/html" href="layouts/SlideOut/SlideOutLayout.html" />
<script type="text/javascript" src="layouts/SlideOut/SlideOutLayout.js"></script>
<link rel="stylesheet" type="text/css" href="layouts/SlideOut/SlideOutLayout.css" />

Split Layout

The Split layout is designed for Windows, iOS and Android tablet applications to effectively organize space on a screen. In this layout, there are two panes - a "master" pane and a "detail" pane. A "master" pane usually presents a list of items. A "detail" pane presents detail information on the item selected in the "master" pane. The type of the layout controller and the layout markup to be used for each pane are determined in a root Split layout controller. The IOSSplitLayoutController that is used in iOS apps applies the Simple layout for both panes. The AndroidSplitLayoutController that is used in Android apps and Win8SplitLayoutController that is used in Windows apps apply the Empty layout for both panes.

When defining views, specify the pane in which a view will be displayed in the Split layout by using the pane option of the corresponding dxView markup component. In addition, denote the layout placeholder in which the view will be displayed within the pane. The Simple and Empty layouts that are used in split layout panes provide the 'content' placeholder. So, put the view's markup within this placeholder. For details on how to do this, refer to the Insert View into Layout topic.

NOTE
If you use the Split layout, the DevExtreme SPA framework adds an additional navigation stack for the "detail" pane. This stack holds all views whose pane option is set to "detail" or is not defined. To put a view to the main navigation stack, set the pane option to "master". If you navigate from the Split layout to a non-Split layout, set the pane option of the target view to "master". Otherwise, this view will be put to the additional ("detail") stack, which may cause unexpected behavior.

iOS

Split

Links:

HTML
<link rel="dx-template" type="text/html" href="layouts/Split/SplitLayout.html" />
<script type="text/javascript" src="layouts/Split/SplitLayout.js"></script>
<link rel="stylesheet" type="text/css" href="layouts/Split/SplitLayout.css" />
<link rel="dx-template" type="text/html" href="layouts/Simple/SimpleLayout.html" />
<script type="text/javascript" src="layouts/Simple/SimpleLayout.js"></script>
<link rel="stylesheet" type="text/css" href="layouts/Simple/SimpleLayout.css" />

Android

Split

Links:

HTML
<link rel="dx-template" type="text/html" href="layouts/Split/SplitLayout.html" />
<script type="text/javascript" src="layouts/Split/SplitLayout.js"></script>
<link rel="stylesheet" type="text/css" href="layouts/Split/SplitLayout.css" />
<link rel="dx-template" type="text/html" href="layouts/Empty/EmptyLayout.html" />
<script type="text/javascript" src="layouts/Empty/EmptyLayout.js"></script>
<link rel="stylesheet" type="text/css" href="layouts/Empty/EmptyLayout.css" />

Windows Phone

Split

Links:

HTML
<link rel="dx-template" type="text/html" href="layouts/Split/SplitLayout.html" />
<script type="text/javascript" src="layouts/Split/SplitLayout.js"></script>
<link rel="stylesheet" type="text/css" href="layouts/Split/SplitLayout.css" />
<link rel="dx-template" type="text/html" href="layouts/Empty/EmptyLayout.html" />
<script type="text/javascript" src="layouts/Empty/EmptyLayout.js"></script>
<link rel="stylesheet" type="text/css" href="layouts/Empty/EmptyLayout.css" />

Customize Split Layout

You can replace layouts used in panes with other ones. For this purpose, you will have to specify a custom layout set where you will create the IOSSplitLayoutController, AndroidSplitLayoutController or/and Win8SplitLayoutController controller(s) passing an object with a specified panesConfig field as a parameter.

JavaScript
window.MyApp = {};
$(function() {
    MyApp.app = new DevExpress.framework.html.HtmlApplication({
        layoutSet:[
            { platform: 'android', controller: new IOSSplitLayoutController() },
            { platform: 'ios', controller: new IOSSplitLayoutController({paneConfig: {
                    content: {
                        controller: new DX.framework.html.NavBarController(),
                        selector: ".master-pane"
                    },
                    detail: {
                        controller: new DX.framework.html.SimpleLayoutController(),
                        selector: ".detail-pane"
                    }                   
                })
            },
            { platform: 'win8', phone: false, controller: new Win8SplitLayoutController() }
        ],
        namespace: MyApp
    });
});

Show Blank View in a Detail Pane

Views shown in a "detail" pane may be accompanied by commands. After executing these commands, navigation to a view may be required. For instance, a particular view should be shown instead of the detail view of the object that has just been removed via a "Delete" command. In phone applications, the "Delete" command executed in a detail view usually returns to a list view (a previous view). In a tablet application, a list view remains displayed in the "master" pane when performing manipulations in the "detail" pane. Thus, it is recommended that you navigate to a blank view in the "detail" pane in such scenarios. The "Blank" view is available within the application project template that comes with DevExtreme. You can use this view as is.

JavaScript
handleDelete: function() {
    //If an object is removed
        if(viewInfo.canBack) {
            AppNamespace.app.back();
        }
        else {
            AppNamespace.app.navigate("Blank", { target: "current" });
        }
    //
},

Save the State of Slitted Views

When refreshing an application page in a browser, the application is recreated and the views that were displayed before the refresh should be displayed again. If you are going to run a Split layout application in a browser, implement the saving and restoring of the application's state. For this purpose, add the Split layout's controller to the state sources collection of the application's state manager. To do this, access the state manager using the stateManager field of the HtmlApplication object and call the addStateSource(stateSource) method passing the Split layout controller as a parameter.

JavaScript
window.MyApp = window.MyApp || {};
$(function() {
    MyApp.app = new DevExpress.framework.html.HtmlApplication({
        namespace: MyApp,
        layoutSet: DevExpress.framework.html.layoutSets['split'],
        //...
    });
    MyApp.app.stateManager.addStateSource(DevExpress.framework.html.layoutSets["split"].controller);
    //...
});

The Split layout controller can be treated as a state source because it has the methods that are required by the state manager to save/restore/remove the application state.

To save the state of the Split layout application when the application page is refreshed, call the saveState method of the HtmlApplication object on the window's unload event.

JavaScript
$(window).unload(function() {
    MyApp.app.saveState();
});

The saveState method will call the saveState method of the application's state manager. The latter will send a request to save the state to all the registered state sources, and to the Split layout controller in particular.

NOTE
This method is called in the DevExtreme Basic Application and Multi-Channel Application templates provided by Visual Studio.

The saved state will be automatically restored by the framework when recreating the application.

Simple Layout

The Simple layout is available for all the platforms supported by the framework. This layout is characterized by the absence of a navigation control on the view. Thus, it is normally used for the views that are invoked to present specific data, perform particular actions and return back to the previous view or pass to the next context view.

iOS

Simple iOS

NOTE
If you place a command to the 'ios-view-footer' command container, add the 'view-footer' content placeholder to your view as well. In this instance, the dxContent component with the 'ios-view-footer' command container defined in the layout will be rendered to the 'view-footer' content placeholder of your view.

Links:

HTML
<link rel="dx-template" type="text/html" href="layouts/Simple/SimpleLayout.html" />
<script type="text/javascript" src="layouts/Simple/SimpleLayout.js"></script>
<link rel="stylesheet" type="text/css" href="layouts/Simple/SimpleLayout.css" />

Android

Simple Android

Links:

HTML
<link rel="dx-template" type="text/html" href="layouts/Simple/SimpleLayout.html" />
<script type="text/javascript" src="layouts/Simple/SimpleLayout.js"></script>
<link rel="stylesheet" type="text/css" href="layouts/Simple/SimpleLayout.css" />

Windows Phone 8

Simple Windows Phone 8

Links:

HTML
<link rel="dx-template" type="text/html" href="layouts/Simple/SimpleLayout.html" />
<script type="text/javascript" src="layouts/Simple/SimpleLayout.js"></script>
<link rel="stylesheet" type="text/css" href="layouts/Simple/SimpleLayout.css" />

Generic

Simple Generic

NOTE
If you place a command to the 'generic-view-footer' command container, add the 'view-footer' content placeholder to your view as well. In this instance, the dxContent component with the 'generic-view-footer' command container defined in the layout will be rendered to the 'view-footer' content placeholder of your view.

Links:

HTML
<link rel="dx-template" type="text/html" href="layouts/Simple/SimpleLayout.html" />
<script type="text/javascript" src="layouts/Simple/SimpleLayout.js"></script>
<link rel="stylesheet" type="text/css" href="layouts/Simple/SimpleLayout.css" />

Popup Layout

The Popup Layout is available for all the platforms supported by the framework. This layout is used to show modal views in a popup window.

The Popup Layout uses the Popup widget to display a view in a popup window. The content of the popup window is managed by a specified layout controller. By default, the SimpleLayoutController is used for the popup window. This means that when defining a modal view, find out which content placeholders and command containers are available in the Simple Layout.

Links:

HTML
<link rel="dx-template" type="text/html" href="layouts/Simple/SimpleLayout.html" />
<script type="text/javascript" src="layouts/Simple/SimpleLayout.js"></script>
<link rel="stylesheet" type="text/css" href="layouts/Simple/SimpleLayout.css" />
<link rel="dx-template" type="text/html" href="layouts/Popup/PopupLayout.html" />
<script type="text/javascript" src="layouts/Popup/PopupLayout.js"></script>
<link rel="stylesheet" type="text/css" href="layouts/Popup/PopupLayout.css" />
NOTE
Add links to the Popup Layout files after all other layout links, because the Popup Layout will be added to the layout set that is used in your application, if you use one of the predefined layout sets - "navbar", "simple", "slideout" and "split".

Customize Popup Layout Content

You can replace the layout that is used in the popup window with another one. For this purpose, you will have to specify a custom layout set where you will create the PopupLayoutController controller passing an object with a specified childController field as a parameter.

Empty Layout

The Empty layout includes a single 'content' content placeholder on any platform.

Links:

HTML
<link rel="dx-template" type="text/html" href="layouts/Empty/EmptyLayout.html" />
<script type="text/javascript" src="layouts/Empty/EmptyLayout.js"></script>
<link rel="stylesheet" type="text/css" href="layouts/Empty/EmptyLayout.css" />

Desktop Layout

The Desktop layout is available for the 'generic' platform only. This platform is set when the application is running in a desktop, or the current platform is not known to the framework. You can also set the 'generic' platform manually to make the application look like a web site.

The Desktop layout is characterized by the presence of a navigation control on a view. The navigation control is a global navigation that provides access to the root views of the application. In addition, there is a toolbar on the view, which you can use to add custom actions.

Desktop Layout

Links:

HTML
<link rel="dx-template" type="text/html" href="layouts/Desktop/DesktopLayout.html" />
<script type="text/javascript" src="layouts/Desktop/DesktopLayout.js"></script>
<link rel="stylesheet" type="text/css" href="layouts/Desktop/DesktopLayout.css" />

Default Command Mapping

Built-in layouts come with default command mapping. This means that if you use particular identifiers for your commands, these commands are automatically added to the command containers of the predefined layouts. The following table details a command location on a toolbar representing a command container according default command mapping.

Command Container Before Center After Menu
ios-header-toolbar "back"
"cancel"
"edit"
"save"
"create"
ios-view-footer "delete"
android-header-toolbar "back" "edit"
"save"
"create"
"cancel"
"delete"
android-footer-toolbar "edit"
"save"
"create" "delete"
android-simple-toolbar "back"
"save"
"create" "edit"
"cancel"
"delete"
generic-header-toolbar "back"
"cancel"
"edit"
"save"
"create"
generic-view-footer "delete"
win8-appbar "create" "edit"
"cancel"
"save"
"delete"
win8-toolbar "previousPage"
win8-phone-appbar "create"
"edit"
"cancel"
"save"
"delete"

Customize Layout CSS

Layout CSS includes classes from the DevExtreme themes. You can customize the classes for any of the DevExtreme themes using the DevExtreme Theme Builder.

DevExtreme Theme Builder

For details, refer to the Theme Builder article.

Ready-to-Use Layout Sets

In non-basic applications, different layouts can be used for different views. For example, Android apps have a navbar on root views only. So to implement such an application, you will have to use a Navbar layout for root views and a Simple layout for child views. To save you time, the framework comes with ready-to-use layout sets.

  • navbar
    Different layout sets are used for different platforms.

  • slideOut
    All views are displayed in the Slideout layout on all platforms.

  • split
    Designed to be used on Windows Phone, iOS and Android tablet devices.

    • Windows Phone
      Root views are displayed in the Navbar layout. Other views are displayed in the Split layout.
    • iOS and Android
      All views are displayed in the Split layout. It is recommended, that the first navigated view in an application includes global navigation. For this purpose, implement a 'navigation' view with a widget(s) that will allow you to navigate to the application's root views.
  • simple
    All views are displayed in the Simple layout on all platforms.

These layout sets are available from the DevExpress.framework.html.layoutSets object. To get a particular layout set, use one of the following approaches.

  • DevExpress.framework.html.layoutSets['navbar']

  • DevExpress.framework.html.layoutSets.navbar

To specify the layout set that you are going to use in your application, use the layoutSet configuration option of your HtmlApplication object.

JavaScript
window.MyApp = {};
$(function() {
    MyApp.app = new DevExpress.framework.html.HtmlApplication({
        namespace: MyApp,
        layoutSet: DevExpress.framework.html.layoutSets['navbar'],
        //...
    });
});

Ensure that the layouts that are demanded by the specified layout set are linked in the application page.

HTML
<!-- Layouts -->
<script type="text/javascript" src="layouts/NavBar/NavbarLayout.js"></script>
<link rel="stylesheet" type="text/css" href="layouts/NavBar/NavbarLayout.css" />
<link rel="dx-template" type="text/html" href="layouts/NavBar/NavbarLayout.html"/>
<script type="text/javascript" src="layouts/Pivot/PivotLayout.js"></script>
<link rel="stylesheet" type="text/css" href="layouts/Pivot/PivotLayout.css" />
<link rel="dx-template" type="text/html" href="layouts/Pivot/PivotLayout.html"/>
<script type="text/javascript" src="layouts/Simple/SimpleLayout.js"></script>
<link rel="stylesheet" type="text/css" href="layouts/Simple/SimpleLayout.css" />
<link rel="dx-template" type="text/html" href="layouts/Simple/SimpleLayout.html"/>

Global Navigation Items

All the predefined layout sets, except for Simple, utilize the layouts that include a widget that implements global navigation. This widget provides access to the main views of the application - the root views. To specify which views must be accessible from global navigation, use the navigation configuration option of the HtmlApplication object.

JavaScript
window.MyApp = {};
$(function() {
    MyApp.app = new DevExpress.framework.html.HtmlApplication({
        namespace: MyApp,
        layoutSet: DevExpress.framework.html.layoutSets['navbar'],
        navigation: [
            {
                title: "Home",
                onExecute: "#home",
                icon: "home"
            },
            {
                title: "About",
                onExecute: "#about",
                icon: "info"
            }
        ],
        //...
    });
});
NOTE
In specific scenarios, you can define global navigation dynamically and render the navigation control so that the defined navigation items are displayed. For this purpose, use the createNavigation and renderNavigation methods of the htmlApplication object.

When navigating to a view, the target URI is compared with the URI provided by the onExecute option of each global navigation command. If there is a command whose URI coincides with the navigated URI, the corresponding item of the widget that implements global navigation (navbar item, slide-out menu item or pivot item) is selected automatically.

There can be scenarios, when you have to select a certain navigation item manually in code. For instance, there is a navigation item with the view1 URI. When navigating to the view1 using the view1/1 URI, this navigation item will not be selected, because its URI does not coincide with the navigated URI. To select it, do the following.

  • Set the id option for the required navigation commands.

    JavaScript
    navigation: [
        {
            id: "view1"
            title: "View1",
            onExecute: "#view1"
        },
        {
            id: "view2"
            title: "View2",
            onExecute: "#view2"
        }
    ],
  • Set the currentNavigationItemId field to the corresponding command id within the required ViewModels.

    JavaScript
    MyApp.view1 = function (params) {
        var viewModel = {
            currentNavigationItemId = "view1"
        };
        return viewModel;
    };

Custom Layout Sets

If the predefined layout sets do not address your task at hand, introduce a custom layout set.

NOTE
Even if you need to use a single layout for all views in your app, introduce a layout set that consists of this single layout.

A custom layout set is an array of objects that define which layout controller should be used and when. Here is an example.

JavaScript
window.MyApp = {};
$(function() {
    MyApp.app = new DevExpress.framework.html.HtmlApplication({
        layoutSet:[
            { platform: 'android', controller: new MyAndroidLayoutController() },
            { platform: 'ios', controller: new MyiOSLayoutController() }
        ],
        namespace: MyApp
    });
});

The object defining a layout within a layout set should expose the following fields.

  • controller
    Specifies an instance of a layout controller.
  • root
    Indicates whether or not the view to which the application navigates must be a root view (the view that is available from global navigation).
  • customResolveRequired
    Indicates whether or not the specified layout controller must be excluded when choosing the most appropriate controller for a view. When you set this field to true, it is implied that you will set it for views manually in a custom context. For this purpose, use the resolveLayoutController event (read below).
  • modal
    Indicates whether or not the specified layout controller must be used to manage a modal view display.
  • Any field of the device object.
    Specifies in which device the layout can be used.
NOTE
Define contexts for using layout controllers precisely, so that several layout controllers cannot be found to be appropriate in any specific context. Otherwise, an exception will be raised.

In very specific cases, when the fields listed above do not allow you to define a context for using a layout, handle the application's resolveLayoutController event. The viewInfo field of the object passed as the event handler's parameter provides you access to information on the currently displayed view. Set the layout controller that should be used for this view using the layoutController field of the object passed as the parameter.

NOTE
The layout controller that is set for a view within the resolveLayoutController event handler should be already initialized. This means that the required templates (layout template and a template for a loading view) are prepared beforehand. For this purpose, this controller must be added to the layout set that is assigned to the application. When the application is created, the layout controllers that are registered using the layoutSet configuration option and that are appropriate for the current device are initialized.
JavaScript
window.AppNamespace = {};
$(function () {
    AppNamespace.myController = new myLayoutController({ layoutTemplateName: "myLayout" });     
    AppNamespace.app = new DevExpress.framework.html.HtmlApplication(
        {
            namespace: AppNamespace,
            layoutSet: [
                { platform: 'android', controller: new MyAndroidLayoutController() },
                { platform: 'ios', controller: new MyiOSLayoutController() },
                { customResolveRequired: true, controller: AppNamespace.myController }
            ],
            //...
         }
    );
    AppNamespace.app.router.register(":view/:name", { view: "home", name: '' });
    AppNamespace.app.on("resolveLayoutController", function(args) {
        var viewName = args.viewInfo.viewName;
        if(viewName === "about") {
            args.layoutController = AppNamespace.myController;
        }
    });
    AppNamespace.app.navigate();
});

You can assign a combination of several predefined layout sets to the application's layoutSet option. In this instance, handle the application's resolveLayoutController event to specify the contexts in which the layout controllers from the combined layout sets must be applied.

JavaScript
function findController(name, controllers) {
    var result = $.grep(controllers, function (item, index) {
        return item.controller.name == name;
    });
    return result.length ? result[0].controller : null;
}
window.AppNamespace = {};
$(function() {
    var layoutSet = [];
    layoutSet.push.apply(layoutSet, DevExpress.framework.html.layoutSets["navbar"]);
    layoutSet.push.apply(layoutSet, DevExpress.framework.html.layoutSets["empty"]);

    AppNamespace.app = new DevExpress.framework.html.HtmlApplication({
        namespace: AppNamespace,
        layoutSet: layoutSet,
        //...
    });
    AppNamespace.app.router.register(":view/:id", { view: "home", id: undefined });
    AppNamespace.app.on("resolveLayoutController", function (args) {
        if (args.viewInfo.viewName == 'home') {
            args.layoutController = findController('empty', args.availableLayoutControllers);
        }
    });
    AppNamespace.app.navigate();
});

As you can see in the code above, you can use the application's collection of available controllers when deciding which layout controller to use for the currently displayed view. This collection includes objects from the application's layout set. But not all the objects - just the ones that can be used for the current device (its platform and type). To access this collection, use the availableLayoutControllers field of the object passed as the resolveLayoutController event handler parameter. To find the required controller within the availableLayoutControllers collection, use the layout controller's name field.