I've created a static class numeric Textbox but i wan't to control what the users paste in te textbox.
For handling paste Event i use textchanged event:
static public void textChanged(EventArgs e, TextBox textbox, double tailleMini, double tailleMaxi, string carNonAutorisé)
{
//Recherche dans la TextBox, la première occurrence de l'expression régulière.
Match match = Regex.Match(textbox.Text, carNonAutorisé);
/*Si il y a une Mauvaise occurence:
* - On efface le contenu collé
* - On prévient l'utilisateur
*/
if (match.Success)
{
textbox.Text = "";
MessageBox.Show("Votre copie un ou des caractère(s) non autorisé", "Attention", MessageBoxButtons.OK, MessageBoxIcon.Information);
}
tailleTextBox(textbox, tailleMini, tailleMaxi);
}
In another class i use this static methode like this
private void tbxSigné_TextChanged(object sender, EventArgs e)
{
FiltreTbx.textChanged(e, tbxSigné, double.MinValue, double.MaxValue, @"[^\d\,\;\.\-]");
}
What i wan't to do is something like that:
if (match.Success)
{
textbox.Text = //Write the text before users paste in the textbox;
}
Anyone have an idea please?
First of all, have you considered using MaskedTextBox instead? It can handle the character filtering for you.
However, for the sake of this exercise, you could think of a solution along this line. This is the usage:
public Form1()
{
InitializeComponent();
FiltreTbx.AddTextBoxFilter(tbxSigné,
double.MinValue, double.MaxValue,
@"[^\d\,\;\.\-]");
}
This AddTextBoxFilter
is a new static method, which you only call once. It will add a TextChanged handler to the TextBox
. This handler uses a closure to store the previous Text
in the text box.
Your static method gained an extra parameter to pass along this previous text.
public class FiltreTbx
{
public static void AddTextBoxFilter(TextBox textbox,
double tailleMini, double tailleMaxi,
string carNonAutorisé)
{
string previousText = textbox.Text;
textbox.TextChanged +=
delegate(object sender, EventArgs e)
{
textChanged(e, textbox, tailleMini, tailleMaxi,
carNonAutorisé, previousText);
previousText = textbox.Text;
};
}
static public void textChanged(EventArgs e, TextBox textbox,
double tailleMini, double tailleMaxi,
string carNonAutorisé, string previousText)
{
//Recherche dans la TextBox, la première occurrence de l'expression régulière.
Match match = Regex.Match(textbox.Text, carNonAutorisé);
/*Si il y a une Mauvaise occurence:
* - On efface le contenu collé
* - On prévient l'utilisateur
*/
if (match.Success)
{
// Set the Text back to the value it had after the previous
// TextChanged event.
textbox.Text = previousText;
MessageBox.Show("Votre copie un ou des caractère(s) non autorisé",
"Attention", MessageBoxButtons.OK,
MessageBoxIcon.Information);
}
tailleTextBox(textbox, tailleMini, tailleMaxi);
}
}
I'm not sure what tailleTextBox
is supposed to do exactly, you did not include that source code, but I suspect it enforces the minimum and maximum values?
Alternate solution
If you want to handle the Paste operation yourself, before it even happens, you will have to intercept the WM_PASTE
message to the text box. One way of doing is would be by creating a specialized control:
using System;
using System.Windows.Forms;
class MyTextBox : TextBox
{
private const int WM_PASTE = 0x0302;
protected override void WndProc(ref Message m)
{
if (m.Msg != WM_PASTE)
{
// Handle all other messages normally
base.WndProc(ref m);
}
else
{
// Some simplified example code that complete replaces the
// text box content only if the clipboard contains a valid double.
// I'll leave improvement of this behavior as an exercise :)
double value;
if (double.TryParse(Clipboard.GetText(), out value))
{
Text = value.ToString();
}
}
}
}
If you define the class in your WinForms project, you should be able to drag it onto your form like any other control.