Skip to main content
All docs

MVVM - Use Report Designer API from ViewModel

  • 5 minutes to read

The DevExpress MVVM Framework allows you to access the ReportDesigner methods from commands defined in the ViewModel. You can develop your own API that extends the built-in functionality of ReportDesigner and optimally meets your requirements.

In this example the Behavior mechanism initializes a service that implements ReportDesigner actions. The service is defined as follows:

using DevExpress.Mvvm.UI;
using DevExpress.Mvvm.UI.Interactivity;
using DevExpress.Xpf.Reports.UserDesigner;
using DevExpress.XtraReports.UI;
using System;
using System.Collections.Generic;
using System.IO;

namespace ManipulateReportDesignerDocuments_MVVM {
    public interface IReportDesignerAPIService {
        IEnumerable<ReportDesignerDocument> Documents { get; }
        ReportDesignerDocument ActiveDocument { get; }
        ReportDesignerDocument NewReport(XtraReport report = null);
        ReportDesignerDocument Open();
        ReportDesignerDocument Open(Stream stream);

    public class ReportDesignerAPIService : ServiceBase, IReportDesignerAPIService {
        ReportDesigner Designer => (ReportDesigner)AssociatedObject;

        public IEnumerable<ReportDesignerDocument> Documents => Designer.Documents;

        public ReportDesignerDocument ActiveDocument => Designer.ActiveDocument;

        public ReportDesignerDocument NewReport(XtraReport report = null) {
            Func<XtraReport> reportFactory = null;
            if(report != null)
                reportFactory = () => report;
            return Designer.NewDocument(reportFactory);

        public ReportDesignerDocument Open() {
            return Designer.OpenDocument();

        public ReportDesignerDocument Open(Stream stream) {
            return Designer.OpenDocument(stream);

The ReportDesignerAPIService is specified as custom behavior. For more information on the Behavior mechanism in DevExpress MVVM Framework, review the following help topic: Behaviors.

The following code uses the ReportDesignerAPIService class as a custom Behavior for the ReportDesigner element in the View:

<dx:ThemedWindow x:Class="ManipulateReportDesignerDocuments_MVVM.MainWindow"
        mc:Ignorable="d" WindowKind="Tabbed" WindowState="Maximized"
        Title="MainWindow" Height="450" Width="800">
        <!-- ... -->
            <dxrud:ReportDesignerBrowserView CloseWindowWhenLastTabIsClosed="False" />
                <Binding Path="DefaultReport" />
                <local:ReportDesignerAPIService />
        <!-- ... -->

The MainViewModel ViewModel class gets the ReportDesignerAPIService service and implements MVVM commands based on the service methods:

using DevExpress.Mvvm;
using DevExpress.Mvvm.DataAnnotations;
using DevExpress.Xpf.Reports.UserDesigner;
using DevExpress.XtraReports.UI;
using System;
using System.Linq;
using System.Windows;
using System.Windows.Resources;

namespace ManipulateReportDesignerDocuments_MVVM {
    public class MainViewModel : ViewModelBase {
        public XtraReport DefaultReport { get; set; }

        IReportDesignerAPIService ReportDesignerAPI => ServiceContainer.GetService<IReportDesignerAPIService>();

        protected override void OnInitializeInRuntime() {
            DefaultReport = new XtraReport();

        public void NewReport() {
        public bool CanNewReport() => ReportDesignerAPI != null;

        public void OpenReport() {
        public bool CanOpenReport() => ReportDesignerAPI != null;

        public void OpenReportFromStream() {
            var stream = Application.GetResourceStream(new Uri("Resources/Invoice.repx", UriKind.Relative))?.Stream;
            if(stream != null) {
                using(stream) {
        public bool CanOpenReportFromStream() => ReportDesignerAPI != null;

        public void CloseActiveDocument() {
        public bool CanCloseActiveDocument() => ReportDesignerAPI?.ActiveDocument != null;

        public void ActivateFirstDocumentTab() {
            ReportDesignerDocument firstTab = ReportDesignerAPI.Documents.First();
        public bool CanActivateFirstDocumentTab() => ReportDesignerAPI?.Documents.Any() ?? false;

        public void SwitchActiveDocumentView() {
            ReportDesignerDocument activeDocument = ReportDesignerAPI.ActiveDocument;
            activeDocument.ViewKind = activeDocument.ViewKind == ReportDesignerDocumentViewKind.Designer
                ? ReportDesignerDocumentViewKind.Preview
                : ReportDesignerDocumentViewKind.Designer;
        public bool CanSwitchActiveDocumentView() => ReportDesignerAPI?.ActiveDocument != null;

For more information on auto-generated commands, review the following help topic: POCO Commands.

The application appears as follows:

Use Report Designer API from ViewModel - Screenshot

View Example: How to Use MVVM Framework to Create Custom Commands for Report Designer