Results 1 to 9 of 9

Thread: Syntax Highlighter

  1. #1

    Thread Starter
    Super Moderator dday9's Avatar
    Join Date
    Mar 2011
    Posts
    12,376

    Syntax Highlighter

    I've been around the forums now for quite a while, and something I see come up quite regularly is someone wanting to develop an IDE. Well an IDE is very hard work, take visual studio's for example. Visual Studio's has intellisense, syntax highlighting, compiler... the list goes on! Well I've taken it upon my self to at least knock out one portion for those wanting to take on the challenge and that's the syntax highlighter.
    The pro's:
    • Highlights syntax in a pure managed .Net way!


    The con's:
    • It's not complete, I will constantly work on it
    • Sort of a memory hog!


    The way I do it is first set up a textfile and have it in a Token{delimiter}Color format. So in my example I post the text file I use looks like this:
    <html>,Goldenrod
    </html>,Goldenrod
    <head>,Goldenrod
    </head>,Goldenrod
    <body>,Goldenrod
    </body>,Goldenrod
    <title>,CornflowerBlue
    </title>,CornflowerBlue
    <h1>,CornflowerBlue
    </h1>,CornflowerBlue
    <h2>,CornflowerBlue
    </h2>,CornflowerBlue
    <h3>,CornflowerBlue
    </h3>,CornflowerBlue
    <h4>,CornflowerBlue
    </h4>,CornflowerBlue
    <h5>,CornflowerBlue
    </h5>,CornflowerBlue
    <h6>,CornflowerBlue
    </h6>,CornflowerBlue
    <p>,CornflowerBlue
    </p>,CornflowerBlue
    <br/>,BlueViolet
    <hr/>,BlueViolet
    <div>,CornflowerBlue
    </div>,CornflowerBlue
    <ol>,CornflowerBlue
    </ol>,CornflowerBlue
    <li>,CornflowerBlue
    </li>,CornflowerBlue
    What I do next is declare a Dictionary(Of String, Color). Then fill that dictionary using this function:
    Code:
        Private Function txt_to_dictionary(ByVal content As String, ByVal delimiter As String) As Dictionary(Of String, Color)
            'Declare a new instance of a dictionary
            Dim dic As New Dictionary(Of String, Color)
    
            'Split up the content by the newline b/c in our textfile we have:
            'value,color
            'value,color
            'etc.
            Dim str() As String = content.Split({Environment.NewLine}, StringSplitOptions.RemoveEmptyEntries)
    
            'Return nothing if there's nothing in the content
            If str.Count = -1 Then
                Return Nothing
            End If
    
            'Iterate through each row, or line
            For rows As Integer = 0 To str.Count - 1
                'Declare the token and color
                'We get the token by getting the substring from 0 to where the delimiter is
                'We get the color by getting the substring from where the delimiter + 1 is to the end
                Dim token As String = str(rows).Substring(0, str(rows).IndexOf(delimiter))
                Dim color As Color = color.FromName(str(rows).Substring(str(rows).IndexOf(delimiter) + 1))
    
                'Add it to our dictionary
                dic.Add(token, color)
            Next
    
            Return dic
        End Function
    The reason I have ByVal content As String, instead of say ByVal filename As String and use a streamreader to read the contents of the text file is because when I use textfiles, I generally add them in My.Resources and that's simply not necessary. Finally in the text_changed event of a RichTextBox I add:
    Code:
            'Get the current location of the cursor
            Dim cursor_location As Integer = RichTextBox1.SelectionStart
    
            'Get the line we're editing
            Dim current_line As Integer = RichTextBox1.GetLineFromCharIndex(cursor_location)
    
            'Iterate through each token
            For Each token As String In token_dictionary.Keys
                'If the line contains the token
                If RichTextBox1.Lines(current_line).Contains(token) Then
                    'Select and color it
                    RichTextBox1.Select(RichTextBox1.Find(token), token.Length)
                    RichTextBox1.SelectionColor = token_dictionary(token)
                End If
            Next
    
            'Finally set the selection color back to black and set the cursor wher it was
            RichTextBox1.SelectionStart = cursor_location
            RichTextBox1.SelectionLength = 0
            RichTextBox1.SelectionColor = Color.Black
    All in all, the final code looks like this:
    Code:
    'Come on now, everyone needs Option Strict/Explicit ON!
    Option Strict On
    Option Explicit On
    Public Class Form1
        Private token_dictionary As Dictionary(Of String, Color)
    
        Private Function txt_to_dictionary(ByVal content As String, ByVal delimiter As String) As Dictionary(Of String, Color)
            'Declare a new instance of a dictionary
            Dim dic As New Dictionary(Of String, Color)
    
            'Split up the content by the newline b/c in our textfile we have:
            'value,color
            'value,color
            'etc.
            Dim str() As String = content.Split({Environment.NewLine}, StringSplitOptions.RemoveEmptyEntries)
    
            'Return nothing if there's nothing in the content
            If str.Count = -1 Then
                Return Nothing
            End If
    
            'Iterate through each row, or line
            For rows As Integer = 0 To str.Count - 1
                'Declare the token and color
                'We get the token by getting the substring from 0 to where the delimiter is
                'We get the color by getting the substring from where the delimiter + 1 is to the end
                Dim token As String = str(rows).Substring(0, str(rows).IndexOf(delimiter))
                Dim color As Color = color.FromName(str(rows).Substring(str(rows).IndexOf(delimiter) + 1))
    
                'Add it to our dictionary
                dic.Add(token, color)
            Next
    
            Return dic
        End Function
    
    
        Private Sub Form1_Load(sender As System.Object, e As System.EventArgs) Handles MyBase.Load
            token_dictionary = txt_to_dictionary(My.Resources.Tokens, ",")
        End Sub
    
        Private Sub RichTextBox1_TextChanged(sender As System.Object, e As System.EventArgs) Handles RichTextBox1.TextChanged
            'Get the current location of the cursor
            Dim cursor_location As Integer = RichTextBox1.SelectionStart
    
            'Get the line we're editing
            Dim current_line As Integer = RichTextBox1.GetLineFromCharIndex(cursor_location)
    
            'Iterate through each token
            For Each token As String In token_dictionary.Keys
                'If the line contains the token
                If RichTextBox1.Lines(current_line).Contains(token) Then
                    'Select and color it
                    RichTextBox1.Select(RichTextBox1.Find(token), token.Length)
                    RichTextBox1.SelectionColor = token_dictionary(token)
                End If
            Next
    
            'Finally set the selection color back to black and set the cursor wher it was
            RichTextBox1.SelectionStart = cursor_location
            RichTextBox1.SelectionLength = 0
            RichTextBox1.SelectionColor = Color.Black
    
        End Sub
    End Class
    To go back to the con's, one thing I haven't figured out yet is for strings. In most cases strings are defined by the text inside double quotation marks: "This is a string!". The problem with my method is that I haven't figured out how to highlight both the double quote and everything inside of it yet. But like I said this is a work in progress, but a good jumping point. Here is an image of the work in progress:
    Name:  syntax highlighter.png
Views: 2457
Size:  24.1 KB
    Last edited by dday9; May 23rd, 2013 at 11:18 AM.
    "Code is like humor. When you have to explain it, it is bad." - Cory House
    VbLessons | HtmlLessons | CssLessons | Code Tags | Sword of Fury - Jameram

  2. #2
    Frenzied Member
    Join Date
    Oct 2012
    Location
    Tampa, FL
    Posts
    1,187

    Re: Syntax Highlighter

    this is neat

  3. #3

    Thread Starter
    Super Moderator dday9's Avatar
    Join Date
    Mar 2011
    Posts
    12,376

    Re: Syntax Highlighter

    Well I updated the code a little bit. What I did was, instead of parsing the whole richtextbox.text, I parse just the line. This reduces a lot of the flickering the control had. The reason I didn't just parse the word that's being typed is because of tags like <img src="">

    Edit -
    The only issue I have with this method is that word wrap must be off.
    "Code is like humor. When you have to explain it, it is bad." - Cory House
    VbLessons | HtmlLessons | CssLessons | Code Tags | Sword of Fury - Jameram

  4. #4
    Addicted Member
    Join Date
    Jul 2011
    Posts
    245

    Re: Syntax Highlighter

    Very sick! I love it.
    Thank you dday9

  5. #5
    Hyperactive Member Grags's Avatar
    Join Date
    Apr 2014
    Posts
    268

    Re: Syntax Highlighter

    Unfortunately
    token_dictionary = txt_to_dictionary(My.Resources.Tokens, ",")
    throws up an error as I don't use my strings as a resource. And it's probably not possible, as I'm constantly adding and removing items from the list that needs to be used. Is there anyway around this?
    The glass is half full if you're filling it, and half empty if you're emptying it.

  6. #6

    Thread Starter
    Super Moderator dday9's Avatar
    Join Date
    Mar 2011
    Posts
    12,376

    Re: Syntax Highlighter

    You would simply load the dictionary using your strings rather than using the resource file. Could you give an example of some of the strings?
    "Code is like humor. When you have to explain it, it is bad." - Cory House
    VbLessons | HtmlLessons | CssLessons | Code Tags | Sword of Fury - Jameram

  7. #7
    Hyperactive Member Grags's Avatar
    Join Date
    Apr 2014
    Posts
    268

    Re: Syntax Highlighter

    Very hard to explain. Though... shortly after writing my above post, I had a brain storm (very rare!). And the following is working perfectly... It's quartered my initial attempt and is universal to the program. I can't remember what sparked it but it was definitely something in your code.

    Code:
        Public Sub Highlight(ByVal r As RichTextBox)
            For i As Integer = 0 To ItemList.Count - 1
                r.Find(ItemList.Item(i), RichTextBoxFinds.None)
                r.SelectionColor = Color.Yellow
                r.SelectedText = StrConv(r.SelectedText, VbStrConv.ProperCase)
                r.SelectionLength = 0
            Next
            For i As Integer = 0 To ObjectList.Count - 1
                r.Find(objectList.Item(i), RichTextBoxFinds.None)
                r.SelectionColor = Color.Lime
                r.SelectedText = StrConv(r.SelectedText, VbStrConv.ProperCase)
                r.SelectionLength = 0
            Next
        End Sub
    But in attempt to answer your question...

    My strings are input from the name of a file (Could be an object or an Item). For example...

    Code:
                Dim S As String
                Dim di As New IO.DirectoryInfo(Path() + "Items/")
                Dim diar1 As IO.FileInfo() = di.GetFiles()
                Dim dra As IO.FileInfo
    
                For Each dra In diar1
                    S = dra.Name.Substring(0, dra.Name.Length - 4)
                    ItemList.Add(S)
                    'Snipped
                Next
    Where I wrote ('snipped) this continues to input all the data from the file into the program.


    Sorry if you feel I wasted your time, I just hope you realise it was your code that helped me get a perfect solution.
    The glass is half full if you're filling it, and half empty if you're emptying it.

  8. #8

    Thread Starter
    Super Moderator dday9's Avatar
    Join Date
    Mar 2011
    Posts
    12,376

    Re: Syntax Highlighter

    Assuming that ItemList is a List(Of String)...

    Change the first parameter of txt_to_dictionary to a string array, rename the parameter to str, and take out the split function in the txt_to_dictionary. Whenever you call the txt_to_dictionary function you'd use this:

    Code:
    token_dictionary = txt_to_dictionary(ItemList.ToArray, ",")
    "Code is like humor. When you have to explain it, it is bad." - Cory House
    VbLessons | HtmlLessons | CssLessons | Code Tags | Sword of Fury - Jameram

  9. #9
    PowerPoster Nightwalker83's Avatar
    Join Date
    Dec 2001
    Location
    Adelaide, Australia
    Posts
    13,344

    Re: Syntax Highlighter

    Quote Originally Posted by dday9 View Post
    The con's:
    • It's not complete, I will constantly work on it
    That's not a con! A con would be if you uploaded/posted something that didn't work at all.
    when you quote a post could you please do it via the "Reply With Quote" button or if it multiple post click the "''+" button then "Reply With Quote" button.
    If this thread is finished with please mark it "Resolved" by selecting "Mark thread resolved" from the "Thread tools" drop-down menu.
    https://get.cryptobrowser.site/30/4111672

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  



Click Here to Expand Forum to Full Width