WPF: Create Syntax Editor for Any Language in 5 Minutes
Tags: csharp, dotnet, wpf
Published: 2021-03-12 13:07:47

---
title: WPF: Create Syntax Editor for Any Language in 5 Minutes
published: true
date: 2021-03-02 11:00:57 UTC
tags: csharp, dotnet, wpf
canonical_url: https://www.syncfusion.com/blogs/post/wpf-create-syntax-editor-for-any-language-in-5-minutes.aspx
cover_image: https://www.syncfusion.com/blogs/wp-content/uploads/2021/02/WPF-Create-Syntax-Editor-for-Any-Language-in-5-Minutes-672x372.png
---

The Syntax Editor provides built-in support for 10+ procedural and markup languages, including C#, Visual Basic, XAML, and JavaScript. It also comes with custom language configurations to apply syntax highlighting and outlining based on the user’s needs.

The Syntax Editor allows users to create a custom language with ease by inheriting one of the following base classes that contain a basic level of implementations and require a minimal set of configurations:

- [LanguageBase](https://help.syncfusion.com/wpf/syntax-editor/language-support/languagebase-members)
- [ProceduralLanguageBase](https://help.syncfusion.com/wpf/syntax-editor/language-support/procedurallanguagebase-class)
- [MarkupLanguageBase](https://help.syncfusion.com/wpf/syntax-editor/language-support/markuplanguagebase-class)

For detailed information on the implementation of these base classes, refer to[custom language support documentation](https://help.syncfusion.com/wpf/syntax-editor/language-support/custom-language-support#customization-of-features).

The **ProceduralLanguageBase** class contains syntax highlighting, outlining, and auto-mode IntelliSense implementations for procedural languages such as C# and Visual Basic, whereas the **MarkupLanguageBase** class contains syntax highlighting and outlining implementations for markup languages such as XAML and XML, and scripting languages such as JavaScript.

Let’s see how to configure a custom language in the Syntax Editor.

## Configuring a custom language: IronPython

The following steps explain how to configure the custom language **IronPython** :

**Step 1: Create a new class, inheriting from the ProceduralLanguageBase class.**

Create a new class inheriting from the **ProceduralLanguageBase** class since **IronPython** ’s start and end tags match with procedural languages. Set the basic properties of the language in the inherited class by using the following code:

```csharp
public class PythonLanguage : ProceduralLanguageBase
{
    public PythonLanguage(EditControl control) : base(control)
    {
        this.Name = "Python";
        this.FileExtension = "py";
        this.ApplyColoring = true;
        this.SupportsIntellisense = false;
        this.SupportsOutlining = true;
        this.TextForeground = Brushes.Black;
    }
}
```

**Step 2: Create a format collection for IronPython.**

Create a collection of **IFormat** -implemented classes to apply in the **Formats** property of the custom language to decide the color applied to tokens by using the following code.

```html
<syncfusion:FormatsCollection x:Key="pythonLanguageFormats">
<syncfusion:EditFormats Foreground="Green" FormatName="CommentFormat"/>
<syncfusion:EditFormats Foreground="Black" FormatName="MultilineCommentFormat"/>
<syncfusion:EditFormats Foreground="Blue" FormatName="KeywordFormat"/>
<syncfusion:EditFormats Foreground="Navy" FormatName="OperatorFormat"/>
<syncfusion:EditFormats Foreground="Gray" FormatName="LiteralsFormat"/>
</syncfusion:FormatsCollection>
```

**Step 3: Create a Lexem collection for IronPython.**

Create a collection of **ILexem** -implemented classes—which decides keywords, comments, literals, and preprocessor information for the custom language—by using the following code.

```html
<syncfusion:LexemCollection x:Key="pythonLanguageLexems">
<syncfusion:Lexem StartText="class \w+[\s:\w,()]+" IsRegex="True" IsMultiline="True" ContainsEndText="True" LexemType="CodeSnippet" EndText="\r\n" ScopeLevel="Class" ShowAlternateIntellisenseText="True" IntellisenseDisplayText="class"/>
<syncfusion:Lexem StartText="def \w+[\s:\w,()]+" IsRegex="True" IsMultiline="True" ContainsEndText="True" LexemType="CodeSnippet" EndText="\r\n" ScopeLevel="Member" ShowAlternateIntellisenseText="True" IntellisenseDisplayText="def"/>
<syncfusion:Lexem StartText="#" EndText="\r\n" IsMultiline="False" ContainsEndText="True" LexemType="Comment" FormatName="CommentFormat"/>
<syncfusion:Lexem StartText=""""" EndText=""""" IsMultiline="True" ContainsEndText="True" LexemType="Comment" FormatName="CommentFormat" />
<syncfusion:Lexem StartText="and" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="as" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="assert" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="break" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="class" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="continue" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="def" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="del" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="elif" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="else" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="except" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="exec" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="finally" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="for" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="from" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="global" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="if" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="import" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="in" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="is" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="lambda" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="not" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="or" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="pass" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="print" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="raise" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="return" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="try" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="while" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="with" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText="yeild" ContainsEndText="False" IsMultiline="False" LexemType="Keyword" FormatName="KeywordFormat"/>
<syncfusion:Lexem StartText=""" EndText=""" IsMultiline="False" LexemType="Literals" FormatName="LiteralsFormat"/>
<syncfusion:Lexem StartText="(" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText=")" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="[" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="]" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="\{" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="\}" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="." ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="," ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText=";" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText=":" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="+" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="-" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="/" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="%" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="^" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="*" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="**" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="|" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="|=" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="&" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="~" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="=" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="<" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText=">" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="==" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="!=" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="<=" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText=">=" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="+=" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="-=" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="*=" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="%=" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="/=" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="&=" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="^=" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="|=" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="<<" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="<<=" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="=>" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="<>" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText=">>=" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
<syncfusion:Lexem StartText="**;=" ContainsEndText="False" IsMultiline="False" LexemType="Operator" FormatName="OperatorFormat"/>
</syncfusion:LexemCollection>
```

**Step 4: Assign Lexem and Format properties to custom python language.**

Initialize and assign **Lexem** and **Format** collections to the custom Python language.

```csharp
PythonLanguage customLanguage = new PythonLanguage(obj as EditControl);
customLanguage.Lexem = this.Resources["pythonLanguageLexems"] as LexemCollection;
customLanguage.Formats = this.Resources["pythonLanguageFormats"] as FormatsCollection;
```

If there is still any need to customize colors for syntax, the **ApplyColoring** method can be overridden to achieve further customization of colors. Similarly, to customize outlining, the **ApplyExpandCollapse** method can be overridden. Please refer to this documentation [topic](https://help.syncfusion.com/wpf/syntax-editor/language-support/custom-language-support#creating-a-custom-language) for detailed information on the usage of overridden methods.

After executing the above configurations, we will get the following output for the **IronPython** language:

![WPF Syntax Editor Customized to Support IronPyton](https://www.syncfusion.com/blogs/wp-content/uploads/2021/02/Syntax-Editor-Customized-to-Support-IronPyton.png)<figcaption>WPF Syntax Editor Customized to Support IronPyton</figcaption>

## References

To learn more, refer to the documentation [custom language support](https://help.syncfusion.com/wpf/syntax-editor/language-support/custom-language-support) and [configuring custom language using WPF syntax editor demo](https://github.com/SyncfusionExamples/configure-custom-language-using-syntax-editor).

## Conclusion

I hope you now feel confident enough to configure a custom language for the Syntax Editor on your own in just four simple steps. This feature will definitely help you extend the usage of the Syntax Editor beyond the supported procedural and markup languages.

If you want to play around with the Syntax Editor, you’ll be happy to know that our WPF demos are now available in the [Microsoft Store](https://www.microsoft.com/en-us/p/syncfusion-wpf-controls-examples/9n99kdhrff6g), and our .NET Core demos are available in the [App Center](https://install.appcenter.ms/orgs/syncfusion-demos/apps/wpf-demos/distribution_groups/release).

For existing customers, the newest version of Essential Studio is available for download from the [License and Downloads](https://www.syncfusion.com/account/downloads) page. If you are not yet a Syncfusion customer, you can try our 30-day [free trial](https://www.syncfusion.com/downloads) to check out our available features.

If you wish to send us feedback or ask any questions, please use the comments section below. You can also contact us through our [support forums](https://www.syncfusion.com/forums), [Direct-Trac](https://www.syncfusion.com/support/directtrac/incidents), or [feedback portal](https://www.syncfusion.com/feedback/wpf). We are always happy to assist you!