VBA - textbox - simplification code

Bonjour,
J'ai crée un Userform-DEVIS et il y a des TEXTBOX pour mettre des quantité, et un fois VALIDER par un Commandbox, celui ci change de Couleur pour signaler a l'utilisateur que c'est OK et il peut retourné au menu.
Mais il arrive que meme apres Validation il change de quantité etc, pas de soucis le Commandbox change de couleur passe au Rouge par exemple afin de revalider.

Donc pour arrivé a cela, j'ai crée plusieurs Private Sub MENUIV1_Change() et jusqu'a Private Sub MENUIV50_Change()
donc j'ai 50 private Sub pour 50 Textbox avec la meme commande dans chaque Sub

Et ma question et peut on simplifier
en un seul SUB par exemple ?

D'avance Merci et j'espere avoir était clair

Bonjour,

Oui, c'est même recommandéé, mais un petit peu compliqué :Si tu n'en a jamais fait il te faudra faire sous-traiter ça par un expert...

Sinon faire une recherche sur Google sur le thème " module de classe vba "

A+

Bonjour fathlaur, galopin01,

Oui, au lieu d'avoir 50 Private Sub différents pour chaque TextBox, vous pouvez utiliser une seule procédure et l'attribuer à tous les TextBox en utilisant la fonction Handles. Cependant, cela n'est pas directement possible en VBA, mais vous pouvez utiliser une technique similaire en utilisant le gestionnaire d'événements de classe.

Voici un exemple sur la façon de le faire:

1 Créez une nouvelle classe. Pour cela, allez dans "Insert" > "Class Module". Nommez cette classe, disons clsTextBox.
2 Dans ce nouveau module de classe, ajoutez le code suivant :

Public WithEvents tb As MSForms.TextBox

Private Sub tb_Change()
    ' Votre logique de validation ici.
    ' Utilisez tb pour accéder aux propriétés du TextBox qui a déclenché l'événement.
End Sub

3 Ensuite, dans votre UserForm, vous devez déclarer une Collection ou un Array pour stocker des instances de clsTextBox, et assigner chaque TextBox à une instance.

Private textBoxes As Collection

Private Sub UserForm_Initialize()
    Set textBoxes = New Collection
    Dim ctl As Control
    For Each ctl In Me.Controls
        If TypeOf ctl Is MSForms.TextBox Then
            Dim ctb As New clsTextBox
            Set ctb.tb = ctl
            textBoxes.Add ctb
        End If
    Next ctl
End Sub

Maintenant, chaque fois qu'un TextBox change, le gestionnaire d'événements dans clsTextBox sera déclenché. Vous pouvez ajouter votre logique de validation dans tb_Change() pour changer la couleur du TextBox, etc.

Sachez que chaque fois que vous modifiez le TextBox, vous utilisez l'objet tb pour accéder aux propriétés et méthodes du TextBox qui a déclenché l'événement. J'espère que cela vous aidera !

Merci Abderrahmane BENALI cela m'as un peu aidé, mais ...
Pour info mais textbox je l'ai est renommé par MENUIV. (Question de clarté, car j'ai pour la menuiserie, electricité etc)
Mais pour faire le teste, dans mon userform, j'ai crée 4 textbox sans les renommés, textbox1 textbox2 etc. Donc j'ai recopié vos informations de code et dans le code de module j'ai fait une modif juste pour l'essai

Public WithEvents tb As MSForms.TextBox

Private Sub tb_Change()
msgbox(" ESSAI DE FONCTIONNEMENT ") ' bien sur pour l'essai
    ' Votre logique de validation ici.
    ' Utilisez tb pour accéder aux propriétés du TextBox qui a déclenché l'événement.
End Sub

Juste un truc que je ne comprend pas, pourquoi quand je modifie dans les 3 premiers textbox crée, cela fonctionne pas, mais si je modifie le 4eme sa fonctionne ???
et peut importe l'ordre c'est toujours le 4eme ? et pour info (J'ai essayé en rajoutant 2 autres et c'est le dernier qui est pris en compte).

Et m'as question est faut il que je renomme mais textbox MENUIV et textbox1 2 3 etc. et autre question je peux faire un call validation par exemple dans le module class, sachant que validation et coder dans mon userform ? Pour le call j'ai trouvé call userform.validation (par exemple)

Lorsque vous utilisez la syntaxe Dim ctb As New clsTextBox, le nouvel objet est créé immédiatement. Cependant, si vous le faites dans une boucle, le nouvel objet écrase l'objet précédent à chaque itération, c'est pourquoi seul le dernier TextBox semble déclencher l'événement.

Pour éviter cela, vous pouvez créer un nouvel objet de manière distincte en utilisant Set,

Private Sub UserForm_Initialize()
    Set textBoxes = New Collection
    Dim ctl As Control
    For Each ctl In Me.Controls
        If TypeOf ctl Is MSForms.TextBox Then
            Dim ctb As clsTextBox
            Set ctb = New clsTextBox
            Set ctb.tb = ctl
            textBoxes.Add ctb
        End If
    Next ctl
End Sub

Avec cette modification, chaque TextBox devrait maintenant déclencher l'événement Change() dans la classe clsTextBox.

Concernant la question de renommer vos TextBox, cela dépend de votre préférence. Si vous souhaitez que votre code soit plus clair et plus explicite, vous pouvez les renommer comme MENUIV1, MENUIV2, etc. Cependant, cela n'a pas d'impact sur la logique de votre programme tant que vous pouvez identifier chaque TextBox univoquement. Vous pouvez utiliser le nom d'origine TextBox1, TextBox2, etc. tant que vous pouvez les distinguer et comprendre leur fonction dans votre programme.

Parfait un grand merci.

Juste comme mon userform a plusieurs page, je vais voir pour faire une condition en fonction de la page. Car pour chaque page la validation est différentes

Une approche pourrait être d'ajouter une condition dans votre méthode tb_Change() pour vérifier la page actuelle et d'appliquer la logique de validation correspondante.

Puisque vous avez mentionné que vous utilisez plusieurs pages, j'imagine que vous utilisez un contrôle MultiPage. Si c'est le cas, vous pouvez vérifier la page actuellement sélectionnée en utilisant MultiPage.Value. Par exemple, vous pouvez ajouter quelque chose comme ceci dans votre classe clsTextBox

Private Sub tb_Change()
    Select Case MultiPage.Value
        Case 0
            ' Logique de validation pour la première page
        Case 1
            ' Logique de validation pour la deuxième page
        ' etc.
    End Select
End Sub

Notez que MultiPage.Value donne l'index de la page actuellement sélectionnée, en commençant par 0.

Cependant, veuillez noter que dans ce code, MultiPage doit être remplacé par le nom réel de votre contrôle MultiPage. Vous aurez également besoin de déterminer comment accéder à ce contrôle depuis la classe - une option pourrait être de le passer en tant que paramètre à la classe. J'espère que cela vous aidera ! ^^

j'était entrain de voir avec un if ...

Mais votre code et plus simple a gerér. Donc j'ai bien MultiPage1 de la page 0 a 5

Donc j'ai fait ceci, en modifiant multipage par multipage1

Private Sub tb_Change()
    Select Case MultiPage1.Value
        Case 0
Msgbox(" Page 0")
            ' Logique de validation pour la première page
        Case 1
Msgbox(" Page 1")
            ' Logique de validation pour la deuxième page
        ' etc.
    End Select
End Sub

Mais j'ai erreur exécution 424, objet requis ??
sur la premier ligne select case .............

L'objet MultiPage1 est un contrôle dans votre UserForm, mais la classe clsTextBox ne le voit pas directement car elle est dans un autre espace de noms. Vous pouvez résoudre ce problème en passant une référence à votre UserForm à la classe.

Ajoutez une nouvelle variable dans la classe clsTextBox pour contenir une référence à votre UserForm

Public WithEvents tb As MSForms.TextBox
Public myForm As UserForm

Quand vous créez de nouvelles instances de clsTextBox dans votre UserForm, définissez également myForm

Private Sub UserForm_Initialize()
    Set textBoxes = New Collection
    Dim ctl As Control
    For Each ctl In Me.Controls
        If TypeOf ctl Is MSForms.TextBox Then
            Dim ctb As clsTextBox
            Set ctb = New clsTextBox
            Set ctb.tb = ctl
            Set ctb.myForm = Me
            textBoxes.Add ctb
        End If
    Next ctl
End Sub

Maintenant, vous pouvez accéder à MultiPage1 dans votre classe en utilisant myForm.MultiPage1

Private Sub tb_Change()
    Select Case myForm.MultiPage1.Value
        Case 0
            MsgBox ("Page 0")
            ' Logique de validation pour la première page
        Case 1
            MsgBox ("Page 1")
            ' Logique de validation pour la deuxième page
        ' etc.
    End Select
End Sub

Chaque instance de clsTextBox aura une référence à votre UserForm, et vous pourrez accéder à tous les contrôles de l'UserForm depuis la classe clsTextBox. J'espère que cela vous aidera !

Que dire a part PARFAIS

Vraiment merci, de votre temps, et surtout j'ai pu apprendre de nouvelle info.

Pas de souci

Rechercher des sujets similaires à "vba textbox simplification code"