WPF TextBox重写 支持选择输入格式

来源:互联网 发布:mac 图库 导出 编辑:程序博客网 时间:2024/05/22 15:29
using System;
using System.Net;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Documents;
using System.Windows.Ink;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Animation;
using System.Windows.Shapes;
using System.Text.RegularExpressions;

namespace cnpc.Dor.Bsc.Components.ProjectGroupReportPresentation.Utilities
{
    public class TextBoxExtend : TextBox
    {
        /// <summary>
        /// 未设置格式时默认用于整型
        /// </summary>
        private string intRegDefault = @"^[0-9]*$";
        /// <summary>
        /// 设置了格式字段时使用
        /// </summary>
        private string intReg = @"^\d{1,n}$";
        /// <summary>
        /// 未设置格式时默认用于小数
        /// </summary>
        private string decimalRegDefault = @"^\d+(\.\d+)?$";
        /// <summary>
        /// 设置了格式字段时小数使用
        /// </summary>
        private string decimalReg = @"^([-+]?\d{1,m})(\.\d{1,n})?$";
        /// <summary>
        /// 正则
        /// </summary>
        private Regex r;

        int IntLength = 0;
        int decimalLength = 0;
        private string OrigenalValue = "";
        bool isTextFirstSet = true; //OrigenalValue 是否已经设置过
        private DependencyPropertyChangedListener dataCotextListener;
        public TextBoxExtend()
            : base()
        {
            IsTabStop = true;

            dataCotextListener = DependencyPropertyChangedListener.Create(this, "DataContext");

            dataCotextListener.ValueChanged += ResetBackColor;
        }

        protected override void OnKeyDown(KeyEventArgs e)
        {
            if (TextType == InputClass.Normal)
            {
                e.Handled = false;

                base.OnKeyDown(e);
            }
            if (TextType == InputClass.Integer) //只能输入整数的情况
            {
                if ((e.Key >= Key.D0 && e.Key <= Key.D9)
                    || (e.Key >= Key.NumPad0 && e.Key <= Key.NumPad9)
                    )
                {
                    if (Text == String.Empty)
                    {
                        e.Handled = false;

                        base.OnKeyDown(e);
                    }
                    else if (TextFormat != null && Text.TrimStart('0').Length == IntLength)
                    {
                        e.Handled = true;
                    }
                    else if (r.IsMatch(Text.TrimStart('0')))
                    {
                        e.Handled = false;

                        base.OnKeyDown(e);
                    }
                    else
                    {
                        e.Handled = true;
                    }
                }
                else if (e.Key == Key.Back
                    || e.Key == Key.Delete
                    || e.Key == Key.Left
                    || e.Key == Key.Right
                    || e.Key == Key.Tab
                    || (e.Key == Key.V && ((Keyboard.Modifiers & ModifierKeys.Control) == ModifierKeys.Control))
                    || (e.Key == Key.C && ((Keyboard.Modifiers & ModifierKeys.Control) == ModifierKeys.Control))
                    || (e.Key == Key.X && ((Keyboard.Modifiers & ModifierKeys.Control) == ModifierKeys.Control))
                    || (e.Key == Key.Z && ((Keyboard.Modifiers & ModifierKeys.Control) == ModifierKeys.Control))
                    )
                {
                    e.Handled = false;

                    base.OnKeyDown(e);
                }
                else
                {
                    e.Handled = true;
                }
            }
            if (TextType == InputClass.Decimal) //带小数的情况
            {
                if (e.PlatformKeyCode == 190 || e.Key == Key.Decimal)
                {
                    if (this.Text.Contains(".") || Text.Length == 0)
                    {
                        e.Handled = true;
                    }
                    else
                    {
                        e.Handled = false;
                    }
                }
                else if ((e.Key >= Key.D0 && e.Key <= Key.D9)
                    || (e.Key >= Key.NumPad0 && e.Key <= Key.NumPad9)
                    )
                {
                    if (Text == String.Empty)
                    {
                        e.Handled = false;
                        base.OnKeyDown(e);
                    }
                    else if (Text.EndsWith(".")) //如果最后一个字符为 . 就先不用正则验证
                    {
                        e.Handled = false;

                        base.OnKeyDown(e);
                    }
                    else if (r.IsMatch(Text.TrimStart('0') + e.Key.ToString().Replace("NumPad", "").Replace("D",""))) //前面已0开头且整数有多位的情况
                    {
                        e.Handled = false;

                        base.OnKeyDown(e);
                    }
                    else if (r.IsMatch(Text.Trim() + e.Key.ToString().Replace("NumPad", "").Replace("D", "")))
                    {
                        e.Handled = false;

                        base.OnKeyDown(e);
                    }
                    else
                    {
                        e.Handled = true;
                    }
                }
                else if (e.Key == Key.Back
                    || e.Key == Key.Delete
                    || e.Key == Key.Left
                    || e.Key == Key.Right
                    || e.Key == Key.Tab
                    || (e.Key == Key.V && ((Keyboard.Modifiers & ModifierKeys.Control) == ModifierKeys.Control))
                    || (e.Key == Key.C && ((Keyboard.Modifiers & ModifierKeys.Control) == ModifierKeys.Control))
                    || (e.Key == Key.X && ((Keyboard.Modifiers & ModifierKeys.Control) == ModifierKeys.Control))
                    || (e.Key == Key.Z && ((Keyboard.Modifiers & ModifierKeys.Control) == ModifierKeys.Control))
                    )
                {
                    e.Handled = false;

                    base.OnKeyDown(e);
                }
                else
                {
                    e.Handled = true;
                }
            }
        }
        protected override void OnLostFocus(RoutedEventArgs e)
        {
            if (IsRequired) // 是否必输项
            {
                if (TextType == InputClass.Decimal || TextType == InputClass.Integer)
                {
                    if (this.Text.Trim() == "" || !this.r.IsMatch(this.Text.Trim().TrimStart('0')))
                    {
                        this.Text = "0";
                    }
                }
                if (TextType == InputClass.Normal)
                {
                    if (Text.Trim() == String.Empty)
                    {
                        this.Background = ColorDefine.RequireColor;
                    }
                    else if (this.Background != ColorDefine.EditedColor && this.Background != ColorDefine.ErrorColor)
                    {
                        this.Background = ColorDefine.NormalColor;
                    }
                }
                base.OnLostFocus(e);
            }
            else
            {
                if (TextType == InputClass.Decimal || TextType == InputClass.Integer)
                {
                    if (this.Text.Trim() != String.Empty
                        && !this.r.IsMatch(this.Text.Trim().TrimStart('0')))
                    {
                        base.Text = "";
                    }
                    base.OnLostFocus(e);
                }
            }
            if (this.AutoChangeColor)
            {
                if (OrigenalValue != Text)
                {
                    Background = ColorDefine.EditedColor;
                }
                else
                {
                    Background = ColorDefine.NormalColor;
                }
                base.OnLostFocus(e);
            }
        }
        protected override void OnGotFocus(RoutedEventArgs e)
        {
            if (isTextFirstSet)
            {
                OrigenalValue = Text;
                isTextFirstSet = false;
            }
            base.OnGotFocus(e);
        }

        public static readonly DependencyProperty InputTypeProperty =
            DependencyProperty.Register("TextType", typeof(InputClass), typeof(TextBoxExtend), null);
        /// <summary>
        /// 文本类型,Normal:普通文本,Integer:整数,Decimal:带小数的数字
        /// </summary>
        public InputClass TextType
        {
            get { return (InputClass)GetValue(InputTypeProperty); }
            set
            {
                if (value == InputClass.Decimal)
                {
                    //默认设置不带格式
                    TextAlignment = System.Windows.TextAlignment.Right;
                    r = new Regex(decimalRegDefault);
                }
                else if (value == InputClass.Integer)
                {
                    //默认设置不带格式
                    TextAlignment = System.Windows.TextAlignment.Right;
                    r = new Regex(intRegDefault);
                }
                SetValue(InputTypeProperty, value);
            }
        }

        public static readonly DependencyProperty IsRequiredProperty =
            DependencyProperty.Register("IsRequired", typeof(bool), typeof(TextBoxExtend), null);
        /// <summary>
        /// 是否必填项
        /// </summary>
        public bool IsRequired
        {
            get { return (bool)GetValue(IsRequiredProperty); }
            set { SetValue(IsRequiredProperty, value); }
        }

        public static readonly DependencyProperty TextFormatProperty =
            DependencyProperty.Register("TextFormat", typeof(string), typeof(TextBoxExtend), null);
        /// <summary>
        /// 整数或带小数数值时使用:####.##
        /// </summary>
        public string TextFormat
        {
            get { return (string)GetValue(TextFormatProperty); }
            set
            {
                if (TextType == InputClass.Normal)
                {
                    //throw new Exception("请先设置TextType属性!");
                }
                if (TextType == InputClass.Integer)
                {
                    //设置正则表达式
                    IntLength = value.Length;
                    if (value != String.Empty)
                    {
                        intReg = intReg.Replace("n", (value.Length).ToString());
                        r = new Regex(intReg);
                    }
                    else
                    {
                        r = new Regex(decimalRegDefault);
                    }
                }
                else if (TextType == InputClass.Decimal)
                {
                    string[] pars = value.Split('.');

                    //设置正则表达式
                    if (pars.Length != 2)
                        throw new FormatException("Format格式设置错误!TextType为Decimal时,必须有小数,例如:####.##");
                    else
                    {
                        IntLength = pars[0].Length;
                        decimalLength = pars[1].Length;
                        string reg = decimalReg.Replace("m", IntLength.ToString()).Replace("n", decimalLength.ToString());
                        r = new Regex(reg);
                    }
                }
                SetValue(TextFormatProperty, value);
            }
        }

        private void ResetBackColor(object sender, DependencyPropertyValueChangedEventArgs e)
        {
            this.Background = ColorDefine.NormalColor;
            isTextFirstSet = true;
            if (isTextFirstSet)
            {
                OrigenalValue = Text;
                isTextFirstSet = false;
            }
        }

        public bool AutoChangeColor
        {
            get { return (bool)GetValue(AutoChangeColorProperty); }
            set { SetValue(AutoChangeColorProperty, value); }
        }

        public static readonly DependencyProperty AutoChangeColorProperty =
            DependencyProperty.Register("AutoChangeColor", typeof(bool), typeof(TextBoxExtend), null);

    }
    public enum InputClass
    {
        Normal = 0,
        Integer = 1,
        Decimal = 2,
    }
}

0 0