欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  IT编程

(二十八)c#Winform自定义控件-文本框(一)

程序员文章站 2022-05-29 10:27:48
前提 入行已经7,8年了,一直想做一套漂亮点的自定义控件,于是就有了本系列文章。 开源地址:https://gitee.com/kwwwvagaa/net_winform_custom_control 如果觉得写的还行,请点个 star 支持一下吧 欢迎前来交流探讨: 企鹅群568015492 目录 ......

前提

入行已经7,8年了,一直想做一套漂亮点的自定义控件,于是就有了本系列文章。

开源地址:

如果觉得写的还行,请点个 star 支持一下吧

欢迎前来交流探讨: 企鹅群568015492 

目录

准备工作

终于到文本框了,文本框将包含原文本框扩展,透明文本框,数字输入文本框,带边框文本框

本文将讲解原文本框扩展,主要增加水印和输入控制

开始

添加一个组件,命名textboxex,继承textbox

属性

  1 private bool blnfocus = false;
  2 
  3         private string _prompttext = string.empty;
  4 
  5         private font _promptfont = new font("微软雅黑", 15f, fontstyle.regular, graphicsunit.pixel);
  6 
  7         private color _promptcolor = color.gray;
  8 
  9         private rectangle _myrectangle = rectangle.fromltrb(1, 3, 1000, 3);
 10 
 11         private textinputtype _inputtype = textinputtype.notcontrol;
 12 
 13         private string _regexpattern = "";
 14 
 15         private string m_stroldvalue = string.empty;
 16 
 17         private decimal _maxvalue = 1000000m;
 18 
 19         private decimal _minvalue = -1000000m;
 20 
 21         private int _declength = 2;
 22 
 23         /// <summary>
 24         /// 水印文字
 25         /// </summary>
 26         [description("水印文字"), category("自定义")]
 27         public string prompttext
 28         {
 29             get
 30             {
 31                 return this._prompttext;
 32             }
 33             set
 34             {
 35                 this._prompttext = value;
 36                 this.onpaint(null);
 37             }
 38         }
 39 
 40         [description("水印字体"), category("自定义")]
 41         public font promptfont
 42         {
 43             get
 44             {
 45                 return this._promptfont;
 46             }
 47             set
 48             {
 49                 this._promptfont = value;
 50             }
 51         }
 52 
 53         [description("水印颜色"), category("自定义")]
 54         public color promptcolor
 55         {
 56             get
 57             {
 58                 return this._promptcolor;
 59             }
 60             set
 61             {
 62                 this._promptcolor = value;
 63             }
 64         }
 65 
 66         public rectangle myrectangle
 67         {
 68             get;
 69             set;
 70         }
 71 
 72         public string oldtext
 73         {
 74             get;
 75             set;
 76         }
 77 
 78         [description("获取或设置一个值,该值指示文本框中的文本输入类型。")]
 79         public textinputtype inputtype
 80         {
 81             get
 82             {
 83                 return this._inputtype;
 84             }
 85             set
 86             {
 87                 this._inputtype = value;
 88                 if (value != textinputtype.notcontrol)
 89                 {
 90                     textchanged -= new eventhandler(this.textboxex_textchanged);
 91                     textchanged += new eventhandler(this.textboxex_textchanged);
 92                 }
 93                 else
 94                 {
 95                     textchanged -= new eventhandler(this.textboxex_textchanged);
 96                 }
 97             }
 98         }
 99         /// <summary>
100         /// 获取或设置一个值,该值指示当输入类型inputtype=regex时,使用的正则表达式。
101         /// </summary>
102         [description("获取或设置一个值,该值指示当输入类型inputtype=regex时,使用的正则表达式。")]
103         public string regexpattern
104         {
105             get
106             {
107                 return this._regexpattern;
108             }
109             set
110             {
111                 this._regexpattern = value;
112             }
113         }
114         /// <summary>
115         /// 当inputtype为数字类型时,能输入的最大值
116         /// </summary>
117         [description("当inputtype为数字类型时,能输入的最大值。")]
118         public decimal maxvalue
119         {
120             get
121             {
122                 return this._maxvalue;
123             }
124             set
125             {
126                 this._maxvalue = value;
127             }
128         }
129         /// <summary>
130         /// 当inputtype为数字类型时,能输入的最小值
131         /// </summary>
132         [description("当inputtype为数字类型时,能输入的最小值。")]
133         public decimal minvalue
134         {
135             get
136             {
137                 return this._minvalue;
138             }
139             set
140             {
141                 this._minvalue = value;
142             }
143         }
144         /// <summary>
145         /// 当inputtype为数字类型时,能输入的最小值
146         /// </summary>
147         [description("当inputtype为数字类型时,小数位数。")]
148         public int declength
149         {
150             get
151             {
152                 return this._declength;
153             }
154             set
155             {
156                 this._declength = value;
157             }
158         }

一些事件

 1 void textboxex_keypress(object sender, keypresseventargs e)
 2         {
 3             //以下代码  取消按下回车或esc的“叮”声
 4             if (e.keychar == system.convert.tochar(13) || e.keychar == system.convert.tochar(27))
 5             {
 6                 e.handled = true;
 7             }
 8         }
 9 
10         private void textboxex_mouseup(object sender, mouseeventargs e)
11         {
12             if (this.blnfocus)
13             {
14                 base.selectall();
15                 this.blnfocus = false;
16             }
17         }
18 
19         private void textboxex_gotfocus(object sender, eventargs e)
20         {
21             this.blnfocus = true;
22             base.selectall();
23         }
24 
25         private void textboxex_textchanged(object sender, eventargs e)
26         {
27             if (this.text == "")
28             {
29                 this.m_stroldvalue = this.text;
30             }
31             else if (this.m_stroldvalue != this.text)
32             {
33                 if (!controlhelper.checkinputtype(this.text, this._inputtype, this._maxvalue, this._minvalue, this._declength, this._regexpattern))
34                 {
35                     int num = base.selectionstart;
36                     if (this.m_stroldvalue.length < this.text.length)
37                     {
38                         num--;
39                     }
40                     else
41                     {
42                         num++;
43                     }
44                     base.textchanged -= new eventhandler(this.textboxex_textchanged);
45                     this.text = this.m_stroldvalue;
46                     base.textchanged += new eventhandler(this.textboxex_textchanged);
47                     if (num < 0)
48                     {
49                         num = 0;
50                     }
51                     base.selectionstart = num;
52                 }
53                 else
54                 {
55                     this.m_stroldvalue = this.text;
56                 }
57             }
58         }

重绘

 1  protected override void onpaint(painteventargs e)
 2         {
 3             base.onpaint(e);
 4             if (string.isnullorempty(this.text) && !string.isnullorempty(this._prompttext))
 5             {
 6                 if (e == null)
 7                 {
 8                     using (graphics graphics = graphics.fromhwnd(base.handle))
 9                     {
10                         if (this.text.length == 0 && !string.isnullorempty(this.prompttext))
11                         {
12                             textformatflags textformatflags = textformatflags.endellipsis | textformatflags.verticalcenter;
13                             if (this.righttoleft == righttoleft.yes)
14                             {
15                                 textformatflags |= (textformatflags.right | textformatflags.righttoleft);
16                             }
17                             textrenderer.drawtext(graphics, this.prompttext, this._promptfont, base.clientrectangle, this._promptcolor, textformatflags);
18                         }
19                     }
20                 }
21             }
22         }

下面是完整代码

  1 // 版权所有  黄正辉  交流群:568015492   qq:623128629
  2 // 文件名称:textboxex.cs
  3 // 创建日期:2019-08-15 16:03:44
  4 // 功能描述:textbox
  5 // 项目地址:https://gitee.com/kwwwvagaa/net_winform_custom_control
  6 using system;
  7 using system.collections.generic;
  8 using system.componentmodel;
  9 using system.diagnostics;
 10 using system.drawing;
 11 using system.linq;
 12 using system.text;
 13 using system.windows.forms;
 14 
 15 namespace hzh_controls.controls
 16 {
 17     public partial class textboxex : textbox
 18     {
 19         private bool blnfocus = false;
 20 
 21         private string _prompttext = string.empty;
 22 
 23         private font _promptfont = new font("微软雅黑", 15f, fontstyle.regular, graphicsunit.pixel);
 24 
 25         private color _promptcolor = color.gray;
 26 
 27         private rectangle _myrectangle = rectangle.fromltrb(1, 3, 1000, 3);
 28 
 29         private textinputtype _inputtype = textinputtype.notcontrol;
 30 
 31         private string _regexpattern = "";
 32 
 33         private string m_stroldvalue = string.empty;
 34 
 35         private decimal _maxvalue = 1000000m;
 36 
 37         private decimal _minvalue = -1000000m;
 38 
 39         private int _declength = 2;
 40 
 41         /// <summary>
 42         /// 水印文字
 43         /// </summary>
 44         [description("水印文字"), category("自定义")]
 45         public string prompttext
 46         {
 47             get
 48             {
 49                 return this._prompttext;
 50             }
 51             set
 52             {
 53                 this._prompttext = value;
 54                 this.onpaint(null);
 55             }
 56         }
 57 
 58         [description("水印字体"), category("自定义")]
 59         public font promptfont
 60         {
 61             get
 62             {
 63                 return this._promptfont;
 64             }
 65             set
 66             {
 67                 this._promptfont = value;
 68             }
 69         }
 70 
 71         [description("水印颜色"), category("自定义")]
 72         public color promptcolor
 73         {
 74             get
 75             {
 76                 return this._promptcolor;
 77             }
 78             set
 79             {
 80                 this._promptcolor = value;
 81             }
 82         }
 83 
 84         public rectangle myrectangle
 85         {
 86             get;
 87             set;
 88         }
 89 
 90         public string oldtext
 91         {
 92             get;
 93             set;
 94         }
 95 
 96         [description("获取或设置一个值,该值指示文本框中的文本输入类型。")]
 97         public textinputtype inputtype
 98         {
 99             get
100             {
101                 return this._inputtype;
102             }
103             set
104             {
105                 this._inputtype = value;
106                 if (value != textinputtype.notcontrol)
107                 {
108                     textchanged -= new eventhandler(this.textboxex_textchanged);
109                     textchanged += new eventhandler(this.textboxex_textchanged);
110                 }
111                 else
112                 {
113                     textchanged -= new eventhandler(this.textboxex_textchanged);
114                 }
115             }
116         }
117         /// <summary>
118         /// 获取或设置一个值,该值指示当输入类型inputtype=regex时,使用的正则表达式。
119         /// </summary>
120         [description("获取或设置一个值,该值指示当输入类型inputtype=regex时,使用的正则表达式。")]
121         public string regexpattern
122         {
123             get
124             {
125                 return this._regexpattern;
126             }
127             set
128             {
129                 this._regexpattern = value;
130             }
131         }
132         /// <summary>
133         /// 当inputtype为数字类型时,能输入的最大值
134         /// </summary>
135         [description("当inputtype为数字类型时,能输入的最大值。")]
136         public decimal maxvalue
137         {
138             get
139             {
140                 return this._maxvalue;
141             }
142             set
143             {
144                 this._maxvalue = value;
145             }
146         }
147         /// <summary>
148         /// 当inputtype为数字类型时,能输入的最小值
149         /// </summary>
150         [description("当inputtype为数字类型时,能输入的最小值。")]
151         public decimal minvalue
152         {
153             get
154             {
155                 return this._minvalue;
156             }
157             set
158             {
159                 this._minvalue = value;
160             }
161         }
162         /// <summary>
163         /// 当inputtype为数字类型时,能输入的最小值
164         /// </summary>
165         [description("当inputtype为数字类型时,小数位数。")]
166         public int declength
167         {
168             get
169             {
170                 return this._declength;
171             }
172             set
173             {
174                 this._declength = value;
175             }
176         }
177 
178         public textboxex()
179         {
180             this.initializecomponent();
181             base.gotfocus += new eventhandler(this.textboxex_gotfocus);
182             base.mouseup += new mouseeventhandler(this.textboxex_mouseup);
183             base.keypress += textboxex_keypress;
184         }
185 
186         void textboxex_keypress(object sender, keypresseventargs e)
187         {
188             //以下代码  取消按下回车或esc的“叮”声
189             if (e.keychar == system.convert.tochar(13) || e.keychar == system.convert.tochar(27))
190             {
191                 e.handled = true;
192             }
193         }
194 
195         private void textboxex_mouseup(object sender, mouseeventargs e)
196         {
197             if (this.blnfocus)
198             {
199                 base.selectall();
200                 this.blnfocus = false;
201             }
202         }
203 
204         private void textboxex_gotfocus(object sender, eventargs e)
205         {
206             this.blnfocus = true;
207             base.selectall();
208         }
209 
210         private void textboxex_textchanged(object sender, eventargs e)
211         {
212             if (this.text == "")
213             {
214                 this.m_stroldvalue = this.text;
215             }
216             else if (this.m_stroldvalue != this.text)
217             {
218                 if (!controlhelper.checkinputtype(this.text, this._inputtype, this._maxvalue, this._minvalue, this._declength, this._regexpattern))
219                 {
220                     int num = base.selectionstart;
221                     if (this.m_stroldvalue.length < this.text.length)
222                     {
223                         num--;
224                     }
225                     else
226                     {
227                         num++;
228                     }
229                     base.textchanged -= new eventhandler(this.textboxex_textchanged);
230                     this.text = this.m_stroldvalue;
231                     base.textchanged += new eventhandler(this.textboxex_textchanged);
232                     if (num < 0)
233                     {
234                         num = 0;
235                     }
236                     base.selectionstart = num;
237                 }
238                 else
239                 {
240                     this.m_stroldvalue = this.text;
241                 }
242             }
243         }
244 
245         protected override void onpaint(painteventargs e)
246         {
247             base.onpaint(e);
248             if (string.isnullorempty(this.text) && !string.isnullorempty(this._prompttext))
249             {
250                 if (e == null)
251                 {
252                     using (graphics graphics = graphics.fromhwnd(base.handle))
253                     {
254                         if (this.text.length == 0 && !string.isnullorempty(this.prompttext))
255                         {
256                             textformatflags textformatflags = textformatflags.endellipsis | textformatflags.verticalcenter;
257                             if (this.righttoleft == righttoleft.yes)
258                             {
259                                 textformatflags |= (textformatflags.right | textformatflags.righttoleft);
260                             }
261                             textrenderer.drawtext(graphics, this.prompttext, this._promptfont, base.clientrectangle, this._promptcolor, textformatflags);
262                         }
263                     }
264                 }
265             }
266         }
267 
268         protected override void wndproc(ref message m)
269         {
270             base.wndproc(ref m);
271             if (m.msg == 15 || m.msg == 7 || m.msg == 8)
272             {
273                 this.onpaint(null);
274             }
275         }
276 
277         protected override void ontextchanged(eventargs e)
278         {
279             base.ontextchanged(e);
280             base.invalidate();
281         }
282     }
283 }

用处及效果

用处:需要控制输入,需要显示水印

最后的话

如果你喜欢的话,请到  点个星 星吧