|
it IS fast, but adding all the keywords in the source code seems crazy.
any chance to support syntax file?
Regards,
unruledboy@hotmail.com
|
|
|
|
|
It would be good to have that.
In the mean time if you need to add many keywords, use a text edit which support macro (such as PFE or Textpad) to write code for you.
|
|
|
|
|
Hi All!!
I have used next code:
private void LoadSettings()
{
ScriptHighLightSettings.Separators = new char[] {
' ', '\r', '\n', ',', '*', '/'
,'.', '-', '+', ':', '(', ')'
,';'
};
ScriptHighLightSettings.KeyWords = new StringCollection();
ScriptHighLightSettings.ExtKeyWords = new StringCollection();
try
{
// Create an instance of StreamReader to read from a file.
// The using statement also closes the StreamReader.
using (StreamReader sr = new StreamReader("scredkeywords"))
{
String line;
String parsingMode = String.Empty;
// Read and display lines from the file until the end of
// the file is reached.
while ((line = sr.ReadLine()) != null)
{
if(parsingMode == String.Empty)
{
if(line == "[KEYWORDS]")
{
parsingMode = line;
}
if(line == "[EXTKEYWORDS]")
{
parsingMode = line;
}
Console.WriteLine(line);
continue;
}
if(line == "")
{
parsingMode = String.Empty;
}
switch (parsingMode)
{
case "[KEYWORDS]":
{
ScriptHighLightSettings.KeyWords.Add(line);
Console.WriteLine(line);
break;
}
case "[EXTKEYWORDS]":
{
ScriptHighLightSettings.ExtKeyWords.Add(line);
Console.WriteLine(line);
break;
}
default:
{
parsingMode = String.Empty;
break;
}
}
}
}
}
catch (Exception e)
{
// Let the user know what went wrong.
Console.WriteLine("The file could not be read:");
Console.WriteLine(e.Message);
}
ScriptHighLightSettings.CommentsColor = Color.Green;
ScriptHighLightSettings.ErrorsColor = Color.Red;
ScriptHighLightSettings.KeyWordsColor = Color.Blue;
ScriptHighLightSettings.ExtKeyWordsColor = Color.Purple;
ScriptHighLightSettings.NumbersColor = Color.LightPink;
ScriptHighLightSettings.StringsColor = Color.LightSeaGreen;
}
My "scredkeywords" file:
[KEYWORDS]
function
if
then
end
nil
local
table
[EXTKEYWORDS]
vec3f
vec2f
camera
Game
SceneManager
NodeGraph
That's all
|
|
|
|
|
RichTextBox is generally broke with drag & drop and multible undo not really working. Implementing syntax highlighting in RichTextBox is a hack that hardly can work without being painful slow and flickering. I would rather use the rock solid Scintilla. With the help of scide which is very mature and Reflector looking at the WinForms code I made a simple Scintilla control, it lacks seriously features, currently I don't need more features for myself.
<br />
Imports System<br />
Imports System.Runtime.InteropServices<br />
Imports System.IO<br />
Imports System.ComponentModel<br />
Imports System.Text<br />
<br />
Imports Stax<br />
Imports Stax.UI<br />
Imports Stax.Win32<br />
<br />
Namespace UI<br />
Public Class Scintilla<br />
Inherits Control<br />
<br />
Private ScintillaHandle As IntPtr<br />
Private DirectPointer As Integer<br />
Private Initialized As Boolean<br />
<br />
Public Sub New()<br />
Dim path As String = CommonDirs.Startup + "SciLexer.dll"<br />
<br />
If File.Exists(path) Then<br />
MyBase.SetStyle(ControlStyles.UserPaint, False)<br />
MyBase.SetStyle(ControlStyles.UseTextForAccessibility, False)<br />
MyBase.SetStyle((ControlStyles.StandardDoubleClick Or ControlStyles.StandardClick), False)<br />
<br />
LoadLibrary("SciLexer.dll")<br />
<br />
ScintillaHandle = CreateWindowEx(0, "Scintilla", "", _<br />
WS.CHILD Or WS.VISIBLE Or WS.TABSTOP, 0, 0, _<br />
Width, Height, Handle, 0, IntPtr.Zero, Nothing)<br />
<br />
DirectPointer = CInt(SlowPerform(2185, 0, 0))<br />
SPerform(2037, CType(65001, UInt32), 0) 'Unicode<br />
<br />
Application.AddMessageFilter(New MessageFiler(AddressOf MessageCallback))<br />
<br />
Initialized = True<br />
Else<br />
BackColor = Color.White<br />
End If<br />
End Sub<br />
<br />
Private Sub MessageCallback(ByRef m As Message, ByRef cancel As Boolean)<br />
If m.HWnd = ScintillaHandle Then<br />
Select Case m.Msg<br />
Case WM.LBUTTONDOWN, WM.RBUTTONDOWN<br />
If Not Focused Then<br />
FindForm.ActiveControl = Me<br />
End If<br />
Case 256, 257, 258, 260, 261 'implements all key event<br />
If CType(GetType(Control).InvokeMember("ProcessKeyMessage", _<br />
Reflection.BindingFlags.Instance Or _<br />
Reflection.BindingFlags.InvokeMethod Or _<br />
Reflection.BindingFlags.NonPublic, _<br />
Nothing, Me, New Object() {m}), Boolean) Then<br />
<br />
cancel = True<br />
End If<br />
End Select<br />
End If<br />
End Sub<br />
<br />
Protected Overrides Function IsInputKey(ByVal keyData As Keys) As Boolean<br />
If (keyData And Keys.Alt) <> Keys.Alt Then<br />
Dim data As Keys = keyData And Keys.KeyCode<br />
<br />
If data <> Keys.Tab Then<br />
Select Case data<br />
Case Keys.Prior, Keys.Next, Keys.End, Keys.Home, _<br />
Keys.Left, Keys.Up, Keys.Right, Keys.Down<br />
<br />
Return True<br />
End Select<br />
Else<br />
Return ((keyData And Keys.Control) = Keys.None)<br />
End If<br />
End If<br />
<br />
Return MyBase.IsInputKey(keyData)<br />
End Function<br />
<br />
#Region " Properties "<br />
Private ReadOnlyValue As Boolean<br />
<br />
<Category("Scintilla"), DefaultValue(False)> _<br />
Public Property [ReadOnly]() As Boolean<br />
Get<br />
If Initialized Then<br />
Return SPerform(2140, 0, 0) <> 0<br />
Else<br />
Return ReadOnlyValue<br />
End If<br />
End Get<br />
Set(ByVal value As Boolean)<br />
ReadOnlyValue = value<br />
<br />
If Initialized Then<br />
If value Then<br />
SPerform(2171, CType(1, System.UInt32), 0)<br />
Else<br />
SPerform(2171, CType(0, System.UInt32), 0)<br />
End If<br />
End If<br />
End Set<br />
End Property<br />
<br />
Public ReadOnly Property Length() As Integer<br />
Get<br />
Return CInt(SPerform(2006, 0, 0))<br />
End Get<br />
End Property<br />
<br />
Private TextValue As String = ""<br />
<br />
Public Overrides Property Text() As String<br />
Get<br />
If Initialized Then<br />
Dim buffer As Byte() = New Byte(Length) {}<br />
Dim ptr As IntPtr = Marshal.AllocHGlobal(buffer.Length)<br />
SPerform(2182, CType(buffer.Length, UInt32), CType(ptr, UInteger))<br />
Marshal.Copy(ptr, buffer, 0, buffer.Length)<br />
Marshal.FreeHGlobal(ptr)<br />
Return UTF8Encoding.UTF8.GetString(buffer, 0, buffer.Length)<br />
End If<br />
<br />
Return TextValue<br />
End Get<br />
Set(ByVal value As String)<br />
TextValue = value<br />
<br />
If Initialized Then<br />
If value Is Nothing Then<br />
value = ""<br />
End If<br />
<br />
Dim buffer As Byte() = UTF8Encoding.UTF8.GetBytes(value + ChrW(0))<br />
Dim ptr As IntPtr = Marshal.AllocHGlobal(buffer.Length)<br />
Marshal.Copy(buffer, 0, ptr, buffer.Length)<br />
SPerform(2181, 0, CType(ptr, UInteger))<br />
Marshal.FreeHGlobal(ptr)<br />
End If<br />
End Set<br />
End Property<br />
<br />
Protected Overrides ReadOnly Property CreateParams() As CreateParams<br />
Get<br />
Dim ret As CreateParams = MyBase.CreateParams<br />
ret.ExStyle = ret.ExStyle Or CInt(WS.EX_CLIENTEDGE)<br />
Return ret<br />
End Get<br />
End Property<br />
#End Region<br />
<br />
#Region " Focus Management "<br />
Private Function GetScintillaFocus() As Boolean<br />
'Debug.WriteLine("GetScintillaFocus")<br />
<br />
If Initialized Then<br />
Return SPerform(2381, 0, 0) <> 0<br />
End If<br />
End Function<br />
<br />
Private Sub SetScintillaFocus(ByVal focus As Boolean)<br />
If Initialized Then<br />
If focus Then<br />
'Debug.WriteLine("SetScintillaFocus true")<br />
SPerform(2380, CType(1, System.UInt32), 0)<br />
Else<br />
'Debug.WriteLine("SetScintillaFocus false")<br />
SPerform(2380, CType(0, System.UInt32), 0)<br />
End If<br />
End If<br />
End Sub<br />
<br />
Protected Overrides Sub OnGotFocus(ByVal e As EventArgs)<br />
'Debug.WriteLine("OnGotFocus")<br />
SetScintillaFocus(SetFocus(ScintillaHandle) <> IntPtr.Zero)<br />
End Sub<br />
<br />
Protected Overrides Sub OnLostFocus(ByVal e As EventArgs)<br />
'Debug.WriteLine("OnLostFocus")<br />
SetScintillaFocus(False)<br />
End Sub<br />
<br />
Public Overrides ReadOnly Property Focused() As Boolean<br />
Get<br />
'Debug.WriteLine("Focused")<br />
Return GetScintillaFocus()<br />
End Get<br />
End Property<br />
#End Region<br />
<br />
#Region " Native Functions "<br />
<DllImport("kernel32")> _<br />
Private Shared Function LoadLibrary(ByVal lpLibFileName As String) As IntPtr<br />
End Function<br />
<br />
<CLSCompliant(False), DllImport("user32")> _<br />
Private Shared Function CreateWindowEx(ByVal dwExStyle As UInteger, ByVal lpClassName As String, ByVal lpWindowName As String, ByVal dwStyle As UInteger, ByVal x As Integer, ByVal y As Integer, ByVal width As Integer, ByVal height As Integer, ByVal hWndParent As IntPtr, ByVal hMenu As Integer, ByVal hInstance As IntPtr, ByVal lpParam As String) As IntPtr<br />
End Function<br />
<br />
<CLSCompliant(False), DllImport("user32.dll")> _<br />
Private Shared Function SendMessage(ByVal hWnd As Integer, ByVal msg As UInt32, ByVal wParam As Integer, ByVal lParam As Integer) As Integer<br />
End Function<br />
<br />
<DllImport("user32.dll")> _<br />
Private Shared Function SetWindowPos(ByVal hWnd As IntPtr, ByVal hWndInsertAfter As Integer, ByVal X As Integer, ByVal Y As Integer, ByVal cx As Integer, ByVal cy As Integer, ByVal uFlags As Integer) As Integer<br />
End Function<br />
<br />
<CLSCompliant(False), DllImport("scilexer.dll", EntryPoint:="Scintilla_DirectFunction")> _<br />
Private Shared Function Perform(ByVal directPointer As Integer, ByVal message As UInt32, ByVal wParam As UInt32, ByVal lParam As UInt32) As Integer<br />
End Function<br />
<br />
<CLSCompliant(False)> _<br />
Private Function SlowPerform(ByVal message As UInt32, ByVal wParam As UInt32, ByVal lParam As UInt32) As UInt32<br />
Return CType(SendMessage(CInt(ScintillaHandle), message, CInt(wParam), CInt(lParam)), UInt32)<br />
End Function<br />
<br />
<CLSCompliant(False)> _<br />
Private Function SPerform(ByVal message As UInt32, ByVal wParam As UInt32, ByVal lParam As UInt32) As UInt32<br />
Return CType(Perform(DirectPointer, message, wParam, lParam), UInt32)<br />
End Function<br />
<br />
<DllImport("user32.dll")> _<br />
Public Shared Function SetFocus(ByVal hwnd As IntPtr) As IntPtr<br />
End Function<br />
#End Region<br />
<br />
#Region " Event Handlers "<br />
Private Sub Scintilla_Resize(ByVal sender As Object, ByVal e As EventArgs) Handles Me.Resize<br />
If Initialized Then<br />
SetWindowPos(ScintillaHandle, 0, ClientRectangle.X, ClientRectangle.Y, ClientRectangle.Width, ClientRectangle.Height, 0)<br />
End If<br />
End Sub<br />
#End Region<br />
<br />
End Class<br />
End Namespace<br />
|
|
|
|
|
I downloaded Scintilla/SciTE, it supports many syntax, very interesting indeed.
Try to use your code and found that you have the following imports
Imports Stax
Imports Stax.UI
Imports Stax.Win32
What are they?
It would be great if the author/someone convert the Scintilla to .net managed code.
|
|
|
|
|
it is a library with commonly used classes like all the window messages are there defined. It shouldn't be hard to replace this. For window messages codes use APIViewer 2004 and transform the declerations with a advanced editor using block selection, replace etc.
|
|
|
|
|
Did they fix the horizontal scrollbar bug?
They put so much work in this project and
still they refuse to see the most obvious problems.
|
|
|
|
|
Hey. Have you tried looking at the demo project?
It shows quite nicely the proper use of the control.
To fix you problem, first of all move your code to the form's initialization segmant instead of the OnTextChange event of the textbox.
than add the line:
richTextBox1.Descriptors.Add(arjun);
Enjoy!
Uriel Guy
|
|
|
|
|
Hiya,
This component is simply great!! Only problem I have is defining string literals.
Any ideas on how this could be accomplished?
If nothing else, posting a possible solution here would enable myself and others to make the changes ourselves.
I must admit that I dont have the time to study the code, in order to figure out how to enable string literals.
|
|
|
|
|
You'll have to excuse my english, But I'm not sure what's the meaning of "string literals".
Can you pleas post an example?
10x!
Uriel
|
|
|
|
|
Sure thing. What I mean is how would I go about coloring the string definition in this example:
<br />
public void Foo(string bar) {<br />
MessageBox.Show("You sent this to me: " + bar);<br />
}<br />
In the above example, the text "You sent this to me:" would in most GUIs be colored after some text coloring scheme. E.g. blue.
BUT it does not seem possible to add a delimiter for quotes. My guess is that it is because the start and end "glyphs" are the same (", ').
|
|
|
|
|
FYI, I posted a fix for this problem on the other "String Literals" thread on this article.
|
|
|
|
|
First of all, this is great work, congratulation Uriel!
I did a quick performance test.
1. Implement SQL Server reserved keywords (170 words)
2. Copy and patse the PetShop_Schema.sql (1122 lines of code)
The all keywords change color within a second or two however when I start typing new code eg. "SELECT * FROM sometable", it take about 5 secs for the code to appear.
I'm using a laptop pentium 4, 512Mb RAM.
It would be great if performance is improved.
|
|
|
|
|
First of all, Sorry for the long time it took me to reply, I havn't been around...
I havn't checked performance with large texts, But I'll believe you check..
An optimization could be possible (for example: only change to color of the text in view). I'll try to get to that soon.
10x for the input,
Uriel
|
|
|
|
|
could you please provide the SQL test for us?
It would be very kind that you send your SQL test to me:
my email: unruledboy@hotmail.com
Thank you very much!
Regards,
unruledboy@hotmail.com
|
|
|
|
|
thank you very much!
i hope that syntax file support will be added
Regards,
unruledboy@hotmail.com
|
|
|
|
|
Has anyone notice that --some text ... does not change color?
or is it just me?
|
|
|
|
|
Hi!
First of all: Very nice component!
Because I have VisualStyles enabled for my written App. and VisualStyles do not support the RichTextBox I cannot use your fine component at this moment. Is it possible to change the base class you derived it?
Many Greetings!
Sebastian.
|
|
|
|
|
Hey.
I'm sorry to say that I don't see such a possibility right now.. I use to many features specific for RichTextBox to change it in a simple manner.
Sorry,
Uriel Guy
|
|
|
|
|
Hi!
Ok. I put your rtb with borders set to 'none' on a normal TextBox adjust it's properties and I had my VisualStyles-friendly 'Syntax highlighting textbox'. Too easy to say!
Greetings!
Sebastian.
|
|
|
|
|
Prerequist:
.HighlightDescriptors.Add(New HighlightDescriptor("<", Color.Gray, Nothing, DescriptorType.Word, DescriptorRecognition.WholeWord, True))
.HighlightDescriptors.Add(New HighlightDescriptor("<<", ">>", Color.DarkGreen, Nothing, DescriptorType.ToCloseToken, DescriptorRecognition.StartsWith, False))
I have this string in my TextBox:
=2*[X]+POWER ( <<nombre>> ; <<puissance>> )
The position of my cursor if after the second < (before Nombre).
When a press Backspace, this error fire:
Length cannot be less than zero.
Parameter name: length
at System.String.Substring(Int32 startIndex, Int32 length)
at UrielGuy.SyntaxHighlightingTextBox.SyntaxHighlightingTextBox.OnTextChanged(EventArgs e)
at System.Windows.Forms.TextBoxBase.WmReflectCommand(Message& m)
at System.Windows.Forms.TextBoxBase.WndProc(Message& m)
at System.Windows.Forms.RichTextBox.WmReflectCommand(Message& m)
at System.Windows.Forms.RichTextBox.WndProc(Message& m)
at UrielGuy.SyntaxHighlightingTextBox.SyntaxHighlightingTextBox.WndProc(Message& m)
at System.Windows.Forms.ControlNativeWindow.OnMessage(Message& m)
at System.Windows.Forms.ControlNativeWindow.WndProc(Message& m)
at System.Windows.Forms.NativeWindow.DebuggableCallback(IntPtr hWnd, Int32 msg, IntPtr wparam, IntPtr lparam)
at System.Windows.Forms.UnsafeNativeMethods.SendMessage(HandleRef hWnd, Int32 msg, IntPtr wParam, IntPtr lParam)
at System.Windows.Forms.Control.SendMessage(Int32 msg, IntPtr wparam, IntPtr lparam)
at System.Windows.Forms.Control.ReflectMessageInternal(IntPtr hWnd, Message& m)
at System.Windows.Forms.Control.WmCommand(Message& m)
at System.Windows.Forms.Control.WndProc(Message& m)
at System.Windows.Forms.GroupBox.WndProc(Message& m)
at System.Windows.Forms.ControlNativeWindow.OnMessage(Message& m)
at System.Windows.Forms.ControlNativeWindow.WndProc(Message& m)
at System.Windows.Forms.NativeWindow.DebuggableCallback(IntPtr hWnd, Int32 msg, IntPtr wparam, IntPtr lparam)
at System.Windows.Forms.UnsafeNativeMethods.CallWindowProc(IntPtr wndProc, IntPtr hWnd, Int32 msg, IntPtr wParam, IntPtr lParam)
at System.Windows.Forms.NativeWindow.DefWndProc(Message& m)
at System.Windows.Forms.Control.DefWndProc(Message& m)
at System.Windows.Forms.Control.WmKeyChar(Message& m)
at System.Windows.Forms.Control.WndProc(Message& m)
at System.Windows.Forms.TextBoxBase.WndProc(Message& m)
at System.Windows.Forms.RichTextBox.WndProc(Message& m)
at UrielGuy.SyntaxHighlightingTextBox.SyntaxHighlightingTextBox.WndProc(Message& m)
at System.Windows.Forms.ControlNativeWindow.OnMessage(Message& m)
at System.Windows.Forms.ControlNativeWindow.WndProc(Message& m)
at System.Windows.Forms.NativeWindow.DebuggableCallback(IntPtr hWnd, Int32 msg, IntPtr wparam, IntPtr lparam)
at System.Windows.Forms.UnsafeNativeMethods.DispatchMessageW(MSG& msg)
at System.Windows.Forms.ComponentManager.System.Windows.Forms.UnsafeNativeMethods+IMsoComponentManager.FPushMessageLoop(Int32 dwComponentID, Int32 reason, Int32 pvLoopData)
at System.Windows.Forms.ThreadContext.RunMessageLoopInner(Int32 reason, ApplicationContext context)
at System.Windows.Forms.ThreadContext.RunMessageLoop(Int32 reason, ApplicationContext context)
at System.Windows.Forms.Application.RunDialog(Form form)
Jean-Luc
|
|
|
|
|
Hey.
10x for the input. I've fixed the bug, un apdate will be available soon (Including Undo/Redo ability as well.)
|
|
|
|
|
Great job! There is one small thing I noticed.
When highlighting the syntax, you disable the WM_PAINT to reduce flicker. You will notice that this doesn't prevent the scroll bars from repainting themselves and flickering during the parsing.
My guess is that when selecting the text to highlight, the control scrolls to the caret.
Type 3 or 4 very long comments using the /* */ that extend multiple lines. You should see what I am talking about.
Thanks
|
|
|
|
|
Hey.
Here's an Idea. I haven't tried it (I don't have the VS on this computer), but it might work.
Move the "mParsing = false;" to the last line of the OnTextChanges metoed, And call the InvalidateMethod after that. It might work, But I havn't checked it yet.
|
|
|
|
|
No luck... is it possible to temporarily disable the scroll to caret functionality while parsing? That may solve it, but i'm not sure how to do it.
|
|
|
|
|