详解C#之WinForm版利用RichTextBox 制作文本编辑器【附源码】

在Windows应用程序开发中,刚刚介绍了WPF版的利用RichTextBox实现文本编辑器,今天继续推出WinForm版的利用RichTextBox实现文本编辑器。本文利用一个简单的小例子,简述如何在WinForm开发中,利用RichTextBox开发文本编辑器,以及RichTextBox的用法,仅供学习分享使用,如有不足之处,还请指正。

图片

Windows窗体中的RichTextBox控件用于显示,输入和操作格式化的文本,RichTextBox除了拥有TextBox控件的所有功能外,还可以显示字体,颜色,链接,从文件中读取和加载图像,以及查找指定的字符。RichTextBox控件通常用于提供类似字体处理程序(如Microsoft Word)的文本操作和显示功能。RichTextBox控件可以显示滚动条,且默认根据需要进行显示。

涉及知识点

在本示例中,涉及知识点如下所示:

  • SelectionFont 获取或设置当前选定文本或插入点的字体。

  • FontStyle 指定应用到文本的字形信息。

  • SelectionAlignment  获取或设置应用到当前选定内容或插入点的对齐方式。

  • SelectionIndent 获取或设置所选内容开始行的缩进距离(以像素为单位)。

  • SelectionCharOffset 获取或设置控件中的文本是显示在基线上、作为上标还是作为基线下方的下标。

  • SelectionColor 获取或设置当前选定文本或插入点的文本颜色。

  • SelectionBackColor   获取或设置在 System.Windows.Forms.RichTextBox 控件中选中文本时文本的颜色。

  • SelectionBullet 获取或设置一个值,通过该值指示项目符号样式是否应用到当前选定内容或插入点。

  • Clipboard Paste 粘贴指定剪贴板格式的剪贴板内容【插入图片时使用】。

  • Find 在对搜索应用特定选项的情况下,在 System.Windows.Forms.RichTextBox 控件的文本中搜索位于控件内特定位置的字符串。

核心代码

1. 定义接口

为了规范和统一,定义实现样式接口IRichFormat,如下所示:

namespace DemoRichText.Model
{/// <summary>/// 富文本框格式/// </summary>public interface IRichFormat{void SetFormat(RichTextBox rtbInfo);}
}

2. 实现样式基类

定义一个接口的默认实现基类BaseRichFormat,此基类是抽象类,如下所示:

namespace DemoRichText.Model
{public abstract class BaseRichFormat : IRichFormat{public abstract void SetFormat(RichTextBox rtbInfo);}
}

3. 具体实现方法

具体到每一个功能样式设置,均继承自BaseRichFormat,如下所示:

namespace DemoRichText.Model
{public class DefaultRickFormat : BaseRichFormat{public override void SetFormat(RichTextBox rtbInfo){}}/// <summary>/// 加粗格式/// </summary>public class BoldRichFormat : BaseRichFormat{public override void SetFormat(RichTextBox rtbInfo){Font oldFont = rtbInfo.SelectionFont;Font newFont;if (oldFont.Bold){newFont = new Font(oldFont, oldFont.Style & ~FontStyle.Bold);//支持位于运算}else{newFont = new Font(oldFont, oldFont.Style | FontStyle.Bold);}rtbInfo.SelectionFont = newFont;}}/// <summary>/// 斜体/// </summary>public class ItalicRichFormat : BaseRichFormat{public override void SetFormat(RichTextBox rtbInfo){Font oldFont = rtbInfo.SelectionFont;Font newFont;if (oldFont.Italic){newFont = new Font(oldFont, oldFont.Style & ~FontStyle.Italic);}else{newFont = new Font(oldFont, oldFont.Style | FontStyle.Italic);}rtbInfo.SelectionFont = newFont;rtbInfo.Focus();}}/// <summary>/// 下划线/// </summary>public class UnderLineRichFormat : BaseRichFormat{public override void SetFormat(RichTextBox rtbInfo){Font oldFont = rtbInfo.SelectionFont;Font newFont;if (oldFont.Underline){newFont = new Font(oldFont, oldFont.Style & ~FontStyle.Underline);}else{newFont = new Font(oldFont, oldFont.Style | FontStyle.Underline);}rtbInfo.SelectionFont = newFont;rtbInfo.Focus();}}/// <summary>/// 删除线/// </summary>public class StrikeLineRichFormat : BaseRichFormat{public override void SetFormat(RichTextBox rtbInfo){Font oldFont = rtbInfo.SelectionFont;Font newFont;if (oldFont.Underline){newFont = new Font(oldFont, oldFont.Style & ~FontStyle.Strikeout);}else{newFont = new Font(oldFont, oldFont.Style | FontStyle.Strikeout);}rtbInfo.SelectionFont = newFont;rtbInfo.Focus();}}/// <summary>/// 左对齐/// </summary>public class LeftRichFormat : BaseRichFormat{public override void SetFormat(RichTextBox rtbInfo){rtbInfo.SelectionAlignment = HorizontalAlignment.Left;rtbInfo.Focus();}}/// <summary>/// 居中对齐/// </summary>public class CenterRichFormat : BaseRichFormat{public override void SetFormat(RichTextBox rtbInfo){if (rtbInfo.SelectionAlignment == HorizontalAlignment.Center){rtbInfo.SelectionAlignment = HorizontalAlignment.Left;}else{rtbInfo.SelectionAlignment = HorizontalAlignment.Center;}rtbInfo.Focus();}}/// <summary>/// 右对齐/// </summary>public class RightRichFormat : BaseRichFormat{public override void SetFormat(RichTextBox rtbInfo){if (rtbInfo.SelectionAlignment == HorizontalAlignment.Right){rtbInfo.SelectionAlignment = HorizontalAlignment.Left;}else{rtbInfo.SelectionAlignment = HorizontalAlignment.Right;}rtbInfo.Focus();}}/// <summary>/// 缩进对齐/// </summary>public class IndentRichFormat : BaseRichFormat{public override void SetFormat(RichTextBox rtbInfo){//每次以10个像素进行缩进rtbInfo.SelectionIndent = rtbInfo.SelectionIndent + 10;rtbInfo.Focus();}}/// <summary>/// 缩进对齐/// </summary>public class OutIndentRichFormat : BaseRichFormat{public override void SetFormat(RichTextBox rtbInfo){//每次以10个像素进行缩进rtbInfo.SelectionIndent = rtbInfo.SelectionIndent - 10;rtbInfo.Focus();}}/// <summary>/// 下标/// </summary>public class SubScriptRichFormat : BaseRichFormat{public override void SetFormat(RichTextBox rtbInfo){if (rtbInfo.SelectionCharOffset < 0){rtbInfo.SelectionCharOffset = 0;}else {rtbInfo.SelectionCharOffset = -5;}rtbInfo.Focus();}}/// <summary>/// 上标/// </summary>public class SuperScriptRichFormat : BaseRichFormat{public override void SetFormat(RichTextBox rtbInfo){if (rtbInfo.SelectionCharOffset > 0){rtbInfo.SelectionCharOffset = 0;}else {rtbInfo.SelectionCharOffset = 5;}rtbInfo.Focus();}}/// <summary>/// 字体/// </summary>public class FontRichFormat : BaseRichFormat{public override void SetFormat(RichTextBox rtbInfo){FontDialog f = new FontDialog();if (f.ShowDialog() == DialogResult.OK){FontFamily family = f.Font.FontFamily;rtbInfo.SelectionFont = new Font(family, rtbInfo.SelectionFont.Size, rtbInfo.SelectionFont.Style);}rtbInfo.Focus();}}/// <summary>/// 文本颜色/// </summary>public class ForeColorRichFormat : BaseRichFormat{public override void SetFormat(RichTextBox rtbInfo){ColorDialog f = new ColorDialog();if (f.ShowDialog() == DialogResult.OK){rtbInfo.SelectionColor = f.Color;}rtbInfo.Focus();}}/// <summary>/// 文本背景颜色/// </summary>public class BgColorRichFormat : BaseRichFormat{public override void SetFormat(RichTextBox rtbInfo){ColorDialog f = new ColorDialog();if (f.ShowDialog() == DialogResult.OK){rtbInfo.SelectionBackColor = f.Color;}rtbInfo.Focus();}}/// <summary>/// UL列表,项目符号样式/// </summary>public class UlRichFormat : BaseRichFormat{public override void SetFormat(RichTextBox rtbInfo){if (rtbInfo.SelectionBullet){rtbInfo.SelectionBullet = false;}else {rtbInfo.SelectionBullet = true;rtbInfo.BulletIndent = 10;}rtbInfo.Focus();}}/// <summary>/// 图片插入/// </summary>public class PicRichFormat : BaseRichFormat{public override void SetFormat(RichTextBox rtbInfo){OpenFileDialog o = new OpenFileDialog();o.InitialDirectory = AppDomain.CurrentDomain.BaseDirectory;o.Title = "请选择图片";o.Filter = "jpeg|*.jpeg|jpg|*.jpg|png|*.png|gif|*.gif";if (o.ShowDialog() == DialogResult.OK) {string fileName = o.FileName;try{Image bmp = Image.FromFile(fileName);Clipboard.SetDataObject(bmp);DataFormats.Format dataFormat = DataFormats.GetFormat(DataFormats.Bitmap);if (rtbInfo.CanPaste(dataFormat)){rtbInfo.Paste(dataFormat);}}catch (Exception exc){MessageBox.Show("图片插入失败。" + exc.Message, "提示",MessageBoxButtons.OK, MessageBoxIcon.Information);}}rtbInfo.Focus();}}/// <summary>/// 删除/// </summary>public class DelRichFormat : BaseRichFormat{public override void SetFormat(RichTextBox rtbInfo){rtbInfo.SelectedText = "";rtbInfo.Focus();}}/// <summary>/// 查找/// </summary>public class SearchRichFormat : BaseRichFormat{public override void SetFormat(RichTextBox rtbInfo){string find = rtbInfo.Tag.ToString();int index=  rtbInfo.Find(find, 0,RichTextBoxFinds.None);int startPos = index;int nextIndex = 0;while (nextIndex != startPos)//循环查找字符串,并用蓝色加粗12号Times New Roman标记之{rtbInfo.SelectionStart = index;rtbInfo.SelectionLength = find.Length;rtbInfo.SelectionColor = Color.Blue;rtbInfo.SelectionFont = new Font("Times New Roman", (float)12, FontStyle.Bold);rtbInfo.Focus();nextIndex = rtbInfo.Find(find, index + find.Length, RichTextBoxFinds.None);if (nextIndex == -1)//若查到文件末尾,则充值nextIndex为初始位置的值,使其达到初始位置,顺利结束循环,否则会有异常。{nextIndex = startPos;}index = nextIndex;}rtbInfo.Focus();}}/// <summary>/// 打印/// </summary>public class PrintRichFormat : BaseRichFormat{private RichTextBox richTextbox;public override void SetFormat(RichTextBox rtbInfo){this.richTextbox = rtbInfo;PrintDocument pd = new PrintDocument();pd.PrintPage += new PrintPageEventHandler(pd_PrintPage);// 打印文档pd.Print();}private void pd_PrintPage(object sender, PrintPageEventArgs ev){//ev.Graphics.DrawString(richTextbox.Text);//ev.HasMorePages = true;}}/// <summary>/// 字体大小/// </summary>public class FontSizeRichFormat : BaseRichFormat{public override void SetFormat(RichTextBox rtbInfo){string fontSize = rtbInfo.Tag.ToString();float fsize = 0.0f;if (float.TryParse(fontSize, out fsize)) {rtbInfo.SelectionFont = new Font(rtbInfo.Font.FontFamily, fsize, rtbInfo.SelectionFont.Style);}rtbInfo.Focus();}}
}

4. 实现工厂模式

因为所有实现都基于同一个接口,所以进一步封装样式设置的实现类,如下所示:

​​​​​​​

namespace DemoRichText.Model
{public class RichFormatFactory{public static IRichFormat CreateRichFormat(BTNType btnType){IRichFormat richFormat;switch (btnType){case BTNType.Bold:richFormat = new BoldRichFormat();break;case BTNType.BGColor:richFormat = new BgColorRichFormat();break;case BTNType.Center:richFormat = new CenterRichFormat();break;case BTNType.Del:richFormat = new DelRichFormat();break;case BTNType.Font:richFormat = new FontRichFormat();break;case BTNType.ForeColor:richFormat = new ForeColorRichFormat();break;case BTNType.FontSize:richFormat = new FontSizeRichFormat();break;case BTNType.Indent:richFormat = new IndentRichFormat();break;case BTNType.Italic:richFormat = new ItalicRichFormat();break;case BTNType.Left:richFormat = new LeftRichFormat();break;case BTNType.OutIndent:richFormat = new OutIndentRichFormat();break;case BTNType.Pic:richFormat = new PicRichFormat();break;case BTNType.Print:richFormat = new PrintRichFormat();break;case BTNType.Right:richFormat = new RightRichFormat();break;case BTNType.Search:richFormat = new SearchRichFormat();break;case BTNType.StrikeLine:richFormat = new StrikeLineRichFormat();break;case BTNType.SubScript:richFormat = new SubScriptRichFormat();break;case BTNType.SuperScript:richFormat = new SuperScriptRichFormat();break;case BTNType.Ul:richFormat = new UlRichFormat();break;case BTNType.UnderLine:richFormat = new UnderLineRichFormat();break;default:richFormat = new DefaultRickFormat();break;}return richFormat;}}
}

5. UI页面代码

由于实现了代码封装,所有页面代码较少,如下所示:

namespace DemoRichText
{public partial class MainForm : Form{public MainForm(){InitializeComponent();}public void btnButtonClick(object sender, EventArgs e) {Button btn = (Button)sender;BTNType btnType;if (Enum.TryParse<BTNType>(btn.Tag.ToString(), out btnType)) {if (btnType == BTNType.Search) {if (!string.IsNullOrEmpty(this.txtSearch.Text.Trim())){this.rtbInfo.Tag = this.txtSearch.Text.Trim();}else {return;}}IRichFormat richFomat = RichFormatFactory.CreateRichFormat(btnType);richFomat.SetFormat(this.rtbInfo);}}private void combFontSize_SelectedIndexChanged(object sender, EventArgs e){float fsize = 12.0f;if (combFontSize.SelectedIndex > -1) {if (float.TryParse(combFontSize.SelectedItem.ToString(), out fsize)) {rtbInfo.Tag = fsize.ToString();IRichFormat richFomat = RichFormatFactory.CreateRichFormat(BTNType.FontSize);richFomat.SetFormat(this.rtbInfo);}return;}}}
}

示例效果图

设置文本对应的格式,具体如下所示:

图片

源码下载

关于源码下载,可关注公众号,并回复关键字WINRICH即可,如下所示:

图片

以上就是【详解C#之WinForm版利用RichTextBox 制作文本编辑器】的全部内容,关于更多详细内容,可参考官方文档。希望能够一起学习,共同进步。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/513050.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

day04-SpringBootWeb入门

一、SpringBootWeb快速入门 1 需求 需求&#xff1a;基于 SpringBoot 的方式开发一个 web 应用&#xff0c;浏览器发起请求 /hello后&#xff0c;给浏览器返回字符串“Hello World ~”。 2 开发步骤 第1步&#xff1a;创建 SpringBoot 工程项目 第2步&#xff1a;定义 HelloC…

Nodejs 第四十六章(redis持久化)

redis持久化 Redis提供两种持久化方式&#xff1a; RDB&#xff08;Redis Database&#xff09;持久化&#xff1a;RDB是一种快照的形式&#xff0c;它会将内存中的数据定期保存到磁盘上。可以通过配置Redis服务器&#xff0c;设置自动触发RDB快照的条件&#xff0c;比如在指…

低代码与数字经济:推动软件开发创新的新引擎

随着数字经济的飞速发展&#xff0c;传统的软件开发方式已经难以满足快速变化的市场需求。在这一背景下&#xff0c;低代码开发平台应运而生&#xff0c;以其高效、灵活的特性&#xff0c;成为推动数字经济创新发展的重要力量。本文将探讨低代码与数字经济的关系&#xff0c;分…

在 Flutter 中使用 flutter_gen 简化图像资产管理

你是否厌倦了在 Flutter 项目中手动管理图像资产的繁琐任务&#xff1f; 告别手工输入资源路径的痛苦&#xff0c;欢迎使用“Flutter Gen”高效资源管理的时代。在本文中&#xff0c;我将带您从手动处理图像资源的挫折到动态生成它们的便利。 选择1&#xff1a;痛苦手动添加–…

自动化测试环境搭建--Linux内网环境【实操经验】

环境信息 Python版本3.6.8 Jenkins版本2.346.3 Allure版本 2.13.2 环境准备 一、Python需要安装库 allure-pytest (2.13.2) pytest (7.0.1) jsonpath (0.82.2) pytest-html (3.2.0) pytest-ordering (0.6) …

Pytorch学习 day03(Tensorboard、Transforms)

Tensorboard Tensorboard能够可视化loss的变化过程&#xff0c;便于我们查看模型的训练状态&#xff0c;也能查看模型当前的输入和输出结果 在Pycharm中&#xff0c;可以通过按住ctrl&#xff0c;并左键点击某个库来进入源文件查看该库的使用方法SummaryWriter是用来向log_dir…

USB - Linux Kernel Menuconfig

Linux kernel&#xff0c;make menuconfig&#xff0c;和USB相关的&#xff0c;在主菜单选择Device Drivers。 Device Drivers下面&#xff0c;找到USB support。 在USB support下面&#xff0c;就可以对USB相关的item进行设置。 按照从上到下的顺序&#xff0c;打开的设置依次…

数据结构学习(四)高级数据结构

高级数据结构 1. 概念 之所以称它们为高级的数据结构&#xff0c;是因为它们的实现要比那些常用的数据结构要复杂很多&#xff0c;能够让我们在处理复杂问题的过程中&#xff0c; 多拥有一把利器&#xff0c;同时掌握好它们的性质&#xff0c;以及所适应的场合&#xff0c;在…

Linux常用命令(超详细)

一、基本命令 1.1 关机和重启 关机 shutdown -h now 立刻关机 shutdown -h 5 5分钟后关机 poweroff 立刻关机 重启 shutdown -r now 立刻重启 shutdown -r 5 5分钟后重启 reboot 立刻重启 1.2 帮助命令 –help命令 shutdown --help&#xff1a; ifconfig --help&#xff1a;查看…

大模型总结

抛开大模型基座训练&#xff0c;我们还可以关注什么&#xff1f; - 知乎 大模型LLM领域&#xff0c;有哪些可以作为学术研究方向&#xff1f; 方向一&#xff1a;大模型的基础理论问题 大力出奇迹&#xff0c;涌现&#xff0c;目前还需要科学家继续研究理论基础 也就是先有…

Spring中@import注解终极揭秘!

技术概念 它能干啥 Import注解在Spring框架中主要用于解决模块化和配置管理方面的技术问题&#xff0c;它可以帮助开发者实现以下几个目标&#xff1a; 模块化配置&#xff1a;在大型项目中&#xff0c;通常需要将配置信息分散到多个配置类中&#xff0c;以便更好地组织和管…

无名管道数据交换

#include<stdio.h> #include <sys/types.h> #include <sys/stat.h> #include<errno.h> #include <unistd.h> #include<fcntl.h> #include<string.h>int main(int argc, const char *argv[]) {//开辟写入管道1if(mkfifo("./AAA&…