我们在使用到WINFORM窗体工作中,要求RichTextBox 加入行号;
之前有看到大牛们写的,但是太复杂繁多,而且有用双TextBox进行联动,非常不错,今天我们尝试RichTextBox +Panel相互联动如下效果.
左侧灰色为Panel,右侧为RichTextBox 控件
1:准备Panel画布如下代码,当接到文件字符后进行坐标解析,绘制行号。
private void showLineNo()
{
//获得当前坐标信息
Point p = this.txtFileView.Location;
int crntFirstIndex = this.txtFileView.GetCharIndexFromPosition(p); int crntFirstLine = this.txtFileView.GetLineFromCharIndex(crntFirstIndex); Point crntFirstPos = this.txtFileView.GetPositionFromCharIndex(crntFirstIndex); p.Y += this.txtFileView.Height; int crntLastIndex = this.txtFileView.GetCharIndexFromPosition(p); int crntLastLine = this.txtFileView.GetLineFromCharIndex(crntLastIndex);
Point crntLastPos = this.txtFileView.GetPositionFromCharIndex(crntLastIndex); //准备画图
Graphics g = this.panel2.CreateGraphics(); Font font = new Font(this.txtFileView.Font, this.txtFileView.Font.Style); SolidBrush brush = new SolidBrush(Color.Green); //画图开始 //刷新画布 Rectangle rect = this.panel2.ClientRectangle;
brush.Color = this.panel2.BackColor; g.FillRectangle(brush, , , this.panel2.ClientRectangle.Width, this.panel2.ClientRectangle.Height); brush.Color = Color.White;//重置画笔颜色 //绘制行号 int lineSpace = ; if (crntFirstLine != crntLastLine)
{
lineSpace = (crntLastPos.Y - crntFirstPos.Y) / (crntLastLine - crntFirstLine); } else
{
lineSpace = Convert.ToInt32(this.txtFileView.Font.Size); }
int brushX = this.panel2.ClientRectangle.Width - Convert.ToInt32(font.Size * ); int brushY = crntLastPos.Y + Convert.ToInt32(font.Size * 0.21f);
for (int i = crntLastLine; i >= crntFirstLine; i--)
{ g.DrawString((i + ).ToString(), font, brush, brushX, brushY); brushY -= lineSpace;
} g.Dispose(); font.Dispose(); brush.Dispose();
}
2:事件准备(启用)如下事件
控件加载事件
private void txtFileView_TextChanged(object sender, EventArgs e)
{
showLineNo();
}
控件滚动事件(当算出的行数大于本控件长度)
private void txtFileView_VScroll(object sender, EventArgs e)
{
showLineNo();
}
完成后,直接启用运行,Demo事例中的效果就出来,方便大家用于各种应用上.