Skip to main content

Use a Custom View Item to Add a Button to a Detail View

  • 6 minutes to read

This article describes how to add a custom control to a Detail View. If you want to display standard XAF Actions in a Detail View, use the technique described in the following topic: Action Container View Item.

A custom View Item should be a ViewItem descendant. You can also inherit it from any of the built-in View Items that XAF supplies. See the following topics for additional information on View Items:

Create a WinForms-Specific View Item

View Example: How to: Use a Custom View Item to Add a Button to a Detail View (WinForms and ASP.NET Web Forms)

Create the ButtonDetailViewItemWin View Item in the WinForms module project (MySolution.Module.Win). If your solution does not contain this project, add this View Item to the WinForms application project (MySolution.Win). Decorate this View Item with the ViewItemAttribute to make this View Item appear in the Application Model‘s ViewItems node.

File:
MySolution.Win\ButtonDetailViewItemWin.cs in solutions without the WinForms-specific Module project;
MySolution.Module.Win\ButtonDetailViewItemWin.cs(.vb) in solutions with the WinForms-specific Module project.

using System;
using System.Windows.Forms;
using DevExpress.ExpressApp.Editors;
using DevExpress.ExpressApp.Model;
using DevExpress.ExpressApp;
// ...
public interface IModelButtonDetailViewItemWin : IModelViewItem { }

[ViewItemAttribute(typeof(IModelButtonDetailViewItemWin))]
public class ButtonDetailViewItemWin : ViewItem {
    public ButtonDetailViewItemWin(IModelViewItem model, Type objectType)
        : base(objectType, model.Id) {
    }
    protected override object CreateControlCore() {
        Button button = new Button();
        button.Text = "Click me!";
        button.Click += button_Click;
        return button;
    }
    void button_Click(object sender, EventArgs e) {
        throw new UserFriendlyException("Action is executed!");
    }
}

Create an ASP.NET Web Forms-Specific View Item

View Example: How to: Use a Custom View Item to Add a Button to a Detail View (WinForms and ASP.NET Web Forms)

In the ASP.NET Web Forms Module project, create the ButtonDetailViewItemWeb View Item and decorate it with the ViewItemAttribute to make this View Item appear in the Application Model’s ViewItems node.

File: MySolution.Module.Web\ButtonDetailViewItemWeb.cs.

using System;
using DevExpress.ExpressApp.Editors;
using DevExpress.ExpressApp.Model;
using DevExpress.ExpressApp.Web;
using DevExpress.Web.ASPxEditors;
// ...
public interface IModelButtonDetailViewItemWeb : IModelViewItem { }

[ViewItemAttribute(typeof(IModelButtonDetailViewItemWeb))]
public class ButtonDetailViewItemWeb : ViewItem {
    public ButtonDetailViewItemWeb(IModelViewItem model, Type objectType)
        : base(objectType, model.Id) {
    }
    protected override object CreateControlCore() {
        ASPxButton button = new ASPxButton();
        button.Text = "Click me!";
        button.EnableClientSideAPI = true;
        button.Click += button_Click;
        return button;
    }
    void button_Click(object sender, EventArgs e) {
        WebWindow.CurrentRequestWindow.RegisterClientScript("ShowAlert", 
@"alert('Action is executed!');");
    }
}

Create an ASP.NET Core Blazor-Specific View Item

View Example: How to: Use a Custom View Item to Add a Button to a Detail View (ASP.NET Core Blazor)

  1. Create a new Razor component (ButtonRenderer in this example) in the ASP.NET Core Blazor module project (MySolution.Module.Blazor). If your solution does not contain this project, add this component to the application project (MySolution.Blazor.Server). In this component, configure the DxButton component, add the Create method that creates RenderFragment, and handle the Click event.

    Note that the component name and its file name should be the same. For more information on Razor component naming conventions, refer to the following section: Names.

    File:
    MySolution.Blazor.Server\Editors\ButtonRenderer.razor in solutions without the ASP.NET Core Blazor-specific Module project;
    MySolution.Module.Blazor\Editors\ButtonRenderer.razor in solutions with the ASP.NET Core Blazor-specific Module project.

    @using DevExpress.Blazor
    
    <DxButton Text=@ComponentModel.Text Click=@(() => ComponentModel.ClickFromUI()) />
    
    @code {
        [Parameter]
        public ButtonModel ComponentModel { get; set; }
        public static RenderFragment Create(ButtonModel componentModel) =>
            @<ButtonRenderer ComponentModel=@componentModel />;
    }
    
  2. Ensure that the component’s Build Action property is set to Content.

  3. Create a ComponentModelBase descendant and name it ButtonModel. In this class, add properties and methods that describe your component.

    File:
    MySolution.Blazor.Server\Editors\ButtonModel.cs in solutions without the ASP.NET Core Blazor-specific Module project;
    MySolution.Module.Blazor\Editors\ButtonModel.cs in solutions with the ASP.NET Core Blazor-specific Module project.

    using System;
    using DevExpress.ExpressApp.Blazor.Components.Models;
    
    namespace MySolution.Module.Blazor {
        public class ButtonModel : ComponentModelBase {
            public string Text {
                get => GetPropertyValue<string>();
                set => SetPropertyValue(value);
            }
            public void ClickFromUI() {
                Click?.Invoke(this, EventArgs.Empty);
            }
            public event EventHandler Click;
        }
    }
    
  4. Create the ButtonDetailViewItemBlazor View Item in the ASP.NET Core Blazor module project (MySolution.Module.Blazor). If your solution does not contain this project, add this component to the ASP.NET Core Blazor application project (MySolution.Blazor.Server). Decorate this View Item with the ViewItemAttribute to make this View Item appear in the Application Model’s ViewItems node.

  5. Override the CreateControlCore method to get a ButtonHolder instance. ButtonHolder returns a render fragment with the custom component. Note that in the XAF Blazor application, CreateControlCore should return an instance that implements the IComponentContentHolder interface.

  6. Override the OnControlCreated method. In this method, subscribe to the component model’s Click event. Implement the logic in the ComponentModel_Click event handler (in our example, the ShowMessage(String, InformationType, Int32, InformationPosition) is called).

  7. Override the BreakLinksToControls() method. In this method, unsubscribe from the component model’s Click event to release resources.

    File:
    MySolution.Blazor.Server\Editors\ButtonDetailViewItemBlazor.cs in solutions without the ASP.NET Core Blazor-specific Module project;
    MySolution.Module.Blazor\Editors\ButtonDetailViewItemBlazor.cs in solutions with the ASP.NET Core Blazor-specific Module project.

    using System;
    using DevExpress.ExpressApp;
    using DevExpress.ExpressApp.Blazor;
    using DevExpress.ExpressApp.Editors;
    using DevExpress.ExpressApp.Model;
    using Microsoft.AspNetCore.Components;
    using MySolution.Module.Blazor.Editors;
    using DevExpress.ExpressApp.Blazor.Components;
    
    namespace MySolution.Module.Blazor
    {
        public interface IModelButtonDetailViewItemBlazor : IModelViewItem { }
    
        [ViewItem(typeof(IModelButtonDetailViewItemBlazor))]
        public class ButtonDetailViewItemBlazor : ViewItem, IComplexViewItem {
            public class ButtonHolder : IComponentContentHolder {
                public ButtonHolder(ButtonModel componentModel) {
                    ComponentModel = componentModel;
                }
                public ButtonModel ComponentModel { get; }
                RenderFragment IComponentContentHolder.ComponentContent => ComponentModelObserver.Create(ComponentModel, ButtonRenderer.Create(ComponentModel));
            }
            private XafApplication application;
            public ButtonDetailViewItemBlazor(IModelViewItem model, Type objectType) : base(objectType, model.Id) { }
            void IComplexViewItem.Setup(IObjectSpace objectSpace, XafApplication application) {
                this.application = application;
            }
            protected override object CreateControlCore() => new ButtonHolder(new ButtonModel());
            protected override void OnControlCreated() {
                if (Control is ButtonHolder holder) {
                    holder.ComponentModel.Text = "Click me!";
                    holder.ComponentModel.Click += ComponentModel_Click;
                }
                base.OnControlCreated();
            }
            public override void BreakLinksToControl(bool unwireEventsOnly) {
                if (Control is ButtonHolder holder) {
                    holder.ComponentModel.Click -= ComponentModel_Click;
                }
                base.BreakLinksToControl(unwireEventsOnly);
            }
            private void ComponentModel_Click(object sender, EventArgs e) {
                application.ShowViewStrategy.ShowMessage("Action is executed!");
            }
        }
    }
    

Add a new View Item on a Detail View

Metadata on the newly implemented View Item is available in the Application Model. You can add the View Item to a Detail View as shown below:

HT_Add_Button3_1

Display a View Item on a Detail View

Display your button or any other View Items on a Detail View as described in the following topic: View Items Layout Customization.

AddButtonViewItemToDetailView

See Also