Winform开发——RichEditBox添加超链接和图片
有时候我们需要在RichEditBox控件中添加超链接进行相关的扩展,比如我们可以在RichEditBox中点击超链接打开目标网址,但是这个功能并没有在VS自带的RichEditBox控件中实现,那么我们这篇将说明如何将超链接添加到RichEditBox中,并给出添加图片的示例代码。
步骤一:RichEditBox的扩展RichEditBoxEx
using System;
using System.ComponentModel;
using System.Drawing;
using System.Windows.Forms;
using System.Runtime.InteropServices;
namespace NewBeeEngine
{
public class RichTextBoxEx : RichTextBox
{
#region Interop-Defines
[StructLayout(LayoutKind.Sequential)]
private struct CHARFORMAT2_STRUCT
{
public UInt32 cbSize;
public UInt32 dwMask;
public UInt32 dwEffects;
public Int32 yHeight;
public Int32 yOffset;
public Int32 crTextColor;
public byte bCharSet;
public byte bPitchAndFamily;
[MarshalAs(UnmanagedType.ByValArray, SizeConst = 32)]
public char[] szFaceName;
public UInt16 wWeight;
public UInt16 sSpacing;
public int crBackColor; // Color.ToArgb() -> int
public int lcid;
public int dwReserved;
public Int16 sStyle;
public Int16 wKerning;
public byte bUnderlineType;
public byte bAnimation;
public byte bRevAuthor;
public byte bReserved1;
}
[DllImport("user32.dll", CharSet = CharSet.Auto)]
private static extern IntPtr SendMessage(IntPtr hWnd, int msg, IntPtr
wParam, IntPtr lParam);
private const int WM_USER = 0x0400;
private const int EM_GETCHARFORMAT =
WM_USER + 58;
private const int EM_SETCHARFORMAT =
WM_USER + 68;
private const int SCF_SELECTION =
0x0001;
private const int SCF_WORD = 0x0002;
private const int SCF_ALL = 0x0004;
#region CHARFORMAT2 Flags
private const UInt32 CFE_BOLD = 0x0001;
private const UInt32 CFE_ITALIC = 0x0002;
private const UInt32 CFE_UNDERLINE =
0x0004;
private const UInt32 CFE_STRIKEOUT =
0x0008;
private const UInt32 CFE_PROTECTED =
0x0010;
private const UInt32 CFE_LINK = 0x0020;
private const UInt32 CFE_AUTOCOLOR =
0x40000000;
private const UInt32 CFE_SUBSCRIPT =
0x00010000; /* Superscript and subscript are */
private const UInt32 CFE_SUPERSCRIPT =
0x00020000; /* mutually
exclusive */
private const int CFM_SMALLCAPS =
0x0040; /* (*) */
private const int CFM_ALLCAPS = 0x0080; /* Displayed
by 3.0 */
private const int CFM_HIDDEN = 0x0100; /*
Hidden by 3.0 */
private const int CFM_OUTLINE = 0x0200; /*
(*) */
private const int CFM_SHADOW = 0x0400; /*
(*) */
private const int CFM_EMBOSS = 0x0800; /*
(*) */
private const int CFM_IMPRINT = 0x1000; /*
(*) */
private const int CFM_DISABLED =
0x2000;
private const int CFM_REVISED = 0x4000;
private const int CFM_BACKCOLOR =
0x04000000;
private const int CFM_LCID = 0x02000000;
private const int CFM_UNDERLINETYPE =
0x00800000; /* Many displayed by 3.0 */
private const int CFM_WEIGHT = 0x00400000;
private const int CFM_SPACING = 0x00200000; /*
Displayed by 3.0 */
private const int CFM_KERNING = 0x00100000; /*
(*) */
private const int CFM_STYLE = 0x00080000; /*
(*) */
private const int CFM_ANIMATION =
0x00040000; /* (*) */
private const int CFM_REVAUTHOR =
0x00008000;
private const UInt32 CFM_BOLD = 0x00000001;
private const UInt32 CFM_ITALIC = 0x00000002;
private const UInt32 CFM_UNDERLINE =
0x00000004;
private const UInt32 CFM_STRIKEOUT =
0x00000008;
private const UInt32 CFM_PROTECTED =
0x00000010;
private const UInt32 CFM_LINK = 0x00000020;
private const UInt32 CFM_SIZE = 0x80000000;
private const UInt32 CFM_COLOR = 0x40000000;
private const UInt32 CFM_FACE = 0x20000000;
private const UInt32 CFM_OFFSET = 0x10000000;
private const UInt32 CFM_CHARSET = 0x08000000;
private const UInt32 CFM_SUBSCRIPT =
CFE_SUBSCRIPT | CFE_SUPERSCRIPT;
private const UInt32 CFM_SUPERSCRIPT =
CFM_SUBSCRIPT;
private const byte CFU_UNDERLINENONE =
0x00000000;
private const byte CFU_UNDERLINE =
0x00000001;
private const byte CFU_UNDERLINEWORD =
0x00000002; /* (*) displayed as ordinary
underline */
private const byte CFU_UNDERLINEDOUBLE =
0x00000003; /* (*) displayed as ordinary
underline */
private const byte CFU_UNDERLINEDOTTED =
0x00000004;
private const byte CFU_UNDERLINEDASH =
0x00000005;
private const byte CFU_UNDERLINEDASHDOT =
0x00000006;
private const byte CFU_UNDERLINEDASHDOTDOT
= 0x00000007;
private const byte CFU_UNDERLINEWAVE =
0x00000008;
private const byte CFU_UNDERLINETHICK =
0x00000009;
private const byte CFU_UNDERLINEHAIRLINE
= 0x0000000A; /* (*) displayed as
ordinary underline */
#endregion
#endregion
public RichTextBoxEx()
{
// Otherwise,
non-standard links get lost when user starts typing
// next to a
non-standard link
this.DetectUrls = false;
}
[DefaultValue(false)]
public new bool DetectUrls
{
get { return base.DetectUrls; }
set { base.DetectUrls = value;
}
}
/// <summary>
/// Insert a given text as a link into the
RichTextBox at the current insert position.
/// </summary>
/// <param
name="text">Text to be
inserted</param>
public void InsertLink(string text)
{
InsertLink(text, this.SelectionStart);
}
/// <summary>
/// Insert a given text at a given position as a
link.
/// </summary>
/// <param
name="text">Text to be
inserted</param>
/// <param
name="position">Insert
position</param>
public void InsertLink(string text, int
position)
{
if (position < 0
|| position > this.Text.Length)
throw new ArgumentOutOfRangeException("position");
this.SelectionStart = position;
this.SelectedText = text;
this.Select(position, text.Length);
this.SetSelectionLink(true);
this.Select(position + text.Length, 0);
}
/// <summary>
/// Insert a given text at at the current input
position as a link.
/// The link text is followed by a hash (#) and
the given hyperlink text, both of
/// them invisible.
/// When clicked on, the whole link text and
hyperlink string are given in the
/// LinkClickedEventArgs.
/// </summary>
/// <param
name="text">Text to be
inserted</param>
/// <param
name="hyperlink">Invisible
hyperlink string to be inserted</param>
public void InsertLink(string text, string
hyperlink)
{
InsertLink(text, hyperlink,
this.SelectionStart);
}
/// <summary>
/// Insert a given text at a given position as a
link. The link text is followed by
/// a hash (#) and the given hyperlink text,
both of them invisible.
/// When clicked on, the whole link text and
hyperlink string are given in the
/// LinkClickedEventArgs.
/// </summary>
/// <param
name="text">Text to be
inserted</param>
/// <param
name="hyperlink">Invisible
hyperlink string to be inserted</param>
/// <param
name="position">Insert
position</param>
public void InsertLink(string text, string
hyperlink, int position)
{
if (position < 0
|| position > this.Text.Length)
throw new ArgumentOutOfRangeException("position");
this.SelectionStart = position;
this.SelectedRtf = @"{\rtf1\ansi
" + text + @"\v
#" + hyperlink + @"\v0}";
this.Select(position, text.Length + hyperlink.Length
+ 1);
this.SetSelectionLink(true);
this.Select(position + text.Length +
hyperlink.Length + 1, 0);
}
/// <summary>
/// Set the current selection's link style
/// </summary>
/// <param
name="link">true: set
link style, false: clear link style</param>
public void SetSelectionLink(bool link)
{
SetSelectionStyle(CFM_LINK,
link ? CFE_LINK : 0);
}
/// <summary>
/// Get the link style for the current selection
/// </summary>
/// <returns>0: link style not set, 1: link style set, -1:
mixed</returns>
public int GetSelectionLink()
{
return GetSelectionStyle(CFM_LINK,
CFE_LINK);
}
private void SetSelectionStyle(UInt32 mask, UInt32 effect)
{
CHARFORMAT2_STRUCT cf = new CHARFORMAT2_STRUCT();
cf.cbSize = (UInt32)Marshal.SizeOf(cf);
cf.dwMask = mask;
cf.dwEffects = effect;
IntPtr wpar = new IntPtr(SCF_SELECTION);
IntPtr lpar = Marshal.AllocCoTaskMem(Marshal.SizeOf(cf));
Marshal.StructureToPtr(cf, lpar, false);
IntPtr res = SendMessage(Handle,
EM_SETCHARFORMAT, wpar, lpar);
Marshal.FreeCoTaskMem(lpar);
}
private int GetSelectionStyle(UInt32 mask, UInt32 effect)
{
CHARFORMAT2_STRUCT cf = new CHARFORMAT2_STRUCT();
cf.cbSize = (UInt32)Marshal.SizeOf(cf);
cf.szFaceName = new char[32];
IntPtr wpar = new IntPtr(SCF_SELECTION);
IntPtr lpar = Marshal.AllocCoTaskMem(Marshal.SizeOf(cf));
Marshal.StructureToPtr(cf, lpar, false);
IntPtr res = SendMessage(Handle,
EM_GETCHARFORMAT, wpar, lpar);
cf = (CHARFORMAT2_STRUCT)Marshal.PtrToStructure(lpar,
typeof(CHARFORMAT2_STRUCT));
int state;
// dwMask holds the
information which properties are consistent throughout the selection:
if ((cf.dwMask &
mask) == mask)
{
if ((cf.dwEffects &
effect) == effect)
state = 1;
else
state = 0;
}
else
{
state = -1;
}
Marshal.FreeCoTaskMem(lpar);
return state;
}
}
}
步骤二:添加图片
//插入图片
private void InserImg(string fileType)
{
switch (fileType.ToLower())
{
case "txt":
Image img1 = Image.FromFile("image\\TXT.bmp");
Clipboard.SetDataObject(img1, false);
engine.information.Paste(DataFormats.GetFormat(DataFormats.Bitmap));
break;
case "doc":
Image img2 = Image.FromFile("image\\DOC.bmp");
Clipboard.SetDataObject(img2, false);
engine.information.Paste(DataFormats.GetFormat(DataFormats.Bitmap));
break;
case "docx":
Image img3 = Image.FromFile("image\\DOCX.bmp");
Clipboard.SetDataObject(img3, false);
engine.information.Paste(DataFormats.GetFormat(DataFormats.Bitmap));
break;
case "pdf":
Image img4 = Image.FromFile("image\\PDF.bmp");
Clipboard.SetDataObject(img4, false);
engine.information.Paste(DataFormats.GetFormat(DataFormats.Bitmap));
break;
case "xml":
Image img5 = Image.FromFile("image\\XML.bmp");
Clipboard.SetDataObject(img5, false);
engine.information.Paste(DataFormats.GetFormat(DataFormats.Bitmap));
break;
case "htm":
Image img6 = Image.FromFile("image\\HTML.bmp");
Clipboard.SetDataObject(img6, false);
engine.information.Paste(DataFormats.GetFormat(DataFormats.Bitmap));
break;
case "html":
Image img7 = Image.FromFile("image\\HTML.bmp");
Clipboard.SetDataObject(img7, false);
engine.information.Paste(DataFormats.GetFormat(DataFormats.Bitmap));
break;
default:
break;
}
}
步骤三:示例、编译、运行
插入超链接示例:
textBox.Select(textBox.Text.Length
- text.Length, text.Length);
textBox.SelectionFont =
new Font("黑体", 15, FontStyle.Bold);
textBox.SetSelectionLink(true);
//超链接点击
private void information_LinkClicked(object sender, LinkClickedEventArgs
e)
{
if (!CheckPassword())
{
return;
}
messageClient.Send("DOWN#" + StringEncrypt.Encrypt(e.LinkText.Substring(0,
e.LinkText.Length - 1), keyBox.Text) + ".aes" + "#");
superTabControl1.SelectedTabIndex
= 2;
}
插入图片示例:
InserImg(text.Substring(text.LastIndexOf('.') + 1, text.Length -
text.LastIndexOf('.') -
2));
删除最后一行示例:
if (engine.information.Text.Length
!= 0)
{
int infoLenth = engine.information.Text.Length;
int lineNumber = engine.information.Lines.Length;
int lastLineLength =
engine.information.Lines[lineNumber - 2].Length;
if (lastLineLength !=
0)
{
engine.information.Select(infoLenth
- lastLineLength - 1, lastLineLength +
1);
engine.information.SelectedText
= "";
}
}