zoukankan      html  css  js  c++  java
  • [Winform控件编程系列之一]制作一个能验证错误的文本框和ErrorProvider的复合控件

        Winform控件编程 

         本人水平有限,写此博客的目的一是为了备忘,二是望高手指正,三是希望和大家交流,也许能给他人一些启示。

         也许你能在我的文章中找到许多似曾相识的代码和文字,没错,我确实是引用了许多网上的文章。但我敢保证的是,所有的代码我都调试过,且被我修改成我认为合适的代码。

         WinForm控件通常有三种类型:复合控件(Composite Controls),扩展控件(Extended Controls),自定义控件(Custom Controls)。  
          复合控件:将现有的各种控件组合起来,形成一个新的控件,将控件的功能集中起来。
          扩展控件:在现有控件的控件的基础上派生出一个新的控件,为原有控件增加新的功能或者修改原有控件的功能。
          自定义控件:直接从System.Windows.Forms.Control类派生出来。Control类提供控件所需要的所有基本功能,包括键盘和鼠标的事件处理。自定义控件是最灵活最强大的方法,但是对开发者的要求也比较高,你必须为Control类的OnPaint事件写代码。

         制作一个能验证错误的文本框和ErrorProvider的复合控件

          对于文本框的验证是一个经常需要用到的功能。你是如何验证用户输入的呢?是在文本框的KeyDown事件中添加代码扑捉按键,防止键入非法字符(比如只能输入数字的文本框);还是在文本框失去焦点时,使用代码验证错误,然后弹出一个错误消息框;或者你使用正则表达式对文本框实施验证。我在使用VB.NET时,如果我想使用户只能录入数字,喜欢用KeyDown事件处理用户按键来防止键入非数字。但我发现此方法有一定的缺陷,它不能防止你复制、粘贴或者使用代码改变文本框值的情形。

          正则表达式是许多人的选择,因为它不打扰用户输入,提高用户体验。但是如果在项目中的每个需验证的地方你都要添加文本框和ErrorProvider组件,是否太麻烦了。我们完全可以制作一个能验证错误的文本框和ErrorProvider组件的复合控件。

          第一步:新建一个.net 2.0 的Windows窗体控件库项目,修改UserControl1.cs的代码,将类继承的UserControl改为TextBox,修改类名为TextBoxValidation。返回设计视图,从工具箱中拖拽一个ErrorProvider组件到设计器中。并修改名称为txtErrorProvider。

         第二步:编码如下:

    using System;
    using System.Collections.Generic;
    using System.ComponentModel;
    using System.Drawing;
    using System.Data;
    using System.Text;
    using System.Windows.Forms;
    using System.Text.RegularExpressions;
    
    namespace TextBoxErrorProvider
    {
    
            /// <summary>
            /// 对文本框内容进行验证
            /// 有四个属性需要设置:errorMessage            错误的文本
            ///                     regexString             验证用的正则表达式
            ///                     validationIsEmpty       是否验证是空值
            ///                     validationIsEmptyString 验证为空的文本框显示的错误消息
            /// 一个方法:GetErrorMessage                   返回当前文本框控件的当前错误描述字符串。
            /// </summary>
            public partial class TextBoxValidation : TextBox
            {
                public TextBoxValidation()
                {
                    InitializeComponent();
                    //验证处理事件
                    this.Validating += new CancelEventHandler(txtValidation_Validating);
                }
    
                private string m_errorMessage = "文本框输入错误";
                private bool m_validationIsEmpty = false;
                private string m_validationIsEmptyString = "文本框不能是空的";
                private string m_regexString = "";
    
                /// <summary>
                /// 验证用的表达式,默认是空的,即不验证。
                /// </summary>
                [Category("自定义属性"), Description("验证用的字符串表达式,默认是空的,即不验证。")]
                public string regexString
                {
                    get { return m_regexString; }
                    set { m_regexString = value; }
                }
                /// <summary>
                /// 错误消息
                /// </summary>
                [Category("自定义属性"), Description("用于设置使用正则表达式验证发生错误时显示的消息")]
                public string errorMessage
                {
                    get { return m_errorMessage; }
                    set { m_errorMessage = value; }
                }
    
    
                /// <summary>
                /// 是否验证文本框是空值,默认是不验证。
                /// </summary>
                [Category("自定义属性"), Description("是否验证文本框是空值,默认是不验证。")]
                public bool validationIsEmpty
                {
                    get { return m_validationIsEmpty; }
                    set { m_validationIsEmpty = value; }
                }
                /// <summary>
                /// 当验证文本框是空值时,显示的错误信息
                /// </summary>
                [Category("自定义属性"), Description("验证为空的文本框显示的错误消息")]
                public string validationIsEmptyString
                {
                    get { return m_validationIsEmptyString; }
                    set { m_validationIsEmptyString = value; }
                }
    
    
                /// <summary>
                /// 验证文本
                /// </summary>
                /// <param name="sender"></param>
                /// <param name="e"></param>
                public virtual void txtValidation_Validating(object sender, CancelEventArgs e)
                {
                     if (string.IsNullOrEmpty(this.Text))
                 {
                     if (m_validationIsEmpty)  //要求非空验证
                     {
                         txtErrorProvider.SetError(this, m_validationIsEmptyString);
                         return;
                     }
                     else
                     {
                         txtErrorProvider.SetError(this, "");
                   }
                }
                 else
                {
                    if (m_regexString != null)
                    {
                        if (!Regex.IsMatch(this.Text, m_regexString))
                        {
                            txtErrorProvider.SetError(this, m_errorMessage);
                        }
                        else
                        { txtErrorProvider.SetError(this, ""); }
                    }
                    else
                    {
                        txtErrorProvider.SetError(this, "");
                    }
                }
    } /// <summary> /// 返回当前文本框控件的当前错误描述字符串。 /// </summary> /// <returns></returns> public string GetErrorMessage() { return this.txtErrorProvider.GetError(this); }       
    //2012年9月27日21:47修改:为方便用户使用键盘输入,增加以下代码。
    /// <summary>
            /// 当用户按下Enter键或者是向下的方向键时,将控件的焦点移走。
            /// 用户按下向上方向键时,将控件的焦点移到上一个控件。
            /// </summary>
            /// <param name="sender"></param>
            /// <param name="e"></param>
             private void TextBoxValidation_KeyDown(object sender, KeyEventArgs e)
            {
               Form controlForm = null;
                //当用户按下Enter键或者是向下的方向键时,将控件的焦点移走
               switch (e.KeyCode)
               {
                   case Keys.Enter:case Keys.Down:
                       {
                           controlForm = this.FindForm();
                           if (controlForm != null)
                           {
                               controlForm.SelectNextControl(this, true, false, true, true);
                           }
                           break;
                       }
                    case Keys.Up: // 用户按下向上方向键时,将控件的焦点移到上一个控件。
                       {
                           controlForm = this.FindForm();
                           if (controlForm != null)
                           {
                               controlForm.SelectNextControl(this, false, false, true, true);
                           }
                           break;
                       }
                }
            }

    } }


         第三步:编译

         第四步:测试

         向解决方案中添加 windows窗体程序项目,在form1上拖拽四个textBoxValidation控件,四个label控件,形成如下图所示:

       为textBoxValidation1、textBoxValidation2添加TextChanged事件处理程序:

            //密码
            private void textBoxValidation1_TextChanged(object sender, EventArgs e)
            {
                this.textBoxValidation1.regexString = this.textBoxValidation2.Text;
            }
            //确认密码
            private void textBoxValidation2_TextChanged(object sender, EventArgs e)
            {
                this.textBoxValidation2.regexString = this.textBoxValidation1.Text;
            }

    设置textBoxValidation1、textBoxValidation2的validationIsEmpty属性为true。


    textBoxValidation3的属性设置如下图:

    textBoxValidation4的属性设置如下图:

     运行结果图:

  • 相关阅读:
    Android 主题theme说明 摘记
    Android开发 去掉标题栏方法 摘记
    安卓项目五子棋代码详解(二)
    关于 ake sure class name exists, is public, and has an empty constructor that is public
    百度地图3.0实现图文并茂的覆盖物
    android onSaveInstanceState()及其配对方法。
    关于集成科大讯飞语音识别的 一个问题总结
    android 关于 webview 控制其它view的显示 以及更改view数据失败的问题总结
    C# 解析 json Newtonsoft果然强大,代码写的真好
    c#数据类型 与sql的对应关系 以及 取值范围
  • 原文地址:https://www.cnblogs.com/shuiguang/p/2704985.html
Copyright © 2011-2022 走看看