Créer macro annuler action

Bonjour,

Encore moi. J'aimerais soliciter à qui peut m'aider. Est ce possible de créer un macro qui annule une action. Par exemple je fais une écriture dans ma ligne, au lieu de suprimer je fais annuler.

Merci d'avance à vous!
Mes respects
Bonisam

21 réponses

Résumé de la discussion

La problématique porte sur la création d'une macro Excel capable d'annuler une saisie sans la supprimer, en s'appuyant sur une détection via l’événement Worksheet_Change et des vérifications de date. Plusieurs solutions proposent de valider le contenu selon le nom de la feuille et l'année, et d'afficher un message d'erreur tout en effaçant l'entrée non valide. Certaines variantes adaptent le code pour tenir compte des années N et N+1, voire pour gérer des mois spécifiques et éviter les erreurs lorsque l'année affichée diffère. D'autres approches indiquent où placer le code (feuilles distinctes ou feuille d'accueil) et proposent des variantes compatibles avec des versions anciennes d'Excel, comme 97-2003.

Bobot (l’IA à votre service)
  1. Modérateur
    Bonjour,
    La moindre des choses serait de dire un p'tit coucou ou un merci lorsque quelqu'un t'apporte une solution. Non?
    2
    1. Bonjour Pijaku,
      Je reviens à vous pour votre message tel :Si tu veux empêcher systématiquement toute saisie de date dont le mois serait différent du nom de l'onglet : 
      
      Private Sub Worksheet_Change(ByVal Target As Range)
      If Target.Column <> 1 Or Target.Value = "" Then Exit Sub
      If UCase(Format(CDate(Target.Value), "mmmm")) <> UCase(ActiveSheet.Name) Then
          MsgBox "Date non valide"
          With Target
              .ClearContents
              .Select
          End With
      End If
      End Sub


      Je veux empêchement seulement les saisies dont le mois est postérieur au mois de l'onglet.
      Est ce un diminutif de votre procedure marche? ou que dois-je faire?

      Merci pour tout
      Mes respects
      Bonisam
      0
      1. Modérateur
        Salut,
        Non ça n'est pas un "diminutif de ma procédure".
        C'est juste le troisième code différent que je fais pour vous sur ce sujet.
        Il aurait mieux valut être clair dès le départ....
        Tu voulais : j'aimerais que tout mois différent du mois de l'année choisie soit systématiquement bloqué. C'est ce que fait ce code.
        A toi de trouver la bonne condition...
        0
    2. Bonjour Mistral 13200,

      A l'execution de la macroefface donné j'ai une erreur 1004 donc je ne comprend plus rien.
      Voyez plustot à l'image suivantes:https://www.cjoint.com/?AHmksVeQtLW

      Merci pour tout
      Mes respects
      Bonisam
      0
      1. Bonjour à vous deux,

        Et de plus il y a deux fichiers différents!!!
        Un sans aucune macro...
        L'autre verrouillé...

        Cordialement
        Mistral
        0
        1. Bonjour,

          Vraiment je m'excuse mais j'ai toujours des difficultés. J'ai crée un bouton d'execution de la macro effacedonnées. Mon problème est quand je lance l'execution de la macro elle m'affiche un message "d'erreur d'execution "1004" (Impossible de modifier une cellule fusionnée). Pourtant mes cellules fusionnées sont"A8:B8 " qui ne sont pas incluse dans ma plage. Et puis quand je part voir dans mes feuilles "mois" les données sont effacer mais ça efface aussi la cellule "A9" et "B9" pourtant ma plage est : "A10:G". Donc je ne comprend vraiment pas.

          Voici mon fichier:http://cjoint.com/?AHks3pQfBQa
          Je vous prie de m'aider encore.
          Merci pour tout
          Mes respects
          Bonisam
          0
          1. http://cjoint.com/?AHks3pQfBQa
            0
          2. http://cjoint.com/?AHks3pQfBQa
            0
          3. Modérateur
            Salut,
            Comment tu veux que je regarde ton fichier, tu l'as protégé de partout par mot de passe..........
            0
        2. Pijaku :
          C'est exactement ce que j'ai fait et tu as raison faire +1 au lieu de +365 est plus intelligent. Merci à toi.

          Bonisam:
          J'ai testé les macros fournies par pikasu et ça fonctionne parfaitement chez moi.
          La permière celle qui contrôle la validité de la date doit être sur une Woorkshett de chaque feuille Mois.
          La seconde pour éffacer se trouve dans un module indépendant et tu dois la lancer manuellement ou à l'aide d'un bouton auquel tu attaches la macro.

          Cordialement
          Mistral
          0
          1. Bonjour,

            Je voulais dire vous demander spécialement de m'envoyé un modèle.
            Dites moi, il faut excuter ou bien automatiquement ça marche?
            Parce que j'ai crée un module standard mais même quand je change d'année les donnée restent.

            je vous renvoie mon fichier:en fait dans la feuille "Acceuil" il y'a une liste déroulante des années. donc je voudrait quand passant à l'année suivante(2012) les donné de l'année antérieur (2011) s'efface. et quand je reviens dans l'antérieur (2011) après je puisse quand même revoir mes donées et vis versa. Ci-joint mon fichier :http://cjoint.com/?AHkoXivjrmm

            Je suis désolé de trop vous embêter pour ça mais comprenez moi.
            Merci pour tout
            Mes respects
            Bonisam
            0
            1. Mon fichie :http://cjoint.com/?AHko3erhtSK
              0
            2. Modérateur
              donc je voudrait quand passant à l'année suivante(2012) les donné de l'année antérieur (2011) s'efface. et quand je reviens dans l'antérieur (2011) après je puisse quand même revoir mes donées et vis versa Je vous réponds de suite, sans regarder votre tableau : impossible sans avoir une base de données stockant toutes les informations.....
              Vous devriez : enregistrer votre classeur, chaque année, sous NomDuClasseur + année, et réinitialiser votre classeur manuellement en lançant la macro ci dessus référencée par ALT+F8...
              0
          2. Pijaku je viens de prendre connaissance de ton dernier message et j'ai fait des essais en aynat modifié la ligne :

            If UCase(Format(CDate(Target.Value), "mmmm")) <> UCase(ActiveSheet.Name) Or Year(Date + 365) <> Year(CDate(Target.Value)) Then

            Dans la Woorksheet des trois premiers mois et ça fonctionne, reste à regler le problème des années bisextilles dont 2012 fait partie.

            Cordialement
            Mistral
            0
            1. Modérateur
              Ce code est entré dans le code de la feuille. Il ne fonctionne par conséquent que dans la feuille concernée. Il suffit donc de faire le bon test dans la feuille janvier.
              Donc dans les feuilles janv fév et mars remplace :
              Year(Date) ou ton fameux Year(Date + 365)
              par :
              Year(Date) + 1
              0
          3. Bonjour,

            je vais faire une requette spéciale à vous de m'envoyé un modèle je vais voir sinon je me bat dans tous les sens en vain.

            Donc si vous pouvez m'envoyer un modèle cela va beaucoup m'aider.
            Merci pour tout
            Mes respects
            Bonisam
            0
            1. Modérateur
              Là j'ai pas compris : je vais faire une requette spéciale ???????????
              Sinon votre fichier est ici...
              0
          4. Bonjour;

            Je voulais juste une précision: où mettre le code? dans chaque feuille où dans la feuille accueil?
            En plus est ce que si une cellule contient une formule, on peut effacé le résultat et conserver la formule?

            Sinon j'ai testé votre dernière reponse mais à moins que j'ai fait une erreur, ça marche pas.

            Merci pour tout
            Mes respects
            Bonisam
            0
            1. Modérateur
              Sub EffaceDonnees() se place dans un module standard (sous visual basic : Insertion/Module).
              si une cellule contient une formule, on peut effacé le résultat et conserver la formule? Alors, logiquement une cellule qui contient une formule (à part certaines comme =AUJOURDHUI()) fait référence à une (au moins) autre cellule qui elle contient une valeur. Si vous supprimez le contenu de toutes les cellules qui contiennent une valeur, les cellules contenant des formules vont :
              - perdre leur valeur,
              - conserver leurs formules.
              Sinon j'ai testé votre dernière reponse mais à moins que j'ai fait une erreur, ça marche pas Moi aussi, j'ai testé, et ça fonctionne... Peut être une erreur de votre part. de toutes façons, le code ne peux fonctionner que depuis un mdule standard...
              A vous...
              0
          5. Celle ci-dessous

            Private Sub Worksheet_Change(ByVal Target As Range)
            If Target.Column <> 1 Or Target.Value = "" Then Exit Sub
            If UCase(Format(CDate(Target.Value), "mmmm")) <> UCase(ActiveSheet.Name) Or Year(Date) <> Year(CDate(Target.Value)) Then
                MsgBox "Date non valide"
                With Target
                    .ClearContents
                    .Select
                End With
            End If
            End Sub


            Qui permet de tester la cohérence de la date saisie sur la bonne feuille et que le millesime de l'année est correcte.
            Cordialement
            Mistral
            0
            1. Modérateur
              Le problème se pose, pour toi, pour les feuilles janvier, février et mars qui sont donc en année N+1. Si tu les utilises avant 2012 par exemple, le test : Year(Date) <> Year(CDate(Target.Value)) ne renverra pas d'erreur de saisie.
              Il faut donc biaiser. Si tu as, par exemple en D12 l'année écrite ex : 2012 en N+1 2011 en N tu peux utiliser ce code (à adapter Range("D12")) :
              Private Sub Worksheet_Change(ByVal Target As Range) 
              If Target.Column <> 1 Or Target.Value = "" Then Exit Sub 
              If UCase(Format(CDate(Target.Value), "mmmm")) <> UCase(ActiveSheet.Name) Or Range("D12") <> Year(CDate(Target.Value)) Then 
                  MsgBox "Date non valide" 
                  With Target 
                      .ClearContents 
                      .Select 
                  End With 
              End If 
              End Sub
              0
          6. Bonjour à vous deux,

            Tout d'abord toutes mes excuses de m'immiscer dans votre échange mais je le suis depuis le début car cela m'interesse.
            J'ai testé la solution de de Pijaku et elle me conviendrait parfaitement mais à condition que ce contrôle puisse se faire sur douze mois mais à cheval sur deux années, d'Avril à Mars par exemple.
            Cordialement
            Mistral
            0
            1. Modérateur
              Salut,
              Bienvenue!
              testé la solution de de Pijaku laquelle? Il y a eu plusieurs questions sur ce sujet...
              0
          7. waoooo! c'est génial. ça marche 5/5. Vous êtes vraiment un génie de la chose.
            mille merci, vous m'avez vraiment sauve et je ne sais comment vous remercier.

            Néanmoins j'ai juste une question: dans mes bricolage je suis arrivé à faire un petit logociel mais un problème perdure.c'est notamment le problème de changement d'année. Est ce possible avec une macro une fois qu'on va à l'année suivante, la base soit remise à zero bien avec une possibilité de retour.
            Je prend un exemple: nous somme en 2011 et une fois qu'on passe à 2012, la base soit remise à vide.

            Merci pour tout votre sacrifice
            Mes respects
            Bonisam
            0
            1. Modérateur
              Pour faire ceci, tu veux supprimer les données contenues dans chaque feuille "mois" de A10 à H dernière ligne, par macro?
              0
            2. Modérateur
              Ce code boucle sur toutes les feuilles de ton classeur.
              Si la feuille ne s'appelle ni "acceuil", ni "Recapitulatif", elle boucle sur toutes les cellules de A10 à H dernière ligne
              Si la cellule ne contient pas de formule, son contenu est effacé.
              Tu dis...
              Sub EffaceDonnees()
              Dim DerLig As Long
              Dim Wsh As Worksheet
              Dim Plage As Range, Cel As Range
              
              For Each Wsh In ThisWorkbook.Worksheets
                  If Wsh.Name <> "Acceuil" And Wsh.Name <> "Recapitulatif" Then
                      With Wsh
                          DerLig = .Columns(1).Find("*", , , , xlByColumns, xlPrevious).Row
                          Set Plage = .Range("A10:H" & DerLig)
                          For Each Cel In Plage
                              If Left(Cel.Formula, 1) <> "=" Then
                                  Cel.ClearContents
                              End If
                          Next
                      End With
                  End If
              Next
              Set Plage = Nothing
              End Sub
              0
          8. oui j'ai testé. Ca mache pour l'année choisie. Par exemple pour l'année 2011 dans la feuille de janvier: si on saisie 01/02/2011 ça bloque (ça c'est bien). mais si on saisie par exemple 01/01/2010 ou 01/01/2012, ça passe.(ça c'est pas bon). j'aimerais que tout mois différent du mois de l'année choisie soit systématiquement bloqué.

            Merci pour tout
            Mes respects
            Bonisam
            0
            1. Modérateur
              Alors code à copier dans chacune de tes feuilles:
              Private Sub Worksheet_Change(ByVal Target As Range)
              If Target.Column <> 1 Or Target.Value = "" Then Exit Sub
              If UCase(Format(CDate(Target.Value), "mmmm")) <> UCase(ActiveSheet.Name) Or Year(Date) <> Year(CDate(Target.Value)) Then
                  MsgBox "Date non valide"
                  With Target
                      .ClearContents
                      .Select
                  End With
              End If
              End Sub
              0
          9. Bonjour pijaku

            Tu avais pourtant dit : Mais si l'année est antérieur à 2011, ça doit passer Ben dans mon code ça passe. En fait je m'excuse c'est une erreur de langage. J'aimerais en fin que tout mois différent du mois de l'année choisie qu'il soit antérieur ou postérieur soit systématiquement réjété.
            Touvez-ci joint une version 97-2003: https://www.cjoint.com/?AHkku0FSgGW

            Merci pour votre aide.
            Mes respects
            Bonisam
            0
            1. Modérateur
              Juste comme ça, as tu testé le code donné dans ma dernière réponse???
              0
          10. Bonjour,

            D'abord je m'excuse, c'était l'heure de la pause ce nous.
            Sinon la procédure marche mais unique pour l'anné 2011. Dans mon cas l'année peut varier et je voulais qu'en fonction de l'année choisie le code tient compte de ça. touvez-ci joint un cas pratique de ce que je veux faire:
            https://www.cjoint.com/?AHjsgoTvJkr

            Merci pour tout
            Mes respects
            Bonisam
            0
            1. Modérateur
              Bonjour,
              Je ne disposes pas d'Excel 2007 et donc ne peux pas ouvrir ton fichier joint. Pour me le passer, merci de l'enregistrer sous format 97-2003.
              Tu avais pourtant dit : Mais si l'année est antérieur à 2011, ça doit passer Ben dans mon code ça passe...
              Si tu veux empêcher systématiquement toute saisie de date dont le mois serait différent du nom de l'onglet :
              Private Sub Worksheet_Change(ByVal Target As Range)
              If Target.Column <> 1 Or Target.Value = "" Then Exit Sub
              If UCase(Format(CDate(Target.Value), "mmmm")) <> UCase(ActiveSheet.Name) Then
                  MsgBox "Date non valide"
                  With Target
                      .ClearContents
                      .Select
                  End With
              End If
              End Sub
              0
          11. Dans une colonne bien précise "colonne A"

            Mes respects
            Bonisam
            0
            1. Modérateur
              Code à coller dans chaque code de feuille :
              Clic droit sur chaque onglet/Visualiser le code
              copier / coller ceci :
              Private Sub Worksheet_Change(ByVal Target As Range)
              If Target.Column <> 1 Or Target.Value = "" Then Exit Sub
              If UCase(Format(CDate(Target.Value), "mmmm")) <> UCase(ActiveSheet.Name) And Year(Target.Value) = Year(Date) Then
                  MsgBox "Date non valide"
                  With Target
                      .ClearContents
                      .Select
                  End With
              End If
              End Sub

              Testes et dis nous...
              0
          12. ok, merci c'est super.
            Je pense que c'est bon pour ça.
            Par contre j'ai un autre problème.
            J'aimerais réaliser une macro de vérification d'erreur.
            En fait j'ai crée 12 feuilles de saisie répresentant les mois de janvier à decembre. donc j'aimerais avoir une macro qui empêche la validation de la date en affichant un message d'erreur de type "date incorrecte" si un utilisateur saisie par exemple 01/02/2011 dans la feuille de janvier. Mais si l'année est antérieur à 2011, ça doit passer.
            Merci pour votre aide
            Mes respects
            Bonisam
            0
            1. Modérateur
              Les dates sont saisies n'importe ou dans la feuille ou dans une colonne bien précise???
              0
          13. pour cette procedure ça devient en fait faire un double travail.
            Mais vraiment vous m'avez eclairer et je comprend mieux. donc en fin je vais préférer laisser tombé ça pour garder la commande standard d'annulation.
            Encore merci pour la prompte réaction surtout votre sens de compréhension.
            Mes respects
            Bonisam
            0
            1. Modérateur
              Après tout dépends de ce que vous souhaitez faire...
              L'annulation d'une procédure peut être remplacée par l'empêchement de réaliser cette procédure si...
              Vous dites.
              0
          14. Modérateur
            Pas de souci, pour tout te dire ça m'a surpris, tes posts étant tous empreints d'une telle politesse. Oublions!

            Répondons plutôt à ta question.

            Il est impossible, par la commande Excel Editions/Annuler, d'annuler la tâche accomplie par une macro. Ca tu le savais déjà.

            Pour "annuler" ce qu'a réalisé un code VBA, il faut écrire le code inverse...

            Exemple :
            Sub EcrisTestEnA1()
            Range("A1") = "Test"
            End Sub

            Sub AnnuleCeQueJaiEcrisEnA1()
            If Range("A1") = "Test" Then
                Range("A1") = ""
            End If
            End Sub
            0
            • 1
            • 2