同系列文章:
/* ---------------------------------------------------------- * 文件名称:TextBoxPlus.cs * * 作者:秦建辉 * * QQ:36748897 * * 博客:http://www.firstsolver.com/wordpress/ * * 开发环境: * Visual Studio V2010 * .NET Framework 4 Client Profile * * 版本历史: * V1.2 2014年05月25日 * 解决了字符转换的错误 * * V1.1 2012年09月08日 * 改进数据清空时的插入位置点 * * V1.0 2012年09月01日 * 在WPF的TextBox中显式显示提示信息 * * 注意事项:该增强控件对输入法的适应性 * ※ 百度输入法 V2.0 正常 * ※ 搜狗输入法 V6.2 正常 * ※ 微软英库拼音输入法 正常 * ※ 汉王栀子花输入法 正常 * ※ 微软拼音输入法 V2010/V2012 在中文状态下输入第一个字符时异常 * ※ 谷歌拼音输入法 V3.0.1.98 在中文状态下输入第一个字符时异常 ------------------------------------------------------------ */ using System; using System.Windows.Controls; using System.Windows.Input; using System.Windows.Media; namespace Splash { /// <summary> /// 在WPF的TextBox中显式显示提示信息 /// </summary> public class TextBoxPlus : TextBox { /// <summary> /// 显式显示的提示信息 /// </summary> public String ExplicitToolTip { get; set; } /// <summary> /// 提示信息的文字颜色,默认为黑灰色 /// </summary> protected Brush InnerToolTipForeground = Brushes.DarkGray; public Brush ToolTipForeground { get { return InnerToolTipForeground; } set { InnerToolTipForeground = value; if (base.Foreground != InnerNormalForeground) { // 处于提示状态,更新提示内容颜色 base.Foreground = value; // 更新文本颜色 } } } /// <summary> /// 正常内容的文字颜色,默认为黑色 /// </summary> /// <remarks> /// 注意:Foreground 被 NormalForeground 替换 /// </remarks> protected Brush InnerNormalForeground = Brushes.Black; public Brush NormalForeground { get { return InnerNormalForeground; } set { InnerNormalForeground = value; if (base.Foreground != InnerToolTipForeground) { // 处于正常状态,更新正常内容颜色 base.Foreground = value; } } } /// <summary> /// 获取或设置一个用于描述前景色的画笔 /// </summary> /// <remarks>隐藏继承成员</remarks> protected new Brush Foreground { get { return base.Foreground; } set { base.Foreground = value; } } /// <summary> /// 获取或设置文本框的文本内容 /// </summary> /// <remarks>隐藏继承成员</remarks> public new String Text { get { if (base.Foreground == InnerToolTipForeground) return String.Empty; // 提示状态 else return base.Text; // 正常状态 } set { base.Text = value; } } /// <summary> /// 是否是内部改变文本 /// </summary> private Boolean IsInnerChange = false; /// <summary> /// 文本框初始内容为空时,设置提示信息 /// </summary> /// <param name="e">事件数据</param> protected override void OnInitialized(EventArgs e) { base.OnInitialized(e); // 设置文本颜色 base.Foreground = InnerNormalForeground; // 触发文本改变事件 if (String.IsNullOrEmpty(base.Text)) { // 显示提示信息 IsInnerChange = true; base.Text = ExplicitToolTip; // 注意:引发新的 TextChanged 事件 // 更换字体颜色 base.Foreground = InnerToolTipForeground; } } /// <summary> /// 当用户每次开始输入时,清除提示信息 /// </summary> /// <param name="e">事件数据</param> protected override void OnPreviewTextInput(TextCompositionEventArgs e) { // 通过字体颜色判断文本框状态 if (base.Foreground == InnerToolTipForeground) { // 清空原有内容 IsInnerChange = true; base.Text = String.Empty; // 更换字体颜色 base.Foreground = InnerNormalForeground; } } /// <summary> /// 当文本框内容为空时,显示提示信息 /// </summary> /// <param name="e">事件数据</param> /// <remarks> /// 注意:粘帖操作不会触发 PreviewTextInput 事件 /// </remarks> protected override void OnTextChanged(TextChangedEventArgs e) { if (IsInnerChange) { // 内部改变事件 IsInnerChange = false; e.Handled = true; return; } // 文本框内容为空 if (String.IsNullOrEmpty(base.Text)) { // 显示提示信息 IsInnerChange = true; base.Text = ExplicitToolTip; // 注意:引发新的 TextChanged 事件 // 设置插入位置在最前面 base.SelectionStart = 0; // 更换字体颜色 base.Foreground = InnerToolTipForeground; // 标记消息已处理 e.Handled = true; } else if (base.Foreground == InnerToolTipForeground) { // 粘帖操作触发 TextChanged 事件 System.Text.StringBuilder sb = new System.Text.StringBuilder(base.MaxLength); foreach (TextChange item in e.Changes) { // 获取粘帖的文字内容 if (item.AddedLength > 0) { sb.Append(base.Text.Substring(item.Offset, item.AddedLength)); } } if (sb.Length > 0) { // 更换字体颜色 base.Foreground = InnerNormalForeground; // 显示增加的文字内容 IsInnerChange = true; base.Text = sb.ToString(); // 注意:引发新的 TextChanged 事件 // 调整插入位置到最后,否则光标会在最前面 base.SelectionStart = sb.Length; } // 标记消息已处理 e.Handled = true; } } } }