• 10 heures
  • Facile

Ce cours est visible gratuitement en ligne.

Ce cours existe en livre papier.

Vous pouvez être accompagné et mentoré par un professeur particulier par visioconférence sur ce cours.

J'ai tout compris !

Mis à jour le 29/10/2019

Macros et VBA

Connectez-vous ou inscrivez-vous gratuitement pour bénéficier de toutes les fonctionnalités de ce cours !

Nous voici presque arrivés à la fin de ce tutoriel ; désormais, vous devriez maitriser Word. Pourtant, il vous reste encore des choses à apprendre. Ce que nous allons voir dans ce chapitre, vous n'en aurez pas l'utilité tous les jours mais cela pourra vous faire gagner du temps lors de votre utilisation de Word.

Vous effectuez fréquemment les mêmes tâches de mise en forme ou de mise en page ? Vous avez l'impression que certaines mises en forme vous prennent beaucoup de temps et d'énergie ? Les macros et le langage VBA sont faits pour vous. Poursuivez vite la lecture et découvrez un univers fascinant qui n'a de limites… que votre propre imagination !

Gagner du temps avec les macros

Arrivés à ce stade du tutoriel, je pense pouvoir affirmer que vous avez une bonne expérience dans la pratique de Word et que vous pouvez réaliser à peu près tous les types de documents possibles et imaginables. Cependant, après avoir rédigé un document, vous passez beaucoup de temps à le mettre en forme et vous apprécieriez l'aide d'un assistant spécialisé dans ce domaine. Cet assistant a un nom : il s'agit de l'enregistreur de macros. Montrez à Word comment réaliser une mise en forme, aussi sophistiquée soit-elle, et il sera capable de la reproduire !

Des macros, des macros ! Je ne sais pas exactement ce qu'est une macro, moi ! Est-ce que ce chapitre est vraiment fait pour moi ?

Je vais immédiatement mettre un terme aux bruits de couloirs selon lesquels les macros sont à réserver à un public averti, qui a une grande expérience de Word et connaît déjà (au moins !) trois ou quatre langages de programmation. Tout ceci est absolument faux ! Si vous savez utiliser Word, vous saurez sans peine créer et mettre en œuvre des macros.

Nous allons commencer par un exemple simple, qui n'a d'autre intérêt que de vous familiariser avec l'enregistreur de macros. La macro en question va mettre en gras le texte sélectionné.

Mais il y a l'icôneGrasdu Ruban pour cela. Pourquoi créer une macro ?

C'est vrai, c'est vrai ! Alors, corsons un peu les choses. Que diriez-vous de créer une macro qui applique simultanément les attributsGras,ItaliqueetSoulignéau texte sélectionné ? Il n'existe aucune icône du Ruban capable de cette prouesse et la macro correspondante est très simple à mettre en place. Alors, au diable l'avarice !

L'enregistreur de macros est disponible dans l'ongletDéveloppeurdu Ruban. Si cet onglet n'est pas encore affiché, basculez sur l'ongletFichieret cliquez surOptions. Dans la boîte de dialogueOptions Word, cliquez surPersonnaliser le Ruban, cochez la caseDéveloppeurpuis validez en cliquant surOK. L'icône de l'enregistreur de macros se trouve dans le groupeCode, comme indiqué à la figure suivante.

Accès à l'enregistreur de macros
Accès à l'enregistreur de macros

Dès son lancement, l'enregistreur de macros mémorise toutes les actions effectuées au clavier et à la souris. Si vous voulez appliquer les attributsGras,ItaliqueetSoulignéà du texte, il faut donc le sélectionner avant de lancer l'enregistrement de la macro, sans quoi cette action est également mémorisée et reproduite à chaque exécution de la macro.

Avant d'aller plus loin, je vous invite à télécharger le documentmacros.docxafin que vous puissiez manipuler tout en suivant mes explications :

Télécharger le document

Ouvrez le documentmacros.docxet sélectionnez le premier paragraphe (1). Maintenant, vous pouvez lancer l'enregistreur de macros : cliquez sur l'icôneEnregistrer une macro(2). Donnez le nomGras_Italique_Soulignéà la macro (3) et validez en cliquant surOK(4), comme indiqué à la figure suivante.

Lancement de l'enregistreur de macros
Lancement de l'enregistreur de macros

Dès le clic sur le boutonOK, le pointeur change de forme pour montrer que l'enregistreur est actif : à partir de maintenant, tout ce que vous ferez avec la souris et le clavier sera mémorisé.

Basculez sur l'ongletAccueildu Ruban puis cliquez successivement sur les icônesGras,ItaliqueetSoulignédu groupePolice.
Basculez sur l'ongletDéveloppeuret cliquez sur l'icôneArrêter l'enregistrement(en lieu et place de l'icôneEnregistrer une macro). Ça y est, vous venez de créer votre première macro !

Je suis sûr que vous brûlez d'impatience de l'utiliser. Sélectionnez le deuxième paragraphe qui, lui n'est pas encore en gras, italique et souligné. Si nécessaire, basculez sur l'ongletDéveloppeurdu Ruban et cliquez sur l'icôneMacrosdu groupeCode.
La boîte de dialogueMacrosdresse la liste des macros enregistrées sur votre ordinateur. Cliquez sur la macroGras_Italique_Soulignépuis sur le boutonExécuter(voir figure suivante).

La macro Gras_Italique_Souligné est sur le point d'être exécutée
La macro Gras_Italique_Souligné est sur le point d'être exécutée

Hourra ! Le deuxième paragraphe est maintenant en gras, italique et souligné. Vous voyez, ce n'est vraiment pas difficile.

Toutes les macros seront basées sur le même principe et ce, indépendamment de leur complexité. Pour vous en persuader, vous allez maintenant définir une macro qui agit sur un tableau. La figure suivante représente l'effet recherché.

Transformation d'un tableau avec une macro
Transformation d'un tableau avec une macro

Je vous sens légèrement nerveux ! N'ayez crainte, tout va bien se passer…
Les plus observateurs d'entre vous auront identifié les transformations appliquées au texte.

Sélectionnez les données à convertir en tableau. Basculez sur l'ongletDéveloppeurdu Ruban puis cliquez sur l'icôneEnregistrer une macrodans le groupeCode.
Donnez à la macro le nomTableaupuis cliquez surOK.

La première étape consiste à convertir le texte en tableau. Rien de plus simple ! Basculez sur l'ongletInsertiondu Ruban, cliquez sur l'icôneTableaudans le groupeTableauxet choisissezConvertir le texte en tableau. Cette action ouvre la boîte de dialogueConvertir le texte en tableau. Cliquez surOKpour accepter les options par défaut.

La deuxième étape applique un style au tableau. L'ongletCréationest automatiquement sélectionné dans le Ruban. Dans le groupeStyles de tableau, cliquez sur l'icôneStyles de tableauet choisissezTrame moyenne 1 – Accent 4(ou celui que vous voulez, je vous ai donné ici celui que j'ai utilisé dans cet exemple).

La troisième et dernière étape centre les données dans les cellules. Basculez sur l'ongletDispositionpuis cliquez sur l'icôneCentrerdans le groupeAlignement.
Vous pouvez arrêter l'enregistrement de la macro. Basculez sur l'ongletDéveloppeuret cliquez sur l'icôneArrêter l'enregistrementdans le groupeCode. La macro est maintenant fonctionnelle.

Désormais, lorsque vous voudrez convertir du texte en tableau, sélectionnez le texte, basculez sur l'ongletDéveloppeurdans le Ruban et cliquez sur l'icôneMacrosdu groupeCode. La boîte de dialogueMacrosdresse la liste des macros enregistrées sur votre ordinateur. Cliquez sur la macroTableaupuis sur le boutonExécuter. En à peine quelques clics, vous pouvez convertir facilement du texte en tableau et le résultat aura toujours la même mise en page !

Faciliter l'exécution des macros

Les macros sont faites pour vous faciliter la vie et pour vous faire gagner du temps sur les actions répétitives. Mais il faut bien avouer que leur exécution depuis l'ongletDéveloppeurn'est pas des plus rapides (clic sur l'icôneMacrosdans le groupeCode, sélection de la macro dans la boîte de dialogueMacros, puis clic sur le boutonExécuter). Que diriez-vous de leur affecter un raccourci clavier ou, pourquoi pas, une icône dans la barre d'outilsAccès rapide?

Un raccourci clavier

Pour affecter un raccourci clavier à une macro, basculez sur l'ongletFichierdu Ruban puis cliquez surOptions. Dans la boîte de dialogueOptions Word, sélectionnez l'ongletPersonnaliser le Rubanpuis cliquez sur le boutonPersonnaliserà droite du libelléRaccourcis clavier. Une nouvelle boîte de dialogue intituléePersonnaliser le claviers'ouvre. SélectionnezMacrosdans la zone de listeCatégories(1), cliquez sur la macro à laquelle vous voulez affecter un raccourci clavier (2), cliquez dans le champNouvelle touche de raccourciet tapez un raccourci en vous assurant que l'information[non attribuée]apparaît à la suite du libelléAffectées à(3). Cliquez successivement surAttribuer,FermerpuisOKpour enregistrer le raccourci clavier (voir figure suivante).

Les différentes étapes pour affecter un raccourci clavier à une macro
Les différentes étapes pour affecter un raccourci clavier à une macro

Vous pouvez désormais appuyer sur Alt + Z (c'est le raccourci que j'ai choisi) pour transformer des données sélectionnées en tableau mis en forme. Avouez que c'est bien plus agréable.

Une icône dans la barre d'outilsAccès rapide

Vous préférez utiliser la barre d'outilsAccès rapide? Pas de problème ! Il vous suffit de cliquer sur l'icônePersonnaliser la barre d'outils Accès rapideet de sélectionnerAutres commandesdans le menu. Cette action ouvre la boîte de dialogueOptions Wordavec l'ongletBarre d'outils Accès rapidesélectionné. ChoisissezMacrosdans la première liste déroulante (1). Les macros qui ont été définies sur l'ordinateur apparaissent dans la première zone de liste. Sélectionnez l'une d'entre elles et cliquez surAjouter(2). Cliquez enfin surOKpour ajouter la macro à la barre d'outilsAccès rapide, comme indiqué à la figure suivante.

Ajouter une macro dans la barre d'outils Accès rapide
Ajouter une macro dans la barre d'outils Accès rapide

J'ai ajouté deux macros dans la barre d'outilsAccès rapideet il m'est impossible de les différencier parce qu'elles utilisent toutes les deux la même icône. Y-a-t-il quelque chose à faire ?

Bien sûr ! Cliquez sur l'icônePersonnaliser la barre d'outils Accès rapideet sélectionnezAutres commandesdans le menu. Cliquez sur l'icône à modifier dans la deuxième zone de liste, puis cliquez surModifier. Vous pouvez maintenant choisir une icône parmi celles proposées (voir figure suivante).

Choix de l'icône d'une macro dans la barre d'outils Accès rapide
Choix de l'icône d'une macro dans la barre d'outils Accès rapide

Exécution automatique de macros

Il existe des noms « réservés » pour les macros, qui permettent notamment de les exécuter automatiquement.

Nom de la macro

Exécution automatique

AutoExec

Au lancement de Word

AutoNew

À la création d'un nouveau document

AutoOpen

À l'ouverture d'un document existant

AutoClose

À la fermeture d'un document

AutoExit

À la fermeture de Word

Supposons par exemple que vous vouliez ouvrir automatiquement le documentTous mes fichiers.docxdès le lancement de Word. Pour cela, vous allez définir la macroAutoExec.

Lancez Word et fermez la page vide ouverte par défaut. Basculez ensuite sur l'ongletDéveloppeurdu Ruban, puis cliquez sur l'icôneEnregistrer une macrodans le groupeCode. Baptisez cette macroAutoExecet validez en cliquant surOK. Basculez sur l'ongletFichierdu Ruban, cliquez surOuvrir, désignez le documentTous mes fichiers.docxet validez en cliquant surOuvrir.
Pour terminer, basculez sur l'ongletDéveloppeurdu Ruban et cliquez surArrêter l'enregistrement.

Pour vous assurer que la macro fonctionne, fermez Word puis rouvrez-le. Le documentTous mes fichiers.docxdoit s'ouvrir automatiquement.

Une erreur d'exécution
Une erreur d'exécution

J'ai le message d'erreur 5174 (« Fichier introuvable ») de la figure suivante. J'ai bien désigné le fichier à ouvrir et le message pointe sur un autre fichier. Word aurait-il perdu la tête ?

Le fichier spécifié est introuvable
Le fichier spécifié est introuvable

Ce problème se produit si vous avez désigné un fichier dans le dossier proposé par défaut par Word. Si le fichier à ouvrir se trouve dans le dossier par défaut, changez de dossier pendant l'enregistrement de la macro puis revenez-y et tout se passera bien.

Quand les macros montrent leurs limites

Nous allons définir (ou plutôt tenter de définir) une macro qui remplace tous les stylesTitre 2d'un document par le styleTitre 3.

Une fois le document ouvert, voici la marche à suivre :

  1. Basculez sur l'ongletDéveloppeurdu Ruban et cliquez sur l'icôneEnregistrer une macro.

  2. Donnez à la macro le nomTitre2_vers_Titre3et validez en cliquant surOK.

  3. Basculez sur l'ongletAccueildu Ruban, puis cliquez surRemplacerdans le groupeModification. La boîte de dialogueRechercher et remplacers'ouvre avec l'ongletRemplacersélectionné.

  4. Cliquez surPluspour la déployer.

  5. Cliquez dans le champRechercherpour y afficher le point d'insertion. Cliquez surFormatpuis surStyle. Sélectionnez le styleTitre 2et validez en cliquant surOK.

  6. Cliquez dans le champRemplacer parpour y afficher le point d'insertion. Cliquez surFormatpuis surStyle. Sélectionnez le styleTitre 3et validez en cliquant surOK. Si vous avez suivi mes consignes à la lettre, la boîte de dialogueRechercher et remplacerdevrait maintenant ressembler à la figure suivante.

  7. Cliquez surRemplacer tout, surOK, puis fermez la boîte de dialogueRechercher et remplaceren cliquant sur sa case de fermeture.

  8. Basculez sur l'ongletDéveloppeuret cliquez sur l'icôneArrêter l'enregistrement.

La boîte de dialogue Rechercher et remplacer est entièrement paramétrée
La boîte de dialogue Rechercher et remplacer est entièrement paramétrée

Pour vérifier le bon fonctionnement de la macro, fermez le document sans enregistrer les modifications, rouvrez-le et exécutez la macroTitre2_vers_Titre3.

Tout fonctionne à la perfection. Cet exemple ne montre pas du tout les limites des macros ! Est-ce que j'aurais mal compris ?

Je sais, je sais, tout va bien… pour le moment ! Mais nous allons corser les choses. Supposons que vous ne vouliez transformer que les trois premiers stylesTitre 2enTitre 3. Reprenez les huit étapes précédentes mais, à l'étape 7, ne cliquez pas surRemplacer tout: cliquez à quatre reprises surRemplacer. Je dis bien à quatre reprises et non à trois. La première va permettre à Word de trouver le premier paragraphe enTitre 2, les trois autres à remplacer les trois premiersTitre 2enTitre 3.

Plutôt facile n'est-ce pas ? Mais imaginez maintenant que vous ayez à faire à un très long document et que vous vouliez remplacer non pas les trois premiersTitre 2, mais les 325 premiers ! C'est sûr, il s'agit d'un très long document… Pensez-vous qu'il soit vraiment raisonnable de cliquer 326 fois sur le boutonRemplacer?

Cet exemple montre les limites des macros. Il est donc temps de passer au VBA pour aller un peu plus loin !

Encore plus loin avec VBA

Je vous sens tressaillir. Et pourtant, il n'y a pas de quoi. En effet, il ne vous faudra que quelques bribes d'anglais pour comprendre la programmation VBA. Même si vous n'êtiez pas très assidus en cours, je suis là pour vous aider.

VBA Signifie Visual Basic for Applications. C'est un langage de programmation intégré à Word qui nous permet de créer manuellement des macros. C'est un peu plus complexe que l'outil que nous venons de voir mais les possibilités qu'offre VBA sont aussi bien plus étendues !

Premiers pas avec le langage VBA

Sans le savoir, vous avez déjà fait du VBA en utilisant l'enregistreur de macros. Pour vous en convaincre, vous allez afficher le code VBA qui correspond à la macroTitre2_vers_Titre3.

Basculez sur l'ongletDéveloppeurdu Ruban, cliquez sur l'icôneMacros, sélectionnez la macroTitre2_vers_Titre3dans la boîte de dialogueMacroset cliquez sur le boutonModifier.
Là, sous vos yeux ébahis, du code s'affiche dans une fenêtre complémentaire :

Sub Titre2_vers_Titre3()
'
' Titre2_vers_Titre3 Macro
'
'
    Selection.Find.ClearFormatting
    Selection.Find.Style = ActiveDocument.Styles("Titre 2")
    Selection.Find.Replacement.ClearFormatting
    Selection.Find.Replacement.Style = ActiveDocument.Styles("Titre 3")
    With Selection.Find
        .Text = ""
        .Replacement.Text = ""
        .Forward = True
        .Wrap = wdFindContinue
        .Format = True
        .MatchCase = False
        .MatchWholeWord = False
        .MatchWildcards = False
        .MatchSoundsLike = False
        .MatchAllWordForms = False
    End With
    Selection.Find.Execute
    With Selection
        If .Find.Forward = True Then
            .Collapse Direction:=wdCollapseStart
        Else
            .Collapse Direction:=wdCollapseEnd
        End If
        .Find.Execute Replace:=wdReplaceOne
        If .Find.Forward = True Then
            .Collapse Direction:=wdCollapseEnd
        Else
            .Collapse Direction:=wdCollapseStart
        End If
        .Find.Execute
    End With
    With Selection
        If .Find.Forward = True Then
            .Collapse Direction:=wdCollapseStart
        Else
            .Collapse Direction:=wdCollapseEnd
        End If
        .Find.Execute Replace:=wdReplaceOne
        If .Find.Forward = True Then
            .Collapse Direction:=wdCollapseEnd
        Else
            .Collapse Direction:=wdCollapseStart
        End If
        .Find.Execute
    End With
    With Selection
        If .Find.Forward = True Then
            .Collapse Direction:=wdCollapseStart
        Else
            .Collapse Direction:=wdCollapseEnd
        End If
        .Find.Execute Replace:=wdReplaceOne
        If .Find.Forward = True Then
            .Collapse Direction:=wdCollapseEnd
        Else
            .Collapse Direction:=wdCollapseStart
        End If
        .Find.Execute
    End With
End Sub

Chaque ligne correspond à une instruction du langage VBA. Ces instructions demandent à Word d'effectuer des actions bien précises sur le document : mettre en exposant, changer le niveau de titre, sélectionner une portion de texte, etc.

Les mots qui composent une instruction comportent une ou parfois plusieurs majuscules, qui sont là pour faciliter leur compréhension et leur lisibilité. Ainsi, le motClearFormattingest composé des motsClearetFormattinget signifie « effacer la mise en forme ». Vous vous demandez certainement pourquoi les motsClearetFormattingn'ont pas été séparés par un espace, comme dans un texte traditionnel. Eh bien, cela vient du fait que le code VBA n'est pas un texte traditionnel : il s'agit d'un ensemble d'instructions destinées à être exécutées par l'ordinateur. Cette syntaxe n'est pas réservée au langage VBA : elle reste valable dans la plupart des langages de programmation.

Structure d'un code VBA

Je vous propose de vous expliquer ici quelques notions de VBA pour vous aider à survivre dans ce milieu à l'apparence hostile. Je ne rentrerai pas dans les détails mais cela sera suffisant pour vous permettre de vous repérer.

Les commentaires

En VBA, il est possible d'insérer des commentaires au milieu de son code ; un commentaire n'est pas pris en compte lorsque le code est exécuté. Vous les repérez facilement, ils commencent par le caractère ', c'est à dire une apostrophe droite (on en voit notamment au début du code précédent).

À quoi servent-ils ? Ce sont des espaces de libre expression (vous pouvez y écrire en français !). Vous pouvez rédiger des commentaires pour expliquer le fonctionnment du code. D'autres personnes pourront ainsi plus rapidement comprendre ce que vous avez voulu faire.

Les procéduresSub

Regardons d'un peu plus près le code qui a été généré par l'enregistreur de macros.
Vous pouvez facilement repérer la macroTitre2_vers_Titre3; elle s'étale entre les lignes suivantes :

Sub Titre2_vers_Titre3()
  …
End Sub

Les motsSubetEnd Subdéfinissent les limites du code associé à la macro et le motTitre2_vers_Titre3est le nom de la macro.

L'ensemble est appelé procédure. C'est un bloc de code qui délimite le début et la fin de la macro.

Et les parenthèses aprèsTitre2_vers_Titre3, c'est juste pour faire joli ?

Eh bien non ! Elles peuvent contenir d'éventuels paramètres transmis à la procédureTitre2_vers_Titre3. Ces paramètres permettent à la procédure de modifier son comportement. Ici, comme aucun paramètre n'est transmis, les parenthèses ne contiennent aucune valeur. L'utilisation de paramètres est un peu avancée pour nous, nous ne nous pencherons donc pas dessus.

Les conditionsIf

Pour permettre au programme de prendre des décisions, on utilise des blocsIfcomme celui-ci :

If .Find.Forward = True Then
    .Collapse Direction:=wdCollapseStart
Else
    .Collapse Direction:=wdCollapseEnd
End If

Ce code peut se traduire de la façon suivante :

Si la condition est respectée Alors
    Faire ceci
Sinon
    Faire cela
Fin de condition

Ici, la condition est « Si on effectue une recherche vers l'avant ».

Ces conditions sont indispensables dans la plupart des programmes. Elles permettent à l'ordinateur de prendre des décisions logiques.

Les blocsWith

Dans le code source, vous pouvez repérer des blocs de code comme celui-ci :

With Selection.Find
    .Text = ""
    .Replacement.Text = ""
    .Forward = True
    .Wrap = wdFindContinue
    .Format = True
    .MatchCase = False
    .MatchWholeWord = False
    .MatchWildcards = False
    .MatchSoundsLike = False
    .MatchAllWordForms = False
End With

Ils commencent parWithet terminent parEnd With. Tout le texte à l'intérieur est indenté, c'est-à-dire décalé vers la droite. Ce décalage n'a pas d'incidence sur le code mais il le rend plus lisible.

Que signifie ce bloc de code qui commence parWith? C'est en fait une façon d'éviter les répétitions dans le code : cela signifie « Avec ». Cela nous évite d'avoir à écrire toujours le même préfixe à chaque ligne :

Selection.Find.Text = ""
Selection.Find.Replacement.Text = ""
Selection.Find.Forward = True
...
Les bouclesFor

Pour répéter plusieurs fois les mêmes instructions, on peut évidemment copier-coller le même code, mais il y a plus efficace : les boucles. C'est un système qui permet de demander à l'ordinateur de répéter plusieurs fois les mêmes actions. La figure suivante illustre ce principe.

Principe de fonctionnement d'une boucle
Principe de fonctionnement d'une boucle

Voici à quoi ressemble une boucle de typeFor(il existe d'autres types de boucles que nous verrons plus loin) :

For i=1 to 10
...
Next i

L'instructionForexécute à dix reprises (i=1 to 10) le code qu'elle renferme, c'est-à-dire le code compris entreFor i=1 to 10etNext i.

Mais que vient faire leidans cette histoire ?

iest une information stockée dans la mémoire de l'ordinateur. On appelle cela une variable. Elle permet à l'ordinateur de compter et donc de se souvenir du nombre d'exécutions de la boucle.

Lors de la première exécution du blocFor Next,ivaut 1. Lors de sa deuxième exécution,ivaut 2. Ainsi de suite, jusqu'à ce queiait pour valeur 10. La boucle est alors exécutée une dernière fois, puis elle se termine et le programme continue avec les instructions qui suivent leNext.

Analyse du code VBA

Le code que nous avons vu plus tôt se décompose en quatre groupes identifiables par leur indentation (c'est-à-dire leur décalage vers la droite). Voici le code du premier groupe :

Selection.Find.ClearFormatting
    Selection.Find.Style = ActiveDocument.Styles("Titre 2")
    Selection.Find.Replacement.ClearFormatting
    Selection.Find.Replacement.Style = ActiveDocument.Styles("Titre 3")
    With Selection.Find
        .Text = ""
        .Replacement.Text = ""
        .Forward = True
        .Wrap = wdFindContinue
        .Format = True
        .MatchCase = False
        .MatchWholeWord = False
        .MatchWildcards = False
        .MatchSoundsLike = False
        .MatchAllWordForms = False
    End With
    Selection.Find.Execute

Sans chercher à comprendre les instructions, vous pouvez assez facilement déduire que le styleTitre 2(Selection.Find.Style = ActiveDocument.Styles("Titre 2")) doit être remplacé par le styleTitre 3(Selection.Find.Replacement.Style = ActiveDocument.Styles("Titre 3")).
Le bloc d'instructions qui s'étend entreWith Selection.FindetEnd Withdéfinit les caractéristiques de la recherche. Au hasard des lignes, vous captez peut-être les mots suivants :

  • Text=""etReplacement.Text="": texte recherché et texte de remplacement ;

  • Forward = True: vers l'avant ;

  • MatchCase = False: insensible à la casse (sans faire de différence entre les majuscules et les minuscules).

Si vous ne comprenez rien à tout cela, ce n'est pas bien grave. Ce qui compte, c'est de pouvoir identifier les blocs d'instructions et de savoir comment les modifier. Si vous avez compris que le premier bloc était à l'origine de la transformation desTitre 2enTitre 3, c'est bien suffisant.

Examinez les trois blocs suivants. Ils sont identiques :

With Selection
    If .Find.Forward = True Then
        .Collapse Direction:=wdCollapseStart
    Else
        .Collapse Direction:=wdCollapseEnd
    End If
    .Find.Execute Replace:=wdReplaceOne
    If .Find.Forward = True Then
        .Collapse Direction:=wdCollapseEnd
    Else
        .Collapse Direction:=wdCollapseStart
    End If
    .Find.Execute
End With

Avez-vous une idée de leur utilité ?
Réfléchissez un peu. L'exercice consistait à effectuer trois remplacements. Il paraît donc logique que chaque bloc soit à l'origine d'un remplacement. Si vous examinez les quelques lignes de ce bloc, vous voyez en particulier l'instructionExecutequi effectue le remplacement :

.Find.Execute Replace:=wdReplaceOne

Ici encore, je vous rassure, il n'est pas nécessaire de comprendre la totalité du code pour pouvoir le modifier. Pour confirmer mes dires, je vais vous demander d'intervenir sur ce code pour effectuer non pas trois mais, disons, dix remplacements. Je vous laisse réfléchir quelques instants…

La première idée qui vient à l'esprit consiste à copier-coller le bloc de code responsable d'un remplacement autant de fois que nécessaire. Sept fois en l'occurrence. Bien qu'un peu lourde, cette solution fonctionne parfaitement. Mais souvenez-vous, nous avons parlé de remplacer les 325 premiers stylesTitre 2. Hors de question de faire autant de copiers-collers !

Ici, nous allons utiliser une boucleFordu typeFor Next. Elle imposera à l'ordinateur d'exécuter ces instructions plusieurs fois.

Voici la totalité du code avec la boucle qui ordonne la répétition :

Sub Titre2_vers_Titre3()
'
' Titre2_vers_Titre3 Macro
'
'
    Selection.Find.ClearFormatting
    Selection.Find.Style = ActiveDocument.Styles("Titre 2")
    Selection.Find.Replacement.ClearFormatting
    Selection.Find.Replacement.Style = ActiveDocument.Styles("Titre 3")
    With Selection.Find
        .Text = ""
        .Replacement.Text = ""
        .Forward = True
        .Wrap = wdFindContinue
        .Format = True
        .MatchCase = False
        .MatchWholeWord = False
        .MatchWildcards = False
        .MatchSoundsLike = False
        .MatchAllWordForms = False
    End With
    Selection.Find.Execute
    For i = 1 To 10
        With Selection
            If .Find.Forward = True Then
                .Collapse Direction:=wdCollapseStart
            Else
                .Collapse Direction:=wdCollapseEnd
            End If
            .Find.Execute Replace:=wdReplaceOne
            If .Find.Forward = True Then
                .Collapse Direction:=wdCollapseEnd
            Else
                .Collapse Direction:=wdCollapseStart
            End If
            .Find.Execute
        End With
    Next i
End Sub

Les boucles sont très importantes en VBA et souvent utilisées pour effectuer des remplacements et mises en forme répétitifs.

VBA et l'autocomplétion

Nous allons voir à travers un exemple que VBA offre de nombreuses possibilités très puissantes. Pour apprendre à les connaître, nous allons utiliser l'autocomplétion.

Vous savez que Word permet d'envoyer par e-mail le document en cours d'édition à un correspondant. Cette technique a déjà été mentionnée dans ce tutoriel mais que diriez-vous cette fois-ci de le faire avec une macro ? Si j'ai choisi cet exemple, c'est pour montrer la puissance du langage VBA : une simple instruction va en effet suffire pour envoyer un e-mail !

Basculez sur l'ongletDéveloppeurpuis cliquez sur l'icôneEnregistrer une macro. Donnez à la macro le nomEnvoiMailet validez en cliquant surOK.
Basculez sur l'ongletFichierdu Ruban. Cliquez surEnregistrer et envoyerpuis surEnvoyer en tant que pièce jointe. Cela crée un nouveau message ayant comme pièce jointe le document en cours d'édition. Cliquez sur l'icôneArrêter l'enregistrementdu groupeCodepour mettre fin à l'enregistrement.
La macro est directement opérationnelle. Examinons le code VBA généré :

Sub EnvoiMail()
'
' EnvoiMail Macro
'
'
    ActiveDocument.SendMail
End Sub

Je ne pense pas qu'il soit nécessaire de donner des précisions. L'unique instruction de cette macro envoie le document grâce àSendMail.

D'accord, VBA est très puissant. Mais existe-t-il d'autres instructions aussi puissantes queSendMail? Et comment en avoir la liste ?

C'est justement ce qui est intéressant. Il est temps pour nous de parler de la magie de l'autocomplétion. Entendez par là la faculté qu'a l'éditeur VBA de proposer des choix adaptés à l'écriture de code en cours. Si tout cela n'est pas clair, placez le point d'insertion après le « l » deSendMailet appuyez sur la touche Entrée. TapezActiveDocumentet faites suivre ce mot d'un point. Immédiatement, une liste de mots-clés vous est proposée, comme à la figure suivante.

L'autocomplétion en pleine action
L'autocomplétion en pleine action

À vous de choisir celui qui correspond à vos besoins. Par exemple :

  • Backgroundagit sur l'arrière-plan du document ;

  • Closeferme le document ;

  • GoTolance la commandeAtteindre(ongletAccueil, groupeModification, icôneRechercher) ;

  • RejectAllRevisionssupprime toutes les marques de révision du document ;

  • Saveenregistre le document ;

  • Undoannule la dernière modification.

Pour choisir un mot, cliquez dessus puis appuyez sur la touche Tab du clavier. Avez-vous remarqué les deux types d'icônes affichées dans la liste ? Les icônes de couleur verte correspondent à des actions et les icônes de couleur grise à des propriétés(voir figure suivante). Vous choisirez les premières pour agir dans le document (exécution d'une instruction, modification d'un élément, envoi d'un e-mail, etc.) et les deuxièmes pour avoir des informations sur le document (nom du thème actif, type d'ombrage, largeur, etc.).

Les actions et les propriétés sont faciles à différencier
Les actions et les propriétés sont faciles à différencier

Certains mots-clés donnent accès à des compléments d'instructions. Par exemple, si vous tapezActiveDocument.Background, ajoutez un point pour accéder à plusieurs autres mots-clés comme à la figure suivante.

Le « . » déclenche l'affichage des mots-clés complémentaires
Le « . » déclenche l'affichage des mots-clés complémentaires

Si vous écrivezActiveDocument.Background.Delete, l'arrière-plan du document sera supprimé.
Si vous n'avez jamais programmé en VBA, tout ceci doit vous sembler assez peu naturel, voire même barbare ! Je vais vous donner un conseil pour progresser dans l'apprentissage de ce langage : utilisez autant que possible l'enregistreur de macros, affichez le code VBA généré et identifiez les différents blocs d'instructions qui le composent. Vous verrez que, petit à petit, les instructions du langage vous deviendront familières. Vous serez rapidement à même de les modifier pour accomplir des tâches qui dépassent les possibilités de l'enregistreur de macros, ou encore d'optimiser le code généré.

Remplacer « m3 » par « m$^3$ »

Les macros et le code VBA sont souvent utilisés pour effectuer des remplacements globaux dans un document. La technique étudiée dans cette section s'intéresse à un remplacement complexe qui combine l'enregistreur de macros et le développement VBA. À vous de la personnaliser pour qu'elle s'adapte aux cas auxquels vous serez confrontés.

Dans un premier temps, nous allons construire la base de la recherche avec l'enregistreur de macros.
Basculez sur l'ongletDéveloppeurdu Ruban et cliquez sur l'icôneEnregistrer une macro. Donnez à la nouvelle macro le nom « m3 » à la nouvelle macro et validez en cliquant surOK.
Basculez sur l'ongletAccueildu Ruban, puis cliquez sur l'icôneRemplacerdans le groupeModification. La boîte de dialogueRechercher et remplacers'ouvre.
Tapez « m3 » dans le champRechercherpuis…

Mais au fait, comment taper « m$^3$ » dans le champRemplacer par? C'est tout bonnement impossible ! Le remplacement global de « m3 » par « m$^3$ » ne pourra donc pas se faire sous l'ongletRemplacer.

Basculez sur l'ongletRechercheret cliquez surSuivant. La première occurrence de « m3 » dans le document est surlignée. Fermez la boîte de dialogueRechercher et remplaceren cliquant sur sa case de fermeture. Nous allons maintenant sélectionner le caractère « 3 ». Appuyez sur la touche Gauche. Le point d'insertion passe à gauche du « m ». Appuyez sur la touche Droite. Le point d'insertion est maintenant devant le « 3 ». Maintenez enfoncée la touche Maj et appuyez sur la touche Droite. Le caractère « 3 » est sélectionné.
L'icôneexposantn'étant pas directement accessible dans le Ruban, vous allez déployer le groupePolicede l'ongletAccueilen cliquant sur la petite icône affichée en bas à droite de ce groupe, comme à la figure suivante. Cochez la caseExposantet validez en cliquant surOK.

Accès à l'icône Exposant
Accès à l'icône Exposant

Vous pouvez maintenant arrêter l'enregistrement de la macro en cliquant sur l'icôneArrêter l'enregistrement.

Avant de poursuivre le développement de la macro, faites-vous plaisir en l'exécutant une fois. Cliquez sur l'icôneMacros, sélectionnez la macrom3et cliquez surExécuter. La macro fonctionne. Par contre, dans son état actuel, vous devrez la lancer plusieurs fois pour que toutes les occurrences de « m3 » du document soient transformés en « m$^3$ ».

L'enregistreur de macros ne peut plus rien pour nous. Voyons s'il est possible d'intervenir dans le code VBA. Cliquez sur l'icôneMacros, sélectionnez la macrom3et cliquez surModifier. Voici le code généré par l'enregistreur de macros :

Sub m3()
'
' m3 Macro
'
'
    Selection.Find.ClearFormatting
    With Selection.Find
        .Text = "m3"
        .Replacement.Text = ""
        .Forward = True
        .Wrap = wdFindContinue
        .Format = False
        .MatchCase = False
        .MatchWholeWord = False
        .MatchWildcards = False
        .MatchSoundsLike = False
        .MatchAllWordForms = False
    End With
    Selection.Find.Execute
    Selection.MoveLeft Unit:=wdCharacter, Count:=1
    Selection.MoveRight Unit:=wdCharacter, Count:=1
    Selection.MoveRight Unit:=wdCharacter, Count:=1, Extend:=wdExtend
    With Selection.Font
        .Name = "+Corps"
        .Size = 11
        .Bold = False
        .Italic = False
        .Underline = wdUnderlineNone
        .UnderlineColor = wdColorAutomatic
        .StrikeThrough = False
        .DoubleStrikeThrough = False
        .Outline = False
        .Emboss = False
        .Shadow = False
        .Hidden = False
        .SmallCaps = False
        .AllCaps = False
        .Color = wdColorAutomatic
        .Engrave = False
        .Superscript = True
        .Subscript = False
        .Spacing = 0
        .Scaling = 100
        .Position = 0
        .Kerning = 0
        .Animation = wdAnimationNone
        .Ligatures = wdLigaturesNone
        .NumberSpacing = wdNumberSpacingDefault
        .NumberForm = wdNumberFormDefault
        .StylisticSet = wdStylisticSetDefault
        .ContextualAlternates = 0
    End With
End Sub

Ne vous laissez pas submerger par l'apparente complexité du code. Ce dernier peut être clairement divisé en trois blocs.

Le premier recherche la prochaine occurrence de « m3 » dans le texte:

Selection.Find.ClearFormatting
    ...
Selection.Find.Execute

Le deuxième sélectionne le caractère « 3 » dans « m3 » :

Selection.MoveLeft Unit:=wdCharacter, Count:=1
...
Selection.MoveRight Unit:=wdCharacter, Count:=1, Extend:=wdExtend

Et enfin le troisième passe le caractère « 3 » en exposant :

With Selection.Font
    ...
End With

Vous voyez, ce n'était pas si difficile. Maintenant, la question est la suivante : comment répéter ces trois blocs d'instructions pour parcourir tout le document ?
Une petite idée ? Avec une boucle bien sûr !

Nous allons encadrer ce code par les instructions suivantes :

While (a<>1)
  'Les trois blocs d'instructions
Wend

Mais qu'est-ce que cea<>1? Et pourquoi une boucleWhile?

La boucleWhileest bien adaptée au traitement répétitif. Elle prend fin lorsqu'une condition n'est plus respectée. Ici, la boucle prend fin lorsqueaest égal à1(a<>1). En effet,While (a<>1)signifie « tant queaest différent de1». Vous vous demandez certainement ce queavient faire là-dedans. Eh bien considérez qu'il s'agit d'un espace dans lequel on peut stocker des valeurs. Pour parler dans le jargon des programmeurs,aest une variable. Étant donné qu'elle n'a pas été définie au préalable, elle sera forcément différente de1lors de l'exécution duWhile. La boucle pourra donc boucler !

Il reste maintenant à pouvoir détecter que tout le document a été parcouru. Pour cela, nous allons insérer les lignes suivantes à la suite duSelection.Find.Execute, c'est-à-dire à la suite de l'instruction qui déclenche la recherche du prochainm3:

If Not (Selection.Find.Found) Then
    a = 1
End If

Est-ce que vous comprenez l'intérêt de cette instruction ? Si on la traduisait en langage compréhensible, nous obtiendrions ceci : si la sélection (If Selection.Find.Found) ne trouve rien (Not), la valeur1est enregistrée dans la variablea(a = 1). La boucleWhileprendra donc fin à sa prochaine exécution, puisqueaest égal à1.

Si aucune occurrence dem3n'est trouvé, les lignes suivantes ne doivent pas être exécutées. En effet, dans ce cas, il n'y a aucun3à sélectionner et à mettre en exposant. Mais alors, que faire ?

L'idéal serait d'utiliser un test du type « S'il n'y a plus de m3 dans le texte, mettre fin au traitement, sinon, poursuivre le traitement ». Par chance, ce test existe dans le langage VBA. Vous devez pour cela utiliser l'instructionIf condition Then action1 Else action2 End If. La condition est la même que dans l'étape précédente :Not (Selection.Find.Found). La première action consiste à enregistrer la valeur1dans la variablea. La deuxième action consiste à exécuter toutes les instructions qui suivent, c'est-à-dire à remplacer le3par un « 3 ». Le code prend donc la forme suivante :

Selection.Find.Execute
    If Not (Selection.Find.Found) Then
        a = 1
    Else
            Selection.MoveLeft Unit:=wdCharacter, Count:=1
            …
            .ContextualAlternates = 0
        End With
    End If
    Wend

Ainsi, les deuxième et troisième blocs de code ne seront exécutés que dans le cas où unm3est trouvé.
Votre code devrait maintenant ressembler à ceci :

Sub m3()
'
' m3 Macro
'
'
    While (a <> 1)
    Selection.Find.ClearFormatting
    With Selection.Find
        .Text = "m3"
        .Replacement.Text = "m3"
        .Forward = True
        .Wrap = wdFindContinue
        .Format = False
        .MatchCase = False
        .MatchWholeWord = False
        .MatchWildcards = False
        .MatchSoundsLike = False
        .MatchAllWordForms = False
    End With
    Selection.Find.Execute
    If Not (Selection.Find.Found) Then
        a = 1
    Else
        Selection.MoveLeft Unit:=wdCharacter, Count:=1
        Selection.MoveRight Unit:=wdCharacter, Count:=1
        Selection.MoveRight Unit:=wdCharacter, Count:=1, Extend:=wdExtend
        With Selection.Font
            .Name = "+Corps"
            .Size = 11
            .Bold = False
            .Italic = False
            .Underline = wdUnderlineNone
            .UnderlineColor = wdColorAutomatic
            .StrikeThrough = False
            .DoubleStrikeThrough = False
            .Outline = False
            .Emboss = False
            .Shadow = False
            .Hidden = False
            .SmallCaps = False
            .AllCaps = False
            .Color = wdColorAutomatic
            .Engrave = False
            .Superscript = True
            .Subscript = False
            .Spacing = 0
            .Scaling = 100
            .Position = 0
            .Kerning = 0
            .Animation = wdAnimationNone
            .Ligatures = wdLigaturesNone
            .NumberSpacing = wdNumberSpacingDefault
            .NumberForm = wdNumberFormDefault
            .StylisticSet = wdStylisticSetDefault
            .ContextualAlternates = 0
        End With
    End If
    Wend
End Sub

Enregistrez-le avec la commandeEnregistrer Normaldans le menuFichier, fermez la fenêtreMicrosoft Visual Basic pour Applicationset exécutez la macro dans votre document.

Catastrophe ! Le code s'exécute indéfiniment. Et ce, malgré la logique mise en place ! Le problème ne vient pas duIf, mais d'un paramètre bien caché dans le premier bloc d'instructions. Aviez-vous remarqué la ligne suivante :

.Wrap = wdFindContinue

La valeurwdFindContinuedemande à Word de poursuivre la recherche une fois qu'il est arrivé à la fin du document. Remplacez-la parwdFindAsk, enregistrez le code et exécutez-le. Hourra ! Le document est parcouru, puis une boîte de dialogue vous demande si la recherche doit recommencer depuis le début (voir figure suivante). Cliquez surNonpour mettre fin au code VBA.

Une boîte de dialogue est affichée lorsque la fin du document est atteinte
Une boîte de dialogue est affichée lorsque la fin du document est atteinte

Pour ceux d'entre vous qui voudraient aller plus loin et qui comprennent l'anglais, je vous conseille l'excellent siteMicrosoft Word MVP FAQ Site. Vous y trouverez de nombreux exemples de macros et de code VBA qui vous permettront de progresser dans votre apprentissage.

Microsoft Word FAQ

En résumé

  • Les macros font gagner beaucoup de temps dans les traitements répétitifs ou complexes. Pour créer une nouvelle macro, vous utiliserez l'enregistreur de macros de Word.

  • Pour faciliter leur exécution, il est possible d'affecter des raccourcis clavier aux macros que vous utilisez le plus souvent ou de leur associer des icônes dans la barre d'outilsAccès rapide.

  • Il est possible d'exécuter automatiquement une macro en lui donnant un nom réservé :AutoExec(au lancement de Word),AutoNew(à la création d'un nouveau document),AutoOpen(à l'ouverture d'un document existant),AutoClose(à la fermeture d'un document) ouAutoExit(à la fermeture de Word).

  • Lorsque les macros montrent leurs limites, vous pouvez éditer le code VBA généré par l'enregistreur de macros.

  • Les instructions de testIf Then Elseet les bouclesWhile Wendfacilitent l'exécution sélective et répétitive du code afin d'appliquer un traitement à des éléments qui vérifient une ou plusieurs conditions.

Exemple de certificat de réussite
Exemple de certificat de réussite