Back to Devexpress

Custom AI-powered Extensions

windowsforms-405336-ai-powered-extensions-custom-ai-powered-extensions.md

latest6.0 KB
Original Source

Custom AI-powered Extensions

  • Jun 01, 2025
  • 3 minutes to read

The following example creates a custom AI-powered extension (“AuthoredStyleExtension”) and integrates it into the DevExpress Rich Text Editor.

Register AI Client

See the following help topic for information on required NuGet packages and system requirements: Register an AI Client.

The following code snippet registers the Azure OpenAI client:

csharp
using Microsoft.Extensions.AI;
using DevExpress.AIIntegration;

internal static class Program {
    [STAThread]
    static void Main() {
        Application.EnableVisualStyles();
        Application.SetCompatibleTextRenderingDefault(false);
        IChatClient azureChatClient = new Azure.AI.OpenAI.AzureOpenAIClient(new Uri(AzureOpenAIEndpoint),
            new System.ClientModel.ApiKeyCredential(AzureOpenAIKey))
            .GetChatClient(ModelId).AsIChatClient();
        AIExtensionsContainerDesktop.Default.RegisterChatClient(azureChatClient);
        // Uncomment the following line if your project targets the .NET Framework and
        // you create AI-powered behaviors in code.
        // DevExpress.AIIntegration.WinForms.BehaviorInitializer.Initialize();
        Application.Run(new Form1());
    }
    static string AzureOpenAIEndpoint { get { return Environment.GetEnvironmentVariable("AZURE_OPENAI_ENDPOINT"); } }
    static string AzureOpenAIKey { get { return Environment.GetEnvironmentVariable("AZURE_OPENAI_APIKEY"); } }
    static string ModelId { get { return "MODEL_NAME"; } }
}
vb
Imports Microsoft.Extensions.AI
Imports DevExpress.AIIntegration

Friend Module Program
    <STAThread>
    Sub Main()
        Application.EnableVisualStyles()
        Application.SetCompatibleTextRenderingDefault(False)
        ' Register Azure.OpenAI
        Dim azureChatClient As IChatClient = New Azure.AI.OpenAI.AzureOpenAIClient(New Uri(AzureOpenAIEndpoint),
            New System.ClientModel.ApiKeyCredential(AzureOpenAIKey)).
            GetChatClient(ModelId).AsIChatClient()
        AIExtensionsContainerDesktop.Default.RegisterChatClient(azureChatClient)
        ' Uncomment the following line if your project targets the .NET Framework and
        ' you create AI-powered behaviors in code.
        ' DevExpress.AIIntegration.WinForms.BehaviorInitializer.Initialize()
        Application.Run(New Form1())
    End Sub
    Private ReadOnly Property AzureOpenAIEndpoint() As String
        Get
            Return Environment.GetEnvironmentVariable("AZURE_OPENAI_ENDPOINT")
        End Get
    End Property
    Private ReadOnly Property AzureOpenAIKey() As String
        Get
            Return Environment.GetEnvironmentVariable("AZURE_OPENAI_APIKEY")
        End Get
    End Property
    Private ReadOnly Property ModelId As String
        Get
            Return "MODEL_NAME"
        End Get
    End Property
End Module

Create an Extension

The AuthoredStyleExtension is based on the DevExpress ChangeStyleExtension. The example overrides the GetSystemPrompt method to customize the prompt:

csharp
using DevExpress.AIIntegration.Extensions;

public class AuthoredStyleExtension : ChangeTextExtension<AuthoredStyleRequest> {
    public AuthoredStyleExtension(IServiceProvider serviceProvider) : base(serviceProvider) { }
    protected override string GetSystemPrompt(AuthoredStyleRequest request) {
        return String.Format("Rewrite this text in the {0} style", request.Author);
    }
}

public class AuthoredStyleRequest : TextRequest {
    public AuthoredStyleRequest(string Author, string Text) : base(Text) {
        this.Author = Author;
    }
    public string Author { get; set; }
}

Integrate an AI-powered Extension into a Rich Text Editor

Register the AuthoredStyleExtension and handle the RichEditControl.PopupMenuShowing event to display a submenu (“Authored Style”) in the popup menu:

csharp
using DevExpress.AIIntegration;
using DevExpress.AIIntegration.WinForms;
using DevExpress.Utils.Menu;
using DevExpress.XtraBars.Ribbon;
using DevExpress.XtraRichEdit.API.Native;

public partial class Form1 : RibbonForm {
    public Form1() {
        InitializeComponent();

        var defaultContainer = AIExtensionsContainerDesktop.Default;
        defaultContainer.Register<AuthoredStyleRequest, AuthoredStyleExtension>();

        string menuCaption = "Authored Style";
        richEditControl.PopupMenuShowing += (s, e) => {
            var menuItem = e.Menu.Items.FirstOrDefault(x => x.Caption == menuCaption) as DXSubMenuItem;
            if (menuItem == null) {
                menuItem = new DXSubMenuItem(menuCaption);
                string[] authors = ["Mark Twain", "Ernest Hemingway", "Maya Angelou"];
                foreach (string author in authors) {
                    menuItem.Items.Add(new DXMenuItem(author, async (ss, ee) => {
                        var extension = (AuthoredStyleExtension)defaultContainer.GetExtension(typeof(AuthoredStyleRequest));
                        DocumentRange selection = richEditControl.Document.Selection;
                        var request = new AuthoredStyleRequest(author, richEditControl.Document.GetText(selection));
                        string result = await AIOverlayForm.Execute(richEditControl, extension, request);
                        richEditControl.Document.Replace(selection, result);
                    }));
                }
                e.Menu.Items.Add(menuItem);
            }
        };
    }
}

Run Demo: Create Custom Extension in MemoEdit

See Also

DevExpress AI-powered Extensions for WinForms