现在的很多编辑工具都能实现代码中关键字的高亮显示,自己一时好玩也就随便写了一个:
首先建立一个XML文件:csharp.xml
<?xml version="1.0" encoding="utf-8" ?> <definition name="C#" caseSensitive="true"> <word color="BLUE">private</word> <word color="BLUE">protected</word> <word color="BLUE">public</word> <word color="BLUE">namespace</word> <word color="BLUE">class</word> <word color="BLUE">for</word> <word color="BLUE">if</word> <word color="BLUE">else</word> <word color="BLUE">while</word> <word color="BLUE">switch</word> <word color="BLUE">case</word> <word color="BLUE">using</word> <word color="BLUE">get</word> <word color="BLUE">return</word> <word color="BLUE">null</word> <word color="BLUE">void</word> <word color="BLUE">int</word> <word color="BLUE">string</word> <word color="BLUE">float</word> <word color="BLUE">char</word> <word color="BLUE">this</word> <word color="BLUE">set</word> <word color="BLUE">new</word> <word color="BLUE">true</word> <word color="BLUE">false</word> <word color="BLUE">const</word> <word color="BLUE">static</word> <word color="BLUE">internal</word> <word color="BLUE">extends</word> <word color="BLUE">super</word> <word color="BLUE">import</word> <word color="BLUE">default</word> <word color="BLUE">break</word> <word color="BLUE">try</word> <word color="BLUE">catch</word> <word color="BLUE">finally</word> <word color="CadetBlue">Main</word> <word color="CadetBlue">WriteLine</word> <word color="CadetBlue">Console</word> <word color="CadetBlue">WriteLine</word> <word color="DarkOrange">;</word> <register>printf</register> </definition>
|
其中color指定了该关键字的颜色.
然后在VS中新建一工程,添加下面的这个类:
using System; using System.Xml; using System.IO; using System.Collections; using System.Reflection; using System.Drawing;
namespace WindowsApplication1 {
public class Parser { private XmlDocument xd=null; private ArrayList al=null; //对xml流解析后,会把每一个关键字字符串放入这个容器中 private bool caseSensitive=false; //记录当前语言大小写敏感否 private ArrayList cl=null;//对xml流解析后,把每一个C关键字颜色保留
internal Parser(SyntaxEditor.Languages language) //构造函数接受一个枚举变量 { Assembly asm = Assembly.GetExecutingAssembly(); string filename=""; switch(language) //取得xml文件名 { case SyntaxEditor.Languages.CSHARP: filename="csharp.xml"; break; case SyntaxEditor.Languages.JSHARP: filename="jsharp.xml"; break; case SyntaxEditor.Languages.SQL: filename="sql.xml"; break; case SyntaxEditor.Languages.VBSCRIPT: filename="vbscript.xml"; break; default: break; }
StreamReader reader= new StreamReader(filename, System.Text.Encoding.UTF8 ); //下面的代码解析xml流
xd=new XmlDocument(); xd.Load(reader);
al=new ArrayList(); cl=new ArrayList(); XmlElement root=xd.DocumentElement;
XmlNodeList xnl=root.SelectNodes("/definition/word"); for(int i=0;i<xnl.Count;i++) { al.Add(xnl[i].ChildNodes[0].Value); //将关键子收集到al cl.Add(xnl[i].Attributes["color"].Value);//收集关键字的颜色 } //检测是否判断大小写 this.caseSensitive=bool.Parse(root.Attributes["caseSensitive"].Value);
}
public Color IsKeyWord(string word ) //判断字符串是否为关键字 {
for(int i=0;i<al.Count;i++) { if(string.Compare(word,al[i].ToString(),!caseSensitive)==0) { string ColorTemp=(cl[i].ToString()!=string.Empty?cl[i].ToString():"Black"); Color c; try { c=Color.FromName(ColorTemp); } catch (Exception e) { c=Color.Black; } return c; } }
return Color.Black;
}
} }
|
然后新建一用户控件继承RichTextBox
using System; using System.Collections; using System.ComponentModel; using System.Drawing; using System.Data; using System.Windows.Forms; using System.Runtime.InteropServices; using HWND = System.IntPtr;
namespace WindowsApplication1 { /// <summary> /// SyntaxEditor 的摘要说明。 /// </summary> public class SyntaxEditor :System.Windows.Forms.RichTextBox { /// <summary> /// 必需的设计器变量。
/// </summary> private System.ComponentModel.Container components = null; int line; private Parser parser; /// <summary> /// 必需的设计器变量。 /// </summary> //使用win32api:SendMessage来防止控件着色时的闪烁现象 [DllImport("user32")] private static extern int SendMessage(HWND hwnd, int wMsg, int wParam, IntPtr lParam); private const int WM_SETREDRAW = 0xB; public SyntaxEditor() { // 该调用是 Windows.Forms 窗体设计器所必需的。 InitializeComponent(); base.WordWrap=false; // TODO: 在 InitComponent 调用后添加任何初始化
} /// <summary> /// 清理所有正在使用的资源。 /// </summary> protected override void Dispose( bool disposing ) { if( disposing ) { if( components != null ) components.Dispose(); } base.Dispose( disposing ); } #region 组件设计器生成的代码 /// <summary> /// 设计器支持所需的方法 - 不要使用代码编辑器 /// 修改此方法的内容。 /// </summary> private void InitializeComponent() { this.Name = "SyntaxEditor";
} #endregion //重写基类的OnTextChanged方法。为了提高效率,程序是对当前文本插入点所在行进行扫描, //以空格为分割符,判断每个单词是否为关键字,并进行着色。 protected override void OnTextChanged(EventArgs e) { if(base.Text!="") { int selectStart=base.SelectionStart; line=base.GetLineFromCharIndex(selectStart); string lineStr=base.Lines[line]; int linestart=0; for(int i=0;i<line;i++) { linestart+=base.Lines[i].Length+1; }
SendMessage(base.Handle, WM_SETREDRAW, 0, IntPtr.Zero);
base.SelectionStart=linestart; base.SelectionLength=lineStr.Length; base.SelectionColor=Color.Black; base.SelectionStart=selectStart; base.SelectionLength=0;
//对一行字符串用空格或者.分开 string[] words=lineStr.Split(new char[]{' ','.','\n','(',')','}','{','"','[',']'}); parser=new Parser(this.language);
for(int i=0;i<words.Length;i++)//一个字符段一个字符段来判断 {
//判断是否是程序保留字 是的话高亮显示 if(parser.IsKeyWord(words[i])!=Color.Empty) { int length=0; for(int j=0;j<i;j++) { length+=words[j].Length; } length+=i; int index=lineStr.IndexOf(words[i],length);
base.SelectionStart=linestart+index; base.SelectionLength=words[i].Length; //base.SelectionFont base.SelectionColor=parser.IsKeyWord(words[i]);
base.SelectionStart=selectStart; base.SelectionLength=0; base.SelectionColor=Color.Black; }
} SendMessage(base.Handle, WM_SETREDRAW, 1, IntPtr.Zero); base.Refresh(); } base.OnTextChanged (e); }
public new bool WordWrap { get{return base.WordWrap;} set{ base.WordWrap=value;} }
public enum Languages { SQL, VBSCRIPT, CSHARP, JSHARP }
private Languages language=Languages.CSHARP;
public Languages Language { get{return this.language;} set{this.language=value;} }
} }
|
这个时候你只要保证XML文件和exe或者数据集(如果你打算这样做)在同一个目录就可以了,看看吧下面就是测试效果:
呵呵 很简单哦,看样子写个C语言编辑环境也不是很难哦 呵呵~
我尝试去掉API在MONO上面编译,可惜MONO并没有支持RichTextBox控件,既然只能在Win上面运行,所以还是加上API好了,可以减少屏幕闪动感觉.
转载:: http://tb.blog.csdn.net/TrackBack.aspx?PostId=549896
请发表评论