KeyDown / KeyPress [Résolu]

Whismeril 11409 Messages postés mardi 11 mars 2003Date d'inscriptionContributeurStatut 21 avril 2018 Dernière intervention - 2 juin 2011 à 19:30 - Dernière réponse : Whismeril 11409 Messages postés mardi 11 mars 2003Date d'inscriptionContributeurStatut 21 avril 2018 Dernière intervention
- 6 juin 2011 à 20:13
Bonjour,
j'ai un formulaire ou certains paramètres doivent être des nombres.
J'utilise donc des MaskedTextBox avec "0000" comme masque.
L'application tourne sur des portable sans clavier numérique, les utilisateur jonglait donc avec Verr.Num ou Shift.
Cependant cette appli est utilisée en parallèle d'une autre ou les saisies sont en minuscules.
J'ai donc mis le clavier en majuscule quand les MaskedTextBox ont le focus et remis le clavier à l'état initial quand ils perdent le focus.
Il y a des cas ou cela ne fonctionne pas bien (appli quiter par Alt+F4 en cours de saisie...)

J'ai donc essayé de changer la frappe, on ne peut pas le faire dans le KeyPress, puisque le masquage n'autorise pas l'événement.
J'ai écrit cette fonction que l'on appelle du keydown ou keyup.
Je n'ai pas trouvé comment forcer la majuscule sur la touche, alors je fais un sendkeys (mais je ne trouve pas ça propre) et le masque bloque la "vraie" touche.
Cependant le masque laisse passer "_", j'ai donc essayé de mettre e.Handle à True dans les 3 événements, ça ne fonctionne pas, ni e = null, j'envoie donc un "BackSpace" par sendkey, (pas propre non plus):

/// <summary>
/// Génére un chiffre si les touches D1 à D0 sont appuyées sans Maj.
/// Cette procédure doit être appelée dans le KeyDown d'une MaskedTextBox dont le masque est 000..0.
/// </summary>
/// paramètre e de l'événement


/// <returns></returns>
private void Chiffre(ref KeyEventArgs e)
{
      //si la VerMaj est actif, on sort
      if (Console.CapsLock) return;

      //Si une touche D0 à D9 est appuyée sans le shift
      if ((e.KeyValue > 47) && (e.KeyValue < 58) && (!e.Shift))
            {
                if (e.KeyCode == Keys.D8) SendKeys.Send("{BKSP}"); //ne me plait pas
                //e.Handled <bold>(e.KeyCode</bold> Keys.D8); Ne fonctionne pas
                //e = null; ne marche pas non plus

                int MonChiffre = e.KeyValue - 48; // 0 c'est 48, 1 c'est 49 etc.
                SendKeys.Send(MonChiffre.ToString()); //préfèrerais un truc du style e = 0
            }
}

Quelqu'un aurait il une meilleur idée?
PS c'est en framework 2.0 car un PC utilisateur est sous 2000.


Merci

Whismeril
Afficher la suite 

5 réponses

Répondre au sujet
Whismeril 11409 Messages postés mardi 11 mars 2003Date d'inscriptionContributeurStatut 21 avril 2018 Dernière intervention - Modifié par Whismeril le 14/06/2014 à 12:32
+3
Utile
Bonsoir,
avec le Sendkey ça a tendance à reboucler infiniment, d'ou les lignes qui te semblaient inutiles.
Ta proposition ne fonctionne pas, mais j'ai fini par trouver comment modifier le message:
protected override bool ProcessCmdKey(ref Message msg, Keys keyData)
{
        //Si VERR.MAJ alors les touches au dessus de AZERTY seront des chiffres, on laisse faire 
        if (Console.CapsLock) return base.ProcessCmdKey(ref msg, keyData);

        switch (keyData)
        {
            //Touches au dessus de AZERTY sans SHIFT
            case Keys.D0:
            case Keys.D1:
            case Keys.D2:
            case Keys.D3:
            case Keys.D4
            case Keys.D5:
            case Keys.D6:
            case Keys.D7:
            case Keys.D8:
            case Keys.D9:
                //c'est là qu'on transforme en chiffre
                //msg.WParam correspond au KeyCode de la touche, il suffit d'applique "une translation"
                //+= ne focntionne pas donc je le fais en 2 lignes
                int MonChiffre = (int)msg.WParam + 48;
                msg.WParam = (IntPtr)MonChiffre;      
                return base.ProcessCmdKey(ref msg, keyData);

             default:
               return base.ProcessCmdKey(ref msg, keyData);
        }
}


Merci de ton aide.

Whismeril
Cette réponse vous a-t-elle aidé ?  
Commenter la réponse de Whismeril
nhervagault 6069 Messages postés dimanche 13 avril 2003Date d'inscription 15 juillet 2011 Dernière intervention - 3 juin 2011 à 21:39
0
Utile
Salut,

Expliques mieux ton probleme?
Tu veux que les touches
1234567890 au dessus du clavier AZERTY
fonctionne avec ou sans caplock ??

Peux tu montrer comment sont attachés les evenements
clavier?
Car la declaration de ton callback me semble fausse

c'est normalement
...(object sender, ..EventArgs e) 


Ce qui n'est pas dans ton exemple.

Merci d'utiliser les balises code!!
Commenter la réponse de nhervagault
Whismeril 11409 Messages postés mardi 11 mars 2003Date d'inscriptionContributeurStatut 21 avril 2018 Dernière intervention - Modifié par Whismeril le 4/12/2014 à 17:32
0
Utile
Bonsoir,
merci de ta réponse.
Il s'agit bien des touches numériques au dessus du clavier.
Pour la signature de l'évènement, j'ai essayé dans le KeyDown, le KeyUp et le KeyPress.
Afin de ne pas m'emmêler les pinceaux, j'ai écrit cette fonction que j'appelle de l'un ou l'autre.
Je n'ai pas transféré sender, parce que je n'en ai pas trouvé l'utilité, le contrôle a forcement le focus puisqu'un appui touche le concerne.

je remets mon code avec les balises (désolé)
/// <summary> 
/// Génére un chiffre si les touches D1 à D0 sont appuyées sans Maj. 
/// Cette procédure doit être appelée dans le KeyDown d'une MaskedTextBox dont le masque est 000..0. 
/// </summary> 
/// paramètre e de l'événement

 
/// <returns></returns> 
private void Chiffre(ref KeyEventArgs e) 
{ 
//si la VerMaj est actif, on sort 
if (Console.CapsLock) return; 

//Si une touche D0 à D9 est appuyée sans le shift 
if ((e.KeyValue > 47) && (e.KeyValue < 58) && (!e.Shift)) 
{ 
    if (e.KeyCode == Keys.D8) SendKeys.Send("{BKSP}"); //ne me plait pas 
     //e.Handled <bold>(e.KeyCode</bold> Keys.D8); Ne fonctionne pas 
     //e = null; ne marche pas non plus 

     int MonChiffre = e.KeyValue - 48; // 0 c'est 48, 1 c'est 49 etc. 
    SendKeys.Send(MonChiffre.ToString()); //préfèrerais un truc du style e = 0 
   } 
} 


Entre temps, j'ai tenté d'appeler cette void depuis le KeyDown, et d'y affecter True à une variable, afin de remettre e.Handled à true dans le KeyPress et le KeyUp, mais ça n'a pas marché non plus.


Whismeril
Commenter la réponse de Whismeril
Whismeril 11409 Messages postés mardi 11 mars 2003Date d'inscriptionContributeurStatut 21 avril 2018 Dernière intervention - Modifié par Whismeril le 4/12/2014 à 17:32
0
Utile
Bonjour,
j'ai résolu une partie de mon problème en dérivant la MaskedTextBox et réécrivant la méthode ProcessCmdKey.
Cependant j'utilise toujours SendKey (ce qui ne me parais pas idéal).
using System;
using System.Windows.Forms;

namespace ChiffreBox
{
    class MaMaskedTextBox:MaskedTextBox
    {
        public MaMaskedTextBox()
        {
        }

        protected override bool ProcessCmdKey(ref Message msg, Keys keyData)
        {
            //Si VERR.MAJ alors les touches au dessus de AZERTY seront des chiffres, on laisse faire 
            if (Console.CapsLock) return base.ProcessCmdKey(ref msg, keyData);

            switch (keyData)
            {
                //Touches au dessus de AZERTY avec SHIFT
                //Cas présents pour ne pas risquer de couac avec la série suivante
                case (Keys.D0 | Keys.Shift):
                case (Keys.D1 | Keys.Shift):
                case (Keys.D2 | Keys.Shift):
                case (Keys.D3 | Keys.Shift):
                case (Keys.D4 | Keys.Shift):
                case (Keys.D5 | Keys.Shift):
                case (Keys.D6 | Keys.Shift):
                case (Keys.D7 | Keys.Shift):
                case (Keys.D8 | Keys.Shift):
                case (Keys.D9 | Keys.Shift):
                    //c'est des chiffres, donc on laisse faire
                    return base.ProcessCmdKey(ref msg, keyData);

                //Touches au dessus de AZERTY sans SHIFT
                case Keys.D0:
                case Keys.D1:
                case Keys.D2:
                case Keys.D3:
                case Keys.D4:
                case Keys.D5:
                case Keys.D6:
                case Keys.D7:
                case Keys.D8:
                case Keys.D9:
                    //c'est là qu'il faut appliquer la majuscule
                    int MonChiffre = (int)msg.WParam - 48; // 0 c'est 48, 1 c'est 49 etc.
                    SendKeys.Send(MonChiffre.ToString()); //préfèrerais un truc du style msg = MonChiffre!! 
                    return true;
                
                default:
                    return base.ProcessCmdKey(ref msg, keyData);
            }

        }
    }
}


Je pense qu'on doit pouvoir agir sur msg (vu qu'il est passé par référence), mais je n'ai pas trouvé comment.
Si quelqu'un a une idée pour remplacer le SendKey, ou une meilleure solution.

Merci


Whismeril
Commenter la réponse de Whismeril
sebmafate 4947 Messages postés lundi 17 février 2003Date d'inscription 14 février 2014 Dernière intervention - Modifié par Whismeril le 4/12/2014 à 17:32
0
Utile
Bonjour,

As-tu essayer de faire :

        protected override bool ProcessCmdKey(ref Message msg, Keys keyData)
        {
            //Si VERR.MAJ alors les touches au dessus de AZERTY seront des chiffres, on laisse faire 
            if (Console.CapsLock) return base.ProcessCmdKey(ref msg, keyData);

            switch (keyData)
            {

/* pour moi, cette partie ne sert à rien 
                //Touches au dessus de AZERTY avec SHIFT
                //Cas présents pour ne pas risquer de couac avec la série suivante
                case (Keys.D0 | Keys.Shift):
                case (Keys.D1 | Keys.Shift):
                case (Keys.D2 | Keys.Shift):
                case (Keys.D3 | Keys.Shift):
                case (Keys.D4 | Keys.Shift):
                case (Keys.D5 | Keys.Shift):
                case (Keys.D6 | Keys.Shift):
                case (Keys.D7 | Keys.Shift):
                case (Keys.D8 | Keys.Shift):
                case (Keys.D9 | Keys.Shift):
                    //c'est des chiffres, donc on laisse faire
                    return base.ProcessCmdKey(ref msg, keyData);

*/

                //Touches au dessus de AZERTY sans SHIFT
                case Keys.D0:
                case Keys.D1:
                case Keys.D2:
                case Keys.D3:
                case Keys.D4:
                case Keys.D5:
                case Keys.D6:
                case Keys.D7:
                case Keys.D8:
                case Keys.D9:
                    return base.ProcessCmdKey(ref msg, keyData | Keys.Shift);
                default:
                    return base.ProcessCmdKey(ref msg, keyData);
            }

        }



Sébastien FERRAND
Ingénieur Concepteur Senior
Microsoft Visual C# MVP 2004 - 2009
Blog Photo
Commenter la réponse de sebmafate

Vous n'êtes pas encore membre ?

inscrivez-vous, c'est gratuit et ça prend moins d'une minute !

Les membres obtiennent plus de réponses que les utilisateurs anonymes.

Le fait d'être membre vous permet d'avoir un suivi détaillé de vos demandes et codes sources.

Le fait d'être membre vous permet d'avoir des options supplémentaires.